diff options
Diffstat (limited to 'src/lib/libcrypto/rand/randfile.c')
-rw-r--r-- | src/lib/libcrypto/rand/randfile.c | 108 |
1 files changed, 86 insertions, 22 deletions
diff --git a/src/lib/libcrypto/rand/randfile.c b/src/lib/libcrypto/rand/randfile.c index 6829d4ec37..658a8d6b65 100644 --- a/src/lib/libcrypto/rand/randfile.c +++ b/src/lib/libcrypto/rand/randfile.c | |||
@@ -60,22 +60,35 @@ | |||
60 | #include <stdio.h> | 60 | #include <stdio.h> |
61 | #include <stdlib.h> | 61 | #include <stdlib.h> |
62 | #include <string.h> | 62 | #include <string.h> |
63 | #include <sys/types.h> | ||
64 | #include <sys/stat.h> | ||
65 | #include <sys/types.h> | ||
66 | 63 | ||
67 | #include "openssl/e_os.h" | 64 | #include "openssl/e_os.h" |
68 | 65 | ||
66 | #ifdef VMS | ||
67 | #include <unixio.h> | ||
68 | #endif | ||
69 | #ifndef NO_SYS_TYPES_H | ||
70 | # include <sys/types.h> | ||
71 | #endif | ||
72 | #ifdef MAC_OS_pre_X | ||
73 | # include <stat.h> | ||
74 | #else | ||
75 | # include <sys/stat.h> | ||
76 | #endif | ||
77 | |||
78 | #include <openssl/crypto.h> | ||
69 | #include <openssl/rand.h> | 79 | #include <openssl/rand.h> |
70 | 80 | ||
71 | #undef BUFSIZE | 81 | #undef BUFSIZE |
72 | #define BUFSIZE 1024 | 82 | #define BUFSIZE 1024 |
73 | #define RAND_DATA 1024 | 83 | #define RAND_DATA 1024 |
74 | 84 | ||
75 | /* #define RFILE ".rand" - defined in ../../e_os.h */ | 85 | /* #define RFILE ".rnd" - defined in ../../e_os.h */ |
76 | 86 | ||
77 | int RAND_load_file(const char *file, long bytes) | 87 | int RAND_load_file(const char *file, long bytes) |
78 | { | 88 | { |
89 | /* If bytes >= 0, read up to 'bytes' bytes. | ||
90 | * if bytes == -1, read complete file. */ | ||
91 | |||
79 | MS_STATIC unsigned char buf[BUFSIZE]; | 92 | MS_STATIC unsigned char buf[BUFSIZE]; |
80 | struct stat sb; | 93 | struct stat sb; |
81 | int i,ret=0,n; | 94 | int i,ret=0,n; |
@@ -85,23 +98,28 @@ int RAND_load_file(const char *file, long bytes) | |||
85 | 98 | ||
86 | i=stat(file,&sb); | 99 | i=stat(file,&sb); |
87 | /* If the state fails, put some crap in anyway */ | 100 | /* If the state fails, put some crap in anyway */ |
88 | RAND_seed(&sb,sizeof(sb)); | 101 | RAND_add(&sb,sizeof(sb),0); |
89 | ret+=sizeof(sb); | ||
90 | if (i < 0) return(0); | 102 | if (i < 0) return(0); |
91 | if (bytes <= 0) return(ret); | 103 | if (bytes == 0) return(ret); |
92 | 104 | ||
93 | in=fopen(file,"rb"); | 105 | in=fopen(file,"rb"); |
94 | if (in == NULL) goto err; | 106 | if (in == NULL) goto err; |
95 | for (;;) | 107 | for (;;) |
96 | { | 108 | { |
97 | n=(bytes < BUFSIZE)?(int)bytes:BUFSIZE; | 109 | if (bytes > 0) |
110 | n = (bytes < BUFSIZE)?(int)bytes:BUFSIZE; | ||
111 | else | ||
112 | n = BUFSIZE; | ||
98 | i=fread(buf,1,n,in); | 113 | i=fread(buf,1,n,in); |
99 | if (i <= 0) break; | 114 | if (i <= 0) break; |
100 | /* even if n != i, use the full array */ | 115 | /* even if n != i, use the full array */ |
101 | RAND_seed(buf,n); | 116 | RAND_add(buf,n,i); |
102 | ret+=i; | 117 | ret+=i; |
103 | bytes-=n; | 118 | if (bytes > 0) |
104 | if (bytes <= 0) break; | 119 | { |
120 | bytes-=n; | ||
121 | if (bytes == 0) break; | ||
122 | } | ||
105 | } | 123 | } |
106 | fclose(in); | 124 | fclose(in); |
107 | memset(buf,0,BUFSIZE); | 125 | memset(buf,0,BUFSIZE); |
@@ -112,29 +130,48 @@ err: | |||
112 | int RAND_write_file(const char *file) | 130 | int RAND_write_file(const char *file) |
113 | { | 131 | { |
114 | unsigned char buf[BUFSIZE]; | 132 | unsigned char buf[BUFSIZE]; |
115 | int i,ret=0; | 133 | int i,ret=0,err=0; |
116 | FILE *out; | 134 | FILE *out = NULL; |
117 | int n; | 135 | int n; |
118 | 136 | ||
119 | /* Under VMS, fopen(file, "wb") will craete a new version of the | 137 | #ifdef VMS |
138 | /* Under VMS, fopen(file, "wb") will create a new version of the | ||
120 | same file. This is not good, so let's try updating an existing | 139 | same file. This is not good, so let's try updating an existing |
121 | one, and create file only if it doesn't already exist. This | 140 | one, and create file only if it doesn't already exist. */ |
122 | should be completely harmless on system that have no file | 141 | /* At the same time, if we just update a file, we also need to |
123 | versions. -- Richard Levitte */ | 142 | truncate it, and unfortunately, ftruncate() and truncate() do |
143 | not exist everywhere. All that remains is to delete old versions | ||
144 | of the random data file (done at the end). */ | ||
145 | #if 0 | ||
124 | out=fopen(file,"rb+"); | 146 | out=fopen(file,"rb+"); |
125 | if (out == NULL && errno == ENOENT) | 147 | if (out == NULL && errno != ENOENT) |
148 | goto err; | ||
149 | #endif | ||
150 | #endif | ||
151 | |||
152 | if (out == NULL) | ||
126 | { | 153 | { |
127 | errno = 0; | 154 | #if defined O_CREAT && defined O_EXCL |
155 | /* chmod(..., 0600) is too late to protect the file, | ||
156 | * permissions should be restrictive from the start */ | ||
157 | int fd = open(file, O_CREAT | O_EXCL, 0600); | ||
158 | if (fd != -1) | ||
159 | out = fdopen(fd, "wb"); | ||
160 | #else | ||
128 | out=fopen(file,"wb"); | 161 | out=fopen(file,"wb"); |
162 | #endif | ||
129 | } | 163 | } |
130 | if (out == NULL) goto err; | 164 | if (out == NULL) goto err; |
165 | #ifndef NO_CHMOD | ||
131 | chmod(file,0600); | 166 | chmod(file,0600); |
167 | #endif | ||
132 | n=RAND_DATA; | 168 | n=RAND_DATA; |
133 | for (;;) | 169 | for (;;) |
134 | { | 170 | { |
135 | i=(n > BUFSIZE)?BUFSIZE:n; | 171 | i=(n > BUFSIZE)?BUFSIZE:n; |
136 | n-=BUFSIZE; | 172 | n-=BUFSIZE; |
137 | RAND_bytes(buf,i); | 173 | if (RAND_bytes(buf,i) <= 0) |
174 | err=1; | ||
138 | i=fwrite(buf,1,i,out); | 175 | i=fwrite(buf,1,i,out); |
139 | if (i <= 0) | 176 | if (i <= 0) |
140 | { | 177 | { |
@@ -144,13 +181,40 @@ int RAND_write_file(const char *file) | |||
144 | ret+=i; | 181 | ret+=i; |
145 | if (n <= 0) break; | 182 | if (n <= 0) break; |
146 | } | 183 | } |
184 | #ifdef VMS | ||
185 | /* We may have updated an existing file using mode "rb+", | ||
186 | * now remove any old extra bytes */ | ||
187 | #if 0 | ||
188 | if (ret > 0) | ||
189 | ftruncate(fileno(out), ret); | ||
190 | #else | ||
191 | /* Try to delete older versions of the file, until there aren't | ||
192 | any */ | ||
193 | { | ||
194 | char *tmpf; | ||
195 | |||
196 | tmpf = Malloc(strlen(file) + 4); /* to add ";-1" and a nul */ | ||
197 | if (tmpf) | ||
198 | { | ||
199 | strcpy(tmpf, file); | ||
200 | strcat(tmpf, ";-1"); | ||
201 | while(delete(tmpf) == 0) | ||
202 | ; | ||
203 | rename(file,";1"); /* Make sure it's version 1, or we | ||
204 | will reach the limit (32767) at | ||
205 | some point... */ | ||
206 | } | ||
207 | } | ||
208 | #endif | ||
209 | #endif | ||
210 | |||
147 | fclose(out); | 211 | fclose(out); |
148 | memset(buf,0,BUFSIZE); | 212 | memset(buf,0,BUFSIZE); |
149 | err: | 213 | err: |
150 | return(ret); | 214 | return(err ? -1 : ret); |
151 | } | 215 | } |
152 | 216 | ||
153 | char *RAND_file_name(char *buf, int size) | 217 | const char *RAND_file_name(char *buf, int size) |
154 | { | 218 | { |
155 | char *s; | 219 | char *s; |
156 | char *ret=NULL; | 220 | char *ret=NULL; |