Hi Naveen,

Thanks for the patch!

On 5/14/26 7:06 PM, Naveen Yerramneni wrote:
> DHCP client extends its lease by unicasting a DHCPREQUEST to its
> original DHCP server when the T1 timer fires (typically at 50% of
> the lease).  If that DHCPREQUEST gets no response, the T2 timer
> fires (typically at 87.5% of the lease) and the client enters the
> REBINDING state, where it broadcasts a DHCPREQUEST using its
> currently leased IP as the source address (rather than 0.0.0.0).
> 
> Today OVN's DHCP relay only matches DHCPREQUEST packets whose source
> IP is 0.0.0.0, so the broadcast DHCPREQUEST sent by a client in the
> REBINDING state is not matched by any relay flow and is dropped.
> The lease cannot be renewed through the relay and the client
> eventually falls back to a fresh DISCOVER.
> 
> Extend the relay to also forward DHCPREQUEST packets whose source IP
> lies in the relay LRP's subnet by widening the source-IP match of
> the DHCP relay request flows to the set
> ip4.src == {0.0.0.0, <lrp_cidr>}, where <lrp_cidr> is the CIDR of
> the relay Logical_Router_Port.  The set is applied to:
> 
> - The priority-100 logical switch flow in ls_in_l2_lkup that
> forwards client DHCP broadcasts to the relay LRP-attachment
> port.
> - The logical router lr_in_ip_input priority-110
> dhcp_relay_req_chk flow.
> - The lr_in_dhcp_relay_req priority-100 forward and priority-1
> drop flows.
> 
> The behaviour is controlled by a new NB_Global option:
> 
> options:dhcp_relay_handle_rebind   boolean (default 'true')
> 
> Setting it to 'false' restores the previous behaviour and matches
> only ip4.src == 0.0.0.0.
>

If we're changing defaults, why not just make it the only behavior?
IIUC you're just extending the existing implementation, right?

Also, this patch fails CI:
https://github.com/ovsrobot/ovn/actions/runs/25747657870/job/75615787412

1
Expecting global_config compute count -  2  not to be 0
test  2  -ne 0
./ovn-macros.at:897: "$@"
Checking engine stats for node northd : recompute - norecompute :
compute - compute
Expecting northd recompute count -  1  to be 0
test  1  -eq 0
./ovn-macros.at:897: "$@"
./ovn-macros.at:897: exit code was 1, expected 0
815. ovn-northd.at:13500: 815. NB_Global and SB_Global incremental
processing (ovn-northd.at:13500): FAILED ( 1 )

Regards,
Dumitru


