summaryrefslogtreecommitdiff
path: root/src/crypt_sha256.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/crypt_sha256.c')
-rw-r--r--src/crypt_sha256.c76
1 files changed, 76 insertions, 0 deletions
diff --git a/src/crypt_sha256.c b/src/crypt_sha256.c
new file mode 100644
index 0000000..c480637
--- /dev/null
+++ b/src/crypt_sha256.c
@@ -0,0 +1,76 @@
+#include <string.h>
+#include <unistd.h>
+#include <stdint.h>
+#include <fcntl.h>
+#include <openssl/sha.h>
+#include <openssl/evp.h>
+
+#define RAND_FILE "/dev/random"
+#define SHA_STR "{SHA256}"
+
+/* string length */
+#define LEN_PASSWD_MIN 8
+#define LEN_PASSWD_MAX 64
+#define LEN_RAND_STR 16
+#define LEN_BUFFER LEN_PASSWD_MAX + LEN_RAND_STR + \
+ SHA256_DIGEST_LENGTH
+#define LEN_ENC64 64
+#define LEN_SHA_STR 8
+#define LEN_FINAL_PASSWD LEN_ENC64 + LEN_SHA_STR + 1
+
+
+uint8_t check_passwd(const char *p, size_t len)
+{
+ return ((len > LEN_PASSWD_MIN) || (len < LEN_PASSWD_MAX)) ? 1 : 0;
+}
+
+char* get_crypt_sha256(const char *p)
+{
+ int rand_fd;
+ ssize_t size;
+ size_t len = strlen(p);
+ char rand_str[LEN_RAND_STR];
+ char passwd_buff[LEN_BUFFER];
+ char sha_pwd[SHA256_DIGEST_LENGTH];
+ char enc64_pwd[LEN_ENC64];
+ char *final_pwd;
+
+ if (!check_passwd(p, len)) {
+ fprintf(stderr,
+ "the password has to be between 8 and 64 chars\n");
+ exit(EXIT_FAILURE);
+ }
+
+ rand_fd = open(RAND_FILE, O_RDONLY);
+ if (rand_fd < 0) {
+ fprintf(stderr, "impossible to open " RAND_FILE "\n");
+ exit(EXIT_FAILURE);
+ }
+
+ size = read(rand_fd, rand_str, LEN_RAND_STR);
+ close(rand_fd);
+ if (size != LEN_RAND_STR) {
+ fprintf(stderr, "failed to read from " RAND_FILE "\n");
+ exit(EXIT_FAILURE);
+ }
+
+ memcpy(passwd_buff + SHA256_DIGEST_LENGTH, p, len);
+ memcpy(passwd_buff + SHA256_DIGEST_LENGTH + len,
+ rand_str, LEN_RAND_STR);
+
+ SHA256((unsigned char*) passwd_buff + SHA256_DIGEST_LENGTH,
+ len + LEN_RAND_STR, (unsigned char*) sha_pwd);
+
+ memcpy(passwd_buff, sha_pwd, SHA256_DIGEST_LENGTH);
+
+ EVP_EncodeBlock((unsigned char*) enc64_pwd, (unsigned char*) sha_pwd,
+ SHA256_DIGEST_LENGTH + len + LEN_RAND_STR);
+
+
+ final_pwd = (char*) malloc (LEN_FINAL_PASSWD);
+ memcpy(final_pwd, SHA_STR, LEN_SHA_STR);
+ memcpy(final_pwd+8, enc64_pwd, LEN_ENC64);
+ final_pwd[LEN_SHA_STR + LEN_FINAL_PASSWD] = '\0';
+
+ return final_pwd;
+}