Skip to content

Commit

Permalink
[master] Finished merge of trac5549a (known/unknown)
Browse files Browse the repository at this point in the history
  • Loading branch information
fxdupont committed Jun 13, 2018
2 parents 6de6024 + d9c77f8 commit 6a856ed
Show file tree
Hide file tree
Showing 18 changed files with 592 additions and 72 deletions.
9 changes: 9 additions & 0 deletions ChangeLog
Original file line number Diff line number Diff line change
@@ -1,3 +1,12 @@
1426. [func] fdupont
Added KNOWN and UNKNOWN built-in client classes: after host lookup
if a matching host entry is found the incoming packet is added to
the KNOWN class, if none is found to the UNKNOWN class. Then
expressions depending directly or indirectly on these classes are
evaluated. Note these classes may be used to select a pool but
they may not to select a subnet.
(Trac #5549, git xxx)

1425. [bug] marcin
Improved performance of the DHCP server running in High
Availability configuration by optimizing the management of
Expand Down
28 changes: 27 additions & 1 deletion doc/examples/kea4/classify2.json
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,33 @@
} ],
"subnet": "192.0.4.0/23",
"interface": "ethY"
}
},
// This subnet is divided in two pools for unknown and known
// (i.e. which have a reservation) clients. The built-in KNOWN and
// UNKNOWN classes are set or not at host reservation lookup (KNOWN if
// this returns something, UNKNOWN if this finds nothing) and client
//classes depending on it are evaluated.
// This happens after subnet selection and before address allocation
//from pools.
{
"pools": [
{
"pool": "192.0.8.100 - 192.0.8.200",
"client-class": "UNKNOWN"
},
{
"pool": "192.0.9.100 - 192.0.9.200",
"client-class": "KNOWN"
}
],
"subnet": "192.0.8.0/23",
"reservations": [
{ "hw-address": "00:00:00:11:22:33", "hostname": "h1" },
{ "hw-address": "00:00:00:44:55:66", "hostname": "h4" },
{ "hw-address": "00:00:00:77:88:99", "hostname": "h7" },
{ "hw-address": "00:00:00:aa:bb:cc", "hostname": "ha" }
]
}
]
},

