]> git.ipfire.org Git - thirdparty/dhcp.git/commitdiff
- A bug in DLPI packet transmission (Solaris, HP/UX) that caused the server
authorDavid Hankins <dhankins@isc.org>
Tue, 24 Mar 2009 18:33:52 +0000 (18:33 +0000)
committerDavid Hankins <dhankins@isc.org>
Tue, 24 Mar 2009 18:33:52 +0000 (18:33 +0000)
  to stop receiving packets is fixed.  The same fix also means that the MAC
  address will no longer appear 'bogus' on DLPI-based systems.
  [ISC-Bugs #19186]

- A bug in select handling was discovered where the results of one select()
  call were discarded, causing the server to process the next select() call
  and use more system calls than required.  This has been repaired - the
  sockets will be handled after the first return from select(), resulting in
  fewer system calls.  [ISC-Bugs #19186]

RELNOTES
common/dlpi.c
omapip/dispatch.c

index 46c28b354b5b336beb8b30d501954f74b27b368a..8eeac4a48d122d2a5ed2e28c244d2008adce9235 100644 (file)
--- a/RELNOTES
+++ b/RELNOTES
@@ -82,6 +82,16 @@ work on other platforms. Please report any problems and suggested fixes to
 - Fixed a cosmetic bug where pretty-printing valid domain-search options would
   result in an erroneous error log message ('garbage in format string').
 
+- A bug in DLPI packet transmission (Solaris, HP/UX) that caused the server
+  to stop receiving packets is fixed.  The same fix also means that the MAC
+  address will no longer appear 'bogus' on DLPI-based systems.
+
+- A bug in select handling was discovered where the results of one select()
+  call were discarded, causing the server to process the next select() call
+  and use more system calls than required.  This has been repaired - the
+  sockets will be handled after the first return from select(), resulting in
+  fewer system calls.
+
                        Changes since 4.1.0b1
 
 - A missing "else" in dhcrelay.c could have caused an interface not to
index a2d5cb2d04f513a2227b820c31471d73650de1f4..56f6b3a9b1c6edae9dc75b922f227cf414944dcd 100644 (file)
@@ -204,7 +204,6 @@ int if_register_dlpi (info)
            log_fatal ("Can't open DLPI device for %s: %m", info -> name);
        }
 
-
        /*
         * Submit a DL_INFO_REQ request, to find the dl_mac_type and 
          * dl_provider_style
@@ -292,8 +291,6 @@ int if_register_dlpi (info)
        }
 #endif
 
-       get_hw_addr(info->name, &info->hw_address);
-
        return sock;
 }
 
@@ -642,6 +639,7 @@ ssize_t receive_packet (interface, buf, len, from, hfrom)
 #endif
 
        if (length <= 0) {
+           log_error("receive_packet: %m");
            return length;
        }
 
@@ -665,8 +663,7 @@ ssize_t receive_packet (interface, buf, len, from, hfrom)
               memcpy ((char *) &hfrom -> hbuf [1], srcaddr, phys_len);
             }
             else {
-              memcpy ((char *) &hfrom -> hbuf [1], (char *) &srcaddr [phys_len],
-                phys_len);
+              memcpy((char *)&hfrom->hbuf[1], srcaddr + sap_len, phys_len);
             }
           } 
           else if (hfrom) {
@@ -694,9 +691,16 @@ ssize_t receive_packet (interface, buf, len, from, hfrom)
        offset = decode_udp_ip_header (interface, dbuf, bufix,
                                       from, length, &paylen);
 
-       /* If the IP or UDP checksum was bad, skip the packet... */
+       /*
+        * If the IP or UDP checksum was bad, skip the packet...
+        *
+        * Note: this happens all the time when writing packets via the
+        * fallback socket.  The packet received by streams does not have
+        * the IP or UDP checksums filled in, as those are calculated by
+        * the hardware.
+        */
        if (offset < 0) {
-           return 0;
+               return 0;
        }
 
        bufix += offset;
@@ -1147,22 +1151,32 @@ static int dlpiunitdataind (fd, daddr, daddrlen,
        ctl.maxlen = DLPI_MAXDLBUF;
        ctl.len = 0;
        ctl.buf = (char *)buf;
-       
+
        data.maxlen = dlen;
        data.len = 0;
        data.buf = (char *)dbuf;
-       
+
        result = getmsg (fd, &ctl, &data, &flags);
-       
+
+       /*
+        * The getmsg() manpage says:
+        *
+        * "On successful completion, a non-negative value is returned."
+        *
+        * This suggests that if MOREDATA or MORECTL are set, we error?
+        * This seems to be safe as it never seems to happen.  Still,
+        * set a log message, so we know if it ever starts happening.
+        */
        if (result != 0) {
+               log_debug("dlpiunitdataind: %m");
                return -1;
        }
-       
+
        if (ctl.len < sizeof (dl_unitdata_ind_t) ||
            dlp -> unitdata_ind.dl_primitive != DL_UNITDATA_IND) {
                return -1;
        }
-       
+
        if (data.len <= 0) {
                return data.len;
        }
@@ -1186,11 +1200,11 @@ static int dlpiunitdataind (fd, daddr, daddrlen,
        if (daddrlen) {
                *daddrlen = dlp -> unitdata_ind.dl_dest_addr_length;
        }
-       
+
        if (grpaddr) {
                *grpaddr = dlp -> unitdata_ind.dl_group_address;
        }
-       
+
        return data.len;
 }
 
@@ -1320,7 +1334,7 @@ void maybe_setup_fallback ()
 
 void 
 get_hw_addr(const char *name, struct hardware *hw) {
-       int sock;
+       int sock, unit;
        long buf[DLPI_MAXDLBUF];
         union DL_primitives *dlp;
 
@@ -1360,6 +1374,20 @@ get_hw_addr(const char *name, struct hardware *hw) {
                                  (unsigned long)dlp->info_ack.dl_mac_type);
        }
 
+       if (dlp->info_ack.dl_provider_style == DL_STYLE2) {
+               /*
+                * Attach to the device.  If this fails, the device
+                * does not exist.
+                */
+               unit = dlpiunit((char *)name);
+
+               if (dlpiattachreq(sock, unit) < 0 ||
+                   dlpiokack(sock, (char *)buf) < 0) {
+                       log_fatal("Can't attach DLPI device for %s: %m",
+                                 name);
+               }
+       }
+
        /*
         * Submit a DL_PHYS_ADDR_REQ request, to find
         * the hardware address.
index dda8ce773b38a3b8d487409912716ad491e89684..5b234dc5ad3760c1f3314b8cf7a98cb55431db03 100644 (file)
@@ -359,7 +359,10 @@ isc_result_t omapi_one_dispatch (omapi_object_t *wo,
                /* We are dry now */ 
                trigger_event(&rw_queue_empty);
                /* Wait for a packet or a timeout... XXX */
-               count = select(max + 1, &rr, &ww, &xx, t ? &to : NULL);
+               r = rr;
+               w = ww;
+               x = xx;
+               count = select(max + 1, &r, &w, &x, t ? &to : NULL);
        }
 
        /* Get the current time... */