summaryrefslogtreecommitdiff
path: root/src/lib/libcrypto/rand/rand_unix.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/libcrypto/rand/rand_unix.c')
-rw-r--r--src/lib/libcrypto/rand/rand_unix.c119
1 files changed, 35 insertions, 84 deletions
diff --git a/src/lib/libcrypto/rand/rand_unix.c b/src/lib/libcrypto/rand/rand_unix.c
index 6c2be5cb96..9376554fae 100644
--- a/src/lib/libcrypto/rand/rand_unix.c
+++ b/src/lib/libcrypto/rand/rand_unix.c
@@ -56,7 +56,7 @@
56 * [including the GNU Public Licence.] 56 * [including the GNU Public Licence.]
57 */ 57 */
58/* ==================================================================== 58/* ====================================================================
59 * Copyright (c) 1998-2006 The OpenSSL Project. All rights reserved. 59 * Copyright (c) 1998-2000 The OpenSSL Project. All rights reserved.
60 * 60 *
61 * Redistribution and use in source and binary forms, with or without 61 * Redistribution and use in source and binary forms, with or without
62 * modification, are permitted provided that the following conditions 62 * modification, are permitted provided that the following conditions
@@ -108,7 +108,6 @@
108 * Hudson (tjh@cryptsoft.com). 108 * Hudson (tjh@cryptsoft.com).
109 * 109 *
110 */ 110 */
111#include <stdio.h>
112 111
113#define USE_SOCKETS 112#define USE_SOCKETS
114#include "e_os.h" 113#include "e_os.h"
@@ -116,7 +115,7 @@
116#include <openssl/rand.h> 115#include <openssl/rand.h>
117#include "rand_lcl.h" 116#include "rand_lcl.h"
118 117
119#if !(defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_WIN32) || defined(OPENSSL_SYS_VMS) || defined(OPENSSL_SYS_OS2) || defined(OPENSSL_SYS_VXWORKS) || defined(OPENSSL_SYS_NETWARE)) 118#if !(defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_WIN32) || defined(OPENSSL_SYS_VMS) || defined(OPENSSL_SYS_OS2) || defined(OPENSSL_SYS_VXWORKS))
120 119
121#include <sys/types.h> 120#include <sys/types.h>
122#include <sys/time.h> 121#include <sys/time.h>
@@ -125,13 +124,6 @@
125#include <fcntl.h> 124#include <fcntl.h>
126#include <unistd.h> 125#include <unistd.h>
127#include <time.h> 126#include <time.h>
128#if defined(OPENSSL_SYS_LINUX) /* should actually be available virtually everywhere */
129# include <poll.h>
130#endif
131#include <limits.h>
132#ifndef FD_SETSIZE
133# define FD_SETSIZE (8*sizeof(fd_set))
134#endif
135 127
136#ifdef __OpenBSD__ 128#ifdef __OpenBSD__
137int RAND_poll(void) 129int RAND_poll(void)
@@ -150,7 +142,7 @@ int RAND_poll(void)
150 142
151 return 1; 143 return 1;
152} 144}
153#else /* !defined(__OpenBSD__) */ 145#else
154int RAND_poll(void) 146int RAND_poll(void)
155{ 147{
156 unsigned long l; 148 unsigned long l;
@@ -162,8 +154,7 @@ int RAND_poll(void)
162#ifdef DEVRANDOM 154#ifdef DEVRANDOM
163 static const char *randomfiles[] = { DEVRANDOM }; 155 static const char *randomfiles[] = { DEVRANDOM };
164 struct stat randomstats[sizeof(randomfiles)/sizeof(randomfiles[0])]; 156 struct stat randomstats[sizeof(randomfiles)/sizeof(randomfiles[0])];
165 int fd; 157 int fd,i;
166 size_t i;
167#endif 158#endif
168#ifdef DEVRANDOM_EGD 159#ifdef DEVRANDOM_EGD
169 static const char *egdsockets[] = { DEVRANDOM_EGD, NULL }; 160 static const char *egdsockets[] = { DEVRANDOM_EGD, NULL };
@@ -191,9 +182,10 @@ int RAND_poll(void)
191#endif 182#endif
192 )) >= 0) 183 )) >= 0)
193 { 184 {
194 int usec = 10*1000; /* spend 10ms on each file */ 185 struct timeval t = { 0, 10*1000 }; /* Spend 10ms on
195 int r; 186 each file. */
196 size_t j; 187 int r,j;
188 fd_set fset;
197 struct stat *st=&randomstats[i]; 189 struct stat *st=&randomstats[i];
198 190
199 /* Avoid using same input... Used to be O_NOFOLLOW 191 /* Avoid using same input... Used to be O_NOFOLLOW
@@ -209,75 +201,35 @@ int RAND_poll(void)
209 201
210 do 202 do
211 { 203 {
212 int try_read = 0; 204 FD_ZERO(&fset);
205 FD_SET(fd, &fset);
206 r = -1;
213 207
214#if defined(OPENSSL_SYS_LINUX) 208 if (select(fd+1,&fset,NULL,NULL,&t) < 0)
215 /* use poll() */ 209 t.tv_usec=0;
216 struct pollfd pset; 210 else if (FD_ISSET(fd, &fset))
217
218 pset.fd = fd;
219 pset.events = POLLIN;
220 pset.revents = 0;
221
222 if (poll(&pset, 1, usec / 1000) < 0)
223 usec = 0;
224 else
225 try_read = (pset.revents & POLLIN) != 0;
226
227#else
228 /* use select() */
229 fd_set fset;
230 struct timeval t;
231
232 t.tv_sec = 0;
233 t.tv_usec = usec;
234
235 if (FD_SETSIZE > 0 && fd >= FD_SETSIZE)
236 {
237 /* can't use select, so just try to read once anyway */
238 try_read = 1;
239 }
240 else
241 {
242 FD_ZERO(&fset);
243 FD_SET(fd, &fset);
244
245 if (select(fd+1,&fset,NULL,NULL,&t) >= 0)
246 {
247 usec = t.tv_usec;
248 if (FD_ISSET(fd, &fset))
249 try_read = 1;
250 }
251 else
252 usec = 0;
253 }
254#endif
255
256 if (try_read)
257 { 211 {
258 r = read(fd,(unsigned char *)tmpbuf+n, ENTROPY_NEEDED-n); 212 r=read(fd,(unsigned char *)tmpbuf+n,
213 ENTROPY_NEEDED-n);
259 if (r > 0) 214 if (r > 0)
260 n += r; 215 n += r;
261 } 216 }
262 else 217
263 r = -1; 218 /* Some Unixen will update t, some
264 219 won't. For those who won't, give
265 /* Some Unixen will update t in select(), some 220 up here, otherwise, we will do
266 won't. For those who won't, or if we
267 didn't use select() in the first place,
268 give up here, otherwise, we will do
269 this once again for the remaining 221 this once again for the remaining
270 time. */ 222 time. */
271 if (usec == 10*1000) 223 if (t.tv_usec == 10*1000)
272 usec = 0; 224 t.tv_usec=0;
273 } 225 }
274 while ((r > 0 || 226 while ((r > 0 || (errno == EINTR || errno == EAGAIN))
275 (errno == EINTR || errno == EAGAIN)) && usec != 0 && n < ENTROPY_NEEDED); 227 && t.tv_usec != 0 && n < ENTROPY_NEEDED);
276 228
277 close(fd); 229 close(fd);
278 } 230 }
279 } 231 }
280#endif /* defined(DEVRANDOM) */ 232#endif
281 233
282#ifdef DEVRANDOM_EGD 234#ifdef DEVRANDOM_EGD
283 /* Use an EGD socket to read entropy from an EGD or PRNGD entropy 235 /* Use an EGD socket to read entropy from an EGD or PRNGD entropy
@@ -292,24 +244,24 @@ int RAND_poll(void)
292 if (r > 0) 244 if (r > 0)
293 n += r; 245 n += r;
294 } 246 }
295#endif /* defined(DEVRANDOM_EGD) */ 247#endif
296 248
297#if defined(DEVRANDOM) || defined(DEVRANDOM_EGD) 249#if defined(DEVRANDOM) || defined(DEVRANDOM_EGD)
298 if (n > 0) 250 if (n > 0)
299 { 251 {
300 RAND_add(tmpbuf,sizeof tmpbuf,(double)n); 252 RAND_add(tmpbuf,sizeof tmpbuf,n);
301 OPENSSL_cleanse(tmpbuf,n); 253 OPENSSL_cleanse(tmpbuf,n);
302 } 254 }
303#endif 255#endif
304 256
305 /* put in some default random data, we need more than just this */ 257 /* put in some default random data, we need more than just this */
306 l=curr_pid; 258 l=curr_pid;
307 RAND_add(&l,sizeof(l),0.0); 259 RAND_add(&l,sizeof(l),0);
308 l=getuid(); 260 l=getuid();
309 RAND_add(&l,sizeof(l),0.0); 261 RAND_add(&l,sizeof(l),0);
310 262
311 l=time(NULL); 263 l=time(NULL);
312 RAND_add(&l,sizeof(l),0.0); 264 RAND_add(&l,sizeof(l),0);
313 265
314#if defined(DEVRANDOM) || defined(DEVRANDOM_EGD) 266#if defined(DEVRANDOM) || defined(DEVRANDOM_EGD)
315 return 1; 267 return 1;
@@ -318,13 +270,12 @@ int RAND_poll(void)
318#endif 270#endif
319} 271}
320 272
321#endif /* defined(__OpenBSD__) */ 273#endif
322#endif /* !(defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_WIN32) || defined(OPENSSL_SYS_VMS) || defined(OPENSSL_SYS_OS2) || defined(OPENSSL_SYS_VXWORKS) || defined(OPENSSL_SYS_NETWARE)) */ 274#endif
323
324 275
325#if defined(OPENSSL_SYS_VXWORKS) 276#if defined(OPENSSL_SYS_VXWORKS)
326int RAND_poll(void) 277int RAND_poll(void)
327 { 278{
328 return 0; 279 return 0;
329 } 280}
330#endif 281#endif