aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c
diff options
context:
space:
mode:
Diffstat (limited to 'linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c')
-rw-r--r--[-rwxr-xr-x]linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c512
1 files changed, 256 insertions, 256 deletions
diff --git a/linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c b/linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c
index 2b7c6be..29b48e8 100755..100644
--- a/linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c
+++ b/linden/indra/libgcrypt/libgcrypt-1.2.2/cipher/rndegd.c
@@ -1,256 +1,256 @@
1/* rndegd.c - interface to the EGD 1/* rndegd.c - interface to the EGD
2 * Copyright (C) 1999, 2000, 2002, 2003 Free Software Foundation, Inc. 2 * Copyright (C) 1999, 2000, 2002, 2003 Free Software Foundation, Inc.
3 * 3 *
4 * This file is part of Libgcrypt. 4 * This file is part of Libgcrypt.
5 * 5 *
6 * Libgcrypt is free software; you can redistribute it and/or modify 6 * Libgcrypt is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU Lesser General Public License as 7 * it under the terms of the GNU Lesser General Public License as
8 * published by the Free Software Foundation; either version 2.1 of 8 * published by the Free Software Foundation; either version 2.1 of
9 * the License, or (at your option) any later version. 9 * the License, or (at your option) any later version.
10 * 10 *
11 * Libgcrypt is distributed in the hope that it will be useful, 11 * Libgcrypt is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU Lesser General Public License for more details. 14 * GNU Lesser General Public License for more details.
15 * 15 *
16 * You should have received a copy of the GNU Lesser General Public 16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this program; if not, write to the Free Software 17 * License along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA 18 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19 */ 19 */
20 20
21#include <config.h> 21#include <config.h>
22#include <stdio.h> 22#include <stdio.h>
23#include <stdlib.h> 23#include <stdlib.h>
24#include <assert.h> 24#include <assert.h>
25#include <errno.h> 25#include <errno.h>
26#include <sys/time.h> 26#include <sys/time.h>
27#include <sys/stat.h> 27#include <sys/stat.h>
28#include <string.h> 28#include <string.h>
29#include <unistd.h> 29#include <unistd.h>
30#include <sys/types.h> 30#include <sys/types.h>
31#include <sys/socket.h> 31#include <sys/socket.h>
32#include <sys/un.h> 32#include <sys/un.h>
33#include "types.h" 33#include "types.h"
34#include "g10lib.h" 34#include "g10lib.h"
35#include "cipher.h" 35#include "cipher.h"
36#include "rand-internal.h" 36#include "rand-internal.h"
37 37
38#ifndef offsetof 38#ifndef offsetof
39#define offsetof(type, member) ((size_t) &((type *)0)->member) 39#define offsetof(type, member) ((size_t) &((type *)0)->member)
40#endif 40#endif
41 41
42static int egd_socket = -1; 42static int egd_socket = -1;
43 43
44/* Allocate a new filename from FIRST_PART and SECOND_PART and to 44/* Allocate a new filename from FIRST_PART and SECOND_PART and to
45 tilde expansion for first_part. SECOND_PART might be NULL. 45 tilde expansion for first_part. SECOND_PART might be NULL.
46 */ 46 */
47static char * 47static char *
48my_make_filename (const char *first_part, const char *second_part) 48my_make_filename (const char *first_part, const char *second_part)
49{ 49{
50 size_t n; 50 size_t n;
51 char *name, *home, *p; 51 char *name, *home, *p;
52 52
53 n = strlen(first_part)+1; 53 n = strlen(first_part)+1;
54 if (second_part) 54 if (second_part)
55 n += strlen (second_part) + 1; 55 n += strlen (second_part) + 1;
56 56
57 home = NULL; 57 home = NULL;
58 if( *first_part == '~' && first_part[1] == '/' 58 if( *first_part == '~' && first_part[1] == '/'
59 && (home = getenv("HOME")) && *home ) 59 && (home = getenv("HOME")) && *home )
60 n += strlen(home); 60 n += strlen(home);
61 61
62 name = gcry_xmalloc(n); 62 name = gcry_xmalloc(n);
63 p = (home 63 p = (home
64 ? stpcpy (stpcpy (name, home), first_part+1 ) 64 ? stpcpy (stpcpy (name, home), first_part+1 )
65 : stpcpy (name, first_part) ); 65 : stpcpy (name, first_part) );
66 66
67 if (second_part) 67 if (second_part)
68 strcpy (stpcpy(p,"/"), second_part); 68 strcpy (stpcpy(p,"/"), second_part);
69 69
70 return name; 70 return name;
71} 71}
72 72
73 73
74static int 74static int
75do_write( int fd, void *buf, size_t nbytes ) 75do_write( int fd, void *buf, size_t nbytes )
76{ 76{
77 size_t nleft = nbytes; 77 size_t nleft = nbytes;
78 int nwritten; 78 int nwritten;
79 79
80 while( nleft > 0 ) 80 while( nleft > 0 )
81 { 81 {
82 nwritten = write( fd, buf, nleft); 82 nwritten = write( fd, buf, nleft);
83 if( nwritten < 0 ) 83 if( nwritten < 0 )
84 { 84 {
85 if( errno == EINTR ) 85 if( errno == EINTR )
86 continue; 86 continue;
87 return -1; 87 return -1;
88 } 88 }
89 nleft -= nwritten; 89 nleft -= nwritten;
90 buf = (char*)buf + nwritten; 90 buf = (char*)buf + nwritten;
91 } 91 }
92 return 0; 92 return 0;
93} 93}
94 94
95static int 95static int
96do_read( int fd, void *buf, size_t nbytes ) 96do_read( int fd, void *buf, size_t nbytes )
97{ 97{
98 int n, nread = 0; 98 int n, nread = 0;
99 99
100 do 100 do
101 { 101 {
102 do 102 do
103 { 103 {
104 n = read(fd, (char*)buf + nread, nbytes ); 104 n = read(fd, (char*)buf + nread, nbytes );
105 } 105 }
106 while( n == -1 && errno == EINTR ); 106 while( n == -1 && errno == EINTR );
107 if( n == -1) 107 if( n == -1)
108 return nread? nread:-1; 108 return nread? nread:-1;
109 if( n == 0) 109 if( n == 0)
110 return -1; 110 return -1;
111 nread += n; 111 nread += n;
112 nbytes -= n; 112 nbytes -= n;
113 } 113 }
114 while( nread < nbytes ); 114 while( nread < nbytes );
115 return nread; 115 return nread;
116} 116}
117 117
118 118
119/* Connect to the EGD and return the file descriptor. Return -1 on 119/* Connect to the EGD and return the file descriptor. Return -1 on
120 error. With NOFAIL set to true, silently fail and return the 120 error. With NOFAIL set to true, silently fail and return the
121 error, otherwise print an error message and die. */ 121 error, otherwise print an error message and die. */
122int 122int
123_gcry_rndegd_connect_socket (int nofail) 123_gcry_rndegd_connect_socket (int nofail)
124{ 124{
125 int fd; 125 int fd;
126 const char *bname = NULL; 126 const char *bname = NULL;
127 char *name; 127 char *name;
128 struct sockaddr_un addr; 128 struct sockaddr_un addr;
129 int addr_len; 129 int addr_len;
130 130
131 if (egd_socket != -1) 131 if (egd_socket != -1)
132 { 132 {
133 close (egd_socket); 133 close (egd_socket);
134 egd_socket = -1; 134 egd_socket = -1;
135 } 135 }
136 136
137#ifdef EGD_SOCKET_NAME 137#ifdef EGD_SOCKET_NAME
138 bname = EGD_SOCKET_NAME; 138 bname = EGD_SOCKET_NAME;
139#endif 139#endif
140 if ( !bname || !*bname ) 140 if ( !bname || !*bname )
141 name = my_make_filename ("~/.gnupg", "entropy"); 141 name = my_make_filename ("~/.gnupg", "entropy");
142 else 142 else
143 name = my_make_filename (bname, NULL); 143 name = my_make_filename (bname, NULL);
144 144
145 if (strlen(name)+1 >= sizeof addr.sun_path) 145 if (strlen(name)+1 >= sizeof addr.sun_path)
146 log_fatal ("EGD socketname is too long\n"); 146 log_fatal ("EGD socketname is too long\n");
147 147
148 memset( &addr, 0, sizeof addr ); 148 memset( &addr, 0, sizeof addr );
149 addr.sun_family = AF_UNIX; 149 addr.sun_family = AF_UNIX;
150 strcpy( addr.sun_path, name ); 150 strcpy( addr.sun_path, name );
151 addr_len = (offsetof( struct sockaddr_un, sun_path ) 151 addr_len = (offsetof( struct sockaddr_un, sun_path )
152 + strlen( addr.sun_path )); 152 + strlen( addr.sun_path ));
153 153
154 fd = socket(AF_UNIX, SOCK_STREAM, 0); 154 fd = socket(AF_UNIX, SOCK_STREAM, 0);
155 if (fd == -1 && !nofail) 155 if (fd == -1 && !nofail)
156 log_fatal("can't create unix domain socket: %s\n", strerror(errno) ); 156 log_fatal("can't create unix domain socket: %s\n", strerror(errno) );
157 else if (connect (fd, (struct sockaddr*)&addr, addr_len) == -1) 157 else if (connect (fd, (struct sockaddr*)&addr, addr_len) == -1)
158 { 158 {
159 if (!nofail) 159 if (!nofail)
160 log_fatal("can't connect to EGD socket `%s': %s\n", 160 log_fatal("can't connect to EGD socket `%s': %s\n",
161 name, strerror(errno) ); 161 name, strerror(errno) );
162 close (fd); 162 close (fd);
163 fd = -1; 163 fd = -1;
164 } 164 }
165 gcry_free(name); 165 gcry_free(name);
166 if (fd != -1) 166 if (fd != -1)
167 egd_socket = fd; 167 egd_socket = fd;
168 return fd; 168 return fd;
169} 169}
170 170
171/**************** 171/****************
172 * Note: We always use the highest level. 172 * Note: We always use the highest level.
173 * To boost the performance we may want to add some 173 * To boost the performance we may want to add some
174 * additional code for level 1 174 * additional code for level 1
175 * 175 *
176 * Using a level of 0 should never block and better add nothing 176 * Using a level of 0 should never block and better add nothing
177 * to the pool. So this is just a dummy for EGD. 177 * to the pool. So this is just a dummy for EGD.
178 */ 178 */
179int 179int
180_gcry_rndegd_gather_random (void (*add)(const void*, size_t, int), 180_gcry_rndegd_gather_random (void (*add)(const void*, size_t, int),
181 int requester, 181 int requester,
182 size_t length, int level ) 182 size_t length, int level )
183{ 183{
184 int fd = egd_socket; 184 int fd = egd_socket;
185 int n; 185 int n;
186 byte buffer[256+2]; 186 byte buffer[256+2];
187 int nbytes; 187 int nbytes;
188 int do_restart = 0; 188 int do_restart = 0;
189 189
190 if( !length ) 190 if( !length )
191 return 0; 191 return 0;
192 if( !level ) 192 if( !level )
193 return 0; 193 return 0;
194 194
195 restart: 195 restart:
196 if (fd == -1 || do_restart) 196 if (fd == -1 || do_restart)
197 fd = _gcry_rndegd_connect_socket (0); 197 fd = _gcry_rndegd_connect_socket (0);
198 198
199 do_restart = 0; 199 do_restart = 0;
200 200
201 nbytes = length < 255? length : 255; 201 nbytes = length < 255? length : 255;
202 /* First time we do it with a non blocking request */ 202 /* First time we do it with a non blocking request */
203 buffer[0] = 1; /* non blocking */ 203 buffer[0] = 1; /* non blocking */
204 buffer[1] = nbytes; 204 buffer[1] = nbytes;
205 if( do_write( fd, buffer, 2 ) == -1 ) 205 if( do_write( fd, buffer, 2 ) == -1 )
206 log_fatal("can't write to the EGD: %s\n", strerror(errno) ); 206 log_fatal("can't write to the EGD: %s\n", strerror(errno) );
207 n = do_read( fd, buffer, 1 ); 207 n = do_read( fd, buffer, 1 );
208 if( n == -1 ) 208 if( n == -1 )
209 { 209 {
210 log_error("read error on EGD: %s\n", strerror(errno)); 210 log_error("read error on EGD: %s\n", strerror(errno));
211 do_restart = 1; 211 do_restart = 1;
212 goto restart; 212 goto restart;
213 } 213 }
214 n = buffer[0]; 214 n = buffer[0];
215 if( n ) 215 if( n )
216 { 216 {
217 n = do_read( fd, buffer, n ); 217 n = do_read( fd, buffer, n );
218 if( n == -1 ) 218 if( n == -1 )
219 { 219 {
220 log_error("read error on EGD: %s\n", strerror(errno)); 220 log_error("read error on EGD: %s\n", strerror(errno));
221 do_restart = 1; 221 do_restart = 1;
222 goto restart; 222 goto restart;
223 } 223 }
224 (*add)( buffer, n, requester ); 224 (*add)( buffer, n, requester );
225 length -= n; 225 length -= n;
226 } 226 }
227 227
228 if( length ) 228 if( length )
229 { 229 {
230 log_info ( 230 log_info (
231 _("Please wait, entropy is being gathered. Do some work if it would\n" 231 _("Please wait, entropy is being gathered. Do some work if it would\n"
232 "keep you from getting bored, because it will improve the quality\n" 232 "keep you from getting bored, because it will improve the quality\n"
233 "of the entropy.\n") ); 233 "of the entropy.\n") );
234 } 234 }
235 while( length ) 235 while( length )
236 { 236 {
237 nbytes = length < 255? length : 255; 237 nbytes = length < 255? length : 255;
238 238
239 buffer[0] = 2; /* blocking */ 239 buffer[0] = 2; /* blocking */
240 buffer[1] = nbytes; 240 buffer[1] = nbytes;
241 if( do_write( fd, buffer, 2 ) == -1 ) 241 if( do_write( fd, buffer, 2 ) == -1 )
242 log_fatal("can't write to the EGD: %s\n", strerror(errno) ); 242 log_fatal("can't write to the EGD: %s\n", strerror(errno) );
243 n = do_read( fd, buffer, nbytes ); 243 n = do_read( fd, buffer, nbytes );
244 if( n == -1 ) 244 if( n == -1 )
245 { 245 {
246 log_error("read error on EGD: %s\n", strerror(errno)); 246 log_error("read error on EGD: %s\n", strerror(errno));
247 do_restart = 1; 247 do_restart = 1;
248 goto restart; 248 goto restart;
249 } 249 }
250 (*add)( buffer, n, requester ); 250 (*add)( buffer, n, requester );
251 length -= n; 251 length -= n;
252 } 252 }
253 memset(buffer, 0, sizeof(buffer) ); 253 memset(buffer, 0, sizeof(buffer) );
254 254
255 return 0; /* success */ 255 return 0; /* success */
256} 256}