Patrick Welche <prlw1@cam.ac.uk>
[netbsd-mini2440.git] / external / ibm-public / postfix / dist / src / tls / tls_prng_file.c
blobc2038ca0ee2c1e3b7134edd3e9fab75d4ab9e67d
1 /* $NetBSD$ */
3 /*++
4 /* NAME
5 /* tls_prng_file 3
6 /* SUMMARY
7 /* seed OpenSSL PRNG from entropy file
8 /* SYNOPSIS
9 /* #include <tls_prng_src.h>
11 /* TLS_PRNG_SRC *tls_prng_file_open(name, timeout)
12 /* const char *name;
13 /* int timeout;
15 /* ssize_t tls_prng_file_read(fh, length)
16 /* TLS_PRNG_SRC *fh;
17 /* size_t length;
19 /* int tls_prng_file_close(fh)
20 /* TLS_PRNG_SRC *fh;
21 /* DESCRIPTION
22 /* tls_prng_file_open() open the specified file and returns
23 /* a handle that should be used with all subsequent access.
25 /* tls_prng_file_read() reads the requested number of bytes from
26 /* the entropy file and updates the OpenSSL PRNG. The file is not
27 /* locked for shared or exclusive access.
29 /* tls_prng_file_close() closes the specified entropy file
30 /* and releases memory that was allocated for the handle.
32 /* Arguments:
33 /* .IP name
34 /* The pathname of the entropy file.
35 /* .IP length
36 /* The number of bytes to read from the entropy file.
37 /* .IP timeout
38 /* Time limit on individual I/O operations.
39 /* DIAGNOSTICS
40 /* tls_prng_file_open() returns a null pointer on error.
42 /* tls_prng_file_read() returns -1 on error, the number
43 /* of bytes received on success.
45 /* tls_prng_file_close() returns -1 on error, 0 on success.
47 /* In all cases the errno variable indicates the type of error.
48 /* LICENSE
49 /* .ad
50 /* .fi
51 /* The Secure Mailer license must be distributed with this software.
52 /* AUTHOR(S)
53 /* Wietse Venema
54 /* IBM T.J. Watson Research
55 /* P.O. Box 704
56 /* Yorktown Heights, NY 10598, USA
57 /*--*/
59 /* System library. */
61 #include <sys_defs.h>
62 #include <fcntl.h>
63 #include <unistd.h>
64 #include <limits.h>
65 #include <errno.h>
67 /* OpenSSL library. */
69 #ifdef USE_TLS
70 #include <openssl/rand.h> /* For the PRNG */
72 /* Utility library. */
74 #include <msg.h>
75 #include <mymalloc.h>
76 #include <connect.h>
77 #include <iostuff.h>
79 /* TLS library. */
81 #include <tls_prng.h>
83 /* tls_prng_file_open - open entropy file */
85 TLS_PRNG_SRC *tls_prng_file_open(const char *name, int timeout)
87 const char *myname = "tls_prng_file_open";
88 TLS_PRNG_SRC *fh;
89 int fd;
91 if ((fd = open(name, O_RDONLY, 0)) < 0) {
92 if (msg_verbose)
93 msg_info("%s: cannot open entropy file %s: %m", myname, name);
94 return (0);
95 } else {
96 fh = (TLS_PRNG_SRC *) mymalloc(sizeof(*fh));
97 fh->fd = fd;
98 fh->name = mystrdup(name);
99 fh->timeout = timeout;
100 if (msg_verbose)
101 msg_info("%s: opened entropy file %s", myname, name);
102 return (fh);
106 /* tls_prng_file_read - update internal PRNG from entropy file */
108 ssize_t tls_prng_file_read(TLS_PRNG_SRC *fh, size_t len)
110 const char *myname = "tls_prng_file_read";
111 char buffer[8192];
112 ssize_t to_read;
113 ssize_t count;
115 if (msg_verbose)
116 msg_info("%s: seed internal pool from file %s", myname, fh->name);
118 if (lseek(fh->fd, 0, SEEK_SET) < 0) {
119 if (msg_verbose)
120 msg_info("cannot seek entropy file %s: %m", fh->name);
121 return (-1);
123 errno = 0;
124 for (to_read = len; to_read > 0; to_read -= count) {
125 if ((count = timed_read(fh->fd, buffer, to_read > sizeof(buffer) ?
126 sizeof(buffer) : to_read,
127 fh->timeout, (void *) 0)) < 0) {
128 if (msg_verbose)
129 msg_info("cannot read entropy file %s: %m", fh->name);
130 return (-1);
132 if (count == 0)
133 break;
134 RAND_seed(buffer, count);
136 if (msg_verbose)
137 msg_info("read %ld bytes from entropy file %s: %m",
138 (long) (len - to_read), fh->name);
139 return (len - to_read);
142 /* tls_prng_file_close - close entropy file */
144 int tls_prng_file_close(TLS_PRNG_SRC *fh)
146 const char *myname = "tls_prng_file_close";
147 int err;
149 if (msg_verbose)
150 msg_info("%s: close entropy file %s", myname, fh->name);
151 err = close(fh->fd);
152 myfree(fh->name);
153 myfree((char *) fh);
154 return (err);
157 #endif