aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRon Yorston <rmy@pobox.com>2018-03-22 14:58:29 +0000
committerRon Yorston <rmy@pobox.com>2018-03-22 15:11:41 +0000
commit6cff8357023adb4d5c9daa027522f883f3905f4c (patch)
tree50964ae864ec3325c2413facaa8efc3a3104f3a6
parentbe9b9ed64e658889229e18e3d089df27d8b724c3 (diff)
downloadbusybox-w32-6cff8357023adb4d5c9daa027522f883f3905f4c.tar.gz
busybox-w32-6cff8357023adb4d5c9daa027522f883f3905f4c.tar.bz2
busybox-w32-6cff8357023adb4d5c9daa027522f883f3905f4c.zip
win32: allow use of shell's PRNG for /dev/urandom
Allow either ISAAC or the shell's built-in pseudo-random number generator to be used for /dev/urandom. The latter is smaller so it's the default.
-rw-r--r--Config.in45
-rw-r--r--shell/Kbuild.src1
-rw-r--r--shell/random.c11
-rw-r--r--shell/random.h3
-rw-r--r--win32/Kbuild11
-rw-r--r--win32/sh_random.c76
6 files changed, 130 insertions, 17 deletions
diff --git a/Config.in b/Config.in
index dc3a6e09a..a18d26720 100644
--- a/Config.in
+++ b/Config.in
@@ -122,18 +122,6 @@ config LFS
122 programs that can benefit from large file support include dd, gzip, 122 programs that can benefit from large file support include dd, gzip,
123 cp, mount, tar. 123 cp, mount, tar.
124 124
125config GLOBBING
126 bool "Allow busybox.exe to expand wildcards"
127 default n
128 depends on PLATFORM_MINGW32
129 help
130 In Microsoft Windows expansion of wildcards on the command line
131 ('globbing') is handled by the C runtime while the BusyBox shell
132 does its own wildcard expansion. For best results when using the
133 shell globbing by the C runtime should be turned off. If you want
134 the BusyBox binary to handle wildcard expansion using the C runtime
135 set this to 'Y'.
136
137config PAM 125config PAM
138 bool "Support PAM (Pluggable Authentication Modules)" 126 bool "Support PAM (Pluggable Authentication Modules)"
139 default n 127 default n
@@ -380,6 +368,39 @@ config PLATFORM_LINUX
380 #This is automatically selected if any applet or feature requires 368 #This is automatically selected if any applet or feature requires
381 #Linux-specific interfaces. You do not need to select it manually. 369 #Linux-specific interfaces. You do not need to select it manually.
382 370
371config GLOBBING
372 bool "Allow busybox.exe to expand wildcards"
373 default n
374 depends on PLATFORM_MINGW32
375 help
376 In Microsoft Windows expansion of wildcards on the command line
377 ('globbing') is handled by the C runtime while the BusyBox shell
378 does its own wildcard expansion. For best results when using the
379 shell globbing by the C runtime should be turned off. If you want
380 the BusyBox binary to handle wildcard expansion using the C runtime
381 set this to 'Y'.
382
383choice
384 prompt "Random number generator"
385 default FEATURE_PRNG_SHELL
386 depends on PLATFORM_MINGW32
387 help
388 BusyBox on Microsoft Windows uses a pseudo-random number
389 generator to emulate the Linux /dev/urandom device. There
390 are two options:
391 - The shell's built-in PRNG.
392 - Bob Jenkins' ISAAC. This is intended to be a secure PRNG. It's
393 slightly faster than the shell's PRNG but is larger both in terms
394 of code and runtime memory.
395
396config FEATURE_PRNG_SHELL
397 bool "Use shell PRNG"
398
399config FEATURE_PRNG_ISAAC
400 bool "Use ISAAC PRNG"
401
402endchoice
403
383comment 'Build Options' 404comment 'Build Options'
384 405
385config STATIC 406config STATIC
diff --git a/shell/Kbuild.src b/shell/Kbuild.src
index 6bba4989f..a287fce4e 100644
--- a/shell/Kbuild.src
+++ b/shell/Kbuild.src
@@ -9,3 +9,4 @@ lib-y:=
9INSERT 9INSERT
10 10
11lib-$(CONFIG_FEATURE_SH_MATH) += math.o 11lib-$(CONFIG_FEATURE_SH_MATH) += math.o
12lib-$(CONFIG_FEATURE_PRNG_SHELL) += random.o
diff --git a/shell/random.c b/shell/random.c
index 5d3620516..614172279 100644
--- a/shell/random.c
+++ b/shell/random.c
@@ -19,6 +19,17 @@
19# include "random.h" 19# include "random.h"
20# define RAND_BASH_MASK 0x7fff 20# define RAND_BASH_MASK 0x7fff
21 21
22# if ENABLE_FEATURE_PRNG_SHELL
23uint32_t FAST_FUNC
24next_random(random_t *rnd)
25{
26 return full_random(rnd) & RAND_BASH_MASK;
27}
28# undef RAND_BASH_MASK
29# define RAND_BASH_MASK 0xffffffff
30# define next_random full_random
31# endif
32
22#else 33#else
23# include <stdint.h> 34# include <stdint.h>
24# include <unistd.h> 35# include <unistd.h>
diff --git a/shell/random.h b/shell/random.h
index c4eb44c13..75fe0f69f 100644
--- a/shell/random.h
+++ b/shell/random.h
@@ -35,6 +35,9 @@ typedef struct random_t {
35 ((rnd)->galois_LFSR = 0) 35 ((rnd)->galois_LFSR = 0)
36 36
37uint32_t next_random(random_t *rnd) FAST_FUNC; 37uint32_t next_random(random_t *rnd) FAST_FUNC;
38#if ENABLE_FEATURE_PRNG_SHELL
39uint32_t full_random(random_t *rnd) FAST_FUNC;
40#endif
38 41
39POP_SAVED_FUNCTION_VISIBILITY 42POP_SAVED_FUNCTION_VISIBILITY
40 43
diff --git a/win32/Kbuild b/win32/Kbuild
index 00950e0f7..f8c8fb5af 100644
--- a/win32/Kbuild
+++ b/win32/Kbuild
@@ -7,18 +7,19 @@ lib-y:=
7lib-$(CONFIG_PLATFORM_MINGW32) += env.o 7lib-$(CONFIG_PLATFORM_MINGW32) += env.o
8lib-$(CONFIG_PLATFORM_MINGW32) += fnmatch.o 8lib-$(CONFIG_PLATFORM_MINGW32) += fnmatch.o
9lib-$(CONFIG_PLATFORM_MINGW32) += fsync.o 9lib-$(CONFIG_PLATFORM_MINGW32) += fsync.o
10lib-$(CONFIG_PLATFORM_MINGW32) += inet_pton.o
10lib-$(CONFIG_PLATFORM_MINGW32) += ioctl.o 11lib-$(CONFIG_PLATFORM_MINGW32) += ioctl.o
11lib-$(CONFIG_PLATFORM_MINGW32) += isaac.o 12lib-$(CONFIG_FEATURE_PRNG_ISAAC) += isaac.o
12lib-$(CONFIG_PLATFORM_MINGW32) += mingw.o 13lib-$(CONFIG_PLATFORM_MINGW32) += mingw.o
13lib-$(CONFIG_PLATFORM_MINGW32) += process.o 14lib-$(CONFIG_PLATFORM_MINGW32) += process.o
14lib-$(CONFIG_PLATFORM_MINGW32) += regex.o 15lib-$(CONFIG_PLATFORM_MINGW32) += mntent.o
15lib-$(CONFIG_PLATFORM_MINGW32) += net.o 16lib-$(CONFIG_PLATFORM_MINGW32) += net.o
16lib-$(CONFIG_PLATFORM_MINGW32) += inet_pton.o
17lib-$(CONFIG_PLATFORM_MINGW32) += poll.o 17lib-$(CONFIG_PLATFORM_MINGW32) += poll.o
18lib-$(CONFIG_PLATFORM_MINGW32) += select.o
19lib-$(CONFIG_PLATFORM_MINGW32) += popen.o 18lib-$(CONFIG_PLATFORM_MINGW32) += popen.o
19lib-$(CONFIG_PLATFORM_MINGW32) += regex.o
20lib-$(CONFIG_PLATFORM_MINGW32) += select.o
21lib-$(CONFIG_FEATURE_PRNG_SHELL) += sh_random.o
20lib-$(CONFIG_PLATFORM_MINGW32) += statfs.o 22lib-$(CONFIG_PLATFORM_MINGW32) += statfs.o
21lib-$(CONFIG_PLATFORM_MINGW32) += mntent.o
22lib-$(CONFIG_PLATFORM_MINGW32) += strptime.o 23lib-$(CONFIG_PLATFORM_MINGW32) += strptime.o
23lib-$(CONFIG_PLATFORM_MINGW32) += system.o 24lib-$(CONFIG_PLATFORM_MINGW32) += system.o
24lib-$(CONFIG_PLATFORM_MINGW32) += termios.o 25lib-$(CONFIG_PLATFORM_MINGW32) += termios.o
diff --git a/win32/sh_random.c b/win32/sh_random.c
new file mode 100644
index 000000000..2948e4a55
--- /dev/null
+++ b/win32/sh_random.c
@@ -0,0 +1,76 @@
1#include "libbb.h"
2#include "../shell/random.h"
3
4/* call 'fn' to put data in 'dt' then copy it to generator state */
5#define GET_DATA(fn, dt) \
6 fn(&dt); \
7 u = (uint32_t *)&dt; \
8 for (j=0; j<sizeof(dt)/sizeof(uint32_t); ++j) { \
9 state[i++%2] ^= *u++; \
10 }
11
12/*
13 * Obtain a few bytes of random-ish data to initialise the generator.
14 * This is unlikely to be very robust: don't rely on it for
15 * anything that needs to be secure.
16 */
17static void get_entropy(uint32_t state[2])
18{
19 int i, j;
20 SYSTEMTIME tm;
21 MEMORYSTATUS ms;
22 SYSTEM_INFO si;
23 LARGE_INTEGER pc;
24 uint32_t *u;
25
26 i = 0;
27 state[i++%2] ^= (uint32_t)GetCurrentProcessId();
28 state[i++%2] ^= (uint32_t)GetCurrentThreadId();
29 state[i++%2] ^= (uint32_t)GetTickCount();
30
31 GET_DATA(GetLocalTime, tm)
32 GET_DATA(GlobalMemoryStatus, ms)
33 GET_DATA(GetSystemInfo, si)
34 GET_DATA(QueryPerformanceCounter, pc)
35
36#if 0
37 {
38 unsigned char *p = (unsigned char *)state;
39
40 for (j=0; j<8; ++j) {
41 fprintf(stderr, "%02x", *p++);
42 if ((j&3) == 3) {
43 fprintf(stderr, " ");
44 }
45 }
46 fprintf(stderr, "\n");
47 }
48#endif
49}
50
51ssize_t get_random_bytes(void *buf, ssize_t count)
52{
53 static random_t rnd;
54 ssize_t save_count = count;
55 uint32_t value;
56 unsigned char *ptr = (unsigned char *)&value;
57
58 if (buf == NULL || count < 0) {
59 errno = EINVAL;
60 return -1;
61 }
62
63 if (UNINITED_RANDOM_T(&rnd)) {
64 uint32_t state[2] = {0, 0};
65
66 get_entropy(state);
67 INIT_RANDOM_T(&rnd, state[0] ? state[0] : 1, state[1]);
68 }
69
70 for (;count > 0; buf+=4, count-=4) {
71 value = full_random(&rnd);
72 memcpy(buf, ptr, count >= 4 ? 4 : count);
73 }
74
75 return save_count;
76}