On Fri, May 06, 2016 at 08:16:16PM +0530, Numan Siddique wrote: > This patch adds a new OVN action 'dhcp_offer' to support native > DHCP in OVN. > > 'dhcp_offer' takes the DHCP options as input params. > Eg. dhcp_offer(offerip = 10.0.0.4, router = 10.0.0.1, > netmask = 255.255.255.0, lease_time = 3600,....) > > ovn-controller parses this action and adds a NXT_PACKET_IN2 > OF flow with 'pause' flag set and the DHCP options stored in > 'userdata' field. > > When the DHCP packet is received by ovn-controller, it frames a > new DHCP reply packet with the DHCP options present in the > 'userdata' field and resumes the packet. > > Eg. dhcp_offer(offerip = 10.0.0.4, router = 10.0.0.1, > netmask = 255.255.255.0, lease_time = 3600,....) > > A new 'DHCP_Options' table is added in SB DB which stores > the support DHCP options with DHCP code and type. ovn-northd is > expected to popule this table. > > The next patch will add logical flows with this action. > > Signed-Off-by: Numan Siddique <nusid...@redhat.com>
Thanks for sending v4! pinctrl_handle_dhcp_offer() is not very skeptical about the contents of buffers. I think that it should do checking, e.g.: ovs_be32 *offer_ip = ofpbuf_try_pull(userdata, sizeof *offer_ip); if (!offer_ip) { /* XXX */ } if (dp_packet_l4_size(pkt) < UDP_HEADER_LEN + sizeof (struct dhcp_header) + sizeof(uint32_t) + 3) { /* XXX */ } The DHCP parsing looked totally bizarre before I re-read the DHCP RFC and re-discovered that in fact the DHCP type is 6 bytes past the DHCP header for compatibility with BOOTP. A comment might help. These casts shouldn't be needed: dhcp_options[0] = (uint8_t) DHCP_OPT_MSG_TYPE; dhcp_options[1] = (uint8_t) 1; It would probably be better to use names that are less easily confused than 'pkt' for the input and 'packet' for the output. 'in' and 'out', 'src' and 'dst', 'old' and 'new', whatever, I don't care much as long as they're distinct.. It's risky to assume that the L2 header in the input packet is exactly ETH_HEADER_LEN bytes (what if there's a VLAN? or an MPLS header?) and that the L3 header is exactly IP_HEADER_LEN bytes. The input packet has l2 and l3 pointers and lengths, please use them (including in the IP total length and csum calculations). Why zero the IP TOS field? Oh, also s/pinctl/pinctrl/ in the function name. GCC points out some format specifiers that need updates: diff --git a/tests/test-ovn-dhcp.c b/tests/test-ovn-dhcp.c index 60726d9..d55299b 100644 --- a/tests/test-ovn-dhcp.c +++ b/tests/test-ovn-dhcp.c @@ -102,7 +102,7 @@ test_dhcp_offer_action(int argc OVS_UNUSED, char *argv[] OVS_UNUSED) if (oc->userdata_len != (expected_dhcp_opts.size + sizeof *ah)) { ovs_fatal(1, "Error. dhcp_offer parse action failed : userdata length" - " mismatch. Expected - %lu : Actual - %u", + " mismatch. Expected - %"PRIuSIZE" : Actual - %"PRIu16, expected_dhcp_opts.size + sizeof *ah, oc->userdata_len); } I think that the documentation could be a little more detailed. For example, the action acts only on DHCPDISCOVER and DHCPREQUEST and does nothing to non-DHCP or other kinds of DHCP. In fact, is the latter a problem? I think that, currently, there is no way to detect that nothing happened, so I think that the DHCP server will end up sending the request back to the client as if it were a reply, which is really weird behavior. I can imagine a few different ways to avoid that, e.g.: - Have the action take a set of actions in {} that only get executed if it really does something. - Have the action set a field that only gets executed if it really does something. I'm also not sure that most people will be able to interpret the documentation for the DHCP_Options table. Can you add a little more exposition and refer to the RFCs that define options? Also a few examples? In particular I don't think that the DHCP_OPT_TYPE_* codes are anything standardized. I think that it would make more sense to put them into the database as "enum"s than as numbers, e.g. "bool", "uint8", ..., and then explain in the documentation what these mean. In parse_dhcp_option(), instead of using hard-coded offsets like cs.values[0].value.u8[127], please use accessors, like ntohll(cs.values[0].value.integer). Then nothing will break if the size of mf_subvalue changes. Maybe we should add more accessors. Please type-check the set in parse_dhcp_option(), that is, if the option is an integer, check that 'cs' is an integer, and similar for strings. Otherwise we could end up dereferencing a "pointer" that is actually an integer. In parse_dhcp_offer_action(), please free dhcp_opts on the error path too. Actually, can you parse the options directly into the ofpacts like this? I guess you'd need a special case for the offered IP, but there's already a special case for that. size_t oc_offset = start_controller_op(ctx->ofpacts, ACTION_OPCODE_DHCP_OFFER, true); while (!lexer_match(ctx->lexer, LEX_T_RPAREN)) { if (!parse_dhcp_option(ctx, ctx->ofpacts)) { return; } } finish_controller_op(ctx->ofpacts, oc_offset); Thanks a lot! Ben _______________________________________________ dev mailing list dev@openvswitch.org http://openvswitch.org/mailman/listinfo/dev