> Signed-off-by: Naveen Yerramneni <[email protected]>
> Acked-by: Aditya Mehakare <[email protected]>
> Acked-by: Huzaifa Calcuttawala <[email protected]>
> ---
> V2:
>   - consider dhcp_relay_handle_rebind as optional to avoid unwanted
>     northd recompute.
> ---
>  Documentation/ref/ovn-logical-flows.7.rst | 32 ++++++++------
>  NEWS                                      |  5 +++
>  northd/en-global-config.c                 |  5 +++
>  northd/northd.c                           | 51 +++++++++++++++++++----
>  ovn-nb.xml                                | 18 ++++++++
>  tests/ovn-northd.at                       | 48 ++++++++++++++++++---
>  tests/ovn.at                              |  9 +++-
>  7 files changed, 140 insertions(+), 28 deletions(-)
> 
> diff --git a/Documentation/ref/ovn-logical-flows.7.rst 
> b/Documentation/ref/ovn-logical-flows.7.rst
> index 0b69d7bb0..0d46301b3 100644
> --- a/Documentation/ref/ovn-logical-flows.7.rst
> +++ b/Documentation/ref/ovn-logical-flows.7.rst
> @@ -1392,7 +1392,9 @@ This table implements switching behavior.  It contains 
> these logical flows:
>  
>  - A priority-100 flow that forwards all DHCP broadcast packets coming from 
> VIFs
>    to the logical router port's MAC when DHCP relay is enabled on the logical
> -  switch.
> +  switch.  By default the ``ip4.src`` match is the set ``{0.0.0.0, 
> lrp_cidr}``.
> +  If ``dhcp_relay_handle_rebind`` in the ``NB_Global`` ``options`` column is 
> set
> +  to ``false`` the match is ``ip4.src == 0.0.0.0`` only.
>  
>  - A priority-100 flow that matches ``reg8[23] == 1`` and does ``output`` 
> action.
>    This ensures that packets that got injected back into this table from 
> egress
> @@ -2199,9 +2201,11 @@ contains the following flows to implement very basic 
> IP host functionality.
>  - For each logical router port configured with DHCP relay the following
>    priority-110 flows are added to manage the DHCP relay traffic:
>  
> -  - if ``inport`` is lrp and ``ip4.src == 0.0.0.0`` and ``ip4.dst ==
> -    255.255.255.255`` and ``ip4.frag == 0`` and ``udp.src == 68`` and 
> ``udp.dst
> -    == 67``, the ``dhcp_relay_req_chk`` action is executed. ::
> +  - if ``inport`` is lrp and ``ip4.src == {0.0.0.0, lrp_cidr}`` and ``ip4.dst
> +    == 255.255.255.255`` and ``ip4.frag == 0`` and ``udp.src == 68`` and
> +    ``udp.dst == 67``, the ``dhcp_relay_req_chk`` action is executed.  
> Setting
> +    ``dhcp_relay_handle_rebind`` in the ``NB_Global`` ``options`` column to
> +    ``false`` restricts the ``ip4.src`` match to ``0.0.0.0`` only. ::
>  
>          reg9[7] = dhcp_relay_req_chk(lrp_ip, dhcp_server_ip);next
>  
> @@ -2499,10 +2503,12 @@ This stage process the DHCP request packets on which 
> ``dhcp_relay_req_chk``
>  action is applied in the IP input stage.
>  
>  - A priority-100 logical flow is added for each logical router port 
> configured
> -  with DHCP relay that matches ``inport`` is lrp and ``ip4.src == 0.0.0.0`` 
> and
> -  ``ip4.dst == 255.255.255.255`` and ``udp.src == 68`` and ``udp.dst == 67`` 
> and
> -  ``reg9[7] == 1`` and applies following actions. If ``reg9[7]`` is set to 1
> -  then, ``dhcp_relay_req_chk`` action was successful. ::
> +  with DHCP relay that matches ``inport`` is lrp and ``ip4.src == {0.0.0.0,
> +  lrp_cidr}`` and ``ip4.dst == 255.255.255.255`` and ``udp.src == 68`` and
> +  ``udp.dst == 67`` and ``reg9[7] == 1`` and applies following actions. If
> +  ``reg9[7]`` is set to 1 then, ``dhcp_relay_req_chk`` action was successful.
> +  Setting ``dhcp_relay_handle_rebind`` in the ``NB_Global`` ``options`` 
> column
> +  to ``false`` restricts the ``ip4.src`` match to ``0.0.0.0`` only. ::
>  
>        ip4.src=lrp ip;
>        ip4.dst=dhcp server ip;
> @@ -2510,10 +2516,12 @@ action is applied in the IP input stage.
>        next;
>  
>  - A priority-1 logical flow is added for each logical router port configured
> -  with DHCP relay that matches ``inport`` is lrp and ``ip4.src == 0.0.0.0`` 
> and
> -  ``ip4.dst == 255.255.255.255`` and ``udp.src == 68`` and ``udp.dst == 67`` 
> and
> -  ``reg9[7] == 0`` and drops the packet. If ``reg9[7]`` is set to 0 then,
> -  ``dhcp_relay_req_chk`` action was unsuccessful.
> +  with DHCP relay that matches ``inport`` is lrp and ``ip4.src == {0.0.0.0,
> +  lrp_cidr}`` and ``ip4.dst == 255.255.255.255`` and ``udp.src == 68`` and
> +  ``udp.dst == 67`` and ``reg9[7] == 0`` and drops the packet. If ``reg9[7]``
> +  is set to 0 then, ``dhcp_relay_req_chk`` action was unsuccessful.  Setting
> +  ``dhcp_relay_handle_rebind`` in the ``NB_Global`` ``options`` column to
> +  ``false`` restricts the ``ip4.src`` match to ``0.0.0.0`` only.
>  
>  - A priority-0 flow that matches all packets to advance to the next table.
>  
> diff --git a/NEWS b/NEWS
> index 9839d19b9..4e8df14ae 100644
> --- a/NEWS
> +++ b/NEWS
> @@ -12,6 +12,11 @@ Post v26.03.0
>       * Add ECMP/multi-homing support for EVPN FDB entries. FDB entries
>         backed by a kernel nexthop group are load-balanced via OpenFlow
>         select groups with weighted buckets.
> +   - The DHCP relay now also forwards DHCPREQUEST packets whose
> +     source IP lies in the relay LRP's subnet, in addition to
> +     ip4.src == 0.0.0.0.  Controlled by the new NB_Global option
> +     dhcp_relay_handle_rebind (default true); set it to false to
> +     match only ip4.src == 0.0.0.0.
>  
>  OVN v26.03.0 - xxx xx xxxx
>  --------------------------
> diff --git a/northd/en-global-config.c b/northd/en-global-config.c
> index d49ddb94a..7fb16b9d7 100644
> --- a/northd/en-global-config.c
> +++ b/northd/en-global-config.c
> @@ -724,6 +724,11 @@ check_nb_options_out_of_sync(
>          return true;
>      }
>  
> +    if (config_out_of_sync(&nb->options, &config_data->nb_options,
> +                           "dhcp_relay_handle_rebind", false)) {
> +        return true;
> +    }
> +
>      return false;
>  }
>  
> diff --git a/northd/northd.c b/northd/northd.c
> index 8305e0428..16c5916a9 100644
> --- a/northd/northd.c
> +++ b/northd/northd.c
> @@ -105,6 +105,11 @@ static bool default_acl_drop;
>   * and ports tunnel key allocation (12 bits for each instead of default 16). 
> */
>  static bool vxlan_mode;
>  
> +/* If 'true' (default), DHCP relay flows match both ip4.src == 0.0.0.0
> + * and ip4.src within the relay LRP's CIDR.  If 'false', only
> + * ip4.src == 0.0.0.0 is matched. */
> +static bool dhcp_relay_handle_rebind = true;
> +
>  #define MAX_OVN_TAGS 4096
>  
>  #define MAX_OVN_NF_GROUP_IDS 256
> @@ -10072,14 +10077,25 @@ build_lswitch_dhcp_relay_flows(struct ovn_port *op,
>      ds_clear(match);
>      ds_clear(actions);
>  
> +    /* Match 0.0.0.0 and the LRP's CIDR when 'dhcp_relay_handle_rebind'
> +     * is enabled (default); match only 0.0.0.0 when disabled. */
> +    struct ds src_ip_match = DS_EMPTY_INITIALIZER;
> +    if (dhcp_relay_handle_rebind && rp->lrp_networks.n_ipv4_addrs > 0) {
> +        ds_put_format(&src_ip_match, "ip4.src == {0.0.0.0, %s/%u}",
> +                      rp->lrp_networks.ipv4_addrs[0].network_s,
> +                      rp->lrp_networks.ipv4_addrs[0].plen);
> +    } else {
> +        ds_put_cstr(&src_ip_match, "ip4.src == 0.0.0.0");
> +    }
> +
>      ds_put_format(
>          match, "inport == %s && eth.src == %s && "
> -        "ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && "
> +        "%s && ip4.dst == 255.255.255.255 && "
>          "udp.src == 68 && udp.dst == 67",
> -        op->json_key, op->lsp_addrs[0].ea_s);
> +        op->json_key, op->lsp_addrs[0].ea_s, ds_cstr(&src_ip_match));
>      ds_put_format(actions,
>                    "eth.dst = %s; outport = %s; next; /* DHCP_RELAY_REQ */",
> -                  rp->lrp_networks.ea_s,sp->json_key);
> +                  rp->lrp_networks.ea_s, sp->json_key);
>      ovn_lflow_add(lflows, op->od,
>                    S_SWITCH_IN_L2_LKUP, 100,
>                    ds_cstr(match),
> @@ -10089,6 +10105,8 @@ build_lswitch_dhcp_relay_flows(struct ovn_port *op,
>                    WITH_HINT(&op->nbsp->header_));
>      ds_clear(match);
>      ds_clear(actions);
> +    ds_destroy(&src_ip_match);
> +
>      free(server_ip_str);
>  }
>  
> @@ -16734,11 +16752,22 @@ build_dhcp_relay_flows_for_lrouter_port(struct 
> ovn_port *op,
>      ds_clear(match);
>      ds_clear(actions);
>  
> +    /* Match 0.0.0.0 and the LRP's CIDR when 'dhcp_relay_handle_rebind'
> +     * is enabled (default); match only 0.0.0.0 when disabled. */
> +    struct ds src_ip_match = DS_EMPTY_INITIALIZER;
> +    if (dhcp_relay_handle_rebind) {
> +        ds_put_format(&src_ip_match, "ip4.src == {0.0.0.0, %s/%u}",
> +                      op->lrp_networks.ipv4_addrs[0].network_s,
> +                      op->lrp_networks.ipv4_addrs[0].plen);
> +    } else {
> +        ds_put_cstr(&src_ip_match, "ip4.src == 0.0.0.0");
> +    }
> +
>      ds_put_format(
>          match, "inport == %s && "
> -        "ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && "
> +        "%s && ip4.dst == 255.255.255.255 && "
>          "ip.frag == 0 && udp.src == 68 && udp.dst == 67",
> -        op->json_key);
> +        op->json_key, ds_cstr(&src_ip_match));
>      ds_put_format(actions,
>                    REGBIT_DHCP_RELAY_REQ_CHK
>                    " = dhcp_relay_req_chk(%s, %s);"
> @@ -16757,10 +16786,10 @@ build_dhcp_relay_flows_for_lrouter_port(struct 
> ovn_port *op,
>  
>      ds_put_format(
>          match, "inport == %s && "
> -        "ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && "
> +        "%s && ip4.dst == 255.255.255.255 && "
>          "udp.src == 68 && udp.dst == 67 && "
>          REGBIT_DHCP_RELAY_REQ_CHK,
> -        op->json_key);
> +        op->json_key, ds_cstr(&src_ip_match));
>      ds_put_format(actions,
>                    "ip4.src = %s; ip4.dst = %s; udp.src = 67; next; "
>                    "/* DHCP_RELAY_REQ */",
> @@ -16775,10 +16804,10 @@ build_dhcp_relay_flows_for_lrouter_port(struct 
> ovn_port *op,
>  
>      ds_put_format(
>          match, "inport == %s && "
> -        "ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && "
> +        "%s && ip4.dst == 255.255.255.255 && "
>          "udp.src == 68 && udp.dst == 67 && "
>          REGBIT_DHCP_RELAY_REQ_CHK" == 0",
> -        op->json_key);
> +        op->json_key, ds_cstr(&src_ip_match));
>      ds_put_format(actions, "drop; /* DHCP_RELAY_REQ */");
>  
>      ovn_lflow_add(lflows, op->od, S_ROUTER_IN_DHCP_RELAY_REQ, 1,
> @@ -16787,6 +16816,7 @@ build_dhcp_relay_flows_for_lrouter_port(struct 
> ovn_port *op,
>  
>      ds_clear(match);
>      ds_clear(actions);
> +    ds_destroy(&src_ip_match);
>  
>      ds_put_format(
>          match, "ip4.src == %s && ip4.dst == %s && "
> @@ -21249,6 +21279,9 @@ ovnnb_db_run(struct northd_input *input_data,
>                                                false);
>      use_common_zone = smap_get_bool(input_data->nb_options, 
> "use_common_zone",
>                                      false);
> +    dhcp_relay_handle_rebind = smap_get_bool(input_data->nb_options,
> +                                             "dhcp_relay_handle_rebind",
> +                                             true);
>  
>      vxlan_mode = input_data->vxlan_mode;
>  
> diff --git a/ovn-nb.xml b/ovn-nb.xml
> index 2e8a6a6f1..f5fb775b5 100644
> --- a/ovn-nb.xml
> +++ b/ovn-nb.xml
> @@ -464,6 +464,24 @@
>          </p>
>        </column>
>  
> +      <column name="options" key="dhcp_relay_handle_rebind"
> +              type='{"type": "boolean"}'>
> +        <p>
> +          Default is <code>true</code>.  The DHCP relay forwards both
> +          broadcast DHCPREQUEST packets sent with no source IP
> +          assigned and those sent with the client's currently leased
> +          IP as the source address.  The latter are typically sent by
> +          clients in the REBINDING state (T2 timer expiry) when they
> +          cannot reach their original DHCP server.
> +        </p>
> +
> +        <p>
> +          Set to <code>false</code> to forward only DHCPREQUEST
> +          packets sent with no source IP assigned.  Refer to
> +          <code>ovn-northd</code>(8) for the exact logical-flow match.
> +        </p>
> +      </column>
> +
>        <group title="Options for services health check confguration">
>          <p>
>            These options are used when health configuration is enabled for
> diff --git a/tests/ovn-northd.at b/tests/ovn-northd.at
> index 074b1526b..52b4f78a0 100644
> --- a/tests/ovn-northd.at
> +++ b/tests/ovn-northd.at
> @@ -13394,23 +13394,43 @@ check ovn-nbctl --wait=sb sync
>  ovn-sbctl lflow-list > lflows
>  AT_CAPTURE_FILE([lflows])
>  
> +# Default: match the set {0.0.0.0, lrp_cidr}.
>  AT_CHECK([grep -e "DHCP_RELAY_" lflows | sed 's/table=../table=??/'], [0], 
> [dnl
> -  table=??(lr_in_ip_input     ), priority=110  , match=(inport == "lrp1" && 
> ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && ip.frag == 0 && udp.src 
> == 68 && udp.dst == 67), action=(reg9[[7]] = dhcp_relay_req_chk(192.168.1.1, 
> 172.16.1.1);next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_ip_input     ), priority=110  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && ip.frag 
> == 0 && udp.src == 68 && udp.dst == 67), action=(reg9[[7]] = 
> dhcp_relay_req_chk(192.168.1.1, 172.16.1.1);next; /* DHCP_RELAY_REQ */)
>    table=??(lr_in_ip_input     ), priority=110  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && ip.frag == 0 && udp.src == 67 && 
> udp.dst == 67), action=(next; /* DHCP_RELAY_RESP */)
> -  table=??(lr_in_dhcp_relay_req), priority=100  , match=(inport == "lrp1" && 
> ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && udp.src == 68 && udp.dst 
> == 67 && reg9[[7]]), action=(ip4.src = 192.168.1.1; ip4.dst = 172.16.1.1; 
> udp.src = 67; next; /* DHCP_RELAY_REQ */)
> -  table=??(lr_in_dhcp_relay_req), priority=1    , match=(inport == "lrp1" && 
> ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && udp.src == 68 && udp.dst 
> == 67 && reg9[[7]] == 0), action=(drop; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_req), priority=100  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]]), action=(ip4.src = 192.168.1.1; ip4.dst 
> = 172.16.1.1; udp.src = 67; next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_req), priority=1    , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]] == 0), action=(drop; /* DHCP_RELAY_REQ */)
>    table=??(lr_in_dhcp_relay_resp_chk), priority=100  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && udp.src == 67 && udp.dst == 67), 
> action=(reg2 = ip4.dst; reg9[[8]] = dhcp_relay_resp_chk(192.168.1.1, 
> 172.16.1.1); next; /* DHCP_RELAY_RESP */)
>    table=??(lr_in_dhcp_relay_resp), priority=100  , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]]), action=(ip4.src = 192.168.1.1; udp.dst = 68; outport = "lrp1"; 
> output; /* DHCP_RELAY_RESP */)
>    table=??(lr_in_dhcp_relay_resp), priority=1    , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]] == 0), action=(drop; /* DHCP_RELAY_RESP */)
> -  table=??(ls_in_l2_lkup      ), priority=100  , match=(inport == 
> "ls0-port1" && eth.src == 02:00:00:00:00:10 && ip4.src == 0.0.0.0 && ip4.dst 
> == 255.255.255.255 && udp.src == 68 && udp.dst == 67), action=(eth.dst = 
> 02:00:00:00:00:01; outport = "lrp1-attachment"; next; /* DHCP_RELAY_REQ */)
> +  table=??(ls_in_l2_lkup      ), priority=100  , match=(inport == 
> "ls0-port1" && eth.src == 02:00:00:00:00:10 && ip4.src == {0.0.0.0, 
> 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src == 68 && udp.dst == 
> 67), action=(eth.dst = 02:00:00:00:00:01; outport = "lrp1-attachment"; next; 
> /* DHCP_RELAY_REQ */)
>  ])
>  
> -# Set invalid dhcp_relay_port in ls0
> +# Invalid dhcp_relay_port: the ls_in_l2_lkup flow is suppressed; the
> +# logical router flows keep the default match.
>  check ovn-nbctl --wait=sb set Logical_Switch ls0 
> other_config:dhcp_relay_port=foo
>  
>  ovn-sbctl lflow-list > lflows
>  AT_CAPTURE_FILE([lflows])
>  
> +AT_CHECK([grep -e "DHCP_RELAY_" lflows | sed 's/table=../table=??/'], [0], 
> [dnl
> +  table=??(lr_in_ip_input     ), priority=110  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && ip.frag 
> == 0 && udp.src == 68 && udp.dst == 67), action=(reg9[[7]] = 
> dhcp_relay_req_chk(192.168.1.1, 172.16.1.1);next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_ip_input     ), priority=110  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && ip.frag == 0 && udp.src == 67 && 
> udp.dst == 67), action=(next; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_req), priority=100  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]]), action=(ip4.src = 192.168.1.1; ip4.dst 
> = 172.16.1.1; udp.src = 67; next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_req), priority=1    , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]] == 0), action=(drop; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_resp_chk), priority=100  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && udp.src == 67 && udp.dst == 67), 
> action=(reg2 = ip4.dst; reg9[[8]] = dhcp_relay_resp_chk(192.168.1.1, 
> 172.16.1.1); next; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_resp), priority=100  , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]]), action=(ip4.src = 192.168.1.1; udp.dst = 68; outport = "lrp1"; 
> output; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_resp), priority=1    , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]] == 0), action=(drop; /* DHCP_RELAY_RESP */)
> +])
> +
> +# Restore the relay port and disable dhcp_relay_handle_rebind: the
> +# relay flows now match only ip4.src == 0.0.0.0.
> +check ovn-nbctl set Logical_Switch ls0 
> other_config:dhcp_relay_port=lrp1-attachment
> +check ovn-nbctl --wait=sb set NB_Global . 
> options:dhcp_relay_handle_rebind=false
> +
> +ovn-sbctl lflow-list > lflows
> +AT_CAPTURE_FILE([lflows])
> +
>  AT_CHECK([grep -e "DHCP_RELAY_" lflows | sed 's/table=../table=??/'], [0], 
> [dnl
>    table=??(lr_in_ip_input     ), priority=110  , match=(inport == "lrp1" && 
> ip4.src == 0.0.0.0 && ip4.dst == 255.255.255.255 && ip.frag == 0 && udp.src 
> == 68 && udp.dst == 67), action=(reg9[[7]] = dhcp_relay_req_chk(192.168.1.1, 
> 172.16.1.1);next; /* DHCP_RELAY_REQ */)
>    table=??(lr_in_ip_input     ), priority=110  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && ip.frag == 0 && udp.src == 67 && 
> udp.dst == 67), action=(next; /* DHCP_RELAY_RESP */)
> @@ -13419,6 +13439,24 @@ AT_CHECK([grep -e "DHCP_RELAY_" lflows | sed 
> 's/table=../table=??/'], [0], [dnl
>    table=??(lr_in_dhcp_relay_resp_chk), priority=100  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && udp.src == 67 && udp.dst == 67), 
> action=(reg2 = ip4.dst; reg9[[8]] = dhcp_relay_resp_chk(192.168.1.1, 
> 172.16.1.1); next; /* DHCP_RELAY_RESP */)
>    table=??(lr_in_dhcp_relay_resp), priority=100  , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]]), action=(ip4.src = 192.168.1.1; udp.dst = 68; outport = "lrp1"; 
> output; /* DHCP_RELAY_RESP */)
>    table=??(lr_in_dhcp_relay_resp), priority=1    , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]] == 0), action=(drop; /* DHCP_RELAY_RESP */)
> +  table=??(ls_in_l2_lkup      ), priority=100  , match=(inport == 
> "ls0-port1" && eth.src == 02:00:00:00:00:10 && ip4.src == 0.0.0.0 && ip4.dst 
> == 255.255.255.255 && udp.src == 68 && udp.dst == 67), action=(eth.dst = 
> 02:00:00:00:00:01; outport = "lrp1-attachment"; next; /* DHCP_RELAY_REQ */)
> +])
> +
> +# Remove the option: flows revert to the default match.
> +check ovn-nbctl --wait=sb remove NB_Global . options dhcp_relay_handle_rebind
> +
> +ovn-sbctl lflow-list > lflows
> +AT_CAPTURE_FILE([lflows])
> +
> +AT_CHECK([grep -e "DHCP_RELAY_" lflows | sed 's/table=../table=??/'], [0], 
> [dnl
> +  table=??(lr_in_ip_input     ), priority=110  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && ip.frag 
> == 0 && udp.src == 68 && udp.dst == 67), action=(reg9[[7]] = 
> dhcp_relay_req_chk(192.168.1.1, 172.16.1.1);next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_ip_input     ), priority=110  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && ip.frag == 0 && udp.src == 67 && 
> udp.dst == 67), action=(next; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_req), priority=100  , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]]), action=(ip4.src = 192.168.1.1; ip4.dst 
> = 172.16.1.1; udp.src = 67; next; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_req), priority=1    , match=(inport == "lrp1" && 
> ip4.src == {0.0.0.0, 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src 
> == 68 && udp.dst == 67 && reg9[[7]] == 0), action=(drop; /* DHCP_RELAY_REQ */)
> +  table=??(lr_in_dhcp_relay_resp_chk), priority=100  , match=(ip4.src == 
> 172.16.1.1 && ip4.dst == 192.168.1.1 && udp.src == 67 && udp.dst == 67), 
> action=(reg2 = ip4.dst; reg9[[8]] = dhcp_relay_resp_chk(192.168.1.1, 
> 172.16.1.1); next; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_resp), priority=100  , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]]), action=(ip4.src = 192.168.1.1; udp.dst = 68; outport = "lrp1"; 
> output; /* DHCP_RELAY_RESP */)
> +  table=??(lr_in_dhcp_relay_resp), priority=1    , match=(ip4.src == 
> 172.16.1.1 && reg2 == 192.168.1.1 && udp.src == 67 && udp.dst == 67 && 
> reg9[[8]] == 0), action=(drop; /* DHCP_RELAY_RESP */)
> +  table=??(ls_in_l2_lkup      ), priority=100  , match=(inport == 
> "ls0-port1" && eth.src == 02:00:00:00:00:10 && ip4.src == {0.0.0.0, 
> 192.168.1.0/24} && ip4.dst == 255.255.255.255 && udp.src == 68 && udp.dst == 
> 67), action=(eth.dst = 02:00:00:00:00:01; outport = "lrp1-attachment"; next; 
> /* DHCP_RELAY_REQ */)
>  ])
>  
>  # Clear the dhcp_relay from lrp1
> diff --git a/tests/ovn.at b/tests/ovn.at
> index fbaa63d99..0e2299b81 100644
> --- a/tests/ovn.at
> +++ b/tests/ovn.at
> @@ -41221,8 +41221,12 @@ sid=$src_ip
>  # send packet
>  send_dhcp_packet $src_mac $src_ip $dst_mac $dst_ip 01 01 $yiaddr $giaddr 
> $sid vif0
>  
> +# The default set match ip4.src == {0.0.0.0, lrp_cidr} compiles to
> +# two OF flows; only the 0.0.0.0 one sees the DISCOVER packet.
> +# Sort for stable ordering.
>  OVS_WAIT_FOR_OUTPUT([ovs-ofctl dump-flows br-int table=$dhcp_relay_req_table 
> | grep -v NXST | grep 255.255.255.255 | grep resubmit |
> -cut -d ' ' -f5-5 | sed "s/,//"], [0], [dnl
> +cut -d ' ' -f5-5 | sed "s/,//" | sort], [0], [dnl
> +n_packets=0
>  n_packets=1
>  ])
>  
> @@ -41233,7 +41237,8 @@ giaddr=`ip_to_hex 192.168.1.1`
>  send_dhcp_packet $src_mac $src_ip $dst_mac $dst_ip 01 01 $yiaddr $giaddr 
> $sid vif0
>  
>  OVS_WAIT_FOR_OUTPUT([ovs-ofctl dump-flows br-int table=$dhcp_relay_req_table 
> | grep -v NXST | grep 255.255.255.255 | grep drop |
> -cut -d ' ' -f5-5 | sed "s/,//"], [0], [dnl
> +cut -d ' ' -f5-5 | sed "s/,//" | sort], [0], [dnl
> +n_packets=0
>  n_packets=1
>  ])
>  

_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev

Reply via email to