safe

Password protected secret keeper
git clone git://git.z3bra.org/safe.git
Log | Files | Refs | README | LICENSE

commit fcb30202c868763203d8dc6f490e030e29a3b6d7
parent 2439226cb260c2c813d69e7a71cb0e2cdf739625
Author: Willy Goiffon <dev@z3bra.org>
Date:   Mon, 24 Jun 2019 18:10:01 +0200

Lock/Unlock sensitive memory chunks

Diffstat:
safe-agent.c | 24++++++++++++++++++------
safe.c | 19+++++++++++++++----
2 files changed, 33 insertions(+), 10 deletions(-)

diff --git a/safe-agent.c b/safe-agent.c @@ -121,27 +121,34 @@ creatsock(char *sockpath) void forgetkey() { - memset(s.saltkey, 0, sizeof(s.saltkey)); + sodium_memzero(s.saltkey, sizeof(s.saltkey)); s.loaded = 0; alarm(0); - fprintf(stderr, "memory cleared\n"); } void sighandler(int signal) { + int term = 0; + switch (signal) { case SIGINT: case SIGTERM: - unlink(sockp); - rmdir(dirname(sockp)); - exit(0); - /* NOTREACHED */ + term = 1; + /* FALLTHROUGH */ case SIGALRM: case SIGUSR1: forgetkey(); + break; } + + if (term) { + unlink(sockp); + rmdir(dirname(sockp)); + sodium_munlock(s.saltkey, sizeof(s.saltkey)); + exit(0); + } } int @@ -259,5 +266,10 @@ skip: signal(SIGUSR1, sighandler); signal(SIGALRM, sighandler); + if (sodium_init() < 0) + return -1; + + sodium_mlock(s.saltkey, sizeof(s.saltkey)); + return servekey(timeout); } diff --git a/safe.c b/safe.c @@ -212,7 +212,7 @@ err: int trydecrypt(struct safe *s, int fd) { - int eof = 0; + int r = 0, eof = 0; ssize_t n; uint8_t tag; uint8_t m[BUFSIZ]; @@ -225,14 +225,16 @@ trydecrypt(struct safe *s, int fd) if (crypto_secretstream_xchacha20poly1305_init_pull(&st, h, s->key)) return -1; + sodium_mlock(m, sizeof(m)); while ((n = xread(fd, c, sizeof(c), &eof)) > 0) { if (crypto_secretstream_xchacha20poly1305_pull(&st, m, &mlen, &tag, c, n, NULL, 0)) - return -1; + r--; if (eof && tag != crypto_secretstream_xchacha20poly1305_TAG_FINAL) - return -1; + r--; } - return 0; + sodium_munlock(m, sizeof(m)); + return r; } int @@ -345,6 +347,8 @@ main(int argc, char *argv[]) if (sodium_init() < 0) return -1; + sodium_mlock(s.key, sizeof(s.key)); + if (!safe) safe = SAFE; @@ -364,6 +368,7 @@ main(int argc, char *argv[]) if (!haskey) { readpass("password:", &passphrase, &pplen); + sodium_mlock(passphrase, pplen); /* write master password entry if not present */ if (fd < 0 && errno == ENOENT) { @@ -372,10 +377,13 @@ main(int argc, char *argv[]) /* input for master password again to check */ readpass("verify:", &passphrase2, &pplen2); + sodium_mlock(passphrase2, pplen2); + if (pplen != pplen2 || memcmp(passphrase, passphrase2, pplen)) { fprintf(stderr, "password mismatch\n"); return -1; } + sodium_munlock(passphrase2, pplen2); fd = open(MASTER, O_RDWR | O_CREAT | O_EXCL, 0600); if (fd < 0) @@ -391,6 +399,7 @@ main(int argc, char *argv[]) deriv((char *)passphrase, &s); } + sodium_munlock(passphrase, pplen); haskey = 1; } @@ -432,5 +441,7 @@ main(int argc, char *argv[]) close(fd); } + sodium_munlock(s.key, sizeof(s.key)); + return 0; }