Expand Down
26 changes: 26 additions & 0 deletions doc/examples/kea6/classify2.json
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,32 @@
} ],
"subnet": "2001:db8:4::/64",
"interface": "ethY"
},
// This subnet is divided in two pools for unknown and known
// (i.e. which have a reservation) clients. The built-in KNOWN and
// UNKNOWN classes are set or not at host reservation lookup (KNOWN if
// this returns something, UNKNOWN if this finds nothing) and client
//classes depending on it are evaluated.
// This happens after subnet selection and before address allocation
//from pools.
{
"pools": [
{
"pool": "2001:db8:8::/64",
"client-class": "UNKNOWN"
},
{
"pool": "2001:db8:9::/64",
"client-class": "KNOWN"
}
],
"subnet": "2001:db8:8::/46",
"reservations": [
{ "hw-address": "00:00:00:11:22:33", "hostname": "h1" },
{ "hw-address": "00:00:00:44:55:66", "hostname": "h4" },
{ "hw-address": "00:00:00:77:88:99", "hostname": "h7" },
{ "hw-address": "00:00:00:aa:bb:cc", "hostname": "ha" }
]
}

]
Expand Down
59 changes: 33 additions & 26 deletions doc/guide/classify.xml
Original file line number Diff line number Diff line change
Expand Up @@ -78,10 +78,11 @@
</para></listitem>
<listitem><para>
Classes with matching expressions and not marked for later ("on
request" or depending on the KNOWN builtin class) evaluation are
processed in the order they are defined in the configuration:
the boolean expression is evaluated and when it returns true
("match") the incoming packet is associated to the class.
request" or depending on the KNOWN/UNKNOWN builtin classes)
evaluation are processed in the order they are defined in the
configuration: the boolean expression is evaluated and when it
returns true ("match") the incoming packet is associated to the
class.
</para></listitem>
<listitem><para>
If a private or code 43 DHCPv4 option is received, decoding it
Expand All @@ -98,18 +99,22 @@
that has a class which matches one of the packet's classes.
</para></listitem>
<listitem><para>
Host reservations are looked for. If an identifier from the incoming
packet matches a host reservation in the subnet or shared network,
the packet is associated with the KNOWN builtin class and all classes
of the host reservation.
Host reservations are looked for. If an identifier from the
incoming packet matches a host reservation in the subnet or
shared network, the packet is associated with the KNOWN class
and all classes of the host reservation. If a reservation is not
found, the packet is assigned to UNKNOWN class.
</para></listitem>
<listitem><para>
Classes with matching expressions using directly or indirectly
the KNOWN builtin class and not marked for later ("on request")
evaluation are processed in the order they are defined in the
configuration: the boolean expression is evaluated and when it
returns true ("match") the incoming packet is associated to the
class.
the KNOWN/UNKNOWN builtin classes and not marked for later ("on
request") evaluation are processed in the order they are defined
in the configuration: the boolean expression is evaluated and
when it returns true ("match") the incoming packet is associated
to the class. The determination whether there is a reservation
for a given client is made after a subnet is selected. As such, it
is not possible to use KNOWN/UNKNOWN classes to select a shared
network or a subnet.
</para></listitem>
<listitem><para>
If needed, addresses and prefixes from pools are assigned,
Expand Down Expand Up @@ -198,11 +203,12 @@
begin with all capital letters.
</para>

<para>Currently recognized builtin class names are ALL and KNOWN
and prefixes VENDOR_CLASS_, AFTER_ , EXTERNAL_ and HA_. The AFTER_ prefix
is a provision for a not yet written hook, the EXTERNAL_ prefix
can be freely used: builtin classes are implicitly defined so
never raise warnings if they do not appear in the configuration.
<para>Currently recognized builtin class names are ALL, KNOWN
and UNKNOWN, and prefixes VENDOR_CLASS_, HA_, AFTER_ and
EXTERNAL_. The AFTER_ prefix is a provision for a not yet
written hook, the EXTERNAL_ prefix can be freely used: builtin
classes are implicitly defined so never raise warnings if they
do not appear in the configuration.
</para>

</section>
Expand Down Expand Up @@ -245,11 +251,12 @@
</para>

<para>
Dependencies between classes are checked too: for instance forward
dependencies are rejected when the configuration is parsed:
an expression can only depend on already defined classes (including
builtin classes) and which are evaluated in a previous or the
same evaluation phase. This does not apply to the KNOWN class.
Dependencies between classes are checked too: for instance
forward dependencies are rejected when the configuration is
parsed: an expression can only depend on already defined classes
(including builtin classes) and which are evaluated in a
previous or the same evaluation phase. This does not apply to
the KNOWN or UNKNOWN classes.
</para>

<para>
Expand Down Expand Up @@ -335,7 +342,7 @@
<entry>Unknown client</entry>
<entry>unknown</entry>
<entry>not member('KNOWN')</entry>
<entry>If there is a hostreservation for the client
<entry>If there is a host reservation for the client
"false" else "true"</entry>
</row>
<row>
Expand Down Expand Up @@ -594,13 +601,13 @@
built-in, i.e., beginning by &quot;VENDOR_CLASS_&quot;,
&quot;AFTER__&quot; (for the to come "after" hook) and
&quot;EXTERNAL_&quot; or equal to &quot;ALL&quot;, &quot;KNOWN&quot;,
etc.
&quot;UNKNOWN&quot;etc.
</para>
<para>"known" and "unknown" are short hands for "member('KNOWN')" and
"not member('KNOWN')". Note the evaluation of any expression using
directly or indirectly the &quot;KNOWN&quot; class is deferred
after the host reservation lookup (i.e. when the &quot;KNOWN&quot;
belonging is determined).
or &quot;UNKNOWN&quot; partition is determined).
</para></listitem>

<listitem><para>
Expand Down
31 changes: 23 additions & 8 deletions doc/guide/dhcp4-srv.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2243,11 +2243,26 @@ It is merely echoed by the server
</para>

<para>
The process of doing classification is conducted in several steps. The first step
is to assess an incoming packet and assign it to zero or more classes. The
second step is to choose a subnet, possibly based on the class information.
The third step is to assign classes from host reservations and
evaluate class expressions depending on the "KNOWN" class.
In a similar way a pool can be constrained to serve only known
clients, i.e. clients which have a reservation, using the
built-in "KNOWN" or "UNKNOWN" classes. One can assign addresses
to registered clients without giving a different address per
reservations, for instance when there is not enough available
addresses. The determination whether there is a reservation
for a given client is made after a subnet is selected. As such, it
is not possible to use KNOWN/UNKNOWN classes to select a shared
network or a subnet.
</para>

<para>
The process of doing classification is conducted in five steps.
The first step is to assess an incoming packet and assign it to
zero or more classes.
The second step is to choose a subnet, possibly based on the
class information.
The next step is to evaluate class expressions depending on the
built-in "KNOWN"/"UNKNOWN" classes after host reservation lookup,
using them for pool selection and to assign classes from host reservations.
After the list of required classes is built and each class of the list
has its expression evaluated: when it returns true the packet is added
as a member of the class.
Expand Down Expand Up @@ -3616,9 +3631,9 @@ It is merely echoed by the server
</screen>

<para>Static class assignments, as shown above, can be used in conjunction
with classification using expressions. The "KNOWN" builtin class is
added to the packet and any class depending on it directly or indirectly
and not only-if-required is evaluated.
with classification using expressions. The "KNOWN" or "UNKNOWN" builtin
class is added to the packet and any class depending on it directly or
indirectly and not only-if-required is evaluated.
</para>

<note>
Expand Down
32 changes: 24 additions & 8 deletions doc/guide/dhcp6-srv.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2237,11 +2237,27 @@ should include options from the isc option space:
</para>

<para>
The process of doing classification is conducted in several steps. The first step
is to assess an incoming packet and assign it to zero or more classes. The
second step is to choose a subnet, possibly based on the class information.
The third step is to assign classes from host reservations and
evaluate class expressions depending on the "KNOWN" class.
In a similar way a pool can be constrained to serve only known
clients, i.e. clients which have a reservation, using the
built-in "KNOWN" or "UNKNOWN" classes. One can assign addresses
to registered clients without giving a different address per
reservations, for instance when there is not enough available
addresses. The determination whether there is a reservation
for a given client is made after a subnet is selected. As such, it
is not possible to use KNOWN/UNKNOWN classes to select a shared
network or a subnet.
</para>

<para>
The process of doing classification is conducted in five steps.
The first step is to assess an incoming packet and assign it to
zero or more classes.
The second step is to choose a subnet, possibly based on the
class information.
The next step is to evaluate class expressions depending on the
built-in "KNOWN"/"UNKNOWN" classes after host reservation lookup,
using them for pool/pd-pool selection and to assign classes from host
reservations.
After the list of required classes is built and each class of the list
has its expression evaluated: when it returns true the packet is added
as a member of the class.
Expand Down Expand Up @@ -3271,9 +3287,9 @@ should include options from the isc option space:

</screen>
<para>Static class assignments, as shown above, can be used in conjunction
with classification using expressions. The "KNOWN" builtin class is
added to the packet and any class depending on it directly or indirectly
and not only-if-required is evaluated.
with classification using expressions. The "KNOWN" or "UNKNOWN" builtin
class is added to the packet and any class depending on it directly or
indirectly and not only-if-required is evaluated.
</para>

<note>
Expand Down
28 changes: 26 additions & 2 deletions src/bin/dhcp4/dhcp4_srv.cc
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,22 @@ Dhcpv4Exchange::Dhcpv4Exchange(const AllocEnginePtr& alloc_engine,
}
}

