/* See LICENSE file for copyright and license details. */ #include "libsecauth.h" #include #include #include #include #include #define PEPPER "pepper" int main(int argc, char *argv[]) { struct libsecauth_spec spec; char *message, *hash; size_t size, off; ssize_t r; int fd; if (argc != 2) { fprintf(stderr, "usage: %s password", argv[0]); return 1; } /* -- SERVER -- */ memset(&spec, 0, sizeof(spec)); spec.prehash = "$6$rounds=2000$salt1$"; spec.xferhash = "$1$salt2$"; spec.client_rounds = 100; spec.server_rounds = 0; size = libsecauth_format_spec(&spec, NULL, 0); message = malloc(size); if (!message) { perror("malloc"); return 1; } libsecauth_format_spec(&spec, message, size); /* -- CLIENT -- */ memset(&spec, 0, sizeof(spec)); if (libsecauth_parse_spec(&spec, message)) { perror("libsecauth_parse_spec"); return 1; } hash = libsecauth_client_hash(&spec, argv[1]); if (!hash) { perror("libsecauth_client_hash"); return 1; } free(message); message = hash; /* -- SERVER -- */ memset(&spec, 0, sizeof(spec)); spec.prehash = "$6$rounds=2000$salt1$"; spec.xferhash = "$1$salt2$"; spec.client_rounds = 100; spec.server_rounds = 0; spec.posthash = "$6$rounds=1000$salt3$"; if (libsecauth_server_hash(&spec, message, PEPPER, &hash) < 0) { perror("libsecauth_server_hash"); return 1; } spec.expected = hash; free(message); size = libsecauth_format_spec(&spec, NULL, 0); message = malloc(size); if (!message) { perror("malloc"); return 1; } libsecauth_format_spec(&spec, message, size); free(hash); message[size - 1] = '\n'; fd = open("democonfig", O_WRONLY | O_CREAT | O_TRUNC, 0600); if (fd < 0) { perror("open"); return 1; } for (off = 0; off < size; off += (size_t)r) { r = write(fd, &message[off], size - off); if (r <= 0) { perror("write"); return 1; } } close(fd); free(message); return 0; }