diff options
author | Dina K Nimeh <Dina.Nimeh@Sun.COM> | 2009-02-27 15:36:17 -0800 |
---|---|---|
committer | Dina K Nimeh <Dina.Nimeh@Sun.COM> | 2009-02-27 15:36:17 -0800 |
commit | 19193bb63b10fe65b6e01f1ce7232407a18a917a (patch) | |
tree | f4020b8a5f362ae77ab9c6255f35f5b61b676b93 /usr/src/lib/libcryptoutil | |
parent | 6b2c23f3a9ab26cb870fe7091351ea9587fdee71 (diff) | |
download | illumos-joyent-19193bb63b10fe65b6e01f1ce7232407a18a917a.tar.gz |
6784451 consolidate duplicative looping_read() and looping_write() code into libcryptoutil
Diffstat (limited to 'usr/src/lib/libcryptoutil')
-rw-r--r-- | usr/src/lib/libcryptoutil/common/cryptoutil.h | 6 | ||||
-rw-r--r-- | usr/src/lib/libcryptoutil/common/mapfile-vers | 3 | ||||
-rw-r--r-- | usr/src/lib/libcryptoutil/common/random.c | 55 |
3 files changed, 52 insertions, 12 deletions
diff --git a/usr/src/lib/libcryptoutil/common/cryptoutil.h b/usr/src/lib/libcryptoutil/common/cryptoutil.h index 85896e398a..d041262129 100644 --- a/usr/src/lib/libcryptoutil/common/cryptoutil.h +++ b/usr/src/lib/libcryptoutil/common/cryptoutil.h @@ -19,7 +19,7 @@ * CDDL HEADER END */ /* - * Copyright 2008 Sun Microsystems, Inc. All rights reserved. + * Copyright 2009 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ @@ -148,6 +148,10 @@ extern int pkcs11_random_data(void *dbuf, size_t dlen); extern int pkcs11_nzero_random_data(void *dbuf, size_t dlen); extern int pkcs11_read_data(char *filename, void **dbuf, size_t *dlen); +extern int open_nointr(const char *path, int oflag, ...); +extern ssize_t readn_nointr(int fd, void *dbuf, size_t dlen); +extern ssize_t writen_nointr(int fd, void *dbuf, size_t dlen); + #ifdef __cplusplus } #endif diff --git a/usr/src/lib/libcryptoutil/common/mapfile-vers b/usr/src/lib/libcryptoutil/common/mapfile-vers index 4fb4647c7e..e7e5b12789 100644 --- a/usr/src/lib/libcryptoutil/common/mapfile-vers +++ b/usr/src/lib/libcryptoutil/common/mapfile-vers @@ -53,6 +53,7 @@ SUNWprivate { get_metaslot_info; get_pkcs11conf_info; hexstr_to_bytes; + open_nointr; pkcs11_default_token; pkcs11_get_pass; pkcs11_mech2keytype; @@ -63,8 +64,10 @@ SUNWprivate { pkcs11_read_data; pkcs11_str2mech; pkcs11_strerror; + readn_nointr; str2lifetime; tohexstr; + writen_nointr; local: *; }; diff --git a/usr/src/lib/libcryptoutil/common/random.c b/usr/src/lib/libcryptoutil/common/random.c index 6d91dbfea4..5a254ed34d 100644 --- a/usr/src/lib/libcryptoutil/common/random.c +++ b/usr/src/lib/libcryptoutil/common/random.c @@ -19,18 +19,17 @@ * CDDL HEADER END */ /* - * Copyright 2008 Sun Microsystems, Inc. All rights reserved. + * Copyright 2009 Sun Microsystems, Inc. All rights reserved. * Use is subject to license terms. */ -#pragma ident "%Z%%M% %I% %E% SMI" - #include <stdio.h> #include <unistd.h> #include <errno.h> #include <string.h> #include <fcntl.h> #include <locale.h> +#include <stdarg.h> #include <cryptoutil.h> #ifdef _REENTRANT @@ -60,13 +59,19 @@ static int urandom_fd = -1; * Equivalent of open(2) insulated from EINTR. * Also sets close-on-exec. */ -static int -OPEN(const char *path, int oflag) +int +open_nointr(const char *path, int oflag, ...) { int fd; + mode_t pmode; + va_list alist; + + va_start(alist, oflag); + pmode = va_arg(alist, mode_t); + va_end(alist); do { - if ((fd = open(path, oflag)) >= 0) { + if ((fd = open(path, oflag, pmode)) >= 0) { (void) fcntl(fd, F_SETFD, FD_CLOEXEC); break; } @@ -78,8 +83,8 @@ OPEN(const char *path, int oflag) /* * Equivalent of read(2) insulated from EINTR. */ -static ssize_t -READ(int fd, void *dbuf, size_t dlen) +ssize_t +readn_nointr(int fd, void *dbuf, size_t dlen) { char *marker = dbuf; size_t left = dlen; @@ -93,6 +98,34 @@ READ(int fd, void *dbuf, size_t dlen) } err = nread; /* hard error */ break; + } else if (nread == 0) { + break; + } + } + return (err != 0 ? err : dlen - left); +} + +/* + * Equivalent of write(2) insulated from EINTR. + */ +ssize_t +writen_nointr(int fd, void *dbuf, size_t dlen) +{ + char *marker = dbuf; + size_t left = dlen; + ssize_t nwrite = 0, err; + + for (err = 0; left > 0 && nwrite != -1; marker += nwrite, + left -= nwrite) { + if ((nwrite = write(fd, marker, left)) < 0) { + if (errno == EINTR) { /* keep trying */ + nwrite = 0; + continue; + } + err = nwrite; /* hard error */ + break; + } else if (nwrite == 0) { + break; } } return (err != 0 ? err : dlen - left); @@ -107,7 +140,7 @@ pkcs11_open_random(void) { RAND_LOCK(&random_mutex); if (random_fd < 0) - random_fd = OPEN(RANDOM_DEVICE, O_RDONLY); + random_fd = open_nointr(RANDOM_DEVICE, O_RDONLY); RAND_UNLOCK(&random_mutex); return (random_fd); } @@ -117,7 +150,7 @@ pkcs11_open_urandom(void) { RAND_LOCK(&urandom_mutex); if (urandom_fd < 0) - urandom_fd = OPEN(URANDOM_DEVICE, O_RDONLY); + urandom_fd = open_nointr(URANDOM_DEVICE, O_RDONLY); RAND_UNLOCK(&urandom_mutex); return (urandom_fd); } @@ -161,7 +194,7 @@ pkcs11_random_data(void *dbuf, size_t dlen) if (pkcs11_open_urandom() < 0) return (-1); - if (READ(urandom_fd, dbuf, dlen) == dlen) + if (readn_nointr(urandom_fd, dbuf, dlen) == dlen) return (0); return (-1); } |