summaryrefslogtreecommitdiff
path: root/xenserver
diff options
context:
space:
mode:
authorGreg Rose <gvrose8192@gmail.com>2022-08-08 13:36:02 -0700
committerIlya Maximets <i.maximets@ovn.org>2022-08-15 13:07:13 +0200
commit83c9518e7c67fb73ab17f6db50f398dc78403814 (patch)
tree7290abe2d043c4f30d55975f6f2d25608a9feadc /xenserver
parentac1332216eb3a1857b942457e1b44a22512b092d (diff)
downloadopenvswitch-83c9518e7c67fb73ab17f6db50f398dc78403814.tar.gz
xenserver: Remove xenserver.
Remove the current xenserver implementation - it is obsolete and since 3.0 we do not support kernel module builds [1]. 1. https://mail.openvswitch.org/pipermail/ovs-dev/2022-July/395789.html [i.maximets] Can be added back if people willing to maintain it will be found. Signed-off-by: Greg Rose <gvrose8192@gmail.com> Signed-off-by: Ilya Maximets <i.maximets@ovn.org>
Diffstat (limited to 'xenserver')
-rw-r--r--xenserver/.gitignore1
-rw-r--r--xenserver/GPLv2339
-rw-r--r--xenserver/LICENSE518
-rw-r--r--xenserver/README.rst175
-rw-r--r--xenserver/automake.mk35
-rwxr-xr-xxenserver/etc_init.d_openvswitch154
-rwxr-xr-xxenserver/etc_init.d_openvswitch-xapi-update80
-rw-r--r--xenserver/etc_logrotate.d_openvswitch21
-rw-r--r--xenserver/etc_profile.d_openvswitch.sh48
-rwxr-xr-xxenserver/etc_xapi.d_plugins_openvswitch-cfg-update269
-rwxr-xr-xxenserver/etc_xensource_scripts_vif265
-rw-r--r--xenserver/openvswitch-xen.spec.in512
-rw-r--r--xenserver/opt_xensource_libexec_InterfaceReconfigure.py972
-rw-r--r--xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py476
-rw-r--r--xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py724
-rwxr-xr-xxenserver/opt_xensource_libexec_interface-reconfigure739
-rw-r--r--xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py331
-rwxr-xr-xxenserver/usr_share_openvswitch_scripts_ovs-xapi-sync404
-rw-r--r--xenserver/usr_share_openvswitch_scripts_sysconfig.template24
19 files changed, 0 insertions, 6087 deletions
diff --git a/xenserver/.gitignore b/xenserver/.gitignore
deleted file mode 100644
index 3679eea07..000000000
--- a/xenserver/.gitignore
+++ /dev/null
@@ -1 +0,0 @@
-/openvswitch-xen.spec
diff --git a/xenserver/GPLv2 b/xenserver/GPLv2
deleted file mode 100644
index d511905c1..000000000
--- a/xenserver/GPLv2
+++ /dev/null
@@ -1,339 +0,0 @@
- GNU GENERAL PUBLIC LICENSE
- Version 2, June 1991
-
- Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
- Preamble
-
- The licenses for most software are designed to take away your
-freedom to share and change it. By contrast, the GNU General Public
-License is intended to guarantee your freedom to share and change free
-software--to make sure the software is free for all its users. This
-General Public License applies to most of the Free Software
-Foundation's software and to any other program whose authors commit to
-using it. (Some other Free Software Foundation software is covered by
-the GNU Lesser General Public License instead.) You can apply it to
-your programs, too.
-
- When we speak of free software, we are referring to freedom, not
-price. Our General Public Licenses are designed to make sure that you
-have the freedom to distribute copies of free software (and charge for
-this service if you wish), that you receive source code or can get it
-if you want it, that you can change the software or use pieces of it
-in new free programs; and that you know you can do these things.
-
- To protect your rights, we need to make restrictions that forbid
-anyone to deny you these rights or to ask you to surrender the rights.
-These restrictions translate to certain responsibilities for you if you
-distribute copies of the software, or if you modify it.
-
- For example, if you distribute copies of such a program, whether
-gratis or for a fee, you must give the recipients all the rights that
-you have. You must make sure that they, too, receive or can get the
-source code. And you must show them these terms so they know their
-rights.
-
- We protect your rights with two steps: (1) copyright the software, and
-(2) offer you this license which gives you legal permission to copy,
-distribute and/or modify the software.
-
- Also, for each author's protection and ours, we want to make certain
-that everyone understands that there is no warranty for this free
-software. If the software is modified by someone else and passed on, we
-want its recipients to know that what they have is not the original, so
-that any problems introduced by others will not reflect on the original
-authors' reputations.
-
- Finally, any free program is threatened constantly by software
-patents. We wish to avoid the danger that redistributors of a free
-program will individually obtain patent licenses, in effect making the
-program proprietary. To prevent this, we have made it clear that any
-patent must be licensed for everyone's free use or not licensed at all.
-
- The precise terms and conditions for copying, distribution and
-modification follow.
-
- GNU GENERAL PUBLIC LICENSE
- TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
- 0. This License applies to any program or other work which contains
-a notice placed by the copyright holder saying it may be distributed
-under the terms of this General Public License. The "Program", below,
-refers to any such program or work, and a "work based on the Program"
-means either the Program or any derivative work under copyright law:
-that is to say, a work containing the Program or a portion of it,
-either verbatim or with modifications and/or translated into another
-language. (Hereinafter, translation is included without limitation in
-the term "modification".) Each licensee is addressed as "you".
-
-Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope. The act of
-running the Program is not restricted, and the output from the Program
-is covered only if its contents constitute a work based on the
-Program (independent of having been made by running the Program).
-Whether that is true depends on what the Program does.
-
- 1. You may copy and distribute verbatim copies of the Program's
-source code as you receive it, in any medium, provided that you
-conspicuously and appropriately publish on each copy an appropriate
-copyright notice and disclaimer of warranty; keep intact all the
-notices that refer to this License and to the absence of any warranty;
-and give any other recipients of the Program a copy of this License
-along with the Program.
-
-You may charge a fee for the physical act of transferring a copy, and
-you may at your option offer warranty protection in exchange for a fee.
-
- 2. You may modify your copy or copies of the Program or any portion
-of it, thus forming a work based on the Program, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
- a) You must cause the modified files to carry prominent notices
- stating that you changed the files and the date of any change.
-
- b) You must cause any work that you distribute or publish, that in
- whole or in part contains or is derived from the Program or any
- part thereof, to be licensed as a whole at no charge to all third
- parties under the terms of this License.
-
- c) If the modified program normally reads commands interactively
- when run, you must cause it, when started running for such
- interactive use in the most ordinary way, to print or display an
- announcement including an appropriate copyright notice and a
- notice that there is no warranty (or else, saying that you provide
- a warranty) and that users may redistribute the program under
- these conditions, and telling the user how to view a copy of this
- License. (Exception: if the Program itself is interactive but
- does not normally print such an announcement, your work based on
- the Program is not required to print an announcement.)
-
-These requirements apply to the modified work as a whole. If
-identifiable sections of that work are not derived from the Program,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works. But when you
-distribute the same sections as part of a whole which is a work based
-on the Program, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Program.
-
-In addition, mere aggregation of another work not based on the Program
-with the Program (or with a work based on the Program) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
- 3. You may copy and distribute the Program (or a work based on it,
-under Section 2) in object code or executable form under the terms of
-Sections 1 and 2 above provided that you also do one of the following:
-
- a) Accompany it with the complete corresponding machine-readable
- source code, which must be distributed under the terms of Sections
- 1 and 2 above on a medium customarily used for software interchange; or,
-
- b) Accompany it with a written offer, valid for at least three
- years, to give any third party, for a charge no more than your
- cost of physically performing source distribution, a complete
- machine-readable copy of the corresponding source code, to be
- distributed under the terms of Sections 1 and 2 above on a medium
- customarily used for software interchange; or,
-
- c) Accompany it with the information you received as to the offer
- to distribute corresponding source code. (This alternative is
- allowed only for noncommercial distribution and only if you
- received the program in object code or executable form with such
- an offer, in accord with Subsection b above.)
-
-The source code for a work means the preferred form of the work for
-making modifications to it. For an executable work, complete source
-code means all the source code for all modules it contains, plus any
-associated interface definition files, plus the scripts used to
-control compilation and installation of the executable. However, as a
-special exception, the source code distributed need not include
-anything that is normally distributed (in either source or binary
-form) with the major components (compiler, kernel, and so on) of the
-operating system on which the executable runs, unless that component
-itself accompanies the executable.
-
-If distribution of executable or object code is made by offering
-access to copy from a designated place, then offering equivalent
-access to copy the source code from the same place counts as
-distribution of the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
- 4. You may not copy, modify, sublicense, or distribute the Program
-except as expressly provided under this License. Any attempt
-otherwise to copy, modify, sublicense or distribute the Program is
-void, and will automatically terminate your rights under this License.
-However, parties who have received copies, or rights, from you under
-this License will not have their licenses terminated so long as such
-parties remain in full compliance.
-
- 5. You are not required to accept this License, since you have not
-signed it. However, nothing else grants you permission to modify or
-distribute the Program or its derivative works. These actions are
-prohibited by law if you do not accept this License. Therefore, by
-modifying or distributing the Program (or any work based on the
-Program), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Program or works based on it.
-
- 6. Each time you redistribute the Program (or any work based on the
-Program), the recipient automatically receives a license from the
-original licensor to copy, distribute or modify the Program subject to
-these terms and conditions. You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties to
-this License.
-
- 7. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License. If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Program at all. For example, if a patent
-license would not permit royalty-free redistribution of the Program by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Program.
-
-If any portion of this section is held invalid or unenforceable under
-any particular circumstance, the balance of the section is intended to
-apply and the section as a whole is intended to apply in other
-circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system, which is
-implemented by public license practices. Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
- 8. If the distribution and/or use of the Program is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Program under this License
-may add an explicit geographical distribution limitation excluding
-those countries, so that distribution is permitted only in or among
-countries not thus excluded. In such case, this License incorporates
-the limitation as if written in the body of this License.
-
- 9. The Free Software Foundation may publish revised and/or new versions
-of the General Public License from time to time. Such new versions will
-be similar in spirit to the present version, but may differ in detail to
-address new problems or concerns.
-
-Each version is given a distinguishing version number. If the Program
-specifies a version number of this License which applies to it and "any
-later version", you have the option of following the terms and conditions
-either of that version or of any later version published by the Free
-Software Foundation. If the Program does not specify a version number of
-this License, you may choose any version ever published by the Free Software
-Foundation.
-
- 10. If you wish to incorporate parts of the Program into other free
-programs whose distribution conditions are different, write to the author
-to ask for permission. For software which is copyrighted by the Free
-Software Foundation, write to the Free Software Foundation; we sometimes
-make exceptions for this. Our decision will be guided by the two goals
-of preserving the free status of all derivatives of our free software and
-of promoting the sharing and reuse of software generally.
-
- NO WARRANTY
-
- 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
-FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
-OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
-PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
-OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
-MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
-TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
-PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
-REPAIR OR CORRECTION.
-
- 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
-WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
-REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
-INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
-OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
-TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
-YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
-PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
-POSSIBILITY OF SUCH DAMAGES.
-
- END OF TERMS AND CONDITIONS
-
- How to Apply These Terms to Your New Programs
-
- If you develop a new program, and you want it to be of the greatest
-possible use to the public, the best way to achieve this is to make it
-free software which everyone can redistribute and change under these terms.
-
- To do so, attach the following notices to the program. It is safest
-to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least
-the "copyright" line and a pointer to where the full notice is found.
-
- <one line to give the program's name and a brief idea of what it does.>
- Copyright (C) <year> <name of author>
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License along
- with this program; if not, write to the Free Software Foundation, Inc.,
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
-
-Also add information on how to contact you by electronic and paper mail.
-
-If the program is interactive, make it output a short notice like this
-when it starts in an interactive mode:
-
- Gnomovision version 69, Copyright (C) year name of author
- Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
- This is free software, and you are welcome to redistribute it
- under certain conditions; type `show c' for details.
-
-The hypothetical commands `show w' and `show c' should show the appropriate
-parts of the General Public License. Of course, the commands you use may
-be called something other than `show w' and `show c'; they could even be
-mouse-clicks or menu items--whatever suits your program.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the program, if
-necessary. Here is a sample; alter the names:
-
- Yoyodyne, Inc., hereby disclaims all copyright interest in the program
- `Gnomovision' (which makes passes at compilers) written by James Hacker.
-
- <signature of Ty Coon>, 1 April 1989
- Ty Coon, President of Vice
-
-This General Public License does not permit incorporating your program into
-proprietary programs. If your program is a subroutine library, you may
-consider it more useful to permit linking proprietary applications with the
-library. If this is what you want to do, use the GNU Lesser General
-Public License instead of this License.
diff --git a/xenserver/LICENSE b/xenserver/LICENSE
deleted file mode 100644
index 00fc4d8cb..000000000
--- a/xenserver/LICENSE
+++ /dev/null
@@ -1,518 +0,0 @@
-As a special exception to the GNU Lesser General Public License, you
-may link, statically or dynamically, a "work that uses the Library"
-with a publicly distributed version of the Library to produce an
-executable file containing portions of the Library, and distribute
-that executable file under terms of your choice, without any of the
-additional requirements listed in clause 6 of the GNU Lesser General
-Public License. By "a publicly distributed version of the Library",
-we mean either the unmodified Library as distributed, or a
-modified version of the Library that is distributed under the
-conditions defined in clause 3 of the GNU Library General Public
-License. This exception does not however invalidate any other reasons
-why the executable file might be covered by the GNU Lesser General
-Public License.
-
-------------
-
- GNU LESSER GENERAL PUBLIC LICENSE
- Version 2.1, February 1999
-
- Copyright (C) 1991, 1999 Free Software Foundation, Inc.
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
-[This is the first released version of the Lesser GPL. It also counts
- as the successor of the GNU Library Public License, version 2, hence
- the version number 2.1.]
-
- Preamble
-
- The licenses for most software are designed to take away your
-freedom to share and change it. By contrast, the GNU General Public
-Licenses are intended to guarantee your freedom to share and change
-free software--to make sure the software is free for all its users.
-
- This license, the Lesser General Public License, applies to some
-specially designated software packages--typically libraries--of the
-Free Software Foundation and other authors who decide to use it. You
-can use it too, but we suggest you first think carefully about whether
-this license or the ordinary General Public License is the better
-strategy to use in any particular case, based on the explanations below.
-
- When we speak of free software, we are referring to freedom of use,
-not price. Our General Public Licenses are designed to make sure that
-you have the freedom to distribute copies of free software (and charge
-for this service if you wish); that you receive source code or can get
-it if you want it; that you can change the software and use pieces of
-it in new free programs; and that you are informed that you can do
-these things.
-
- To protect your rights, we need to make restrictions that forbid
-distributors to deny you these rights or to ask you to surrender these
-rights. These restrictions translate to certain responsibilities for
-you if you distribute copies of the library or if you modify it.
-
- For example, if you distribute copies of the library, whether gratis
-or for a fee, you must give the recipients all the rights that we gave
-you. You must make sure that they, too, receive or can get the source
-code. If you link other code with the library, you must provide
-complete object files to the recipients, so that they can relink them
-with the library after making changes to the library and recompiling
-it. And you must show them these terms so they know their rights.
-
- We protect your rights with a two-step method: (1) we copyright the
-library, and (2) we offer you this license, which gives you legal
-permission to copy, distribute and/or modify the library.
-
- To protect each distributor, we want to make it very clear that
-there is no warranty for the free library. Also, if the library is
-modified by someone else and passed on, the recipients should know
-that what they have is not the original version, so that the original
-author's reputation will not be affected by problems that might be
-introduced by others.
-
- Finally, software patents pose a constant threat to the existence of
-any free program. We wish to make sure that a company cannot
-effectively restrict the users of a free program by obtaining a
-restrictive license from a patent holder. Therefore, we insist that
-any patent license obtained for a version of the library must be
-consistent with the full freedom of use specified in this license.
-
- Most GNU software, including some libraries, is covered by the
-ordinary GNU General Public License. This license, the GNU Lesser
-General Public License, applies to certain designated libraries, and
-is quite different from the ordinary General Public License. We use
-this license for certain libraries in order to permit linking those
-libraries into non-free programs.
-
- When a program is linked with a library, whether statically or using
-a shared library, the combination of the two is legally speaking a
-combined work, a derivative of the original library. The ordinary
-General Public License therefore permits such linking only if the
-entire combination fits its criteria of freedom. The Lesser General
-Public License permits more lax criteria for linking other code with
-the library.
-
- We call this license the "Lesser" General Public License because it
-does Less to protect the user's freedom than the ordinary General
-Public License. It also provides other free software developers Less
-of an advantage over competing non-free programs. These disadvantages
-are the reason we use the ordinary General Public License for many
-libraries. However, the Lesser license provides advantages in certain
-special circumstances.
-
- For example, on rare occasions, there may be a special need to
-encourage the widest possible use of a certain library, so that it becomes
-a de-facto standard. To achieve this, non-free programs must be
-allowed to use the library. A more frequent case is that a free
-library does the same job as widely used non-free libraries. In this
-case, there is little to gain by limiting the free library to free
-software only, so we use the Lesser General Public License.
-
- In other cases, permission to use a particular library in non-free
-programs enables a greater number of people to use a large body of
-free software. For example, permission to use the GNU C Library in
-non-free programs enables many more people to use the whole GNU
-operating system, as well as its variant, the GNU/Linux operating
-system.
-
- Although the Lesser General Public License is Less protective of the
-users' freedom, it does ensure that the user of a program that is
-linked with the Library has the freedom and the wherewithal to run
-that program using a modified version of the Library.
-
- The precise terms and conditions for copying, distribution and
-modification follow. Pay close attention to the difference between a
-"work based on the library" and a "work that uses the library". The
-former contains code derived from the library, whereas the latter must
-be combined with the library in order to run.
-
- GNU LESSER GENERAL PUBLIC LICENSE
- TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
- 0. This License Agreement applies to any software library or other
-program which contains a notice placed by the copyright holder or
-other authorized party saying it may be distributed under the terms of
-this Lesser General Public License (also called "this License").
-Each licensee is addressed as "you".
-
- A "library" means a collection of software functions and/or data
-prepared so as to be conveniently linked with application programs
-(which use some of those functions and data) to form executables.
-
- The "Library", below, refers to any such software library or work
-which has been distributed under these terms. A "work based on the
-Library" means either the Library or any derivative work under
-copyright law: that is to say, a work containing the Library or a
-portion of it, either verbatim or with modifications and/or translated
-straightforwardly into another language. (Hereinafter, translation is
-included without limitation in the term "modification".)
-
- "Source code" for a work means the preferred form of the work for
-making modifications to it. For a library, complete source code means
-all the source code for all modules it contains, plus any associated
-interface definition files, plus the scripts used to control compilation
-and installation of the library.
-
- Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope. The act of
-running a program using the Library is not restricted, and output from
-such a program is covered only if its contents constitute a work based
-on the Library (independent of the use of the Library in a tool for
-writing it). Whether that is true depends on what the Library does
-and what the program that uses the Library does.
-
- 1. You may copy and distribute verbatim copies of the Library's
-complete source code as you receive it, in any medium, provided that
-you conspicuously and appropriately publish on each copy an
-appropriate copyright notice and disclaimer of warranty; keep intact
-all the notices that refer to this License and to the absence of any
-warranty; and distribute a copy of this License along with the
-Library.
-
- You may charge a fee for the physical act of transferring a copy,
-and you may at your option offer warranty protection in exchange for a
-fee.
-
- 2. You may modify your copy or copies of the Library or any portion
-of it, thus forming a work based on the Library, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
- a) The modified work must itself be a software library.
-
- b) You must cause the files modified to carry prominent notices
- stating that you changed the files and the date of any change.
-
- c) You must cause the whole of the work to be licensed at no
- charge to all third parties under the terms of this License.
-
- d) If a facility in the modified Library refers to a function or a
- table of data to be supplied by an application program that uses
- the facility, other than as an argument passed when the facility
- is invoked, then you must make a good faith effort to ensure that,
- in the event an application does not supply such function or
- table, the facility still operates, and performs whatever part of
- its purpose remains meaningful.
-
- (For example, a function in a library to compute square roots has
- a purpose that is entirely well-defined independent of the
- application. Therefore, Subsection 2d requires that any
- application-supplied function or table used by this function must
- be optional: if the application does not supply it, the square
- root function must still compute square roots.)
-
-These requirements apply to the modified work as a whole. If
-identifiable sections of that work are not derived from the Library,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works. But when you
-distribute the same sections as part of a whole which is a work based
-on the Library, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote
-it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Library.
-
-In addition, mere aggregation of another work not based on the Library
-with the Library (or with a work based on the Library) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
- 3. You may opt to apply the terms of the ordinary GNU General Public
-License instead of this License to a given copy of the Library. To do
-this, you must alter all the notices that refer to this License, so
-that they refer to the ordinary GNU General Public License, version 2,
-instead of to this License. (If a newer version than version 2 of the
-ordinary GNU General Public License has appeared, then you can specify
-that version instead if you wish.) Do not make any other change in
-these notices.
-
- Once this change is made in a given copy, it is irreversible for
-that copy, so the ordinary GNU General Public License applies to all
-subsequent copies and derivative works made from that copy.
-
- This option is useful when you wish to copy part of the code of
-the Library into a program that is not a library.
-
- 4. You may copy and distribute the Library (or a portion or
-derivative of it, under Section 2) in object code or executable form
-under the terms of Sections 1 and 2 above provided that you accompany
-it with the complete corresponding machine-readable source code, which
-must be distributed under the terms of Sections 1 and 2 above on a
-medium customarily used for software interchange.
-
- If distribution of object code is made by offering access to copy
-from a designated place, then offering equivalent access to copy the
-source code from the same place satisfies the requirement to
-distribute the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
- 5. A program that contains no derivative of any portion of the
-Library, but is designed to work with the Library by being compiled or
-linked with it, is called a "work that uses the Library". Such a
-work, in isolation, is not a derivative work of the Library, and
-therefore falls outside the scope of this License.
-
- However, linking a "work that uses the Library" with the Library
-creates an executable that is a derivative of the Library (because it
-contains portions of the Library), rather than a "work that uses the
-library". The executable is therefore covered by this License.
-Section 6 states terms for distribution of such executables.
-
- When a "work that uses the Library" uses material from a header file
-that is part of the Library, the object code for the work may be a
-derivative work of the Library even though the source code is not.
-Whether this is true is especially significant if the work can be
-linked without the Library, or if the work is itself a library. The
-threshold for this to be true is not precisely defined by law.
-
- If such an object file uses only numerical parameters, data
-structure layouts and accessors, and small macros and small inline
-functions (ten lines or less in length), then the use of the object
-file is unrestricted, regardless of whether it is legally a derivative
-work. (Executables containing this object code plus portions of the
-Library will still fall under Section 6.)
-
- Otherwise, if the work is a derivative of the Library, you may
-distribute the object code for the work under the terms of Section 6.
-Any executables containing that work also fall under Section 6,
-whether or not they are linked directly with the Library itself.
-
- 6. As an exception to the Sections above, you may also combine or
-link a "work that uses the Library" with the Library to produce a
-work containing portions of the Library, and distribute that work
-under terms of your choice, provided that the terms permit
-modification of the work for the customer's own use and reverse
-engineering for debugging such modifications.
-
- You must give prominent notice with each copy of the work that the
-Library is used in it and that the Library and its use are covered by
-this License. You must supply a copy of this License. If the work
-during execution displays copyright notices, you must include the
-copyright notice for the Library among them, as well as a reference
-directing the user to the copy of this License. Also, you must do one
-of these things:
-
- a) Accompany the work with the complete corresponding
- machine-readable source code for the Library including whatever
- changes were used in the work (which must be distributed under
- Sections 1 and 2 above); and, if the work is an executable linked
- with the Library, with the complete machine-readable "work that
- uses the Library", as object code and/or source code, so that the
- user can modify the Library and then relink to produce a modified
- executable containing the modified Library. (It is understood
- that the user who changes the contents of definitions files in the
- Library will not necessarily be able to recompile the application
- to use the modified definitions.)
-
- b) Use a suitable shared library mechanism for linking with the
- Library. A suitable mechanism is one that (1) uses at run time a
- copy of the library already present on the user's computer system,
- rather than copying library functions into the executable, and (2)
- will operate properly with a modified version of the library, if
- the user installs one, as long as the modified version is
- interface-compatible with the version that the work was made with.
-
- c) Accompany the work with a written offer, valid for at
- least three years, to give the same user the materials
- specified in Subsection 6a, above, for a charge no more
- than the cost of performing this distribution.
-
- d) If distribution of the work is made by offering access to copy
- from a designated place, offer equivalent access to copy the above
- specified materials from the same place.
-
- e) Verify that the user has already received a copy of these
- materials or that you have already sent this user a copy.
-
- For an executable, the required form of the "work that uses the
-Library" must include any data and utility programs needed for
-reproducing the executable from it. However, as a special exception,
-the materials to be distributed need not include anything that is
-normally distributed (in either source or binary form) with the major
-components (compiler, kernel, and so on) of the operating system on
-which the executable runs, unless that component itself accompanies
-the executable.
-
- It may happen that this requirement contradicts the license
-restrictions of other proprietary libraries that do not normally
-accompany the operating system. Such a contradiction means you cannot
-use both them and the Library together in an executable that you
-distribute.
-
- 7. You may place library facilities that are a work based on the
-Library side-by-side in a single library together with other library
-facilities not covered by this License, and distribute such a combined
-library, provided that the separate distribution of the work based on
-the Library and of the other library facilities is otherwise
-permitted, and provided that you do these two things:
-
- a) Accompany the combined library with a copy of the same work
- based on the Library, uncombined with any other library
- facilities. This must be distributed under the terms of the
- Sections above.
-
- b) Give prominent notice with the combined library of the fact
- that part of it is a work based on the Library, and explaining
- where to find the accompanying uncombined form of the same work.
-
- 8. You may not copy, modify, sublicense, link with, or distribute
-the Library except as expressly provided under this License. Any
-attempt otherwise to copy, modify, sublicense, link with, or
-distribute the Library is void, and will automatically terminate your
-rights under this License. However, parties who have received copies,
-or rights, from you under this License will not have their licenses
-terminated so long as such parties remain in full compliance.
-
- 9. You are not required to accept this License, since you have not
-signed it. However, nothing else grants you permission to modify or
-distribute the Library or its derivative works. These actions are
-prohibited by law if you do not accept this License. Therefore, by
-modifying or distributing the Library (or any work based on the
-Library), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Library or works based on it.
-
- 10. Each time you redistribute the Library (or any work based on the
-Library), the recipient automatically receives a license from the
-original licensor to copy, distribute, link with or modify the Library
-subject to these terms and conditions. You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties with
-this License.
-
- 11. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License. If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Library at all. For example, if a patent
-license would not permit royalty-free redistribution of the Library by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Library.
-
-If any portion of this section is held invalid or unenforceable under any
-particular circumstance, the balance of the section is intended to apply,
-and the section as a whole is intended to apply in other circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system which is
-implemented by public license practices. Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
- 12. If the distribution and/or use of the Library is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Library under this License may add
-an explicit geographical distribution limitation excluding those countries,
-so that distribution is permitted only in or among countries not thus
-excluded. In such case, this License incorporates the limitation as if
-written in the body of this License.
-
- 13. The Free Software Foundation may publish revised and/or new
-versions of the Lesser General Public License from time to time.
-Such new versions will be similar in spirit to the present version,
-but may differ in detail to address new problems or concerns.
-
-Each version is given a distinguishing version number. If the Library
-specifies a version number of this License which applies to it and
-"any later version", you have the option of following the terms and
-conditions either of that version or of any later version published by
-the Free Software Foundation. If the Library does not specify a
-license version number, you may choose any version ever published by
-the Free Software Foundation.
-
- 14. If you wish to incorporate parts of the Library into other free
-programs whose distribution conditions are incompatible with these,
-write to the author to ask for permission. For software which is
-copyrighted by the Free Software Foundation, write to the Free
-Software Foundation; we sometimes make exceptions for this. Our
-decision will be guided by the two goals of preserving the free status
-of all derivatives of our free software and of promoting the sharing
-and reuse of software generally.
-
- NO WARRANTY
-
- 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
-WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
-EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
-OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
-KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
-IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
-PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
-LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
-THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
-
- 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
-WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
-AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
-FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
-CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
-LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
-RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
-FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
-SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
-DAMAGES.
-
- END OF TERMS AND CONDITIONS
-
- How to Apply These Terms to Your New Libraries
-
- If you develop a new library, and you want it to be of the greatest
-possible use to the public, we recommend making it free software that
-everyone can redistribute and change. You can do so by permitting
-redistribution under these terms (or, alternatively, under the terms of the
-ordinary General Public License).
-
- To apply these terms, attach the following notices to the library. It is
-safest to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least the
-"copyright" line and a pointer to where the full notice is found.
-
- <one line to give the library's name and a brief idea of what it does.>
- Copyright (C) <year> <name of author>
-
- This library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- This library is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with this library; if not, write to the Free Software
- Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
-
-Also add information on how to contact you by electronic and paper mail.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the library, if
-necessary. Here is a sample; alter the names:
-
- Yoyodyne, Inc., hereby disclaims all copyright interest in the
- library `Frob' (a library for tweaking knobs) written by James Random Hacker.
-
- <signature of Ty Coon>, 1 April 1990
- Ty Coon, President of Vice
-
-That's all there is to it!
diff --git a/xenserver/README.rst b/xenserver/README.rst
deleted file mode 100644
index c30805fc3..000000000
--- a/xenserver/README.rst
+++ /dev/null
@@ -1,175 +0,0 @@
-..
- Copyright (C) 2009, 2010, 2011 Nicira, Inc.
-
- Licensed under the Apache License, Version 2.0 (the "License"); you may
- not use this file except in compliance with the License. You may obtain
- a copy of the License at
-
- http://www.apache.org/licenses/LICENSE-2.0
-
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
- WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
- License for the specific language governing permissions and limitations
- under the License.
-
- Convention for heading levels in Open vSwitch documentation:
-
- ======= Heading 0 (reserved for the title in a document)
- ------- Heading 1
- ~~~~~~~ Heading 2
- +++++++ Heading 3
- ''''''' Heading 4
-
- Avoid deeper levels because they do not render well.
-
-================
-XenServer README
-================
-
-This directory contains files for seamless integration of Open vSwitch on
-Citrix XenServer hosts managed by the Citrix management tools.
-
-Files in this directory are licensed on a file-by-file basis. Refer to each
-file for details.
-
-Most of the files in this directory are installed on a XenServer system under
-the same name; underscores are replaced by slashes. The files are:
-
-etc_init.d_openvswitch
- Initializes Open vSwitch at boot and shuts it down at shutdown.
-
-etc_init.d_openvswitch-xapi-update
- Init script to ensure openvswitch-cfg-update is called for the current host
- at boot.
-
-etc_logrotate.d_openvswitch
- Ensures that logs in /var/log/openvswitch are rotated periodically and that
- appropriate daemons reopen their log files at that point.
-
-etc_profile.d_openvswitch.sh
- Open vSwitch-related shell functions for the administrator's convenience.
-
-etc_xapi.d_plugins_openvswitch-cfg-update
- xapi plugin script to update the cache of configuration items in the
- ovs-vswitchd configuration that are managed in the xapi database when
- integrated with Citrix management tools.
-
-etc_xensource_scripts_vif
- Open vSwitch-aware replacement for Citrix script of the same name.
-
-openvswitch-xen.spec
- spec file for building RPMs to install on a XenServer host.
-
-opt_xensource_libexec_interface-reconfigure
- Open vSwitch-aware replacements for Citrix script of the same names.
-
-opt_xensource_libexec_InterfaceReconfigureBridge.py
- See above.
-
-opt_xensource_libexec_InterfaceReconfigure.py
- See above.
-
-opt_xensource_libexec_InterfaceReconfigureVswitch.py
- See above.
-
-usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py
- xsconsole plugin to configure the pool-wide configuration keys used to
- control Open vSwitch when integrated with Citrix management tools.
-
-usr_share_openvswitch_scripts_ovs-xapi-sync
- Daemon to monitor the external_ids columns of the Bridge and Interface OVSDB
- tables for changes that require interrogating XAPI.
-
-usr_share_openvswitch_scripts_sysconfig.template
- Template for Open vSwitch's /etc/sysconfig/openvswitch configuration file.
-
-Open vSwitch installs a number of xen-bugtool extensions in
-``/etc/xensource/bugtool`` to gather additional information useful for
-debugging. The sources for the extensions are in
-``../utilities/bugtool/plugins``:
-
-kernel-info/openvswitch.xml
- Collect kernel information relevant to Open vSwitch, such as slabinfo.
-
-network-status/openvswitch.xml
- Collect networking information relevant to Open vSwitch. Runs the following
- scripts, which are described below:
-
- * ovs-bugtool-bfd-show
- * ovs-bugtool-cfm-show
- * ovs-bugtool-fdb-show
- * ovs-bugtool-lacp-show
- * ovs-bugtool-list-dbs
- * ovs-bugtool-ovsdb-dump
- * ovs-bugtool-tc-class-show
- * ovs-bugtool-bond-show
- * ovs-bugtool-ovs-ofctl-show
- * ovs-bugtool-ovs-ofctl-dump-flows
- * ovs-bugtool-ovs-appctl-dpif
- * ovs-bugtool-coverage-show
- * ovs-bugtool-memory-show
- * ovs-bugtool-vsctl-show
- * ovs-bugtool-conntrack-dump
-
-system-configuration/openvswitch.xml
- Collect system configuration information relevant to Open vSwitch, including
- timezone. Runs the following script which is described below:
-
- * ovs-bugtool-daemons-ver
-
-system-configuration.xml
- Collect system configuration data. This category is configured to collect up
- to 1Mb of data, take up to 60 seconds to collect data, run every time and is
- hidden from display in XenCenter.
-
-A number of scripts are installed in ``/usr/share/openvswitch/scripts`` to
-assist Open vSwitch's xen-bugtool extensions. The sources for the scripts are
-located in ``../utilities/bugtool``:
-
-ovs-bugtool-bfd-show
- Script to dump detailed BFD information for all enabled interfaces.
-
-ovs-bugtool-cfm-show
- Script to dump detailed CFM information for all enabled interfaces.
-
-ovs-bugtool-fdb-show
- Script to collect a summary of learned MACs for each bridge.
-
-ovs-bugtool-lacp-show
- Script to dump detailed LACP information for all enabled ports.
-
-ovs-bugtool-list-dbs
- Script to list the databases controlled by ovsdb-server.
-
-ovs-bugtool-ovsdb-dump
- Script to dump contents of Open vSwitch configuration database in
- comma-separated value format.
-
-ovs-bugtool-tc-class-show
- Script to dump tc class configuration for all network interfaces.
-
-ovs-bugtool-ovs-ofctl-show
- Script to dump information about flow tables and ports of each bridge.
-
-ovs-bugtool-ovs-ofctl-dump-flows
- Script to dump openflow flows of each bridge.
-
-ovs-bugtool-ovs-appctl-dpif
- Script to collect a summary of configured datapaths and datapath flows.
-
-ovs-bugtool-coverage-show
- Script to count the number of times particular events occur during
- ovs-vswitchd's runtime.
-
-ovs-bugtool-memory-show
- Script to show some basic statistics about ovs-vswitchd's memory usage.
-
-ovs-bugtool-vsctl-show
- Script to show a brief overview of the database contents.
-
-ovs-bugtool-conntrack-dump
- Script to show all the connection entries in the tracker.
-
-ovs-bugtool-daemons-ver
- Script to dump version information for all Open vSwitch daemons.
diff --git a/xenserver/automake.mk b/xenserver/automake.mk
deleted file mode 100644
index ead0f4a7c..000000000
--- a/xenserver/automake.mk
+++ /dev/null
@@ -1,35 +0,0 @@
-# Copyright (C) 2009, 2010, 2011, 2012, 2014 Nicira, Inc.
-#
-# Copying and distribution of this file, with or without modification,
-# are permitted in any medium without royalty provided the copyright
-# notice and this notice are preserved. This file is offered as-is,
-# without warranty of any kind.
-
-EXTRA_DIST += \
- xenserver/GPLv2 \
- xenserver/LICENSE \
- xenserver/README.rst \
- xenserver/automake.mk \
- xenserver/etc_init.d_openvswitch \
- xenserver/etc_init.d_openvswitch-xapi-update \
- xenserver/etc_logrotate.d_openvswitch \
- xenserver/etc_profile.d_openvswitch.sh \
- xenserver/etc_xapi.d_plugins_openvswitch-cfg-update \
- xenserver/etc_xensource_scripts_vif \
- xenserver/openvswitch-xen.spec \
- xenserver/openvswitch-xen.spec.in \
- xenserver/opt_xensource_libexec_InterfaceReconfigure.py \
- xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py \
- xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py \
- xenserver/opt_xensource_libexec_interface-reconfigure \
- xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py \
- xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync \
- xenserver/usr_share_openvswitch_scripts_sysconfig.template
-
-FLAKE8_PYFILES += \
- xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync
-
-$(srcdir)/xenserver/openvswitch-xen.spec: xenserver/openvswitch-xen.spec.in $(top_builddir)/config.status
- $(AM_V_GEN)($(ro_shell) && sed -e 's,[@]VERSION[@],$(VERSION),g') \
- < $(srcdir)/xenserver/$(@F).in > $(@F).tmp || exit 1; \
- if cmp -s $(@F).tmp $@; then touch $@; rm $(@F).tmp; else mv $(@F).tmp $@; fi
diff --git a/xenserver/etc_init.d_openvswitch b/xenserver/etc_init.d_openvswitch
deleted file mode 100755
index 7d2103fa2..000000000
--- a/xenserver/etc_init.d_openvswitch
+++ /dev/null
@@ -1,154 +0,0 @@
-#!/bin/sh
-#
-# openvswitch
-#
-# chkconfig: 2345 09 91
-# description: Manage Open vSwitch kernel modules and user-space daemons
-
-# Copyright (C) 2009, 2010, 2011 Nicira, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-### BEGIN INIT INFO
-# Provides: openvswitch-switch
-# Required-Start:
-# Required-Stop:
-# Default-Start: 2 3 4 5
-# Default-Stop: 0 1 6
-# Short-Description: Open vSwitch switch
-### END INIT INFO
-
-. /usr/share/openvswitch/scripts/ovs-lib || exit 1
-. /etc/xensource-inventory
-test -e /etc/sysconfig/openvswitch && . /etc/sysconfig/openvswitch
-
-case `cat /etc/xensource/network.conf` in
- vswitch|openvswitch)
- ;;
- bridge)
- exit 0
- ;;
- *)
- echo "Open vSwitch disabled (/etc/xensource/network.conf is invalid)" >&2
- exit 0
- ;;
-esac
-
-start_ovs_xapi_sync () {
- if daemon_is_running ovs-xapi-sync; then
- log_success_msg "ovs-xapi-sync is already running"
- else
- PYTHONPATH=/usr/share/openvswitch/python \
- /usr/share/openvswitch/scripts/ovs-xapi-sync \
- --log-file --pidfile --detach --monitor unix:/var/run/openvswitch/db.sock
- fi
-}
-
-start () {
- set ovs_ctl ${1-start}
- set "$@" --system-id="$INSTALLATION_UUID"
- set "$@" --system-type="$PRODUCT_BRAND"
- set "$@" --system-version="$PRODUCT_VERSION-$BUILD_NUMBER"
- set "$@" --external-id=xs-system-uuid="$INSTALLATION_UUID"
- set "$@" --daemon-cwd=/var/xen/openvswitch
- if test X"$FORCE_COREFILES" != X; then
- set "$@" --force-corefiles="$FORCE_COREFILES"
- fi
- if test X"$OVSDB_SERVER_PRIORITY" != X; then
- set "$@" --ovsdb-server-priority="$OVSDB_SERVER_PRIORITY"
- fi
- if test X"$VSWITCHD_PRIORITY" != X; then
- set "$@" --ovs-vswitchd-priority="$VSWITCHD_PRIORITY"
- fi
- if test X"$VSWITCHD_MLOCKALL" != X; then
- set "$@" --mlockall="$VSWITCHD_MLOCKALL"
- fi
- if test ! -e /var/run/openvswitch.booted; then
- touch /var/run/openvswitch.booted
- set "$@" --delete-bridges
- fi
- set "$@" $OVS_CTL_OPTS
- "$@"
-
- start_ovs_xapi_sync
-
- ovs_ctl --protocol=gre enable-protocol
-
- touch /var/lock/subsys/openvswitch
-}
-
-force_reload_kmod () {
- start force-reload-kmod
-
- # Restart the high-availability daemon if it is running. Otherwise
- # it loses its heartbeat and reboots the system after a few minutes.
- if pidof xhad >/dev/null && test -e /etc/xensource/xhad.conf; then
- PATH=$PATH:/opt/xensource/xha
- action "Stopping HA daemon" ha_stop_daemon
- action "Starting HA daemon" ha_start_daemon
- fi
-
- action "Stopping ovs-xapi-sync" stop_daemon ovs-xapi-sync
- action "Starting ovs-xapi-sync" start_ovs_xapi_sync
-}
-
-stop () {
- ovs_ctl stop
- stop_daemon ovs-xapi-sync
- rm -f /var/lock/subsys/openvswitch
-}
-
-restart () {
- if [ "$1" = "--save-flows=yes" ]; then
- stop_daemon ovs-xapi-sync
- start restart
- else
- stop
- start
- fi
-}
-
-case $1 in
- start)
- start
- ;;
- stop)
- stop
- ;;
- restart)
- shift
- restart "$@"
- ;;
- reload|force-reload)
- # The main OVS daemons keep up-to-date, but ovs-xapi-sync needs help.
- if daemon_is_running ovs-xapi-sync; then
- action "Configuring Open vSwitch external IDs" \
- ovs-appctl -t ovs-xapi-sync flush-cache
- fi
- ;;
- status)
- ovs_ctl status && daemon_status ovs-xapi-sync
- ;;
- version)
- ovs_ctl version
- ;;
- force-reload-kmod)
- force_reload_kmod
- ;;
- help)
- printf "openvswitch [start|stop|restart|reload|force-reload|status|version]\n"
- ;;
- *)
- printf "Unknown command: $1\n"
- exit 1
- ;;
-esac
diff --git a/xenserver/etc_init.d_openvswitch-xapi-update b/xenserver/etc_init.d_openvswitch-xapi-update
deleted file mode 100755
index 12a9db2a1..000000000
--- a/xenserver/etc_init.d_openvswitch-xapi-update
+++ /dev/null
@@ -1,80 +0,0 @@
-#!/bin/bash
-#
-# openvswitch-xapi-update
-#
-# chkconfig: 2345 95 01
-# description: Update Open vSwitch configuration from XAPI database at boot
-
-# Copyright (C) 2009, 2010 Nicira, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-### BEGIN INIT INFO
-# Provides: openvswitch-xapi-update
-# Required-Start: $network $remote_fs
-# Required-Stop: $network
-# Default-Start: 3 5
-# Default-Stop:
-# Short-Description: openvswitch-xapi-update
-# Description: reconfigures Open vSwitch based on XAPI configuration
-### END INIT INFO
-
-. /etc/init.d/functions
-
-function do_host_call {
- xe host-call-plugin host-uuid="$INSTALLATION_UUID" plugin="openvswitch-cfg-update" fn="update" >/dev/null
-}
-
-function start {
- if [ ! -f /etc/xensource-inventory ]; then
- printf "openvswitch-xapi-update ERROR: XenSource inventory not present in /etc/xensource-inventory\n"
- exit 1
- fi
-
- if test -e /etc/xensource/network.conf; then
- NETWORK_MODE=$(cat /etc/xensource/network.conf)
- fi
-
- case ${NETWORK_MODE:=openvswitch} in
- vswitch|openvswitch)
- ;;
- bridge)
- exit 0
- ;;
- *)
- echo "Open vSwitch disabled (/etc/xensource/network.conf is invalid)" >&2
- exit 0
- ;;
- esac
-
- source /etc/xensource-inventory
- action "Updating configuration" do_host_call
-}
-
-case "$1" in
- start)
- start
- ;;
- stop)
- # Nothing to do here.
- ;;
- restart)
- start
- ;;
- help)
- printf "openvswitch-xapi-update [start|stop|restart]\n"
- ;;
- *)
- printf "Unknown command: $1\n"
- exit 1
- ;;
-esac
diff --git a/xenserver/etc_logrotate.d_openvswitch b/xenserver/etc_logrotate.d_openvswitch
deleted file mode 100644
index cd7b3a9d5..000000000
--- a/xenserver/etc_logrotate.d_openvswitch
+++ /dev/null
@@ -1,21 +0,0 @@
-# Copyright (C) 2009, 2010, 2011, 2012, 2017 Nicira, Inc.
-#
-# Copying and distribution of this file, with or without modification,
-# are permitted in any medium without royalty provided the copyright
-# notice and this notice are preserved. This file is offered as-is,
-# without warranty of any kind.
-
-/var/log/openvswitch/*.log {
- daily
- compress
- sharedscripts
- missingok
- postrotate
- # Tell Open vSwitch daemons to reopen their log files
- if [ -d /var/run/openvswitch ]; then
- for pidfile in `cd /var/run/openvswitch && echo *.pid`; do
- ovs-appctl -t "${pidfile%%.pid}" vlog/reopen 2>/dev/null || :
- done
- fi
- endscript
-}
diff --git a/xenserver/etc_profile.d_openvswitch.sh b/xenserver/etc_profile.d_openvswitch.sh
deleted file mode 100644
index 63b254359..000000000
--- a/xenserver/etc_profile.d_openvswitch.sh
+++ /dev/null
@@ -1,48 +0,0 @@
-# Copyright (C) 2009, 2010, 2011 Nicira, Inc.
-#
-# Copying and distribution of this file, with or without modification,
-# are permitted in any medium without royalty provided the copyright
-# notice and this notice are preserved. This file is offered as-is,
-# without warranty of any kind.
-
-alias vswitch='service openvswitch'
-alias openvswitch='service openvswitch'
-
-function watchdp {
- watch ovs-dpctl show "$@"
-}
-
-function watchdpflows {
- local grep=""
- local dp=$1
- shift
- if [ $# -gt 0 ]; then
- grep="| grep $@"
- fi
- watch "ovs-dpctl dump-flows $dp $grep"
-}
-
-function watchflows {
- local grep=""
- local dp=$1
- shift
- bridge=$(ovs-dpctl show $dp | grep 'port 0:' | cut -d' ' -f 3)
- if [ $# -gt 0 ]; then
- grep="| grep $@"
- fi
- watch "ovs-ofctl dump-flows unix:/var/run/$bridge.mgmt $grep"
-}
-
-function monitorlogs {
- local grep=""
- if [ $# -gt 0 ]; then
- grep="| grep --line-buffered '^==> .* <==$"
- for i in "$@"; do
- grep="$grep\|$i"
- done
- grep="$grep'"
- fi
- cmd="tail -F /var/log/messages /var/log/openvswitch/ovs-vswitchd.log /var/log/openvswitch/ovsdb-server /var/log/xensource.log $grep | tee /var/log/monitorlogs.out"
- printf "cmd: $cmd\n"
- eval "$cmd"
-}
diff --git a/xenserver/etc_xapi.d_plugins_openvswitch-cfg-update b/xenserver/etc_xapi.d_plugins_openvswitch-cfg-update
deleted file mode 100755
index b8db88194..000000000
--- a/xenserver/etc_xapi.d_plugins_openvswitch-cfg-update
+++ /dev/null
@@ -1,269 +0,0 @@
-#!/usr/bin/env python3
-#
-# xapi plugin script to update the cache of configuration items in the
-# ovs-vswitchd configuration that are managed in the xapi database when
-# integrated with Citrix management tools.
-
-# Copyright (C) 2009, 2010, 2011, 2012, 2013, 2020 Nicira, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-# TBD: - error handling needs to be improved. Currently this can leave
-# TBD: the system in a bad state if anything goes wrong.
-
-import XenAPIPlugin
-import os
-import subprocess
-import syslog
-import re
-
-vsctl = '/usr/bin/ovs-vsctl'
-ofctl = '/usr/bin/ovs-ofctl'
-cacert_filename = '/etc/openvswitch/vswitchd.cacert'
-ovsdb_port = '6640'
-
-
-# Delete the CA certificate, so that we go back to boot-strapping mode
-def delete_cacert():
- try:
- os.remove(cacert_filename)
- except OSError:
- # Ignore error if file doesn't exist
- pass
-
-
-def update(session, args):
- # Refresh bridge network UUIDs in case this host joined or left a pool.
- script = '/opt/xensource/libexec/interface-reconfigure'
- try:
- retval = subprocess.call([script, 'rewrite'])
- if retval != 0:
- syslog.syslog('%s exited with status %d' % (script, retval))
- except OSError, e:
- syslog.syslog('%s: failed to execute (%s)' % (script, e.strerror))
-
- pools = session.xenapi.pool.get_all()
- # We assume there is only ever one pool...
- if len(pools) == 0:
- raise XenAPIPlugin.Failure('NO_POOL_FOR_HOST', [])
- if len(pools) > 1:
- raise XenAPIPlugin.Failure('MORE_THAN_ONE_POOL_FOR_HOST', [])
- new_controller = False
- pool = session.xenapi.pool.get_record(pools[0])
- controller = pool.get('vswitch_controller')
- ret_str = ''
- currentControllers = vswitchCurrentControllers()
-
- if not controller and currentControllers:
- delete_cacert()
- try:
- emergency_reset(session, None)
- except:
- pass
- removeControllerCfg()
- ret_str += 'Successfully removed controller config. '
- # controller cannot be empty, otherwise, this will always be True.
- elif controller and controller not in currentControllers:
- delete_cacert()
- try:
- emergency_reset(session, None)
- except:
- pass
- setControllerCfg(controller)
- new_controller = True
- ret_str += 'Successfully set controller to %s. ' % controller
-
- try:
- pool_fail_mode = pool['other_config']['vswitch-controller-fail-mode']
- except KeyError, e:
- pool_fail_mode = None
-
- bton = {}
-
- for rec in session.xenapi.network.get_all_records().values():
- try:
- bton[rec['bridge']] = rec
- except KeyError:
- pass
-
- # If new controller, get management MAC addresses from XAPI now
- # in case fail_mode set to secure which may affect XAPI access
- mgmt_bridge = None
- host_mgmt_mac = None
- host_mgmt_device = None
- pool_mgmt_macs = {}
- if new_controller:
- query = 'field "management"="true"'
- recs = session.xenapi.PIF.get_all_records_where(query)
- for rec in recs.itervalues():
- pool_mgmt_macs[rec.get('MAC')] = rec.get('device')
-
- dib_changed = False
- fail_mode_changed = False
- for bridge in vswitchCfgQuery(['list-br']).split():
- network = bton[bridge]
- bridge = vswitchCfgQuery(['br-to-parent', bridge])
-
- xapi_dib = network['other_config'].get('vswitch-disable-in-band')
- if not xapi_dib:
- xapi_dib = ''
-
- ovs_dib = vswitchCfgQuery(['--', '--if-exists', 'get', 'Bridge',
- bridge,
- 'other_config:disable-in-band']).strip('"')
-
- # Do nothing if setting is invalid, and warn the user.
- if xapi_dib not in ['true', 'false', '']:
- ret_str += '"' + xapi_dib + '"' + \
- ' is an invalid value for vswitch-disable-in-band on ' + \
- bridge + ' '
-
- # Change bridge disable-in-band option if XAPI and OVS states differ.
- elif xapi_dib != ovs_dib:
- # 'true' or 'false'
- if xapi_dib:
- vswitchCfgMod(['--', 'set', 'Bridge', bridge,
- 'other_config:disable-in-band=' + xapi_dib])
- # '' or None
- else:
- vswitchCfgMod(['--', 'remove', 'Bridge', bridge,
- 'other_config', 'disable-in-band'])
- dib_changed = True
-
- # Change bridge fail_mode if XAPI state differs from OVS state.
- bridge_fail_mode = vswitchCfgQuery(['get', 'Bridge',
- bridge, 'fail_mode']).strip('[]"')
-
- try:
- other_config = bton[bridge]['other_config']
- fail_mode = other_config['vswitch-controller-fail-mode']
- except KeyError, e:
- fail_mode = None
-
- if fail_mode not in ['secure', 'standalone']:
- fail_mode = pool_fail_mode
-
- if fail_mode != 'secure':
- fail_mode = 'standalone'
-
- if bridge_fail_mode != fail_mode:
- vswitchCfgMod(['--', 'set', 'Bridge', bridge,
- 'fail_mode=%s' % fail_mode])
- fail_mode_changed = True
-
- # Determine local mgmt MAC address if host being added to secure
- # pool so we can add default flows to allow management traffic
- if new_controller and fail_mode_changed and pool_fail_mode == 'secure':
- oc = vswitchCfgQuery(['get', 'Bridge', bridge, 'other-config'])
- m = re.match('.*hwaddr="([0-9a-fA-F:].*)".*', oc)
- if m and m.group(1) in pool_mgmt_macs.keys():
- mgmt_bridge = bridge
- host_mgmt_mac = m.group(1)
- host_mgmt_device = pool_mgmt_macs[host_mgmt_mac]
-
- if (host_mgmt_mac is not None and mgmt_bridge is not None and
- host_mgmt_device is not None):
- tp = 'idle_timeout=0,priority=0'
- port = vswitchCfgQuery(['get', 'interface', host_mgmt_device,
- 'ofport'])
-
- addFlow(mgmt_bridge, '%s,in_port=%s,arp,nw_proto=1,actions=local' %
- (tp, port))
- addFlow(mgmt_bridge, '%s,in_port=local,arp,dl_src=%s,actions=%s' %
- (tp, host_mgmt_mac, port))
- addFlow(mgmt_bridge, '%s,in_port=%s,dl_dst=%s,actions=local' %
- (tp, port, host_mgmt_mac))
- addFlow(mgmt_bridge, '%s,in_port=local,dl_src=%s,actions=%s' %
- (tp, host_mgmt_mac, port))
-
- if dib_changed:
- ret_str += 'Updated in-band management. '
- if fail_mode_changed:
- ret_str += 'Updated fail_mode. '
-
- if ret_str != '':
- return ret_str
- else:
- return 'No change to configuration'
-
-
-def vswitchCurrentControllers():
- controllers = vswitchCfgQuery(['get-manager'])
-
- def parse_controller(controller):
- if controller.startswith('ssl:'):
- return controller.split(':')[1]
-
- return controller.split(':')[0]
-
- return [parse_controller(controller)
- for controller in controllers.split('\n')
- if controller]
-
-
-def removeControllerCfg():
- vswitchCfgMod(['--', 'del-manager',
- '--', 'del-ssl'])
-
-
-def setControllerCfg(controller):
- # /etc/xensource/xapi-ssl.pem is mentioned twice below because it
- # contains both the private key and the certificate.
- vswitchCfgMod(['--', 'del-manager',
- '--', 'del-ssl',
- '--', '--bootstrap', 'set-ssl',
- '/etc/xensource/xapi-ssl.pem',
- '/etc/xensource/xapi-ssl.pem',
- cacert_filename,
- '--', 'set-manager', 'ssl:' + controller + ':' + ovsdb_port])
-
-
-def vswitchCfgQuery(action_args):
- cmd = [vsctl, '-vconsole:off'] + action_args
- output = subprocess.Popen(cmd, stdout=subprocess.PIPE).communicate()
- if len(output) == 0 or output[0] is None:
- output = ''
- else:
- output = output[0].strip()
- return output
-
-
-def vswitchCfgMod(action_args):
- cmd = [vsctl, '--timeout=5', '-vconsole:off'] + action_args
- exitcode = subprocess.call(cmd)
- if exitcode != 0:
- raise XenAPIPlugin.Failure('VSWITCH_CONFIG_MOD_FAILURE',
- [str(exitcode), str(action_args)])
-
-
-def emergency_reset(session, args):
- cmd = [vsctl, '--timeout=5', 'emer-reset']
- exitcode = subprocess.call(cmd)
- if exitcode != 0:
- raise XenAPIPlugin.Failure('VSWITCH_EMER_RESET_FAILURE',
- [str(exitcode)])
-
- return 'Successfully reset configuration'
-
-
-def addFlow(switch, flow):
- cmd = [ofctl, 'add-flow', switch, flow]
- exitcode = subprocess.call(cmd)
- if exitcode != 0:
- raise XenAPIPlugin.Failure('VSWITCH_ADD_FLOW_FAILURE',
- [str(exitcode), str(switch), str(flow)])
-
-
-if __name__ == '__main__':
- XenAPIPlugin.dispatch({'update': update,
- 'emergency_reset': emergency_reset})
diff --git a/xenserver/etc_xensource_scripts_vif b/xenserver/etc_xensource_scripts_vif
deleted file mode 100755
index 78434fb6c..000000000
--- a/xenserver/etc_xensource_scripts_vif
+++ /dev/null
@@ -1,265 +0,0 @@
-#!/bin/sh
-
-# Copyright (C) 2008,2009 Citrix Systems, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
-# by the Free Software Foundation; version 2.1 only. with the special
-# exception on linking described in file LICENSE.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU Lesser General Public License for more details.
-
-# CA-23900: Warning: when VIFs are added to windows guests with PV drivers the backend vif device is registered,
-# unregistered and then registered again. This causes the udev event to fire twice and this script runs twice.
-# Since the first invocation of the script races with the device unregistration, spurious errors are possible
-# which will be logged but are safe to ignore since the second script invocation should complete the operation.
-# Note that each script invocation is run synchronously from udev and so the scripts don't race with each other.
-
-# Keep other-config/ keys in sync with device.ml:vif_udev_keys
-
-BRCTL="/usr/sbin/brctl"
-IP="/sbin/ip"
-
-vsctl="/usr/bin/ovs-vsctl"
-
-handle_promiscuous()
-{
- local arg=$(xenstore-read "${PRIVATE}/other-config/promiscuous" 2>/dev/null)
- if [ $? -eq 0 -a -n "${arg}" ] ; then
- case $NETWORK_MODE in
- bridge)
- case "${arg}" in
- true|on) echo 1 > /sys/class/net/${dev}/brport/promisc ;;
- *) echo 0 > /sys/class/net/${dev}/brport/promisc ;;
- esac
- ;;
- openvswitch)
- logger -t script-vif "${dev}: Promiscuous ports are not supported via Open vSwitch."
- ;;
- esac
- fi
-}
-
-handle_ethtool()
-{
- local opt=$1
- local arg=$(xenstore-read "${PRIVATE}/other-config/ethtool-${opt}" 2>/dev/null)
- if [ $? -eq 0 -a -n "${arg}" ] ; then
- case "${arg}" in
- true|on) /sbin/ethtool -K "${dev}" "${opt}" on ;;
- false|off) /sbin/ethtool -K "${dev}" "${opt}" off ;;
- *) logger -t scripts-vif "Unknown ethtool argument ${opt}=${arg} on ${dev}/${VIFUUID}" ;;
- esac
- fi
-}
-
-handle_mtu()
-{
- local mtu=$(xenstore-read "${PRIVATE}/MTU" 2>/dev/null)
- if [ $? -eq 0 -a -n "${mtu}" ]; then
- logger -t scripts-vif "Setting ${dev} MTU ${mtu}"
- ${IP} link set "${dev}" mtu ${mtu} || logger -t scripts-vif "Failed to ip link set ${dev} mtu ${mtu}. Error code $?"
- fi
-}
-
-set_vif_external_id()
-{
- local key=$1
- local value=$2
-
- logger -t scripts-vif "vif${DOMID}.${DEVID} external-ids:\"${key}\"=\"${value}\""
-
- echo "-- set interface vif${DOMID}.${DEVID} external-ids:\"${key}\"=\"${value}\""
-}
-
-handle_vswitch_vif_details()
-{
- local vm=$(xenstore-read "/local/domain/$DOMID/vm" 2>/dev/null)
- if [ $? -eq 0 -a -n "${vm}" ] ; then
- local vm_uuid=$(xenstore-read "$vm/uuid" 2>/dev/null)
- fi
- if [ -n "${vm_uuid}" ] ; then
- set_vif_external_id "xs-vm-uuid" "${vm_uuid}"
- fi
-
- local vif_uuid=$(xenstore-read "${PRIVATE}/vif-uuid" 2>/dev/null)
- if [ -n "${vif_uuid}" ] ; then
- set_vif_external_id "xs-vif-uuid" "${vif_uuid}"
- fi
-
- local vif_details=
- local net_uuid=$(xenstore-read "${PRIVATE}/network-uuid" 2>/dev/null)
- if [ -n "${net_uuid}" ] ; then
- set_vif_external_id "xs-network-uuid" "${net_uuid}"
- fi
- local address=$(xenstore-read "/local/domain/$DOMID/device/vif/$DEVID/mac" 2>/dev/null)
- if [ -n "${address}" ] ; then
- set_vif_external_id "attached-mac" "${address}"
- fi
-}
-
-add_to_bridge()
-{
- local address=$(xenstore-read "${PRIVATE}/bridge-MAC")
- if [ $? -ne 0 -o -z "${address}" ]; then
- logger -t scripts-vif "Failed to read ${PRIVATE}/bridge-MAC from xenstore"
- exit 1
- fi
- local bridge=$(xenstore-read "${PRIVATE}/bridge")
- if [ $? -ne 0 -o -z "${bridge}" ]; then
- logger -t scripts-vif "Failed to read ${PRIVATE}/bridge from xenstore"
- exit 1
- fi
- logger -t scripts-vif "Adding ${dev} to ${bridge} with address ${address}"
-
- ${IP} link set "${dev}" down || logger -t scripts-vif "Failed to ip link set ${dev} down"
- ${IP} link set "${dev}" arp off || logger -t scripts-vif "Failed to ip link set ${dev} arp off"
- ${IP} link set "${dev}" multicast off || logger -t scripts-vif "Failed to ip link set ${dev} multicast off"
- ${IP} link set "${dev}" address "${address}" || logger -t scripts-vif "Failed to ip link set ${dev} address ${address}"
- ${IP} addr flush "${dev}" || logger -t scripts-vif "Failed to ip addr flush ${dev}"
-
- case $NETWORK_MODE in
- bridge)
- ${BRCTL} setfd "${bridge}" 0 || logger -t scripts-vif "Failed to brctl setfd ${bridge} 0"
- ${BRCTL} addif "${bridge}" "${dev}" || logger -t scripts-vif "Failed to brctl addif ${bridge} ${dev}"
- ;;
- openvswitch)
- if [ "$TYPE" = "vif" ] ; then
- local vif_details=$(handle_vswitch_vif_details $bridge)
- fi
-
- $vsctl --timeout=30 -- --if-exists del-port $dev -- add-port $bridge $dev $vif_details
- ;;
- esac
-
- ${IP} link set "${dev}" up || logger -t scripts-vif "Failed to ip link set ${dev} up"
-}
-
-remove_from_bridge()
-{
- case $NETWORK_MODE in
- bridge)
- # Nothing to do
- ;;
- openvswitch)
- $vsctl --timeout=30 -- del-port $dev
- ;;
- esac
-}
-
-call_hook_script() {
- local domid=$1
- local action=$2
- # Call the VIF hotplug hook if present
- if [ -x /etc/xapi.d/vif-hotplug ]; then
- local vm=$(xenstore-read "/local/domain/$domid/vm" 2>/dev/null)
- if [ $? -eq 0 -a -n "${vm}" ] ; then
- local vm_uuid=$(xenstore-read "$vm/uuid" 2>/dev/null)
- fi
- if [ -n "${vm_uuid}" ] ; then
- logger -t scripts-vif "VM UUID ${vm_uuid}"
- fi
-
- local vif_uuid=$(xenstore-read "${PRIVATE}/vif-uuid" 2>/dev/null)
- if [ -n "${vif_uuid}" ] ; then
- logger -t scripts-vif "VIF UUID ${vif_uuid}"
- fi
- if [ -n "${vif_uuid}" -a -n "${vm_uuid}" ] ; then
- logger -t scripts-vif "Calling VIF hotplug hook for VM ${vm_uuid}, VIF ${vif_uuid}"
- /etc/xapi.d/vif-hotplug -action "${action}" -vifuuid "${vif_uuid}" -vmuuid "${vm_uuid}"
- fi
- fi
-}
-
-NETWORK_MODE=$(cat /etc/xensource/network.conf)
-ACTION=$1
-
-# Older versions of XenServer do not pass in the type as an argument
-if [[ $# -lt 2 ]]; then
- TYPE=vif
-else
- TYPE=$2
-fi
-
-case $NETWORK_MODE in
- bridge|openvswitch) ;;
- vswitch) NETWORK_MODE=openvswitch ;;
- *)
- logger -t scripts-vif "Unknown network mode $NETWORK_MODE"
- exit 1
- ;;
-esac
-
-case ${TYPE} in
- vif)
- if [ -z ${XENBUS_PATH} ]; then
- DOMID=$3
- DEVID=$4
- else
- DOMID=`echo ${XENBUS_PATH} | cut -f 3 -d '/'`
- DEVID=`echo ${XENBUS_PATH} | cut -f 4 -d '/'`
- fi
- dev=vif${DOMID}.${DEVID}
- ;;
- tap)
- dev=$INTERFACE
- DOMID=`echo ${dev#tap} | cut -f 1 -d '.'`
- DEVID=`echo ${dev#tap} | cut -f 2 -d '.'`
- ;;
- *)
- logger -t scripts-vif "unknown interface type ${TYPE}"
- exit 1
- ;;
-esac
-
-XAPI=/xapi/${DOMID}/hotplug/vif/${DEVID}
-HOTPLUG=/xapi/${DOMID}/hotplug/vif/${DEVID}
-PRIVATE=/xapi/${DOMID}/private/vif/${DEVID}
-
-logger -t scripts-vif "Called as \"$@\" domid:$DOMID devid:$DEVID mode:$NETWORK_MODE"
-case "${ACTION}" in
-online)
- if [ "${TYPE}" = "vif" ] ; then
- handle_ethtool rx
- handle_ethtool tx
- handle_ethtool sg
- handle_ethtool tso
- handle_ethtool ufo
- handle_ethtool gso
-
- handle_mtu
- add_to_bridge
- handle_promiscuous
-
- xenstore-write "${HOTPLUG}/vif" "${dev}"
- xenstore-write "${HOTPLUG}/hotplug" "online"
-
- # xs-xen.pq.hq:91e986b8e49f netback-wait-for-hotplug
- xenstore-write "/local/domain/0/backend/vif/${DOMID}/${DEVID}/hotplug-status" "connected"
- call_hook_script $DOMID "${ACTION}"
- fi
- ;;
-
-add)
- if [ "${TYPE}" = "tap" ] ; then
- add_to_bridge
- fi
- ;;
-
-remove)
- if [ "${TYPE}" = "vif" ] ;then
- xenstore-rm "${HOTPLUG}/hotplug"
- call_hook_script $DOMID "${ACTION}"
- fi
- logger -t scripts-vif "${dev} has been removed"
- remove_from_bridge
- ;;
-
-move)
- if [ "${TYPE}" = "vif" ] ;then
- add_to_bridge
- fi
-esac
diff --git a/xenserver/openvswitch-xen.spec.in b/xenserver/openvswitch-xen.spec.in
deleted file mode 100644
index ae22f2f5c..000000000
--- a/xenserver/openvswitch-xen.spec.in
+++ /dev/null
@@ -1,512 +0,0 @@
-# Spec file for Open vSwitch.
-
-# Copyright (C) 2009, 2010, 2011, 2012, 2013, 2014, 2015, 2016 Nicira, Inc.
-#
-# Copying and distribution of this file, with or without modification,
-# are permitted in any medium without royalty provided the copyright
-# notice and this notice are preserved. This file is offered as-is,
-# without warranty of any kind.
-
-# For XenServer version < 6.5, when building, the rpmbuild command line
-# should define openvswitch_version, kernel_name, kernel_version and
-# kernel_flavor using -D arguments.
-# for example:
-#
-# rpmbuild -D "openvswitch_version 1.1.0+build123"
-# -D "kernel_name NAME-xen"
-# -D "kernel_version 2.6.32.12-0.7.1.xs5.6.100.323.170596"
-# -D "kernel_flavor xen"
-# -bb /usr/src/redhat/SPECS/openvswitch-xen.spec
-#
-# For XenServer version >= 6.5, use kernel_uname which should be
-# the `uname -r` output.
-# for example:
-#
-# rpmbuild -D "openvswitch_version 2.3.0+build123"
-# -D "kernel_uname 3.10.0+2"
-# -bb /usr/src/redhat/SPECS/openvswitch-xen.spec
-#
-# If tests have to be skipped while building, specify the '--without check'
-# option. For example:
-# rpmbuild -bb --without check xenserver/openvswitch-xen.spec
-
-%if %{?openvswitch_version:0}%{!?openvswitch_version:1}
-%define openvswitch_version @VERSION@
-%endif
-
-%if %{?kernel_uname:1}%{!?kernel_uname:0}
-%define kernel_name kernel
-%define kernel_version %{kernel_uname}
-%endif
-
-%if %{?kernel_name:0}%{!?kernel_name:1}
-%define kernel %(rpm -qa 'kernel*xen-devel' | head -1)
-%define kernel_name %(rpm -q --queryformat "%%{Name}" %{kernel} | sed 's/-devel//' | sed 's/kernel-//')
-%define kernel_version %(rpm -q --queryformat "%%{Version}-%%{Release}" %{kernel})
-%define kernel_flavor xen
-%endif
-
-%if %{?xen_version:0}%{!?xen_version:1}
-%define xen_version %{kernel_version}%{?kernel_flavor:%{kernel_flavor}}
-%endif
-
-# bump this when breaking compatibility with userspace
-%define module_abi_version 0
-
-# build-supplemental-pack.sh requires this naming for kernel module packages
-%define module_package modules%{?kernel_flavor:-%{kernel_flavor}}-%{kernel_version}
-
-%bcond_without check
-
-Name: openvswitch
-Summary: Open vSwitch daemon/database/utilities
-Group: System Environment/Daemons
-URL: http://www.openvswitch.org/
-Vendor: Nicira, Inc.
-Version: %{openvswitch_version}
-
-License: ASL 2.0
-Release: 1
-Source: openvswitch-%{openvswitch_version}.tar.gz
-Buildroot: /tmp/openvswitch-xen-rpm
-Requires: openvswitch.ko.%{module_abi_version}
-
-%description
-Open vSwitch provides standard network bridging functions augmented with
-support for the OpenFlow protocol for remote per-flow control of
-traffic.
-
-%package %{module_package}
-Summary: Open vSwitch kernel module
-Group: System Environment/Kernel
-License: GPLv2
-Provides: %{name}-modules%{?kernel_flavor:-%{kernel_flavor}} = %{kernel_version}, openvswitch.ko.%{module_abi_version}
-%if %{?kernel_uname:0}%{!?kernel_uname:1}
-Requires: kernel%{?kernel_flavor:-%{kernel_flavor}} = %{kernel_version}
-%endif
-%if %{?kernel_uname:1}%{!?kernel_uname:0}
-Requires: kernel-uname-r = %{kernel_version}
-%endif
-
-%description %{module_package}
-Open vSwitch Linux kernel module compiled against kernel version
-%{kernel_version}%{?kernel_flavor:%{kernel_flavor}}.
-
-%prep
-%setup -q -n openvswitch-%{openvswitch_version}
-
-%build
-./configure --prefix=/usr --sysconfdir=/etc --localstatedir=%{_localstatedir} --with-linux=/lib/modules/%{xen_version}/build --enable-ssl CFLAGS='-g -O2 -msse -msse2'
-make %{_smp_mflags}
-
-%install
-rm -rf $RPM_BUILD_ROOT
-make install DESTDIR=$RPM_BUILD_ROOT
-install -d -m 755 $RPM_BUILD_ROOT/etc
-install -d -m 755 $RPM_BUILD_ROOT/etc/init.d
-install -m 755 xenserver/etc_init.d_openvswitch \
- $RPM_BUILD_ROOT/etc/init.d/openvswitch
-install -m 755 xenserver/etc_init.d_openvswitch-xapi-update \
- $RPM_BUILD_ROOT/etc/init.d/openvswitch-xapi-update
-install -d -m 755 $RPM_BUILD_ROOT/etc/sysconfig
-install -d -m 755 $RPM_BUILD_ROOT/etc/logrotate.d
-install -m 755 xenserver/etc_logrotate.d_openvswitch \
- $RPM_BUILD_ROOT/etc/logrotate.d/openvswitch
-install -d -m 755 $RPM_BUILD_ROOT/etc/profile.d
-install -m 755 xenserver/etc_profile.d_openvswitch.sh \
- $RPM_BUILD_ROOT/etc/profile.d/openvswitch.sh
-install -d -m 755 $RPM_BUILD_ROOT/etc/xapi.d/plugins
-install -m 755 xenserver/etc_xapi.d_plugins_openvswitch-cfg-update \
- $RPM_BUILD_ROOT/etc/xapi.d/plugins/openvswitch-cfg-update
-install -d -m 755 $RPM_BUILD_ROOT/usr/share/openvswitch/scripts
-install -m 755 xenserver/opt_xensource_libexec_interface-reconfigure \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/interface-reconfigure
-install -m 644 xenserver/opt_xensource_libexec_InterfaceReconfigure.py \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/InterfaceReconfigure.py
-install -m 644 xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/InterfaceReconfigureBridge.py
-install -m 644 xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/InterfaceReconfigureVswitch.py
-install -m 755 xenserver/etc_xensource_scripts_vif \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/vif
-install -m 755 xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/ovs-xapi-sync
-install -m 755 xenserver/usr_share_openvswitch_scripts_sysconfig.template \
- $RPM_BUILD_ROOT/usr/share/openvswitch/scripts/sysconfig.template
-install -d -m 755 $RPM_BUILD_ROOT/usr/lib/xsconsole/plugins-base
-install -m 644 \
- xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py \
- $RPM_BUILD_ROOT/usr/lib/xsconsole/plugins-base/XSFeatureVSwitch.py
-
-install -d -m 755 $RPM_BUILD_ROOT/lib/modules/%{xen_version}/extra/openvswitch
-find datapath/linux -name *.ko -exec install -m 755 \{\} $RPM_BUILD_ROOT/lib/modules/%{xen_version}/extra/openvswitch \;
-
-install -d -m 755 $RPM_BUILD_ROOT/etc/xensource/bugtool
-cp -rf $RPM_BUILD_ROOT/usr/share/openvswitch/bugtool-plugins/* $RPM_BUILD_ROOT/etc/xensource/bugtool
-
-# Get rid of stuff we don't want to make RPM happy.
-rm \
- $RPM_BUILD_ROOT/usr/bin/ovs-testcontroller \
- $RPM_BUILD_ROOT/usr/bin/ovs-l3ping \
- $RPM_BUILD_ROOT/usr/bin/ovs-pki \
- $RPM_BUILD_ROOT/usr/bin/ovs-test \
- $RPM_BUILD_ROOT/usr/share/man/man8/ovs-testcontroller.8 \
- $RPM_BUILD_ROOT/usr/share/man/man8/ovs-l3ping.8 \
- $RPM_BUILD_ROOT/usr/share/man/man8/ovs-pki.8 \
- $RPM_BUILD_ROOT/usr/share/man/man8/ovs-test.8
-(cd "$RPM_BUILD_ROOT" && rm -f usr/lib/lib*)
-(cd "$RPM_BUILD_ROOT" && rm -rf usr/include)
-(cd "$RPM_BUILD_ROOT" && rm -rf usr/lib/pkgconfig)
-
-install -d -m 755 $RPM_BUILD_ROOT/var/lib/openvswitch
-
-%check
-%if %{with check}
- if make check TESTSUITEFLAGS='%{_smp_mflags}' RECHECK=yes; then :;
- else
- cat tests/testsuite.log
- exit 1
- fi
-%endif
-
-%clean
-rm -rf $RPM_BUILD_ROOT
-
-%post
-# A list of Citrix XenServer scripts that we might need to replace
-# with our own versions.
-scripts="
- /etc/xensource/scripts/vif
- /opt/xensource/libexec/InterfaceReconfigure.py
- /opt/xensource/libexec/InterfaceReconfigureBridge.py
- /opt/xensource/libexec/InterfaceReconfigureVswitch.py
- /opt/xensource/libexec/interface-reconfigure"
-
-# Calculate into $md5sums a comma-separated set of md5sums of the
-# Citrix XenServer scripts that we might need to replace. We might be
-# upgrading an older version of the package that moved the files out
-# of the way, so we need to look for the files in those out-of-the-way
-# locations first.
-md5sums=
-for script in $scripts; do
- b=$(basename "$script")
- if test -e /usr/lib/openvswitch/xs-saved/"$b"; then
- f=/usr/lib/openvswitch/xs-saved/"$b"
- elif test -e /usr/lib/openvswitch/xs-original/"$b"; then
- f=/usr/lib/openvswitch/xs-original/"$b"
- elif test -e "$script" && test ! -h "$script"; then
- f=$script
- else
- printf "\n$script: not found\n"
- f=/dev/null
- fi
- md5sums="$md5sums,$(md5sum $f | awk '{print $1}')"
-done
-md5sums=${md5sums#,}
-
-# Now check the md5sums against the known sets of md5sums:
-#
-# - If they are known to be a version of XenServer scripts that we should
-# replace, we replace them (by putting $scripts into $replace_files).
-#
-# - Otherwise, we guess that it's better not to replace them, because the
-# improvements that our versions of the scripts provide are minimal, so
-# it's better to avoid possibly breaking any changes made upstream by
-# Citrix.
-case $md5sums in
- cf09a68d9f8b434e79a4c83b01a3bb4b,395866df1b0b20c12c4dd2f7de0ecdb4,9d493545ae81463239d3162cbc798852,862d0939b441de9264a900628e950fe9,21f85db25599d7f026cd489385d58aa6)
- keep_files=
- replace_files=$scripts
- printf "\nVerified host scripts from XenServer 6.0.0.\n"
- ;;
-
- c5f48246577a17cf1b971fb5ce4e920b,2e2c912f86f9c536c89adc34ff3c2b2b,28d3ff72d72bdec4f37d70699f5edb76,67e1d0af16fc1ddf10009c5c063ad2ba,f3feff30aa3b3f8b514664a96a8dc0ab)
- keep_files=
- replace_files=$scripts
- printf "\nVerified host scripts from XenServer 5.6-SP2.\n"
- ;;
-
- c5f48246577a17cf1b971fb5ce4e920b,2e2c912f86f9c536c89adc34ff3c2b2b,28d3ff72d72bdec4f37d70699f5edb76,67e1d0af16fc1ddf10009c5c063ad2ba,24bae6906d182ba47668174f8e480cc6)
- keep_files=
- replace_files=$scripts
- printf "\nVerified host scripts from XenServer 5.6-FP1.\n"
- ;;
-
- *)
- keep_files=$scripts
- replace_files=
- cat <<EOF
-
-The host scripts on this machine are not those of any supported
-version of XenServer. On XenServer earlier than 5.6-FP1, your Open
-vSwitch installation will not work. On XenServer 5.6-FP1 or later,
-Open vSwitch is not verified to work, which could lead to unexpected
-behavior.
-
-EOF
- ;;
-esac
-
-if grep -F net.ipv4.conf.all.arp_filter /etc/sysctl.conf >/dev/null 2>&1; then :; else
- cat >>/etc/sysctl.conf <<EOF
-# This works around an issue in xhad, which binds to a particular
-# Ethernet device, which in turn causes ICMP port unreachable messages
-# if packets are received are on the wrong interface, which in turn
-# can happen if we send out ARP replies on every interface (as Linux
-# does by default) instead of just on the interface that has the IP
-# address being ARPed for, which this sysctl setting in turn works
-# around.
-#
-# Bug #1378.
-net.ipv4.conf.all.arp_filter = 1
-EOF
-fi
-
-if test ! -e /etc/openvswitch/conf.db; then
- install -d -m 755 -o root -g root /etc/openvswitch
-
- # Create ovs-vswitchd config database
- ovsdb-tool -vconsole:off create /etc/openvswitch/conf.db \
- /usr/share/openvswitch/vswitch.ovsschema
-
- # Create initial table in config database
- ovsdb-tool -vconsole:off transact /etc/openvswitch/conf.db \
- '[{"op": "insert", "table": "Open_vSwitch", "row": {}}]' \
- > /dev/null
-fi
-
-# Create default or update existing /etc/sysconfig/openvswitch.
-SYSCONFIG=/etc/sysconfig/openvswitch
-TEMPLATE=/usr/share/openvswitch/scripts/sysconfig.template
-if [ ! -e $SYSCONFIG ]; then
- cp $TEMPLATE $SYSCONFIG
-else
- for var in $(awk -F'[ :]' '/^# [_A-Z0-9]+:/{print $2}' $TEMPLATE)
- do
- if ! grep $var $SYSCONFIG >/dev/null 2>&1; then
- echo >> $SYSCONFIG
- sed -n "/$var:/,/$var=/p" $TEMPLATE >> $SYSCONFIG
- fi
- done
-fi
-
-# Deliberately break %postun in broken OVS builds that revert original
-# XenServer scripts during rpm -U by moving the directory where it thinks
-# they are saved.
-if [ -d /usr/lib/openvswitch/xs-original ]; then
- mkdir -p /usr/lib/openvswitch/xs-saved
- mv /usr/lib/openvswitch/xs-original/* /usr/lib/openvswitch/xs-saved/ &&
- rmdir /usr/lib/openvswitch/xs-original
-fi
-
-# Replace XenServer files by our versions.
-mkdir -p /usr/lib/openvswitch/xs-saved \
- || printf "Could not create script backup directory.\n"
-for f in $replace_files; do
- s=$(basename "$f")
- t=$(readlink "$f")
- if [ -f "$f" ] && [ "$t" != "/usr/share/openvswitch/scripts/$s" ]; then
- mv "$f" /usr/lib/openvswitch/xs-saved/ \
- || printf "Could not save original XenServer $s script\n"
- ln -s "/usr/share/openvswitch/scripts/$s" "$f" \
- || printf "Could not link to Open vSwitch $s script\n"
- fi
-done
-
-# Clean up dangling symlinks to removed OVS replacement scripts no longer
-# provided by OVS. Any time a replacement script is removed from OVS,
-# it should be added here to ensure correct reversion from old versions of
-# OVS that don't clean up dangling symlinks during the uninstall phase.
-for orig in /usr/sbin/xen-bugtool $keep_files; do
- saved=/usr/lib/openvswitch/xs-saved/$(basename "$orig")
- [ -e "$saved" ] && mv -f "$saved" "$orig"
-done
-
-# Ensure all required services are set to run
-for s in openvswitch openvswitch-xapi-update; do
- if chkconfig --list $s >/dev/null 2>&1; then
- chkconfig --del $s || printf "Could not remove $s init script.\n"
- fi
- chkconfig --add $s || printf "Could not add $s init script.\n"
- chkconfig $s on || printf "Could not enable $s init script.\n"
-done
-
-if [ "$1" = "1" ]; then # $1 = 1 for install
- # Configure system to use Open vSwitch
- /opt/xensource/bin/xe-switch-network-backend vswitch
-else # $1 = 2 for upgrade
-
- mode=$(cat /etc/xensource/network.conf)
- if [ "$mode" != "vswitch" ] && [ "$mode" != "openvswitch" ]; then
- printf "\nThe server is not configured to run Open vSwitch. To run in\n"
- printf "vswitch mode, you must run the following command:\n\n"
- printf " xe-switch-network-backend vswitch"
- printf "\n\n"
- fi
-fi
-
-%posttrans %{module_package}
-# Ensure that modprobe will find our modules.
-#
-# This has to be in %posttrans instead of %post because older versions
-# installed modules into a different directory and "rpm -U" runs the
-# new version's %post before removing the old version's files, so if
-# we use %post then depmod may find the old versions that are about to
-# be removed.
-depmod %{xen_version}
-
-mode=$(cat /etc/xensource/network.conf)
-if [ "$mode" = "vswitch" ] || [ "$mode" = "openvswitch" ]; then
- printf "\nTo use the newly installed Open vSwitch kernel module, you\n"
- printf "will either have to reboot the hypervisor or follow any\n"
- printf "workarounds provided by your administration guide. Failure to do\n"
- printf "so may result in incorrect operation."
- printf "\n\n"
-fi
-
-%preun
-if [ "$1" = "0" ]; then # $1 = 0 for uninstall
- # Configure system to use bridge
- /opt/xensource/bin/xe-switch-network-backend bridge
-
- # The "openvswitch" service should have been removed from
- # "xe-switch-network-backend bridge".
- for s in openvswitch openvswitch-xapi-update; do
- if chkconfig --list $s >/dev/null 2>&1; then
- chkconfig --del $s || printf "Could not remove $s init script."
- fi
- done
-fi
-
-%postun
-# Restore original XenServer scripts if the OVS equivalent no longer exists.
-# This works both in the upgrade and erase cases.
-# This lists every file that every version of OVS has ever replaced. Never
-# remove old files that OVS no longer replaces, or upgrades from old versions
-# will fail to restore the XS originals, leaving the system in a broken state.
-# Also be sure to add removed script paths to the %post scriptlet above to
-# prevent the same problem when upgrading from old versions of OVS that lack
-# this restore-on-upgrade logic.
-for f in \
- /etc/xensource/scripts/vif \
- /usr/sbin/xen-bugtool \
- /opt/xensource/libexec/interface-reconfigure \
- /opt/xensource/libexec/InterfaceReconfigure.py \
- /opt/xensource/libexec/InterfaceReconfigureBridge.py \
- /opt/xensource/libexec/InterfaceReconfigureVswitch.py
-do
- # Only revert dangling symlinks.
- if [ -h "$f" ] && [ ! -e "$f" ]; then
- s=$(basename "$f")
- if [ ! -f "/usr/lib/openvswitch/xs-saved/$s" ]; then
- printf "Original XenServer $s script not present in /usr/lib/openvswitch/xs-saved\n" >&2
- printf "Could not restore original XenServer script.\n" >&2
- else
- (rm -f "$f" \
- && mv "/usr/lib/openvswitch/xs-saved/$s" "$f") \
- || printf "Could not restore original XenServer $s script.\n" >&2
- fi
- fi
-done
-
-if [ "$1" = "0" ]; then # $1 = 0 for uninstall
- rm -f /usr/lib/xsconsole/plugins-base/XSFeatureVSwitch.pyc \
- /usr/lib/xsconsole/plugins-base/XSFeatureVSwitch.pyo
-
- rm -f /usr/share/openvswitch/scripts/InterfaceReconfigure.pyc \
- /usr/share/openvswitch/scripts/InterfaceReconfigure.pyo \
- /usr/share/openvswitch/scripts/InterfaceReconfigureBridge.pyc \
- /usr/share/openvswitch/scripts/InterfaceReconfigureBridge.pyo \
- /usr/share/openvswitch/scripts/InterfaceReconfigureVSwitch.pyc \
- /usr/share/openvswitch/scripts/InterfaceReconfigureVSwitch.pyo
-
- # Remove all configuration files
- rm -f /etc/openvswitch/conf.db
- rm -f /etc/sysconfig/openvswitch
- rm -f /etc/openvswitch/vswitchd.cacert
-
- # Remove saved XenServer scripts directory, but only if it's empty
- rmdir -p /usr/lib/openvswitch/xs-saved 2>/dev/null
-fi
-
-exit 0
-
-%files
-%defattr(-,root,root)
-/etc/bash_completion.d/ovs-appctl-bashcomp.bash
-/etc/bash_completion.d/ovs-vsctl-bashcomp.bash
-/etc/init.d/openvswitch
-/etc/init.d/openvswitch-xapi-update
-/etc/xapi.d/plugins/openvswitch-cfg-update
-/etc/xensource/bugtool/*
-/etc/logrotate.d/openvswitch
-/etc/profile.d/openvswitch.sh
-/usr/share/openvswitch/python/
-/usr/share/openvswitch/bugtool-plugins/*
-/usr/share/openvswitch/scripts/ovs-check-dead-ifs
-/usr/share/openvswitch/scripts/ovs-xapi-sync
-/usr/share/openvswitch/scripts/interface-reconfigure
-/usr/share/openvswitch/scripts/InterfaceReconfigure.py
-/usr/share/openvswitch/scripts/InterfaceReconfigureBridge.py
-/usr/share/openvswitch/scripts/InterfaceReconfigureVswitch.py
-/usr/share/openvswitch/scripts/vif
-/usr/share/openvswitch/scripts/sysconfig.template
-/usr/share/openvswitch/scripts/ovs-bugtool-*
-/usr/share/openvswitch/scripts/ovs-save
-/usr/share/openvswitch/scripts/ovs-ctl
-/usr/share/openvswitch/scripts/ovs-lib
-/usr/share/openvswitch/scripts/ovs-vtep
-/usr/share/openvswitch/vswitch.ovsschema
-/usr/share/openvswitch/local-config.ovsschema
-/usr/share/openvswitch/vtep.ovsschema
-/usr/sbin/ovs-bugtool
-/usr/sbin/ovs-vswitchd
-/usr/sbin/ovsdb-server
-/usr/bin/ovs-appctl
-/usr/bin/ovs-dpctl
-/usr/bin/ovs-dpctl-top
-/usr/bin/ovs-docker
-/usr/bin/ovs-ofctl
-/usr/bin/ovs-parse-backtrace
-/usr/bin/ovs-pcap
-/usr/bin/ovs-tcpundump
-/usr/bin/ovs-vlan-test
-/usr/bin/ovs-vsctl
-/usr/bin/ovsdb-client
-/usr/bin/ovsdb-tool
-/usr/bin/vtep-ctl
-/usr/bin/ovs-tcpdump
-/usr/lib/xsconsole/plugins-base/XSFeatureVSwitch.py
-/usr/share/man/man1/ovsdb-client.1.gz
-/usr/share/man/man1/ovsdb-server.1.gz
-/usr/share/man/man1/ovsdb-tool.1.gz
-/usr/share/man/man5/ovsdb.local-config.5.gz
-/usr/share/man/man5/ovsdb-server.5.gz
-/usr/share/man/man5/ovs-vswitchd.conf.db.5.gz
-/usr/share/man/man5/vtep.5.gz
-/usr/share/man/man7/ovs-fields.7.gz
-/usr/share/man/man8/ovs-appctl.8.gz
-/usr/share/man/man8/ovs-bugtool.8.gz
-/usr/share/man/man8/ovs-ctl.8.gz
-/usr/share/man/man8/ovs-dpctl.8.gz
-/usr/share/man/man8/ovs-dpctl-top.8.gz
-/usr/share/man/man8/ovs-ofctl.8.gz
-/usr/share/man/man8/ovs-parse-backtrace.8.gz
-/usr/share/man/man1/ovs-pcap.1.gz
-/usr/share/man/man1/ovs-tcpundump.1.gz
-/usr/share/man/man8/ovs-vlan-test.8.gz
-/usr/share/man/man8/ovs-vsctl.8.gz
-/usr/share/man/man8/ovs-vswitchd.8.gz
-/usr/share/man/man8/vtep-ctl.8.gz
-/usr/share/man/man8/ovs-tcpdump.8.gz
-/var/lib/openvswitch
-/var/log/openvswitch
-%exclude /usr/lib/xsconsole/plugins-base/*.py[co]
-%exclude /usr/share/openvswitch/scripts/*.py[co]
-%exclude /usr/share/openvswitch/python/*.py[co]
-%exclude /usr/share/openvswitch/python/ovs/*.py[co]
-%exclude /usr/share/openvswitch/python/ovs/db/*.py[co]
-
-%files %{module_package}
-/lib/modules/%{xen_version}/extra/openvswitch/openvswitch.ko
-/lib/modules/%{xen_version}/extra/openvswitch/vport-*.ko
diff --git a/xenserver/opt_xensource_libexec_InterfaceReconfigure.py b/xenserver/opt_xensource_libexec_InterfaceReconfigure.py
deleted file mode 100644
index 74b784d34..000000000
--- a/xenserver/opt_xensource_libexec_InterfaceReconfigure.py
+++ /dev/null
@@ -1,972 +0,0 @@
-# Copyright (c) 2008,2009 Citrix Systems, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
-# by the Free Software Foundation; version 2.1 only. with the special
-# exception on linking described in file LICENSE.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU Lesser General Public License for more details.
-#
-import sys
-import syslog
-import os
-
-from xml.dom.minidom import getDOMImplementation
-from xml.dom.minidom import parse as parseXML
-
-the_root_prefix = ""
-def root_prefix():
- """Returns a string to prefix to all file name references, which
- is useful for testing."""
- return the_root_prefix
-def set_root_prefix(prefix):
- global the_root_prefix
- the_root_prefix = prefix
-
-log_destination = "syslog"
-def get_log_destination():
- """Returns the current log destination.
- 'syslog' means "log to syslog".
- 'stderr' means "log to stderr"."""
- return log_destination
-def set_log_destination(dest):
- global log_destination
- log_destination = dest
-
-#
-# Logging.
-#
-
-def log(s):
- if get_log_destination() == 'syslog':
- syslog.syslog(s)
- else:
- sys.stderr.write(s + '\n')
- sys.stderr.flush()
-
-#
-# Exceptions.
-#
-
-class Error(Exception):
- def __init__(self, msg):
- Exception.__init__(self)
- self.msg = msg
-
-#
-# Run external utilities
-#
-
-def run_command(command):
- log("Running command: " + ' '.join(command))
- rc = os.spawnl(os.P_WAIT, root_prefix() + command[0], *command)
- if rc != 0:
- log("Command failed %d: " % rc + ' '.join(command))
- return False
- return True
-
-#
-# Configuration File Handling.
-#
-
-class ConfigurationFile(object):
- """Write a file, tracking old and new versions.
-
- Supports writing a new version of a file and applying and
- reverting those changes.
- """
-
- __STATE = {"OPEN":"OPEN",
- "NOT-APPLIED":"NOT-APPLIED", "APPLIED":"APPLIED",
- "REVERTED":"REVERTED", "COMMITTED": "COMMITTED"}
-
- def __init__(self, path):
- dirname,basename = os.path.split(path)
-
- self.__state = self.__STATE['OPEN']
- self.__children = []
-
- self.__path = os.path.join(dirname, basename)
- self.__oldpath = os.path.join(dirname, "." + basename + ".xapi-old")
- self.__newpath = os.path.join(dirname, "." + basename + ".xapi-new")
-
- self.__f = open(self.__newpath, "w")
-
- def attach_child(self, child):
- self.__children.append(child)
-
- def path(self):
- return self.__path
-
- def readlines(self):
- try:
- return open(self.path()).readlines()
- except:
- return ""
-
- def write(self, args):
- if self.__state != self.__STATE['OPEN']:
- raise Error("Attempt to write to file in state %s" % self.__state)
- self.__f.write(args)
-
- def close(self):
- if self.__state != self.__STATE['OPEN']:
- raise Error("Attempt to close file in state %s" % self.__state)
-
- self.__f.close()
- self.__state = self.__STATE['NOT-APPLIED']
-
- def changed(self):
- if self.__state != self.__STATE['NOT-APPLIED']:
- raise Error("Attempt to compare file in state %s" % self.__state)
-
- return True
-
- def apply(self):
- if self.__state != self.__STATE['NOT-APPLIED']:
- raise Error("Attempt to apply configuration from state %s" % self.__state)
-
- for child in self.__children:
- child.apply()
-
- log("Applying changes to %s configuration" % self.__path)
-
- # Remove previous backup.
- if os.access(self.__oldpath, os.F_OK):
- os.unlink(self.__oldpath)
-
- # Save current configuration.
- if os.access(self.__path, os.F_OK):
- os.link(self.__path, self.__oldpath)
- os.unlink(self.__path)
-
- # Apply new configuration.
- assert(os.path.exists(self.__newpath))
- os.link(self.__newpath, self.__path)
-
- # Remove temporary file.
- os.unlink(self.__newpath)
-
- self.__state = self.__STATE['APPLIED']
-
- def revert(self):
- if self.__state != self.__STATE['APPLIED']:
- raise Error("Attempt to revert configuration from state %s" % self.__state)
-
- for child in self.__children:
- child.revert()
-
- log("Reverting changes to %s configuration" % self.__path)
-
- # Remove existing new configuration
- if os.access(self.__newpath, os.F_OK):
- os.unlink(self.__newpath)
-
- # Revert new configuration.
- if os.access(self.__path, os.F_OK):
- os.link(self.__path, self.__newpath)
- os.unlink(self.__path)
-
- # Revert to old configuration.
- if os.access(self.__oldpath, os.F_OK):
- os.link(self.__oldpath, self.__path)
- os.unlink(self.__oldpath)
-
- # Leave .*.xapi-new as an aid to debugging.
-
- self.__state = self.__STATE['REVERTED']
-
- def commit(self):
- if self.__state != self.__STATE['APPLIED']:
- raise Error("Attempt to commit configuration from state %s" % self.__state)
-
- for child in self.__children:
- child.commit()
-
- log("Committing changes to %s configuration" % self.__path)
-
- if os.access(self.__oldpath, os.F_OK):
- os.unlink(self.__oldpath)
- if os.access(self.__newpath, os.F_OK):
- os.unlink(self.__newpath)
-
- self.__state = self.__STATE['COMMITTED']
-
-#
-# Helper functions for encoding/decoding database attributes to/from XML.
-#
-
-def _str_to_xml(xml, parent, tag, val):
- e = xml.createElement(tag)
- parent.appendChild(e)
- v = xml.createTextNode(val)
- e.appendChild(v)
-def _str_from_xml(n):
- def getText(nodelist):
- rc = ""
- for node in nodelist:
- if node.nodeType == node.TEXT_NODE:
- rc = rc + node.data
- return rc
- return getText(n.childNodes).strip()
-
-def _bool_to_xml(xml, parent, tag, val):
- if val:
- _str_to_xml(xml, parent, tag, "True")
- else:
- _str_to_xml(xml, parent, tag, "False")
-def _bool_from_xml(n):
- s = _str_from_xml(n)
- if s == "True":
- return True
- elif s == "False":
- return False
- else:
- raise Error("Unknown boolean value %s" % s)
-
-def _strlist_to_xml(xml, parent, ltag, itag, val):
- e = xml.createElement(ltag)
- parent.appendChild(e)
- for v in val:
- c = xml.createElement(itag)
- e.appendChild(c)
- cv = xml.createTextNode(v)
- c.appendChild(cv)
-def _strlist_from_xml(n, ltag, itag):
- ret = []
- for n in n.childNodes:
- if n.nodeName == itag:
- ret.append(_str_from_xml(n))
- return ret
-
-def _map_to_xml(xml, parent, tag, val, attrs):
- e = xml.createElement(tag)
- parent.appendChild(e)
- for n,v in val.items():
- if n in attrs:
- _str_to_xml(xml, e, n, v)
- else:
- log("Unknown other-config attribute: %s" % n)
-
-def _map_from_xml(n, attrs):
- ret = {}
- for n in n.childNodes:
- if n.nodeName in attrs:
- ret[n.nodeName] = _str_from_xml(n)
- return ret
-
-def _otherconfig_to_xml(xml, parent, val, attrs):
- return _map_to_xml(xml, parent, "other_config", val, attrs)
-def _otherconfig_from_xml(n, attrs):
- return _map_from_xml(n, attrs)
-
-#
-# Definitions of the database objects (and their attributes) used by interface-reconfigure.
-#
-# Each object is defined by a dictionary mapping an attribute name in
-# the xapi database to a tuple containing two items:
-# - a function which takes this attribute and encodes it as XML.
-# - a function which takes XML and decocdes it into a value.
-#
-# other-config attributes are specified as a simple array of strings
-
-_PIF_XML_TAG = "pif"
-_VLAN_XML_TAG = "vlan"
-_TUNNEL_XML_TAG = "tunnel"
-_BOND_XML_TAG = "bond"
-_NETWORK_XML_TAG = "network"
-_POOL_XML_TAG = "pool"
-
-_ETHTOOL_OTHERCONFIG_ATTRS = ['ethtool-%s' % x for x in ['autoneg', 'speed', 'duplex', 'rx', 'tx', 'sg', 'tso', 'ufo', 'gso', 'gro', 'lro'] ]
-
-_PIF_OTHERCONFIG_ATTRS = [ 'domain', 'peerdns', 'defaultroute', 'mtu', 'static-routes' ] + \
- [ 'bond-%s' % x for x in ['mode', 'miimon', 'downdelay', 'updelay', 'use_carrier', 'hashing-algorithm'] ] + \
- [ 'vlan-bug-workaround' ] + \
- _ETHTOOL_OTHERCONFIG_ATTRS
-
-_PIF_ATTRS = { 'uuid': (_str_to_xml,_str_from_xml),
- 'management': (_bool_to_xml,_bool_from_xml),
- 'network': (_str_to_xml,_str_from_xml),
- 'device': (_str_to_xml,_str_from_xml),
- 'bond_master_of': (lambda x, p, t, v: _strlist_to_xml(x, p, 'bond_master_of', 'slave', v),
- lambda n: _strlist_from_xml(n, 'bond_master_of', 'slave')),
- 'bond_slave_of': (_str_to_xml,_str_from_xml),
- 'VLAN': (_str_to_xml,_str_from_xml),
- 'VLAN_master_of': (_str_to_xml,_str_from_xml),
- 'VLAN_slave_of': (lambda x, p, t, v: _strlist_to_xml(x, p, 'VLAN_slave_of', 'master', v),
- lambda n: _strlist_from_xml(n, 'VLAN_slave_Of', 'master')),
- 'tunnel_access_PIF_of': (lambda x, p, t, v: _strlist_to_xml(x, p, 'tunnel_access_PIF_of', 'pif', v),
- lambda n: _strlist_from_xml(n, 'tunnel_access_PIF_of', 'pif')),
- 'tunnel_transport_PIF_of': (lambda x, p, t, v: _strlist_to_xml(x, p, 'tunnel_transport_PIF_of', 'pif', v),
- lambda n: _strlist_from_xml(n, 'tunnel_transport_PIF_of', 'pif')),
- 'ip_configuration_mode': (_str_to_xml,_str_from_xml),
- 'IP': (_str_to_xml,_str_from_xml),
- 'netmask': (_str_to_xml,_str_from_xml),
- 'gateway': (_str_to_xml,_str_from_xml),
- 'DNS': (_str_to_xml,_str_from_xml),
- 'MAC': (_str_to_xml,_str_from_xml),
- 'other_config': (lambda x, p, t, v: _otherconfig_to_xml(x, p, v, _PIF_OTHERCONFIG_ATTRS),
- lambda n: _otherconfig_from_xml(n, _PIF_OTHERCONFIG_ATTRS)),
-
- # Special case: We write the current value
- # PIF.currently-attached to the cache but since it will
- # not be valid when we come to use the cache later
- # (i.e. after a reboot) we always read it as False.
- 'currently_attached': (_bool_to_xml, lambda n: False),
- }
-
-_VLAN_ATTRS = { 'uuid': (_str_to_xml,_str_from_xml),
- 'tagged_PIF': (_str_to_xml,_str_from_xml),
- 'untagged_PIF': (_str_to_xml,_str_from_xml),
- }
-
-_TUNNEL_ATTRS = { 'uuid': (_str_to_xml,_str_from_xml),
- 'access_PIF': (_str_to_xml,_str_from_xml),
- 'transport_PIF': (_str_to_xml,_str_from_xml),
- }
-_BOND_ATTRS = { 'uuid': (_str_to_xml,_str_from_xml),
- 'master': (_str_to_xml,_str_from_xml),
- 'slaves': (lambda x, p, t, v: _strlist_to_xml(x, p, 'slaves', 'slave', v),
- lambda n: _strlist_from_xml(n, 'slaves', 'slave')),
- }
-
-_NETWORK_OTHERCONFIG_ATTRS = [ 'mtu',
- 'static-routes',
- 'vswitch-controller-fail-mode',
- 'vswitch-disable-in-band' ] \
- + _ETHTOOL_OTHERCONFIG_ATTRS
-
-_NETWORK_ATTRS = { 'uuid': (_str_to_xml,_str_from_xml),
- 'bridge': (_str_to_xml,_str_from_xml),
- 'MTU': (_str_to_xml,_str_from_xml),
- 'PIFs': (lambda x, p, t, v: _strlist_to_xml(x, p, 'PIFs', 'PIF', v),
- lambda n: _strlist_from_xml(n, 'PIFs', 'PIF')),
- 'other_config': (lambda x, p, t, v: _otherconfig_to_xml(x, p, v, _NETWORK_OTHERCONFIG_ATTRS),
- lambda n: _otherconfig_from_xml(n, _NETWORK_OTHERCONFIG_ATTRS)),
- }
-
-_POOL_OTHERCONFIG_ATTRS = ['vswitch-controller-fail-mode']
-
-_POOL_ATTRS = { 'other_config': (lambda x, p, t, v: _otherconfig_to_xml(x, p, v, _POOL_OTHERCONFIG_ATTRS),
- lambda n: _otherconfig_from_xml(n, _POOL_OTHERCONFIG_ATTRS)),
- }
-
-#
-# Database Cache object
-#
-
-_db = None
-
-def db():
- assert(_db is not None)
- return _db
-
-def db_init_from_cache(cache):
- global _db
- assert(_db is None)
- _db = DatabaseCache(cache_file=cache)
-
-def db_init_from_xenapi(session):
- global _db
- assert(_db is None)
- _db = DatabaseCache(session_ref=session)
-
-class DatabaseCache(object):
- def __read_xensource_inventory(self):
- filename = root_prefix() + "/etc/xensource-inventory"
- f = open(filename, "r")
- lines = [x.strip("\n") for x in f.readlines()]
- f.close()
-
- defs = [ (l[:l.find("=")], l[(l.find("=") + 1):]) for l in lines ]
- defs = [ (a, b.strip("'")) for (a,b) in defs ]
-
- return dict(defs)
-
- def __pif_on_host(self,pif):
- return pif in self.__pifs
-
- def __get_pif_records_from_xapi(self, session, host):
- self.__pifs = {}
- for (p,rec) in session.xenapi.PIF.get_all_records().items():
- if rec['host'] != host:
- continue
- self.__pifs[p] = {}
- for f in _PIF_ATTRS:
- self.__pifs[p][f] = rec[f]
- self.__pifs[p]['other_config'] = {}
- for f in _PIF_OTHERCONFIG_ATTRS:
- if f not in rec['other_config']: continue
- self.__pifs[p]['other_config'][f] = rec['other_config'][f]
-
- def __get_vlan_records_from_xapi(self, session):
- self.__vlans = {}
- for (v,rec) in session.xenapi.VLAN.get_all_records().items():
- if not self.__pif_on_host(rec['untagged_PIF']):
- continue
- self.__vlans[v] = {}
- for f in _VLAN_ATTRS:
- self.__vlans[v][f] = rec[f]
-
- def __get_tunnel_records_from_xapi(self, session):
- self.__tunnels = {}
- for t in session.xenapi.tunnel.get_all():
- rec = session.xenapi.tunnel.get_record(t)
- if not self.__pif_on_host(rec['transport_PIF']):
- continue
- self.__tunnels[t] = {}
- for f in _TUNNEL_ATTRS:
- self.__tunnels[t][f] = rec[f]
-
- def __get_bond_records_from_xapi(self, session):
- self.__bonds = {}
- for (b,rec) in session.xenapi.Bond.get_all_records().items():
- if not self.__pif_on_host(rec['master']):
- continue
- self.__bonds[b] = {}
- for f in _BOND_ATTRS:
- self.__bonds[b][f] = rec[f]
-
- def __get_network_records_from_xapi(self, session):
- self.__networks = {}
- for (n,rec) in session.xenapi.network.get_all_records().items():
- self.__networks[n] = {}
- for f in _NETWORK_ATTRS:
- if f == "PIFs":
- # drop PIFs on other hosts
- self.__networks[n][f] = [p for p in rec[f] if self.__pif_on_host(p)]
- elif f == "MTU" and f not in rec:
- # XenServer 5.5 network records did not have an
- # MTU field, so allow this to be missing.
- pass
- else:
- self.__networks[n][f] = rec[f]
- self.__networks[n]['other_config'] = {}
- for f in _NETWORK_OTHERCONFIG_ATTRS:
- if f not in rec['other_config']: continue
- self.__networks[n]['other_config'][f] = rec['other_config'][f]
-
- def __get_pool_records_from_xapi(self, session):
- self.__pools = {}
- for p in session.xenapi.pool.get_all():
- rec = session.xenapi.pool.get_record(p)
-
- self.__pools[p] = {}
-
- for f in _POOL_ATTRS:
- self.__pools[p][f] = rec[f]
-
- for f in _POOL_OTHERCONFIG_ATTRS:
- if f in rec['other_config']:
- self.__pools[p]['other_config'][f] = rec['other_config'][f]
-
- def __to_xml(self, xml, parent, key, ref, rec, attrs):
- """Encode a database object as XML"""
- e = xml.createElement(key)
- parent.appendChild(e)
- if ref:
- e.setAttribute('ref', ref)
-
- for n,v in rec.items():
- if n in attrs:
- h,_ = attrs[n]
- h(xml, e, n, v)
- else:
- raise Error("Unknown attribute %s" % n)
- def __from_xml(self, e, attrs):
- """Decode a database object from XML"""
- ref = e.attributes['ref'].value
- rec = {}
- for n in e.childNodes:
- if n.nodeName in attrs:
- _,h = attrs[n.nodeName]
- rec[n.nodeName] = h(n)
- return (ref,rec)
-
- def __init__(self, session_ref=None, cache_file=None):
- if session_ref and cache_file:
- raise Error("can't specify session reference and cache file")
- if cache_file == None:
- import XenAPI
- session = XenAPI.xapi_local()
-
- if not session_ref:
- log("No session ref given on command line, logging in.")
- session.xenapi.login_with_password("root", "")
- else:
- session._session = session_ref
-
- try:
-
- inventory = self.__read_xensource_inventory()
- assert('INSTALLATION_UUID' in inventory)
- log("host uuid is %s" % inventory['INSTALLATION_UUID'])
-
- host = session.xenapi.host.get_by_uuid(inventory['INSTALLATION_UUID'])
-
- self.__get_pif_records_from_xapi(session, host)
- self.__get_pool_records_from_xapi(session)
- self.__get_tunnel_records_from_xapi(session)
- self.__get_vlan_records_from_xapi(session)
- self.__get_bond_records_from_xapi(session)
- self.__get_network_records_from_xapi(session)
- finally:
- if not session_ref:
- session.xenapi.session.logout()
- else:
- log("Loading xapi database cache from %s" % cache_file)
-
- xml = parseXML(root_prefix() + cache_file)
-
- self.__pifs = {}
- self.__bonds = {}
- self.__vlans = {}
- self.__pools = {}
- self.__tunnels = {}
- self.__networks = {}
-
- assert(len(xml.childNodes) == 1)
- toplevel = xml.childNodes[0]
-
- assert(toplevel.nodeName == "xenserver-network-configuration")
-
- for n in toplevel.childNodes:
- if n.nodeName == "#text":
- pass
- elif n.nodeName == _PIF_XML_TAG:
- (ref,rec) = self.__from_xml(n, _PIF_ATTRS)
- self.__pifs[ref] = rec
- elif n.nodeName == _BOND_XML_TAG:
- (ref,rec) = self.__from_xml(n, _BOND_ATTRS)
- self.__bonds[ref] = rec
- elif n.nodeName == _VLAN_XML_TAG:
- (ref,rec) = self.__from_xml(n, _VLAN_ATTRS)
- self.__vlans[ref] = rec
- elif n.nodeName == _TUNNEL_XML_TAG:
- (ref,rec) = self.__from_xml(n, _TUNNEL_ATTRS)
- self.__vlans[ref] = rec
- elif n.nodeName == _NETWORK_XML_TAG:
- (ref,rec) = self.__from_xml(n, _NETWORK_ATTRS)
- self.__networks[ref] = rec
- elif n.nodeName == _POOL_XML_TAG:
- (ref,rec) = self.__from_xml(n, _POOL_ATTRS)
- self.__pools[ref] = rec
- else:
- raise Error("Unknown XML element %s" % n.nodeName)
-
- def save(self, cache_file):
-
- xml = getDOMImplementation().createDocument(
- None, "xenserver-network-configuration", None)
- for (ref,rec) in self.__pifs.items():
- self.__to_xml(xml, xml.documentElement, _PIF_XML_TAG, ref, rec, _PIF_ATTRS)
- for (ref,rec) in self.__bonds.items():
- self.__to_xml(xml, xml.documentElement, _BOND_XML_TAG, ref, rec, _BOND_ATTRS)
- for (ref,rec) in self.__vlans.items():
- self.__to_xml(xml, xml.documentElement, _VLAN_XML_TAG, ref, rec, _VLAN_ATTRS)
- for (ref,rec) in self.__tunnels.items():
- self.__to_xml(xml, xml.documentElement, _TUNNEL_XML_TAG, ref, rec, _TUNNEL_ATTRS)
- for (ref,rec) in self.__networks.items():
- self.__to_xml(xml, xml.documentElement, _NETWORK_XML_TAG, ref, rec,
- _NETWORK_ATTRS)
- for (ref,rec) in self.__pools.items():
- self.__to_xml(xml, xml.documentElement, _POOL_XML_TAG, ref, rec, _POOL_ATTRS)
-
- temp_file = cache_file + ".%d" % os.getpid()
- f = open(temp_file, 'w')
- f.write(xml.toprettyxml())
- f.close()
- os.rename(temp_file, cache_file)
-
- def get_pif_by_uuid(self, uuid):
- pifs = map(lambda ref_rec: ref_rec[0],
- filter(lambda ref_rec: uuid == ref_rec[1]['uuid'],
- self.__pifs.items()))
- if len(pifs) == 0:
- raise Error("Unknown PIF \"%s\"" % uuid)
- elif len(pifs) > 1:
- raise Error("Non-unique PIF \"%s\"" % uuid)
-
- return pifs[0]
-
- def get_pifs_by_device(self, device):
- return list(map(lambda ref_rec: ref_rec[0],
- list(filter(lambda ref_rec: ref_rec[1]['device'] == device,
- self.__pifs.items()))))
-
- def get_networks_with_bridge(self, bridge):
- return list(map(lambda ref_rec: ref_rec[0],
- list(filter(lambda ref_rec: ref_rec[1]['bridge'] == bridge,
- self.__networks.items()))))
-
- def get_network_by_bridge(self, bridge):
- #Assumes one network has bridge.
- try:
- return self.get_networks_with_bridge(bridge)[0]
- except KeyError:
- return None
-
- def get_pif_by_bridge(self, bridge):
- networks = self.get_networks_with_bridge(bridge)
-
- if len(networks) == 0:
- raise Error("No matching network \"%s\"" % bridge)
-
- answer = None
- for network in networks:
- nwrec = self.get_network_record(network)
- for pif in nwrec['PIFs']:
- pifrec = self.get_pif_record(pif)
- if answer:
- raise Error("Multiple PIFs on host for network %s" % (bridge))
- answer = pif
- if not answer:
- raise Error("No PIF on host for network %s" % (bridge))
- return answer
-
- def get_pif_record(self, pif):
- if pif in self.__pifs:
- return self.__pifs[pif]
- raise Error("Unknown PIF \"%s\"" % pif)
- def get_all_pifs(self):
- return self.__pifs
- def pif_exists(self, pif):
- return pif in self.__pifs
-
- def get_management_pif(self):
- """ Returns the management pif on host
- """
- all = self.get_all_pifs()
- for pif in all:
- pifrec = self.get_pif_record(pif)
- if pifrec['management']: return pif
- return None
-
- def get_network_record(self, network):
- if network in self.__networks:
- return self.__networks[network]
- raise Error("Unknown network \"%s\"" % network)
-
- def get_bond_record(self, bond):
- if bond in self.__bonds:
- return self.__bonds[bond]
- else:
- return None
-
- def get_vlan_record(self, vlan):
- if vlan in self.__vlans:
- return self.__vlans[vlan]
- else:
- return None
-
- def get_pool_record(self):
- if len(self.__pools) > 0:
- return list(self.__pools.values())[0]
-
-#
-#
-#
-PIF_OTHERCONFIG_DEFAULTS = {'gro': 'off', 'lro': 'off'}
-
-def ethtool_settings(oc, defaults = {}):
- settings = []
- if 'ethtool-speed' in oc:
- val = oc['ethtool-speed']
- if val in ["10", "100", "1000"]:
- settings += ['speed', val]
- else:
- log("Invalid value for ethtool-speed = %s. Must be 10|100|1000." % val)
- if 'ethtool-duplex' in oc:
- val = oc['ethtool-duplex']
- if val in ["half", "full"]:
- settings += ['duplex', val]
- else:
- log("Invalid value for ethtool-duplex = %s. Must be half|full." % val)
- if 'ethtool-autoneg' in oc:
- val = oc['ethtool-autoneg']
- if val in ["true", "on"]:
- settings += ['autoneg', 'on']
- elif val in ["false", "off"]:
- settings += ['autoneg', 'off']
- else:
- log("Invalid value for ethtool-autoneg = %s. Must be on|true|off|false." % val)
- offload = []
- for opt in ("rx", "tx", "sg", "tso", "ufo", "gso", "gro", "lro"):
- if "ethtool-" + opt in oc:
- val = oc["ethtool-" + opt]
- if val in ["true", "on"]:
- offload += [opt, 'on']
- elif val in ["false", "off"]:
- offload += [opt, 'off']
- else:
- log("Invalid value for ethtool-%s = %s. Must be on|true|off|false." % (opt, val))
- elif opt in defaults:
- offload += [opt, defaults[opt]]
- return settings,offload
-
-# By default the MTU is taken from the Network.MTU setting for VIF,
-# PIF and Bridge. However it is possible to override this by using
-# {VIF,PIF,Network}.other-config:mtu.
-#
-# type parameter is a string describing the object that the oc parameter
-# is from. e.g. "PIF", "Network"
-def mtu_setting(nw, type, oc):
- mtu = None
-
- nwrec = db().get_network_record(nw)
- if 'MTU' in nwrec:
- mtu = nwrec['MTU']
- else:
- mtu = "1500"
-
- if 'mtu' in oc:
- log("Override Network.MTU setting on bridge %s from %s.MTU is %s" % \
- (nwrec['bridge'], type, mtu))
- mtu = oc['mtu']
-
- if mtu is not None:
- try:
- int(mtu) # Check that the value is an integer
- return mtu
- except ValueError as x:
- log("Invalid value for mtu = %s" % mtu)
-
- return None
-
-#
-# IP Network Devices -- network devices with IP configuration
-#
-def pif_ipdev_name(pif):
- """Return the ipdev name associated with pif"""
- pifrec = db().get_pif_record(pif)
- nwrec = db().get_network_record(pifrec['network'])
-
- if nwrec['bridge']:
- # TODO: sanity check that nwrec['bridgeless'] != 'true'
- return nwrec['bridge']
- else:
- # TODO: sanity check that nwrec['bridgeless'] == 'true'
- return pif_netdev_name(pif)
-
-#
-# Bare Network Devices -- network devices without IP configuration
-#
-
-def netdev_exists(netdev):
- return os.path.exists(root_prefix() + "/sys/class/net/" + netdev)
-
-
-def unicode_2to3(string):
- if sys.version_info < (3,):
- return string.encode()
- return string
-
-
-def pif_netdev_name(pif):
- """Get the netdev name for a PIF."""
-
- pifrec = db().get_pif_record(pif)
-
- if pif_is_vlan(pif):
- return unicode_2to3("%(device)s.%(VLAN)s" % pifrec)
- else:
- return unicode_2to3(pifrec['device'])
-
-#
-# Bridges
-#
-
-def pif_is_bridged(pif):
- pifrec = db().get_pif_record(pif)
- nwrec = db().get_network_record(pifrec['network'])
-
- if nwrec['bridge']:
- # TODO: sanity check that nwrec['bridgeless'] != 'true'
- return True
- else:
- # TODO: sanity check that nwrec['bridgeless'] == 'true'
- return False
-
-def pif_bridge_name(pif):
- """Return the bridge name of a pif.
-
- PIF must be a bridged PIF."""
- pifrec = db().get_pif_record(pif)
-
- nwrec = db().get_network_record(pifrec['network'])
-
- if nwrec['bridge']:
- return nwrec['bridge']
- else:
- raise Error("PIF %(uuid)s does not have a bridge name" % pifrec)
-
-#
-# Bonded PIFs
-#
-def pif_is_bond(pif):
- pifrec = db().get_pif_record(pif)
-
- return len(pifrec['bond_master_of']) > 0
-
-def pif_get_bond_masters(pif):
- """Returns a list of PIFs which are bond masters of this PIF"""
-
- pifrec = db().get_pif_record(pif)
-
- bso = pifrec['bond_slave_of']
-
- # bond-slave-of is currently a single reference but in principle a
- # PIF could be a member of several bonds which are not
- # concurrently attached. Be robust to this possibility.
- if not bso or bso == "OpaqueRef:NULL":
- bso = []
- elif not type(bso) == list:
- bso = [bso]
-
- bondrecs = [db().get_bond_record(bond) for bond in bso]
- bondrecs = [rec for rec in bondrecs if rec]
-
- return [bond['master'] for bond in bondrecs]
-
-def pif_get_bond_slaves(pif):
- """Returns a list of PIFs which make up the given bonded pif."""
-
- pifrec = db().get_pif_record(pif)
-
- bmo = pifrec['bond_master_of']
- if len(bmo) > 1:
- raise Error("Bond-master-of contains too many elements")
-
- if len(bmo) == 0:
- return []
-
- bondrec = db().get_bond_record(bmo[0])
- if not bondrec:
- raise Error("No bond record for bond master PIF")
-
- return bondrec['slaves']
-
-#
-# VLAN PIFs
-#
-
-def pif_is_vlan(pif):
- return db().get_pif_record(pif)['VLAN'] != '-1'
-
-def pif_get_vlan_slave(pif):
- """Find the PIF which is the VLAN slave of pif.
-
-Returns the 'physical' PIF underneath the a VLAN PIF @pif."""
-
- pifrec = db().get_pif_record(pif)
-
- vlan = pifrec['VLAN_master_of']
- if not vlan or vlan == "OpaqueRef:NULL":
- raise Error("PIF is not a VLAN master")
-
- vlanrec = db().get_vlan_record(vlan)
- if not vlanrec:
- raise Error("No VLAN record found for PIF")
-
- return vlanrec['tagged_PIF']
-
-def pif_get_vlan_masters(pif):
- """Returns a list of PIFs which are VLANs on top of the given pif."""
-
- pifrec = db().get_pif_record(pif)
- vlans = [db().get_vlan_record(v) for v in pifrec['VLAN_slave_of']]
- return [v['untagged_PIF'] for v in vlans if v and db().pif_exists(v['untagged_PIF'])]
-
-#
-# Tunnel PIFs
-#
-def pif_is_tunnel(pif):
- return len(db().get_pif_record(pif)['tunnel_access_PIF_of']) > 0
-
-#
-# Datapath base class
-#
-
-class Datapath(object):
- """Object encapsulating the actions necessary to (de)configure the
- datapath for a given PIF. Does not include configuration of the
- IP address on the ipdev.
- """
-
- def __init__(self, pif):
- self._pif = pif
-
- @classmethod
- def rewrite(cls):
- """Class method called when write action is called. Can be used
- to update any backend specific configuration."""
- pass
-
- def configure_ipdev(self, cfg):
- """Write ifcfg TYPE field for an IPdev, plus any type specific
- fields to cfg
- """
- raise NotImplementedError
-
- def preconfigure(self, parent):
- """Prepare datapath configuration for PIF, but do not actually
- apply any changes.
-
- Any configuration files should be attached to parent.
- """
- raise NotImplementedError
-
- def bring_down_existing(self):
- """Tear down any existing network device configuration which
- needs to be undone in order to bring this PIF up.
- """
- raise NotImplementedError
-
- def configure(self):
- """Apply the configuration prepared in the preconfigure stage.
-
- Should assume any configuration files changed attached in
- the preconfigure stage are applied and bring up the
- necessary devices to provide the datapath for the
- PIF.
-
- Should not bring up the IPdev.
- """
- raise NotImplementedError
-
- def post(self):
- """Called after the IPdev has been brought up.
-
- Should do any final setup, including reinstating any
- devices which were taken down in the bring_down_existing
- hook.
- """
- raise NotImplementedError
-
- def bring_down(self):
- """Tear down and deconfigure the datapath. Should assume the
- IPdev has already been brought down.
- """
- raise NotImplementedError
-
-def DatapathFactory():
- # XXX Need a datapath object for bridgeless PIFs
-
- try:
- network_conf = open(root_prefix() + "/etc/xensource/network.conf", 'r')
- network_backend = network_conf.readline().strip()
- network_conf.close()
- except Exception as e:
- raise Error("failed to determine network backend:" + e)
-
- if network_backend == "bridge":
- from InterfaceReconfigureBridge import DatapathBridge
- return DatapathBridge
- elif network_backend in ["openvswitch", "vswitch"]:
- from InterfaceReconfigureVswitch import DatapathVswitch
- return DatapathVswitch
- else:
- raise Error("unknown network backend %s" % network_backend)
diff --git a/xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py b/xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py
deleted file mode 100644
index 5cc22319a..000000000
--- a/xenserver/opt_xensource_libexec_InterfaceReconfigureBridge.py
+++ /dev/null
@@ -1,476 +0,0 @@
-# Copyright (c) 2008,2009 Citrix Systems, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
-# by the Free Software Foundation; version 2.1 only. with the special
-# exception on linking described in file LICENSE.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU Lesser General Public License for more details.
-#
-from InterfaceReconfigure import *
-
-import sys
-import time
-
-sysfs_bonding_masters = root_prefix() + "/sys/class/net/bonding_masters"
-
-def open_pif_ifcfg(pif):
- pifrec = db().get_pif_record(pif)
-
- interface = pif_netdev_name(pif)
- log("Configuring %s (%s)" % (interface, pifrec['MAC']))
-
- f = ConfigurationFile("%s/etc/sysconfig/network-scripts/ifcfg-%s" % (root_prefix(), interface))
-
- f.write("# DO NOT EDIT: This file (%s) was autogenerated by %s\n" % \
- (os.path.basename(f.path()), os.path.basename(sys.argv[0])))
- f.write("XEMANAGED=yes\n")
- f.write("DEVICE=%s\n" % interface)
- f.write("ONBOOT=no\n")
-
- return f
-
-#
-# Bare Network Devices -- network devices without IP configuration
-#
-
-def netdev_down(netdev):
- """Bring down a bare network device"""
- if not netdev_exists(netdev):
- log("netdev: down: device %s does not exist, ignoring" % netdev)
- return
- run_command(["/sbin/ifdown", netdev])
-
-def netdev_up(netdev, mtu=None):
- """Bring up a bare network device"""
- #if not netdev_exists(netdev):
- # raise Error("netdev: up: device %s does not exist" % netdev)
-
- run_command(["/sbin/ifup", netdev])
-
-#
-# Bonding driver
-#
-
-def load_bonding_driver():
- log("Loading bonding driver")
- run_command(["/sbin/modprobe", "bonding"])
- try:
- # bond_device_exists() uses the contents of sysfs_bonding_masters to work out which devices
- # have already been created. Unfortunately the driver creates "bond0" automatically at
- # modprobe init. Get rid of this now or our accounting will go wrong.
- f = open(sysfs_bonding_masters, "w")
- f.write("-bond0")
- f.close()
- except IOError as e:
- log("Failed to load bonding driver: %s" % e)
-
-def bonding_driver_loaded():
- lines = open(root_prefix() + "/proc/modules").read().split("\n")
- modules = [line.split(" ")[0] for line in lines]
- return "bonding" in modules
-
-def bond_device_exists(name):
- f = open(sysfs_bonding_masters, "r")
- bonds = f.readline().split()
- f.close()
- return name in bonds
-
-def __create_bond_device(name):
-
- if not bonding_driver_loaded():
- load_bonding_driver()
-
- if bond_device_exists(name):
- log("bond master %s already exists, not creating" % name)
- else:
- log("Creating bond master %s" % name)
- try:
- f = open(sysfs_bonding_masters, "w")
- f.write("+" + name)
- f.close()
- except IOError as e:
- log("Failed to create %s: %s" % (name, e))
-
-def create_bond_device(pif):
- """Ensures that a bond master device exists in the kernel."""
-
- if not pif_is_bond(pif):
- return
-
- __create_bond_device(pif_netdev_name(pif))
-
-def __destroy_bond_device(name):
- if bond_device_exists(name):
- retries = 10 # 10 * 0.5 seconds
- while retries > 0:
- retries = retries - 1
- log("Destroying bond master %s (%d attempts remain)" % (name,retries))
- try:
- f = open(sysfs_bonding_masters, "w")
- f.write("-" + name)
- f.close()
- retries = 0
- except IOError as e:
- time.sleep(0.5)
- else:
- log("bond master %s does not exist, not destroying" % name)
-
-def destroy_bond_device(pif):
- """No, Mr. Bond, I expect you to die."""
-
- pifrec = db().get_pif_record(pif)
-
- if not pif_is_bond(pif):
- return
-
- # If the bonding module isn't loaded then do nothing.
- if not os.access(sysfs_bonding_masters, os.F_OK):
- return
-
- name = pif_netdev_name(pif)
-
- __destroy_bond_device(name)
-
-#
-# Bring Interface up/down.
-#
-
-def bring_down_interface(pif, destroy=False):
- """Bring down the interface associated with PIF.
-
- Brings down the given interface as well as any physical interfaces
- which are bond slaves of this one. This is because they will be
- required when the bond is brought up."""
-
- def destroy_bridge(pif):
- """Bring down the bridge associated with a PIF."""
- #if not pif_is_bridged(pif):
- # return
- bridge = pif_bridge_name(pif)
- if not netdev_exists(bridge):
- log("destroy_bridge: bridge %s does not exist, ignoring" % bridge)
- return
- log("Destroy bridge %s" % bridge)
- netdev_down(bridge)
- run_command(["/usr/sbin/brctl", "delbr", bridge])
-
- def destroy_vlan(pif):
- vlan = pif_netdev_name(pif)
- if not netdev_exists(vlan):
- log("vconfig del: vlan %s does not exist, ignoring" % vlan)
- return
- log("Destroy vlan device %s" % vlan)
- run_command(["/sbin/vconfig", "rem", vlan])
-
- if pif_is_vlan(pif):
- interface = pif_netdev_name(pif)
- log("bring_down_interface: %s is a VLAN" % interface)
- netdev_down(interface)
-
- if destroy:
- destroy_vlan(pif)
- destroy_bridge(pif)
- else:
- return
-
- slave = pif_get_vlan_slave(pif)
- if db().get_pif_record(slave)['currently_attached']:
- log("bring_down_interface: vlan slave is currently attached")
- return
-
- masters = pif_get_vlan_masters(slave)
- masters = [m for m in masters if m != pif and db().get_pif_record(m)['currently_attached']]
- if len(masters) > 0:
- log("bring_down_interface: vlan slave has other masters")
- return
-
- log("bring_down_interface: no more masters, bring down vlan slave %s" % pif_netdev_name(slave))
- pif = slave
- else:
- vlan_masters = pif_get_vlan_masters(pif)
- log("vlan masters of %s - %s" % (db().get_pif_record(pif)['device'], [pif_netdev_name(m) for m in vlan_masters]))
- if len([m for m in vlan_masters if db().get_pif_record(m)['currently_attached']]) > 0:
- log("Leaving %s up due to currently attached VLAN masters" % pif_netdev_name(pif))
- return
-
- # pif is now either a bond or a physical device which needs to be brought down
-
- # Need to bring down bond slaves first since the bond device
- # must be up to enslave/unenslave.
- bond_slaves = pif_get_bond_slaves_sorted(pif)
- log("bond slaves of %s - %s" % (db().get_pif_record(pif)['device'], [pif_netdev_name(s) for s in bond_slaves]))
- for slave in bond_slaves:
- slave_interface = pif_netdev_name(slave)
- if db().get_pif_record(slave)['currently_attached']:
- log("leave bond slave %s up (currently attached)" % slave_interface)
- continue
- log("bring down bond slave %s" % slave_interface)
- netdev_down(slave_interface)
- # Also destroy the bridge associated with the slave, since
- # it will carry the MAC address and possibly an IP address
- # leading to confusion.
- destroy_bridge(slave)
-
- interface = pif_netdev_name(pif)
- log("Bring interface %s down" % interface)
- netdev_down(interface)
-
- if destroy:
- destroy_bond_device(pif)
- destroy_bridge(pif)
-
-def interface_is_up(pif):
- try:
- interface = pif_netdev_name(pif)
- state = open("%s/sys/class/net/%s/operstate" % (root_prefix(), interface)).read().strip()
- return state == "up"
- except:
- return False # interface prolly doesn't exist
-
-def bring_up_interface(pif):
- """Bring up the interface associated with a PIF.
-
- Also bring up the interfaces listed in additional.
- """
-
- # VLAN on bond seems to need bond brought up explicitly, but VLAN
- # on normal device does not. Might as well always bring it up.
- if pif_is_vlan(pif):
- slave = pif_get_vlan_slave(pif)
- if not interface_is_up(slave):
- bring_up_interface(slave)
-
- interface = pif_netdev_name(pif)
-
- create_bond_device(pif)
-
- log("Bring interface %s up" % interface)
- netdev_up(interface)
-
-
-#
-# Datapath topology configuration.
-#
-
-def _configure_physical_interface(pif):
- """Write the configuration for a physical interface.
-
- Writes the configuration file for the physical interface described by
- the pif object.
-
- Returns the open file handle for the interface configuration file.
- """
-
- pifrec = db().get_pif_record(pif)
-
- log("Configuring physical interface %s" % pifrec['device'])
-
- f = open_pif_ifcfg(pif)
-
- f.write("TYPE=Ethernet\n")
- f.write("HWADDR=%(MAC)s\n" % pifrec)
-
- settings,offload = ethtool_settings(pifrec['other_config'],
- PIF_OTHERCONFIG_DEFAULTS)
- if len(settings):
- f.write("ETHTOOL_OPTS=\"%s\"\n" % str.join(" ", settings))
- if len(offload):
- f.write("ETHTOOL_OFFLOAD_OPTS=\"%s\"\n" % str.join(" ", offload))
-
- mtu = mtu_setting(pifrec['network'], "PIF", pifrec['other_config'])
- if mtu:
- f.write("MTU=%s\n" % mtu)
-
- return f
-
-def pif_get_bond_slaves_sorted(pif):
- pifrec = db().get_pif_record(pif)
-
- # build a list of slave's pifs
- slave_pifs = pif_get_bond_slaves(pif)
-
- # Ensure any currently attached slaves are listed in the opposite order to the order in
- # which they were attached. The first slave attached must be the last detached since
- # the bond is using its MAC address.
- try:
- attached_slaves = open("%s/sys/class/net/%s/bonding/slaves" % (root_prefix(), pifrec['device'])).readline().split()
- for slave in attached_slaves:
- pifs = [p for p in db().get_pifs_by_device(slave) if not pif_is_vlan(p)]
- slave_pif = pifs[0]
- slave_pifs.remove(slave_pif)
- slave_pifs.insert(0, slave_pif)
- except IOError:
- pass
-
- return slave_pifs
-
-def _configure_bond_interface(pif):
- """Write the configuration for a bond interface.
-
- Writes the configuration file for the bond interface described by
- the pif object. Handles writing the configuration for the slave
- interfaces.
-
- Returns the open file handle for the bond interface configuration
- file.
- """
-
- pifrec = db().get_pif_record(pif)
-
- f = open_pif_ifcfg(pif)
-
- if pifrec['MAC'] != "":
- f.write("MACADDR=%s\n" % pifrec['MAC'])
-
- for slave in pif_get_bond_slaves(pif):
- s = _configure_physical_interface(slave)
- s.write("MASTER=%(device)s\n" % pifrec)
- s.write("SLAVE=yes\n")
- s.close()
- f.attach_child(s)
-
- settings,offload = ethtool_settings(pifrec['other_config'])
- if len(settings):
- f.write("ETHTOOL_OPTS=\"%s\"\n" % str.join(" ", settings))
- if len(offload):
- f.write("ETHTOOL_OFFLOAD_OPTS=\"%s\"\n" % str.join(" ", offload))
-
- mtu = mtu_setting(pifrec['network'], "Bond-PIF", pifrec['other_config'])
- if mtu:
- f.write("MTU=%s\n" % mtu)
-
- # The bond option defaults
- bond_options = {
- "mode": "balance-slb",
- "miimon": "100",
- "downdelay": "200",
- "updelay": "31000",
- "use_carrier": "1",
- "hashing-algorithm": "src_mac",
- }
-
- # override defaults with values from other-config whose keys being with "bond-"
- oc = pifrec['other_config']
- overrides = filter(lambda key,val: key.startswith("bond-"), oc.items())
- overrides = map(lambda key,val: (key[5:], val), overrides)
- bond_options.update(overrides)
-
- # write the bond options to ifcfg-bondX
- f.write('BONDING_OPTS="')
- for (name,val) in bond_options.items():
- f.write("%s=%s " % (name,val))
- f.write('"\n')
- return f
-
-def _configure_vlan_interface(pif):
- """Write the configuration for a VLAN interface.
-
- Writes the configuration file for the VLAN interface described by
- the pif object. Handles writing the configuration for the master
- interface if necessary.
-
- Returns the open file handle for the VLAN interface configuration
- file.
- """
-
- slave = _configure_pif(pif_get_vlan_slave(pif))
-
- pifrec = db().get_pif_record(pif)
-
- f = open_pif_ifcfg(pif)
- f.write("VLAN=yes\n")
-
- settings,offload = ethtool_settings(pifrec['other_config'])
- if len(settings):
- f.write("ETHTOOL_OPTS=\"%s\"\n" % str.join(" ", settings))
- if len(offload):
- f.write("ETHTOOL_OFFLOAD_OPTS=\"%s\"\n" % str.join(" ", offload))
-
- mtu = mtu_setting(pifrec['network'], "VLAN-PIF", pifrec['other_config'])
- if mtu:
- f.write("MTU=%s\n" % mtu)
-
- f.attach_child(slave)
-
- return f
-
-def _configure_pif(pif):
- """Write the configuration for a PIF object.
-
- Writes the configuration file the PIF and all dependent
- interfaces (bond slaves and VLAN masters etc).
-
- Returns the open file handle for the interface configuration file.
- """
-
- if pif_is_vlan(pif):
- f = _configure_vlan_interface(pif)
- elif pif_is_bond(pif):
- f = _configure_bond_interface(pif)
- else:
- f = _configure_physical_interface(pif)
-
- f.write("BRIDGE=%s\n" % pif_bridge_name(pif))
- f.close()
-
- return f
-
-#
-#
-#
-
-class DatapathBridge(Datapath):
- def __init__(self, pif):
- if pif_is_tunnel(pif):
- raise Error("Tunnel PIFs are not supported in Bridge mode")
-
- Datapath.__init__(self, pif)
- log("Configured for Bridge datapath")
-
- def configure_ipdev(self, cfg):
- if pif_is_bridged(self._pif):
- cfg.write("TYPE=Bridge\n")
- cfg.write("DELAY=0\n")
- cfg.write("STP=off\n")
- cfg.write("PIFDEV=%s\n" % pif_netdev_name(self._pif))
- else:
- cfg.write("TYPE=Ethernet\n")
-
- def preconfigure(self, parent):
- pf = _configure_pif(self._pif)
- parent.attach_child(pf)
-
- def bring_down_existing(self):
- # Bring down any VLAN masters so that we can reconfigure the slave.
- for master in pif_get_vlan_masters(self._pif):
- name = pif_netdev_name(master)
- log("action_up: bring down vlan master %s" % (name))
- netdev_down(name)
-
- # interface-reconfigure is never explicitly called to down a bond master.
- # However, when we are called to up a slave it is implicit that we are destroying the master.
- bond_masters = pif_get_bond_masters(self._pif)
- for master in bond_masters:
- log("action_up: bring down bond master %s" % (pif_netdev_name(master)))
- # bring down master
- bring_down_interface(master, destroy=True)
-
- # No masters left - now its safe to reconfigure the slave.
- bring_down_interface(self._pif)
-
- def configure(self):
- bring_up_interface(self._pif)
-
- def post(self):
- # Bring back any currently-attached VLAN masters
- for master in [v for v in pif_get_vlan_masters(self._pif) if db().get_pif_record(v)['currently_attached']]:
- name = pif_netdev_name(master)
- log("action_up: bring up %s" % (name))
- netdev_up(name)
-
- def bring_down(self):
- bring_down_interface(self._pif, destroy=True)
diff --git a/xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py b/xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py
deleted file mode 100644
index 9ada3776f..000000000
--- a/xenserver/opt_xensource_libexec_InterfaceReconfigureVswitch.py
+++ /dev/null
@@ -1,724 +0,0 @@
-# Copyright (c) 2008,2009,2011 Citrix Systems, Inc.
-# Copyright (c) 2009,2010,2011,2012,2013,2017 Nicira, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
-# by the Free Software Foundation; version 2.1 only. with the special
-# exception on linking described in file LICENSE.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU Lesser General Public License for more details.
-#
-from InterfaceReconfigure import *
-import os
-import re
-import subprocess
-
-#
-# Bare Network Devices -- network devices without IP configuration
-#
-
-def netdev_down(netdev):
- """Bring down a bare network device"""
- if not netdev_exists(netdev):
- log("netdev: down: device %s does not exist, ignoring" % netdev)
- return
- run_command(["/sbin/ip", "link", "set", netdev, 'down'])
-
-def netdev_up(netdev, mtu=None):
- """Bring up a bare network device"""
- if not netdev_exists(netdev):
- raise Error("netdev: up: device %s does not exist" % netdev)
-
- if mtu:
- mtu = ["mtu", mtu]
- else:
- mtu = []
-
- run_command(["/sbin/ip", "link", "set", netdev, 'up'] + mtu)
-
-# This is a list of drivers that do support VLAN tx or rx acceleration, but
-# to which the VLAN bug workaround should not be applied. This could be
-# because these are known-good drivers (that is, they do not have any of
-# the bugs that the workaround avoids) or because the VLAN bug workaround
-# will not work for them and may cause other problems.
-#
-# This is a very short list because few drivers have been tested.
-NO_VLAN_WORKAROUND_DRIVERS = (
- "bonding",
-)
-def netdev_get_driver_name(netdev):
- """Returns the name of the driver for network device 'netdev'"""
- symlink = '%s/sys/class/net/%s/device/driver' % (root_prefix(), netdev)
- try:
- target = os.readlink(symlink)
- except OSError as e:
- log("%s: could not read netdev's driver name (%s)" % (netdev, e))
- return None
-
- slash = target.rfind('/')
- if slash < 0:
- log("target %s of symbolic link %s does not contain slash"
- % (target, symlink))
- return None
-
- return target[slash + 1:]
-
-def netdev_get_features(netdev):
- """Returns the features bitmap for the driver for 'netdev'.
- The features bitmap is a set of NETIF_F_ flags supported by its driver."""
- try:
- features = open("%s/sys/class/net/%s/features" % (root_prefix(), netdev)).read().strip()
- return int(features, 0)
- except:
- return 0 # interface prolly doesn't exist
-
-def netdev_has_vlan_accel(netdev):
- """Returns True if 'netdev' supports VLAN acceleration, False otherwise."""
- NETIF_F_HW_VLAN_TX = 128
- NETIF_F_HW_VLAN_RX = 256
- NETIF_F_VLAN = NETIF_F_HW_VLAN_TX | NETIF_F_HW_VLAN_RX
- return (netdev_get_features(netdev) & NETIF_F_VLAN) != 0
-
-#
-# PIF miscellanea
-#
-
-def pif_currently_in_use(pif):
- """Determine if a PIF is currently in use.
-
- A PIF is determined to be currently in use if
- - PIF.currently-attached is true
- - Any bond master is currently attached
- - Any VLAN master is currently attached
- """
- rec = db().get_pif_record(pif)
- if rec['currently_attached']:
- log("configure_datapath: %s is currently attached" % (pif_netdev_name(pif)))
- return True
- for b in pif_get_bond_masters(pif):
- if pif_currently_in_use(b):
- log("configure_datapath: %s is in use by BOND master %s" % (pif_netdev_name(pif),pif_netdev_name(b)))
- return True
- for v in pif_get_vlan_masters(pif):
- if pif_currently_in_use(v):
- log("configure_datapath: %s is in use by VLAN master %s" % (pif_netdev_name(pif),pif_netdev_name(v)))
- return True
- return False
-
-#
-# Datapath Configuration
-#
-
-def pif_datapath(pif):
- """Return the datapath PIF associated with PIF.
-A non-VLAN PIF is its own datapath PIF, except that a bridgeless PIF has
-no datapath PIF at all.
-A VLAN PIF's datapath PIF is its VLAN slave's datapath PIF.
-"""
- if pif_is_vlan(pif):
- return pif_datapath(pif_get_vlan_slave(pif))
-
- pifrec = db().get_pif_record(pif)
- nwrec = db().get_network_record(pifrec['network'])
- if not nwrec['bridge']:
- return None
- else:
- return pif
-
-def datapath_get_physical_pifs(pif):
- """Return the PIFs for the physical network device(s) associated with a datapath PIF.
-For a bond master PIF, these are the bond slave PIFs.
-For a non-VLAN, non-bond master PIF, the PIF is its own physical device PIF.
-
-A VLAN PIF cannot be a datapath PIF.
-"""
- if pif_is_tunnel(pif):
- return []
- elif pif_is_vlan(pif):
- # Seems like overkill...
- raise Error("get-physical-pifs should not get passed a VLAN")
- elif pif_is_bond(pif):
- return pif_get_bond_slaves(pif)
- else:
- return [pif]
-
-def datapath_deconfigure_physical(netdev):
- return ['--', '--with-iface', '--if-exists', 'del-port', netdev]
-
-def vsctl_escape(s):
- if s.isalnum():
- return s
-
- def escape(match):
- c = match.group(0)
- if c == '\0':
- raise Error("strings may not contain null bytes")
- elif c == '\\':
- return r'\\'
- elif c == '\n':
- return r'\n'
- elif c == '\r':
- return r'\r'
- elif c == '\t':
- return r'\t'
- elif c == '\b':
- return r'\b'
- elif c == '\a':
- return r'\a'
- else:
- return r'\x%02x' % ord(c)
- return '"' + re.sub(r'["\\\000-\037]', escape, s) + '"'
-
-def datapath_configure_tunnel(pif):
- pass
-
-def datapath_configure_bond(pif,slaves):
- bridge = pif_bridge_name(pif)
- pifrec = db().get_pif_record(pif)
- interface = pif_netdev_name(pif)
-
- argv = ['--', '--fake-iface', 'add-bond', bridge, interface]
- for slave in slaves:
- argv += [pif_netdev_name(slave)]
-
- # Bonding options.
- bond_options = {
- "mode": "balance-slb",
- "miimon": "100",
- "downdelay": "200",
- "updelay": "31000",
- "use_carrier": "1",
- "hashing-algorithm": "src_mac",
- }
- # override defaults with values from other-config whose keys
- # being with "bond-"
- oc = pifrec['other_config']
- overrides = filter(lambda key_val:
- key_val[0].startswith("bond-"), oc.items())
- overrides = map(lambda key_val: (key_val[0][5:], key_val[1]), overrides)
- bond_options.update(overrides)
- mode = None
- halgo = None
-
- argv += ['--', 'set', 'Port', interface]
- if pifrec['MAC'] != "":
- argv += ['MAC=%s' % vsctl_escape(pifrec['MAC'])]
- for (name,val) in sorted(bond_options.items()):
- if name in ['updelay', 'downdelay']:
- # updelay and downdelay have dedicated schema columns.
- # The value must be a nonnegative integer.
- try:
- value = int(val)
- if value < 0:
- raise ValueError
-
- argv += ['bond_%s=%d' % (name, value)]
- except ValueError:
- log("bridge %s has invalid %s '%s'" % (bridge, name, value))
- elif name in ['miimon', 'use_carrier']:
- try:
- value = int(val)
- if value < 0:
- raise ValueError
-
- if name == 'use_carrier':
- if value:
- value = "carrier"
- else:
- value = "miimon"
- argv += ["other-config:bond-detect-mode=%s" % value]
- else:
- argv += ["other-config:bond-miimon-interval=%d" % value]
- except ValueError:
- log("bridge %s has invalid %s '%s'" % (bridge, name, value))
- elif name == "mode":
- mode = val
- elif name == "hashing-algorithm":
- halgo = val
- else:
- # Pass other bond options into other_config.
- argv += ["other-config:%s=%s" % (vsctl_escape("bond-%s" % name),
- vsctl_escape(val))]
-
- if mode == 'lacp':
- argv += ['lacp=active']
-
- if halgo == 'src_mac':
- argv += ['bond_mode=balance-slb']
- elif halgo == "tcpudp_ports":
- argv += ['bond_mode=balance-tcp']
- else:
- log("bridge %s has invalid bond-hashing-algorithm '%s'" % (bridge, halgo))
- argv += ['bond_mode=balance-slb']
- elif mode in ['balance-slb', 'active-backup']:
- argv += ['lacp=off', 'bond_mode=%s' % mode]
- else:
- log("bridge %s has invalid bond-mode '%s'" % (bridge, mode))
- argv += ['lacp=off', 'bond_mode=balance-slb']
-
- return argv
-
-def datapath_deconfigure_bond(netdev):
- return ['--', '--with-iface', '--if-exists', 'del-port', netdev]
-
-def datapath_deconfigure_ipdev(interface):
- return ['--', '--with-iface', '--if-exists', 'del-port', interface]
-
-def datapath_modify_config(commands):
- #log("modifying configuration:")
- #for c in commands:
- # log(" %s" % c)
-
- rc = run_command(['/usr/bin/ovs-vsctl'] + ['--timeout=20']
- + [c for c in commands if not c.startswith('#')])
- if not rc:
- raise Error("Failed to modify vswitch configuration")
- return True
-
-#
-# Toplevel Datapath Configuration.
-#
-
-def configure_datapath(pif):
- """Bring up the configuration for 'pif', which must not be a VLAN PIF, by:
- - Tearing down other PIFs that use the same physical devices as 'pif'.
- - Ensuring that 'pif' itself is set up.
- - *Not* tearing down any PIFs that are stacked on top of 'pif' (i.e. VLANs
- on top of 'pif'.
-
- Returns a tuple containing
- - A list containing the necessary vsctl command line arguments
- - A list of additional devices which should be brought up after
- the configuration is applied.
- - A list containing flows to apply to the pif bridge, note that
- port numbers may need to be substituted once ofport is known
- """
-
- vsctl_argv = []
- extra_up_ports = []
- bridge_flows = []
-
- assert not pif_is_vlan(pif)
- bridge = pif_bridge_name(pif)
-
- physical_devices = datapath_get_physical_pifs(pif)
-
- vsctl_argv += ['## configuring datapath %s' % bridge]
-
- # Determine additional devices to deconfigure.
- #
- # Given all physical devices which are part of this PIF we need to
- # consider:
- # - any additional bond which a physical device is part of.
- # - any additional physical devices which are part of an additional bond.
- #
- # Any of these which are not currently in use should be brought
- # down and deconfigured.
- extra_down_bonds = []
- extra_down_ports = []
- for p in physical_devices:
- for bond in pif_get_bond_masters(p):
- if bond == pif:
- log("configure_datapath: leaving bond %s up" % pif_netdev_name(bond))
- continue
- if bond in extra_down_bonds:
- continue
- if db().get_pif_record(bond)['currently_attached']:
- log("configure_datapath: implicitly tearing down currently-attached bond %s" % pif_netdev_name(bond))
-
- extra_down_bonds += [bond]
-
- for s in pif_get_bond_slaves(bond):
- if s in physical_devices:
- continue
- if s in extra_down_ports:
- continue
- if pif_currently_in_use(s):
- continue
- extra_down_ports += [s]
-
- log("configure_datapath: bridge - %s" % bridge)
- log("configure_datapath: physical - %s" % [pif_netdev_name(p) for p in physical_devices])
- log("configure_datapath: extra ports - %s" % [pif_netdev_name(p) for p in extra_down_ports])
- log("configure_datapath: extra bonds - %s" % [pif_netdev_name(p) for p in extra_down_bonds])
-
- # Need to fully deconfigure any bridge which any of the:
- # - physical devices
- # - bond devices
- # - sibling devices
- # refers to
- for brpif in physical_devices + extra_down_ports + extra_down_bonds:
- if brpif == pif:
- continue
- b = pif_bridge_name(brpif)
- #ifdown(b)
- # XXX
- netdev_down(b)
- vsctl_argv += ['# remove bridge %s' % b]
- vsctl_argv += ['--', '--if-exists', 'del-br', b]
-
- for n in extra_down_ports:
- dev = pif_netdev_name(n)
- vsctl_argv += ['# deconfigure sibling physical device %s' % dev]
- vsctl_argv += datapath_deconfigure_physical(dev)
- netdev_down(dev)
-
- for n in extra_down_bonds:
- dev = pif_netdev_name(n)
- vsctl_argv += ['# deconfigure bond device %s' % dev]
- vsctl_argv += datapath_deconfigure_bond(dev)
- netdev_down(dev)
-
- for p in physical_devices:
- dev = pif_netdev_name(p)
- vsctl_argv += ['# deconfigure physical port %s' % dev]
- vsctl_argv += datapath_deconfigure_physical(dev)
-
- vsctl_argv += ['--', '--may-exist', 'add-br', bridge]
-
- if len(physical_devices) > 1:
- vsctl_argv += ['# deconfigure bond %s' % pif_netdev_name(pif)]
- vsctl_argv += datapath_deconfigure_bond(pif_netdev_name(pif))
- vsctl_argv += ['# configure bond %s' % pif_netdev_name(pif)]
- vsctl_argv += datapath_configure_bond(pif, physical_devices)
- extra_up_ports += [pif_netdev_name(pif)]
- elif len(physical_devices) == 1:
- iface = pif_netdev_name(physical_devices[0])
- vsctl_argv += ['# add physical device %s' % iface]
- vsctl_argv += ['--', '--may-exist', 'add-port', bridge, iface]
- elif pif_is_tunnel(pif):
- datapath_configure_tunnel(pif)
-
- vsctl_argv += ['# configure Bridge MAC']
- vsctl_argv += ['--', 'set', 'Bridge', bridge,
- 'other-config:hwaddr=%s' % vsctl_escape(db().get_pif_record(pif)['MAC'])]
-
- pool = db().get_pool_record()
- network = db().get_network_by_bridge(bridge)
- network_rec = None
- fail_mode = None
- valid_fail_modes = ['standalone', 'secure']
-
- if network:
- network_rec = db().get_network_record(network)
- fail_mode = network_rec['other_config'].get('vswitch-controller-fail-mode')
-
- if (fail_mode not in valid_fail_modes) and pool:
- fail_mode = pool['other_config'].get('vswitch-controller-fail-mode')
- # Add default flows to allow management traffic if fail-mode
- # transitions to secure based on pool fail-mode setting
- if fail_mode == 'secure' and db().get_pif_record(pif).get('management', False):
- prev_fail_mode = vswitchCfgQuery(['get-fail-mode', bridge])
- if prev_fail_mode != 'secure':
- tp = 'idle_timeout=0,priority=0'
- host_mgmt_mac = db().get_pif_record(pif)['MAC']
- # account for bond as management interface
- if len(physical_devices) > 1:
- bridge_flows += ['%s,in_port=local,arp,dl_src=%s,actions=NORMAL' % (tp, host_mgmt_mac)]
- bridge_flows += ['%s,in_port=local,dl_src=%s,actions=NORMAL' % (tp, host_mgmt_mac)]
- # we don't know slave ofports yet, substitute later
- bridge_flows += ['%s,in_port=%%s,arp,nw_proto=1,actions=local' % (tp)]
- bridge_flows += ['%s,in_port=%%s,dl_dst=%s,actions=local' % (tp, host_mgmt_mac)]
- else:
- bridge_flows += ['%s,in_port=%%s,arp,nw_proto=1,actions=local' % (tp)]
- bridge_flows += ['%s,in_port=local,arp,dl_src=%s,actions=%%s' % (tp, host_mgmt_mac)]
- bridge_flows += ['%s,in_port=%%s,dl_dst=%s,actions=local' % (tp, host_mgmt_mac)]
- bridge_flows += ['%s,in_port=local,dl_src=%s,actions=%%s' % (tp, host_mgmt_mac)]
-
- if fail_mode not in valid_fail_modes:
- fail_mode = 'standalone'
-
- vsctl_argv += ['--', 'set', 'Bridge', bridge, 'fail_mode=%s' % fail_mode]
-
- if network_rec:
- dib = network_rec['other_config'].get('vswitch-disable-in-band')
- if not dib:
- vsctl_argv += ['--', 'remove', 'Bridge', bridge, 'other_config', 'disable-in-band']
- elif dib in ['true', 'false']:
- vsctl_argv += ['--', 'set', 'Bridge', bridge, 'other_config:disable-in-band=' + dib]
- else:
- log('"' + dib + '"' "isn't a valid setting for other_config:disable-in-band on " + bridge)
-
- vsctl_argv += set_br_external_ids(pif)
- vsctl_argv += ['## done configuring datapath %s' % bridge]
-
- return vsctl_argv,extra_up_ports,bridge_flows
-
-def deconfigure_bridge(pif):
- vsctl_argv = []
-
- bridge = pif_bridge_name(pif)
-
- log("deconfigure_bridge: bridge - %s" % bridge)
-
- vsctl_argv += ['# deconfigure bridge %s' % bridge]
- vsctl_argv += ['--', '--if-exists', 'del-br', bridge]
-
- return vsctl_argv
-
-def set_br_external_ids(pif):
- pifrec = db().get_pif_record(pif)
- dp = pif_datapath(pif)
- dprec = db().get_pif_record(dp)
-
- xs_network_uuids = []
- for nwpif in db().get_pifs_by_device(pifrec['device']):
- rec = db().get_pif_record(nwpif)
-
- # When state is read from dbcache PIF.currently_attached
- # is always assumed to be false... Err on the side of
- # listing even detached networks for the time being.
- #if nwpif != pif and not rec['currently_attached']:
- # log("Network PIF %s not currently attached (%s)" % (rec['uuid'],pifrec['uuid']))
- # continue
- nwrec = db().get_network_record(rec['network'])
-
- uuid = nwrec['uuid']
- if pif_is_vlan(nwpif):
- xs_network_uuids.append(uuid)
- else:
- xs_network_uuids.insert(0, uuid)
-
- vsctl_argv = []
- vsctl_argv += ['# configure xs-network-uuids']
- vsctl_argv += ['--', 'br-set-external-id', pif_bridge_name(pif),
- 'xs-network-uuids', ';'.join(xs_network_uuids)]
-
- return vsctl_argv
-
-#
-#
-#
-
-class DatapathVswitch(Datapath):
- def __init__(self, pif):
- Datapath.__init__(self, pif)
- self._dp = pif_datapath(pif)
- self._ipdev = pif_ipdev_name(pif)
- self._bridge_flows = []
-
- if pif_is_vlan(pif) and not self._dp:
- raise Error("Unbridged VLAN devices not implemented yet")
-
- log("Configured for Vswitch datapath")
-
- @classmethod
- def rewrite(cls):
- if not os.path.exists("/var/run/openvswitch/db.sock"):
- # ovsdb-server is not running, so we can't update the database.
- # Probably we are being called as part of system shutdown. Just
- # skip the update, since the external-ids will be updated on the
- # next boot anyhow.
- return
-
- vsctl_argv = []
- for pif in db().get_all_pifs():
- pifrec = db().get_pif_record(pif)
- if not pif_is_vlan(pif) and pifrec['currently_attached']:
- vsctl_argv += set_br_external_ids(pif)
-
- if vsctl_argv != []:
- datapath_modify_config(vsctl_argv)
-
- def configure_ipdev(self, cfg):
- cfg.write("TYPE=Ethernet\n")
-
- def preconfigure(self, parent):
- vsctl_argv = []
- extra_ports = []
- bridge_flows = []
-
- pifrec = db().get_pif_record(self._pif)
- dprec = db().get_pif_record(self._dp)
-
- ipdev = self._ipdev
- c,e,f = configure_datapath(self._dp)
- bridge = pif_bridge_name(self._pif)
- vsctl_argv += c
- extra_ports += e
- bridge_flows += f
-
- dpname = pif_bridge_name(self._dp)
-
- if pif_is_vlan(self._pif):
- # In some cases XAPI may misguidedly leave an instance of
- # 'bridge' which should be deleted.
- vsctl_argv += ['--', '--if-exists', 'del-br', bridge]
-
- # configure_datapath() set up the underlying datapath bridge.
- # Stack a VLAN bridge on top of it.
- vsctl_argv += ['--', '--may-exist', 'add-br',
- bridge, dpname, pifrec['VLAN']]
-
- vsctl_argv += set_br_external_ids(self._pif)
-
- if ipdev != bridge:
- vsctl_argv += ["# deconfigure ipdev %s" % ipdev]
- vsctl_argv += datapath_deconfigure_ipdev(ipdev)
- vsctl_argv += ["# reconfigure ipdev %s" % ipdev]
- vsctl_argv += ['--', 'add-port', bridge, ipdev]
-
- if ipdev != dpname:
- vsctl_argv += ['# configure Interface MAC']
- vsctl_argv += ['--', 'set', 'Interface', pif_ipdev_name(self._pif),
- 'MAC=%s' % vsctl_escape(dprec['MAC'])]
-
- self._vsctl_argv = vsctl_argv
- self._extra_ports = extra_ports
- self._bridge_flows = bridge_flows
-
- def bring_down_existing(self):
- # interface-reconfigure is never explicitly called to down a
- # bond master. However, when we are called to up a slave it
- # is implicit that we are destroying the master. Conversely,
- # when we are called to up a bond is is implicit that we are
- # taking down the slaves.
- #
- # This is (only) important in the case where the device being
- # implicitly taken down uses DHCP. We need to kill the
- # dhclient process, otherwise performing the inverse operation
- # later later will fail because ifup will refuse to start a
- # duplicate dhclient.
- bond_masters = pif_get_bond_masters(self._pif)
- for master in bond_masters:
- log("action_up: bring down bond master %s" % (pif_netdev_name(master)))
- run_command(["/sbin/ifdown", pif_bridge_name(master)])
-
- bond_slaves = pif_get_bond_slaves(self._pif)
- for slave in bond_slaves:
- log("action_up: bring down bond slave %s" % (pif_netdev_name(slave)))
- run_command(["/sbin/ifdown", pif_bridge_name(slave)])
-
- def configure(self):
- # Bring up physical devices. ovs-vswitchd initially enables or
- # disables bond slaves based on whether carrier is detected
- # when they are added, and a network device that is down
- # always reports "no carrier".
- physical_devices = datapath_get_physical_pifs(self._dp)
-
- if pif_is_bond(self._dp):
- brec = db().get_pif_record(self._dp)
- bond_mtu = mtu_setting(brec['network'], "PIF", brec['other_config'])
- else:
- bond_mtu = None
-
- for p in physical_devices:
- prec = db().get_pif_record(p)
- oc = prec['other_config']
-
- dev = pif_netdev_name(p)
-
- if bond_mtu:
- mtu = bond_mtu
- else:
- mtu = mtu_setting(prec['network'], "PIF", oc)
-
- netdev_up(dev, mtu)
-
- settings, offload = ethtool_settings(oc, PIF_OTHERCONFIG_DEFAULTS)
- if len(settings):
- run_command(['/sbin/ethtool', '-s', dev] + settings)
- if len(offload):
- run_command(['/sbin/ethtool', '-K', dev] + offload)
-
- driver = netdev_get_driver_name(dev)
- if 'vlan-bug-workaround' in oc:
- vlan_bug_workaround = oc['vlan-bug-workaround'] == 'true'
- elif driver in NO_VLAN_WORKAROUND_DRIVERS:
- vlan_bug_workaround = False
- else:
- vlan_bug_workaround = netdev_has_vlan_accel(dev)
-
- datapath_modify_config(self._vsctl_argv)
- if self._bridge_flows:
- ofports = []
- physical_devices = datapath_get_physical_pifs(self._dp)
- if len(physical_devices) > 1:
- for slave in physical_devices:
- name = pif_netdev_name(slave)
- ofport = vswitchCfgQuery(['get', 'interface', name, 'ofport'])
- ofports.append(ofport)
- else:
- name = pif_netdev_name(self._dp)
- ofport = vswitchCfgQuery(['get', 'interface', name, 'ofport'])
- ofports.append(ofport)
- dpname = pif_bridge_name(self._dp)
- for flow in self._bridge_flows:
- if flow.find('in_port=%s') != -1 or flow.find('actions=%s') != -1:
- for port in ofports:
- f = flow % (port.decode())
- run_command(['/usr/bin/ovs-ofctl', 'add-flow', dpname, f])
- else:
- run_command(['/usr/bin/ovs-ofctl', 'add-flow', dpname, flow])
-
- def post(self):
- for p in self._extra_ports:
- log("action_up: bring up %s" % p)
- netdev_up(p)
-
- def bring_down(self):
- vsctl_argv = []
-
- dp = self._dp
- ipdev = self._ipdev
-
- bridge = pif_bridge_name(dp)
-
- log("deconfigure ipdev %s on %s" % (ipdev,bridge))
- vsctl_argv += ["# deconfigure ipdev %s" % ipdev]
- vsctl_argv += datapath_deconfigure_ipdev(ipdev)
-
- if pif_is_vlan(self._pif):
- # Delete the VLAN bridge.
- vsctl_argv += deconfigure_bridge(self._pif)
-
- # If the VLAN's slave is attached, leave datapath setup.
- slave = pif_get_vlan_slave(self._pif)
- if db().get_pif_record(slave)['currently_attached']:
- log("action_down: vlan slave is currently attached")
- dp = None
-
- # If the VLAN's slave has other VLANs that are attached, leave datapath setup.
- for master in pif_get_vlan_masters(slave):
- if master != self._pif and db().get_pif_record(master)['currently_attached']:
- log("action_down: vlan slave has other master: %s" % pif_netdev_name(master))
- dp = None
-
- # Otherwise, take down the datapath too (fall through)
- if dp:
- log("action_down: no more masters, bring down slave %s" % bridge)
- else:
- # Stop here if this PIF has attached VLAN masters.
- masters = [db().get_pif_record(m)['VLAN'] for m in pif_get_vlan_masters(self._pif) if db().get_pif_record(m)['currently_attached']]
- if len(masters) > 0:
- log("Leaving datapath %s up due to currently attached VLAN masters %s" % (bridge, masters))
- dp = None
-
- if dp:
- vsctl_argv += deconfigure_bridge(dp)
-
- physical_devices = [pif_netdev_name(p) for p in datapath_get_physical_pifs(dp)]
-
- log("action_down: bring down physical devices - %s" % physical_devices)
-
- for p in physical_devices:
- netdev_down(p)
-
- datapath_modify_config(vsctl_argv)
-
-#
-# utility methods
-#
-
-def vswitchCfgQuery(action_args):
- cmd = ['%s/usr/bin/ovs-vsctl' % root_prefix(),
- '-vconsole:off'] + action_args
- output = subprocess.Popen(cmd, stdout=subprocess.PIPE).communicate()
- if len(output) == 0 or output[0] == None:
- output = ""
- else:
- output = output[0].strip()
- return output
diff --git a/xenserver/opt_xensource_libexec_interface-reconfigure b/xenserver/opt_xensource_libexec_interface-reconfigure
deleted file mode 100755
index 9c20725de..000000000
--- a/xenserver/opt_xensource_libexec_interface-reconfigure
+++ /dev/null
@@ -1,739 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright (c) 2008,2009 Citrix Systems, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU Lesser General Public License as published
-# by the Free Software Foundation; version 2.1 only. with the special
-# exception on linking described in file LICENSE.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU Lesser General Public License for more details.
-#
-"""Usage:
-
- %(command-name)s <PIF> up
- %(command-name)s <PIF> down
- %(command-name)s rewrite
- %(command-name)s --force <BRIDGE> up
- %(command-name)s --force <BRIDGE> down
- %(command-name)s --force <BRIDGE> rewrite --device=<INTERFACE> --mac=<MAC-ADDRESS> <CONFIG>
-
- where <PIF> is one of:
- --session <SESSION-REF> --pif <PIF-REF>
- --pif-uuid <PIF-UUID>
- and <CONFIG> is one of:
- --mode=dhcp
- --mode=static --ip=<IPADDR> --netmask=<NM> [--gateway=<GW>]
-
- Options:
- --session A session reference to use to access the xapi DB
- --pif A PIF reference within the session.
- --pif-uuid The UUID of a PIF.
- --force An interface name.
- --root-prefix=DIR Use DIR as alternate root directory (for testing).
- --no-syslog Write log messages to stderr instead of system log.
-"""
-
-# Notes:
-# 1. Every pif belongs to exactly one network
-# 2. Every network has zero or one pifs
-# 3. A network may have an associated bridge, allowing vifs to be attached
-# 4. A network may be bridgeless (there's no point having a bridge over a storage pif)
-
-from InterfaceReconfigure import *
-
-import os, sys, getopt
-import syslog
-import traceback
-import re
-import random
-import syslog
-
-management_pif = None
-
-dbcache_file = "/var/xapi/network.dbcache"
-
-#
-# Logging.
-#
-
-def log_pif_action(action, pif):
- pifrec = db().get_pif_record(pif)
- rec = {}
- rec['uuid'] = pifrec['uuid']
- rec['ip_configuration_mode'] = pifrec['ip_configuration_mode']
- rec['action'] = action
- rec['pif_netdev_name'] = pif_netdev_name(pif)
- rec['message'] = "Bring %(action)s PIF %(uuid)s" % rec
- log("%(message)s: %(pif_netdev_name)s configured as %(ip_configuration_mode)s" % rec)
-
-#
-# Exceptions.
-#
-
-class Usage(Exception):
- def __init__(self, msg):
- Exception.__init__(self)
- self.msg = msg
-
-#
-# Boot from Network filesystem or device.
-#
-
-def check_allowed(pif):
- """Determine whether interface-reconfigure should be manipulating this PIF.
-
- Used to prevent system PIFs (such as network root disk) from being interfered with.
- """
-
- pifrec = db().get_pif_record(pif)
- try:
- f = open(root_prefix() + "/proc/ardence")
- macline = filter(lambda x: x.startswith("HWaddr:"), f.readlines())
- f.close()
- if len(macline) == 1:
- p = re.compile(".*\s%(MAC)s\s.*" % pifrec, re.IGNORECASE)
- if p.match(macline[0]):
- log("Skipping PVS device %(device)s (%(MAC)s)" % pifrec)
- return False
- except IOError:
- pass
- return True
-
-#
-# Bare Network Devices -- network devices without IP configuration
-#
-
-def netdev_remap_name(pif, already_renamed=[]):
- """Check whether 'pif' exists and has the correct MAC.
- If not, try to find a device with the correct MAC and rename it.
- 'already_renamed' is used to avoid infinite recursion.
- """
-
- def read1(name):
- file = None
- try:
- file = open(name, 'r')
- return file.readline().rstrip('\n')
- finally:
- if file != None:
- file.close()
-
- def get_netdev_mac(device):
- try:
- return read1("%s/sys/class/net/%s/address" % (root_prefix(), device))
- except:
- # Probably no such device.
- return None
-
- def get_netdev_tx_queue_len(device):
- try:
- return int(read1("%s/sys/class/net/%s/tx_queue_len" % (root_prefix(), device)))
- except:
- # Probably no such device.
- return None
-
- def get_netdev_by_mac(mac):
- for device in os.listdir(root_prefix() + "/sys/class/net"):
- dev_mac = get_netdev_mac(device)
- if (dev_mac and mac.lower() == dev_mac.lower() and
- get_netdev_tx_queue_len(device)):
- return device
- return None
-
- def rename_netdev(old_name, new_name):
- raise Error("Trying to rename %s to %s - This functionality has been removed" % (old_name, new_name))
- # log("Changing the name of %s to %s" % (old_name, new_name))
- # run_command(['/sbin/ip', 'link', 'set', old_name, 'down'])
- # if not run_command(['/sbin/ip', 'link', 'set', old_name, 'name', new_name]):
- # raise Error("Could not rename %s to %s" % (old_name, new_name))
-
- pifrec = db().get_pif_record(pif)
- device = pifrec['device']
- mac = pifrec['MAC']
-
- # Is there a network device named 'device' at all?
- device_exists = netdev_exists(device)
- if device_exists:
- # Yes. Does it have MAC 'mac'?
- found_mac = get_netdev_mac(device)
- if found_mac and mac.lower() == found_mac.lower():
- # Yes, everything checks out the way we want. Nothing to do.
- return
- else:
- log("No network device %s" % device)
-
- # What device has MAC 'mac'?
- cur_device = get_netdev_by_mac(mac)
- if not cur_device:
- log("No network device has MAC %s" % mac)
- return
-
- # First rename 'device', if it exists, to get it out of the way
- # for 'cur_device' to replace it.
- if device_exists:
- rename_netdev(device, "dev%d" % random.getrandbits(24))
-
- # Rename 'cur_device' to 'device'.
- rename_netdev(cur_device, device)
-
-#
-# IP Network Devices -- network devices with IP configuration
-#
-
-def ifdown(netdev):
- """Bring down a network interface"""
- if not netdev_exists(netdev):
- log("ifdown: device %s does not exist, ignoring" % netdev)
- return
- if not os.path.exists("%s/etc/sysconfig/network-scripts/ifcfg-%s" % (root_prefix(), netdev)):
- log("ifdown: device %s exists but ifcfg-%s does not" % (netdev,netdev))
- run_command(["/sbin/ip", "link", "set", netdev, 'down'])
- return
- run_command(["/sbin/ifdown", netdev])
-
-def ifup(netdev):
- """Bring up a network interface"""
- if not os.path.exists(root_prefix() + "/etc/sysconfig/network-scripts/ifcfg-%s" % netdev):
- raise Error("ifup: device %s exists but ifcfg-%s does not" % (netdev,netdev))
- d = os.getenv("DHCLIENTARGS","")
- if os.path.exists("/etc/firstboot.d/data/firstboot_in_progress"):
- os.putenv("DHCLIENTARGS", d + " -T 240 " )
- run_command(["/sbin/ifup", netdev])
- os.putenv("DHCLIENTARGS", d )
-
-#
-#
-#
-
-def pif_rename_physical_devices(pif):
- if pif_is_tunnel(pif):
- return
-
- if pif_is_vlan(pif):
- pif = pif_get_vlan_slave(pif)
-
- if pif_is_bond(pif):
- pifs = pif_get_bond_slaves(pif)
- else:
- pifs = [pif]
-
- for pif in pifs:
- netdev_remap_name(pif)
-
-#
-# IP device configuration
-#
-
-def ipdev_configure_static_routes(interface, oc, f):
- """Open a route-<interface> file for static routes.
-
- Opens the static routes configuration file for interface and writes one
- line for each route specified in the network's other config "static-routes" value.
- E.g. if
- interface ( RO): xenbr1
- other-config (MRW): static-routes: 172.16.0.0/15/192.168.0.3,172.18.0.0/16/192.168.0.4;...
-
- Then route-xenbr1 should be
- 172.16.0.0/15 via 192.168.0.3 dev xenbr1
- 172.18.0.0/16 via 192.168.0.4 dev xenbr1
- """
- if 'static-routes' in oc:
- # The key is present - extract comma separates entries
- lines = oc['static-routes'].split(',')
- else:
- # The key is not present, i.e. there are no static routes
- lines = []
-
- child = ConfigurationFile("%s/etc/sysconfig/network-scripts/route-%s" % (root_prefix(), interface))
- child.write("# DO NOT EDIT: This file (%s) was autogenerated by %s\n" % \
- (os.path.basename(child.path()), os.path.basename(sys.argv[0])))
-
- try:
- for l in lines:
- network, masklen, gateway = l.split('/')
- child.write("%s/%s via %s dev %s\n" % (network, masklen, gateway, interface))
-
- f.attach_child(child)
- child.close()
-
- except ValueError as e:
- log("Error in other-config['static-routes'] format for network %s: %s" % (interface, e))
-
-def ipdev_open_ifcfg(pif):
- ipdev = pif_ipdev_name(pif)
-
- log("Writing network configuration for %s" % ipdev)
-
- f = ConfigurationFile("%s/etc/sysconfig/network-scripts/ifcfg-%s" % (root_prefix(), ipdev))
-
- f.write("# DO NOT EDIT: This file (%s) was autogenerated by %s\n" % \
- (os.path.basename(f.path()), os.path.basename(sys.argv[0])))
- f.write("XEMANAGED=yes\n")
- f.write("DEVICE=%s\n" % ipdev)
- f.write("ONBOOT=no\n")
- f.write("NOZEROCONF=yes\n")
-
- return f
-
-def ipdev_configure_network(pif, dp):
- """Write the configuration file for a network.
-
- Writes configuration derived from the network object into the relevant
- ifcfg file. The configuration file is passed in, but if the network is
- bridgeless it will be ifcfg-<interface>, otherwise it will be ifcfg-<bridge>.
-
- This routine may also write ifcfg files of the networks corresponding to other PIFs
- in order to maintain consistency.
-
- params:
- pif: Opaque_ref of pif
- dp: Datapath object
- """
-
- pifrec = db().get_pif_record(pif)
- nw = pifrec['network']
- nwrec = db().get_network_record(nw)
-
- ipdev = pif_ipdev_name(pif)
-
- f = ipdev_open_ifcfg(pif)
-
- mode = pifrec['ip_configuration_mode']
- log("Configuring %s using %s configuration" % (ipdev, mode))
-
- oc = None
- if 'other_config' in pifrec:
- oc = pifrec['other_config']
-
- dp.configure_ipdev(f)
-
- if pifrec['ip_configuration_mode'] == "DHCP":
- f.write("BOOTPROTO=dhcp\n")
- f.write("PERSISTENT_DHCLIENT=yes\n")
- elif pifrec['ip_configuration_mode'] == "Static":
- f.write("BOOTPROTO=none\n")
- f.write("NETMASK=%(netmask)s\n" % pifrec)
- f.write("IPADDR=%(IP)s\n" % pifrec)
- f.write("GATEWAY=%(gateway)s\n" % pifrec)
- elif pifrec['ip_configuration_mode'] == "None":
- f.write("BOOTPROTO=none\n")
- else:
- raise Error("Unknown ip-configuration-mode %s" % pifrec['ip_configuration_mode'])
-
- if 'other_config' in nwrec:
- settings,offload = ethtool_settings(nwrec['other_config'])
- if len(settings):
- f.write("ETHTOOL_OPTS=\"%s\"\n" % str.join(" ", settings))
- if len(offload):
- f.write("ETHTOOL_OFFLOAD_OPTS=\"%s\"\n" % str.join(" ", offload))
-
- ipdev_configure_static_routes(ipdev, nwrec['other_config'], f)
-
- mtu = mtu_setting(nw, "Network", nwrec['other_config'])
- if mtu:
- f.write("MTU=%s\n" % mtu)
-
-
- if 'DNS' in pifrec and pifrec['DNS'] != "":
- ServerList = pifrec['DNS'].split(",")
- for i in range(len(ServerList)): f.write("DNS%d=%s\n" % (i+1, ServerList[i]))
- if oc and 'domain' in oc:
- f.write("DOMAIN='%s'\n" % oc['domain'].replace(',', ' '))
-
- # There can be only one DNSDEV and one GATEWAYDEV in /etc/sysconfig/network.
- #
- # The peerdns pif will be the one with
- # pif::other-config:peerdns=true, or the mgmt pif if none have
- # this set.
- #
- # The gateway pif will be the one with
- # pif::other-config:defaultroute=true, or the mgmt pif if none
- # have this set.
-
- # Work out which pif on this host should be the DNSDEV and which
- # should be the GATEWAYDEV
- #
- # Note: we prune out the bond master pif (if it exists). This is
- # because when we are called to bring up an interface with a bond
- # master, it is implicit that we should bring down that master.
-
- pifs_on_host = [p for p in db().get_all_pifs() if not p in pif_get_bond_masters(pif)]
-
- # now prune out bond slaves as they are not connected to the IP
- # stack and so cannot be used as gateway or DNS devices.
- pifs_on_host = [ p for p in pifs_on_host if len(pif_get_bond_masters(p)) == 0]
-
- # loop through all the pifs on this host looking for one with
- # other-config:peerdns = true, and one with
- # other-config:default-route=true
- peerdns_pif = None
- defaultroute_pif = None
- for __pif in pifs_on_host:
- __pifrec = db().get_pif_record(__pif)
- __oc = __pifrec['other_config']
- if 'peerdns' in __oc and __oc['peerdns'] == 'true':
- if peerdns_pif == None:
- peerdns_pif = __pif
- else:
- log('Warning: multiple pifs with "peerdns=true" - choosing %s and ignoring %s' % \
- (db().get_pif_record(peerdns_pif)['device'], __pifrec['device']))
- if 'defaultroute' in __oc and __oc['defaultroute'] == 'true':
- if defaultroute_pif == None:
- defaultroute_pif = __pif
- else:
- log('Warning: multiple pifs with "defaultroute=true" - choosing %s and ignoring %s' % \
- (db().get_pif_record(defaultroute_pif)['device'], __pifrec['device']))
-
- # If no pif is explicitly specified then use the mgmt pif for
- # peerdns/defaultroute.
- if peerdns_pif == None:
- peerdns_pif = management_pif
- if defaultroute_pif == None:
- defaultroute_pif = management_pif
-
- is_dnsdev = peerdns_pif == pif
- is_gatewaydev = defaultroute_pif == pif
-
- if is_dnsdev or is_gatewaydev:
- fnetwork = ConfigurationFile(root_prefix() + "/etc/sysconfig/network")
- for line in fnetwork.readlines():
- if is_dnsdev and line.lstrip().startswith('DNSDEV='):
- fnetwork.write('DNSDEV=%s\n' % ipdev)
- is_dnsdev = False
- elif is_gatewaydev and line.lstrip().startswith('GATEWAYDEV='):
- fnetwork.write('GATEWAYDEV=%s\n' % ipdev)
- is_gatewaydev = False
- else:
- fnetwork.write(line)
-
- if is_dnsdev:
- fnetwork.write('DNSDEV=%s\n' % ipdev)
- if is_gatewaydev:
- fnetwork.write('GATEWAYDEV=%s\n' % ipdev)
-
- fnetwork.close()
- f.attach_child(fnetwork)
-
- return f
-
-#
-# Toplevel actions
-#
-
-def action_up(pif, force):
- pifrec = db().get_pif_record(pif)
-
- ipdev = pif_ipdev_name(pif)
- dp = DatapathFactory()(pif)
-
- log("action_up: %s" % ipdev)
-
- f = ipdev_configure_network(pif, dp)
-
- dp.preconfigure(f)
-
- f.close()
-
- pif_rename_physical_devices(pif)
-
- # if we are not forcing the interface up then attempt to tear down
- # any existing devices which might interfere with brinign this one
- # up.
- if not force:
- ifdown(ipdev)
-
- dp.bring_down_existing()
-
- try:
- f.apply()
-
- dp.configure()
-
- ifup(ipdev)
-
- dp.post()
-
- # Update /etc/issue (which contains the IP address of the management interface)
- os.system(root_prefix() + "/sbin/update-issue")
-
- f.commit()
- except Error as e:
- log("failed to apply changes: %s" % e.msg)
- f.revert()
- raise
-
-def action_down(pif):
- ipdev = pif_ipdev_name(pif)
- dp = DatapathFactory()(pif)
-
- log("action_down: %s" % ipdev)
-
- ifdown(ipdev)
-
- dp.bring_down()
-
-def action_rewrite():
- DatapathFactory().rewrite()
-
-# This is useful for reconfiguring the mgmt interface after having lost connectivity to the pool master
-def action_force_rewrite(bridge, config):
- def getUUID():
- import subprocess
- uuid,_ = subprocess.Popen(['uuidgen'], stdout = subprocess.PIPE).communicate()
- return uuid.strip()
-
- # Notes:
- # 1. that this assumes the interface is bridged
- # 2. If --gateway is given it will make that the default gateway for the host
-
- # extract the configuration
- try:
- mode = config['mode']
- mac = config['mac']
- interface = config['device']
- except:
- raise Usage("Please supply --mode, --mac and --device")
-
- if mode == 'static':
- try:
- netmask = config['netmask']
- ip = config['ip']
- except:
- raise Usage("Please supply --netmask and --ip")
- try:
- gateway = config['gateway']
- except:
- gateway = None
- elif mode != 'dhcp':
- raise Usage("--mode must be either static or dhcp")
-
- if 'vlan' in config:
- is_vlan = True
- vlan_slave, vlan_vid = config['vlan'].split('.')
- else:
- is_vlan = False
-
- if is_vlan:
- raise Error("Force rewrite of VLAN not implemented")
-
- log("Configuring %s using %s configuration" % (bridge, mode))
-
- f = ConfigurationFile(root_prefix() + dbcache_file)
-
- pif_uuid = getUUID()
- network_uuid = getUUID()
-
- f.write('<?xml version="1.0" ?>\n')
- f.write('<xenserver-network-configuration>\n')
- f.write('\t<pif ref="OpaqueRef:%s">\n' % pif_uuid)
- f.write('\t\t<network>OpaqueRef:%s</network>\n' % network_uuid)
- f.write('\t\t<management>True</management>\n')
- f.write('\t\t<uuid>%sPif</uuid>\n' % interface)
- f.write('\t\t<bond_slave_of>OpaqueRef:NULL</bond_slave_of>\n')
- f.write('\t\t<bond_master_of/>\n')
- f.write('\t\t<VLAN_slave_of/>\n')
- f.write('\t\t<VLAN_master_of>OpaqueRef:NULL</VLAN_master_of>\n')
- f.write('\t\t<VLAN>-1</VLAN>\n')
- f.write('\t\t<tunnel_access_PIF_of/>\n')
- f.write('\t\t<tunnel_transport_PIF_of/>\n')
- f.write('\t\t<device>%s</device>\n' % interface)
- f.write('\t\t<MAC>%s</MAC>\n' % mac)
- f.write('\t\t<other_config/>\n')
- if mode == 'dhcp':
- f.write('\t\t<ip_configuration_mode>DHCP</ip_configuration_mode>\n')
- f.write('\t\t<IP></IP>\n')
- f.write('\t\t<netmask></netmask>\n')
- f.write('\t\t<gateway></gateway>\n')
- f.write('\t\t<DNS></DNS>\n')
- elif mode == 'static':
- f.write('\t\t<ip_configuration_mode>Static</ip_configuration_mode>\n')
- f.write('\t\t<IP>%s</IP>\n' % ip)
- f.write('\t\t<netmask>%s</netmask>\n' % netmask)
- if gateway is not None:
- f.write('\t\t<gateway>%s</gateway>\n' % gateway)
- f.write('\t\t<DNS></DNS>\n')
- else:
- raise Error("Unknown mode %s" % mode)
- f.write('\t</pif>\n')
-
- f.write('\t<network ref="OpaqueRef:%s">\n' % network_uuid)
- f.write('\t\t<uuid>InitialManagementNetwork</uuid>\n')
- f.write('\t\t<PIFs>\n')
- f.write('\t\t\t<PIF>OpaqueRef:%s</PIF>\n' % pif_uuid)
- f.write('\t\t</PIFs>\n')
- f.write('\t\t<bridge>%s</bridge>\n' % bridge)
- f.write('\t\t<other_config/>\n')
- f.write('\t</network>\n')
- f.write('</xenserver-network-configuration>\n')
-
- f.close()
-
- try:
- f.apply()
- f.commit()
- except Error as e:
- log("failed to apply changes: %s" % e.msg)
- f.revert()
- raise
-
-def main(argv=None):
- global management_pif
-
- session = None
- pif_uuid = None
- pif = None
-
- force_interface = None
- force_management = False
-
- if argv is None:
- argv = sys.argv
-
- try:
- try:
- shortops = "h"
- longops = [ "pif=", "pif-uuid=",
- "session=",
- "force=",
- "force-interface=",
- "management",
- "mac=", "device=", "mode=", "ip=", "netmask=", "gateway=",
- "root-prefix=",
- "no-syslog",
- "help" ]
- arglist, args = getopt.gnu_getopt(argv[1:], shortops, longops)
- except getopt.GetoptError as msg:
- raise Usage(msg)
-
- force_rewrite_config = {}
-
- for o,a in arglist:
- if o == "--pif":
- pif = a
- elif o == "--pif-uuid":
- pif_uuid = a
- elif o == "--session":
- session = a
- elif o == "--force-interface" or o == "--force":
- force_interface = a
- elif o == "--management":
- force_management = True
- elif o in ["--mac", "--device", "--mode", "--ip", "--netmask", "--gateway"]:
- force_rewrite_config[o[2:]] = a
- elif o == "--root-prefix":
- set_root_prefix(a)
- elif o == "--no-syslog":
- set_log_destination("stderr")
- elif o == "-h" or o == "--help":
- print(__doc__ % {'command-name': os.path.basename(argv[0])})
- return 0
-
- if get_log_destination() == "syslog":
- syslog.openlog(os.path.basename(argv[0]))
- log("Called as " + str.join(" ", argv))
-
- if len(args) < 1:
- raise Usage("Required option <action> not present")
- if len(args) > 1:
- raise Usage("Too many arguments")
-
- action = args[0]
-
- if not action in ["up", "down", "rewrite", "rewrite-configuration"]:
- raise Usage("Unknown action \"%s\"" % action)
-
- # backwards compatibility
- if action == "rewrite-configuration": action = "rewrite"
-
- if ( session or pif ) and pif_uuid:
- raise Usage("--session/--pif and --pif-uuid are mutually exclusive.")
- if ( session and not pif ) or ( not session and pif ):
- raise Usage("--session and --pif must be used together.")
- if force_interface and ( session or pif or pif_uuid ):
- raise Usage("--force is mutually exclusive with --session, --pif and --pif-uuid")
- if len(force_rewrite_config) and not (force_interface and action == "rewrite"):
- raise Usage("\"--force rewrite\" needed for --device, --mode, --ip, --netmask, and --gateway")
- if (action == "rewrite") and (pif or pif_uuid ):
- raise Usage("rewrite action does not take --pif or --pif-uuid")
-
- global db
- if force_interface:
- log("Force interface %s %s" % (force_interface, action))
-
- if action == "rewrite":
- action_force_rewrite(force_interface, force_rewrite_config)
- elif action in ["up", "down"]:
- db_init_from_cache(dbcache_file)
- pif = db().get_pif_by_bridge(force_interface)
- management_pif = db().get_management_pif()
-
- if action == "up":
- action_up(pif, True)
- elif action == "down":
- action_down(pif)
- else:
- raise Error("Unknown action %s" % action)
- else:
- db_init_from_xenapi(session)
-
- if pif_uuid:
- pif = db().get_pif_by_uuid(pif_uuid)
-
- if action == "rewrite":
- action_rewrite()
- else:
- if not pif:
- raise Usage("No PIF given")
-
- if force_management:
- # pif is going to be the management pif
- management_pif = pif
- else:
- # pif is not going to be the management pif.
- # Search DB cache for pif on same host with management=true
- pifrec = db().get_pif_record(pif)
- management_pif = db().get_management_pif()
-
- log_pif_action(action, pif)
-
- if not check_allowed(pif):
- return 0
-
- if action == "up":
- action_up(pif, False)
- elif action == "down":
- action_down(pif)
- else:
- raise Error("Unknown action %s" % action)
-
- # Save cache.
- db().save(dbcache_file)
-
- except Usage as err:
- sys.stderr.write(err.msg + "\n")
- sys.stderr.write("For help use --help.\n")
- sys.stderr.flush()
- return 2
- except Error as err:
- log(err.msg)
- return 1
-
- return 0
-
-if __name__ == "__main__":
- rc = 1
- try:
- rc = main()
- except:
- ex = sys.exc_info()
- err = traceback.format_exception(*ex)
- for exline in err:
- log(exline)
-
- syslog.closelog()
-
- sys.exit(rc)
diff --git a/xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py b/xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py
deleted file mode 100644
index 8946917d5..000000000
--- a/xenserver/usr_lib_xsconsole_plugins-base_XSFeatureVSwitch.py
+++ /dev/null
@@ -1,331 +0,0 @@
-# Copyright (c) 2009,2010,2011,2012,2013 Nicira, Inc.
-# Copyright (c) 2007-2011 Citrix Systems Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; version 2 only.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License along
-# with this program; if not, write to the Free Software Foundation, Inc.,
-# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
-
-from XSConsoleLog import *
-
-import os
-import socket
-import subprocess
-
-vsctl="/usr/bin/ovs-vsctl"
-
-if __name__ == "__main__":
- raise Exception("This script is a plugin for xsconsole and cannot run independently")
-
-from XSConsoleStandard import *
-
-class VSwitchService:
- service = {}
-
- def __init__(self, name, processname=None):
- self.name = name
- self.processname = processname
- if self.processname == None:
- self.processname = name
-
- def version(self):
- try:
- output = ShellPipe(["service", self.name, "version"]).Stdout()
- except StandardError as e:
- XSLogError("vswitch version retrieval error: " + str(e))
- return "<unknown>"
- for line in output:
- if self.processname in line:
- return line.split()[-1]
- return "<unknown>"
-
- def status(self):
- try:
- output = ShellPipe(["service", self.name, "status"]).Stdout()
- except StandardError as e:
- XSLogError("vswitch status retrieval error: " + str(e))
- return "<unknown>"
- if len(output) == 0:
- return "<unknown>"
- for line in output:
- if self.processname not in line:
- continue
- elif "running" in line:
- return "Running"
- elif "stop" in line:
- return "Stopped"
- else:
- return "<unknown>"
- return "<unknown>"
-
- def restart(self):
- try:
- ShellPipe(["service", self.name, "restart"]).Call()
- except StandardError as e:
- XSLogError("vswitch restart error: " + str(e))
-
- @classmethod
- def Inst(cls, name, processname=None):
- key = name
- if processname != None:
- key = key + "-" + processname
- if name not in cls.service:
- cls.service[key] = VSwitchService(name, processname)
- return cls.service[key]
-
-class VSwitchConfig:
-
- @staticmethod
- def Get(action):
- try:
- arg = [vsctl, "-vconsole:off"] + action.split()
- output = ShellPipe(arg).Stdout()
- except StandardError as e:
- XSLogError("config retrieval error: " + str(e))
- return "<unknown>"
-
- if len(output) == 0:
- output = ""
- else:
- output = output[0].strip()
- return output
-
-
-class VSwitchControllerDialogue(Dialogue):
- def __init__(self):
- Dialogue.__init__(self)
- data=Data.Inst()
-
- self.hostsInPool = 0
- self.hostsUpdated = 0
- self.xs_version = data.host.software_version.product_version('')
- pool = data.GetPoolForThisHost()
- if pool is not None:
- self.controller = pool.get("vswitch_controller", "")
- else:
- self.controller = ""
-
- choiceDefs = [
- ChoiceDef(Lang("Set pool-wide controller"),
- lambda: self.getController()),
- ChoiceDef(Lang("Delete pool-wide controller"),
- lambda: self.deleteController()),
- ChoiceDef(Lang("Resync server controller config"),
- lambda: self.syncController()),
-# ChoiceDef(Lang("Restart ovs-vswitchd"),
-# lambda: self.restartService("vswitch")),
- ]
- self.menu = Menu(self, None, Lang("Configure Open vSwitch"), choiceDefs)
-
- self.ChangeState("INITIAL")
-
- def BuildPane(self):
- pane = self.NewPane(DialoguePane(self.parent))
- pane.TitleSet(Lang("Configure Open vSwitch"))
- pane.AddBox()
-
- def ChangeState(self, inState):
- self.state = inState
- self.BuildPane()
- self.UpdateFields()
-
- def UpdateFields(self):
- self.Pane().ResetPosition()
- getattr(self, "UpdateFields" + self.state)() # Dispatch method named 'UpdateFields'+self.state
-
- def UpdateFieldsINITIAL(self):
- pane = self.Pane()
- pane.AddTitleField(Lang("Select an action"))
- pane.AddMenuField(self.menu)
- pane.AddKeyHelpField( { Lang("<Enter>") : Lang("OK"), Lang("<Esc>") : Lang("Cancel") } )
-
- def UpdateFieldsGETCONTROLLER(self):
- pane = self.Pane()
- pane.ResetFields()
-
- pane.AddTitleField(Lang("Enter IP address of controller"))
- pane.AddInputField(Lang("Address", 16), self.controller, "address")
- pane.AddKeyHelpField( { Lang("<Enter>") : Lang("OK"), Lang("<Esc>") : Lang("Exit") } )
- if pane.CurrentInput() is None:
- pane.InputIndexSet(0)
-
- def HandleKey(self, inKey):
- handled = False
- if hasattr(self, "HandleKey" + self.state):
- handled = getattr(self, "HandleKey" + self.state)(inKey)
- if not handled and inKey == 'KEY_ESCAPE':
- Layout.Inst().PopDialogue()
- handled = True
- return handled
-
- def HandleKeyINITIAL(self, inKey):
- return self.menu.HandleKey(inKey)
-
- def HandleKeyGETCONTROLLER(self, inKey):
- pane = self.Pane()
- if pane.CurrentInput() is None:
- pane.InputIndexSet(0)
- if inKey == 'KEY_ENTER':
- inputValues = pane.GetFieldValues()
- self.controller = inputValues['address']
- Layout.Inst().PopDialogue()
-
- # Make sure the controller is specified as a valid dotted quad
- try:
- socket.inet_aton(self.controller)
- except socket.error:
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Please enter in dotted quad format")))
- return True
-
- Layout.Inst().TransientBanner(Lang("Setting controller..."))
- try:
- self.SetController(self.controller)
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Setting controller successful")))
- except Exception as e:
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Setting controller failed")))
-
- self.ChangeState("INITIAL")
- return True
- else:
- return pane.CurrentInput().HandleKey(inKey)
-
- def restartService(self, name):
- s = VSwitchService.Inst(name)
- s.restart()
- Layout.Inst().PopDialogue()
-
- def getController(self):
- self.ChangeState("GETCONTROLLER")
- self.Pane().InputIndexSet(0)
-
- def deleteController(self):
- self.controller = ""
- Layout.Inst().PopDialogue()
- Layout.Inst().TransientBanner(Lang("Deleting controller..."))
- try:
- self.SetController(None)
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Controller deletion successful")))
- except Exception as e:
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Controller deletion failed")))
-
- def syncController(self):
- Layout.Inst().PopDialogue()
- Layout.Inst().TransientBanner(Lang("Resyncing controller setting..."))
- try:
- Task.Sync(lambda s: self._updateThisServer(s))
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Resyncing controller config successful")))
- except Exception as e:
- Layout.Inst().PushDialogue(InfoDialogue(Lang("Resyncing controller config failed")))
-
- def SetController(self, ip):
- self.hostsInPool = 0
- self.hostsUpdated = 0
- Task.Sync(lambda s: self._modifyPoolConfig(s, ip or ""))
- # Should be done asynchronously, maybe with an external script?
- Task.Sync(lambda s: self._updateActiveServers(s))
-
- def _modifyPoolConfig(self, session, value):
- """Modify pool configuration.
-
- If value == "" then delete configuration, otherwise set to value.
- """
- pools = session.xenapi.pool.get_all()
- # We assume there is only ever one pool...
- if len(pools) == 0:
- XSLogFatal(Lang("No pool found for host."))
- return
- if len(pools) > 1:
- XSLogFatal(Lang("More than one pool for host."))
- return
- session.xenapi.pool.set_vswitch_controller(value)
- Data.Inst().Update()
-
- def _updateActiveServers(self, session):
- hosts = session.xenapi.host.get_all()
- self.hostsUpdated = 0
- self.hostsInPool = len(hosts)
- self.UpdateFields()
- for host in hosts:
- Layout.Inst().TransientBanner("Updating host %d out of %d"
- % (self.hostsUpdated + 1, self.hostsInPool))
- session.xenapi.host.call_plugin(host, "openvswitch-cfg-update", "update", {})
- self.hostsUpdated = self.hostsUpdated + 1
-
- def _updateThisServer(self, session):
- data = Data.Inst()
- host = data.host.opaqueref()
- session.xenapi.host.call_plugin(host, "openvswitch-cfg-update", "update", {})
-
-
-class XSFeatureVSwitch:
-
- @classmethod
- def StatusUpdateHandler(cls, inPane):
- data = Data.Inst()
- xs_version = data.host.software_version.product_version('')
-
- inPane.AddTitleField(Lang("Open vSwitch"))
-
- inPane.NewLine()
-
- inPane.AddStatusField(Lang("Version", 20),
- VSwitchService.Inst("openvswitch", "ovs-vswitchd").version())
-
- inPane.NewLine()
-
- pool = data.GetPoolForThisHost()
- if pool is not None:
- dbController = pool.get("vswitch_controller", "")
- else:
- dbController = ""
-
- if dbController == "":
- dbController = Lang("<None>")
- inPane.AddStatusField(Lang("Controller (config)", 20), dbController)
- controller = VSwitchConfig.Get("get-manager")
-
- if controller == "":
- controller = Lang("<None>")
- elif controller[0:4] == "ssl:":
- controller = controller.split(':')[1]
- inPane.AddStatusField(Lang("Controller (in-use)", 20), controller)
-
- inPane.NewLine()
- inPane.AddStatusField(Lang("ovs-vswitchd status", 20),
- VSwitchService.Inst("openvswitch", "ovs-vswitchd").status())
- inPane.AddStatusField(Lang("ovsdb-server status", 20),
- VSwitchService.Inst("openvswitch", "ovsdb-server").status())
-
- inPane.AddKeyHelpField( {
- Lang("<Enter>") : Lang("Reconfigure"),
- Lang("<F5>") : Lang("Refresh")
- })
-
- @classmethod
- def ActivateHandler(cls):
- DialogueUtils.AuthenticatedOnly(lambda: Layout.Inst().PushDialogue(VSwitchControllerDialogue()))
-
- def Register(self):
- Importer.RegisterNamedPlugIn(
- self,
- 'VSwitch', # Key of this plugin for replacement, etc.
- {
- 'menuname' : 'MENU_NETWORK',
- 'menupriority' : 800,
- 'menutext' : Lang('Open vSwitch') ,
- 'statusupdatehandler' : self.StatusUpdateHandler,
- 'activatehandler' : self.ActivateHandler
- }
- )
-
-# Register this plugin when module is imported, IFF vswitchd is running
-if os.path.exists('/var/run/openvswitch/ovs-vswitchd.pid'):
- XSFeatureVSwitch().Register()
diff --git a/xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync b/xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync
deleted file mode 100755
index bff85464b..000000000
--- a/xenserver/usr_share_openvswitch_scripts_ovs-xapi-sync
+++ /dev/null
@@ -1,404 +0,0 @@
-#!/usr/bin/env python3
-# Copyright (c) 2009, 2010, 2011, 2012, 2013, 2020 Nicira, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-
-# A daemon to monitor the external_ids columns of the Bridge and
-# Interface OVSDB tables for changes that require interrogating XAPI.
-# Its responsibilities include:
-#
-# - Set the "bridge-id" key in the Bridge table.
-# - Set the "iface-id" key in the Interface table.
-# - Set the fail-mode on internal bridges.
-
-import argparse
-import os
-import sys
-import time
-
-import XenAPI
-
-import ovs.daemon
-import ovs.db.idl
-import ovs.dirs
-import ovs.unixctl
-import ovs.unixctl.server
-
-vlog = ovs.vlog.Vlog("ovs-xapi-sync")
-session = None
-flush_cache = False
-exiting = False
-xapi_down = False
-
-
-def unixctl_exit(conn, unused_argv, unused_aux):
- global exiting
- exiting = True
- conn.reply(None)
-
-
-def unixctl_flush_cache(conn, unused_argv, unused_aux):
- global flush_cache
- flush_cache = True
- conn.reply(None)
-
-
-# Set up a session to interact with XAPI.
-#
-# On system start-up, OVS comes up before XAPI, so we can't log into the
-# session until later. Try to do this on-demand, since we won't
-# actually do anything interesting until XAPI is up.
-def init_session():
- global session
- if session is not None:
- return True
-
- try:
- session = XenAPI.xapi_local()
- session.xenapi.login_with_password("", "")
- except XenAPI.Failure as e:
- session = None
- vlog.warn("Couldn't login to XAPI (%s)" % e)
- return False
-
- return True
-
-
-def get_network_by_bridge(br_name):
- if not init_session():
- vlog.warn("Failed to get bridge id %s because"
- " XAPI session could not be initialized" % br_name)
- return None
-
- recs = session.xenapi.network.get_all_records_where(
- 'field "bridge"="%s"' % br_name)
- if len(recs) > 0:
- return next(iter(recs.values()))
-
- return None
-
-
-# There are possibilities when multiple xs-network-uuids are set for a bridge.
-# In cases like that, we should choose the bridge-id associated with the bridge
-# name.
-def get_single_bridge_id(bridge_ids, br_name, default=None):
- global xapi_down
-
- rec = get_network_by_bridge(br_name)
- if rec and rec['uuid'] in bridge_ids:
- return rec['uuid']
-
- vlog.warn("Failed to get a single bridge id from Xapi.")
- xapi_down = True
- return default
-
-
-# By default, the "bridge-id" external id in the Bridge table is the
-# same as "xs-network-uuids". This may be overridden by defining a
-# "nicira-bridge-id" key in the "other_config" field of the network
-# record of XAPI. If nicira-bridge-id is undefined returns default.
-# On error returns None.
-def get_bridge_id(br_name, default=None):
- rec = get_network_by_bridge(br_name)
- if rec:
- return rec['other_config'].get('nicira-bridge-id', default)
- return None
-
-
-# By default, the "iface-id" external id in the Interface table is the
-# same as "xs-vif-uuid". This may be overridden by defining a
-# "nicira-iface-id" key in the "other_config" field of the VIF
-# record of XAPI.
-def get_iface_id(if_name, xs_vif_uuid):
- if not if_name.startswith("vif") and not if_name.startswith("tap"):
- # Treat whatever was passed into 'xs_vif_uuid' as a default
- # value for non-VIFs.
- return xs_vif_uuid
-
- if not init_session():
- vlog.warn("Failed to get interface id %s because"
- " XAPI session could not be initialized" % if_name)
- return xs_vif_uuid
-
- try:
- vif = session.xenapi.VIF.get_by_uuid(xs_vif_uuid)
- rec = session.xenapi.VIF.get_record(vif)
- return rec['other_config'].get('nicira-iface-id', xs_vif_uuid)
- except XenAPI.Failure:
- vlog.warn("Could not find XAPI entry for VIF %s" % if_name)
- return xs_vif_uuid
-
-
-# By default, the "vm-id" external id in the Interface table is the
-# same as "xs-vm-uuid". This may be overridden by defining a
-# "nicira-vm-id" key in the "other_config" field of the VM
-# record of XAPI.
-def get_vm_id(if_name, xs_vm_uuid):
- if not if_name.startswith("vif") and not if_name.startswith("tap"):
- # Treat whatever was passed into 'xs_vm_uuid' as a default
- # value for non-VIFs.
- return xs_vm_uuid
-
- if not init_session():
- vlog.warn("Failed to get vm id for interface id %s because"
- " XAPI session could not be initialized" % if_name)
- return xs_vm_uuid
-
- try:
- vm = session.xenapi.VM.get_by_uuid(xs_vm_uuid)
- rec = session.xenapi.VM.get_record(vm)
- return rec['other_config'].get('nicira-vm-id', xs_vm_uuid)
- except XenAPI.Failure:
- vlog.warn("Could not find XAPI entry for VIF %s" % if_name)
- return xs_vm_uuid
-
-
-def set_or_delete(d, key, value):
- if value is None:
- if key in d:
- del d[key]
- return True
- else:
- if d.get(key) != value:
- d[key] = value
- return True
- return False
-
-
-def set_external_id(row, key, value):
- row.verify("external_ids")
- external_ids = row.external_ids
- if set_or_delete(external_ids, key, value):
- row.external_ids = external_ids
-
-
-# XenServer does not call interface-reconfigure on internal networks,
-# which is where the fail-mode would normally be set.
-def update_fail_mode(row):
- rec = get_network_by_bridge(row.name)
- if not rec:
- return
-
- fail_mode = rec['other_config'].get('vswitch-controller-fail-mode')
-
- if not fail_mode:
- pools = session.xenapi.pool.get_all()
- if len(pools) == 1:
- prec = session.xenapi.pool.get_record(pools[0])
- fail_mode = prec['other_config'].get(
- 'vswitch-controller-fail-mode')
-
- if fail_mode not in ['standalone', 'secure']:
- fail_mode = 'standalone'
-
- row.verify("fail_mode")
- if row.fail_mode != fail_mode:
- row.fail_mode = fail_mode
-
-
-def update_in_band_mgmt(row):
- rec = get_network_by_bridge(row.name)
- if not rec:
- return
-
- dib = rec['other_config'].get('vswitch-disable-in-band')
-
- row.verify("other_config")
- other_config = row.other_config
- if dib and dib not in ['true', 'false']:
- vlog.warn('"%s" isn\'t a valid setting for '
- "other_config:disable-in-band on %s" % (dib, row.name))
- elif set_or_delete(other_config, 'disable-in-band', dib):
- row.other_config = other_config
-
-
-def main():
- global flush_cache, xapi_down
-
- parser = argparse.ArgumentParser()
- parser.add_argument("database", metavar="DATABASE",
- help="A socket on which ovsdb-server is listening.")
- parser.add_argument("--root-prefix", metavar="DIR", default='',
- help="Use DIR as alternate root directory"
- " (for testing).")
-
- ovs.vlog.add_args(parser)
- ovs.daemon.add_args(parser)
- args = parser.parse_args()
- ovs.vlog.handle_args(args)
- ovs.daemon.handle_args(args)
-
- remote = args.database
- schema_helper = ovs.db.idl.SchemaHelper()
- schema_helper.register_columns("Bridge", ["name", "external_ids",
- "other_config", "fail_mode"])
- schema_helper.register_columns("Interface", ["name", "external_ids"])
- idl = ovs.db.idl.Idl(remote, schema_helper)
-
- ovs.daemon.daemonize()
-
- ovs.unixctl.command_register("exit", "", 0, 0, unixctl_exit, None)
- ovs.unixctl.command_register("flush-cache", "", 0, 0, unixctl_flush_cache,
- None)
- error, unixctl_server = ovs.unixctl.server.UnixctlServer.create(None)
- if error:
- ovs.util.ovs_fatal(error, "could not create unixctl server", vlog)
-
- # This daemon is usually started before XAPI, but to complete our
- # tasks, we need it. Wait here until it's up.
- cookie_file = args.root_prefix + "/var/run/xapi_init_complete.cookie"
- while not os.path.exists(cookie_file):
- time.sleep(1)
-
- bridges = {} # Map from bridge name to nicira-bridge-id
- iface_ids = {} # Map from xs-vif-uuid to iface-id
- vm_ids = {} # Map from xs-vm-uuid to vm-id
- seqno = idl.change_seqno # Sequence number when we last processed the db
- while True:
- unixctl_server.run()
- if exiting:
- break
-
- idl.run()
- if not xapi_down and not flush_cache and seqno == idl.change_seqno:
- poller = ovs.poller.Poller()
- unixctl_server.wait(poller)
- idl.wait(poller)
- poller.block()
- continue
-
- if xapi_down:
- vlog.warn("Xapi is probably down. Retry again after a second.")
- time.sleep(1)
- xapi_down = False
-
- if flush_cache:
- vlog.info("Flushing cache as the result of unixctl.")
- bridges = {}
- iface_ids = {}
- vm_ids = {}
- flush_cache = False
- seqno = idl.change_seqno
-
- txn = ovs.db.idl.Transaction(idl)
-
- new_bridges = {}
- for row in idl.tables["Bridge"].rows.values():
- bridge_id = bridges.get(row.name)
- if bridge_id is None:
- # Configure the new bridge.
- update_fail_mode(row)
- update_in_band_mgmt(row)
-
- # Get the correct bridge_id, if we can.
- bridge_id = get_bridge_id(row.name)
- if bridge_id is None:
- xs_network_uuids = row.external_ids.get("xs-network-uuids")
- if xs_network_uuids:
- bridge_ids = xs_network_uuids.split(";")
- if len(bridge_ids) == 1:
- bridge_id = bridge_ids[0]
- else:
- bridge_id = get_single_bridge_id(bridge_ids,
- row.name)
- set_external_id(row, "bridge-id", bridge_id)
-
- if bridge_id is not None:
- new_bridges[row.name] = bridge_id
- bridges = new_bridges
-
- iface_by_name = {}
- for row in idl.tables["Interface"].rows.values():
- iface_by_name[row.name] = row
-
- new_iface_ids = {}
- new_vm_ids = {}
- for row in idl.tables["Interface"].rows.values():
- # Match up paired vif and tap devices.
- if row.name.startswith("vif"):
- vif = row
- tap = iface_by_name.get("tap%s" % row.name[3:])
- elif row.name.startswith("tap"):
- tap = row
- vif = iface_by_name.get("vif%s" % row.name[3:])
- else:
- tap = vif = None
-
- # Several tap external-ids need to be copied from the vif.
- if row == tap and vif:
- keys = ["attached-mac",
- "xs-network-uuid",
- "xs-vif-uuid",
- "xs-vm-uuid"]
- for k in keys:
- set_external_id(row, k, vif.external_ids.get(k))
-
- # Map from xs-vif-uuid to iface-id.
- #
- # (A tap's xs-vif-uuid comes from its vif. That falls out
- # naturally from the copy loop above.)
- xvu = row.external_ids.get("xs-vif-uuid")
- if xvu:
- iface_id = (new_iface_ids.get(xvu)
- or iface_ids.get(xvu)
- or get_iface_id(row.name, xvu))
- new_iface_ids[xvu] = iface_id
- else:
- # No xs-vif-uuid therefore no iface-id.
- iface_id = None
- set_external_id(row, "iface-id", iface_id)
-
- # Map from xs-vm-uuid to vm-id.
- xvmu = row.external_ids.get("xs-vm-uuid")
- if xvmu:
- vm_id = (new_vm_ids.get(xvmu)
- or vm_ids.get(xvmu)
- or get_vm_id(row.name, xvmu))
- new_vm_ids[xvmu] = vm_id
- else:
- vm_id = None
- set_external_id(row, "vm-id", vm_id)
-
- # When there's a vif and a tap, the tap is active (used for
- # traffic). When there's just a vif, the vif is active.
- #
- # A tap on its own shouldn't happen, and we don't know
- # anything about other kinds of devices, so we don't use
- # an iface-status for those devices at all.
- if vif and tap:
- set_external_id(tap, "iface-status", "active")
- set_external_id(vif, "iface-status", "inactive")
- elif vif:
- set_external_id(vif, "iface-status", "active")
- else:
- set_external_id(row, "iface-status", None)
- iface_ids = new_iface_ids
- vm_ids = new_vm_ids
-
- txn.add_comment("ovs-xapi-sync: Updating records from XAPI")
- txn.commit_block()
-
- unixctl_server.close()
- idl.close()
-
-
-if __name__ == '__main__':
- try:
- main()
- except SystemExit:
- # Let system.exit() calls complete normally
- raise
- except:
- vlog.exception("traceback")
- sys.exit(ovs.daemon.RESTART_EXIT_CODE)
diff --git a/xenserver/usr_share_openvswitch_scripts_sysconfig.template b/xenserver/usr_share_openvswitch_scripts_sysconfig.template
deleted file mode 100644
index 2c0845296..000000000
--- a/xenserver/usr_share_openvswitch_scripts_sysconfig.template
+++ /dev/null
@@ -1,24 +0,0 @@
-### Configuration options for openvswitch
-
-# Copyright (C) 2009, 2010, 2011 Nicira, Inc.
-
-# FORCE_COREFILES: If 'yes' then core files will be enabled.
-# FORCE_COREFILES=yes
-
-# OVSDB_SERVER_PRIORITY: "nice" priority at which to run ovsdb-server.
-#
-# OVSDB_SERVER_PRIORITY=-10
-
-# VSWITCHD_PRIORITY: "nice" priority at which to run ovs-vswitchd.
-# VSWITCHD_PRIORITY=-10
-
-# VSWITCHD_MLOCKALL: Whether to pass ovs-vswitchd the --mlockall option.
-# This option should be set to "yes" or "no". The default is "yes".
-# Enabling this option can avoid networking interruptions due to
-# system memory pressure in extraordinary situations, such as multiple
-# concurrent VM import operations.
-# VSWITCHD_MLOCKALL=yes
-
-# OVS_CTL_OPTS: Extra options to pass to ovs-ctl. This is, for example,
-# a suitable place to specify --ovs-vswitchd-wrapper=valgrind.
-# OVS_CTL_OPTS=