initial commit
Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
10
.gitignore
vendored
Normal file
@ -0,0 +1,10 @@
|
||||
*.py[co]
|
||||
*~
|
||||
*.egg-info/
|
||||
build/
|
||||
dist/
|
||||
|
||||
GTAGS
|
||||
GRTAGS
|
||||
GPATH
|
||||
GSYMS
|
674
COPYING
Normal file
@ -0,0 +1,674 @@
|
||||
GNU GENERAL PUBLIC LICENSE
|
||||
Version 3, 29 June 2007
|
||||
|
||||
Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
|
||||
Everyone is permitted to copy and distribute verbatim copies
|
||||
of this license document, but changing it is not allowed.
|
||||
|
||||
Preamble
|
||||
|
||||
The GNU General Public License is a free, copyleft license for
|
||||
software and other kinds of works.
|
||||
|
||||
The licenses for most software and other practical works are designed
|
||||
to take away your freedom to share and change the works. By contrast,
|
||||
the GNU General Public License is intended to guarantee your freedom to
|
||||
share and change all versions of a program--to make sure it remains free
|
||||
software for all its users. We, the Free Software Foundation, use the
|
||||
GNU General Public License for most of our software; it applies also to
|
||||
any other work released this way by its authors. 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
|
||||
them 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 prevent others from denying you
|
||||
these rights or asking you to surrender the rights. Therefore, you have
|
||||
certain responsibilities if you distribute copies of the software, or if
|
||||
you modify it: responsibilities to respect the freedom of others.
|
||||
|
||||
For example, if you distribute copies of such a program, whether
|
||||
gratis or for a fee, you must pass on to the recipients the same
|
||||
freedoms that you received. 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.
|
||||
|
||||
Developers that use the GNU GPL protect your rights with two steps:
|
||||
(1) assert copyright on the software, and (2) offer you this License
|
||||
giving you legal permission to copy, distribute and/or modify it.
|
||||
|
||||
For the developers' and authors' protection, the GPL clearly explains
|
||||
that there is no warranty for this free software. For both users' and
|
||||
authors' sake, the GPL requires that modified versions be marked as
|
||||
changed, so that their problems will not be attributed erroneously to
|
||||
authors of previous versions.
|
||||
|
||||
Some devices are designed to deny users access to install or run
|
||||
modified versions of the software inside them, although the manufacturer
|
||||
can do so. This is fundamentally incompatible with the aim of
|
||||
protecting users' freedom to change the software. The systematic
|
||||
pattern of such abuse occurs in the area of products for individuals to
|
||||
use, which is precisely where it is most unacceptable. Therefore, we
|
||||
have designed this version of the GPL to prohibit the practice for those
|
||||
products. If such problems arise substantially in other domains, we
|
||||
stand ready to extend this provision to those domains in future versions
|
||||
of the GPL, as needed to protect the freedom of users.
|
||||
|
||||
Finally, every program is threatened constantly by software patents.
|
||||
States should not allow patents to restrict development and use of
|
||||
software on general-purpose computers, but in those that do, we wish to
|
||||
avoid the special danger that patents applied to a free program could
|
||||
make it effectively proprietary. To prevent this, the GPL assures that
|
||||
patents cannot be used to render the program non-free.
|
||||
|
||||
The precise terms and conditions for copying, distribution and
|
||||
modification follow.
|
||||
|
||||
TERMS AND CONDITIONS
|
||||
|
||||
0. Definitions.
|
||||
|
||||
"This License" refers to version 3 of the GNU General Public License.
|
||||
|
||||
"Copyright" also means copyright-like laws that apply to other kinds of
|
||||
works, such as semiconductor masks.
|
||||
|
||||
"The Program" refers to any copyrightable work licensed under this
|
||||
License. Each licensee is addressed as "you". "Licensees" and
|
||||
"recipients" may be individuals or organizations.
|
||||
|
||||
To "modify" a work means to copy from or adapt all or part of the work
|
||||
in a fashion requiring copyright permission, other than the making of an
|
||||
exact copy. The resulting work is called a "modified version" of the
|
||||
earlier work or a work "based on" the earlier work.
|
||||
|
||||
A "covered work" means either the unmodified Program or a work based
|
||||
on the Program.
|
||||
|
||||
To "propagate" a work means to do anything with it that, without
|
||||
permission, would make you directly or secondarily liable for
|
||||
infringement under applicable copyright law, except executing it on a
|
||||
computer or modifying a private copy. Propagation includes copying,
|
||||
distribution (with or without modification), making available to the
|
||||
public, and in some countries other activities as well.
|
||||
|
||||
To "convey" a work means any kind of propagation that enables other
|
||||
parties to make or receive copies. Mere interaction with a user through
|
||||
a computer network, with no transfer of a copy, is not conveying.
|
||||
|
||||
An interactive user interface displays "Appropriate Legal Notices"
|
||||
to the extent that it includes a convenient and prominently visible
|
||||
feature that (1) displays an appropriate copyright notice, and (2)
|
||||
tells the user that there is no warranty for the work (except to the
|
||||
extent that warranties are provided), that licensees may convey the
|
||||
work under this License, and how to view a copy of this License. If
|
||||
the interface presents a list of user commands or options, such as a
|
||||
menu, a prominent item in the list meets this criterion.
|
||||
|
||||
1. Source Code.
|
||||
|
||||
The "source code" for a work means the preferred form of the work
|
||||
for making modifications to it. "Object code" means any non-source
|
||||
form of a work.
|
||||
|
||||
A "Standard Interface" means an interface that either is an official
|
||||
standard defined by a recognized standards body, or, in the case of
|
||||
interfaces specified for a particular programming language, one that
|
||||
is widely used among developers working in that language.
|
||||
|
||||
The "System Libraries" of an executable work include anything, other
|
||||
than the work as a whole, that (a) is included in the normal form of
|
||||
packaging a Major Component, but which is not part of that Major
|
||||
Component, and (b) serves only to enable use of the work with that
|
||||
Major Component, or to implement a Standard Interface for which an
|
||||
implementation is available to the public in source code form. A
|
||||
"Major Component", in this context, means a major essential component
|
||||
(kernel, window system, and so on) of the specific operating system
|
||||
(if any) on which the executable work runs, or a compiler used to
|
||||
produce the work, or an object code interpreter used to run it.
|
||||
|
||||
The "Corresponding Source" for a work in object code form means all
|
||||
the source code needed to generate, install, and (for an executable
|
||||
work) run the object code and to modify the work, including scripts to
|
||||
control those activities. However, it does not include the work's
|
||||
System Libraries, or general-purpose tools or generally available free
|
||||
programs which are used unmodified in performing those activities but
|
||||
which are not part of the work. For example, Corresponding Source
|
||||
includes interface definition files associated with source files for
|
||||
the work, and the source code for shared libraries and dynamically
|
||||
linked subprograms that the work is specifically designed to require,
|
||||
such as by intimate data communication or control flow between those
|
||||
subprograms and other parts of the work.
|
||||
|
||||
The Corresponding Source need not include anything that users
|
||||
can regenerate automatically from other parts of the Corresponding
|
||||
Source.
|
||||
|
||||
The Corresponding Source for a work in source code form is that
|
||||
same work.
|
||||
|
||||
2. Basic Permissions.
|
||||
|
||||
All rights granted under this License are granted for the term of
|
||||
copyright on the Program, and are irrevocable provided the stated
|
||||
conditions are met. This License explicitly affirms your unlimited
|
||||
permission to run the unmodified Program. The output from running a
|
||||
covered work is covered by this License only if the output, given its
|
||||
content, constitutes a covered work. This License acknowledges your
|
||||
rights of fair use or other equivalent, as provided by copyright law.
|
||||
|
||||
You may make, run and propagate covered works that you do not
|
||||
convey, without conditions so long as your license otherwise remains
|
||||
in force. You may convey covered works to others for the sole purpose
|
||||
of having them make modifications exclusively for you, or provide you
|
||||
with facilities for running those works, provided that you comply with
|
||||
the terms of this License in conveying all material for which you do
|
||||
not control copyright. Those thus making or running the covered works
|
||||
for you must do so exclusively on your behalf, under your direction
|
||||
and control, on terms that prohibit them from making any copies of
|
||||
your copyrighted material outside their relationship with you.
|
||||
|
||||
Conveying under any other circumstances is permitted solely under
|
||||
the conditions stated below. Sublicensing is not allowed; section 10
|
||||
makes it unnecessary.
|
||||
|
||||
3. Protecting Users' Legal Rights From Anti-Circumvention Law.
|
||||
|
||||
No covered work shall be deemed part of an effective technological
|
||||
measure under any applicable law fulfilling obligations under article
|
||||
11 of the WIPO copyright treaty adopted on 20 December 1996, or
|
||||
similar laws prohibiting or restricting circumvention of such
|
||||
measures.
|
||||
|
||||
When you convey a covered work, you waive any legal power to forbid
|
||||
circumvention of technological measures to the extent such circumvention
|
||||
is effected by exercising rights under this License with respect to
|
||||
the covered work, and you disclaim any intention to limit operation or
|
||||
modification of the work as a means of enforcing, against the work's
|
||||
users, your or third parties' legal rights to forbid circumvention of
|
||||
technological measures.
|
||||
|
||||
4. Conveying Verbatim Copies.
|
||||
|
||||
You may convey 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;
|
||||
keep intact all notices stating that this License and any
|
||||
non-permissive terms added in accord with section 7 apply to the code;
|
||||
keep intact all notices of the absence of any warranty; and give all
|
||||
recipients a copy of this License along with the Program.
|
||||
|
||||
You may charge any price or no price for each copy that you convey,
|
||||
and you may offer support or warranty protection for a fee.
|
||||
|
||||
5. Conveying Modified Source Versions.
|
||||
|
||||
You may convey a work based on the Program, or the modifications to
|
||||
produce it from the Program, in the form of source code under the
|
||||
terms of section 4, provided that you also meet all of these conditions:
|
||||
|
||||
a) The work must carry prominent notices stating that you modified
|
||||
it, and giving a relevant date.
|
||||
|
||||
b) The work must carry prominent notices stating that it is
|
||||
released under this License and any conditions added under section
|
||||
7. This requirement modifies the requirement in section 4 to
|
||||
"keep intact all notices".
|
||||
|
||||
c) You must license the entire work, as a whole, under this
|
||||
License to anyone who comes into possession of a copy. This
|
||||
License will therefore apply, along with any applicable section 7
|
||||
additional terms, to the whole of the work, and all its parts,
|
||||
regardless of how they are packaged. This License gives no
|
||||
permission to license the work in any other way, but it does not
|
||||
invalidate such permission if you have separately received it.
|
||||
|
||||
d) If the work has interactive user interfaces, each must display
|
||||
Appropriate Legal Notices; however, if the Program has interactive
|
||||
interfaces that do not display Appropriate Legal Notices, your
|
||||
work need not make them do so.
|
||||
|
||||
A compilation of a covered work with other separate and independent
|
||||
works, which are not by their nature extensions of the covered work,
|
||||
and which are not combined with it such as to form a larger program,
|
||||
in or on a volume of a storage or distribution medium, is called an
|
||||
"aggregate" if the compilation and its resulting copyright are not
|
||||
used to limit the access or legal rights of the compilation's users
|
||||
beyond what the individual works permit. Inclusion of a covered work
|
||||
in an aggregate does not cause this License to apply to the other
|
||||
parts of the aggregate.
|
||||
|
||||
6. Conveying Non-Source Forms.
|
||||
|
||||
You may convey a covered work in object code form under the terms
|
||||
of sections 4 and 5, provided that you also convey the
|
||||
machine-readable Corresponding Source under the terms of this License,
|
||||
in one of these ways:
|
||||
|
||||
a) Convey the object code in, or embodied in, a physical product
|
||||
(including a physical distribution medium), accompanied by the
|
||||
Corresponding Source fixed on a durable physical medium
|
||||
customarily used for software interchange.
|
||||
|
||||
b) Convey the object code in, or embodied in, a physical product
|
||||
(including a physical distribution medium), accompanied by a
|
||||
written offer, valid for at least three years and valid for as
|
||||
long as you offer spare parts or customer support for that product
|
||||
model, to give anyone who possesses the object code either (1) a
|
||||
copy of the Corresponding Source for all the software in the
|
||||
product that is covered by this License, on a durable physical
|
||||
medium customarily used for software interchange, for a price no
|
||||
more than your reasonable cost of physically performing this
|
||||
conveying of source, or (2) access to copy the
|
||||
Corresponding Source from a network server at no charge.
|
||||
|
||||
c) Convey individual copies of the object code with a copy of the
|
||||
written offer to provide the Corresponding Source. This
|
||||
alternative is allowed only occasionally and noncommercially, and
|
||||
only if you received the object code with such an offer, in accord
|
||||
with subsection 6b.
|
||||
|
||||
d) Convey the object code by offering access from a designated
|
||||
place (gratis or for a charge), and offer equivalent access to the
|
||||
Corresponding Source in the same way through the same place at no
|
||||
further charge. You need not require recipients to copy the
|
||||
Corresponding Source along with the object code. If the place to
|
||||
copy the object code is a network server, the Corresponding Source
|
||||
may be on a different server (operated by you or a third party)
|
||||
that supports equivalent copying facilities, provided you maintain
|
||||
clear directions next to the object code saying where to find the
|
||||
Corresponding Source. Regardless of what server hosts the
|
||||
Corresponding Source, you remain obligated to ensure that it is
|
||||
available for as long as needed to satisfy these requirements.
|
||||
|
||||
e) Convey the object code using peer-to-peer transmission, provided
|
||||
you inform other peers where the object code and Corresponding
|
||||
Source of the work are being offered to the general public at no
|
||||
charge under subsection 6d.
|
||||
|
||||
A separable portion of the object code, whose source code is excluded
|
||||
from the Corresponding Source as a System Library, need not be
|
||||
included in conveying the object code work.
|
||||
|
||||
A "User Product" is either (1) a "consumer product", which means any
|
||||
tangible personal property which is normally used for personal, family,
|
||||
or household purposes, or (2) anything designed or sold for incorporation
|
||||
into a dwelling. In determining whether a product is a consumer product,
|
||||
doubtful cases shall be resolved in favor of coverage. For a particular
|
||||
product received by a particular user, "normally used" refers to a
|
||||
typical or common use of that class of product, regardless of the status
|
||||
of the particular user or of the way in which the particular user
|
||||
actually uses, or expects or is expected to use, the product. A product
|
||||
is a consumer product regardless of whether the product has substantial
|
||||
commercial, industrial or non-consumer uses, unless such uses represent
|
||||
the only significant mode of use of the product.
|
||||
|
||||
"Installation Information" for a User Product means any methods,
|
||||
procedures, authorization keys, or other information required to install
|
||||
and execute modified versions of a covered work in that User Product from
|
||||
a modified version of its Corresponding Source. The information must
|
||||
suffice to ensure that the continued functioning of the modified object
|
||||
code is in no case prevented or interfered with solely because
|
||||
modification has been made.
|
||||
|
||||
If you convey an object code work under this section in, or with, or
|
||||
specifically for use in, a User Product, and the conveying occurs as
|
||||
part of a transaction in which the right of possession and use of the
|
||||
User Product is transferred to the recipient in perpetuity or for a
|
||||
fixed term (regardless of how the transaction is characterized), the
|
||||
Corresponding Source conveyed under this section must be accompanied
|
||||
by the Installation Information. But this requirement does not apply
|
||||
if neither you nor any third party retains the ability to install
|
||||
modified object code on the User Product (for example, the work has
|
||||
been installed in ROM).
|
||||
|
||||
The requirement to provide Installation Information does not include a
|
||||
requirement to continue to provide support service, warranty, or updates
|
||||
for a work that has been modified or installed by the recipient, or for
|
||||
the User Product in which it has been modified or installed. Access to a
|
||||
network may be denied when the modification itself materially and
|
||||
adversely affects the operation of the network or violates the rules and
|
||||
protocols for communication across the network.
|
||||
|
||||
Corresponding Source conveyed, and Installation Information provided,
|
||||
in accord with this section must be in a format that is publicly
|
||||
documented (and with an implementation available to the public in
|
||||
source code form), and must require no special password or key for
|
||||
unpacking, reading or copying.
|
||||
|
||||
7. Additional Terms.
|
||||
|
||||
"Additional permissions" are terms that supplement the terms of this
|
||||
License by making exceptions from one or more of its conditions.
|
||||
Additional permissions that are applicable to the entire Program shall
|
||||
be treated as though they were included in this License, to the extent
|
||||
that they are valid under applicable law. If additional permissions
|
||||
apply only to part of the Program, that part may be used separately
|
||||
under those permissions, but the entire Program remains governed by
|
||||
this License without regard to the additional permissions.
|
||||
|
||||
When you convey a copy of a covered work, you may at your option
|
||||
remove any additional permissions from that copy, or from any part of
|
||||
it. (Additional permissions may be written to require their own
|
||||
removal in certain cases when you modify the work.) You may place
|
||||
additional permissions on material, added by you to a covered work,
|
||||
for which you have or can give appropriate copyright permission.
|
||||
|
||||
Notwithstanding any other provision of this License, for material you
|
||||
add to a covered work, you may (if authorized by the copyright holders of
|
||||
that material) supplement the terms of this License with terms:
|
||||
|
||||
a) Disclaiming warranty or limiting liability differently from the
|
||||
terms of sections 15 and 16 of this License; or
|
||||
|
||||
b) Requiring preservation of specified reasonable legal notices or
|
||||
author attributions in that material or in the Appropriate Legal
|
||||
Notices displayed by works containing it; or
|
||||
|
||||
c) Prohibiting misrepresentation of the origin of that material, or
|
||||
requiring that modified versions of such material be marked in
|
||||
reasonable ways as different from the original version; or
|
||||
|
||||
d) Limiting the use for publicity purposes of names of licensors or
|
||||
authors of the material; or
|
||||
|
||||
e) Declining to grant rights under trademark law for use of some
|
||||
trade names, trademarks, or service marks; or
|
||||
|
||||
f) Requiring indemnification of licensors and authors of that
|
||||
material by anyone who conveys the material (or modified versions of
|
||||
it) with contractual assumptions of liability to the recipient, for
|
||||
any liability that these contractual assumptions directly impose on
|
||||
those licensors and authors.
|
||||
|
||||
All other non-permissive additional terms are considered "further
|
||||
restrictions" within the meaning of section 10. If the Program as you
|
||||
received it, or any part of it, contains a notice stating that it is
|
||||
governed by this License along with a term that is a further
|
||||
restriction, you may remove that term. If a license document contains
|
||||
a further restriction but permits relicensing or conveying under this
|
||||
License, you may add to a covered work material governed by the terms
|
||||
of that license document, provided that the further restriction does
|
||||
not survive such relicensing or conveying.
|
||||
|
||||
If you add terms to a covered work in accord with this section, you
|
||||
must place, in the relevant source files, a statement of the
|
||||
additional terms that apply to those files, or a notice indicating
|
||||
where to find the applicable terms.
|
||||
|
||||
Additional terms, permissive or non-permissive, may be stated in the
|
||||
form of a separately written license, or stated as exceptions;
|
||||
the above requirements apply either way.
|
||||
|
||||
8. Termination.
|
||||
|
||||
You may not propagate or modify a covered work except as expressly
|
||||
provided under this License. Any attempt otherwise to propagate or
|
||||
modify it is void, and will automatically terminate your rights under
|
||||
this License (including any patent licenses granted under the third
|
||||
paragraph of section 11).
|
||||
|
||||
However, if you cease all violation of this License, then your
|
||||
license from a particular copyright holder is reinstated (a)
|
||||
provisionally, unless and until the copyright holder explicitly and
|
||||
finally terminates your license, and (b) permanently, if the copyright
|
||||
holder fails to notify you of the violation by some reasonable means
|
||||
prior to 60 days after the cessation.
|
||||
|
||||
Moreover, your license from a particular copyright holder is
|
||||
reinstated permanently if the copyright holder notifies you of the
|
||||
violation by some reasonable means, this is the first time you have
|
||||
received notice of violation of this License (for any work) from that
|
||||
copyright holder, and you cure the violation prior to 30 days after
|
||||
your receipt of the notice.
|
||||
|
||||
Termination of your rights under this section does not terminate the
|
||||
licenses of parties who have received copies or rights from you under
|
||||
this License. If your rights have been terminated and not permanently
|
||||
reinstated, you do not qualify to receive new licenses for the same
|
||||
material under section 10.
|
||||
|
||||
9. Acceptance Not Required for Having Copies.
|
||||
|
||||
You are not required to accept this License in order to receive or
|
||||
run a copy of the Program. Ancillary propagation of a covered work
|
||||
occurring solely as a consequence of using peer-to-peer transmission
|
||||
to receive a copy likewise does not require acceptance. However,
|
||||
nothing other than this License grants you permission to propagate or
|
||||
modify any covered work. These actions infringe copyright if you do
|
||||
not accept this License. Therefore, by modifying or propagating a
|
||||
covered work, you indicate your acceptance of this License to do so.
|
||||
|
||||
10. Automatic Licensing of Downstream Recipients.
|
||||
|
||||
Each time you convey a covered work, the recipient automatically
|
||||
receives a license from the original licensors, to run, modify and
|
||||
propagate that work, subject to this License. You are not responsible
|
||||
for enforcing compliance by third parties with this License.
|
||||
|
||||
An "entity transaction" is a transaction transferring control of an
|
||||
organization, or substantially all assets of one, or subdividing an
|
||||
organization, or merging organizations. If propagation of a covered
|
||||
work results from an entity transaction, each party to that
|
||||
transaction who receives a copy of the work also receives whatever
|
||||
licenses to the work the party's predecessor in interest had or could
|
||||
give under the previous paragraph, plus a right to possession of the
|
||||
Corresponding Source of the work from the predecessor in interest, if
|
||||
the predecessor has it or can get it with reasonable efforts.
|
||||
|
||||
You may not impose any further restrictions on the exercise of the
|
||||
rights granted or affirmed under this License. For example, you may
|
||||
not impose a license fee, royalty, or other charge for exercise of
|
||||
rights granted under this License, and you may not initiate litigation
|
||||
(including a cross-claim or counterclaim in a lawsuit) alleging that
|
||||
any patent claim is infringed by making, using, selling, offering for
|
||||
sale, or importing the Program or any portion of it.
|
||||
|
||||
11. Patents.
|
||||
|
||||
A "contributor" is a copyright holder who authorizes use under this
|
||||
License of the Program or a work on which the Program is based. The
|
||||
work thus licensed is called the contributor's "contributor version".
|
||||
|
||||
A contributor's "essential patent claims" are all patent claims
|
||||
owned or controlled by the contributor, whether already acquired or
|
||||
hereafter acquired, that would be infringed by some manner, permitted
|
||||
by this License, of making, using, or selling its contributor version,
|
||||
but do not include claims that would be infringed only as a
|
||||
consequence of further modification of the contributor version. For
|
||||
purposes of this definition, "control" includes the right to grant
|
||||
patent sublicenses in a manner consistent with the requirements of
|
||||
this License.
|
||||
|
||||
Each contributor grants you a non-exclusive, worldwide, royalty-free
|
||||
patent license under the contributor's essential patent claims, to
|
||||
make, use, sell, offer for sale, import and otherwise run, modify and
|
||||
propagate the contents of its contributor version.
|
||||
|
||||
In the following three paragraphs, a "patent license" is any express
|
||||
agreement or commitment, however denominated, not to enforce a patent
|
||||
(such as an express permission to practice a patent or covenant not to
|
||||
sue for patent infringement). To "grant" such a patent license to a
|
||||
party means to make such an agreement or commitment not to enforce a
|
||||
patent against the party.
|
||||
|
||||
If you convey a covered work, knowingly relying on a patent license,
|
||||
and the Corresponding Source of the work is not available for anyone
|
||||
to copy, free of charge and under the terms of this License, through a
|
||||
publicly available network server or other readily accessible means,
|
||||
then you must either (1) cause the Corresponding Source to be so
|
||||
available, or (2) arrange to deprive yourself of the benefit of the
|
||||
patent license for this particular work, or (3) arrange, in a manner
|
||||
consistent with the requirements of this License, to extend the patent
|
||||
license to downstream recipients. "Knowingly relying" means you have
|
||||
actual knowledge that, but for the patent license, your conveying the
|
||||
covered work in a country, or your recipient's use of the covered work
|
||||
in a country, would infringe one or more identifiable patents in that
|
||||
country that you have reason to believe are valid.
|
||||
|
||||
If, pursuant to or in connection with a single transaction or
|
||||
arrangement, you convey, or propagate by procuring conveyance of, a
|
||||
covered work, and grant a patent license to some of the parties
|
||||
receiving the covered work authorizing them to use, propagate, modify
|
||||
or convey a specific copy of the covered work, then the patent license
|
||||
you grant is automatically extended to all recipients of the covered
|
||||
work and works based on it.
|
||||
|
||||
A patent license is "discriminatory" if it does not include within
|
||||
the scope of its coverage, prohibits the exercise of, or is
|
||||
conditioned on the non-exercise of one or more of the rights that are
|
||||
specifically granted under this License. You may not convey a covered
|
||||
work if you are a party to an arrangement with a third party that is
|
||||
in the business of distributing software, under which you make payment
|
||||
to the third party based on the extent of your activity of conveying
|
||||
the work, and under which the third party grants, to any of the
|
||||
parties who would receive the covered work from you, a discriminatory
|
||||
patent license (a) in connection with copies of the covered work
|
||||
conveyed by you (or copies made from those copies), or (b) primarily
|
||||
for and in connection with specific products or compilations that
|
||||
contain the covered work, unless you entered into that arrangement,
|
||||
or that patent license was granted, prior to 28 March 2007.
|
||||
|
||||
Nothing in this License shall be construed as excluding or limiting
|
||||
any implied license or other defenses to infringement that may
|
||||
otherwise be available to you under applicable patent law.
|
||||
|
||||
12. No Surrender of Others' Freedom.
|
||||
|
||||
If 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 convey a
|
||||
covered work so as to satisfy simultaneously your obligations under this
|
||||
License and any other pertinent obligations, then as a consequence you may
|
||||
not convey it at all. For example, if you agree to terms that obligate you
|
||||
to collect a royalty for further conveying from those to whom you convey
|
||||
the Program, the only way you could satisfy both those terms and this
|
||||
License would be to refrain entirely from conveying the Program.
|
||||
|
||||
13. Use with the GNU Affero General Public License.
|
||||
|
||||
Notwithstanding any other provision of this License, you have
|
||||
permission to link or combine any covered work with a work licensed
|
||||
under version 3 of the GNU Affero General Public License into a single
|
||||
combined work, and to convey the resulting work. The terms of this
|
||||
License will continue to apply to the part which is the covered work,
|
||||
but the special requirements of the GNU Affero General Public License,
|
||||
section 13, concerning interaction through a network will apply to the
|
||||
combination as such.
|
||||
|
||||
14. Revised Versions of this License.
|
||||
|
||||
The Free Software Foundation may publish revised and/or new versions of
|
||||
the GNU 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 that a certain numbered version of the GNU General
|
||||
Public License "or any later version" applies to it, you have the
|
||||
option of following the terms and conditions either of that numbered
|
||||
version or of any later version published by the Free Software
|
||||
Foundation. If the Program does not specify a version number of the
|
||||
GNU General Public License, you may choose any version ever published
|
||||
by the Free Software Foundation.
|
||||
|
||||
If the Program specifies that a proxy can decide which future
|
||||
versions of the GNU General Public License can be used, that proxy's
|
||||
public statement of acceptance of a version permanently authorizes you
|
||||
to choose that version for the Program.
|
||||
|
||||
Later license versions may give you additional or different
|
||||
permissions. However, no additional obligations are imposed on any
|
||||
author or copyright holder as a result of your choosing to follow a
|
||||
later version.
|
||||
|
||||
15. Disclaimer of Warranty.
|
||||
|
||||
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.
|
||||
|
||||
16. Limitation of Liability.
|
||||
|
||||
IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
||||
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
|
||||
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.
|
||||
|
||||
17. Interpretation of Sections 15 and 16.
|
||||
|
||||
If the disclaimer of warranty and limitation of liability provided
|
||||
above cannot be given local legal effect according to their terms,
|
||||
reviewing courts shall apply local law that most closely approximates
|
||||
an absolute waiver of all civil liability in connection with the
|
||||
Program, unless a warranty or assumption of liability accompanies a
|
||||
copy of the Program in return for a fee.
|
||||
|
||||
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
|
||||
state 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 3 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, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
Also add information on how to contact you by electronic and paper mail.
|
||||
|
||||
If the program does terminal interaction, make it output a short
|
||||
notice like this when it starts in an interactive mode:
|
||||
|
||||
<program> Copyright (C) <year> <name of author>
|
||||
This program 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, your program's commands
|
||||
might be different; for a GUI interface, you would use an "about box".
|
||||
|
||||
You should also get your employer (if you work as a programmer) or school,
|
||||
if any, to sign a "copyright disclaimer" for the program, if necessary.
|
||||
For more information on this, and how to apply and follow the GNU GPL, see
|
||||
<http://www.gnu.org/licenses/>.
|
||||
|
||||
The GNU 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. But first, please read
|
||||
<http://www.gnu.org/philosophy/why-not-lgpl.html>.
|
10
MANIFEST.in
Normal file
@ -0,0 +1,10 @@
|
||||
include COPYING LICENSE
|
||||
include README.rst
|
||||
include MANIFEST.in
|
||||
graft contrib
|
||||
graft doc
|
||||
graft etc
|
||||
recursive-exclude doc/build/*/ *
|
||||
global-exclude *~
|
||||
global-exclude *.pyc
|
||||
global-exclude .gitignore
|
75
README.rst
Normal file
@ -0,0 +1,75 @@
|
||||
****************************
|
||||
Ryu Network Operating System
|
||||
****************************
|
||||
|
||||
For details, please see the documentation under doc/ directory and
|
||||
make html (or make <format you prefer>). If you have any
|
||||
questions, suggestions, and patches, the mailing list is available at
|
||||
`ryu-devel ML
|
||||
<https://lists.sourceforge.net/lists/listinfo/ryu-devel>`_.
|
||||
|
||||
Ryu Official site is `<http://www.osrg.net/ryu/>`_.
|
||||
|
||||
|
||||
Overview
|
||||
========
|
||||
Ryu is an open-sourced Network Operating System (NOS) licensed under
|
||||
GPL v3. It's fully written in Python.
|
||||
|
||||
Ryu aims to provide a logically centralized control and well defined
|
||||
API that make it easy for operators to create new network management
|
||||
and control applications. Currently, Ryu supports OpenFlow protocol to
|
||||
modify the behavior of network devices.
|
||||
|
||||
We aim at the de facto OSS NOS implementation and NOS API.
|
||||
|
||||
Currently, Ryu is shipped with one control application for `OpenStack
|
||||
<http://openstack.org/.>`_ network management L2 segregation of
|
||||
tenants without using VLAN. The application includes changes to
|
||||
OpenStack (nova, quantum ovs plugin, etc).
|
||||
|
||||
The project goal is to develop an OSS Network Operating System that
|
||||
has high quality enough for use in large production environment in
|
||||
code quality/functionality/usability.
|
||||
|
||||
|
||||
TODO
|
||||
====
|
||||
* OpenFlow Protocol version 1.2 (right after the spec release)
|
||||
* The better API for control applications
|
||||
* Cluster support
|
||||
* ...too many for here.
|
||||
|
||||
|
||||
Quick Start
|
||||
===========
|
||||
Get source code::
|
||||
|
||||
% git clone git://github.com/osrg/ryu.git
|
||||
|
||||
Then just type::
|
||||
|
||||
% cd ryu; python ./setup.py install
|
||||
|
||||
and run ryu-manager command which is installed.
|
||||
Then set up your openflow switch (hardware switch or OVS) to connect the ip
|
||||
address and port to which ryu-manager is listening.
|
||||
If you want to use it with Openstack (nova and quantum with ovs plugin),
|
||||
please refer detailed documents under doc/ directory.
|
||||
|
||||
|
||||
Requirement
|
||||
===========
|
||||
* python-setuptools
|
||||
* python-gevent >= 0.13
|
||||
* python-gflags
|
||||
* python-sphinx
|
||||
|
||||
|
||||
Project Members
|
||||
===============
|
||||
* OHMURA Kei <ohmura.kei at lab.ntt.co.jp>
|
||||
* MORITA Kazutaka <morita.kazutaka at lab.ntt.co.jp>
|
||||
* Isaku Yamahata <yamahata at valinux co jp>
|
||||
* FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
|
||||
|
55
bin/ryu-client
Executable file
@ -0,0 +1,55 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import sys
|
||||
from optparse import OptionParser
|
||||
|
||||
from ryu.app.client import OFPClient
|
||||
|
||||
|
||||
def client_test():
|
||||
parser = OptionParser(usage="Usage: %prog [OPTIONS] <command> [args]")
|
||||
parser.add_option("-H", "--host", dest="host", type="string",
|
||||
default="127.0.0.1", help="ip address rest api service")
|
||||
parser.add_option("-p", "--port", dest="port", type="int", default="8080")
|
||||
|
||||
options, args = parser.parse_args()
|
||||
if len(args) == 0:
|
||||
parser.print_help()
|
||||
sys.exit(1)
|
||||
|
||||
client = OFPClient(options.host + ':' + str(options.port))
|
||||
commands = {
|
||||
'list_nets': lambda a: sys.stdout.write(client.get_networks()),
|
||||
'create_net': lambda a: client.create_network(a[1]),
|
||||
'update_net': lambda a: client.update_network(a[1]),
|
||||
'delete_net': lambda a: client.delete_network(a[1]),
|
||||
'list_ports': lambda a: sys.stdout.write(client.get_ports(a[1])),
|
||||
'create_port': lambda a: client.create_port(a[1], a[2], a[3]),
|
||||
'update_port': lambda a: client.update_port(a[1], a[2], a[3]),
|
||||
'delete_port': lambda a: client.delete_port(a[1], a[2], a[3])
|
||||
}
|
||||
|
||||
# allow '-', instead of '_'
|
||||
commands.update(dict([(k.replace('_', '-'), v)
|
||||
for (k, v) in commands.items()]))
|
||||
|
||||
cmd = args[0]
|
||||
commands[cmd](args)
|
||||
|
||||
if __name__ == "__main__":
|
||||
client_test()
|
69
bin/ryu-manager
Executable file
@ -0,0 +1,69 @@
|
||||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import gevent
|
||||
import gflags
|
||||
import logging
|
||||
import sys
|
||||
|
||||
from gevent import monkey
|
||||
monkey.patch_all()
|
||||
|
||||
from ryu import log
|
||||
log.earlyInitLog(logging.DEBUG)
|
||||
|
||||
from ryu import flags
|
||||
from ryu import utils
|
||||
from ryu.base.app_manager import AppManager
|
||||
from ryu.controller import controller
|
||||
from ryu.app import wsapi
|
||||
from ryu.app import rest
|
||||
from ryu.controller import network
|
||||
|
||||
|
||||
FLAGS = gflags.FLAGS
|
||||
gflags.DEFINE_multistring('app_lists',
|
||||
['ryu.app.simple_isolation.SimpleIsolation',
|
||||
'ryu.app.rest.restapi'],
|
||||
'application module name to run')
|
||||
|
||||
|
||||
def main():
|
||||
utils.find_flagfile()
|
||||
args = FLAGS(sys.argv)
|
||||
log.initLog()
|
||||
|
||||
nw = network.network()
|
||||
|
||||
app_mgr = AppManager()
|
||||
app_mgr.load_apps(FLAGS.app_lists, network=nw)
|
||||
|
||||
services = []
|
||||
|
||||
ctlr = controller.OpenFlowController()
|
||||
thr = gevent.spawn_later(0, ctlr)
|
||||
services.append(thr)
|
||||
|
||||
# NOX webservice API
|
||||
ws = wsapi.wsapi()
|
||||
thr = gevent.spawn_later(0, ws)
|
||||
services.append(thr)
|
||||
|
||||
gevent.joinall(services)
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
130
doc/Makefile
Normal file
@ -0,0 +1,130 @@
|
||||
# Makefile for Sphinx documentation
|
||||
#
|
||||
|
||||
# You can set these variables from the command line.
|
||||
SPHINXOPTS =
|
||||
SPHINXBUILD = sphinx-build
|
||||
PAPER =
|
||||
BUILDDIR = build
|
||||
|
||||
# Internal variables.
|
||||
PAPEROPT_a4 = -D latex_paper_size=a4
|
||||
PAPEROPT_letter = -D latex_paper_size=letter
|
||||
ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) source
|
||||
|
||||
.PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest
|
||||
|
||||
help:
|
||||
@echo "Please use \`make <target>' where <target> is one of"
|
||||
@echo " html to make standalone HTML files"
|
||||
@echo " dirhtml to make HTML files named index.html in directories"
|
||||
@echo " singlehtml to make a single large HTML file"
|
||||
@echo " pickle to make pickle files"
|
||||
@echo " json to make JSON files"
|
||||
@echo " htmlhelp to make HTML files and a HTML help project"
|
||||
@echo " qthelp to make HTML files and a qthelp project"
|
||||
@echo " devhelp to make HTML files and a Devhelp project"
|
||||
@echo " epub to make an epub"
|
||||
@echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
|
||||
@echo " latexpdf to make LaTeX files and run them through pdflatex"
|
||||
@echo " text to make text files"
|
||||
@echo " man to make manual pages"
|
||||
@echo " changes to make an overview of all changed/added/deprecated items"
|
||||
@echo " linkcheck to check all external links for integrity"
|
||||
@echo " doctest to run all doctests embedded in the documentation (if enabled)"
|
||||
|
||||
clean:
|
||||
-rm -rf $(BUILDDIR)/*
|
||||
|
||||
html:
|
||||
$(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html
|
||||
@echo
|
||||
@echo "Build finished. The HTML pages are in $(BUILDDIR)/html."
|
||||
|
||||
dirhtml:
|
||||
$(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml
|
||||
@echo
|
||||
@echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml."
|
||||
|
||||
singlehtml:
|
||||
$(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml
|
||||
@echo
|
||||
@echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml."
|
||||
|
||||
pickle:
|
||||
$(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle
|
||||
@echo
|
||||
@echo "Build finished; now you can process the pickle files."
|
||||
|
||||
json:
|
||||
$(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json
|
||||
@echo
|
||||
@echo "Build finished; now you can process the JSON files."
|
||||
|
||||
htmlhelp:
|
||||
$(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp
|
||||
@echo
|
||||
@echo "Build finished; now you can run HTML Help Workshop with the" \
|
||||
".hhp project file in $(BUILDDIR)/htmlhelp."
|
||||
|
||||
qthelp:
|
||||
$(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp
|
||||
@echo
|
||||
@echo "Build finished; now you can run "qcollectiongenerator" with the" \
|
||||
".qhcp project file in $(BUILDDIR)/qthelp, like this:"
|
||||
@echo "# qcollectiongenerator $(BUILDDIR)/qthelp/ryu.qhcp"
|
||||
@echo "To view the help file:"
|
||||
@echo "# assistant -collectionFile $(BUILDDIR)/qthelp/ryu.qhc"
|
||||
|
||||
devhelp:
|
||||
$(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp
|
||||
@echo
|
||||
@echo "Build finished."
|
||||
@echo "To view the help file:"
|
||||
@echo "# mkdir -p $$HOME/.local/share/devhelp/ryu"
|
||||
@echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/ryu"
|
||||
@echo "# devhelp"
|
||||
|
||||
epub:
|
||||
$(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub
|
||||
@echo
|
||||
@echo "Build finished. The epub file is in $(BUILDDIR)/epub."
|
||||
|
||||
latex:
|
||||
$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
|
||||
@echo
|
||||
@echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex."
|
||||
@echo "Run \`make' in that directory to run these through (pdf)latex" \
|
||||
"(use \`make latexpdf' here to do that automatically)."
|
||||
|
||||
latexpdf:
|
||||
$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
|
||||
@echo "Running LaTeX files through pdflatex..."
|
||||
$(MAKE) -C $(BUILDDIR)/latex all-pdf
|
||||
@echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
|
||||
|
||||
text:
|
||||
$(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text
|
||||
@echo
|
||||
@echo "Build finished. The text files are in $(BUILDDIR)/text."
|
||||
|
||||
man:
|
||||
$(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man
|
||||
@echo
|
||||
@echo "Build finished. The manual pages are in $(BUILDDIR)/man."
|
||||
|
||||
changes:
|
||||
$(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes
|
||||
@echo
|
||||
@echo "The overview file is in $(BUILDDIR)/changes."
|
||||
|
||||
linkcheck:
|
||||
$(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck
|
||||
@echo
|
||||
@echo "Link check complete; look for any errors in the above output " \
|
||||
"or in $(BUILDDIR)/linkcheck/output.txt."
|
||||
|
||||
doctest:
|
||||
$(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest
|
||||
@echo "Testing of doctests in the sources finished, look at the " \
|
||||
"results in $(BUILDDIR)/doctest/output.txt."
|
0
doc/source/_static/.placeholder
Normal file
0
doc/source/_templates/.placeholder
Normal file
216
doc/source/conf.py
Normal file
@ -0,0 +1,216 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
#
|
||||
# ryu documentation build configuration file, created by
|
||||
# sphinx-quickstart on Mon Dec 5 15:38:48 2011.
|
||||
#
|
||||
# This file is execfile()d with the current directory set to its containing dir.
|
||||
#
|
||||
# Note that not all possible configuration values are present in this
|
||||
# autogenerated file.
|
||||
#
|
||||
# All configuration values have a default; values that are commented out
|
||||
# serve to show the default.
|
||||
|
||||
import sys, os
|
||||
|
||||
# If extensions (or modules to document with autodoc) are in another directory,
|
||||
# add these directories to sys.path here. If the directory is relative to the
|
||||
# documentation root, use os.path.abspath to make it absolute, like shown here.
|
||||
#sys.path.insert(0, os.path.abspath('.'))
|
||||
|
||||
# -- General configuration -----------------------------------------------------
|
||||
|
||||
# If your documentation needs a minimal Sphinx version, state it here.
|
||||
#needs_sphinx = '1.0'
|
||||
|
||||
# Add any Sphinx extension module names here, as strings. They can be extensions
|
||||
# coming with Sphinx (named 'sphinx.ext.*') or your custom ones.
|
||||
extensions = []
|
||||
|
||||
# Add any paths that contain templates here, relative to this directory.
|
||||
templates_path = ['_templates']
|
||||
|
||||
# The suffix of source filenames.
|
||||
source_suffix = '.rst'
|
||||
|
||||
# The encoding of source files.
|
||||
#source_encoding = 'utf-8-sig'
|
||||
|
||||
# The master toctree document.
|
||||
master_doc = 'index'
|
||||
|
||||
# General information about the project.
|
||||
project = u'ryu'
|
||||
copyright = u'2011, ryu development team'
|
||||
|
||||
# The version info for the project you're documenting, acts as replacement for
|
||||
# |version| and |release|, also used in various other places throughout the
|
||||
# built documents.
|
||||
#
|
||||
# The short X.Y version.
|
||||
version = '0.1'
|
||||
# The full version, including alpha/beta/rc tags.
|
||||
release = '0.1'
|
||||
|
||||
# The language for content autogenerated by Sphinx. Refer to documentation
|
||||
# for a list of supported languages.
|
||||
#language = None
|
||||
|
||||
# There are two options for replacing |today|: either, you set today to some
|
||||
# non-false value, then it is used:
|
||||
#today = ''
|
||||
# Else, today_fmt is used as the format for a strftime call.
|
||||
#today_fmt = '%B %d, %Y'
|
||||
|
||||
# List of patterns, relative to source directory, that match files and
|
||||
# directories to ignore when looking for source files.
|
||||
exclude_patterns = []
|
||||
|
||||
# The reST default role (used for this markup: `text`) to use for all documents.
|
||||
#default_role = None
|
||||
|
||||
# If true, '()' will be appended to :func: etc. cross-reference text.
|
||||
#add_function_parentheses = True
|
||||
|
||||
# If true, the current module name will be prepended to all description
|
||||
# unit titles (such as .. function::).
|
||||
#add_module_names = True
|
||||
|
||||
# If true, sectionauthor and moduleauthor directives will be shown in the
|
||||
# output. They are ignored by default.
|
||||
#show_authors = False
|
||||
|
||||
# The name of the Pygments (syntax highlighting) style to use.
|
||||
pygments_style = 'sphinx'
|
||||
|
||||
# A list of ignored prefixes for module index sorting.
|
||||
#modindex_common_prefix = []
|
||||
|
||||
|
||||
# -- Options for HTML output ---------------------------------------------------
|
||||
|
||||
# The theme to use for HTML and HTML Help pages. See the documentation for
|
||||
# a list of builtin themes.
|
||||
html_theme = 'default'
|
||||
|
||||
# Theme options are theme-specific and customize the look and feel of a theme
|
||||
# further. For a list of options available for each theme, see the
|
||||
# documentation.
|
||||
#html_theme_options = {}
|
||||
|
||||
# Add any paths that contain custom themes here, relative to this directory.
|
||||
#html_theme_path = []
|
||||
|
||||
# The name for this set of Sphinx documents. If None, it defaults to
|
||||
# "<project> v<release> documentation".
|
||||
#html_title = None
|
||||
|
||||
# A shorter title for the navigation bar. Default is the same as html_title.
|
||||
#html_short_title = None
|
||||
|
||||
# The name of an image file (relative to this directory) to place at the top
|
||||
# of the sidebar.
|
||||
#html_logo = None
|
||||
|
||||
# The name of an image file (within the static path) to use as favicon of the
|
||||
# docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32
|
||||
# pixels large.
|
||||
#html_favicon = None
|
||||
|
||||
# Add any paths that contain custom static files (such as style sheets) here,
|
||||
# relative to this directory. They are copied after the builtin static files,
|
||||
# so a file named "default.css" will overwrite the builtin "default.css".
|
||||
html_static_path = ['_static']
|
||||
|
||||
# If not '', a 'Last updated on:' timestamp is inserted at every page bottom,
|
||||
# using the given strftime format.
|
||||
#html_last_updated_fmt = '%b %d, %Y'
|
||||
|
||||
# If true, SmartyPants will be used to convert quotes and dashes to
|
||||
# typographically correct entities.
|
||||
#html_use_smartypants = True
|
||||
|
||||
# Custom sidebar templates, maps document names to template names.
|
||||
#html_sidebars = {}
|
||||
|
||||
# Additional templates that should be rendered to pages, maps page names to
|
||||
# template names.
|
||||
#html_additional_pages = {}
|
||||
|
||||
# If false, no module index is generated.
|
||||
#html_domain_indices = True
|
||||
|
||||
# If false, no index is generated.
|
||||
#html_use_index = True
|
||||
|
||||
# If true, the index is split into individual pages for each letter.
|
||||
#html_split_index = False
|
||||
|
||||
# If true, links to the reST sources are added to the pages.
|
||||
#html_show_sourcelink = True
|
||||
|
||||
# If true, "Created using Sphinx" is shown in the HTML footer. Default is True.
|
||||
#html_show_sphinx = True
|
||||
|
||||
# If true, "(C) Copyright ..." is shown in the HTML footer. Default is True.
|
||||
#html_show_copyright = True
|
||||
|
||||
# If true, an OpenSearch description file will be output, and all pages will
|
||||
# contain a <link> tag referring to it. The value of this option must be the
|
||||
# base URL from which the finished HTML is served.
|
||||
#html_use_opensearch = ''
|
||||
|
||||
# This is the file name suffix for HTML files (e.g. ".xhtml").
|
||||
#html_file_suffix = None
|
||||
|
||||
# Output file base name for HTML help builder.
|
||||
htmlhelp_basename = 'ryudoc'
|
||||
|
||||
|
||||
# -- Options for LaTeX output --------------------------------------------------
|
||||
|
||||
# The paper size ('letter' or 'a4').
|
||||
#latex_paper_size = 'letter'
|
||||
|
||||
# The font size ('10pt', '11pt' or '12pt').
|
||||
#latex_font_size = '10pt'
|
||||
|
||||
# Grouping the document tree into LaTeX files. List of tuples
|
||||
# (source start file, target name, title, author, documentclass [howto/manual]).
|
||||
latex_documents = [
|
||||
('index', 'ryu.tex', u'ryu Documentation',
|
||||
u'ryu development team', 'manual'),
|
||||
]
|
||||
|
||||
# The name of an image file (relative to this directory) to place at the top of
|
||||
# the title page.
|
||||
#latex_logo = None
|
||||
|
||||
# For "manual" documents, if this is true, then toplevel headings are parts,
|
||||
# not chapters.
|
||||
#latex_use_parts = False
|
||||
|
||||
# If true, show page references after internal links.
|
||||
#latex_show_pagerefs = False
|
||||
|
||||
# If true, show URL addresses after external links.
|
||||
#latex_show_urls = False
|
||||
|
||||
# Additional stuff for the LaTeX preamble.
|
||||
#latex_preamble = ''
|
||||
|
||||
# Documents to append as an appendix to all manuals.
|
||||
#latex_appendices = []
|
||||
|
||||
# If false, no module index is generated.
|
||||
#latex_domain_indices = True
|
||||
|
||||
|
||||
# -- Options for manual page output --------------------------------------------
|
||||
|
||||
# One entry per manual page. List of tuples
|
||||
# (source start file, name, description, authors, manual section).
|
||||
man_pages = [
|
||||
('index', 'ryu', u'ryu Documentation',
|
||||
[u'ryu development team'], 1)
|
||||
]
|
43
doc/source/getting_started.rst
Normal file
@ -0,0 +1,43 @@
|
||||
.. _getting_started:
|
||||
|
||||
***************
|
||||
Getting Started
|
||||
***************
|
||||
|
||||
Overview/What's Ryu the Network OS
|
||||
==================================
|
||||
Ryu is an open-sourced Network OS which is licensed under GPL v3.
|
||||
It supports openflow protocol.
|
||||
|
||||
If you are not familiar with Software Defined Network(SDN) and
|
||||
OpenFlow/openflow controller,
|
||||
please refer to `openflow org <http://www.openflow.org/>`_ .
|
||||
|
||||
The mailing list is available at
|
||||
`ryu-devel ML <https://lists.sourceforge.net/lists/listinfo/ryu-devel>`_
|
||||
|
||||
|
||||
Installing Ryu Network OS
|
||||
=========================
|
||||
Extract source code and just type::
|
||||
|
||||
% python ./setup.py install
|
||||
|
||||
Then, run ryu-manager.
|
||||
It listens to ip address 0.0.0.0 and port 6633 by default.
|
||||
Then have your openflow switch (hardware or openvswitch OVS) to connect to
|
||||
ryu-manager.
|
||||
|
||||
For OVS case, you can done it by
|
||||
|
||||
% ovs-vsctl set-controller <your bridge> tcp:<ip addr>[:<port: default 6633>]
|
||||
|
||||
At the moment, ryu-manager supports only tcp method.
|
||||
If you want to use it with openstack nova and quantum OVS plugin,
|
||||
Please refer to :ref:`using_with_openstack`.
|
||||
|
||||
Configuration
|
||||
=============
|
||||
It can be configured by passing configuration file like::
|
||||
|
||||
ryu-manager [--flagfile <path to configuration file>]
|
66
doc/source/how_l2_segregation_works.rst
Normal file
@ -0,0 +1,66 @@
|
||||
.. _how_it_works:
|
||||
|
||||
****************************
|
||||
How Ryu L2 segregation works
|
||||
****************************
|
||||
This section describes how Ryu L2 segregation works.
|
||||
|
||||
tenant/network id creation
|
||||
==========================
|
||||
When tenant(= network id) is created, Quantum server tells it to Ryu.
|
||||
Ryu remembers the network id.
|
||||
|
||||
.. image:: /images/network-creation.png
|
||||
|
||||
|
||||
association OVS port to network id
|
||||
==================================
|
||||
#. When VM instance is created, the network port is created in OVS and
|
||||
it is associated to network id that VM belongs to.
|
||||
|
||||
#. quantum OVS agent tells the associated (network id, ovs port) to Ryu.
|
||||
Ryu remembers (network id, ovs port) relationship.
|
||||
|
||||
#. quantum OVS agent also tells to Ryu which OVS port is not managed by
|
||||
nova/quantum, but is connected to external ether cable.
|
||||
We call it external OVS port or that the port is external.
|
||||
|
||||
|
||||
.. image:: /images/assoc-ovs-port.png
|
||||
|
||||
|
||||
mac learing
|
||||
===========
|
||||
When VM sends packets, Ryu determins network id from OVS port and then
|
||||
associates src mac address to network id.
|
||||
|
||||
.. image:: /images/mac-learning.png
|
||||
|
||||
|
||||
packet filtering(L2 unicast case)
|
||||
=================================
|
||||
* When VM sending L2-unicast packet, Ryu checks if the destination mac
|
||||
address belongs to the same netowrk id of the source mac address which
|
||||
is same to the network id that the OVS port is associated to.
|
||||
* If no, the packet is dropped.
|
||||
* If yes, send the packet is sent to ports which belongs to the same
|
||||
network id and external port.
|
||||
|
||||
.. image:: /images/filtering-outgoing.png
|
||||
.. image:: /images/filtering-incoming.png
|
||||
|
||||
|
||||
packet filtering(L2 broadcast case)
|
||||
===================================
|
||||
* When VM sending L2-broadcast/multicaset packet, Ryu checks if the source
|
||||
mac address.
|
||||
* send the packet to all external ports and all OVS ports that belongs
|
||||
to the same network id of the source mac address.
|
||||
* When receiving broacast/multicast packet from the external ports,
|
||||
Ryu checks if the source mac address belongs to known network id.
|
||||
|
||||
* If yes, send the packet to the external ports except incoming one
|
||||
and the all OVS ports that belongs to the network id
|
||||
* if no, drop the packet.
|
||||
|
||||
.. image:: /images/filtering-broadcast.png
|
BIN
doc/source/images/assoc-ovs-port.png
Normal file
After Width: | Height: | Size: 73 KiB |
572
doc/source/images/assoc-ovs-port.svg
Normal file
@ -0,0 +1,572 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="assoc-ovs-port.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/assoc-ovs-port.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="526.18109"
|
||||
inkscape:cy="372.04724"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="50"
|
||||
inkscape:window-y="3"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5113"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) translate(1,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lenda"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lenda"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5800"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#05ff00;stroke-width:1.0pt;fill:#05ff00;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lendan"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lendan"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5943"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;marker-start:none;stroke:#059500;stroke-width:1.0pt;fill:#059500"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient6508"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(1.3132307,0,0,2.7180446,-75.36157,-1462.7849)"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621" />
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 123.73525,580.64067 0,-137.21137"
|
||||
id="path6078"
|
||||
inkscape:connector-curvature="0" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6508);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:2.11107063;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="279.1908"
|
||||
height="382.82706"
|
||||
x="-773.92023"
|
||||
y="38.426575"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(447.14019,-66.6113)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="80.828072"
|
||||
y="594.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="573.76764"
|
||||
x="74.293457"
|
||||
height="168.16565"
|
||||
width="337.21384"
|
||||
id="rect5351-5"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.17921257px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2"
|
||||
y="732.48846"
|
||||
x="126.48773"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="732.48846"
|
||||
x="126.48773"
|
||||
id="tspan5355-6"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,33.246065,405.64778)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274"
|
||||
y="671.74854"
|
||||
x="129.07115"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="671.74854"
|
||||
x="129.07115"
|
||||
id="tspan5276"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="694.24854"
|
||||
x="129.07115"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,-136.00519,426.12072)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="604.38098"
|
||||
x="106.25084"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="604.38098"
|
||||
x="106.25084"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228"
|
||||
d="m 125.69215,649.44811 0.20564,-35.3061"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="272.5264"
|
||||
y="768.13312"
|
||||
id="text3193"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3195"
|
||||
x="272.5264"
|
||||
y="768.13312">physical host</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#059500;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:10, 5;stroke-dashoffset:0;marker-end:url(#Arrow1Lendan)"
|
||||
d="m 133.53606,634.54513 c 324.65191,31.85264 390.25092,-12.63222 485.1402,-57.57977"
|
||||
id="path4298"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<g
|
||||
id="g5754"
|
||||
transform="translate(67.380584,-198.52388)">
|
||||
<path
|
||||
transform="matrix(1.1689088,0,0,0.56811324,22.97702,634.03964)"
|
||||
d="m 269.78156,191.14935 c 0,17.44202 -37.62559,31.58157 -84.0391,31.58157 -46.41351,0 -84.03909,-14.13955 -84.03909,-31.58157 0,-17.44202 37.62558,-31.58157 84.03909,-31.58157 46.41351,0 84.0391,14.13955 84.0391,31.58157 z"
|
||||
sodipodi:ry="31.581572"
|
||||
sodipodi:rx="84.039093"
|
||||
sodipodi:cy="191.14935"
|
||||
sodipodi:cx="185.74246"
|
||||
id="path6269"
|
||||
style="opacity:0.4125;fill:#3866a9;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="arc" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6271"
|
||||
y="746.23999"
|
||||
x="149.63055"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:#000000;stroke-opacity:1;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="746.23999"
|
||||
x="149.63055"
|
||||
id="tspan6273"
|
||||
sodipodi:role="line">quantum_ovs_agent</tspan></text>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="49.00404"
|
||||
y="820.76062"
|
||||
id="text6045"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="49.00404"
|
||||
y="820.76062"
|
||||
id="tspan6049">associates OVS port to network id</tspan></text>
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(-137.65551,-234.28264)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#05ff00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="459.41306"
|
||||
y="697.02533"
|
||||
id="text6080"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6082"
|
||||
x="459.41306"
|
||||
y="697.02533">network_id</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:10, 5;stroke-dashoffset:0;marker-end:url(#Arrow1Lend)"
|
||||
d="M 128.63566,546.33782 C 275.64784,379.72402 611.32565,513.26008 611.32565,513.26008"
|
||||
id="path6084"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="286.67377"
|
||||
y="374.82364"
|
||||
id="text6494"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6496"
|
||||
x="286.67377"
|
||||
y="374.82364">external port</tspan></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot6500"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion6502"><rect
|
||||
id="rect6504"
|
||||
width="978.85608"
|
||||
height="519.44305"
|
||||
x="-91.882614"
|
||||
y="261.40448" /></flowRegion><flowPara
|
||||
id="flowPara6506"></flowPara></flowRoot> </g>
|
||||
</svg>
|
After Width: | Height: | Size: 22 KiB |
BIN
doc/source/images/compute-node.png
Normal file
After Width: | Height: | Size: 71 KiB |
722
doc/source/images/compute-node.svg
Normal file
@ -0,0 +1,722 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="compute-node.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/compute-node.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.81601008"
|
||||
inkscape:cx="538.22825"
|
||||
inkscape:cy="378.53655"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1314"
|
||||
inkscape:window-height="980"
|
||||
inkscape:window-x="110"
|
||||
inkscape:window-y="42"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.6454892,0,0,2.6579041,-106.61003,-1414.0767)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-6"
|
||||
xlink:href="#linearGradient5343-7-43"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-43">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-0" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-3" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2041922,0,0,2.7019977,-347.48146,-932.31394)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient8058"
|
||||
xlink:href="#linearGradient5343-7-4-5"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4-5">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1-6" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6-1" />
|
||||
</linearGradient>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 237.11002,689.51457 1.86077,-123.1146"
|
||||
id="path6488-0-2"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5485-6"
|
||||
d="m 246.19071,689.24143 0.82837,-123.63888"
|
||||
style="fill:none;stroke:#000000;stroke-width:5.2421937;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6079-6);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:2.33679771;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4-9"
|
||||
width="349.8284"
|
||||
height="374.35648"
|
||||
x="-981.90985"
|
||||
y="53.918316"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="14.34453"
|
||||
y="1039.1901"
|
||||
id="text5549"
|
||||
sodipodi:linespacing="125%"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/compute-node.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5551"
|
||||
x="14.34453"
|
||||
y="1039.1901">compute node: single NIC</tspan></text>
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(-60,2)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667" />
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 347.28719,818.50031 -235.12212,0 -1.13388,-109.57905 95.01236,-0.15491"
|
||||
id="path6473-0"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cccc" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5485-5"
|
||||
d="m 369.67935,811.39255 -0.65638,-99.51593 -85.07583,-0.79742"
|
||||
style="fill:none;stroke:#000000;stroke-width:5.2421937;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
sodipodi:nodetypes="ccc" />
|
||||
<path
|
||||
sodipodi:type="arc"
|
||||
style="opacity:0.4125;fill:#3866a9;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path6269-5"
|
||||
sodipodi:cx="185.74246"
|
||||
sodipodi:cy="191.14935"
|
||||
sodipodi:rx="84.039093"
|
||||
sodipodi:ry="31.581572"
|
||||
d="m 269.78156,191.14935 a 84.039093,31.581572 0 1 1 -168.07819,0 84.039093,31.581572 0 1 1 168.07819,0 z"
|
||||
transform="matrix(1.1689088,0,0,0.56811324,34.35592,665.4191)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:#000000;stroke-opacity:1;font-family:Bitstream Vera Sans"
|
||||
x="159.9389"
|
||||
y="777.61945"
|
||||
id="text6271-1"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6273-1"
|
||||
x="159.9389"
|
||||
y="777.61945">quantum_ovs_agent</tspan></text>
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 157.93794,773.53672 -45.24394,0"
|
||||
id="path6488-0"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<g
|
||||
id="g5864-4-8-5"
|
||||
transform="matrix(1,0,0,0.71409652,-491.78016,176.92621)">
|
||||
<rect
|
||||
y="601.5531"
|
||||
x="722.52655"
|
||||
height="59.086094"
|
||||
width="26.969246"
|
||||
id="rect5858-6-0-0"
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="matrix(0,1,-1,0,0,0)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5860-69-9-6"
|
||||
y="-729.16479"
|
||||
x="603.36359"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="-729.16479"
|
||||
x="603.36359"
|
||||
id="tspan5862-8-6-4"
|
||||
sodipodi:role="line">peth</tspan></text>
|
||||
</g>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="opacity:0.275;fill:#b1c76d;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path3488"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="703.35907"
|
||||
sodipodi:cy="240.93047"
|
||||
sodipodi:r1="24.436026"
|
||||
sodipodi:r2="21.162218"
|
||||
sodipodi:arg1="2.0736395"
|
||||
sodipodi:arg2="2.5972383"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 691.58289,262.3417 -12.65458,-20.90409 11.77618,-21.41123 24.43076,-0.50715 12.65458,20.90409 -11.77618,21.41123 z"
|
||||
transform="matrix(1.57683,0,0,0.88317766,-864.61882,496.27264)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="216.08893"
|
||||
y="715.48041"
|
||||
id="text3490"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3492"
|
||||
x="216.08893"
|
||||
y="715.48041">bridge</tspan></text>
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.67163575px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6-1"
|
||||
width="26.969246"
|
||||
height="42.193172"
|
||||
x="98.511742"
|
||||
y="691.39148" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:20.2810154px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="819.70374"
|
||||
y="-87.1661"
|
||||
id="text5860-69-2"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,0.84504232,-1.1833727,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8-0"
|
||||
x="819.70374"
|
||||
y="-87.1661">veth</tspan></text>
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.67163575px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6-1-4"
|
||||
width="26.969246"
|
||||
height="42.193172"
|
||||
x="356.81827"
|
||||
y="689.26471" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:20.2810154px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="819.55377"
|
||||
y="-307.13614"
|
||||
id="text5860-69-2-6"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,0.84504232,-1.1833727,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8-0-2"
|
||||
x="819.55377"
|
||||
y="-307.13614">veth</tspan></text>
|
||||
<g
|
||||
transform="translate(189.61855,-3.63579)"
|
||||
id="g4188-6">
|
||||
<rect
|
||||
y="807.76764"
|
||||
x="120.29346"
|
||||
height="168.16565"
|
||||
width="337.21384"
|
||||
id="rect5351-5-2-9"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.17921257px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
transform="translate(-228.13313,-0.39285583)" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2-6"
|
||||
y="966.48846"
|
||||
x="172.48773"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="translate(-228.13313,-0.39285583)"><tspan
|
||||
y="966.48846"
|
||||
x="172.48773"
|
||||
id="tspan5355-6-5"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<g
|
||||
id="g4099-6"
|
||||
transform="translate(-228.13313,-0.39285583)">
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-6"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.69506452,0,0,0.47991755,79.246065,639.64778)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="175.07115"
|
||||
y="905.74854"
|
||||
id="text5274-3"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-4"
|
||||
x="175.07115"
|
||||
y="905.74854"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="175.07115"
|
||||
y="928.24854"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
id="tspan3167-1">tenant-X</tspan></text>
|
||||
</g>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5329-7-8"
|
||||
y="913.58319"
|
||||
x="311.78284"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="translate(-228.13313,-0.39285583)"><tspan
|
||||
id="tspan5333-1"
|
||||
y="913.58319"
|
||||
x="311.78284"
|
||||
sodipodi:role="line">...</tspan></text>
|
||||
<g
|
||||
id="g6174-1-3-4"
|
||||
transform="translate(-334.01622,209.06446)">
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5523-9-0"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:arg2="0.52359878"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
transform="matrix(1.0086434,0,0,0.68923037,243.74678,449.4383)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="486.00281"
|
||||
y="627.69855"
|
||||
id="text5525-6-8-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5527-5-2"
|
||||
x="486.00281"
|
||||
y="627.69855">OVS</tspan></text>
|
||||
</g>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-9"
|
||||
d="M 180.26786,884.67321 374.03954,832.21569"
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
transform="translate(-228.13313,-0.39285583)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6230-0"
|
||||
d="m 293.74741,898.5905 88.85662,-53.52808"
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
transform="translate(-228.13313,-0.39285583)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6232-1"
|
||||
d="m 395.45077,882.53208 18.19954,-34.25796"
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
transform="translate(-228.13313,-0.39285583)" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text7945-1-8-0"
|
||||
y="855.57654"
|
||||
x="90.787804"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#193edc;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="translate(-228.13313,-0.39285583)"><tspan
|
||||
style="fill:#31562b;fill-opacity:1;stroke:none"
|
||||
y="855.57654"
|
||||
x="90.787804"
|
||||
id="tspan7947-2-1-8"
|
||||
sodipodi:role="line">openflow</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,-44.98222,640.35447)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-8-1"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-5-6"
|
||||
y="906.84808"
|
||||
x="278.97601"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="translate(-228.13313,-0.39285583)"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="906.84808"
|
||||
x="278.97601"
|
||||
id="tspan5276-33-7"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-8-8"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="929.34808"
|
||||
x="278.97601"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#ccff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-7-8"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.69506452,0,0,0.47991755,79.246065,639.64778)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="175.07115"
|
||||
y="905.74854"
|
||||
id="text5274-7-2"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-1-1"
|
||||
x="175.07115"
|
||||
y="905.74854"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="175.07115"
|
||||
y="928.24854"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
id="tspan3167-2-3">tenant-...</tspan></text>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="29.411377"
|
||||
y="589.0155"
|
||||
id="text3348"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3350"
|
||||
x="29.411377"
|
||||
y="589.0155">peth: physical NIC</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="29.411377"
|
||||
y="614.0155"
|
||||
id="tspan3352">veth: virtual NIC</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
x="64.95018"
|
||||
y="656.40637"
|
||||
id="text3354"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="64.95018"
|
||||
y="656.40637"
|
||||
id="tspan3358">physical host</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 30 KiB |
BIN
doc/source/images/filtering-broadcast.png
Normal file
After Width: | Height: | Size: 77 KiB |
882
doc/source/images/filtering-broadcast.svg
Normal file
@ -0,0 +1,882 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="filtering-broadcast.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/filtering-broadcast.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="378.08468"
|
||||
inkscape:cy="372.04724"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="153"
|
||||
inkscape:window-y="155"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
style="overflow:visible;"
|
||||
id="Arrow1Send"
|
||||
refX="0.0"
|
||||
refY="0.0"
|
||||
orient="auto"
|
||||
inkscape:stockid="Arrow1Send">
|
||||
<path
|
||||
transform="scale(0.2) rotate(180) translate(6,0)"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
id="path4154" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4166"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5113"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) translate(1,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lenda"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lenda"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5800"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#05ff00;stroke-width:1.0pt;fill:#05ff00;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lendan"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lendan"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5943"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;marker-start:none;stroke:#059500;stroke-width:1.0pt;fill:#059500"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient6508"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(2.1604673,0,0,4.0490813,171.38161,-2201.4268)"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2MendC"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4651"
|
||||
style="stroke-linejoin:round;font-size:12.0;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.62500000;fill:#05ff00"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend4"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend4"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path6229"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#0000ff;stroke-width:1.0pt;fill:#0000ff;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-8"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-7"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-9"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-2"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-1"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-75"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 299.73525,592.64067 0,-137.21137"
|
||||
id="path6078"
|
||||
inkscape:connector-curvature="0" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6508);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.30488253;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="459.31204"
|
||||
height="570.29883"
|
||||
x="-977.85541"
|
||||
y="34.933594"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<rect
|
||||
y="559.10913"
|
||||
x="60.505432"
|
||||
height="367.65173"
|
||||
width="519.54852"
|
||||
id="rect5351-5"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:5.83484936px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2"
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
id="tspan5355-6"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,209.24607,569.64778)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
id="tspan5276"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="858.24854"
|
||||
x="305.07117"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,39.99481,438.12072)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228"
|
||||
d="m 301.69654,637.7282 0.16768,162.95949"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:9.474823;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="234.13361"
|
||||
y="961.9939"
|
||||
id="text3193"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3195"
|
||||
x="234.13361"
|
||||
y="961.9939">physical host</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="text6045"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="tspan3090">broadcast filtering</tspan></text>
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(38.34449,-222.28264)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#05ff00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="459.41306"
|
||||
y="697.02533"
|
||||
id="text6080"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6082"
|
||||
x="459.41306"
|
||||
y="697.02533" /></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot6500"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion6502"><rect
|
||||
id="rect6504"
|
||||
width="978.85608"
|
||||
height="519.44305"
|
||||
x="-91.882614"
|
||||
y="261.40448" /></flowRegion><flowPara
|
||||
id="flowPara6506" /></flowRoot> <rect
|
||||
y="391.50186"
|
||||
x="539.10345"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364-7"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366-8"
|
||||
y="423.66403"
|
||||
x="546.43896"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="423.66403"
|
||||
x="546.43896"
|
||||
id="tspan5368-6"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<rect
|
||||
y="451.30692"
|
||||
x="543.70288"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7-9"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1-8"
|
||||
y="496.10165"
|
||||
x="517.40717"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="496.10165"
|
||||
x="517.40717"
|
||||
id="tspan5238-6-0-7-5"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(252.26686,-258.61948)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="80.828072"
|
||||
y="594.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="392.70511"
|
||||
x="336.8739"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366"
|
||||
y="424.86722"
|
||||
x="344.20935"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="424.86722"
|
||||
x="344.20935"
|
||||
id="tspan5368"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<rect
|
||||
y="448.73129"
|
||||
x="330.94141"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1"
|
||||
y="493.36758"
|
||||
x="316.90228"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="493.36758"
|
||||
x="316.90228"
|
||||
id="tspan5238-6-0-7"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,36.24517,333.72159)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-9"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-7"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
id="tspan5276-5"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-3"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="622.32227"
|
||||
x="132.07027"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,418.47684,336.17178)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-8"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-8"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
id="tspan5276-3"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-1"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="624.77258"
|
||||
x="514.30194"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
id="text3315"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3317"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
style="font-size:22px;fill:#ff0000">X:block</tspan></text>
|
||||
<rect
|
||||
y="382.81296"
|
||||
x="147.81929"
|
||||
height="97.126534"
|
||||
width="101.95992"
|
||||
id="rect5232-3-7"
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.68900102px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<rect
|
||||
y="383.77469"
|
||||
x="148.8909"
|
||||
height="47.919254"
|
||||
width="99.525726"
|
||||
id="rect5234-1-0"
|
||||
style="fill:none;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.95860159000000000px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-0-4"
|
||||
y="428.19177"
|
||||
x="142.9001"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="428.19177"
|
||||
x="142.9001"
|
||||
id="tspan5238-7-8"
|
||||
sodipodi:role="line">broadcast/</tspan><tspan
|
||||
y="449.74713"
|
||||
x="142.9001"
|
||||
sodipodi:role="line"
|
||||
id="tspan3123">multicast</tspan></text>
|
||||
<rect
|
||||
y="432.63403"
|
||||
x="148.29062"
|
||||
height="24.908871"
|
||||
width="99.792274"
|
||||
id="rect5234-2-4-0"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.69205552px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-4"
|
||||
y="477.57947"
|
||||
x="145.92354"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="477.57947"
|
||||
x="145.92354"
|
||||
id="tspan5238-6-0-2"
|
||||
sodipodi:role="line">src addr</tspan></text>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5280-1-9"
|
||||
y="504.86719"
|
||||
x="163.08846"
|
||||
style="font-size:15.80727291px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="504.86719"
|
||||
x="163.08846"
|
||||
id="tspan5282-8-6"
|
||||
sodipodi:role="line">data</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 272.57822,610.10054 -95.55792,-1.2251"
|
||||
id="path6078-6"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 464.91915,612.55074 -132.31096,-1.2251"
|
||||
id="path6078-9"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-0"
|
||||
d="m 270.11538,448.07067 0.1713,126.73982"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8"
|
||||
d="m 270.11603,628.79147 -77.01907,-1.48458"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8-7"
|
||||
d="m 337.67593,631.84027 35.90109,1.00644"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:4.11323547;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="172.32462"
|
||||
y="658.73059"
|
||||
id="text4337-4"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan4339-5"
|
||||
x="172.32462"
|
||||
y="658.73059">forward</tspan></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot4029"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion4031"><rect
|
||||
id="rect4033"
|
||||
width="580.69812"
|
||||
height="236.4446"
|
||||
x="526.79364"
|
||||
y="-33.844967" /></flowRegion><flowPara
|
||||
id="flowPara4035"></flowPara></flowRoot> </g>
|
||||
</svg>
|
After Width: | Height: | Size: 36 KiB |
BIN
doc/source/images/filtering-incoming.png
Normal file
After Width: | Height: | Size: 79 KiB |
958
doc/source/images/filtering-incoming.svg
Normal file
@ -0,0 +1,958 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="filtering-incoming.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/filtering-incoming.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="452.97333"
|
||||
inkscape:cy="372.04724"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="118"
|
||||
inkscape:window-y="72"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
style="overflow:visible;"
|
||||
id="Arrow1Send"
|
||||
refX="0.0"
|
||||
refY="0.0"
|
||||
orient="auto"
|
||||
inkscape:stockid="Arrow1Send">
|
||||
<path
|
||||
transform="scale(0.2) rotate(180) translate(6,0)"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
id="path4154" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4166"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5113"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) translate(1,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lenda"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lenda"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5800"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#05ff00;stroke-width:1.0pt;fill:#05ff00;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lendan"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lendan"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5943"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;marker-start:none;stroke:#059500;stroke-width:1.0pt;fill:#059500"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient6508"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(2.1604673,0,0,4.0490813,171.38161,-2201.4268)"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2MendC"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4651"
|
||||
style="stroke-linejoin:round;font-size:12.0;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.62500000;fill:#05ff00"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend4"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend4"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path6229"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#0000ff;stroke-width:1.0pt;fill:#0000ff;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-8"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-7"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-9"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-2"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-1"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-75"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 299.73525,592.64067 0,-137.21137"
|
||||
id="path6078"
|
||||
inkscape:connector-curvature="0" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6508);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.30488253;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="459.31204"
|
||||
height="570.29883"
|
||||
x="-977.85541"
|
||||
y="34.933594"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<rect
|
||||
y="559.10913"
|
||||
x="60.505432"
|
||||
height="367.65173"
|
||||
width="519.54852"
|
||||
id="rect5351-5"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:5.83484936px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2"
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
id="tspan5355-6"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,209.24607,569.64778)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
id="tspan5276"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="858.24854"
|
||||
x="305.07117"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,39.99481,438.12072)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228"
|
||||
d="m 301.69654,637.7282 0.16768,162.95949"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:9.474823;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="234.13361"
|
||||
y="961.9939"
|
||||
id="text3193"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3195"
|
||||
x="234.13361"
|
||||
y="961.9939">physical host</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="text6045"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="tspan3090">incoming filtering</tspan></text>
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(38.34449,-222.28264)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#05ff00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="459.41306"
|
||||
y="697.02533"
|
||||
id="text6080"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6082"
|
||||
x="459.41306"
|
||||
y="697.02533" /></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot6500"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion6502"><rect
|
||||
id="rect6504"
|
||||
width="978.85608"
|
||||
height="519.44305"
|
||||
x="-91.882614"
|
||||
y="261.40448" /></flowRegion><flowPara
|
||||
id="flowPara6506" /></flowRoot> <g
|
||||
id="g5284-2"
|
||||
transform="matrix(0.7624367,0,0,0.67711861,-166.08141,112.88421)">
|
||||
<rect
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.78552711px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5232-3"
|
||||
width="117.8242"
|
||||
height="109.24851"
|
||||
x="628.36981"
|
||||
y="431.12851" />
|
||||
<rect
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-1"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.65686"
|
||||
y="432.41547" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="638.27789"
|
||||
y="458.18796"
|
||||
id="text5236-0"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-7"
|
||||
x="638.27789"
|
||||
y="458.18796">dst addr</tspan></text>
|
||||
<rect
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-2-4"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.04431"
|
||||
y="470.39359" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="637.66534"
|
||||
y="496.16611"
|
||||
id="text5236-9-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-6-0"
|
||||
x="637.66534"
|
||||
y="496.16611">src addr</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="661.55481"
|
||||
y="534.14423"
|
||||
id="text5280-1"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5282-8"
|
||||
x="661.55481"
|
||||
y="534.14423">data</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="396.40228"
|
||||
x="656.7132"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364-7"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366-8"
|
||||
y="428.56445"
|
||||
x="664.04871"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="428.56445"
|
||||
x="664.04871"
|
||||
id="tspan5368-6"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<rect
|
||||
y="456.20734"
|
||||
x="661.31262"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7-9"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1-8"
|
||||
y="501.30164"
|
||||
x="628.24133"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="501.30164"
|
||||
x="628.24133"
|
||||
id="tspan5238-6-0-7-5"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(369.87661,-253.71907)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="80.828072"
|
||||
y="594.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="397.60553"
|
||||
x="454.48364"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366"
|
||||
y="429.76764"
|
||||
x="461.81909"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="429.76764"
|
||||
x="461.81909"
|
||||
id="tspan5368"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<rect
|
||||
y="453.63171"
|
||||
x="448.55115"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1"
|
||||
y="498.56757"
|
||||
x="427.73648"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="498.56757"
|
||||
x="427.73648"
|
||||
id="tspan5238-6-0-7"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,36.24517,333.72159)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-9"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-7"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
id="tspan5276-5"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-3"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="622.32227"
|
||||
x="132.07027"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,418.47684,336.17178)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-8"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-8"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
id="tspan5276-3"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-1"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="624.77258"
|
||||
x="514.30194"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="328.93289"
|
||||
y="394.23975"
|
||||
id="text3311"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3313"
|
||||
x="328.93289"
|
||||
y="394.23975">drop</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
id="text3315"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3317"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
style="font-size:22px;fill:#ff0000">X:block</tspan></text>
|
||||
<rect
|
||||
y="406.02759"
|
||||
x="173.75699"
|
||||
height="73.974197"
|
||||
width="89.833496"
|
||||
id="rect5232-3-7"
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.56441098px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<rect
|
||||
y="406.89899"
|
||||
x="174.73828"
|
||||
height="24.947573"
|
||||
width="88.805061"
|
||||
id="rect5234-1-0"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.65335387px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-0-4"
|
||||
y="450.29169"
|
||||
x="170.86581"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="450.29169"
|
||||
x="170.86581"
|
||||
id="tspan5238-7-8"
|
||||
sodipodi:role="line">dst addr</tspan></text>
|
||||
<rect
|
||||
y="432.61469"
|
||||
x="174.27127"
|
||||
height="24.947573"
|
||||
width="88.805061"
|
||||
id="rect5234-2-4-0"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.65335387px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-4"
|
||||
y="477.57947"
|
||||
x="170.42569"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="477.57947"
|
||||
x="170.42569"
|
||||
id="tspan5238-6-0-2"
|
||||
sodipodi:role="line">src addr</tspan></text>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5280-1-9"
|
||||
y="504.86719"
|
||||
x="187.59061"
|
||||
style="font-size:15.80727291px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="504.86719"
|
||||
x="187.59061"
|
||||
id="tspan5282-8-6"
|
||||
sodipodi:role="line">data</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="189.2713"
|
||||
y="395.23572"
|
||||
id="text3373"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3375"
|
||||
x="189.2713"
|
||||
y="395.23572">pass</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 272.57822,610.10054 -95.55792,-1.2251"
|
||||
id="path6078-6"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 464.91915,612.55074 -132.31096,-1.2251"
|
||||
id="path6078-9"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-0"
|
||||
d="m 270.11538,448.07067 0.1713,126.73982"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8"
|
||||
d="m 270.11603,628.79147 -77.01907,-1.48458"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8-7"
|
||||
d="m 337.67593,631.84027 35.90109,1.00644"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:4.11323547;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="172.32462"
|
||||
y="658.73059"
|
||||
id="text4337-4"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan4339-5"
|
||||
x="172.32462"
|
||||
y="658.73059">forward</tspan></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot3137"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion3139"><rect
|
||||
id="rect3141"
|
||||
width="584.37341"
|
||||
height="270.74744"
|
||||
x="469.21387"
|
||||
y="-63.247402" /></flowRegion><flowPara
|
||||
id="flowPara3143"></flowPara></flowRoot> </g>
|
||||
</svg>
|
After Width: | Height: | Size: 39 KiB |
BIN
doc/source/images/filtering-outgoing.png
Normal file
After Width: | Height: | Size: 81 KiB |
960
doc/source/images/filtering-outgoing.svg
Normal file
@ -0,0 +1,960 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="filtering-outgoing.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/filtering-outgoing.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="440.44106"
|
||||
inkscape:cy="372.04724"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="94"
|
||||
inkscape:window-y="41"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
style="overflow:visible;"
|
||||
id="Arrow1Send"
|
||||
refX="0.0"
|
||||
refY="0.0"
|
||||
orient="auto"
|
||||
inkscape:stockid="Arrow1Send">
|
||||
<path
|
||||
transform="scale(0.2) rotate(180) translate(6,0)"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
id="path4154" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4166"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5113"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) translate(1,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lenda"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lenda"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5800"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#05ff00;stroke-width:1.0pt;fill:#05ff00;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lendan"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lendan"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5943"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;marker-start:none;stroke:#059500;stroke-width:1.0pt;fill:#059500"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient6508"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(2.1604673,0,0,4.0490813,171.38161,-2201.4268)"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2MendC"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4651"
|
||||
style="stroke-linejoin:round;font-size:12.0;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.62500000;fill:#05ff00"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend4"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend4"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path6229"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#0000ff;stroke-width:1.0pt;fill:#0000ff;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-8"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-7"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-9"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-2"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow2MendC-1"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4651-75"
|
||||
style="font-size:12px;fill:#05ff00;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.625;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 -2.2072895,0.01601326 8.7185884,-4.0017078 c -1.7454984,2.3720609 -1.7354408,5.6174519 -6e-7,8.035443 z"
|
||||
transform="scale(-0.6,-0.6)" />
|
||||
</marker>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 299.73525,592.64067 0,-137.21137"
|
||||
id="path6078"
|
||||
inkscape:connector-curvature="0" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6508);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.30488253;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="459.31204"
|
||||
height="570.29883"
|
||||
x="-977.85541"
|
||||
y="34.933594"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<rect
|
||||
y="559.10913"
|
||||
x="60.505432"
|
||||
height="367.65173"
|
||||
width="519.54852"
|
||||
id="rect5351-5"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:5.83484936px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2"
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="906.9986"
|
||||
x="259.60919"
|
||||
id="tspan5355-6"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,209.24607,569.64778)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="835.74854"
|
||||
x="305.07117"
|
||||
id="tspan5276"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="858.24854"
|
||||
x="305.07117"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,39.99481,438.12072)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="616.38098"
|
||||
x="282.25085"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228"
|
||||
d="m 301.69654,810.2751 0.16768,-162.95949"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:9.474823;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="234.13361"
|
||||
y="961.9939"
|
||||
id="text3193"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3195"
|
||||
x="234.13361"
|
||||
y="961.9939">physical host</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="text6045"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="31.2332"
|
||||
y="1021.6772"
|
||||
id="tspan3090">unicast filtering</tspan></text>
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(38.34449,-222.28264)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#05ff00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="459.41306"
|
||||
y="697.02533"
|
||||
id="text6080"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6082"
|
||||
x="459.41306"
|
||||
y="697.02533" /></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot6500"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion6502"><rect
|
||||
id="rect6504"
|
||||
width="978.85608"
|
||||
height="519.44305"
|
||||
x="-91.882614"
|
||||
y="261.40448" /></flowRegion><flowPara
|
||||
id="flowPara6506" /></flowRoot> <g
|
||||
id="g5284-2"
|
||||
transform="matrix(0.7624367,0,0,0.67711861,-148.92999,421.60979)">
|
||||
<rect
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.78552711px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5232-3"
|
||||
width="117.8242"
|
||||
height="109.24851"
|
||||
x="628.36981"
|
||||
y="431.12851" />
|
||||
<rect
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-1"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.65686"
|
||||
y="432.41547" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="638.27789"
|
||||
y="458.18796"
|
||||
id="text5236-0"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-7"
|
||||
x="638.27789"
|
||||
y="458.18796">dst addr</tspan></text>
|
||||
<rect
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-2-4"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.04431"
|
||||
y="470.39359" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="637.66534"
|
||||
y="496.16611"
|
||||
id="text5236-9-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-6-0"
|
||||
x="637.66534"
|
||||
y="496.16611">src addr</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="661.55481"
|
||||
y="534.14423"
|
||||
id="text5280-1"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5282-8"
|
||||
x="661.55481"
|
||||
y="534.14423">data</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="378.02576"
|
||||
x="536.65326"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364-7"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366-8"
|
||||
y="410.18793"
|
||||
x="543.98877"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="410.18793"
|
||||
x="543.98877"
|
||||
id="tspan5368-6"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<rect
|
||||
y="437.83081"
|
||||
x="541.25269"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7-9"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1-8"
|
||||
y="481.8017"
|
||||
x="515.09814"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="481.8017"
|
||||
x="515.09814"
|
||||
id="tspan5238-6-0-7-5"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(249.81666,-272.0956)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="80.828072"
|
||||
y="594.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="379.229"
|
||||
x="334.42374"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366"
|
||||
y="411.39111"
|
||||
x="341.75919"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="411.39111"
|
||||
x="341.75919"
|
||||
id="tspan5368"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<rect
|
||||
y="435.25519"
|
||||
x="328.49124"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1"
|
||||
y="479.06763"
|
||||
x="314.59326"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="479.06763"
|
||||
x="314.59326"
|
||||
id="tspan5238-6-0-7"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,36.24517,333.72159)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-9"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-7"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="599.82227"
|
||||
x="132.07027"
|
||||
id="tspan5276-5"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-3"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="622.32227"
|
||||
x="132.07027"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,418.47684,336.17178)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-8"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-8"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="602.27258"
|
||||
x="514.30194"
|
||||
id="tspan5276-3"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-1"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="624.77258"
|
||||
x="514.30194"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="346.08432"
|
||||
y="702.96533"
|
||||
id="text3311"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3313"
|
||||
x="346.08432"
|
||||
y="702.96533">drop</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
id="text3315"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3317"
|
||||
x="383.86325"
|
||||
y="639.50299"
|
||||
style="font-size:22px;fill:#ff0000">X:block</tspan></text>
|
||||
<rect
|
||||
y="714.75317"
|
||||
x="190.90842"
|
||||
height="73.974197"
|
||||
width="89.833496"
|
||||
id="rect5232-3-7"
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.56441098px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<rect
|
||||
y="715.62457"
|
||||
x="191.88971"
|
||||
height="24.947573"
|
||||
width="88.805061"
|
||||
id="rect5234-1-0"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.65335387px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-0-4"
|
||||
y="777.89038"
|
||||
x="187.02913"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="777.89038"
|
||||
x="187.02913"
|
||||
id="tspan5238-7-8"
|
||||
sodipodi:role="line">dst addr</tspan></text>
|
||||
<rect
|
||||
y="741.34027"
|
||||
x="191.4227"
|
||||
height="24.947573"
|
||||
width="88.805061"
|
||||
id="rect5234-2-4-0"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.65335387px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-4"
|
||||
y="805.17816"
|
||||
x="186.589"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="805.17816"
|
||||
x="186.589"
|
||||
id="tspan5238-6-0-2"
|
||||
sodipodi:role="line">src addr</tspan></text>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5280-1-9"
|
||||
y="832.46588"
|
||||
x="203.75392"
|
||||
style="font-size:15.80727291px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"
|
||||
transform="scale(1.0611323,0.94238956)"><tspan
|
||||
y="832.46588"
|
||||
x="203.75392"
|
||||
id="tspan5282-8-6"
|
||||
sodipodi:role="line">data</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="206.42273"
|
||||
y="703.9613"
|
||||
id="text3373"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3375"
|
||||
x="206.42273"
|
||||
y="703.9613">pass</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 272.57822,610.10054 -95.55792,-1.2251"
|
||||
id="path6078-6"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 464.91915,612.55074 -132.31096,-1.2251"
|
||||
id="path6078-9"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-0"
|
||||
d="m 270.11538,579.86992 0.1713,-126.73982"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8"
|
||||
d="m 270.11603,628.79147 -77.01907,-1.48458"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228-8-7"
|
||||
d="m 337.67593,631.84027 35.90109,1.00644"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:4.11323547;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="-536.76379"
|
||||
y="249.9476"
|
||||
id="text4337"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,-1,1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan4339"
|
||||
x="-536.76379"
|
||||
y="249.9476">forward</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="172.32462"
|
||||
y="658.73059"
|
||||
id="text4337-4"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan4339-5"
|
||||
x="172.32462"
|
||||
y="658.73059">forward</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 38 KiB |
BIN
doc/source/images/logical-view.png
Normal file
After Width: | Height: | Size: 63 KiB |
623
doc/source/images/logical-view.svg
Normal file
@ -0,0 +1,623 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="logical-view.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/logical-view.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
</defs>
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="1.1517355"
|
||||
inkscape:cx="527.91764"
|
||||
inkscape:cy="392.97266"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1375"
|
||||
inkscape:window-height="1083"
|
||||
inkscape:window-x="18"
|
||||
inkscape:window-y="2"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false" />
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title />
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<rect
|
||||
style="opacity:0.325;fill:#aade87;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.69828618px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5357-9"
|
||||
width="325.40015"
|
||||
height="193.2157"
|
||||
x="634.08337"
|
||||
y="652.44501" />
|
||||
<rect
|
||||
style="opacity:0.325;fill:#aade87;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.70321101px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5357"
|
||||
width="325.3952"
|
||||
height="195.95367"
|
||||
x="24.654757"
|
||||
y="649.00568" />
|
||||
<rect
|
||||
style="fill:#5555ff;fill-rule:evenodd;stroke:#000000;stroke-width:0.33128864px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect3772"
|
||||
width="111.84713"
|
||||
height="36.141087"
|
||||
x="334.73782"
|
||||
y="438.67487" />
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,8.893779,516.39652)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="60.610229"
|
||||
y="772.59448"
|
||||
id="text5274"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276"
|
||||
x="60.610229"
|
||||
y="772.59448"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-9"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,224.04537,515.72527)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="274.87598"
|
||||
y="774.58069"
|
||||
id="text5274-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-3"
|
||||
x="274.87598"
|
||||
y="774.58069"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-3"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,93.490245,515.06779)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1.0;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="144.32086"
|
||||
y="773.92322"
|
||||
id="text5274-9"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-1"
|
||||
x="144.32086"
|
||||
y="773.92322"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1.0;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="215.02756"
|
||||
y="766.42914"
|
||||
id="text5329"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="215.02756"
|
||||
y="766.42914"
|
||||
id="tspan5333">...</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 168.30708,671.18896 0,66.437"
|
||||
id="path5353"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 78.83869,737.62585 0,-38.97615 227.75678,0 0,38.97615"
|
||||
id="path5355"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="34.547245"
|
||||
y="835.06689"
|
||||
id="text5359"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5361"
|
||||
x="34.547245"
|
||||
y="835.06689">Tenant-X</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-31"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,618.32488,517.09536)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="670.04132"
|
||||
y="773.29333"
|
||||
id="text5274-96"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-7"
|
||||
x="670.04132"
|
||||
y="773.29333"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-9-5"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,833.47647,516.42411)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="884.30707"
|
||||
y="775.27954"
|
||||
id="text5274-8-2"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-3-9"
|
||||
x="884.30707"
|
||||
y="775.27954"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-3-1"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.54468914,0,0,0.43300157,702.92135,515.76663)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="753.75195"
|
||||
y="774.62207"
|
||||
id="text5274-9-2"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-1-4"
|
||||
x="753.75195"
|
||||
y="774.62207"
|
||||
style="font-size:32px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;writing-mode:lr-tb;text-anchor:start;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="824.45868"
|
||||
y="767.12799"
|
||||
id="text5329-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="824.45868"
|
||||
y="767.12799"
|
||||
id="tspan5333-7">...</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 777.73818,671.8878 0,66.437"
|
||||
id="path5353-5"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 688.26979,738.32469 0,-38.97615 227.75678,0 0,38.97615"
|
||||
id="path5355-0"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="643.97833"
|
||||
y="835.76575"
|
||||
id="text5359-5"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5361-5"
|
||||
x="643.97833"
|
||||
y="835.76575">Tenant-Y</tspan></text>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5479"
|
||||
y="728.68225"
|
||||
x="471.24713"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="728.68225"
|
||||
x="471.24713"
|
||||
id="tspan5481"
|
||||
sodipodi:role="line">...</tspan></text>
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5485"
|
||||
d="m 164.66453,628.43991 0,-75.7058 612.28244,0 0,78.3467"
|
||||
style="fill:none;stroke:#000000;stroke-width:3.49188328;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 389.76378,472.76376 0,77.95276 2.65748,0"
|
||||
id="path5512"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="339.0433"
|
||||
y="463.04724"
|
||||
id="text5514"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5516"
|
||||
x="339.0433"
|
||||
y="463.04724">gateway</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 388.87795,387.72439 0,49.6063 0,0"
|
||||
id="path5518"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="opacity:0.325;fill:#5555ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5543"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="349.90158"
|
||||
sodipodi:cy="64.665352"
|
||||
sodipodi:r1="34.501789"
|
||||
sodipodi:r2="28.966175"
|
||||
sodipodi:arg1="-1.0612041"
|
||||
sodipodi:arg2="-0.62241192"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 366.73229,34.547239 17.6677,29.634878 -16.83071,30.118112 -34.49841,0.483235 -17.66769,-29.634877 16.8307,-30.118112 z"
|
||||
transform="translate(39.862204,292.0551)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="303.83856"
|
||||
y="355.83463"
|
||||
id="text5545"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5547"
|
||||
x="303.83856"
|
||||
y="355.83463">public internet</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="22.857574"
|
||||
y="1011.2186"
|
||||
id="text5549"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5551"
|
||||
x="22.857574"
|
||||
y="1011.2186">Logical network view</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:8.48272705;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0;marker-start:url(#Arrow1Mstart);marker-end:url(#Arrow1Mend)"
|
||||
d="m 361.69128,800.92899 254.92112,0"
|
||||
id="path8990"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="380.34985"
|
||||
y="560.3197"
|
||||
id="text9936"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="translate(0,308.2677)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan9938"
|
||||
x="380.34985"
|
||||
y="560.3197">L2-level</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="380.34985"
|
||||
y="610.3197"
|
||||
id="tspan9940">segregation</tspan></text>
|
||||
<a
|
||||
style="fill:#ff2ad4;fill-opacity:1"
|
||||
transform="matrix(1.7591674,0,0,1.2473597,-134.20474,-124.3429)"
|
||||
id="a4003">
|
||||
<rect
|
||||
style="fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.48250109px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect2985"
|
||||
width="124.30867"
|
||||
height="49.962151"
|
||||
x="140.79437"
|
||||
y="588.12579" />
|
||||
</a>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text4006"
|
||||
y="656.40906"
|
||||
x="132.9359"
|
||||
style="font-size:20px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="656.40906"
|
||||
x="132.9359"
|
||||
id="tspan4008"
|
||||
sodipodi:role="line">gateway</tspan></text>
|
||||
<rect
|
||||
style="fill:#ffcc00;fill-rule:evenodd;stroke:#000000;stroke-width:0.72736639px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect3065"
|
||||
width="89.108681"
|
||||
height="17.268652"
|
||||
x="231.68684"
|
||||
y="641.18787" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:14px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#ffcc00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="233.42279"
|
||||
y="654.40955"
|
||||
id="text3067"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
style="fill:#000000;fill-opacity:1"
|
||||
sodipodi:role="line"
|
||||
x="233.42279"
|
||||
y="654.40955"
|
||||
id="tspan3071">dhcp server</tspan></text>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text3070"
|
||||
y="665.98871"
|
||||
x="296.07492"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="665.98871"
|
||||
x="296.07492"
|
||||
id="tspan3072"
|
||||
sodipodi:role="line" /></text>
|
||||
<a
|
||||
style="fill:#ff2ad4;fill-opacity:1"
|
||||
transform="matrix(1.7591674,0,0,1.1959526,459.74622,-92.580367)"
|
||||
id="a4003-7">
|
||||
<rect
|
||||
style="fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.48250109px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect2985-4"
|
||||
width="124.30867"
|
||||
height="49.962151"
|
||||
x="140.79437"
|
||||
y="588.12579" />
|
||||
</a>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text4006-1"
|
||||
y="655.35114"
|
||||
x="726.88684"
|
||||
style="font-size:20px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:start;line-height:125%;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="655.35114"
|
||||
x="726.88684"
|
||||
id="tspan4008-1"
|
||||
sodipodi:role="line">gateway</tspan></text>
|
||||
<rect
|
||||
style="fill:#ffcc00;fill-rule:evenodd;stroke:#000000;stroke-width:0.72736639px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect3065-4"
|
||||
width="89.108681"
|
||||
height="17.268652"
|
||||
x="824.59692"
|
||||
y="642.11475" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:14px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#ffcc00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="826.33289"
|
||||
y="655.33643"
|
||||
id="text3067-1"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
style="fill:#000000;fill-opacity:1"
|
||||
sodipodi:role="line"
|
||||
x="826.33289"
|
||||
y="655.33643"
|
||||
id="tspan3071-7">dhcp server</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="143.30341"
|
||||
y="633.5274"
|
||||
id="text5487"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5489"
|
||||
x="143.30341"
|
||||
y="633.5274">NAT</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="754.6554"
|
||||
y="635.15948"
|
||||
id="text5487-3"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5489-6"
|
||||
x="754.6554"
|
||||
y="635.15948">NAT</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 27 KiB |
BIN
doc/source/images/mac-learning.png
Normal file
After Width: | Height: | Size: 94 KiB |
764
doc/source/images/mac-learning.svg
Normal file
@ -0,0 +1,764 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="mac-learning.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/mac-learning.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="374.1874"
|
||||
inkscape:cy="324.99839"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="54"
|
||||
inkscape:window-y="32"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<marker
|
||||
style="overflow:visible;"
|
||||
id="Arrow1Send"
|
||||
refX="0.0"
|
||||
refY="0.0"
|
||||
orient="auto"
|
||||
inkscape:stockid="Arrow1Send">
|
||||
<path
|
||||
transform="scale(0.2) rotate(180) translate(6,0)"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
id="path4154" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4166"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5113"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) translate(1,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lenda"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lenda"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5800"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#05ff00;stroke-width:1.0pt;fill:#05ff00;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lendan"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lendan"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5943"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;marker-start:none;stroke:#059500;stroke-width:1.0pt;fill:#059500"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient6508"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(1.963808,0,0,2.0387048,132.33185,-1087.5143)"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow2MendC"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2MendC"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4651"
|
||||
style="stroke-linejoin:round;font-size:12.0;fill-rule:evenodd;stroke:#05ff00;stroke-width:0.62500000;fill:#05ff00"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(0.6) rotate(180) translate(0,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend4"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend4"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path6229"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#0000ff;stroke-width:1.0pt;fill:#0000ff;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title />
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 123.73525,606.64067 0,-137.21137"
|
||||
id="path6078"
|
||||
inkscape:connector-curvature="0" />
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6508);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:2.23578811;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="417.50256"
|
||||
height="287.14444"
|
||||
x="-912.29431"
|
||||
y="38.488934"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(423.13207,13.647835)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="80.828072"
|
||||
y="594.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="615.96716"
|
||||
x="86.097534"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
y="573.9325"
|
||||
x="74.458321"
|
||||
height="295.24646"
|
||||
width="233.97559"
|
||||
id="rect5351-5"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:3.5089395px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353-2"
|
||||
y="854.9986"
|
||||
x="83.609177"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="854.9986"
|
||||
x="83.609177"
|
||||
id="tspan5355-6"
|
||||
sodipodi:role="line">nova-compute</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,33.246065,517.64778)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274"
|
||||
y="783.74854"
|
||||
x="129.07115"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="783.74854"
|
||||
x="129.07115"
|
||||
id="tspan5276"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="806.24854"
|
||||
x="129.07115"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,-136.00519,452.12072)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="630.38098"
|
||||
x="106.25084"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="630.38098"
|
||||
x="106.25084"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
<path
|
||||
sodipodi:nodetypes="cc"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path6228"
|
||||
d="m 125.69434,759.67428 0.17857,-108.00709"
|
||||
style="fill:none;stroke:#05ff00;stroke-width:8.14929199;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2MendC)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="58.133625"
|
||||
y="897.9939"
|
||||
id="text3193"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3195"
|
||||
x="58.133625"
|
||||
y="897.9939">physical host</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="33.077721"
|
||||
y="977.57361"
|
||||
id="text6045"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="33.077721"
|
||||
y="977.57361"
|
||||
id="tspan6049">associates mac address</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="33.077721"
|
||||
y="1027.5736"
|
||||
id="tspan3090">to network id of OVS port</tspan></text>
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(-137.65551,-208.28264)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#05ff00;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="459.41306"
|
||||
y="697.02533"
|
||||
id="text6080"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6082"
|
||||
x="459.41306"
|
||||
y="697.02533" /></text>
|
||||
<flowRoot
|
||||
xml:space="preserve"
|
||||
id="flowRoot6500"
|
||||
style="fill:black;stroke:none;stroke-opacity:1;stroke-width:1px;stroke-linejoin:miter;stroke-linecap:butt;fill-opacity:1;font-family:Bitstream Vera Sans;font-style:normal;font-weight:normal;font-size:40px;line-height:125%;letter-spacing:0px;word-spacing:0px"><flowRegion
|
||||
id="flowRegion6502"><rect
|
||||
id="rect6504"
|
||||
width="978.85608"
|
||||
height="519.44305"
|
||||
x="-91.882614"
|
||||
y="261.40448" /></flowRegion><flowPara
|
||||
id="flowPara6506" /></flowRoot> <text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text4810"
|
||||
y="754.66254"
|
||||
x="144.56197"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="754.66254"
|
||||
x="144.56197"
|
||||
id="tspan4812"
|
||||
sodipodi:role="line">send packet</tspan></text>
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path4814"
|
||||
d="m 153.13769,623.1046 335.67781,0"
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-end:url(#Arrow2Lend)" />
|
||||
<g
|
||||
id="g5284-2"
|
||||
transform="matrix(0.7624367,0,0,0.67711861,-318.80448,357.75715)">
|
||||
<rect
|
||||
style="fill:#f2f2f2;stroke:#000000;stroke-width:0.78552711px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5232-3"
|
||||
width="117.8242"
|
||||
height="109.24851"
|
||||
x="628.36981"
|
||||
y="431.12851" />
|
||||
<rect
|
||||
style="fill:#b3b3b3;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-1"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.65686"
|
||||
y="432.41547" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="638.27789"
|
||||
y="458.18796"
|
||||
id="text5236-0"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-7"
|
||||
x="638.27789"
|
||||
y="458.18796">dst addr</tspan></text>
|
||||
<rect
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.90931469px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5234-2-4"
|
||||
width="116.47533"
|
||||
height="36.843727"
|
||||
x="629.04431"
|
||||
y="470.39359" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="637.66534"
|
||||
y="496.16611"
|
||||
id="text5236-9-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5238-6-0"
|
||||
x="637.66534"
|
||||
y="496.16611">src addr</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="661.55481"
|
||||
y="534.14423"
|
||||
id="text5280-1"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5282-8"
|
||||
x="661.55481"
|
||||
y="534.14423">data</tspan></text>
|
||||
</g>
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5340"
|
||||
y="589.2738"
|
||||
x="145.78708"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="589.2738"
|
||||
x="145.78708"
|
||||
id="tspan5342"
|
||||
sodipodi:role="line">packet in event</tspan></text>
|
||||
<rect
|
||||
y="664.97241"
|
||||
x="507.73914"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031623px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366"
|
||||
y="697.13458"
|
||||
x="515.07465"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="697.13458"
|
||||
x="515.07465"
|
||||
id="tspan5368"
|
||||
sodipodi:role="line">tenant-X</tspan></text>
|
||||
<rect
|
||||
y="720.99866"
|
||||
x="511.80664"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940903px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1"
|
||||
y="782.27899"
|
||||
x="487.34879"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="782.27899"
|
||||
x="487.34879"
|
||||
id="tspan5238-6-0-7"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<rect
|
||||
y="664.02014"
|
||||
x="720.37482"
|
||||
height="41.623135"
|
||||
width="183.73491"
|
||||
id="rect5364-7"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.03031622999999994px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5366-8"
|
||||
y="696.18231"
|
||||
x="727.71033"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="696.18231"
|
||||
x="727.71033"
|
||||
id="tspan5368-6"
|
||||
sodipodi:role="line">tenant-Y</tspan></text>
|
||||
<rect
|
||||
y="723.8252"
|
||||
x="724.97424"
|
||||
height="24.921518"
|
||||
width="96.129616"
|
||||
id="rect5234-2-4-7-9"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.67940902999999997px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
transform="scale(1.0611323,0.94238956)"
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5236-9-8-1-8"
|
||||
y="785.27838"
|
||||
x="688.23566"
|
||||
style="font-size:17.24429703px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="785.27838"
|
||||
x="688.23566"
|
||||
id="tspan5238-6-0-7-5"
|
||||
sodipodi:role="line">mac addr</tspan></text>
|
||||
<path
|
||||
transform="translate(0,308.2677)"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5536"
|
||||
d="M 245.0203,381.46444 C 396.93288,431.6936 504.74182,428.0183 504.74182,428.0183"
|
||||
style="stroke-linejoin:miter;marker-end:url(#Arrow1Lend4);stroke-opacity:1;marker-start:none;stroke-dashoffset:0;stroke:#0000ff;stroke-linecap:butt;stroke-miterlimit:4;stroke-dasharray:15, 5;stroke-width:5;fill:none" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6170"
|
||||
y="791.41553"
|
||||
x="344.25351"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#0000ff;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="791.41553"
|
||||
x="344.25351"
|
||||
id="tspan6172"
|
||||
sodipodi:role="line">associate</tspan><tspan
|
||||
id="tspan6174"
|
||||
y="841.41553"
|
||||
x="344.25351"
|
||||
sodipodi:role="line">mac address to</tspan><tspan
|
||||
id="tspan6176"
|
||||
y="891.41553"
|
||||
x="344.25351"
|
||||
sodipodi:role="line">network id</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 29 KiB |
BIN
doc/source/images/minimul-setup.png
Normal file
After Width: | Height: | Size: 120 KiB |
903
doc/source/images/minimul-setup.svg
Normal file
@ -0,0 +1,903 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="minimul-setup.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/minimul-setup.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.81601008"
|
||||
inkscape:cx="326.8338"
|
||||
inkscape:cy="349.33466"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1314"
|
||||
inkscape:window-height="980"
|
||||
inkscape:window-x="30"
|
||||
inkscape:window-y="141"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(2.2778076,0,0,6.0730972,231.64447,-3322.8016)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Mend6-0"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5404-3"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill:#ff0000;fill-rule:evenodd;stroke:#ff0000;stroke-width:1pt;marker-start:none"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1MendN-9"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5645-1"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill:#ff0000;fill-rule:evenodd;stroke:#ff0000;stroke-width:1pt;marker-start:none"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343"
|
||||
id="linearGradient5349"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-190.51819,-497.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347" />
|
||||
</linearGradient>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title />
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<rect
|
||||
style="opacity:0.5;fill:url(#linearGradient6079);fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:4.15592432;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect3065-4"
|
||||
width="484.2583"
|
||||
height="855.37451"
|
||||
x="-980.01013"
|
||||
y="31.449005"
|
||||
transform="matrix(0,-1,1,0,0,0)" />
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 543.11341,673.45817 -320.85591,-1.38039 1.07056,39.84316"
|
||||
id="path6473"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccc" />
|
||||
<rect
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:2.71000719px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5351-5"
|
||||
width="336.37537"
|
||||
height="122.49554"
|
||||
x="417.9646"
|
||||
y="700.86536" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="458.61511"
|
||||
y="812.50928"
|
||||
id="text5353-2"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5355-6"
|
||||
x="458.61511"
|
||||
y="812.50928">nova-compute</tspan></text>
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5485"
|
||||
d="m 575.81554,518.47262 -0.0744,-131.08463"
|
||||
style="fill:none;stroke:#000000;stroke-width:5.05247164;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="32.64756"
|
||||
y="1027.5137"
|
||||
id="text5549"
|
||||
sodipodi:linespacing="125%"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/compute-node.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5551"
|
||||
x="32.64756"
|
||||
y="1027.5137">All-in-One setup</tspan></text>
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<g
|
||||
id="g6280"
|
||||
transform="translate(312.16089,-235.21169)">
|
||||
<g
|
||||
transform="matrix(1,0,0,0.71409652,-474.38063,289.09459)"
|
||||
id="g5864-4">
|
||||
<rect
|
||||
style="fill:#00ffff;fill-rule:evenodd;stroke:#000000;stroke-width:0.79479539px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5858-6"
|
||||
width="26.969246"
|
||||
height="59.086094"
|
||||
x="722.52655"
|
||||
y="601.5531" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="611.76575"
|
||||
y="-729.16479"
|
||||
id="text5860-69"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,1,-1,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5862-8"
|
||||
x="611.76575"
|
||||
y="-729.16479">eth</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
<g
|
||||
transform="translate(65.5766,51.261127)"
|
||||
id="g6174-1">
|
||||
<path
|
||||
transform="matrix(1.0086434,0,0,0.68923037,243.74678,449.4383)"
|
||||
d="m 289.53315,248.36246 -14.42324,24.98178 -28.84647,0 -14.42324,-24.98178 14.42324,-24.98178 28.84647,0 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="0.52359878"
|
||||
sodipodi:arg1="0"
|
||||
sodipodi:r2="24.981781"
|
||||
sodipodi:r1="28.846476"
|
||||
sodipodi:cy="248.36246"
|
||||
sodipodi:cx="260.68668"
|
||||
sodipodi:sides="6"
|
||||
id="path5523-9"
|
||||
style="opacity:0.5;fill:#2ad4ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5525-6"
|
||||
y="627.69855"
|
||||
x="486.00281"
|
||||
style="font-size:20px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="627.69855"
|
||||
x="486.00281"
|
||||
id="tspan5527-5"
|
||||
sodipodi:role="line">OVS</tspan></text>
|
||||
</g>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 467.62072,731.43747 83.47892,-52.45752"
|
||||
id="path6228"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="M 692.60743,728.07086 596.83779,684.0091"
|
||||
id="path6232"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
sodipodi:type="arc"
|
||||
style="opacity:0.4125;fill:#3866a9;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path6269"
|
||||
sodipodi:cx="185.74246"
|
||||
sodipodi:cy="191.14935"
|
||||
sodipodi:rx="84.039093"
|
||||
sodipodi:ry="31.581572"
|
||||
d="m 269.78156,191.14935 c 0,17.44202 -37.62559,31.58157 -84.0391,31.58157 -46.41351,0 -84.03909,-14.13955 -84.03909,-31.58157 0,-17.44202 37.62558,-31.58157 84.03909,-31.58157 46.41351,0 84.0391,14.13955 84.0391,31.58157 z"
|
||||
transform="matrix(1.1689088,0,0,0.56811324,10.97702,488.03964)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:#000000;stroke-opacity:1;font-family:Bitstream Vera Sans"
|
||||
x="137.63055"
|
||||
y="600.23999"
|
||||
id="text6271"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan6273"
|
||||
x="137.63055"
|
||||
y="600.23999">quantum_ovs_agent</tspan></text>
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(-60,2)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#193edc;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="289.90646"
|
||||
y="697.4389"
|
||||
id="text7945-1-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan7947-2-1"
|
||||
x="289.90646"
|
||||
y="697.4389"
|
||||
style="fill:#31562b;fill-opacity:1;stroke:none">openflow</tspan></text>
|
||||
<rect
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.7666558px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5351-8"
|
||||
width="112.94334"
|
||||
height="29.197376"
|
||||
x="505.20587"
|
||||
y="843.80408" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="506.81201"
|
||||
y="865.17035"
|
||||
id="text5353-29"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5355-2"
|
||||
x="506.81201"
|
||||
y="865.17035">nova-api</tspan></text>
|
||||
<rect
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.99003595px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5351-8-4"
|
||||
width="189.8004"
|
||||
height="28.973995"
|
||||
x="485.51215"
|
||||
y="894.55353" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="487.00659"
|
||||
y="915.80811"
|
||||
id="text5353-29-6"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5355-2-3"
|
||||
x="487.00659"
|
||||
y="915.80811">nova-scheduler</tspan></text>
|
||||
<g
|
||||
id="g6388"
|
||||
transform="translate(37.098036,274.46221)">
|
||||
<rect
|
||||
style="fill:#4975b6;fill-opacity:0.23137255;fill-rule:evenodd;stroke:#000000;stroke-width:0.84044451px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect6358"
|
||||
width="187.50786"
|
||||
height="29.064722"
|
||||
x="85.200211"
|
||||
y="530.91882" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360"
|
||||
y="552.26874"
|
||||
x="90.55011"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="552.26874"
|
||||
x="90.55011"
|
||||
id="tspan6362"
|
||||
sodipodi:role="line">quantum-server</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.89793426px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5351-8-4-8"
|
||||
width="155.63452"
|
||||
height="29.066097"
|
||||
x="493.65576"
|
||||
y="940.33221" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="497.19629"
|
||||
y="961.63287"
|
||||
id="text5353-29-6-8"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5355-2-3-5"
|
||||
x="497.19629"
|
||||
y="961.63287">nova-...</tspan></text>
|
||||
<g
|
||||
id="g6234"
|
||||
transform="translate(65.43986,27.776)">
|
||||
<rect
|
||||
y="515.01691"
|
||||
x="415.87427"
|
||||
height="80.739517"
|
||||
width="196.60234"
|
||||
id="rect5351"
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:1.68203735px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5353"
|
||||
y="541.27826"
|
||||
x="435.22226"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="541.27826"
|
||||
x="435.22226"
|
||||
id="tspan5355"
|
||||
sodipodi:role="line">nova-network</tspan></text>
|
||||
</g>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="692.86469"
|
||||
y="559.70044"
|
||||
id="text5487-3"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5489-6"
|
||||
x="692.86469"
|
||||
y="559.70044"
|
||||
style="fill:#ff0000">SNAT</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#ff0000;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2, 2;stroke-dashoffset:0;marker-start:none;marker-end:url(#Arrow1MendN)"
|
||||
d="m 498.15874,603.65235 c -53.4194,-45.94069 -7.50046,-82.28109 -7.50046,-82.28109 l 57.69296,-4.27355"
|
||||
id="path6239"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccc" />
|
||||
<path
|
||||
style="fill:none;stroke:#ff0000;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2, 2;stroke-dashoffset:0;marker-start:none;marker-end:url(#Arrow1Mend6)"
|
||||
d="m 650.54421,602.47083 c 53.4194,-45.94069 10.71214,-81.21053 10.71214,-81.21053 l -57.69296,-4.27355"
|
||||
id="path6239-4"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="ccc" />
|
||||
<rect
|
||||
style="opacity:0.41249999999999998;fill:#05ff00;fill-rule:evenodd;stroke:#000000;stroke-width:0.71524047999999996px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;fill-opacity:1"
|
||||
id="rect5947"
|
||||
width="62.431255"
|
||||
height="24.849373"
|
||||
x="584.12842"
|
||||
y="-524.00653"
|
||||
transform="matrix(0,1,-1,0,0,0)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:16.64327431px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="636.57861"
|
||||
y="-468.99884"
|
||||
id="text5949"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,0.92462636,-1.0815179,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5951"
|
||||
x="636.57861"
|
||||
y="-468.99884">gw-xxx</tspan></text>
|
||||
<rect
|
||||
style="opacity:0.41249999999999998;fill:#00fffc;fill-rule:evenodd;stroke:#000000;stroke-width:0.70914637999999997px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;fill-opacity:1"
|
||||
id="rect5947-4"
|
||||
width="61.371914"
|
||||
height="24.849373"
|
||||
x="581.86981"
|
||||
y="-651.82678"
|
||||
transform="matrix(0,1,-1,0,0,0)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:16.50146866px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="639.50269"
|
||||
y="-582.18176"
|
||||
id="text5949-7"
|
||||
sodipodi:linespacing="125%"
|
||||
transform="matrix(0,0.91674822,-1.0908121,0,0,0)"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5951-3"
|
||||
x="639.50269"
|
||||
y="-582.18176">gw-yyy</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="M 576.43361,730.03267 574.12928,689.8299"
|
||||
id="path6228-0"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 596.04122,664.31823 41.81277,-21.30086"
|
||||
id="path6228-3"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="M 549.47316,662.38705 514.081,646.69379"
|
||||
id="path6228-06"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<path
|
||||
style="fill:none;stroke:#6b7393;stroke-width:5.03195906;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 416.33269,761.13247 -45.30653,0.15491 -0.64494,57.28036 -61.39088,0.0557"
|
||||
id="path7949"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cccc"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90" />
|
||||
<rect
|
||||
style="fill:#5555ff;fill-rule:evenodd;stroke:#000000;stroke-width:0.33128864px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect3772"
|
||||
width="111.84713"
|
||||
height="36.141087"
|
||||
x="514.22339"
|
||||
y="412.79633" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="518.52893"
|
||||
y="437.1687"
|
||||
id="text5514"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5516"
|
||||
x="518.52893"
|
||||
y="437.1687">gateway</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="opacity:0.325;fill:#5555ff;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:3;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5543"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="349.90158"
|
||||
sodipodi:cy="64.665352"
|
||||
sodipodi:r1="34.501789"
|
||||
sodipodi:r2="28.966175"
|
||||
sodipodi:arg1="-1.0612041"
|
||||
sodipodi:arg2="-0.62241192"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 366.73229,34.547239 17.6677,29.634878 -16.83071,30.118112 -34.49841,0.483235 -17.66769,-29.634877 16.8307,-30.118112 z"
|
||||
transform="translate(223.34776,292.17655)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="487.32413"
|
||||
y="355.95609"
|
||||
id="text5545"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5547"
|
||||
x="487.32413"
|
||||
y="355.95609">public internet</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="53.920906"
|
||||
y="948.19678"
|
||||
id="text3555"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3557"
|
||||
x="53.920906"
|
||||
y="948.19678">physical host</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-6"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.69506452,0,0,0.47991755,376.19731,483.38087)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="472.0224"
|
||||
y="749.48163"
|
||||
id="text5274-3"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-4"
|
||||
x="472.0224"
|
||||
y="749.48163"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="472.0224"
|
||||
y="771.98163"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
id="tspan3167-1">tenant-X</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="608.73407"
|
||||
y="757.31628"
|
||||
id="text5329-7"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
x="608.73407"
|
||||
y="757.31628"
|
||||
id="tspan5333-1">...</tspan></text>
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#00fffc;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250-8-1"
|
||||
sodipodi:sides="6"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:arg2="1.5626709"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
transform="matrix(0.69506452,0,0,0.47991755,480.10215,484.48042)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="575.92719"
|
||||
y="750.58118"
|
||||
id="text5274-5-6"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276-33-7"
|
||||
x="575.92719"
|
||||
y="750.58118"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans">VM</tspan><tspan
|
||||
sodipodi:role="line"
|
||||
x="575.92719"
|
||||
y="773.08118"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
id="tspan3167-8-8">tenant-Y</tspan></text>
|
||||
<path
|
||||
transform="matrix(0.69506452,0,0,0.47991755,604.3304,483.77373)"
|
||||
d="m 171.85039,632.4803 -69.88264,0.56783 -35.433072,-60.23622 34.449562,-60.80405 69.88263,-0.56783 35.43308,60.23622 z"
|
||||
inkscape:randomized="0"
|
||||
inkscape:rounded="0"
|
||||
inkscape:flatsided="true"
|
||||
sodipodi:arg2="1.5626709"
|
||||
sodipodi:arg1="1.0390722"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:r1="69.884941"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:sides="6"
|
||||
id="path5250-7-8"
|
||||
style="fill:#ccff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
sodipodi:type="star" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text5274-7-2"
|
||||
y="749.87451"
|
||||
x="700.15552"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="749.87451"
|
||||
x="700.15552"
|
||||
id="tspan5276-1-1"
|
||||
sodipodi:role="line">VM</tspan><tspan
|
||||
id="tspan3167-2-3"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
y="772.37451"
|
||||
x="700.15552"
|
||||
sodipodi:role="line">tenant-...</tspan></text>
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 172.06998,743.00719 -1.00693,59.89335"
|
||||
id="path6473-7-9"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<g
|
||||
id="g6423-3"
|
||||
transform="translate(-3.945028,138.1109)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="86.955444"
|
||||
y="577.54102" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="598.81049"
|
||||
x="92.224907"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="598.81049"
|
||||
x="92.224907"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<path
|
||||
style="fill:#000000;fill-opacity:0;stroke:#1afc00;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
d="m 172.06997,610.65589 -1.00693,105.23593"
|
||||
id="path6473-7-9-2"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cc" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="401.80255"
|
||||
y="550.07538"
|
||||
id="text5487-3-7"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5489-6-7"
|
||||
x="401.80255"
|
||||
y="550.07538"
|
||||
style="fill:#ff0000">SNAT</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 37 KiB |
BIN
doc/source/images/network-creation.png
Normal file
After Width: | Height: | Size: 43 KiB |
484
doc/source/images/network-creation.svg
Normal file
@ -0,0 +1,484 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:osb="http://www.openswatchbook.org/uri/2009/osb"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="1052.3622"
|
||||
height="744.09448"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="0.48.1 r9760"
|
||||
sodipodi:docname="network-creation.svg"
|
||||
inkscape:export-filename="/home/yamahata/openvswitch/sp-lab/scarab/scarab-2/doc/source/images/network-creation.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90">
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.8162589"
|
||||
inkscape:cx="319.62556"
|
||||
inkscape:cy="372.04724"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1345"
|
||||
inkscape:window-height="1004"
|
||||
inkscape:window-x="52"
|
||||
inkscape:window-y="100"
|
||||
inkscape:window-maximized="0"
|
||||
inkscape:snap-grids="true"
|
||||
inkscape:snap-to-guides="false"
|
||||
inkscape:snap-bbox="false"
|
||||
inkscape:snap-page="false"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true" />
|
||||
<defs
|
||||
id="defs4">
|
||||
<linearGradient
|
||||
id="linearGradient6493"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#000000;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop6495" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
id="linearGradient5313"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#5555ff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5315" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5567"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5564"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.4) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow2Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow2Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5579"
|
||||
style="font-size:12.0;fill-rule:evenodd;stroke-width:0.62500000;stroke-linejoin:round;"
|
||||
d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
|
||||
transform="scale(1.1) rotate(180) translate(1,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lend"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lend"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5561"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none;"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Lstart"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Lstart"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
id="path5558"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1.0pt;marker-start:none"
|
||||
transform="scale(0.8) translate(12.5,0)" />
|
||||
</marker>
|
||||
<inkscape:path-effect
|
||||
effect="skeletal"
|
||||
id="path-effect5339"
|
||||
is_visible="true"
|
||||
pattern="M 0,0 0,10 10,5 z"
|
||||
copytype="single_stretched"
|
||||
prop_scale="1"
|
||||
scale_y_rel="false"
|
||||
spacing="0"
|
||||
normal_offset="0"
|
||||
tang_offset="0"
|
||||
prop_units="false"
|
||||
vertical_pattern="false"
|
||||
fuse_tolerance="0" />
|
||||
<linearGradient
|
||||
id="linearGradient5242"
|
||||
osb:paint="solid">
|
||||
<stop
|
||||
style="stop-color:#7fff2a;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5244" />
|
||||
</linearGradient>
|
||||
<inkscape:perspective
|
||||
sodipodi:type="inkscape:persp3d"
|
||||
inkscape:vp_x="0 : 372.04724 : 1"
|
||||
inkscape:vp_y="0 : 1000 : 0"
|
||||
inkscape:vp_z="1052.3622 : 372.04724 : 1"
|
||||
inkscape:persp3d-origin="526.18109 : 248.03149 : 1"
|
||||
id="perspective3009" />
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendM"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendM"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4159"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1LendF"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1LendF"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path4585"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.8) rotate(180) translate(12.5,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend6"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1Mend6"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5404"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1MendN"
|
||||
orient="auto"
|
||||
refY="0.0"
|
||||
refX="0.0"
|
||||
id="Arrow1MendN"
|
||||
style="overflow:visible;">
|
||||
<path
|
||||
id="path5645"
|
||||
d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
|
||||
style="marker-start:none;stroke:#ff0000;stroke-width:1.0pt;fill:#ff0000;fill-rule:evenodd"
|
||||
transform="scale(0.4) rotate(180) translate(10,0)" />
|
||||
</marker>
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
xlink:href="#linearGradient5343-7"
|
||||
id="linearGradient5349-6"
|
||||
x1="-532.43896"
|
||||
y1="622.73621"
|
||||
x2="-318.84055"
|
||||
y2="622.73621"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
gradientTransform="matrix(0.83990127,0,0,1.846462,-201.58875,-629.6685)" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4" />
|
||||
</linearGradient>
|
||||
<linearGradient
|
||||
y2="622.73621"
|
||||
x2="-318.84055"
|
||||
y1="622.73621"
|
||||
x1="-532.43896"
|
||||
gradientTransform="matrix(1.2042654,0,0,2.6602952,-344.10309,-1384.9447)"
|
||||
gradientUnits="userSpaceOnUse"
|
||||
id="linearGradient6079-9"
|
||||
xlink:href="#linearGradient5343-7-4"
|
||||
inkscape:collect="always" />
|
||||
<linearGradient
|
||||
inkscape:collect="always"
|
||||
id="linearGradient5343-7-4">
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:1;"
|
||||
offset="0"
|
||||
id="stop5345-4-1" />
|
||||
<stop
|
||||
style="stop-color:#aaccff;stop-opacity:0;"
|
||||
offset="1"
|
||||
id="stop5347-4-6" />
|
||||
</linearGradient>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Mend-0"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5567-3"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;marker-start:none"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)" />
|
||||
</marker>
|
||||
<marker
|
||||
inkscape:stockid="Arrow1Mend"
|
||||
orient="auto"
|
||||
refY="0"
|
||||
refX="0"
|
||||
id="Arrow1Mend-3"
|
||||
style="overflow:visible">
|
||||
<path
|
||||
inkscape:connector-curvature="0"
|
||||
id="path5567-6"
|
||||
d="M 0,0 5,-5 -12.5,0 5,5 0,0 z"
|
||||
style="fill-rule:evenodd;stroke:#000000;stroke-width:1pt;marker-start:none"
|
||||
transform="matrix(-0.4,0,0,-0.4,-4,0)" />
|
||||
</marker>
|
||||
</defs>
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(0,-308.2677)">
|
||||
<a
|
||||
id="a4003"
|
||||
transform="matrix(1,0,0,0.81896683,-0.728701,296.31497)"
|
||||
style="fill:#ff2ad4;fill-opacity:1" />
|
||||
<path
|
||||
style="opacity:0.275;fill:#dd6de5;fill-opacity:0.46666667;fill-rule:nonzero;stroke:#ff0000;stroke-width:4.27355194;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:2.13677602, 2.13677602;stroke-dashoffset:0"
|
||||
d=""
|
||||
id="path4088"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<g
|
||||
id="g6388"
|
||||
transform="translate(6.78831,-4)">
|
||||
<rect
|
||||
style="fill:#4975b6;fill-opacity:0.23137255;fill-rule:evenodd;stroke:#000000;stroke-width:0.84044451px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect6358"
|
||||
width="187.50786"
|
||||
height="29.064722"
|
||||
x="85.200211"
|
||||
y="530.91882" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360"
|
||||
y="552.26874"
|
||||
x="90.55011"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="552.26874"
|
||||
x="90.55011"
|
||||
id="tspan6362"
|
||||
sodipodi:role="line">quantum-server</tspan></text>
|
||||
</g>
|
||||
<g
|
||||
id="g6423"
|
||||
transform="translate(-54,-12)"
|
||||
style="opacity:0.6125;fill:#3866a9;fill-opacity:0.46666667">
|
||||
<rect
|
||||
style="fill:#b1c76d;fill-opacity:0.46666667;fill-rule:evenodd;stroke:#ff1300;stroke-width:4;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
|
||||
id="rect6358-7"
|
||||
width="267.63913"
|
||||
height="28.903856"
|
||||
x="104.82807"
|
||||
y="644.69769" />
|
||||
<text
|
||||
sodipodi:linespacing="125%"
|
||||
id="text6360-0"
|
||||
y="664.05432"
|
||||
x="110.9668"
|
||||
style="font-size:22px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#3866a9;fill-opacity:0.46666667;stroke:none;font-family:Bitstream Vera Sans"
|
||||
xml:space="preserve"><tspan
|
||||
y="664.05432"
|
||||
x="110.9668"
|
||||
id="tspan6362-5"
|
||||
sodipodi:role="line"
|
||||
style="fill:#ff0000;fill-opacity:1;stroke:#000000;stroke-opacity:1">ryu-openflow-controller</tspan></text>
|
||||
</g>
|
||||
<g
|
||||
id="g5185"
|
||||
transform="translate(433.62298,-530.03116)">
|
||||
<path
|
||||
sodipodi:type="star"
|
||||
style="fill:#05ff00;fill-opacity:1;fill-rule:nonzero;stroke:#000000;stroke-width:2;stroke-linecap:butt;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
|
||||
id="path5250"
|
||||
sodipodi:sides="4"
|
||||
sodipodi:cx="136.41731"
|
||||
sodipodi:cy="572.24408"
|
||||
sodipodi:r1="71.642792"
|
||||
sodipodi:r2="23.694832"
|
||||
sodipodi:arg1="0.77972212"
|
||||
sodipodi:arg2="1.5651204"
|
||||
inkscape:flatsided="true"
|
||||
inkscape:rounded="0"
|
||||
inkscape:randomized="0"
|
||||
d="M 187.36314,622.61483 86.046567,623.18991 85.471483,521.87333 186.78806,521.29825 z"
|
||||
transform="matrix(1.1467071,0,0,0.47597907,23.850931,641.90155)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:18px;font-style:normal;font-weight:normal;text-align:center;line-height:125%;letter-spacing:0px;word-spacing:0px;text-anchor:middle;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="178.89684"
|
||||
y="899.05359"
|
||||
id="text5274"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5276"
|
||||
x="178.89684"
|
||||
y="899.05359"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans" /><tspan
|
||||
sodipodi:role="line"
|
||||
x="178.89684"
|
||||
y="921.55359"
|
||||
style="font-size:18px;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-align:center;line-height:125%;writing-mode:lr-tb;text-anchor:middle;font-family:Bitstream Vera Sans;-inkscape-font-specification:Bitstream Vera Sans"
|
||||
id="tspan3167">tenant-X</tspan></text>
|
||||
</g>
|
||||
<rect
|
||||
style="opacity:0.275;fill:#ff2ad4;fill-opacity:1;fill-rule:evenodd;stroke:#000000;stroke-width:0.93824238px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
|
||||
id="rect5351-8-5"
|
||||
width="170.15692"
|
||||
height="29.025789"
|
||||
x="98.554108"
|
||||
y="427.91269" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:24px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="100.07444"
|
||||
y="449.19312"
|
||||
id="text5353-29-7"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5355-2-4"
|
||||
x="100.07444"
|
||||
y="449.19312">nova-network</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="129.29095"
|
||||
y="352.08868"
|
||||
id="text3547"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan3549"
|
||||
x="129.29095"
|
||||
y="352.08868">User</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;stroke-miterlimit:4;stroke-dasharray:none;marker-start:none;marker-end:url(#Arrow1Mend)"
|
||||
d="m 175.98121,52.60308 0,62.16728"
|
||||
id="path3551"
|
||||
inkscape:connector-curvature="0"
|
||||
transform="translate(0,308.2677)" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="190.32751"
|
||||
y="397.21472"
|
||||
id="text5167"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5169"
|
||||
x="190.32751"
|
||||
y="397.21472">tenant creation</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-start:none;marker-end:url(#Arrow1Mend)"
|
||||
d="m 172.75392,457.01705 0,62.16728"
|
||||
id="path3551-0"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="184.589"
|
||||
y="501.46448"
|
||||
id="text5215"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5217"
|
||||
x="184.589"
|
||||
y="501.46448">network creation</tspan></text>
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="285.96948"
|
||||
y="556.84967"
|
||||
id="text5219"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5221"
|
||||
x="285.96948"
|
||||
y="556.84967">allocate network id</tspan></text>
|
||||
<path
|
||||
style="fill:none;stroke:#000000;stroke-width:5;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;marker-start:none;marker-end:url(#Arrow1Mend)"
|
||||
d="m 173.06401,556.31518 0,62.16728"
|
||||
id="path3551-0-2"
|
||||
inkscape:connector-curvature="0" />
|
||||
<text
|
||||
xml:space="preserve"
|
||||
style="font-size:40px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;font-family:Bitstream Vera Sans"
|
||||
x="196.01624"
|
||||
y="612.55072"
|
||||
id="text5247"
|
||||
sodipodi:linespacing="125%"><tspan
|
||||
sodipodi:role="line"
|
||||
id="tspan5249"
|
||||
x="196.01624"
|
||||
y="612.55072">tell network id</tspan></text>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 18 KiB |
1434
doc/source/images/network-id.svg
Normal file
After Width: | Height: | Size: 62 KiB |
BIN
doc/source/images/physical-view.png
Normal file
After Width: | Height: | Size: 183 KiB |
1434
doc/source/images/physical-view.svg
Normal file
After Width: | Height: | Size: 62 KiB |
BIN
doc/source/images/trace-route.png
Normal file
After Width: | Height: | Size: 129 KiB |
1000
doc/source/images/trace-route.svg
Normal file
After Width: | Height: | Size: 46 KiB |
26
doc/source/index.rst
Normal file
@ -0,0 +1,26 @@
|
||||
.. ryu documentation master file, created by
|
||||
sphinx-quickstart on Mon Dec 5 15:38:48 2011.
|
||||
You can adapt this file completely to your liking, but it should at least
|
||||
contain the root `toctree` directive.
|
||||
|
||||
**********************************
|
||||
Welcome to RYU the Network OS(NOS)
|
||||
**********************************
|
||||
|
||||
Contents:
|
||||
|
||||
.. toctree::
|
||||
:maxdepth: 2
|
||||
|
||||
overview.rst
|
||||
getting_started.rst
|
||||
using_with_openstack.rst
|
||||
how_l2_segregation_works.rst
|
||||
|
||||
Indices and tables
|
||||
==================
|
||||
|
||||
* :ref:`genindex`
|
||||
* :ref:`modindex`
|
||||
* :ref:`search`
|
||||
|
1
doc/source/overview.rst
Normal file
@ -0,0 +1 @@
|
||||
.. include:: ../../README.rst
|
251
doc/source/using_with_openstack.rst
Normal file
@ -0,0 +1,251 @@
|
||||
.. _using_with_openstack:
|
||||
|
||||
***************************************************************
|
||||
Using Ryu Network OS with with OpenStack as OpenFlow controller
|
||||
***************************************************************
|
||||
This section describes how to setup openstack (nova, quantum) and
|
||||
ryu-manager.
|
||||
It is assumed that kvm with libvirt is used and each host machines that run
|
||||
nova-compute/nova-network has two physical NICs.
|
||||
It would be possible to deploy it with single NIC machines as described at
|
||||
the last section.
|
||||
|
||||
NOTE: How to use nova isn't described in this document.
|
||||
|
||||
Overview
|
||||
========
|
||||
|
||||
Ryu is designed/implemented with for production use in mind, so it cooperates
|
||||
very well with `OpenStack <http://www.openstack.org/>`_ .
|
||||
With nova and quantum OVS plugin,
|
||||
Ryu provides L2 segregation of Multi-tenants without any switch feature/settings
|
||||
like VLAN. So it's very easy to use/experiment/deploy this segregation as
|
||||
the below figure.
|
||||
|
||||
.. image:: /images/logical-view.png
|
||||
|
||||
|
||||
|
||||
Physical machine setup
|
||||
----------------------
|
||||
The following figure depicts how physical hosts are connected and each daemons
|
||||
are deployed.
|
||||
|
||||
.. image:: /images/physical-view.png
|
||||
|
||||
Although the nova-api, nova-scheduler, nova-network and related openstack
|
||||
daemons are installed in each own physical machines in the above picture,
|
||||
they can be installed on a physical machine which also runs nova-compute.
|
||||
Each host machine has two nics and one is connected to management LAN
|
||||
and other is connected to deployment LAN.
|
||||
|
||||
|
||||
How to install/setup
|
||||
====================
|
||||
If you are not familiar with installing/setting up nova/quantum/openvswitch
|
||||
from the source, please refer to OpenStack document and get back here again.
|
||||
[
|
||||
`OpenStack docs <http://docs.openstack.org/>`_ ,
|
||||
`Nova <http://www.openstack.org/projects/compute/>`_ ,
|
||||
`Quantum <http://docs.openstack.org/incubation/>`_ ,
|
||||
`OpenvSwtich and Quantum Part 1 <http://openvswitch.org/openstack/2011/07/25/openstack-quantum-and-open-vswitch-part-1/>`_ ,
|
||||
`OpenvSwtich and Quantum Part 2 <http://openvswitch.org/openstack/2011/07/25/openstack-quantum-and-open-vswitch-part-1/>`_ ,
|
||||
`OVS Quantum Plugin Documentation <http://openvswitch.org/openstack/documentation/>`_
|
||||
]
|
||||
|
||||
* Install ryu and run ryu-manager
|
||||
* install ryu from the source code on the hosts on which you run
|
||||
* nova-compute,
|
||||
* quantum-server and
|
||||
* ryu-manager.
|
||||
|
||||
This is because quantum-server and ova quantum agent which runs on
|
||||
nova-compute node needs ryu-client library to communicate ryu-manager.
|
||||
|
||||
Type in ryu source directory::
|
||||
|
||||
% python ./setup.py install
|
||||
|
||||
* edit /etc/ryu/ryu.conf on the host on which you run ryu-manager
|
||||
if necessary
|
||||
|
||||
No configuration is needed on hosts that runs quantum and ovs quantum
|
||||
agent.
|
||||
|
||||
* run ryu network os::
|
||||
|
||||
% ryu-manager [----flagfile /etc/ryu/ryu.conf]
|
||||
|
||||
|
||||
* get nova source and quantum source from github
|
||||
* They are a bit modified from openstack master tree. They are available
|
||||
at github for convinience
|
||||
|
||||
* https://github.com/osrg/nova/tree/ryu
|
||||
* https://github.com/osrg/quantum/tree/ryu
|
||||
|
||||
clone them by typing the followings in an appropriate directory::
|
||||
|
||||
% git clone --branch ryu git://github.com/osrg/nova.git
|
||||
% git clone --branch ryu git://github.com/osrg/quantum.git
|
||||
|
||||
If you prefer https, try those::
|
||||
|
||||
% git clone --branch ryu https://github.com/osrg/nova.git
|
||||
% git clone --branch ryu https://github.com/osrg/quantum.git
|
||||
|
||||
|
||||
* Install nova and quantum as usual.
|
||||
(And other Openstack related component if necessary. e.g. glance)
|
||||
|
||||
Each daemons can be installed in a single machine or in different machines.
|
||||
Please refer to Openstack documentation for details.
|
||||
You may want to set up multiple nova-compute nodes for interesting use case.
|
||||
|
||||
* Setup nova daemons. (Edit nova.conf)
|
||||
Specifically configure nova-network and nova-compute
|
||||
|
||||
* configure nova-network
|
||||
* --fixed_ranges=<setup here>
|
||||
* --network_size=<setup here>
|
||||
* --network_manager=nova.network.quantum.manager.QuantumManage
|
||||
* --quantum_connection_host=<quantume server ip address>
|
||||
* --firewall_driver=nova.virt.libvirt.firewall.NopFirewallDriver
|
||||
|
||||
NOP firewall driver is newly introduced for demonstrating Ryu
|
||||
capability.
|
||||
If you want, other existing firewall driver can be specified.
|
||||
But such specification don't have any effect in fact
|
||||
because ryu directly controls packets to VM instance via OVS bypassing
|
||||
netfilter/iptables.
|
||||
|
||||
* --linuxnet_interface_driver=nova.network.linux_net.LinuxOVSOFInterfaceDriver
|
||||
* set up OVS on each nova-compute node
|
||||
|
||||
If Ubuntu is used, you can install it from packages as
|
||||
openvswitch-datapath-dkms, openvswitch-common, openvswitch-switch
|
||||
If you already use bridge, you may need to edit /etc/modules to load
|
||||
openvswitch kernel module, openvswitch_mod and brcompat_mod, before
|
||||
bridge module and reboot to unload bridge module.
|
||||
|
||||
And then create ovs bridge::
|
||||
|
||||
# ovs-vsctl add-br <bridge name: usually br-int>
|
||||
|
||||
And if you connect NIC to OVS bridge.::
|
||||
|
||||
# ovs-vsctl add-port <bridge name:br-int> <ether interface: e.g. eth<N>>
|
||||
|
||||
* configure each nova-compute
|
||||
* --libvirt_type=kvm
|
||||
* --libvirt_ovs_integration_bridge=<OVS bridge:br-int>
|
||||
* --libvirt_vif_type=ethernet
|
||||
* --libvirt_vif_driver=nova.virt.libvirt.vif.LibvirtOpenVswitchDriver
|
||||
|
||||
* install quantum server and have quantum to use OVS pluging
|
||||
* Edit [PLUGIN] section of /etc/quantum/plugins.ini
|
||||
* provider = quantum.plugins.openvswitch.ovs_quantum_plugin.OVSQuantumPlugin
|
||||
|
||||
* Edit [OVS] section of
|
||||
/etc/quantum/plugins/openvswitch/ovs_quantum_plugin.ini
|
||||
|
||||
In addition to normal quantum OVS settings, add the followings.
|
||||
* integration-bridge = <OVS bridge name: br-int>
|
||||
* plugin_driver = quantum.plugins.openvswitch.ovs_quantum_plugin.OFPRyuDriver
|
||||
* agent_driver = OVSQuantumOFPRyuAgent
|
||||
* openflow-controller = <ryu-manager IP address>:<ryu openflow port: default 6633>
|
||||
* openflow-rest-api = <ryu-manager IP address>:<RYU reset API port: default 8080>
|
||||
|
||||
* Run quantum server
|
||||
* install quantum OVS agent on each nova-compute node
|
||||
* Edit /etc/quantum/plugins/openvswitch/ovs_quantum_plugin.ini
|
||||
* Run ovs agent::
|
||||
|
||||
# ovs_quantum_agent.py -v ./etc/quantum/plugins/openvswitch/ovs_quantum_plugin.ini
|
||||
|
||||
* Then as usual openstack nova operation, create user, project, network and
|
||||
run instances.
|
||||
* Enjoy!
|
||||
|
||||
|
||||
Testing
|
||||
=======
|
||||
Yay, now you have ryu network OS set up.
|
||||
You would want to really they are L2-segregated.
|
||||
|
||||
* create multi projects and run instances.
|
||||
* ping/traceroute between them.
|
||||
* tcpdump in the instances
|
||||
|
||||
The routing between gateway(gw-xxx) of each tenants are disabled
|
||||
by nova.network.linux_net.LinuxOVSOFInterfaceDriver by installing iptables
|
||||
rule on nova-network host::
|
||||
|
||||
# iptable -t filter -A nova-network-FORWARD --in-interface gw-+ --out-interface gw-+
|
||||
|
||||
Thus pinging/tracerouting between VMs in distinct tenants doesn't work.
|
||||
If you drop the above rule by::
|
||||
|
||||
# iptable -t filter -D nova-network-FORWARD --in-interface gw-+ --out-interface gw-+
|
||||
|
||||
You will see ping/tracerout works. Please notice that the packets go through
|
||||
gw-xxx and gw-yyy, not directly.
|
||||
|
||||
.. image:: /images/trace-route.png
|
||||
|
||||
|
||||
Caveats
|
||||
=======
|
||||
* Run the following daemons in this order
|
||||
#. Run Ryu network OS
|
||||
#. Run quantum with OVS plugin
|
||||
#. Run quantum OVS agent
|
||||
#. run your guest instance
|
||||
|
||||
For now, ryu-manager doesn't have persistent store, so if it's rebooted,
|
||||
all the necessary information must be told again from quantum server/agent.
|
||||
|
||||
* nova-manage network delete doesn't work
|
||||
|
||||
At this moment, quantum doesn't implement network delete fully yet.
|
||||
If you issue the command, it fails. And you need to fix nova/quantum DB
|
||||
by hand using SQL.
|
||||
|
||||
|
||||
Appendix
|
||||
========
|
||||
In the above, two physical NIC deployment is described.
|
||||
Some people may want to use those settings with single NIC machine or even
|
||||
with single machine.
|
||||
It would be possible as the following pictures, but we haven't tested those
|
||||
setting. If you success it, please report it.
|
||||
|
||||
single NIC/All-in-One setting
|
||||
-----------------------------
|
||||
If your host machines have only single NIC, it would be possible to use
|
||||
Ryu network OS with Linux bridge. However we haven't tested such setups.
|
||||
|
||||
.. image:: /images/compute-node.png
|
||||
|
||||
|
||||
All-in-One Setup
|
||||
----------------
|
||||
You can also setup in single physical host as the following picture.
|
||||
|
||||
.. image:: /images/minimul-setup.png
|
||||
|
||||
You can setup the above environment quickly using DevStack.
|
||||
|
||||
#. Install Ubuntu 11.10 (Oneiric)
|
||||
|
||||
#. Download Ryu enabled DevStack from github
|
||||
::
|
||||
|
||||
% git clone --branch ryu git://github.com/osrg/devstack.git
|
||||
|
||||
#. Start the install
|
||||
::
|
||||
|
||||
% cd devstack; ./stack.sh
|
||||
|
||||
It will take a few minutes.
|
7
etc/ryu/ryu.conf
Normal file
@ -0,0 +1,7 @@
|
||||
# Sample configuration file
|
||||
|
||||
#--wsapi_host=<hostip>
|
||||
#--wsapi_port=<port:8080>
|
||||
#--ofp_listen_host=<hostip>
|
||||
#--ofp_listen_port=<port:6633>
|
||||
#--simple_isolation_allow_host=False
|
0
ryu/__init__.py
Normal file
0
ryu/app/__init__.py
Normal file
74
ryu/app/client.py
Normal file
@ -0,0 +1,74 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import httplib
|
||||
import urlparse
|
||||
|
||||
|
||||
class OFPClientV1_0(object):
|
||||
version = 'v1.0'
|
||||
|
||||
# /{network_id}/{dpid}_{port}
|
||||
network_path = '%s'
|
||||
port_path = '%s/%s_%s'
|
||||
|
||||
def __init__(self, address):
|
||||
r = urlparse.SplitResult('', address, '', '', '')
|
||||
self.host = r.hostname
|
||||
self.port = r.port
|
||||
self.url_prefix = '/' + self.version + '/'
|
||||
|
||||
def _do_request(self, method, action):
|
||||
conn = httplib.HTTPConnection(self.host, self.port)
|
||||
url = self.url_prefix + action
|
||||
conn.request(method, url)
|
||||
res = conn.getresponse()
|
||||
if res.status in (httplib.OK,
|
||||
httplib.CREATED,
|
||||
httplib.ACCEPTED,
|
||||
httplib.NO_CONTENT):
|
||||
return res
|
||||
|
||||
raise httplib.HTTPException('code %d reason %s' %
|
||||
(res.status, res.reason))
|
||||
|
||||
def get_networks(self):
|
||||
res = self._do_request('GET', '')
|
||||
return res.read()
|
||||
|
||||
def create_network(self, network_id):
|
||||
self._do_request('POST', self.network_path % network_id)
|
||||
|
||||
def update_network(self, network_id):
|
||||
self._do_request('PUT', self.network_path % network_id)
|
||||
|
||||
def delete_network(self, network_id):
|
||||
self._do_request('DELETE', self.network_path % network_id)
|
||||
|
||||
def get_ports(self, network_id):
|
||||
res = self._do_request('GET', self.network_path % network_id)
|
||||
return res.read()
|
||||
|
||||
def create_port(self, network_id, dpid, port):
|
||||
self._do_request('POST', self.port_path % (network_id, dpid, port))
|
||||
|
||||
def update_port(self, network_id, dpid, port):
|
||||
self._do_request('PUT', self.port_path % (network_id, dpid, port))
|
||||
|
||||
def delete_port(self, network_id, dpid, port):
|
||||
self._do_request('DELETE', self.port_path % (network_id, dpid, port))
|
||||
|
||||
|
||||
OFPClient = OFPClientV1_0
|
210
ryu/app/rest.py
Normal file
@ -0,0 +1,210 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import json
|
||||
from ryu.exception import NetworkNotFound, NetworkAlreadyExist
|
||||
from ryu.exception import PortNotFound, PortAlreadyExist
|
||||
from ryu.app.wsapi import *
|
||||
|
||||
# REST API
|
||||
|
||||
# get the list of networks
|
||||
# GET /v1.0/
|
||||
#
|
||||
# register a new network.
|
||||
# Fail if the network is already registered.
|
||||
# POST /v1.0/{network-id}
|
||||
#
|
||||
# update a new network.
|
||||
# Success as nop even if the network is already registered.
|
||||
#
|
||||
# PUT /v1.0/{network-id}
|
||||
#
|
||||
# remove a network
|
||||
# DELETE /v1.0/{network-id}
|
||||
#
|
||||
# get the list of sets of dpid and port
|
||||
# GET /v1.0/{network-id}/
|
||||
#
|
||||
# register a new set of dpid and port
|
||||
# Fail if the port is already registered.
|
||||
# POST /v1.0/{network-id}/{dpid}_{port-id}
|
||||
#
|
||||
# update a new set of dpid and port
|
||||
# Success as nop even if same port already registered
|
||||
# PUT /v1.0/{network-id}/{dpid}_{port-id}
|
||||
#
|
||||
# remove a set of dpid and port
|
||||
# DELETE /v1.0/{network-id}/{dpid}_{port-id}
|
||||
|
||||
# We store networks and ports like the following:
|
||||
#
|
||||
# {network_id: [(dpid, port), ...
|
||||
# {3: [(3,4), (4,7)], 5: [(3,6)], 1: [(5,6), (4,5), (4, 10)]}
|
||||
#
|
||||
|
||||
|
||||
class WSPathNetwork(WSPathComponent):
|
||||
""" Match a network id string """
|
||||
|
||||
def __str__(self):
|
||||
return "{network-id}"
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == None:
|
||||
return WSPathExtractResult(error="End of requested URI")
|
||||
|
||||
return WSPathExtractResult(value=pc)
|
||||
|
||||
|
||||
class WSPathPort(WSPathComponent):
|
||||
""" Match a {dpid}_{port-id} string """
|
||||
|
||||
def __str__(self):
|
||||
return "{dpid}_{port-id}"
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == None:
|
||||
return WSPathExtractResult(error="End of requested URI")
|
||||
|
||||
try:
|
||||
dpid_str, port_str = pc.split('_')
|
||||
dpid = int(dpid_str, 16)
|
||||
port = int(port_str)
|
||||
except ValueError:
|
||||
return WSPathExtractResult(error="Invalid format: %s" % pc)
|
||||
|
||||
return WSPathExtractResult(value={'dpid': dpid, 'port': port})
|
||||
|
||||
|
||||
class restapi:
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
self.ws = wsapi()
|
||||
self.api = self.ws.get_version("1.0")
|
||||
self.nw = kwargs['network']
|
||||
self.register()
|
||||
|
||||
def list_networks_handler(self, request, data):
|
||||
request.setHeader("Content-Type", 'application/json')
|
||||
return json.dumps(self.nw.list_networks())
|
||||
|
||||
def create_network_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
|
||||
try:
|
||||
self.nw.create_network(network_id)
|
||||
except NetworkAlreadyExist:
|
||||
request.setResponseCode(409)
|
||||
|
||||
return ""
|
||||
|
||||
def update_network_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
self.nw.update_network(network_id)
|
||||
return ""
|
||||
|
||||
def remove_network_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
|
||||
try:
|
||||
self.nw.remove_network(network_id)
|
||||
except NetworkNotFound:
|
||||
request.setResponseCode(404)
|
||||
|
||||
return ""
|
||||
|
||||
def list_ports_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
|
||||
try:
|
||||
body = json.dumps(self.nw.list_ports(network_id))
|
||||
except NetworkNotFound:
|
||||
body = ""
|
||||
request.setResponseCode(404)
|
||||
|
||||
request.setHeader("Content-Type", 'application/json')
|
||||
return body
|
||||
|
||||
def create_port_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
dpid = data['{dpid}_{port-id}']['dpid']
|
||||
port = data['{dpid}_{port-id}']['port']
|
||||
|
||||
try:
|
||||
self.nw.create_port(network_id, dpid, port)
|
||||
except NetworkNotFound:
|
||||
request.setResponseCode(404)
|
||||
except PortAlreadyExist:
|
||||
request.setResponseCode(409)
|
||||
|
||||
return ""
|
||||
|
||||
def update_port_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
dpid = data['{dpid}_{port-id}']['dpid']
|
||||
port = data['{dpid}_{port-id}']['port']
|
||||
|
||||
try:
|
||||
self.nw.update_port(network_id, dpid, port)
|
||||
except NetworkNotFound:
|
||||
request.setResponseCode(404)
|
||||
|
||||
return ""
|
||||
|
||||
def remove_port_handler(self, request, data):
|
||||
network_id = data['{network-id}']
|
||||
dpid = data['{dpid}_{port-id}']['dpid']
|
||||
port = data['{dpid}_{port-id}']['port']
|
||||
|
||||
try:
|
||||
self.nw.remove_port(network_id, dpid, port)
|
||||
except (NetworkNotFound, PortNotFound):
|
||||
request.setResponseCode(404)
|
||||
|
||||
return ""
|
||||
|
||||
def register(self):
|
||||
self.api.register_request(self.list_networks_handler, "GET",
|
||||
[],
|
||||
"get the list of networks")
|
||||
|
||||
self.api.register_request(self.create_network_handler, "POST",
|
||||
[WSPathNetwork()],
|
||||
"register a new network")
|
||||
|
||||
self.api.register_request(self.update_network_handler, "PUT",
|
||||
[WSPathNetwork()],
|
||||
"update a network")
|
||||
|
||||
self.api.register_request(self.remove_network_handler, "DELETE",
|
||||
[WSPathNetwork()],
|
||||
"remove a network")
|
||||
|
||||
self.api.register_request(self.list_ports_handler, "GET",
|
||||
[WSPathNetwork()],
|
||||
"get the list of sets of dpid and port")
|
||||
|
||||
self.api.register_request(self.create_port_handler, "POST",
|
||||
[WSPathNetwork(), WSPathPort()],
|
||||
"register a new set of dpid and port")
|
||||
|
||||
self.api.register_request(self.update_port_handler, "PUT",
|
||||
[WSPathNetwork(), WSPathPort()],
|
||||
"update a set of dpid and port")
|
||||
|
||||
self.api.register_request(self.remove_port_handler, "DELETE",
|
||||
(WSPathNetwork(), WSPathPort()),
|
||||
"remove a set of dpid and port")
|
21
ryu/app/rest_nw_id.py
Normal file
@ -0,0 +1,21 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
NW_ID_EXTERNAL = '__NW_ID_EXTERNAL__'
|
||||
NW_ID_UNKNOWN = '__NW_ID_UNKNOWN__'
|
||||
|
||||
# PORT_TYPE_VM = 'guestvm'
|
||||
# PORT_TYPE_GW = 'gateway'
|
||||
# PORT_TYPE_EXTERNAL = 'external'
|
242
ryu/app/simple_isolation.py
Normal file
@ -0,0 +1,242 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
import struct
|
||||
|
||||
from ryu.app.rest_nw_id import NW_ID_UNKNOWN, NW_ID_EXTERNAL
|
||||
from ryu.exception import MacAddressDuplicated
|
||||
from ryu.exception import PortUnknown
|
||||
from ryu.controller import event
|
||||
from ryu.controller import mac_to_network
|
||||
from ryu.controller import mac_to_port
|
||||
from ryu.controller.handler import main_dispatcher
|
||||
from ryu.controller.handler import config_dispatcher
|
||||
from ryu.controller.handler import set_ev_cls
|
||||
from ryu.lib.mac import haddr_to_str
|
||||
|
||||
LOG = logging.getLogger('ryu.app.simple_isolation')
|
||||
|
||||
|
||||
class SimpleIsolation(object):
|
||||
def __init__(self, *args, **kwargs):
|
||||
self.nw = kwargs['network']
|
||||
self.mac2port = mac_to_port.MacToPortTable()
|
||||
self.mac2net = mac_to_network.MacToNetwork(self.nw)
|
||||
|
||||
@set_ev_cls(event.EventOFPSwitchFeatures, config_dispatcher)
|
||||
def switch_features_handler(self, ev):
|
||||
self.mac2port.dpid_add(ev.msg.datapath_id)
|
||||
self.nw.add_datapath(ev.msg)
|
||||
|
||||
@set_ev_cls(event.EventOFPBarrierReply)
|
||||
def barrier_reply_handler(ev):
|
||||
LOG.debug('barrier reply ev %s msg %s', ev, ev.msg)
|
||||
|
||||
def _modflow_and_send_packet(self, msg, src, dst, actions):
|
||||
datapath = msg.datapath
|
||||
|
||||
#
|
||||
# install flow and then send packet
|
||||
#
|
||||
wildcards = datapath.ofproto.OFPFW_ALL
|
||||
wildcards &= ~(datapath.ofproto.OFPFW_IN_PORT |
|
||||
datapath.ofproto.OFPFW_DL_SRC |
|
||||
datapath.ofproto.OFPFW_DL_DST)
|
||||
match = datapath.ofproto_parser.OFPMatch(wildcards,
|
||||
msg.in_port, src, dst,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0)
|
||||
|
||||
datapath.send_flow_mod(
|
||||
match=match, cookie=0, command=datapath.ofproto.OFPFC_ADD,
|
||||
idle_timeout=0, hard_timeout=0, priority=32768,
|
||||
buffer_id=0xffffffff, out_port=datapath.ofproto.OFPP_NONE,
|
||||
flags=datapath.ofproto.OFPFF_SEND_FLOW_REM, actions=actions)
|
||||
|
||||
datapath.send_packet_out(msg.buffer_id, msg.in_port, actions)
|
||||
|
||||
def _forward_to_nw_id(self, msg, src, dst, nw_id, out_port):
|
||||
assert out_port is not None
|
||||
datapath = msg.datapath
|
||||
|
||||
if not self.nw.same_network(datapath.id, nw_id, out_port,
|
||||
NW_ID_EXTERNAL):
|
||||
LOG.debug('packet is blocked src %s dst %s '
|
||||
'from %d to %d on datapath %d',
|
||||
haddr_to_str(src), haddr_to_str(dst),
|
||||
msg.in_port, out_port, datapath.id)
|
||||
return
|
||||
|
||||
LOG.debug("learned dpid %s in_port %d out_port %d src %s dst %s",
|
||||
datapath.id, msg.in_port, out_port,
|
||||
haddr_to_str(src), haddr_to_str(dst))
|
||||
actions = [datapath.ofproto_parser.OFPActionOutput(out_port)]
|
||||
self._modflow_and_send_packet(msg, src, dst, actions)
|
||||
|
||||
def _flood_to_nw_id(self, msg, src, dst, nw_id):
|
||||
datapath = msg.datapath
|
||||
actions = []
|
||||
LOG.debug("dpid %s in_port %d src %s dst %s ports %s",
|
||||
datapath.id, msg.in_port,
|
||||
haddr_to_str(src), haddr_to_str(dst),
|
||||
self.nw.dpids.get(datapath.id, {}).items())
|
||||
for port_no in self.nw.filter_ports(datapath.id, msg.in_port,
|
||||
nw_id, NW_ID_EXTERNAL):
|
||||
LOG.debug("port_no %s", port_no)
|
||||
actions.append(datapath.ofproto_parser.OFPActionOutput(port_no))
|
||||
self._modflow_and_send_packet(msg, src, dst, actions)
|
||||
|
||||
def _learned_mac_or_flood_to_nw_id(self, msg, src, dst,
|
||||
dst_nw_id, out_port):
|
||||
if out_port is not None:
|
||||
self._forward_to_nw_id(msg, src, dst, dst_nw_id, out_port)
|
||||
else:
|
||||
self._flood_to_nw_id(msg, src, dst, dst_nw_id)
|
||||
|
||||
@set_ev_cls(event.EventOFPPacketIn, main_dispatcher)
|
||||
def packet_in_handler(self, ev):
|
||||
# LOG.debug('packet in ev %s msg %s', ev, ev.msg)
|
||||
msg = ev.msg
|
||||
datapath = msg.datapath
|
||||
|
||||
dst, src, eth_type = struct.unpack_from('!6s6sH', buffer(msg.data), 0)
|
||||
|
||||
try:
|
||||
port_nw_id = self.nw.get_network(datapath.id, msg.in_port)
|
||||
except PortUnknown:
|
||||
port_nw_id = NW_ID_UNKNOWN
|
||||
|
||||
if port_nw_id != NW_ID_UNKNOWN:
|
||||
# Here it is assumed that the
|
||||
# (port <-> network id)/(mac <-> network id) relationship
|
||||
# is stable once the port is created. The port will be destroyed
|
||||
# before assigning new network id to the given port.
|
||||
# This is correct nova-network/nova-compute.
|
||||
try:
|
||||
# allow external -> known nw id change
|
||||
self.mac2net.add_mac(src, port_nw_id, NW_ID_EXTERNAL)
|
||||
except MacAddressDuplicated:
|
||||
LOG.warn('mac address %s is already in use.'
|
||||
' So (dpid %s, port %s) can not use it',
|
||||
haddr_to_str(src), datapath.id, msg.in_port)
|
||||
#
|
||||
# should we install drop action pro-actively for future?
|
||||
#
|
||||
return
|
||||
|
||||
old_port = self.mac2port.port_add(datapath.id, msg.in_port, src)
|
||||
if old_port is not None and old_port != msg.in_port:
|
||||
# We really overwrite already learned mac address.
|
||||
# So discard already installed stale flow entry which conflicts
|
||||
# new port.
|
||||
wildcards = datapath.ofproto.OFPFW_ALL
|
||||
wildcards &= ~datapath.ofproto.OFPFW_DL_DST
|
||||
match = datapath.ofproto_parser.OFPMatch(wildcards,
|
||||
0, 0, src,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0)
|
||||
|
||||
datapath.send_flow_mod(match=match, cookie=0,
|
||||
command=datapath.ofproto.OFPFC_DELETE, idle_timeout=0,
|
||||
hard_timeout=0, priority=32768, out_port=old_port)
|
||||
|
||||
# to make sure the old flow entries are purged.
|
||||
datapath.send_barrier()
|
||||
|
||||
src_nw_id = self.mac2net.get_network(src, NW_ID_UNKNOWN)
|
||||
dst_nw_id = self.mac2net.get_network(dst, NW_ID_UNKNOWN)
|
||||
|
||||
# we handle multicast packet as same as broadcast
|
||||
first_oct = struct.unpack_from('B', dst)[0]
|
||||
broadcast = (dst == '\xff' * 6) or (first_oct & 0x01)
|
||||
out_port = self.mac2port.port_get(datapath.id, dst)
|
||||
|
||||
#
|
||||
# there are several combinations:
|
||||
# in_port: known nw_id, external, unknown nw,
|
||||
# src mac: known nw_id, external, unknown nw,
|
||||
# dst mac: known nw_id, external, unknown nw, and broadcast/multicast
|
||||
# where known nw_id: is quantum network id
|
||||
# external: means that these ports are connected to outside
|
||||
# unknown nw: means that we don't know this port is bounded to
|
||||
# specific nw_id or external
|
||||
# broadcast: the destination mac address is broadcast address
|
||||
# (or multicast address)
|
||||
#
|
||||
# Can the following logic be refined/shortened?
|
||||
#
|
||||
|
||||
if port_nw_id != NW_ID_EXTERNAL and port_nw_id != NW_ID_UNKNOWN:
|
||||
if broadcast:
|
||||
# flood to all ports of external or src_nw_id
|
||||
self._flood_to_nw_id(msg, src, dst, src_nw_id)
|
||||
elif src_nw_id != NW_ID_EXTERNAL and src_nw_id != NW_ID_UNKNOWN:
|
||||
# try learned mac check if the port is net_id
|
||||
# or
|
||||
# flood to all ports of external or src_nw_id
|
||||
self._learned_mac_or_flood_to_nw_id(msg, src, dst,
|
||||
src_nw_id, out_port)
|
||||
else:
|
||||
# NW_ID_EXTERNAL or NW_ID_UNKNOWN
|
||||
# drop packets
|
||||
return
|
||||
|
||||
elif port_nw_id == NW_ID_EXTERNAL:
|
||||
if src_nw_id != NW_ID_EXTERNAL and src_nw_id != NW_ID_UNKNOWN:
|
||||
if broadcast:
|
||||
# flood to all ports of external or src_nw_id
|
||||
self._flood_to_nw_id(msg, src, dst, src_nw_id)
|
||||
elif (dst_nw_id != NW_ID_EXTERNAL and
|
||||
dst_nw_id != NW_ID_UNKNOWN):
|
||||
if src_nw_id == dst_nw_id:
|
||||
# try learned mac
|
||||
# check if the port is external or same net_id
|
||||
# or
|
||||
# flood to all ports of external or src_nw_id
|
||||
self._learned_mac_or_flood_to_nw_id(msg, src, dst,
|
||||
src_nw_id,
|
||||
out_port)
|
||||
else:
|
||||
# should not occur?
|
||||
LOG.debug("should this case happen?")
|
||||
elif dst_nw_id == NW_ID_EXTERNAL:
|
||||
# try learned mac
|
||||
# or
|
||||
# flood to all ports of external or src_nw_id
|
||||
self._learned_mac_or_flood_to_nw_id(msg, src, dst,
|
||||
src_nw_id, out_port)
|
||||
else:
|
||||
assert dst_nw_id == NW_ID_UNKNOWN
|
||||
|
||||
elif src_nw_id == NW_ID_EXTERNAL:
|
||||
# drop packet
|
||||
pass
|
||||
else:
|
||||
# should not occur?
|
||||
# drop packets
|
||||
assert src_nw_id == NW_ID_UNKNOWN
|
||||
else:
|
||||
# drop packets?
|
||||
assert port_nw_id == NW_ID_UNKNOWN
|
||||
|
||||
@set_ev_cls(event.EventOFPPortStatus, main_dispatcher)
|
||||
def port_status_handler(self, ev):
|
||||
msg = ev.msg
|
||||
datapath = msg.datapath
|
||||
datapath.send_delete_all_flows()
|
||||
datapath.send_barrier()
|
||||
|
||||
@set_ev_cls(event.EventOFPBarrierReply, main_dispatcher)
|
||||
def barrier_replay_handler(self, ev):
|
||||
pass
|
93
ryu/app/simple_switch.py
Normal file
@ -0,0 +1,93 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
import struct
|
||||
|
||||
from ryu.controller import event
|
||||
from ryu.controller import mac_to_port
|
||||
from ryu.controller.handler import main_dispatcher
|
||||
from ryu.controller.handler import set_ev_cls
|
||||
from ryu.lib.mac import haddr_to_str
|
||||
from ryu.lib.mac import haddr_to_bin
|
||||
|
||||
|
||||
LOG = logging.getLogger('ryu.app.simple_switch')
|
||||
|
||||
# TODO: we should split the handler into two parts, protocol
|
||||
# independent and dependant parts.
|
||||
|
||||
# TODO: can we use dpkt python library?
|
||||
|
||||
# TODO: we need to move the followings to something like db
|
||||
|
||||
|
||||
class SimpleSwitch(object):
|
||||
def __init__(self, *args, **kwargs):
|
||||
self.mac2port = mac_to_port.MacToPortTable()
|
||||
|
||||
@set_ev_cls(event.EventOFPPacketIn, main_dispatcher)
|
||||
def packetInHandler(self, ev):
|
||||
msg = ev.msg
|
||||
datapath = msg.datapath
|
||||
ofproto = datapath.ofproto
|
||||
|
||||
dst, src, eth_type = struct.unpack_from('!6s6sH', buffer(msg.data), 0)
|
||||
|
||||
dpid = datapath.id
|
||||
self.mac2port.dpid_add(dpid)
|
||||
LOG.info("packet in %s %s %s %s",
|
||||
dpid, haddr_to_str(src), haddr_to_str(dst), msg.in_port)
|
||||
|
||||
self.mac2port.port_add(dpid, msg.in_port, src)
|
||||
out_port = self.mac2port.port_get(dpid, dst)
|
||||
|
||||
if out_port == None:
|
||||
LOG.info("out_port not found")
|
||||
out_port = ofproto.OFPP_FLOOD
|
||||
|
||||
actions = [datapath.ofproto_parser.OFPActionOutput(out_port)]
|
||||
|
||||
if out_port != ofproto.OFPP_FLOOD:
|
||||
wildcards = ofproto.OFPFW_ALL
|
||||
wildcards &= ~(ofproto.OFPFW_IN_PORT |
|
||||
ofproto.OFPFW_DL_DST |
|
||||
ofproto.OFPFW_NW_TOS)
|
||||
match = datapath.ofproto_parser.OFPMatch(
|
||||
wildcards, msg.in_port,
|
||||
haddr_to_bin('00:00:00:00:00:00'), dst,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0)
|
||||
|
||||
datapath.send_flow_mod(
|
||||
match=match, cookie=0, command=ofproto.OFPFC_ADD,
|
||||
idle_timeout=0, hard_timeout=0, priority=32768,
|
||||
flags=ofproto.OFPFF_SEND_FLOW_REM, actions=actions)
|
||||
|
||||
datapath.send_packet_out(msg.buffer_id, msg.in_port, actions)
|
||||
|
||||
@set_ev_cls(event.EventOFPPortStatus, main_dispatcher)
|
||||
def portStatusHandler(self, ev):
|
||||
msg = ev.msg
|
||||
reason = msg.reason
|
||||
port_no = msg.port_no
|
||||
|
||||
ofproto = msg.datapath.ofproto
|
||||
if reason == ofproto.OFPPR_ADD:
|
||||
LOG.info("port added %s", port_no)
|
||||
elif reason == ofproto.OFPPR_DELETE:
|
||||
LOG.info("port deleted %s", port_no)
|
||||
elif reason == ofproto.OFPPR_MODIFY:
|
||||
LOG.info("port modified %s", port_no)
|
||||
else:
|
||||
LOG.info("Illeagal port state %s %s", port_no, reason)
|
578
ryu/app/wsapi.py
Normal file
@ -0,0 +1,578 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
#
|
||||
# This code is based on webservice.py from NOX project:
|
||||
# Copyright 2008 (C) Nicira, Inc.
|
||||
|
||||
import gflags
|
||||
import logging
|
||||
import re
|
||||
import textwrap
|
||||
import simplejson
|
||||
from copy import copy
|
||||
from gevent.pywsgi import WSGIServer
|
||||
from webob import Request, Response
|
||||
|
||||
LOG = logging.getLogger('ryu.app.wsapi')
|
||||
|
||||
FLAGS = gflags.FLAGS
|
||||
gflags.DEFINE_string('wsapi_host', '', 'webapp listen host')
|
||||
gflags.DEFINE_integer('wsapi_port', 8080, 'webapp listen port')
|
||||
|
||||
### Response functions:
|
||||
#
|
||||
# The following functions can be used to generate various error responses.
|
||||
# These should only ever be used for the web-services interface, not the
|
||||
# user-facing web interface.
|
||||
|
||||
|
||||
def forbidden(request, errmsg, otherInfo={}):
|
||||
"""Return an error code indicating client is forbidden from accessing."""
|
||||
request.setResponseCode(403)
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = errmsg
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def badRequest(request, errmsg, otherInfo={}):
|
||||
"""Return an error indicating a problem in data from the client."""
|
||||
request.setResponseCode(400, "Bad request")
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = "The server did not understand the request."
|
||||
d["error"] = errmsg
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def conflictError(request, errmsg, otherURI=None, otherInfo={}):
|
||||
"""Return an error indicating something conflicts with the request."""
|
||||
if otherURI != None:
|
||||
request.setResponseCode(409, "Conflicts with another resource")
|
||||
request.setHeader("Location", otherURI.encode("utf-8"))
|
||||
else:
|
||||
request.setResponseCode(409, "Internal server conflict")
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = "Request failed due to simultaneous access."
|
||||
d["error"] = errmsg
|
||||
d["otherURI"] = otherURI
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def internalError(request, errmsg, otherInfo={}):
|
||||
"""Return an error code indicating an error in the server."""
|
||||
request.setResponseCode(500)
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = \
|
||||
"The server failed while attempting to perform request."
|
||||
d["error"] = errmsg
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def notFound(request, errmsg, otherInfo={}):
|
||||
"""Return an error indicating a resource could not be found."""
|
||||
request.setResponseCode(404, "Resource not found")
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = "The server does not have data for the request."
|
||||
d["error"] = errmsg
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def methodNotAllowed(request, errmsg, valid_methods, otherInfo={}):
|
||||
"""Return an error indicating this request method is not allowed."""
|
||||
request.setResponseCode(405, "Method not allowed")
|
||||
method_txt = ", ".join(valid_methods)
|
||||
request.setHeader("Allow", method_txt)
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = "The server can not perform this operation."
|
||||
d["error"] = errmsg
|
||||
d["validMethods"] = valid_methods
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
def unauthorized(request, errmsg="", otherInfo={}):
|
||||
"""Return an error indicating a client was not authorized."""
|
||||
request.setResponseCode(401, "Unauthorized")
|
||||
request.setHeader("Content-Type", "application/json")
|
||||
if errmsg != "":
|
||||
errmsg = ": " + errmsg
|
||||
d = copy(otherInfo)
|
||||
d["displayError"] = "Unauthorized%s\n\n" % (errmsg, )
|
||||
d["error"] = errmsg
|
||||
d["loginInstructions"] = \
|
||||
"You must login using 'POST /ws.v1/login' nd pass the resulting " + \
|
||||
"cookie with\neach equest."
|
||||
return simplejson.dumps(d)
|
||||
|
||||
|
||||
### Message Body handling
|
||||
#
|
||||
def json_parse_message_body(request):
|
||||
content = request.content.read()
|
||||
content_type = request.getHeader("content-type")
|
||||
if content_type == None or content_type.find("application/json") == -1:
|
||||
e = ["The message body must have Content-Type application/json\n",
|
||||
"instead of %s. " % content_type]
|
||||
if content_type == "application/x-www-form-urlencoded":
|
||||
e.append("The web\nserver decoded the message body as:\n\n")
|
||||
e.append(str(request.args))
|
||||
else:
|
||||
e.append("The message body was:\n\n")
|
||||
e.append(content)
|
||||
LOG.error("".join(e))
|
||||
return None
|
||||
if len(content) == 0:
|
||||
LOG.error("Message body was empty. "
|
||||
"It should be valid JSON encoded data for this request.")
|
||||
return None
|
||||
try:
|
||||
data = simplejson.loads(content)
|
||||
except:
|
||||
LOG.error("Message body is not valid json data. "
|
||||
"It was:\n\n%s" % (content,))
|
||||
return None
|
||||
return data
|
||||
|
||||
|
||||
class WhitespaceNormalizer:
|
||||
def __init__(self):
|
||||
self._re = re.compile("\s+")
|
||||
|
||||
def normalize_whitespace(self, s):
|
||||
return self._re.sub(" ", s).strip()
|
||||
|
||||
|
||||
class WSPathTreeNode:
|
||||
_wsn = WhitespaceNormalizer()
|
||||
|
||||
def __init__(self, parent, path_component):
|
||||
self.path_component = path_component
|
||||
self._handlers = {}
|
||||
self._parent = parent
|
||||
self._children = []
|
||||
self._tw = textwrap.TextWrapper()
|
||||
self._tw.width = 78
|
||||
self._tw.initial_indent = " " * 4
|
||||
self._tw.subsequent_indent = self._tw.initial_indent
|
||||
|
||||
def parent(self):
|
||||
return self._parent()
|
||||
|
||||
def _matching_child(self, path_component):
|
||||
for c in self._children:
|
||||
if str(c.path_component) == str(path_component):
|
||||
return c
|
||||
return None
|
||||
|
||||
def has_child(self, path_component):
|
||||
return self._matching_child(path_component) != None
|
||||
|
||||
def add_child(self, path_component):
|
||||
c = self._matching_child(path_component)
|
||||
if c == None:
|
||||
c = WSPathTreeNode(self, path_component)
|
||||
self._children.append(c)
|
||||
return c
|
||||
|
||||
def path_str(self):
|
||||
if self._parent == None:
|
||||
return ""
|
||||
return self._parent.path_str() + "/" + str(self.path_component)
|
||||
|
||||
def set_handler(self, request_method, handler, doc):
|
||||
if request_method in self._handlers:
|
||||
raise KeyError("%s %s is already handled by '%s'" %
|
||||
(request_method, self.path_str(),
|
||||
repr(self._handlers[request_method][0])))
|
||||
d = self._wsn.normalize_whitespace(doc)
|
||||
d = self._tw.fill(d)
|
||||
self._handlers[request_method] = (handler, d)
|
||||
|
||||
def interface_doc(self, base_path):
|
||||
msg = []
|
||||
p = base_path + self.path_str()
|
||||
for k in self._handlers:
|
||||
msg.extend((k, " ", p, "\n"))
|
||||
doc = self._handlers[k][1]
|
||||
if doc != None:
|
||||
msg.extend((doc, "\n\n"))
|
||||
for c in self._children:
|
||||
msg.append(c.interface_doc(base_path))
|
||||
return "".join(msg)
|
||||
|
||||
def handle(self, t):
|
||||
s = t.next_path_string()
|
||||
if s != None:
|
||||
r = None
|
||||
if len(self._children) == 0:
|
||||
t.request_uri_too_long()
|
||||
for c in self._children:
|
||||
r = c.path_component.extract(s, t.data)
|
||||
if r.error == None:
|
||||
t.data[str(c.path_component)] = r.value
|
||||
t.failed_paths = []
|
||||
r = c.handle(t)
|
||||
break
|
||||
else:
|
||||
t.failed_paths.append((c.path_str(), r.error))
|
||||
if len(t.failed_paths) > 0:
|
||||
return t.invalid_request()
|
||||
return r
|
||||
else:
|
||||
try:
|
||||
h, d = self._handlers[t.request_method()]
|
||||
except KeyError:
|
||||
return t.unsupported_method(self._handlers.keys())
|
||||
return t.call_handler(h)
|
||||
|
||||
|
||||
class WSPathTraversal:
|
||||
|
||||
def __init__(self, request):
|
||||
self._request = request
|
||||
self._pathiter = iter(request.postpath)
|
||||
self.data = {}
|
||||
self.failed_paths = []
|
||||
|
||||
def request_method(self):
|
||||
return self._request.method
|
||||
|
||||
def next_path_string(self):
|
||||
try:
|
||||
return self._pathiter.next()
|
||||
except StopIteration:
|
||||
return None
|
||||
|
||||
def call_handler(self, handler):
|
||||
try:
|
||||
return handler(self._request, self.data)
|
||||
except Exception, e:
|
||||
LOG.error("caught unhandled exception with path '%s' : %s" % \
|
||||
(str(self._request.postpath), e))
|
||||
internalError(self._request, "Unhandled server error")
|
||||
|
||||
def _error_wrapper(self, l):
|
||||
msg = []
|
||||
msg.append("You submitted the following request.\n\n")
|
||||
msg.append(" %s %s\n\n" %
|
||||
(self._request.method, self._request.path))
|
||||
msg.append("This request is not valid. ")
|
||||
msg.extend(l)
|
||||
msg.append("\n\nYou can get a list of all valid requests with the ")
|
||||
msg.append("following request.\n\n ")
|
||||
msg.append("GET /" + "/".join(self._request.prepath) + "/doc")
|
||||
return "".join(msg)
|
||||
|
||||
def request_uri_too_long(self):
|
||||
e = ["The request URI path extended beyond all available URIs."]
|
||||
return notFound(self._request, self._error_wrapper(e))
|
||||
|
||||
def unsupported_method(self, valid_methods):
|
||||
if len(valid_methods) > 0:
|
||||
e = ["This URI only supports the following methods.\n\n "]
|
||||
e.append(", ".join(valid_methods))
|
||||
else:
|
||||
e = ["There are no supported request methods\non this URI. "]
|
||||
e.append("It is only used as part of longer URI paths.")
|
||||
return methodNotAllowed(self._request, self._error_wrapper(e),
|
||||
valid_methods)
|
||||
|
||||
def invalid_request(self):
|
||||
e = []
|
||||
if len(self.failed_paths) > 0:
|
||||
e.append("The following paths were evaluated and failed\n")
|
||||
e.append("for the indicated reason.")
|
||||
for p, m in self.failed_paths:
|
||||
e.append("\n\n - %s\n %s" % (p, m))
|
||||
return notFound(self._request, self._error_wrapper(e))
|
||||
|
||||
|
||||
### Registering for requests
|
||||
#
|
||||
class WSRequestHandler:
|
||||
"""Class to determine appropriate handler for a web services request."""
|
||||
|
||||
def __init__(self):
|
||||
self._path_tree = WSPathTreeNode(None, None)
|
||||
|
||||
def register(self, handler, request_method, path_components, doc=None):
|
||||
"""Register a web services request handler.
|
||||
|
||||
The parameters are:
|
||||
|
||||
- handler: a function to be called when the specified request
|
||||
method and path component list are matched. It must
|
||||
have the signature:
|
||||
|
||||
handler(request, extracted_data)
|
||||
|
||||
Here the 'request' parameter is a twisted request object
|
||||
to be used to output the result and extracted_data is a
|
||||
dictionary of data extracted by the WSPath subclass
|
||||
instances in the 'path_components' parameter indexed
|
||||
by str(path_component_instance).
|
||||
|
||||
- request_method: the HTTP request method of the request to
|
||||
be handled.
|
||||
|
||||
- path_components: a list of 'WSPathComponent' subclasses
|
||||
describing the path to be handled.
|
||||
|
||||
- doc: a string describing the result of this request."""
|
||||
pn = self._path_tree
|
||||
for pc in path_components:
|
||||
pn = pn.add_child(pc)
|
||||
pn.set_handler(request_method.upper(), handler, doc)
|
||||
|
||||
def handle(self, request):
|
||||
return self._path_tree.handle(WSPathTraversal(request))
|
||||
|
||||
def interface_doc(self, base_path):
|
||||
"""Text describing all current valid requests."""
|
||||
d = """\
|
||||
This is a RESTful web interface to NOX network applications. The applications
|
||||
running on this NOX instance support the following requests.\n\n"""
|
||||
|
||||
return d + self._path_tree.interface_doc(base_path)
|
||||
|
||||
|
||||
class WSPathExtractResult:
|
||||
def __init__(self, value=None, error=None):
|
||||
self.value = value
|
||||
self.error = error
|
||||
|
||||
|
||||
class WSPathComponent:
|
||||
"""Base class for WS path component extractors"""
|
||||
|
||||
def __init__(self):
|
||||
"""Initialize a path component extractor
|
||||
|
||||
Currently this does nothing but that may change in the future.
|
||||
Subclasses should call this to be sure."""
|
||||
pass
|
||||
|
||||
def __str__(self):
|
||||
"""Get the string representation of the path component
|
||||
|
||||
This is used in generating information about the available paths
|
||||
and conform to the following conventions:
|
||||
|
||||
- If a fixed string is being matched, it should be that string.
|
||||
- In all other cases, it should be a description of what is
|
||||
being extracted within angle brackets, for example,
|
||||
'<existing database table name>'.
|
||||
|
||||
This string is also the key in the dictionary callbacks registered
|
||||
with a WSPathParser instance receive to obtain the extracted
|
||||
information."""
|
||||
err = "The '__str__' method must be implemented by subclasses."
|
||||
raise NotImplementedError(err)
|
||||
|
||||
def extract(self, pc, extracted_data):
|
||||
"""Determine if 'pc' matches this path component type
|
||||
|
||||
Returns a WSPathExtractResult object with value set to the
|
||||
extracted value for this path component if the extraction succeeded
|
||||
or error set to an error describing why it did not succeed.
|
||||
|
||||
The 'pc' parameter may have the value 'None' if all path components
|
||||
have been exhausted during previous WS path parsing. This is
|
||||
to allow path component types that are optional at the end
|
||||
of a WS.
|
||||
|
||||
The extracted_data parameter contains data extracted
|
||||
from earlier path components, which can be used during the
|
||||
extraction if needed. It is a dictionary keyed by the
|
||||
str(path_component) for each previous path component."""
|
||||
err = "The 'extract' method must be implemented by subclasses."
|
||||
raise NotImplementedError(err)
|
||||
|
||||
|
||||
class WSPathStaticString(WSPathComponent):
|
||||
"""Match a static string in the WS path, possibly case insensitive."""
|
||||
|
||||
def __init__(self, str, case_insensitive=False):
|
||||
WSPathComponent.__init__(self)
|
||||
self.case_insensitive = case_insensitive
|
||||
if case_insensitive:
|
||||
self.str = str.lower()
|
||||
else:
|
||||
self.str = str
|
||||
|
||||
def __str__(self):
|
||||
return self.str
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == None:
|
||||
return WSPathExtractResult(error="End of requested URI")
|
||||
|
||||
if self.case_insensitive:
|
||||
if pc.lower() == self.str:
|
||||
return WSPathExtractResult(value=pc)
|
||||
else:
|
||||
if pc == self.str:
|
||||
return WSPathExtractResult(value=pc)
|
||||
return WSPathExtractResult(error="'%s' != '%s'" % (pc, self.str))
|
||||
|
||||
|
||||
class WSPathRegex(WSPathComponent):
|
||||
"""Match a regex in the WS path.
|
||||
|
||||
This can not be used directly but must be subclassed. Typically
|
||||
the only thing a subclass must override is the '__str__'
|
||||
method.
|
||||
|
||||
The value returned from the 'extract' method is the python regular
|
||||
expression match object, from subgroups in the expression can be
|
||||
examined, etc."""
|
||||
def __init__(self, regexp):
|
||||
WSPathComponent.__init__(self)
|
||||
self.re = re.compile(regexp)
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == None:
|
||||
return WSPathExtractResult(error="End of requested URI")
|
||||
m = re.match(pc)
|
||||
if m == None:
|
||||
return WSPathExtractResult(error="Regexp did not match: %s" %
|
||||
self.re.pattern)
|
||||
return WSPathExtractResult(value=m)
|
||||
|
||||
|
||||
class WSPathTrailingSlash(WSPathComponent):
|
||||
"""Match a null string at a location in the WS path.
|
||||
|
||||
This is typically used at the end of a WS path to require a
|
||||
trailing slash."""
|
||||
|
||||
def __init__(self):
|
||||
WSPathComponent.__init__(self)
|
||||
|
||||
def __str__(self):
|
||||
return "/"
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == "":
|
||||
return WSPathExtractResult(True)
|
||||
else:
|
||||
return WSPathExtractResult(
|
||||
error="Data following expected trailing slash")
|
||||
|
||||
|
||||
# match any string, and retrieve it by 'name'
|
||||
# (e.g., WSPathArbitraryString('<hostname>')
|
||||
class WSPathArbitraryString(WSPathComponent):
|
||||
def __init__(self, name):
|
||||
WSPathComponent.__init__(self)
|
||||
self._name = name
|
||||
|
||||
def __str__(self):
|
||||
return self._name
|
||||
|
||||
def extract(self, pc, data):
|
||||
if pc == None:
|
||||
return WSPathExtractResult(error="End of requested URI")
|
||||
return WSPathExtractResult(unicode(pc, 'utf-8'))
|
||||
|
||||
|
||||
class WSRequest:
|
||||
|
||||
def __init__(self, env, start_response):
|
||||
self.env = env
|
||||
self.start_response = start_response
|
||||
self.version = None
|
||||
|
||||
req = Request(env)
|
||||
self.method = req.method
|
||||
self.path = req.path
|
||||
self.segs = [s for s in self.path.split('/') if s]
|
||||
|
||||
self.rsp = Response(status=200)
|
||||
|
||||
try:
|
||||
version_str = self.segs[0]
|
||||
except IndexError:
|
||||
return
|
||||
|
||||
p = re.compile('^v(?P<ver>.+)$')
|
||||
m = p.match(version_str)
|
||||
if m:
|
||||
self.version = m.group('ver')
|
||||
|
||||
self.prepath = [version_str]
|
||||
self.postpath = self.segs[1:]
|
||||
|
||||
def setHeader(self, name, value):
|
||||
self.rsp.headers[name] = value
|
||||
|
||||
def setResponseCode(self, code, message=None):
|
||||
if not isinstance(code, (int, long)):
|
||||
raise TypeError("HTTP response code must be int or long")
|
||||
if message:
|
||||
self.rsp.status = str(code) + " " + message
|
||||
else:
|
||||
self.rsp.status = code
|
||||
|
||||
def sendResponse(self, body):
|
||||
self.rsp.body = body
|
||||
return self.rsp(self.env, self.start_response)
|
||||
|
||||
|
||||
class WSRes:
|
||||
|
||||
def _get_interface_doc(self, request, arg):
|
||||
request.setHeader("Content-Type", "text/plain")
|
||||
return self.mgr.interface_doc("/" + "/".join(request.prepath))
|
||||
|
||||
def __init__(self, version='1.0'):
|
||||
self.version = version
|
||||
self.mgr = WSRequestHandler()
|
||||
self.register_request(self._get_interface_doc,
|
||||
"GET", (WSPathStaticString("doc"),),
|
||||
"""Get a summary of requests supported by this
|
||||
web service interface.""")
|
||||
|
||||
def register_request(self, handler, request_method, path_components, doc):
|
||||
self.mgr.register(handler, request_method, path_components, doc)
|
||||
|
||||
def render(self, request):
|
||||
return self.mgr.handle(request)
|
||||
|
||||
|
||||
class wsapi:
|
||||
|
||||
_versions = {'1.0': WSRes('1.0')}
|
||||
|
||||
@classmethod
|
||||
def get_version(cls, version):
|
||||
return cls._versions[version]
|
||||
|
||||
def application(self, env, start_response):
|
||||
wsreq = WSRequest(env, start_response)
|
||||
if wsreq.version in wsapi._versions:
|
||||
body = wsapi._versions[wsreq.version].render(wsreq)
|
||||
else:
|
||||
body = notFound(wsreq, "")
|
||||
return wsreq.sendResponse(body)
|
||||
|
||||
def __call__(self):
|
||||
server = WSGIServer((FLAGS.wsapi_host, FLAGS.wsapi_port),
|
||||
self.application)
|
||||
server.serve_forever()
|
0
ryu/base/__init__.py
Normal file
45
ryu/base/app_manager.py
Normal file
@ -0,0 +1,45 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import itertools
|
||||
import logging
|
||||
|
||||
from ryu import utils
|
||||
from ryu.controller.handler import register_instance
|
||||
|
||||
LOG = logging.getLogger('ryu.base.app_manager')
|
||||
|
||||
|
||||
class AppManager(object):
|
||||
def __init__(self):
|
||||
self.applications = {}
|
||||
|
||||
def load(self, app_mod_name, *args, **kwargs):
|
||||
# for now, only single instance of a given module
|
||||
# Do we need to support multiple instances?
|
||||
# Yes, maybe for slicing.
|
||||
assert app_mod_name not in self.applications
|
||||
|
||||
cls = utils.import_object(app_mod_name)
|
||||
app = cls(*args, **kwargs)
|
||||
register_instance(app)
|
||||
|
||||
self.applications[app_mod_name] = app
|
||||
|
||||
def load_apps(self, app_lists, *args, **kwargs):
|
||||
for app in itertools.chain.from_iterable([app_list.split(',')
|
||||
for app_list in app_lists]):
|
||||
self.load(app, *args, **kwargs)
|
||||
LOG.info('loading app %s', app)
|
14
ryu/controller/__init__.py
Normal file
@ -0,0 +1,14 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
201
ryu/controller/controller.py
Normal file
@ -0,0 +1,201 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import gflags
|
||||
import logging
|
||||
import gevent
|
||||
from gevent.server import StreamServer
|
||||
from gevent.queue import Queue
|
||||
|
||||
from ryu.ofproto import ofproto
|
||||
from ryu.ofproto import ofproto_parser
|
||||
from ryu.ofproto import ofproto_v1_0
|
||||
from ryu.ofproto import ofproto_v1_0_parser
|
||||
|
||||
from ryu.controller import dispatcher
|
||||
from ryu.controller import event
|
||||
from ryu.controller import handler
|
||||
from ryu.lib.mac import haddr_to_bin
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.controller')
|
||||
|
||||
FLAGS = gflags.FLAGS
|
||||
gflags.DEFINE_string('ofp_listen_host', '', 'openflow listen host')
|
||||
gflags.DEFINE_integer('ofp_tcp_listen_port', ofproto.OFP_TCP_PORT,
|
||||
'openflow tcp listen port')
|
||||
|
||||
|
||||
class OpenFlowController(object):
|
||||
def __init__(self):
|
||||
super(OpenFlowController, self).__init__()
|
||||
|
||||
# entry point
|
||||
def __call__(self):
|
||||
#LOG.debug('call')
|
||||
self.server_loop()
|
||||
|
||||
def server_loop(self):
|
||||
server = StreamServer((FLAGS.ofp_listen_host,
|
||||
FLAGS.ofp_tcp_listen_port),
|
||||
DatapathConnectionFactory)
|
||||
#LOG.debug('loop')
|
||||
server.serve_forever()
|
||||
|
||||
|
||||
def _deactivate(method):
|
||||
def deactivate(self):
|
||||
try:
|
||||
method(self)
|
||||
finally:
|
||||
self.is_active = False
|
||||
return deactivate
|
||||
|
||||
|
||||
class Datapath(object):
|
||||
supported_ofp_version = {
|
||||
ofproto_v1_0.OFP_VERSION: (ofproto_v1_0,
|
||||
ofproto_v1_0_parser),
|
||||
}
|
||||
default_ofp_version = ofproto_v1_0.OFP_VERSION
|
||||
|
||||
def __init__(self, socket, address):
|
||||
super(Datapath, self).__init__()
|
||||
|
||||
self.socket = socket
|
||||
self.address = address
|
||||
self.is_active = True
|
||||
|
||||
# XIX limit queue size somehow to prevent it from eating memory up
|
||||
self.recv_q = Queue()
|
||||
self.send_q = Queue()
|
||||
|
||||
self.ev_q = dispatcher.EventQueue(handler.handshake_dispatcher)
|
||||
|
||||
self.version_sent = None
|
||||
self.version_recv = None
|
||||
self.version_used = None
|
||||
self.set_version(self.default_ofp_version)
|
||||
self.id = None # datapath_id is unknown yet
|
||||
self.ports = None
|
||||
|
||||
def set_version(self, version):
|
||||
assert version in self.supported_ofp_version
|
||||
self.ofproto, self.ofproto_parser = self.supported_ofp_version[version]
|
||||
|
||||
# Low level socket handling layer
|
||||
@_deactivate
|
||||
def _recv_loop(self):
|
||||
buf = bytearray()
|
||||
required_len = ofproto.OFP_HEADER_SIZE
|
||||
|
||||
while self.is_active:
|
||||
ret = self.socket.recv(ofproto.OFP_MSG_SIZE_MAX)
|
||||
if len(ret) == 0:
|
||||
self.is_active = False
|
||||
break
|
||||
buf += ret
|
||||
while len(buf) >= required_len:
|
||||
(version, msg_type, msg_len, xid) = ofproto_parser.header(buf)
|
||||
required_len = msg_len
|
||||
if len(buf) < required_len:
|
||||
break
|
||||
|
||||
msg = ofproto_parser.msg(self,
|
||||
version, msg_type, msg_len, xid, buf)
|
||||
#LOG.debug('queue msg %s cls %s', msg, msg.__class__)
|
||||
self.recv_q.put(msg)
|
||||
|
||||
buf = buf[required_len:]
|
||||
required_len = ofproto.OFP_HEADER_SIZE
|
||||
|
||||
@_deactivate
|
||||
def _send_loop(self):
|
||||
while self.is_active:
|
||||
buf = self.send_q.get()
|
||||
self.socket.sendall(buf)
|
||||
|
||||
def send(self, buf):
|
||||
self.send_q.put(buf)
|
||||
|
||||
def send_msg(self, msg):
|
||||
assert isinstance(msg, self.ofproto_parser.MsgBase)
|
||||
msg.serialize()
|
||||
# LOG.debug('send_msg %s', msg)
|
||||
self.send(msg.buf)
|
||||
|
||||
def serve(self):
|
||||
send_thr = gevent.spawn(self._send_loop)
|
||||
ev_thr = gevent.spawn(self._event_loop)
|
||||
|
||||
# send hello message immediately
|
||||
self.version_sent = self.ofproto.OFP_VERSION
|
||||
hello = self.ofproto_parser.OFPHello(self)
|
||||
self.send_msg(hello)
|
||||
|
||||
self._recv_loop()
|
||||
gevent.joinall([ev_thr, send_thr])
|
||||
|
||||
@_deactivate
|
||||
def _event_loop(self):
|
||||
while self.is_active:
|
||||
msg = self.recv_q.get()
|
||||
#LOG.debug('_event_loop ev %s cls %s', msg, msg.__class__)
|
||||
self.ev_q.queue(event.ofp_msg_to_ev(msg))
|
||||
|
||||
def send_ev(self, ev):
|
||||
#LOG.debug('send_ev %s', ev)
|
||||
self.ev_q.queue(ev)
|
||||
|
||||
#
|
||||
# Utility methods for convenience
|
||||
#
|
||||
def send_packet_out(self, buffer_id=0xffffffff, in_port=None,
|
||||
actions=None, data=None):
|
||||
if in_port is None:
|
||||
in_port = self.ofproto.OFPP_NONE
|
||||
packet_out = self.ofproto_parser.OFPPacketOut(
|
||||
self, buffer_id, in_port, actions, data)
|
||||
self.send_msg(packet_out)
|
||||
|
||||
def send_flow_mod(self, match, cookie, command, idle_timeout, hard_timeout,
|
||||
priority, buffer_id=0xffffffff,
|
||||
out_port=None, flags=0, actions=None):
|
||||
if out_port is None:
|
||||
out_port = self.ofproto.OFPP_NONE
|
||||
flow_mod = self.ofproto_parser.OFPFlowMod(
|
||||
self, match, cookie, command, idle_timeout, hard_timeout,
|
||||
priority, buffer_id, out_port, flags, actions)
|
||||
self.send_msg(flow_mod)
|
||||
|
||||
def send_delete_all_flows(self):
|
||||
addr = haddr_to_bin('00:00:00:00:00:00')
|
||||
match = self.ofproto_parser.OFPMatch(self.ofproto.OFPFW_ALL,
|
||||
0, addr, addr, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0)
|
||||
self.send_flow_mod(
|
||||
match=match, cookie=0, command=self.ofproto.OFPFC_DELETE,
|
||||
idle_timeout=0, hard_timeout=0, priority=0, buffer_id=0,
|
||||
out_port=self.ofproto.OFPP_NONE, flags=0, actions=None)
|
||||
|
||||
def send_barrier(self):
|
||||
barrier_request = self.ofproto_parser.OFPBarrierRequest(self)
|
||||
self.send_msg(barrier_request)
|
||||
|
||||
|
||||
def DatapathConnectionFactory(socket, address):
|
||||
LOG.debug('connected socket:%s address:%s', socket, address)
|
||||
|
||||
datapath = Datapath(socket, address)
|
||||
datapath.serve()
|
108
ryu/controller/dispatcher.py
Normal file
@ -0,0 +1,108 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import copy
|
||||
import logging
|
||||
from gevent import queue
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.dispatcher')
|
||||
|
||||
|
||||
class EventQueue(object):
|
||||
def __init__(self, dispatcher):
|
||||
self.dispatcher = dispatcher
|
||||
self.is_dispatching = False
|
||||
self.ev_q = queue.Queue()
|
||||
|
||||
def set_dispatcher(self, dispatcher):
|
||||
self.dispatcher = dispatcher
|
||||
|
||||
def queue_raw(self, ev):
|
||||
self.ev_q.put(ev)
|
||||
|
||||
class _EventQueueGuard(object):
|
||||
def __init__(self, ev_q):
|
||||
self.ev_q = ev_q
|
||||
|
||||
def __enter__(self):
|
||||
self.ev_q.is_dispatching = True
|
||||
|
||||
def __exit__(self, type, value, traceback):
|
||||
self.ev_q.is_dispatching = False
|
||||
return False
|
||||
|
||||
def queue(self, ev):
|
||||
if self.is_dispatching:
|
||||
self.queue_raw(ev)
|
||||
return
|
||||
|
||||
with self._EventQueueGuard(self):
|
||||
assert self.ev_q.empty()
|
||||
|
||||
self.dispatcher(ev)
|
||||
while not self.ev_q.empty():
|
||||
ev = self.ev_q.get()
|
||||
self.dispatcher(ev)
|
||||
|
||||
|
||||
class EventDispatcher(object):
|
||||
def __init__(self, name):
|
||||
self.name = name
|
||||
self.events = {}
|
||||
|
||||
def register_handler(self, ev_cls, handler):
|
||||
assert callable(handler)
|
||||
self.events.setdefault(ev_cls, [])
|
||||
self.events[ev_cls].append(handler)
|
||||
|
||||
def register_handlers(self, handlers):
|
||||
for ev_cls, h in handlers:
|
||||
self.register_handler(ev_cls, h)
|
||||
|
||||
def unregister_handler(self, ev_cls, handler):
|
||||
del self.events[ev_cls][handler]
|
||||
|
||||
def register_static(self, ev_cls):
|
||||
'''helper decorator to statically register handler for event class'''
|
||||
def register(handler):
|
||||
'''helper decorator to register handler statically '''
|
||||
if isinstance(handler, staticmethod):
|
||||
# class staticmethod is not callable.
|
||||
handler = handler.__func__
|
||||
self.register_handler(ev_cls, handler)
|
||||
return handler
|
||||
return register
|
||||
|
||||
def __call__(self, ev):
|
||||
self.dispatch(ev)
|
||||
|
||||
def dispatch(self, ev):
|
||||
#LOG.debug('dispatch %s', ev)
|
||||
if ev.__class__ not in self.events:
|
||||
LOG.info('unhandled event %s', ev)
|
||||
return
|
||||
|
||||
# Is this necessary?
|
||||
#
|
||||
# copy handler list because the list is not stable.
|
||||
# event handler may block/switch thread execution
|
||||
# and un/register other handlers.
|
||||
#
|
||||
handlers = copy.copy(self.events[ev.__class__])
|
||||
|
||||
for h in handlers:
|
||||
ret = h(ev)
|
||||
if ret is False:
|
||||
break
|
76
ryu/controller/event.py
Normal file
@ -0,0 +1,76 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import inspect
|
||||
|
||||
|
||||
class EventBase(object):
|
||||
# Nothing yet
|
||||
pass
|
||||
|
||||
|
||||
class EventOFPMsgBase(EventBase):
|
||||
def __init__(self, msg):
|
||||
self.msg = msg
|
||||
|
||||
|
||||
#
|
||||
# Create event type corresponding to OFP Msg
|
||||
#
|
||||
|
||||
_OFP_MSG_EVENTS = {}
|
||||
|
||||
|
||||
def _ofp_msg_name_to_ev_name(msg_name):
|
||||
return 'Event' + msg_name
|
||||
|
||||
|
||||
def ofp_msg_to_ev(msg):
|
||||
name = _ofp_msg_name_to_ev_name(msg.__class__.__name__)
|
||||
return _OFP_MSG_EVENTS[name](msg)
|
||||
|
||||
|
||||
def _create_ofp_msg_ev_class(msg_cls):
|
||||
name = _ofp_msg_name_to_ev_name(msg_cls.__name__)
|
||||
# print 'creating event %s' % name
|
||||
|
||||
if name in _OFP_MSG_EVENTS:
|
||||
return
|
||||
|
||||
cls = type(name, (EventOFPMsgBase,),
|
||||
dict(__init__=lambda self, msg:
|
||||
super(self.__class__, self).__init__(msg)))
|
||||
globals()[name] = cls
|
||||
_OFP_MSG_EVENTS[name] = cls
|
||||
|
||||
|
||||
def _create_ofp_msg_ev_from_module(modname):
|
||||
(f, s, t) = modname.rpartition('.')
|
||||
mod = __import__(modname, fromlist=[f])
|
||||
print mod
|
||||
for k, cls in mod.__dict__.items():
|
||||
if not inspect.isclass(cls):
|
||||
continue
|
||||
if 'cls_msg_type' not in cls.__dict__:
|
||||
continue
|
||||
_create_ofp_msg_ev_class(cls)
|
||||
|
||||
|
||||
# TODO:XXX
|
||||
_PARSER_MODULE_LIST = ['ryu.ofproto.ofproto_v1_0_parser']
|
||||
|
||||
for m in _PARSER_MODULE_LIST:
|
||||
# print 'loading module %s' % m
|
||||
_create_ofp_msg_ev_from_module(m)
|
219
ryu/controller/handler.py
Normal file
@ -0,0 +1,219 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import copy
|
||||
import inspect
|
||||
import logging
|
||||
import struct
|
||||
|
||||
from ryu.controller import event
|
||||
from ryu.controller import dispatcher
|
||||
from ryu.lib.mac import haddr_to_bin
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.handler')
|
||||
|
||||
handshake_dispatcher = dispatcher.EventDispatcher('handshake')
|
||||
config_dispatcher = dispatcher.EventDispatcher('config')
|
||||
main_dispatcher = dispatcher.EventDispatcher('main')
|
||||
|
||||
|
||||
def set_ev_cls(ev_cls, dispatchers=None):
|
||||
def _set_ev_cls_dec(handler):
|
||||
handler.ev_cls = ev_cls
|
||||
if dispatchers is not None:
|
||||
handler.dispatchers = dispatchers
|
||||
return handler
|
||||
return _set_ev_cls_dec
|
||||
|
||||
|
||||
def _is_ev_handler(meth):
|
||||
return 'ev_cls' in meth.__dict__
|
||||
|
||||
|
||||
def _listify(may_list):
|
||||
if may_list is None:
|
||||
may_list = []
|
||||
if not isinstance(may_list, list):
|
||||
may_list = [may_list]
|
||||
return may_list
|
||||
|
||||
|
||||
def _get_hnd_spec_dispatchers(handler, dispatchers):
|
||||
hnd_spec_dispatchers = _listify(getattr(handler, 'dispatchers', None))
|
||||
# LOG.debug("hnd_spec_dispatchers %s", hnd_spec_dispatchers)
|
||||
if hnd_spec_dispatchers:
|
||||
_dispatchers = copy.copy(dispatchers)
|
||||
_dispatchers.extend(hnd_spec_dispatchers)
|
||||
else:
|
||||
_dispatchers = dispatchers
|
||||
|
||||
return _dispatchers
|
||||
|
||||
|
||||
def register_cls(dispatchers=None):
|
||||
dispatchers = _listify(dispatchers)
|
||||
|
||||
def _register_cls_method(cls):
|
||||
for k, f in inspect.getmembers(cls, inspect.isfunction):
|
||||
# LOG.debug('cls %s k %s f %s', cls, k, f)
|
||||
if not _is_ev_handler(f):
|
||||
continue
|
||||
|
||||
_dispatchers = _get_hnd_spec_dispatchers(f, dispatchers)
|
||||
# LOG.debug("_dispatchers %s", _dispatchers)
|
||||
for d in _dispatchers:
|
||||
# LOG.debug('register dispatcher %s ev %s cls %s k %s f %s',
|
||||
# d.name, f.ev_cls, cls, k, f)
|
||||
d.register_handler(f.ev_cls, f)
|
||||
|
||||
return _register_cls_method
|
||||
|
||||
|
||||
def register_instance(i, dispatchers=None):
|
||||
dispatchers = _listify(dispatchers)
|
||||
|
||||
for k, m in inspect.getmembers(i, inspect.ismethod):
|
||||
# LOG.debug('instance %s k %s m %s', i, k, m)
|
||||
if not _is_ev_handler(m):
|
||||
continue
|
||||
|
||||
_dispatchers = _get_hnd_spec_dispatchers(m, dispatchers)
|
||||
# LOG.debug("_dispatchers %s", _dispatchers)
|
||||
for d in _dispatchers:
|
||||
# LOG.debug('register dispatcher %s ev %s k %s m %s',
|
||||
# d.name, m.ev_cls, k, m)
|
||||
d.register_handler(m.ev_cls, m)
|
||||
|
||||
|
||||
@register_cls([handshake_dispatcher, config_dispatcher, main_dispatcher])
|
||||
class EchoHandler(object):
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPEchoRequest)
|
||||
def echo_request_handler(ev):
|
||||
msg = ev.msg
|
||||
# LOG.debug('echo request msg %s %s', msg, str(msg.data))
|
||||
datapath = msg.datapath
|
||||
echo_reply = datapath.ofproto_parser.OFPEchoReply(datapath)
|
||||
echo_reply.data = msg.data
|
||||
datapath.send_msg(echo_reply)
|
||||
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPEchoReply)
|
||||
def echo_reply_handler(ev):
|
||||
# do nothing
|
||||
# msg = ev.msg
|
||||
# LOG.debug('echo reply ev %s %s', msg, str(msg.data))
|
||||
pass
|
||||
|
||||
|
||||
@register_cls([handshake_dispatcher, config_dispatcher, main_dispatcher])
|
||||
class ErrorMsgHandler(object):
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPErrorMsg)
|
||||
def error_msg_handler(ev):
|
||||
msg = ev.msg
|
||||
LOG.debug('error msg ev %s type 0x%x code 0x%x %s',
|
||||
msg, msg.type, msg.code, str(msg.data))
|
||||
msg.datapath.is_active = False
|
||||
|
||||
|
||||
@register_cls(handshake_dispatcher)
|
||||
class HandShakeHandler(object):
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPHello)
|
||||
def hello_handler(ev):
|
||||
LOG.debug('hello ev %s', ev)
|
||||
msg = ev.msg
|
||||
datapath = msg.datapath
|
||||
|
||||
# TODO: check if received version is supported.
|
||||
# pre 1.0 is not supported
|
||||
if msg.version not in datapath.supported_ofp_version:
|
||||
# send the error
|
||||
error_msg = datapath.ofproto_parser.OFPErrorMsg(datapath)
|
||||
error_msg.type = datapath.ofproto.OFPET_HELLO_FAILED
|
||||
error_msg.code = datapath.ofproto.OFPHFC_INCOMPATIBLE
|
||||
error_msg.data = 'unsupported version 0x%x' % msg.version
|
||||
datapath.send_msg(error_msg)
|
||||
return
|
||||
|
||||
datapath.version = min(datapath.version_sent, msg.version)
|
||||
datapath.set_version(datapath.version)
|
||||
|
||||
# now send feature
|
||||
features_reqeust = datapath.ofproto_parser.OFPFeaturesRequest(datapath)
|
||||
datapath.send_msg(features_reqeust)
|
||||
|
||||
# now move on to config state
|
||||
LOG.debug('move onto config mode')
|
||||
datapath.ev_q.set_dispatcher(config_dispatcher)
|
||||
|
||||
|
||||
@register_cls(config_dispatcher)
|
||||
class ConfigHandler(object):
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPSwitchFeatures)
|
||||
def switch_features_handler(ev):
|
||||
msg = ev.msg
|
||||
datapath = msg.datapath
|
||||
LOG.debug('switch features ev %s', msg)
|
||||
|
||||
datapath.id = msg.datapath_id
|
||||
datapath.ports = msg.ports
|
||||
|
||||
ofproto = datapath.ofproto
|
||||
ofproto_parser = datapath.ofproto_parser
|
||||
set_config = ofproto_parser.OFPSetConfig(
|
||||
datapath, ofproto.OFPC_FRAG_NORMAL,
|
||||
128 # TODO:XXX
|
||||
)
|
||||
datapath.send_msg(set_config)
|
||||
|
||||
#
|
||||
# drop all flows in order to put datapath into unknown state
|
||||
#
|
||||
datapath.send_delete_all_flows()
|
||||
|
||||
datapath.send_barrier()
|
||||
|
||||
# The above OFPC_DELETE request may trigger flow removed event.
|
||||
# Just ignore them.
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPFlowRemoved)
|
||||
def flow_removed_handler(ev):
|
||||
LOG.debug("flow removed ev %s msg %s", ev, ev.msg)
|
||||
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPBarrierReply)
|
||||
def barrier_reply_handler(ev):
|
||||
LOG.debug('barrier reply ev %s msg %s', ev, ev.msg)
|
||||
|
||||
# move on to main state
|
||||
LOG.debug('move onto main mode')
|
||||
ev.msg.datapath.ev_q.set_dispatcher(main_dispatcher)
|
||||
|
||||
|
||||
@register_cls(main_dispatcher)
|
||||
class MainHandler(object):
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPFlowRemoved)
|
||||
def flow_removed_handler(ev):
|
||||
msg = ev.msg
|
||||
|
||||
@staticmethod
|
||||
@set_ev_cls(event.EventOFPPortStatus)
|
||||
def port_status_handler(ev):
|
||||
msg = ev.msg
|
||||
LOG.debug('port status %s', msg.reason)
|
56
ryu/controller/mac_to_network.py
Normal file
@ -0,0 +1,56 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
|
||||
from ryu.exception import MacAddressDuplicated
|
||||
from ryu.lib.mac import haddr_to_str
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.mac_to_network')
|
||||
|
||||
|
||||
class MacToNetwork(object):
|
||||
def __init__(self, nw):
|
||||
self.mac_to_net = {}
|
||||
self.dpid = {}
|
||||
self.nw = nw
|
||||
|
||||
def get_network(self, mac, default=None):
|
||||
return self.mac_to_net.get(mac, default)
|
||||
|
||||
def add_mac(self, mac, nw_id, nw_id_external=None):
|
||||
_nw_id = self.mac_to_net.get(mac)
|
||||
if _nw_id == nw_id:
|
||||
return
|
||||
|
||||
# allow changing from nw_id_external to known nw id
|
||||
if _nw_id is None or _nw_id == nw_id_external:
|
||||
self.mac_to_net[mac] = nw_id
|
||||
LOG.debug('overwrite nw_id: mac %s nw old %s new %s',
|
||||
haddr_to_str(mac), _nw_id, nw_id)
|
||||
return
|
||||
|
||||
if nw_id == nw_id_external:
|
||||
# this can happens when the packet traverses
|
||||
# VM-> tap-> ovs-> ext-port-> wire-> ext-port-> ovs-> tap-> VM
|
||||
return
|
||||
|
||||
LOG.warn('duplicated nw_id: mac %s nw old %s new %s',
|
||||
haddr_to_str(mac), _nw_id, nw_id)
|
||||
|
||||
raise MacAddressDuplicated(mac=mac)
|
||||
|
||||
def del_mac(self, mac):
|
||||
del self.mac_to_net[mac]
|
48
ryu/controller/mac_to_port.py
Normal file
@ -0,0 +1,48 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
from ryu.lib.mac import haddr_to_str
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.mac_to_port')
|
||||
|
||||
|
||||
class MacToPortTable(object):
|
||||
"""MAC addr <-> (dpid, port name)"""
|
||||
|
||||
def __init__(self):
|
||||
self.mac_to_port = {}
|
||||
|
||||
def dpid_add(self, dpid):
|
||||
LOG.debug('dpid_add: 0x%016x', dpid)
|
||||
self.mac_to_port.setdefault(dpid, {})
|
||||
|
||||
def port_add(self, dpid, port, mac):
|
||||
"""
|
||||
:returns: old port if learned. (this may be = port)
|
||||
None otherwise
|
||||
"""
|
||||
old_port = self.mac_to_port[dpid].get(mac, None)
|
||||
self.mac_to_port[dpid][mac] = port
|
||||
|
||||
if old_port is not None and old_port != port:
|
||||
LOG.debug('port_add: 0x%016x 0x%04x %s',
|
||||
dpid, port, haddr_to_str(mac))
|
||||
|
||||
return old_port
|
||||
|
||||
def port_get(self, dpid, mac):
|
||||
# LOG.debug('dpid 0x%016x mac %s', dpid, haddr_to_str(mac))
|
||||
return self.mac_to_port[dpid].get(mac)
|
155
ryu/controller/network.py
Normal file
@ -0,0 +1,155 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
|
||||
from ryu.exception import NetworkNotFound, NetworkAlreadyExist
|
||||
from ryu.exception import PortAlreadyExist, PortNotFound, PortUnknown
|
||||
from ryu.app.rest_nw_id import NW_ID_UNKNOWN
|
||||
|
||||
LOG = logging.getLogger('ryu.controller.network')
|
||||
|
||||
|
||||
class network(object):
|
||||
def __init__(self, nw_id_unknown=NW_ID_UNKNOWN):
|
||||
self.nw_id_unknown = nw_id_unknown
|
||||
self.networks = {}
|
||||
self.dpids = {}
|
||||
|
||||
def _check_nw_id_unknown(self, network_id):
|
||||
if network_id == self.nw_id_unknown:
|
||||
raise NetworkAlreadyExist(network_id=network_id)
|
||||
|
||||
def list_networks(self):
|
||||
return self.networks.keys()
|
||||
|
||||
def update_network(self, network_id):
|
||||
self._check_nw_id_unknown(network_id)
|
||||
self.networks.setdefault(network_id, set())
|
||||
|
||||
def create_network(self, network_id):
|
||||
self._check_nw_id_unknown(network_id)
|
||||
if network_id in self.networks:
|
||||
raise NetworkAlreadyExist(network_id=network_id)
|
||||
|
||||
self.networks[network_id] = set()
|
||||
|
||||
def remove_network(self, network_id):
|
||||
try:
|
||||
del(self.networks[network_id])
|
||||
except KeyError:
|
||||
raise NetworkNotFound(network_id=network_id)
|
||||
|
||||
def list_ports(self, network_id):
|
||||
try:
|
||||
# use list() to keep compatibility for output
|
||||
# set() isn't json serializable
|
||||
return list(self.networks[network_id])
|
||||
except KeyError:
|
||||
raise NetworkNotFound(network_id=network_id)
|
||||
|
||||
def _update_port(self, network_id, dpid, port, port_may_exist):
|
||||
def _known_nw_id(nw_id):
|
||||
return nw_id is not None and nw_id != self.nw_id_unknown
|
||||
|
||||
self._check_nw_id_unknown(network_id)
|
||||
try:
|
||||
old_network_id = self.dpids.get(dpid, {}).get(port, None)
|
||||
if ((dpid, port) in self.networks[network_id] or
|
||||
_known_nw_id(old_network_id)):
|
||||
if not port_may_exist:
|
||||
raise PortAlreadyExist(network_id=network_id,
|
||||
dpid=dpid, port=port)
|
||||
|
||||
if old_network_id != network_id:
|
||||
self.networks[network_id].add((dpid, port))
|
||||
if _known_nw_id(old_network_id):
|
||||
self.networks[old_network_id].remove((dpid, port))
|
||||
except KeyError:
|
||||
raise NetworkNotFound(network_id=network_id)
|
||||
|
||||
self.dpids.setdefault(dpid, {})
|
||||
self.dpids[dpid][port] = network_id
|
||||
|
||||
def create_port(self, network_id, dpid, port):
|
||||
self._update_port(network_id, dpid, port, False)
|
||||
|
||||
def update_port(self, network_id, dpid, port):
|
||||
self._update_port(network_id, dpid, port, True)
|
||||
|
||||
def remove_port(self, network_id, dpid, port):
|
||||
try:
|
||||
self.networks[network_id].remove((dpid, port))
|
||||
except KeyError:
|
||||
raise NetworkNotFound(network_id=network_id)
|
||||
except ValueError:
|
||||
raise PortNotFound(network_id=network_id, dpid=dpid, port=port)
|
||||
|
||||
del self.dpids[dpid][port]
|
||||
|
||||
def same_network(self, dpid, nw_id, out_port, allow_nw_id_external=None):
|
||||
assert nw_id != self.nw_id_unknown
|
||||
dp = self.dpids.get(dpid, {})
|
||||
out_nw = dp.get(out_port)
|
||||
|
||||
if nw_id == out_nw:
|
||||
return True
|
||||
|
||||
if (allow_nw_id_external is not None and
|
||||
(allow_nw_id_external == nw_id or allow_nw_id_external == out_nw)):
|
||||
# allow external network -> known network id
|
||||
return True
|
||||
|
||||
LOG.debug('blocked dpid %s nw_id %s out_port %d out_nw %s'
|
||||
'external %s',
|
||||
dpid, nw_id, out_port, out_nw, allow_nw_id_external)
|
||||
return False
|
||||
|
||||
def get_network(self, dpid, port):
|
||||
try:
|
||||
return self.dpids[dpid][port]
|
||||
except KeyError:
|
||||
raise PortUnknown(dpid=dpid, port=port)
|
||||
|
||||
def add_datapath(self, ofp_switch_features):
|
||||
datapath = ofp_switch_features.datapath
|
||||
dpid = ofp_switch_features.datapath_id
|
||||
ports = ofp_switch_features.ports
|
||||
self.dpids.setdefault(dpid, {})
|
||||
dp = self.dpids[dpid]
|
||||
for port_no in ports:
|
||||
if port_no == 0 or port_no >= datapath.ofproto.OFPP_MAX:
|
||||
# skip fake output ports
|
||||
continue
|
||||
|
||||
if port_no not in dp:
|
||||
dp[port_no] = self.nw_id_unknown
|
||||
|
||||
def filter_ports(self, dpid, in_port, nw_id, allow_nw_id_external=None):
|
||||
assert nw_id != self.nw_id_unknown
|
||||
ret = []
|
||||
|
||||
ports = self.dpids.get(dpid, {})
|
||||
for port_no, _nw_id in ports.items():
|
||||
if port_no == in_port:
|
||||
continue
|
||||
|
||||
if _nw_id == nw_id:
|
||||
ret.append(port_no)
|
||||
elif (allow_nw_id_external is not None and
|
||||
_nw_id == allow_nw_id_external):
|
||||
ret.append(port_no)
|
||||
|
||||
return ret
|
63
ryu/exception.py
Normal file
@ -0,0 +1,63 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
class RyuException(Exception):
|
||||
message = 'An unknown exception'
|
||||
|
||||
def __init__(self, msg=None, **kwargs):
|
||||
self.kwargs = kwargs
|
||||
if msg is None:
|
||||
msg = self.message
|
||||
|
||||
try:
|
||||
msg = msg % kwargs
|
||||
except Exception as e:
|
||||
msg = self.message
|
||||
|
||||
super(RyuException, self).__init__(msg)
|
||||
|
||||
|
||||
class OFPUnknownVersion(RyuException):
|
||||
message = 'unknown version %(version)x'
|
||||
|
||||
|
||||
class OFPMalformedMessage:
|
||||
message = 'malformed message'
|
||||
|
||||
|
||||
class NetworkNotFound(RyuException):
|
||||
message = 'no such network id %(network_id)s'
|
||||
|
||||
|
||||
class NetworkAlreadyExist(RyuException):
|
||||
message = 'network id %(network_id)s already exists'
|
||||
|
||||
|
||||
class PortNotFound(RyuException):
|
||||
message = 'no such port (%(dpid)s, %(port)s) in network %(network_id)s'
|
||||
|
||||
|
||||
class PortAlreadyExist(RyuException):
|
||||
message = 'port (%(dpid)s, %(port)s) in network %(network_id)s ' \
|
||||
'already exists'
|
||||
|
||||
|
||||
class PortUnknown(RyuException):
|
||||
message = 'unknown network id for port (%(dpid)s %(port)s)'
|
||||
|
||||
|
||||
class MacAddressDuplicated(RyuException):
|
||||
message = 'MAC address %(mac)s is duplicated'
|
24
ryu/flags.py
Normal file
@ -0,0 +1,24 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
"""
|
||||
global flags
|
||||
"""
|
||||
|
||||
import gflags
|
||||
|
||||
FLAGS = gflags.FLAGS
|
||||
|
||||
# GLOBAL flags
|
||||
gflags.DEFINE_boolean('monkey_patch', False, 'do monkey patch')
|
0
ryu/lib/__init__.py
Normal file
23
ryu/lib/mac.py
Normal file
@ -0,0 +1,23 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
def haddr_to_str(addr):
|
||||
return ''.join(['%02x:' % ord(char) for char in addr[0:6]])[:-1]
|
||||
|
||||
|
||||
def haddr_to_bin(string):
|
||||
return ''.join(['%c' % chr(int(i, 16)) for i in
|
||||
string.split(':')])
|
82
ryu/log.py
Normal file
@ -0,0 +1,82 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import gflags
|
||||
import inspect
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
|
||||
FLAGS = gflags.FLAGS
|
||||
|
||||
gflags.DEFINE_integer('default_log_level', None, 'default log level')
|
||||
gflags.DEFINE_bool('verbose', False, 'show debug output')
|
||||
|
||||
gflags.DEFINE_bool('use_stderr', True, 'log to standard error')
|
||||
gflags.DEFINE_string('use_syslog', False, 'output to syslog')
|
||||
gflags.DEFINE_string('log_dir', None, 'log file directory')
|
||||
gflags.DEFINE_string('log_file', None, 'log file name')
|
||||
gflags.DEFINE_string('log_file_mode', '0644', 'default log file permission')
|
||||
|
||||
|
||||
_early_log_handler = None
|
||||
|
||||
|
||||
def earlyInitLog(level=None):
|
||||
global _early_log_handler
|
||||
_early_log_handler = logging.StreamHandler(sys.stderr)
|
||||
|
||||
log = logging.getLogger()
|
||||
log.addHandler(_early_log_handler)
|
||||
if level is not None:
|
||||
log.setLevel(level)
|
||||
|
||||
|
||||
def _get_log_file():
|
||||
if FLAGS.log_file:
|
||||
return FLAGS.log_file
|
||||
if FLAGS.log_dir:
|
||||
return os.path.join(FLAGS.logdir,
|
||||
os.path.basename(inspect.stack()[-1][1])) + '.log'
|
||||
return None
|
||||
|
||||
|
||||
def initLog():
|
||||
global _early_log_handler
|
||||
|
||||
log = logging.getLogger()
|
||||
if FLAGS.use_stderr:
|
||||
log.addHandler(logging.StreamHandler(sys.stderr))
|
||||
if _early_log_handler is not None:
|
||||
log.removeHandler(_early_log_handler)
|
||||
_early_log_handler = None
|
||||
|
||||
if FLAGS.use_syslog:
|
||||
syslog = logging.handlers.SysLogHandler(address='/dev/log')
|
||||
log.addHandler(syslog)
|
||||
|
||||
log_file = _get_log_file()
|
||||
if log_file is not None:
|
||||
logging.addHandler(logging.handlers.WatchedFileHandler(log_file))
|
||||
mode = int(FLAGS.log_file_mnode, 8)
|
||||
os.chmod(log_file, mode)
|
||||
|
||||
if FLAGS.verbose:
|
||||
log.setLevel(logging.DEBUG)
|
||||
elif FLAGS.default_log_level is not None:
|
||||
log.setLevel(FLAGS.default_log_level)
|
||||
else:
|
||||
log.setLevel(logging.INFO)
|
16
ryu/ofproto/__init__.py
Normal file
@ -0,0 +1,16 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
from . import ofproto_v1_0 as ofproto
|
49
ryu/ofproto/ofproto_parser.py
Normal file
@ -0,0 +1,49 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import logging
|
||||
import struct
|
||||
|
||||
from ryu import exception
|
||||
|
||||
from . import ofproto
|
||||
|
||||
LOG = logging.getLogger('ryu.ofproto.ofproto_parser')
|
||||
|
||||
|
||||
def header(buf):
|
||||
assert len(buf) >= ofproto.OFP_HEADER_SIZE
|
||||
#LOG.debug('len %d bufsize %d', len(buf), ofproto.OFP_HEADER_SIZE)
|
||||
return struct.unpack_from(ofproto.OFP_HEADER_PACK_STR, buffer(buf))
|
||||
|
||||
|
||||
_MSG_PARSERS = {}
|
||||
|
||||
|
||||
def register_msg_parser(version):
|
||||
def register(msg_parser):
|
||||
_MSG_PARSERS[version] = msg_parser
|
||||
return msg_parser
|
||||
return register
|
||||
|
||||
|
||||
def msg(datapath, version, msg_type, msg_len, xid, buf):
|
||||
assert len(buf) >= msg_len
|
||||
|
||||
msg_parser = _MSG_PARSERS.get(version)
|
||||
if msg_parser is None:
|
||||
raise exception.OFPUnknownVersion(version=version)
|
||||
|
||||
return msg_parser(datapath, version, msg_type, msg_len, xid, buf)
|
437
ryu/ofproto/ofproto_v1_0.py
Normal file
@ -0,0 +1,437 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
from struct import calcsize
|
||||
|
||||
# define constants
|
||||
OFP_VERSION = 0x01
|
||||
OFP_MAX_TABLE_NAME_LEN = 32
|
||||
OFP_MAX_TABLE_NAME_LEN_STR = str(OFP_MAX_TABLE_NAME_LEN)
|
||||
OFP_MAX_PORT_NAME_LEN = 16
|
||||
OFP_TCP_PORT = 6633
|
||||
OFP_SSL_PORT = 6633
|
||||
OFP_ETH_ALEN = 6
|
||||
OFP_ETH_ALEN_STR = str(OFP_ETH_ALEN)
|
||||
|
||||
# enum ofp_port
|
||||
OFPP_MAX = 0xff00
|
||||
OFPP_IN_PORT = 0xfff8 # Send the packet out the input port. This
|
||||
# virtual port must be explicitly used
|
||||
# in order to send back out of the input
|
||||
# port.
|
||||
OFPP_TABLE = 0xfff9 # Perform actions in flow table.
|
||||
# NB: This can only be the destination
|
||||
# port for packet-out messages.
|
||||
OFPP_NORMAL = 0xfffa # Process with normal L2/L3 switching.
|
||||
OFPP_FLOOD = 0xfffb # All physical ports except input port and
|
||||
# those disabled by STP.
|
||||
OFPP_ALL = 0xfffc # All physical ports except input port.
|
||||
OFPP_CONTROLLER = 0xfffd # Send to controller.
|
||||
OFPP_LOCAL = 0xfffe # Local openflow "port".
|
||||
OFPP_NONE = 0xffff # Not associated with a physical port.
|
||||
|
||||
# enum ofp_type
|
||||
OFPT_HELLO = 0 # Symmetric message
|
||||
OFPT_ERROR = 1 # Symmetric message
|
||||
OFPT_ECHO_REQUEST = 2 # Symmetric message
|
||||
OFPT_ECHO_REPLY = 3 # Symmetric message
|
||||
OFPT_VENDOR = 4 # Symmetric message
|
||||
OFPT_FEATURES_REQUEST = 5 # Controller/switch message
|
||||
OFPT_FEATURES_REPLY = 6 # Controller/switch message
|
||||
OFPT_GET_CONFIG_REQUEST = 7 # Controller/switch message
|
||||
OFPT_GET_CONFIG_REPLY = 8 # Controller/switch message
|
||||
OFPT_SET_CONFIG = 9 # Controller/switch message
|
||||
OFPT_PACKET_IN = 10 # Async message
|
||||
OFPT_FLOW_REMOVED = 11 # Async message
|
||||
OFPT_PORT_STATUS = 12 # Async message
|
||||
OFPT_PACKET_OUT = 13 # Controller/switch message
|
||||
OFPT_FLOW_MOD = 14 # Controller/switch message
|
||||
OFPT_PORT_MOD = 15 # Controller/switch message
|
||||
OFPT_STATS_REQUEST = 16 # Controller/switch message
|
||||
OFPT_STATS_REPLY = 17 # Controller/switch message
|
||||
OFPT_BARRIER_REQUEST = 18 # Controller/switch message
|
||||
OFPT_BARRIER_REPLY = 19 # Controller/switch message
|
||||
OFPT_QUEUE_GET_CONFIG_REQUEST = 20 # Controller/switch message
|
||||
OFPT_QUEUE_GET_CONFIG_REPLY = 21 # Controller/switch message
|
||||
|
||||
OFP_HEADER_PACK_STR = '!BBHI'
|
||||
OFP_HEADER_SIZE = 8
|
||||
OFP_MSG_SIZE_MAX = 65535
|
||||
assert calcsize(OFP_HEADER_PACK_STR) == OFP_HEADER_SIZE
|
||||
|
||||
# define constants
|
||||
OFP_DEFAULT_MISS_SEND_LEN = 128
|
||||
|
||||
# enum ofp_config_flags
|
||||
OFPC_FRAG_NORMAL = 0 # No special handling for fragments.
|
||||
OFPC_FRAG_DROP = 1 # Drop fragments.
|
||||
OFPC_FRAG_REASM = 2 # Reassemble (only if OFPC_IP_REASM set).
|
||||
OFPC_FRAG_NX_MATCH = 3 # Make first fragments available for matching.
|
||||
OFPC_FRAG_MASK = 3
|
||||
|
||||
OFP_SWITCH_CONFIG_PACK_STR = '!HH'
|
||||
OFP_SWITCH_CONFIG_SIZE = 12
|
||||
assert (calcsize(OFP_SWITCH_CONFIG_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_SWITCH_CONFIG_SIZE)
|
||||
|
||||
# enum ofp_capabilities
|
||||
OFPC_FLOW_STATS = 1 << 0 # Flow statistics.
|
||||
OFPC_TABLE_STATS = 1 << 1 # Table statistics.
|
||||
OFPC_PORT_STATS = 1 << 2 # Port statistics.
|
||||
OFPC_STP = 1 << 3 # 802.1d spanning tree.
|
||||
OFPC_RESERVED = 1 << 4 # Reserved, must not be set.
|
||||
OFPC_IP_REASM = 1 << 5 # Can reassemble IP fragments.
|
||||
OFPC_QUEUE_STATS = 1 << 6 # Queue statistics.
|
||||
OFPC_ARP_MATCH_IP = 1 << 7 # Match IP addresses in ARP pkts.
|
||||
|
||||
# enum ofp_port_config
|
||||
OFPPC_PORT_DOWN = 1 << 0 # Port is administratively down.
|
||||
OFPPC_NO_STP = 1 << 1 # Disable 802.1D spanning tree on port.
|
||||
OFPPC_NO_RECV = 1 << 2 # Drop all packets except 802.1D
|
||||
# spanning tree packets
|
||||
OFPPC_NO_RECV_STP = 1 << 3 # Drop received 802.1D STP packets.
|
||||
OFPPC_NO_FLOOD = 1 << 4 # Do not include this port when flooding.
|
||||
OFPPC_NO_FWD = 1 << 5 # Drop packets forwarded to port.
|
||||
OFPPC_NO_PACKET_IN = 1 << 6 # Do not send packet-in msgs for port.
|
||||
|
||||
# enum ofp_port_state
|
||||
OFPPS_LINK_DOWN = 1 << 0 # No physical link present.
|
||||
OFPPS_STP_LISTEN = 0 << 8 # Not learning or relaying frames.
|
||||
OFPPS_STP_LEARN = 1 << 8 # Learning but not relaying frames.
|
||||
OFPPS_STP_FORWARD = 2 << 8 # Learning and relaying frames.
|
||||
OFPPS_STP_BLOCK = 3 << 8 # Not part of spanning tree.
|
||||
OFPPS_STP_MASK = 3 << 8 # Bit mask for OFPPS_STP_* values.
|
||||
|
||||
# enum ofp_port_features
|
||||
OFPPF_10MB_HD = 1 << 0 # 10 Mb half-duplex rate support.
|
||||
OFPPF_10MB_FD = 1 << 1 # 10 Mb full-duplex rate support.
|
||||
OFPPF_100MB_HD = 1 << 2 # 100 Mb half-duplex rate support.
|
||||
OFPPF_100MB_FD = 1 << 3 # 100 Mb full-duplex rate support.
|
||||
OFPPF_1GB_HD = 1 << 4 # 1 Gb half-duplex rate support.
|
||||
OFPPF_1GB_FD = 1 << 5 # 1 Gb full-duplex rate support.
|
||||
OFPPF_10GB_FD = 1 << 6 # 10 Gb full-duplex rate support.
|
||||
OFPPF_COPPER = 1 << 7 # Copper medium.
|
||||
OFPPF_FIBER = 1 << 8 # Fiber medium.
|
||||
OFPPF_AUTONEG = 1 << 9 # Auto-negotiation.
|
||||
OFPPF_PAUSE = 1 << 10 # Pause.
|
||||
OFPPF_PAUSE_ASYM = 1 << 11 # Asymmetric pause.
|
||||
|
||||
_OFP_PHY_PORT_PACK_STR = 'H' + OFP_ETH_ALEN_STR + 's' + str(OFP_MAX_PORT_NAME_LEN) + 'sIIIIII'
|
||||
OFP_PHY_PORT_PACK_STR = '!' + _OFP_PHY_PORT_PACK_STR
|
||||
OFP_PHY_PORT_SIZE = 48
|
||||
assert calcsize(OFP_PHY_PORT_PACK_STR) == OFP_PHY_PORT_SIZE
|
||||
|
||||
OFP_SWITCH_FEATURES_PACK_STR = '!QIB3xII'
|
||||
OFP_SWITCH_FEATURES_SIZE = 32
|
||||
assert (calcsize(OFP_SWITCH_FEATURES_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_SWITCH_FEATURES_SIZE)
|
||||
|
||||
# enum ofp_port_reason
|
||||
OFPPR_ADD = 0 # The port was added.
|
||||
OFPPR_DELETE = 1 # The port was removed.
|
||||
OFPPR_MODIFY = 2 # Some attribute of the port has changed.
|
||||
|
||||
OFP_PORT_STATUS_PACK_STR = '!B7x' + _OFP_PHY_PORT_PACK_STR
|
||||
OFP_PORT_STATUS_DESC_OFFSET = OFP_HEADER_SIZE + 8
|
||||
OFP_PORT_STATUS_SIZE = 64
|
||||
assert (calcsize(OFP_PORT_STATUS_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_PORT_STATUS_SIZE)
|
||||
|
||||
OFP_PORT_MOD_PACK_STR = '!H' + OFP_ETH_ALEN_STR + 'BIII4x'
|
||||
OFP_PORT_MOD_SIZE = 32
|
||||
assert calcsize(OFP_PORT_MOD_PACK_STR) + OFP_HEADER_SIZE == OFP_PORT_MOD_SIZE
|
||||
|
||||
# enum ofp_packet_in_reason
|
||||
OFPR_NO_MATCH = 0 # No matching flow.
|
||||
OFPR_ACTION = 1 # Action explicitly output to controller.
|
||||
|
||||
OFP_PACKET_IN_PACK_STR = '!IHHBx2x' # the last 2x is for ofp_packet_in::data
|
||||
OFP_PACKET_IN_SIZE = 20
|
||||
OFP_PACKET_IN_DATA_OFFSET = 18
|
||||
assert calcsize(OFP_PACKET_IN_PACK_STR) + OFP_HEADER_SIZE == OFP_PACKET_IN_SIZE
|
||||
|
||||
# enum ofp_action_type
|
||||
OFPAT_OUTPUT = 0 # Output to switch port.
|
||||
OFPAT_SET_VLAN_VID = 1 # Set the 802.1q VLAN id.
|
||||
OFPAT_SET_VLAN_PCP = 2 # Set the 802.1q priority.
|
||||
OFPAT_STRIP_VLAN = 3 # Strip the 802.1q header.
|
||||
OFPAT_SET_DL_SRC = 4 # Ethernet source address.
|
||||
OFPAT_SET_DL_DST = 5 # Ethernet destination address.
|
||||
OFPAT_SET_NW_SRC = 6 # IP source address.
|
||||
OFPAT_SET_NW_DST = 7 # IP destination address.
|
||||
OFPAT_SET_NW_TOS = 8 # IP ToS (DSCP field, 6 bits).
|
||||
OFPAT_SET_TP_SRC = 9 # TCP/UDP source port.
|
||||
OFPAT_SET_TP_DST = 10 # TCP/UDP destination port.
|
||||
OFPAT_ENQUEUE = 11 # Output to queue.
|
||||
OFPAT_VENDOR = 0xffff
|
||||
|
||||
OFP_ACTION_OUTPUT_PACK_STR = '!HHHH'
|
||||
OFP_ACTION_OUTPUT_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_OUTPUT_PACK_STR) == OFP_ACTION_OUTPUT_SIZE
|
||||
OFP_ACTION_OUTPUT_LEN = 8
|
||||
|
||||
# define constants
|
||||
OFP_VLAN_NONE = 0xffff
|
||||
|
||||
OFP_ACTION_VLAN_VID_PACK_STR = '!HHH2x'
|
||||
OFP_ACTION_VLAN_VID_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_VLAN_VID_PACK_STR) == OFP_ACTION_VLAN_VID_SIZE
|
||||
|
||||
OFP_ACTION_VLAN_PCP_PACK_STR = '!HHB3x'
|
||||
OFP_ACTION_VLAN_PCP_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_VLAN_PCP_PACK_STR) == OFP_ACTION_VLAN_PCP_SIZE
|
||||
|
||||
OFP_ACTION_DL_ADDR_PACK_STR = '!HH' + OFP_ETH_ALEN_STR + 'B6x'
|
||||
OFP_ACTION_DL_ADDR_SIZE = 16
|
||||
assert calcsize(OFP_ACTION_DL_ADDR_PACK_STR) == OFP_ACTION_DL_ADDR_SIZE
|
||||
|
||||
OFP_ACTION_NW_ADDR_PACK_STR = '!HHI'
|
||||
OFP_ACTION_NW_ADDR_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_NW_ADDR_PACK_STR) == OFP_ACTION_NW_ADDR_SIZE
|
||||
|
||||
OFP_ACTION_NW_TOS_PACK_STR = '!HHB3x'
|
||||
OFP_ACTION_NW_TOS_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_NW_TOS_PACK_STR) == OFP_ACTION_NW_TOS_SIZE
|
||||
|
||||
OFP_ACTION_TP_PORT_PACK_STR = '!HHH2x'
|
||||
OFP_ACTION_TP_PORT_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_TP_PORT_PACK_STR) == OFP_ACTION_TP_PORT_SIZE
|
||||
|
||||
OFP_ACTION_VENDOR_HEADER_PACK_STR = '!HHI'
|
||||
OFP_ACTION_VENDOR_HEADER_SIZE = 8
|
||||
assert (calcsize(OFP_ACTION_VENDOR_HEADER_PACK_STR) ==
|
||||
OFP_ACTION_VENDOR_HEADER_SIZE)
|
||||
|
||||
OFP_ACTION_HEADER_PACK_STR = '!HH4x'
|
||||
OFP_ACTION_HEADER_SIZE = 8
|
||||
assert calcsize(OFP_ACTION_HEADER_PACK_STR) == OFP_ACTION_HEADER_SIZE
|
||||
|
||||
OFP_ACTION_QUEUE_PACK_STR = '!HHH6xI'
|
||||
OFP_ACTION_QUEUE_SIZE = 16
|
||||
assert calcsize(OFP_ACTION_QUEUE_PACK_STR) == OFP_ACTION_QUEUE_SIZE
|
||||
|
||||
OFP_ACTION_PACK_STR = '!H'
|
||||
# because of union ofp_action
|
||||
# OFP_ACTION_SIZE = 8
|
||||
# assert calcsize(OFP_ACTION_PACK_STR) == OFP_ACTION_SIZE
|
||||
|
||||
OFP_PACKET_OUT_PACK_STR = '!IHH'
|
||||
OFP_PACKET_OUT_SIZE = 16
|
||||
assert (calcsize(OFP_PACKET_OUT_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_PACKET_OUT_SIZE)
|
||||
|
||||
# enum ofp_flow_mod_command
|
||||
OFPFC_ADD = 0 # New flow.
|
||||
OFPFC_MODIFY = 1 # Modify all matching flows.
|
||||
OFPFC_MODIFY_STRICT = 2 # Modify entry strictly matching wildcards
|
||||
OFPFC_DELETE = 3 # Delete all matching flows.
|
||||
OFPFC_DELETE_STRICT = 4 # Strictly match wildcards and priority.
|
||||
|
||||
# enum ofp_flow_wildcards
|
||||
OFPFW_IN_PORT = 1 << 0 # Switch input port.
|
||||
OFPFW_DL_VLAN = 1 << 1 # VLAN vid.
|
||||
OFPFW_DL_SRC = 1 << 2 # Ethernet source address.
|
||||
OFPFW_DL_DST = 1 << 3 # Ethernet destination address.
|
||||
OFPFW_DL_TYPE = 1 << 4 # Ethernet frame type.
|
||||
OFPFW_NW_PROTO = 1 << 5 # IP protocol.
|
||||
OFPFW_TP_SRC = 1 << 6 # TCP/UDP source port.
|
||||
OFPFW_TP_DST = 1 << 7 # TCP/UDP destination port.
|
||||
OFPFW_NW_SRC_SHIFT = 8
|
||||
OFPFW_NW_SRC_BITS = 6
|
||||
OFPFW_NW_SRC_MASK = ((1 << OFPFW_NW_SRC_BITS) - 1) << OFPFW_NW_SRC_SHIFT
|
||||
OFPFW_NW_SRC_ALL = 32 << OFPFW_NW_SRC_SHIFT
|
||||
OFPFW_NW_DST_SHIFT = 14
|
||||
OFPFW_NW_DST_BITS = 6
|
||||
OFPFW_NW_DST_MASK = ((1 << OFPFW_NW_DST_BITS) - 1) << OFPFW_NW_DST_SHIFT
|
||||
OFPFW_NW_DST_ALL = 32 << OFPFW_NW_DST_SHIFT
|
||||
OFPFW_DL_VLAN_PCP = 1 << 20 # VLAN priority.
|
||||
OFPFW_NW_TOS = 1 << 21 # IP ToS (DSCP field, 6 bits).
|
||||
OFPFW_ALL = ((1 << 22) - 1)
|
||||
|
||||
# define constants
|
||||
OFPFW_ICMP_TYPE = OFPFW_TP_SRC
|
||||
OFPFW_ICMP_CODE = OFPFW_TP_DST
|
||||
OFP_DL_TYPE_ETH2_CUTOFF = 0x0600
|
||||
OFP_DL_TYPE_NOT_ETH_TYPE = 0x05ff
|
||||
OFP_VLAN_NONE = 0xffff
|
||||
|
||||
_OFP_MATCH_PACK_STR = 'IH' + OFP_ETH_ALEN_STR + 's' + OFP_ETH_ALEN_STR + 'sHBxHBB2xIIHH'
|
||||
OFP_MATCH_PACK_STR = '!' + _OFP_MATCH_PACK_STR
|
||||
OFP_MATCH_SIZE = 40
|
||||
assert calcsize(OFP_MATCH_PACK_STR) == OFP_MATCH_SIZE
|
||||
|
||||
OFP_FLOW_PERMANENT = 0
|
||||
OFP_DEFAULT_PRIORITY = 0x8000
|
||||
|
||||
# enum ofp_flow_mod_flags
|
||||
OFPFF_SEND_FLOW_REM = 1 << 0 # Send flow removed message when flow
|
||||
# expires or is deleted.
|
||||
OFPFF_CHECK_OVERLAP = 1 << 1 # Check for overlapping entries first.
|
||||
OFPFF_EMERG = 1 << 2 # Ramark this is for emergency.
|
||||
|
||||
_OFP_FLOW_MOD_PACK_STR0 = 'QHHHHIHH'
|
||||
OFP_FLOW_MOD_PACK_STR = '!' + _OFP_MATCH_PACK_STR + _OFP_FLOW_MOD_PACK_STR0
|
||||
OFP_FLOW_MOD_PACK_STR0 = '!' + _OFP_FLOW_MOD_PACK_STR0
|
||||
OFP_FLOW_MOD_SIZE = 72
|
||||
assert calcsize(OFP_FLOW_MOD_PACK_STR) + OFP_HEADER_SIZE == OFP_FLOW_MOD_SIZE
|
||||
|
||||
# enum ofp_flow_removed_reason
|
||||
OFPRR_IDLE_TIMEOUT = 0 # Flow idle time exceeded idle_timeout.
|
||||
OFPRR_HARD_TIMEOUT = 1 # Time exceeded hard_timeout.
|
||||
OFPRR_DELETE = 2 # Evicted by a DELETE flow mod.
|
||||
|
||||
_OFP_FLOW_REMOVED_PACK_STR0 = 'QHBxIIH2xQQ'
|
||||
OFP_FLOW_REMOVED_PACK_STR = '!' + _OFP_MATCH_PACK_STR + \
|
||||
_OFP_FLOW_REMOVED_PACK_STR0
|
||||
OFP_FLOW_REMOVED_PACK_STR0 = '!' + _OFP_FLOW_REMOVED_PACK_STR0
|
||||
OFP_FLOW_REMOVED_SIZE = 88
|
||||
assert (calcsize(OFP_FLOW_REMOVED_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_FLOW_REMOVED_SIZE)
|
||||
|
||||
|
||||
# enum ofp_error_type
|
||||
OFPET_HELLO_FAILED = 0 # Hello protocol failed.
|
||||
OFPET_BAD_REQUEST = 1 # Request was not understood.
|
||||
OFPET_BAD_ACTION = 2 # Error in action description.
|
||||
OFPET_FLOW_MOD_FAILED = 3 # Problem modifying flow entry.
|
||||
OFPET_PORT_MOD_FAILED = 4 # OFPT_PORT_MOD failed.
|
||||
OFPET_QUEUE_OP_FAILED = 5 # Queue operation failed.
|
||||
|
||||
# enum ofp_hello_failed_code
|
||||
OFPHFC_INCOMPATIBLE = 0 # No compatible version.
|
||||
OFPHFC_EPERM = 1 # Permissions error.
|
||||
|
||||
# enum ofp_bad_request_code
|
||||
OFPBRC_BAD_VERSION = 0 # ofp_header.version not supported.
|
||||
OFPBRC_BAD_TYPE = 1 # ofp_header.type not supported.
|
||||
OFPBRC_BAD_STAT = 2 # ofp_stats_msg.type not supported.
|
||||
OFPBRC_BAD_VENDOR = 3 # Vendor not supported (in ofp_vendor_header
|
||||
# or ofp_stats_msg).
|
||||
OFPBRC_BAD_SUBTYPE = 4 # Vendor subtype not supported.
|
||||
OFPBRC_EPERM = 5 # Permissions error.
|
||||
OFPBRC_BAD_LEN = 6 # Wrong request length for type.
|
||||
OFPBRC_BUFFER_EMPTY = 7 # Specified buffer has already been used.
|
||||
OFPBRC_BUFFER_UNKNOWN = 8 # Specified buffer does not exist.
|
||||
|
||||
# enum ofp_bad_action_code
|
||||
OFPBAC_BAD_TYPE = 0 # Unknown action type.
|
||||
OFPBAC_BAD_LEN = 1 # Length problem in actions.
|
||||
OFPBAC_BAD_VENDOR = 2 # Unknown vendor id specified.
|
||||
OFPBAC_BAD_VENDOR_TYPE = 3 # Unknown action type for vendor id.
|
||||
OFPBAC_BAD_OUT_PORT = 4 # Problem validating output action.
|
||||
OFPBAC_BAD_ARGUMENT = 5 # Bad action argument.
|
||||
OFPBAC_EPERM = 6 # Permissions error.
|
||||
OFPBAC_TOO_MANY = 7 # Can't handle this many actions.
|
||||
OFPBAC_BAD_QUEUE = 8 # Problem validating output queue.
|
||||
|
||||
# enum ofp_flow_mod_failed_code
|
||||
OFPFMFC_ALL_TABLES_FULL = 0 # Flow not added because of full tables.
|
||||
OFPFMFC_OVERLAP = 1 # Attempted to add overlapping flow with
|
||||
# CHECK_OVERLAP flags set.
|
||||
OFPFMFC_EPERM = 2 # Permissions error.
|
||||
OFPFMFC_BAD_EMERG_TIMEOUT = 3 # Flow not added because of non-zero idle/hard
|
||||
# timeout.
|
||||
OFPFMFC_BAD_COMMAND = 4 # Unknown command.
|
||||
OFPFMFC_UNSUPPORTED = 5 # Unsupported action list - cannot process in
|
||||
# the order specified.
|
||||
|
||||
# enum ofp_port_mod_failed_code
|
||||
OFPPMFC_BAD_PORT = 0 # Specified port does not exist.
|
||||
OFPPMFC_BAD_HW_ADDR = 1 # Specified hardware address is wrong.
|
||||
|
||||
# enum ofp_queue_op_failed_code
|
||||
OFPQOFC_BAD_PORT = 0 # Invalid port (or port does not exist).
|
||||
OFPQOFC_BAD_QUEUE = 1 # Queue does not exist.
|
||||
OFPQOFC_EPERM = 2 # Permissions error.
|
||||
|
||||
OFP_ERROR_MSG_PACK_STR = '!HH'
|
||||
OFP_ERROR_MSG_SIZE = 12
|
||||
assert calcsize(OFP_ERROR_MSG_PACK_STR) + OFP_HEADER_SIZE == OFP_ERROR_MSG_SIZE
|
||||
|
||||
# enum ofp_stats_types
|
||||
OFPST_DESC = 1
|
||||
OFPST_FLOW = 2
|
||||
OFPST_AGGREGATE = 3
|
||||
OFPST_TABLE = 4
|
||||
OFPST_PORT = 5
|
||||
OFPST_QUEUE = 6
|
||||
OFPST_VENDOR = 0xffff
|
||||
|
||||
_OFP_STATS_MSG_PACK_STR = 'HH'
|
||||
OFP_STATS_MSG_PACK_STR = '!' + _OFP_STATS_MSG_PACK_STR
|
||||
OFP_STATS_MSG_SIZE = 12
|
||||
assert calcsize(OFP_STATS_MSG_PACK_STR) + OFP_HEADER_SIZE == OFP_STATS_MSG_SIZE
|
||||
|
||||
# enum ofp_stats_reply_flags
|
||||
OFPSF_REPLY_MORE = 1 << 0 # More replies to follow.
|
||||
|
||||
# define constants
|
||||
DESC_STR_LEN = 256
|
||||
DESC_STR_LEN_STR = str(DESC_STR_LEN)
|
||||
SERIAL_NUM_LEN = 32
|
||||
SERIAL_NUM_LEN_STR = str(SERIAL_NUM_LEN)
|
||||
|
||||
OFP_DESC_STATS_PACK_STR = '!' + \
|
||||
DESC_STR_LEN_STR + 'c' + \
|
||||
DESC_STR_LEN_STR + 'c' + \
|
||||
DESC_STR_LEN_STR + 'c' + \
|
||||
SERIAL_NUM_LEN_STR + 'c' + \
|
||||
DESC_STR_LEN_STR + 'c'
|
||||
OFP_DESC_STATS_SIZE = 1068
|
||||
assert (calcsize(OFP_DESC_STATS_PACK_STR) + OFP_STATS_MSG_SIZE ==
|
||||
OFP_DESC_STATS_SIZE)
|
||||
|
||||
OFP_FLOW_STATS_REQUEST_PACK_STR = '!' + _OFP_MATCH_PACK_STR + 'BxH'
|
||||
OFP_FLOW_STATS_REQUEST_SIZE = 56
|
||||
assert (calcsize(OFP_FLOW_STATS_REQUEST_PACK_STR) + OFP_STATS_MSG_SIZE ==
|
||||
OFP_FLOW_STATS_REQUEST_SIZE)
|
||||
|
||||
OFP_FLOW_STATS_PACK_STR = '!HBx' + _OFP_MATCH_PACK_STR + 'IIHHH6xQQQ'
|
||||
OFP_FLOW_STATS_SIZE = 88
|
||||
assert calcsize(OFP_FLOW_STATS_PACK_STR) == OFP_FLOW_STATS_SIZE
|
||||
|
||||
OFP_AGGREGATE_STATS_REPLY_PACK_STR = '!QQI4x'
|
||||
OFP_AGGREGATE_STATS_REPLY_SIZE = 36
|
||||
assert (calcsize(OFP_AGGREGATE_STATS_REPLY_PACK_STR) +
|
||||
OFP_STATS_MSG_SIZE == OFP_AGGREGATE_STATS_REPLY_SIZE)
|
||||
|
||||
OFP_TABLE_STATS_PACK_STR = '!B3x' + OFP_MAX_TABLE_NAME_LEN_STR + 'cIIIQQ'
|
||||
OFP_TABLE_STATS_SIZE = 64
|
||||
assert calcsize(OFP_TABLE_STATS_PACK_STR) == OFP_TABLE_STATS_SIZE
|
||||
|
||||
OFP_PORT_STATS_REQUEST_PACK_STR = '!H6x'
|
||||
OFP_PORT_STATS_REQUEST_SIZE = 20
|
||||
assert (calcsize(OFP_PORT_STATS_REQUEST_PACK_STR) + OFP_STATS_MSG_SIZE ==
|
||||
OFP_PORT_STATS_REQUEST_SIZE)
|
||||
|
||||
OFP_PORT_STATS_PACK_STR = '!H6xQQQQQQQQQQQQ'
|
||||
OFP_PORT_STATS_SIZE = 104
|
||||
assert calcsize(OFP_PORT_STATS_PACK_STR) == OFP_PORT_STATS_SIZE
|
||||
|
||||
OFPQ_ALL = 0xffffffff
|
||||
|
||||
OFP_QUEUE_STATS_PACK_STR = '!H2xIQQQ'
|
||||
OFP_QUEUE_STATS_SIZE = 32
|
||||
assert calcsize(OFP_QUEUE_STATS_PACK_STR) == OFP_QUEUE_STATS_SIZE
|
||||
|
||||
OFP_VENDOR_STATS_MSG_PACK_STR = '!I'
|
||||
OFP_VENDOR_STATS_MSG_SIZE = 16
|
||||
assert (calcsize(OFP_VENDOR_STATS_MSG_PACK_STR) + OFP_STATS_MSG_SIZE ==
|
||||
OFP_VENDOR_STATS_MSG_SIZE)
|
||||
|
||||
OFP_VENDOR_HEADER_PACK_STR = '!I'
|
||||
OFP_VENDOR_HEADER_SIZE = 12
|
||||
assert (calcsize(OFP_VENDOR_HEADER_PACK_STR) + OFP_HEADER_SIZE ==
|
||||
OFP_VENDOR_HEADER_SIZE)
|
542
ryu/ofproto/ofproto_v1_0_parser.py
Normal file
@ -0,0 +1,542 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import collections
|
||||
import struct
|
||||
|
||||
from . import ofproto_parser
|
||||
from . import ofproto_v1_0
|
||||
|
||||
import logging
|
||||
LOG = logging.getLogger('ryu.ofproto.ofproto_v1_0_parser')
|
||||
|
||||
_MSG_PARSERS = {}
|
||||
|
||||
|
||||
def _set_msg_type(msg_type):
|
||||
def _set_cls_msg_type(cls):
|
||||
cls.cls_msg_type = msg_type
|
||||
return cls
|
||||
return _set_cls_msg_type
|
||||
|
||||
|
||||
def _register_parser(cls):
|
||||
'''class decorator to register msg parser'''
|
||||
assert cls.cls_msg_type is not None
|
||||
assert cls.cls_msg_type not in _MSG_PARSERS
|
||||
_MSG_PARSERS[cls.cls_msg_type] = cls.parser
|
||||
return cls
|
||||
|
||||
|
||||
@ofproto_parser.register_msg_parser(ofproto_v1_0.OFP_VERSION)
|
||||
def msg_parser(datapath, version, msg_type, msg_len, xid, buf):
|
||||
parser = _MSG_PARSERS.get(msg_type)
|
||||
return parser(datapath, version, msg_type, msg_len, xid, buf)
|
||||
|
||||
|
||||
class MsgBase(object):
|
||||
def __init__(self, datapath):
|
||||
self.datapath = datapath
|
||||
self.version = None
|
||||
self.msg_type = None
|
||||
self.msg_len = None
|
||||
self.xid = None
|
||||
self.buf = None
|
||||
|
||||
def set_headers(self, version, msg_type, msg_len, xid):
|
||||
assert msg_type == self.cls_msg_type
|
||||
|
||||
self.version = version
|
||||
self.msg_type = msg_type
|
||||
self.msg_len = msg_len
|
||||
self.xid = xid
|
||||
|
||||
def set_buf(self, buf):
|
||||
self.buf = buffer(buf)
|
||||
|
||||
def __str__(self):
|
||||
return 'version: 0x%x msg_type 0x%x xid 0x%x' % (self.version,
|
||||
self.msg_type,
|
||||
self.xid)
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = cls(datapath)
|
||||
msg.set_headers(version, msg_type, msg_len, xid)
|
||||
msg.set_buf(buf)
|
||||
return msg
|
||||
|
||||
def _serialize_pre(self):
|
||||
assert self.version is None
|
||||
assert self.msg_type is None
|
||||
assert self.buf is None
|
||||
|
||||
self.version = ofproto_v1_0.OFP_VERSION
|
||||
self.msg_type = self.cls_msg_type
|
||||
self.buf = bytearray().zfill(ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
|
||||
def _serialize_header(self):
|
||||
# buffer length is determined after trailing data is formated.
|
||||
assert self.version is not None
|
||||
assert self.msg_type is not None
|
||||
assert self.msg_len is None
|
||||
assert self.xid is None
|
||||
assert self.buf is not None
|
||||
assert len(self.buf) >= ofproto_v1_0.OFP_HEADER_SIZE
|
||||
|
||||
self.msg_len = len(self.buf)
|
||||
self.xid = 0 # TODO:XXX
|
||||
|
||||
struct.pack_into(ofproto_v1_0.OFP_HEADER_PACK_STR, self.buf, 0,
|
||||
self.version, self.msg_type, self.msg_len, self.xid)
|
||||
|
||||
def _serialize_body(self):
|
||||
pass
|
||||
|
||||
def serialize(self):
|
||||
self._serialize_pre()
|
||||
self._serialize_body()
|
||||
self._serialize_header()
|
||||
|
||||
|
||||
def _pack_into(fmt, buf, offset, *args):
|
||||
if len(buf) < offset:
|
||||
buf += bytearray().zfill(offset - len(buf))
|
||||
|
||||
if len(buf) == offset:
|
||||
buf += struct.pack(fmt, *args)
|
||||
return
|
||||
|
||||
needed_len = offset + struct.calcsize(fmt)
|
||||
if len(buf) < needed_len:
|
||||
buf += bytearray().zfill(needed_len - len(buf))
|
||||
|
||||
struct.pack_into(fmt, buf, offset, *args)
|
||||
|
||||
|
||||
def _str_attr(msg, buf, attr_list):
|
||||
for attr in attr_list:
|
||||
val = getattr(msg, attr, None)
|
||||
if val is not None:
|
||||
buf += ' %s %s' % (attr, val)
|
||||
|
||||
return buf
|
||||
|
||||
|
||||
#
|
||||
# common structures
|
||||
#
|
||||
|
||||
class OFPPhyPort(collections.namedtuple('OFPPhyPort', (
|
||||
'port_no', 'hw_addr', 'name', 'config', 'state', 'curr', 'advertised',
|
||||
'supported', 'peer'))):
|
||||
|
||||
@classmethod
|
||||
def parser(cls, buf, offset):
|
||||
port = struct.unpack_from(ofproto_v1_0.OFP_PHY_PORT_PACK_STR,
|
||||
buf, offset)
|
||||
return cls(*port)
|
||||
|
||||
|
||||
class OFPMatch(collections.namedtuple('OFPMatchBase', (
|
||||
'wildcards', 'in_port', 'dl_src', 'dl_dst', 'dl_vlan',
|
||||
'dl_vlan_pcp', 'dl_type', 'nw_tos', 'nw_proto',
|
||||
'nw_src', 'nw_dst', 'tp_src', 'tp_dst'))):
|
||||
|
||||
def serialize(self, buf, offset):
|
||||
_pack_into(ofproto_v1_0.OFP_MATCH_PACK_STR, buf, offset, *self)
|
||||
|
||||
@classmethod
|
||||
def parse(cls, buf, offset):
|
||||
match = struct.unpack_from(ofproto_v1_0.OFP_MATCH_PACK_STR,
|
||||
buf, offset)
|
||||
return cls(*match)
|
||||
|
||||
|
||||
class OFPActionHeader(object):
|
||||
def __init__(self, type, len):
|
||||
self.type = type
|
||||
self.len = len
|
||||
|
||||
def serlize(self, buf, offset):
|
||||
_pack_into(ofproto_v1_0.OFP_ACTION_HEADER_PACK_STR,
|
||||
buf, offset, self.type, self.len)
|
||||
|
||||
|
||||
class OFPActionOutput(OFPActionHeader):
|
||||
def __init__(self, port, max_len=0):
|
||||
super(OFPActionOutput,
|
||||
self).__init__(ofproto_v1_0.OFPAT_OUTPUT,
|
||||
ofproto_v1_0.OFP_ACTION_OUTPUT_LEN)
|
||||
self.port = port
|
||||
self.max_len = max_len
|
||||
|
||||
def serialize(self, buf, offset):
|
||||
_pack_into(ofproto_v1_0.OFP_ACTION_OUTPUT_PACK_STR,
|
||||
buf, offset, self.type, self.len, self.port, self.max_len)
|
||||
|
||||
|
||||
# TODO:XXX more actions
|
||||
|
||||
|
||||
#
|
||||
# Symmetric messages
|
||||
# parser + serializer
|
||||
#
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_HELLO)
|
||||
class OFPHello(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPHello, self).__init__(datapath)
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_ERROR)
|
||||
class OFPErrorMsg(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPErrorMsg, self).__init__(datapath)
|
||||
self.type = None
|
||||
self.code = None
|
||||
self.data = None
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPErrorMsg, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
msg.type, msg.code = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_ERROR_MSG_PACK_STR, msg.buf,
|
||||
ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
msg.data = msg.buf[ofproto_v1_0.OFP_ERROR_MSG_SIZE:]
|
||||
return msg
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.data is not None
|
||||
_pack_into(ofproto_v1_0.OFP_ERROR_MSG_PACK_STR, self.buf,
|
||||
ofproto_v1_0.OFP_HEADER_SIZE, self.type, self.code)
|
||||
self.buf += self.data
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_ECHO_REQUEST)
|
||||
class OFPEchoRequest(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPEchoRequest, self).__init__(datapath)
|
||||
self.data = None
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPEchoRequest, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
msg.data = msg.buf[ofproto_v1_0.OFP_HEADER_SIZE:]
|
||||
return msg
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.data is not None
|
||||
self.buf += self.data
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_ECHO_REPLY)
|
||||
class OFPEchoReply(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPEchoReply, self).__init__(datapath)
|
||||
self.data = None
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPEchoReply, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
msg.data = msg.buf[ofproto_v1_0.OFP_HEADER_SIZE:]
|
||||
return msg
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.data is not None
|
||||
self.buf += self.data
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_VENDOR)
|
||||
class OFPVendor(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPVendor, self).__init__(datapath)
|
||||
self.data = None
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPVendor, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
msg.vendor = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_VENDOR_HEADER_PACK_STR, msg.buf,
|
||||
ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
msg.data = msg.buf[ofproto_v1_0.OFP_VENDOR_HEADER_SIZE:]
|
||||
return msg
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.data is not None
|
||||
_pack_into(ofproto_v1_0.OFP_VENDOR_HEADER_PACK_STR,
|
||||
self.buf, ofproto_v1_0.OFP_HEADER_SIZE, self.vendor)
|
||||
self.buf += self.data
|
||||
|
||||
|
||||
#
|
||||
# asymmetric message (datapath -> controller)
|
||||
# parser only
|
||||
#
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_FEATURES_REPLY)
|
||||
class OFPSwitchFeatures(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPSwitchFeatures, self).__init__(datapath)
|
||||
|
||||
def __str__(self):
|
||||
buf = super(OFPSwitchFeatures, self).__str__() + ' port'
|
||||
for port_no, p in getattr(self, 'ports', {}).items():
|
||||
buf += ' ' + str(p)
|
||||
return buf
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPSwitchFeatures, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
(msg.datapath_id,
|
||||
msg.n_buffers,
|
||||
msg.n_tables,
|
||||
msg.capabilities,
|
||||
msg.actions) = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_SWITCH_FEATURES_PACK_STR, msg.buf,
|
||||
ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
|
||||
msg.ports = {}
|
||||
n_ports = ((msg_len - ofproto_v1_0.OFP_SWITCH_FEATURES_SIZE) /
|
||||
ofproto_v1_0.OFP_PHY_PORT_SIZE)
|
||||
offset = ofproto_v1_0.OFP_SWITCH_FEATURES_SIZE
|
||||
for i in range(n_ports):
|
||||
port = OFPPhyPort.parser(msg.buf, offset)
|
||||
# print 'port = %s' % str(port)
|
||||
msg.ports[port.port_no] = port
|
||||
offset += ofproto_v1_0.OFP_PHY_PORT_SIZE
|
||||
|
||||
return msg
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_PORT_STATUS)
|
||||
class OFPPortStatus(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPPortStatus, self).__init__(datapath)
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPPortStatus, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
msg.reason = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_PORT_STATUS_PACK_STR,
|
||||
msg.buf, ofproto_v1_0.OFP_HEADER_SIZE)[0]
|
||||
msg.desc = OFPPhyPort.parser(msg.buf,
|
||||
ofproto_v1_0.OFP_PORT_STATUS_DESC_OFFSET)
|
||||
return msg
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_PACKET_IN)
|
||||
class OFPPacketIn(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPPacketIn, self).__init__(datapath)
|
||||
|
||||
def __str__(self):
|
||||
buf = super(OFPPacketIn, self).__str__()
|
||||
return _str_attr(self, buf,
|
||||
('buffer_id', 'total_len', 'in_port', 'reason'))
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPPacketIn, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
(msg.buffer_id,
|
||||
msg.total_len,
|
||||
msg.in_port,
|
||||
msg.reason) = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_PACKET_IN_PACK_STR,
|
||||
msg.buf, ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
msg.data = msg.buf[ofproto_v1_0.OFP_PACKET_IN_DATA_OFFSET:]
|
||||
return msg
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_GET_CONFIG_REPLY)
|
||||
class OFPSwitchConfig(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPSwitchConfig, self).__init__(datapath)
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPSwitchConfig, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
(msg.flags, msg.miss_send_len) = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_SWITCH_CONFIG_PACK_STR,
|
||||
msg.buf, ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
return msg
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_BARRIER_REPLY)
|
||||
class OFPBarrierReply(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPBarrierReply, self).__init__(datapath)
|
||||
|
||||
|
||||
@_register_parser
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_FLOW_REMOVED)
|
||||
class OFPFlowRemoved(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPFlowRemoved, self).__init__(datapath)
|
||||
|
||||
def __str__(self):
|
||||
buf = super(OFPFlowRemoved, self).__str__()
|
||||
return _str_attr(self, buf,
|
||||
('match', 'cookie', 'priority', 'reason',
|
||||
'duration_sec', 'duration_nsec',
|
||||
'idle_timeout', 'packet_count', 'idle_count'))
|
||||
|
||||
@classmethod
|
||||
def parser(cls, datapath, version, msg_type, msg_len, xid, buf):
|
||||
msg = super(OFPFlowRemoved, cls).parser(datapath, version, msg_type,
|
||||
msg_len, xid, buf)
|
||||
|
||||
msg.match = OFPMatch.parse(msg.buf, ofproto_v1_0.OFP_HEADER_SIZE)
|
||||
|
||||
(msg.cookie,
|
||||
msg.priority,
|
||||
msg.reason,
|
||||
msg.duration_sec,
|
||||
msg.duration_nsec,
|
||||
msg.idle_timeout,
|
||||
msg.packet_count,
|
||||
msg.byte_count) = struct.unpack_from(
|
||||
ofproto_v1_0.OFP_FLOW_REMOVED_PACK_STR0, msg.buf,
|
||||
ofproto_v1_0.OFP_HEADER_SIZE + ofproto_v1_0.OFP_MATCH_SIZE)
|
||||
|
||||
return msg
|
||||
|
||||
#
|
||||
# controller-to-switch message
|
||||
# serializer only
|
||||
#
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_FEATURES_REQUEST)
|
||||
class OFPFeaturesRequest(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPFeaturesRequest, self).__init__(datapath)
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_GET_CONFIG_REQUEST)
|
||||
class OFPGetConfigRequest(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPGetConfigRequest, self).__init__(datapath)
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_SET_CONFIG)
|
||||
class OFPSetConfig(MsgBase):
|
||||
def __init__(self, datapath, flags=None, miss_send_len=None):
|
||||
super(OFPSetConfig, self).__init__(datapath)
|
||||
self.flags = flags
|
||||
self.miss_send_len = miss_send_len
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.flags is not None
|
||||
assert self.miss_send_len is not None
|
||||
_pack_into(ofproto_v1_0.OFP_SWITCH_CONFIG_PACK_STR,
|
||||
self.buf, ofproto_v1_0.OFP_HEADER_SIZE,
|
||||
self.flags, self.miss_send_len)
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_PACKET_OUT)
|
||||
class OFPPacketOut(MsgBase):
|
||||
def __init__(self, datapath, buffer_id=None, in_port=None, actions=None,
|
||||
data=None):
|
||||
super(OFPPacketOut, self).__init__(datapath)
|
||||
self.buffer_id = buffer_id
|
||||
self.in_port = in_port
|
||||
self.actions_len = None
|
||||
self.actions = actions
|
||||
self.data = data
|
||||
|
||||
def _serialize_body(self):
|
||||
assert self.buffer_id is not None
|
||||
assert self.in_port is not None
|
||||
assert self.actions_len is None
|
||||
assert self.actions is not None
|
||||
|
||||
self.actions_len = 0
|
||||
offset = ofproto_v1_0.OFP_PACKET_OUT_SIZE
|
||||
for a in self.actions:
|
||||
a.serialize(self.buf, offset)
|
||||
offset += a.len
|
||||
self.actions_len += a.len
|
||||
|
||||
if self.data is not None:
|
||||
assert self.buffer_id == -1
|
||||
self.buf += self.data
|
||||
|
||||
_pack_into(ofproto_v1_0.OFP_PACKET_OUT_PACK_STR,
|
||||
self.buf, ofproto_v1_0.OFP_HEADER_SIZE,
|
||||
self.buffer_id, self.in_port, self.actions_len)
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_FLOW_MOD)
|
||||
class OFPFlowMod(MsgBase):
|
||||
def __init__(self, datapath, match=None, cookie=None,
|
||||
command=None, idle_timeout=None, hard_timeout=None,
|
||||
priority=None, buffer_id=None, out_port=None,
|
||||
flags=None, actions=None):
|
||||
super(OFPFlowMod, self).__init__(datapath)
|
||||
self.match = match
|
||||
self.cookie = cookie
|
||||
self.command = command
|
||||
self.idle_timeout = idle_timeout
|
||||
self.hard_timeout = hard_timeout
|
||||
self.priority = priority
|
||||
self.buffer_id = buffer_id
|
||||
self.out_port = out_port
|
||||
self.flags = flags
|
||||
self.actions = actions
|
||||
|
||||
def _serialize_body(self):
|
||||
offset = ofproto_v1_0.OFP_HEADER_SIZE
|
||||
self.match.serialize(self.buf, offset)
|
||||
|
||||
offset += ofproto_v1_0.OFP_MATCH_SIZE
|
||||
_pack_into(ofproto_v1_0.OFP_FLOW_MOD_PACK_STR0, self.buf, offset,
|
||||
self.cookie, self.command,
|
||||
self.idle_timeout, self.hard_timeout,
|
||||
self.priority, self.buffer_id, self.out_port,
|
||||
self.flags)
|
||||
|
||||
offset = ofproto_v1_0.OFP_FLOW_MOD_SIZE
|
||||
if self.actions is not None:
|
||||
for a in self.actions:
|
||||
a.serialize(self.buf, offset)
|
||||
offset += a.len
|
||||
|
||||
|
||||
@_set_msg_type(ofproto_v1_0.OFPT_BARRIER_REQUEST)
|
||||
class OFPBarrierRequest(MsgBase):
|
||||
def __init__(self, datapath):
|
||||
super(OFPBarrierRequest, self).__init__(datapath)
|
62
ryu/utils.py
Normal file
@ -0,0 +1,62 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import inspect
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
LOG = logging.getLogger('ryu.utils')
|
||||
|
||||
def import_module(modname):
|
||||
(f, s, t) = modname.rpartition('.')
|
||||
mod = __import__(modname, fromlist=[f])
|
||||
return mod
|
||||
|
||||
|
||||
def import_object(modname):
|
||||
try:
|
||||
return import_module(modname)
|
||||
except ImportError:
|
||||
(from_mod, sep, target) = modname.rpartition('.')
|
||||
mod = import_module(from_mod)
|
||||
return getattr(mod, target)
|
||||
|
||||
|
||||
RYU_DEFAULT_FLAG_FILE = ('ryu.conf', 'etc/ryu/ryu.conf' '/etc/ryu/ryu.conf')
|
||||
|
||||
|
||||
def find_flagfile(default_path=RYU_DEFAULT_FLAG_FILE):
|
||||
if '--flagfile' in sys.argv:
|
||||
return
|
||||
|
||||
script_dir = os.path.dirname(inspect.stack()[-1][1])
|
||||
|
||||
for filename in RYU_DEFAULT_FLAG_FILE:
|
||||
if not os.path.abspath(filename):
|
||||
if os.path.exists(filename):
|
||||
# try relative to current path
|
||||
filename = os.path.abspath(filename)
|
||||
elif os.path.exists(os.path.join(script_dir, filename)):
|
||||
# try relative to script dir
|
||||
filename = os.path.join(script_dir, filename)
|
||||
|
||||
if not os.path.exists(filename):
|
||||
continue
|
||||
|
||||
flagfile = '--flagfile=%s' % filename
|
||||
sys.argv.insert(1, flagfile)
|
||||
LOG.debug('flagfile = %s', filename)
|
||||
return
|
38
setup.py
Normal file
@ -0,0 +1,38 @@
|
||||
# Copyright (C) 2011 Nippon Telegraph and Telephone Corporation.
|
||||
# Copyright (C) 2011 Isaku Yamahata <yamahata at valinux co jp>
|
||||
#
|
||||
# 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 3 of the 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 General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
import os
|
||||
|
||||
from setuptools import find_packages
|
||||
from setuptools import setup
|
||||
|
||||
README = os.path.join(os.path.dirname(__file__), 'README.rst')
|
||||
long_description = open(README).read() + '\n\n'
|
||||
|
||||
setup(name='ryu',
|
||||
version='0.1',
|
||||
description=("Ryu Network Operating System"),
|
||||
long_description=long_description,
|
||||
keywords='openflow openvswitch openstack',
|
||||
url='http://www.osrg.net/ryu/',
|
||||
# author='',
|
||||
autor_email='ryu-devel@lists.sourceforge.net',
|
||||
license='GPL v3 only',
|
||||
packages=find_packages(),
|
||||
scripts=['bin/ryu-manager',
|
||||
'bin/ryu-client'],
|
||||
data_files=[('etc/ryu', ['etc/ryu/ryu.conf'])],
|
||||
# install_requires=[]
|
||||
)
|