apr-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Victor J. Orlikowski" <...@dulug.duke.edu>
Subject [PATCH] Modifications to egd/prngd support
Date Tue, 09 Jul 2002 09:34:29 GMT
The following patch, for which I have to give much credit for the
inspiration to the OpenSSL guys, allows one to simply do a --with-egd
when doing a configure, which will cause the probe of a set of
pre-determined sockets for egd. One can still do a --with-egd=blah
with this patch.

Looking for comments/complaints, prior to a commit.

Index: configure.in
===================================================================
RCS file: /home/cvs/apr/configure.in,v
retrieving revision 1.460
diff -u -d -r1.460 configure.in
--- configure.in	2 Jul 2002 21:33:43 -0000	1.460
+++ configure.in	9 Jul 2002 09:28:59 -0000
@@ -1544,11 +1544,12 @@
 
 AC_ARG_WITH(egd, 
   [  --with-egd=<path>       use egd-compatible socket],
-  [ if test "$withval" = "yes"; then
-      AC_ERROR([You must specify a default EGD socket path.])
+  [ AC_DEFINE(HAVE_EGD)
+    if test "$withval" = "yes"; then
+        AC_DEFINE_UNQUOTED(EGD_DEFAULT_SOCKET, ["/var/run/egd-pool","/dev/egd-pool","/etc/egd-pool","/etc/entropy"])
+    else
+        AC_DEFINE_UNQUOTED(EGD_DEFAULT_SOCKET, ["$withval"])
     fi
-    AC_DEFINE(HAVE_EGD)
-    AC_DEFINE_UNQUOTED(EGD_DEFAULT_SOCKET, [$withval])
     AC_MSG_RESULT(EGD-compatible daemon)
     rand="1"
   ])
Index: misc/unix/rand.c
===================================================================
RCS file: /home/cvs/apr/misc/unix/rand.c,v
retrieving revision 1.13
diff -u -d -r1.13 rand.c
--- misc/unix/rand.c	25 Jun 2002 21:24:07 -0000	1.13
+++ misc/unix/rand.c	9 Jul 2002 09:28:59 -0000
@@ -86,7 +86,7 @@
 #ifdef DEV_RANDOM
 
     int rnd;
-    size_t got, tot;
+    apr_size_t got, tot;
 
     if ((rnd = open(STR(DEV_RANDOM), O_RDONLY)) == -1) 
 	return errno;
@@ -119,76 +119,87 @@
      * 0x04 (report PID)
      *   0xMM (length of PID string, not null-terminated) MM chars
      */
-    int egd_socket, egd_path_len, rv;
+    static const char *egd_sockets[] = { EGD_DEFAULT_SOCKET, NULL };
+    const char **egdsockname = NULL;
+
+    int egd_socket, egd_path_len, rv, bad_errno;
     struct sockaddr_un addr;
     apr_socklen_t egd_addr_len;
-    size_t resp_expected;
+    apr_size_t resp_expected;
     unsigned char req[2], resp[255];
     unsigned char *curbuf = buf;
 
-    egd_path_len = strlen(STR(EGD_DEFAULT_SOCKET));
-
-    if (egd_path_len > sizeof(addr.sun_path)) {
-        return APR_EINVAL;
-    }
-
-    memset(&addr, 0, sizeof(struct sockaddr_un));
-    addr.sun_family = AF_UNIX;
-    memcpy(addr.sun_path, STR(EGD_DEFAULT_SOCKET), egd_path_len);
-    egd_addr_len = APR_OFFSETOF(struct sockaddr_un, sun_path) + 
-                   egd_path_len; 
-
-    egd_socket = socket(PF_UNIX, SOCK_STREAM, 0);
-
-    if (egd_socket == -1) {
-        return errno;
-    }
+    for (egdsockname = egd_sockets; *egdsockname && length > 0; egdsockname++)
{
+        egd_path_len = strlen(*egdsockname);
+        
+        if (egd_path_len > sizeof(addr.sun_path)) {
+            return APR_EINVAL;
+        }
 
-    rv = connect(egd_socket, (struct sockaddr*)&addr, egd_addr_len);
+        memset(&addr, 0, sizeof(struct sockaddr_un));
+        addr.sun_family = AF_UNIX;
+        memcpy(addr.sun_path, *egdsockname, egd_path_len);
+        egd_addr_len = APR_OFFSETOF(struct sockaddr_un, sun_path) + 
+          egd_path_len; 
 
-    if (rv == -1) {
-        return errno;
-    }
+        egd_socket = socket(PF_UNIX, SOCK_STREAM, 0);
 
-    /* EGD can only return 255 bytes of data at a time.  Silly.  */ 
-    while (length > 0) {
-        ssize_t srv;
-        req[0] = 2; /* We'll block for now. */
-        req[1] = length > 255 ? 255: length;
+        if (egd_socket == -1) {
+            return errno;
+        }
 
-        srv = write(egd_socket, req, 2);
-        if (srv == -1) {
-            int bad_errno = errno;
+        rv = connect(egd_socket, (struct sockaddr*)&addr, egd_addr_len);
 
-            shutdown(egd_socket, SHUT_RDWR);
-            close(egd_socket);
-            return bad_errno;
+        if (rv == -1) {
+            bad_errno = errno;
+            continue;
         }
 
-        if (srv != 2) {
-            shutdown(egd_socket, SHUT_RDWR);
-            close(egd_socket);
-            return APR_EGENERAL;  /* Try again. */
-        }
+        /* EGD can only return 255 bytes of data at a time.  Silly.  */ 
+        while (length > 0) {
+            apr_ssize_t srv;
+            req[0] = 2; /* We'll block for now. */
+            req[1] = length > 255 ? 255: length;
 
-        resp_expected = req[1];
-        srv = read(egd_socket, resp, resp_expected);
-        if (srv == -1) {
-            int bad_errno = errno;
+            srv = write(egd_socket, req, 2);
+            if (srv == -1) {
+                bad_errno = errno;
+                shutdown(egd_socket, SHUT_RDWR);
+                close(egd_socket);
+                break;
+            }
 
-            shutdown(egd_socket, SHUT_RDWR);
-            close(egd_socket);
-            return bad_errno;
+            if (srv != 2) {
+                shutdown(egd_socket, SHUT_RDWR);
+                close(egd_socket);
+                return APR_EGENERAL;
+            }
+            
+            resp_expected = req[1];
+            srv = read(egd_socket, resp, resp_expected);
+            if (srv == -1) {
+                bad_errno = errno;
+                shutdown(egd_socket, SHUT_RDWR);
+                close(egd_socket);
+                return bad_errno;
+            }
+            
+            memcpy(curbuf, resp, srv);
+            curbuf += srv;
+            length -= srv;
         }
+        
+        shutdown(egd_socket, SHUT_RDWR);
+        close(egd_socket);
+    }
 
-        memcpy(curbuf, resp, srv);
-        curbuf += srv;
-        length -= srv;
+    if (length > 0) {
+        /* We must have iterated through the list of sockets,
+         * and no go. Return the errno.
+         */
+        return bad_errno;
     }
 
-    shutdown(egd_socket, SHUT_RDWR);
-    close(egd_socket);
-    
 #elif defined(HAVE_TRUERAND) /* use truerand */
 
     extern int randbyte(void);	/* from the truerand library */

Thanks,
Victor
-- 
Victor J. Orlikowski   | The Wall is Down, But the Threat Remains!
==================================================================
orlikowski@apache.org  | vjo@dulug.duke.edu | vjo@us.ibm.com

Mime
View raw message