// Set KNOWN builtin class if something was found, UNKNOWN if not.
if (!context_->hosts_.empty()) {
query->addClass("KNOWN");
LOG_DEBUG(dhcp4_logger, DBG_DHCP4_BASIC, DHCP4_CLASS_ASSIGNED)
.arg(query->getLabel())
.arg("KNOWN");
} else {
query->addClass("UNKNOWN");
LOG_DEBUG(dhcp4_logger, DBG_DHCP4_BASIC, DHCP4_CLASS_ASSIGNED)
.arg(query->getLabel())
.arg("UNKNOWN");
}

// Perform second pass of classification.
Dhcpv4Srv::evaluateClasses(query, true);

const ClientClasses& classes = query_->getClasses();
if (!classes.empty()) {
LOG_DEBUG(dhcp4_logger, DBG_DHCP4_BASIC, DHCP4_CLASS_ASSIGNED)
Expand Down Expand Up @@ -3197,10 +3213,14 @@ void Dhcpv4Srv::classifyPacket(const Pkt4Ptr& pkt) {
// All packets belongs to ALL.
pkt->addClass("ALL");

// First phase: built-in vendor class processing
// First: built-in vendor class processing.
classifyByVendor(pkt);

// Run match expressions
// Run match expressions on classes not depending on KNOWN/UNKNOWN.
evaluateClasses(pkt, false);
}

void Dhcpv4Srv::evaluateClasses(const Pkt4Ptr& pkt, bool depend_on_known) {
// Note getClientClassDictionary() cannot be null
const ClientClassDictionaryPtr& dict =
CfgMgr::instance().getCurrentCfg()->getClientClassDictionary();
Expand All @@ -3217,6 +3237,10 @@ void Dhcpv4Srv::classifyPacket(const Pkt4Ptr& pkt) {
if ((*it)->getRequired()) {
continue;
}
// Not the right pass.
if ((*it)->getDependOnKnown() != depend_on_known) {
continue;
}
// Evaluate the expression which can return false (no match),
// true (match) or raise an exception (error)
try {
Expand Down
16 changes: 16 additions & 0 deletions src/bin/dhcp4/dhcp4_srv.h
Original file line number Diff line number Diff line change
Expand Up @@ -850,6 +850,22 @@ class Dhcpv4Srv : public Daemon {
/// @param pkt packet to be classified
void classifyPacket(const Pkt4Ptr& pkt);

public:

/// @brief Evaluate classes.
///
/// @note Second part of the classification.
///
/// Evaluate expressions of client classes: if it returns true the class
/// is added to the incoming packet.
///
/// @param pkt packet to be classified.
/// @param depend_on_known if false classes depending on the KNOWN or
/// UNKNOWN classes are skipped, if true only these classes are evaluated.
static void evaluateClasses(const Pkt4Ptr& pkt, bool depend_on_known);

protected:

/// @brief Assigns incoming packet to zero or more classes (required pass).
///
/// @note This required classification evaluates all classes which
Expand Down
Loading

0 comments on commit 6a856ed

Please sign in to comment.