]> git.ipfire.org Git - thirdparty/dhcp.git/commitdiff
[v4_1_esv] Added "-iu" command line argument to dhcrelay
authorThomas Markwalder <tmark@isc.org>
Wed, 10 Aug 2016 18:52:01 +0000 (14:52 -0400)
committerThomas Markwalder <tmark@isc.org>
Wed, 10 Aug 2016 18:52:01 +0000 (14:52 -0400)
    Manually merged 41547a.

RELNOTES
common/discover.c
relay/dhcrelay.8
relay/dhcrelay.c

index 22be8bb8c59b9cbba5e5aba9e91ea9dd97ddd768..49447803a03450cc9de328d514bc298f1ac31349 100644 (file)
--- a/RELNOTES
+++ b/RELNOTES
@@ -104,6 +104,10 @@ by Eric Young (eay@cryptsoft.com).
   it runs out.
   [ISC-Bugs #42452]
 
+- Add a new command line option, "-iu", to dhcrelay which allows one
+  or more interfaces to be regisetered to listen only for BOOTP replies.
+  [ISC-Bugs #41547]
+
                        Changes since 4.1-ESV-R13b1
 
 - None
index da0c3f81d61de6b3e8a0ca14265c54913aa00655..81d20e085a64259ee7fa3bb81447972ef5b50329 100644 (file)
@@ -950,8 +950,14 @@ discover_interfaces(int state) {
                ir = 0;
        else if (state == DISCOVER_UNCONFIGURED)
                ir = INTERFACE_REQUESTED | INTERFACE_AUTOMATIC;
-       else
+       else {
                ir = INTERFACE_REQUESTED;
+               if (state == DISCOVER_RELAY && local_family == AF_INET) {
+                       /* We're a v4 relay without specifically requested
+                        * interfaces, so mark them all as bidirectional. */
+                       ir |= INTERFACE_STREAMS;
+               }
+       }
 
        /* Cycle through the list of interfaces looking for IP addresses. */
        while (next_iface(&info, &err, &ifaces)) {
index 91d4e6c2b10e30c6a4fc8a2334557ce3c95b2205..695a2145b3f549a0727a6d7af59f8b6522162af5 100644 (file)
@@ -76,6 +76,15 @@ dhcrelay - Dynamic Host Configuration Protocol Relay Agent
 [
 .B ...
 .B -i
+.I interfaceN
+]
+]
+[
+.B -iu
+.I interface0
+[
+.B ...
+.B -iu
 .I interfaceN 
 ]
 ]
@@ -196,12 +205,19 @@ a query that came via a different relay agent.  If this option is not
 specified, such packets will be relayed anyway.
 .TP
 -i \fIifname\fR
-Listen for DHCPv4/BOOTP queries on interface \fIifname\fR.  Multiple
+Listen for DHCPv4/BOOTP traffic on interface \fIifname\fR.  Multiple
 interfaces may be specified by using more than one \fB-i\fR option.  If
 no interfaces are specified on the command line, dhcrelay will identify
 all network interfaces, eliminating non-broadcast interfaces if possible,
 and attempt to listen on all of them.
 .TP
+-iu \fIifname\fR
+Specifies an upstream network interface for DHCPv4 relay mode: an
+interface from which replies from servers and other relay agents will be
+accepted.  Multiple interfaces may be specified by using more
+than one \fB-u\fR option.  This argument is intended to be used
+in conjunction with one or more -i arguments.
+.TP
 -m \fIappend\fR|\fIreplace\fR|\fIforward\fR|\fIdiscard\fR
 Control the handling of incoming DHCPv4 packets which already contain
 relay agent options.  If such a packet does not have \fIgiaddr\fR set in
index f52e64349cd0eff0aa68cbc8515c28130cb23686..a0bb5e69d34a586b3fa3d41ac8ef002aa50942a1 100644 (file)
@@ -141,6 +141,7 @@ char *progname;
 "                     [-pf <pid-file>] [--no-pid]\n"\
 "                     [-m append|replace|forward|discard]\n" \
 "                     [-i interface0 [ ... -i interfaceN]\n" \
+"                     [-ui interface0 [ ... -ui interfaceN]\n" \
 "                     server0 [ ... serverN]\n\n" \
 "       %s -6   [-d] [-q] [-I] [-c <hops>] [-p <port>]\n" \
 "                     [-pf <pid-file>] [--no-pid]\n"\
@@ -154,6 +155,7 @@ char *progname;
 "                [-pf <pid-file>] [--no-pid]\n"\
 "                [-m append|replace|forward|discard]\n" \
 "                [-i interface0 [ ... -i interfaceN]\n" \
+"                [-ui interface0 [ ... -ui interfaceN]\n" \
 "                server0 [ ... serverN]\n\n"
 #endif
 
@@ -311,7 +313,34 @@ main(int argc, char **argv) {
                                          isc_result_totext(status));
                        }
                        strcpy(tmp->name, argv[i]);
-                       interface_snorf(tmp, INTERFACE_REQUESTED);
+                       interface_snorf(tmp, (INTERFACE_REQUESTED
+                                             | INTERFACE_STREAMS));
+                       interface_dereference(&tmp, MDL);
+               } else if (!strcmp(argv[i], "-iu")) {
+#ifdef DHCPv6
+                       if (local_family_set && (local_family == AF_INET6)) {
+                               usage(use_v4command, argv[i]);
+                       }
+                       local_family_set = 1;
+                       local_family = AF_INET;
+#endif
+                       if (++i == argc) {
+                               usage(use_noarg, argv[i-1]);
+                       }
+                       if (strlen(argv[i]) >= sizeof(tmp->name)) {
+                               log_fatal("%s: interface name too long "
+                                         "(is %ld)",
+                                         argv[i], (long)strlen(argv[i]));
+                       }
+                       status = interface_allocate(&tmp, MDL);
+                       if (status != ISC_R_SUCCESS) {
+                               log_fatal("%s: interface_allocate: %s",
+                                         argv[i],
+                                         isc_result_totext(status));
+                       }
+                       strcpy(tmp->name, argv[i]);
+                       interface_snorf(tmp, (INTERFACE_REQUESTED
+                                             | INTERFACE_UPSTREAM));
                        interface_dereference(&tmp, MDL);
                } else if (!strcmp(argv[i], "-a")) {
 #ifdef DHCPv6
@@ -670,6 +699,11 @@ do_relay4(struct interface_info *ip, struct dhcp_packet *packet,
 
        /* If it's a bootreply, forward it to the client. */
        if (packet->op == BOOTREPLY) {
+               if (!(ip->flags & INTERFACE_UPSTREAM)) {
+                       log_debug("Dropping reply received on %s", ip->name);
+                       return;
+               }
+
                if (!(packet->flags & htons(BOOTP_BROADCAST)) &&
                        can_unicast_without_arp(out)) {
                        to.sin_addr = packet->yiaddr;