adds sha2 support for keyfile auth

Fri, 24 Feb 2017 11:17:53 +0100

author
Olaf Wintermann <olaf.wintermann@gmail.com>
date
Fri, 24 Feb 2017 11:17:53 +0100
changeset 174
8f2a834d1d68
parent 171
af7e2d80dee6
child 179
ef6827505bd2

adds sha2 support for keyfile auth

make/solaris.mk file | annotate | diff | comparison | revisions
src/server/config/keyfile.c file | annotate | diff | comparison | revisions
src/server/daemon/keyfile_auth.c file | annotate | diff | comparison | revisions
src/server/daemon/keyfile_auth.h file | annotate | diff | comparison | revisions
--- a/make/solaris.mk	Tue Feb 14 12:56:23 2017 +0100
+++ b/make/solaris.mk	Fri Feb 24 11:17:53 2017 +0100
@@ -29,7 +29,7 @@
 
 # compiler and linker flags
 CFLAGS += -DSOLARIS -D_REENTRANT -D_POSIX_PTHREAD_SEMANTICS
-LDFLAGS += -lsocket -lnsl -lsendfile -lposix4 -lpthread -ldl -lm -lldap
+LDFLAGS += -lsocket -lnsl -lsendfile -lposix4 -lpthread -ldl -lm -lmd -lldap
 
 #PLUGINS = java
 
--- a/src/server/config/keyfile.c	Tue Feb 14 12:56:23 2017 +0100
+++ b/src/server/config/keyfile.c	Fri Feb 24 11:17:53 2017 +0100
@@ -104,6 +104,10 @@
     
     if(!sstrcmp(hash_type, sstr("SSHA"))) {
         entry->hashtype = KEYFILE_SSHA;
+    } else if(!sstrcmp(hash_type, sstr("SSHA256"))) {
+        entry->hashtype = KEYFILE_SSHA256;
+    } else if(!sstrcmp(hash_type, sstr("SSHA512"))) {
+        entry->hashtype = KEYFILE_SSHA512;
     } else {
         // unkown hash type
         log_ereport(
--- a/src/server/daemon/keyfile_auth.c	Tue Feb 14 12:56:23 2017 +0100
+++ b/src/server/daemon/keyfile_auth.c	Fri Feb 24 11:17:53 2017 +0100
@@ -29,7 +29,14 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+
 #include <openssl/sha.h>
+#if defined(__sun) && defined(__SunOS_5_10)
+#include <sha2.h>
+#define SHA256_Init     SHA256Init
+#define SHA256_Update   SHA256Update
+#define SHA256_Final    SHA256Final
+#endif
 
 #include "../util/atomic.h"
 #include "../util/util.h"
@@ -113,10 +120,7 @@
 
 int keyfile_user_verify_password(User *user, char *password) {
     KeyfileUser *usr = (KeyfileUser*)user;
-    switch(usr->hash_type) {
-        case KEYFILE_SSHA: return ssha_verify(usr, password);
-    }
-    return 0;
+    return ssha_verify(usr, password);
 }
 
 int keyfile_user_check_group(User *user, char *group) {
@@ -137,26 +141,54 @@
 
 int ssha_verify(KeyfileUser *user, char *password) {
     /*
-     * SSHA: SHA1(pw + salt) + 8 bytes salt
+     * SSHA: SHA(pw + salt) + salt
      * user->hash is already base64 decoded
      */
     
-    // TODO: variable length salt
+    size_t hlen;
+    switch(user->hash_type) {
+        case KEYFILE_SSHA: hlen = 20; break;
+        case KEYFILE_SSHA256: hlen = 32; break;
+        case KEYFILE_SSHA512: hlen = 64; break;
+    }
     
-    char *salt = user->hash + user->hashlen - 8; // last 8 bytes are the salt 
-    size_t pwlen = strlen(password);
+    char *salt = user->hash + hlen;
+    size_t saltlen = user->hashlen - hlen;
+    
+    size_t pwlen = strlen(password); 
     
-    size_t saltpwlen = pwlen + 8;
-    char *saltpw = malloc(saltpwlen);
-    memcpy(saltpw, password, pwlen);
-    memcpy(saltpw + pwlen, salt, 8);
+    unsigned char pwhash[64];
+    switch(user->hash_type) {
+        case KEYFILE_SSHA: {
+            SHA_CTX ctx;
+            SHA1_Init(&ctx);
+            SHA1_Update(&ctx, password, pwlen);
+            SHA1_Update(&ctx, salt, saltlen);
+            SHA1_Final(pwhash, &ctx);
+            break;
+        }
+        case KEYFILE_SSHA256: {
+            SHA256_CTX ctx;
+            SHA256_Init(&ctx);
+            SHA256_Update(&ctx, password, pwlen);
+            SHA256_Update(&ctx, salt, saltlen);
+            SHA256_Final(pwhash, &ctx);
+            break;
+        }
+        case KEYFILE_SSHA512: {
+            SHA512_CTX ctx;
+            SHA512_Init(&ctx);
+            SHA512_Update(&ctx, password, pwlen);
+            SHA512_Update(&ctx, salt, saltlen);
+            SHA512_Final(pwhash, &ctx);
+            break;
+        }
+    }
     
-    unsigned char pwhash[20];
-    SHA1((const unsigned char*)saltpw, saltpwlen, pwhash);
-    
-    if(!memcmp(user->hash, pwhash, 20)) {
+    if(!memcmp(user->hash, pwhash, hlen)) {
         return 1;
     } else {
         return 0;
     }
 }
+
--- a/src/server/daemon/keyfile_auth.h	Tue Feb 14 12:56:23 2017 +0100
+++ b/src/server/daemon/keyfile_auth.h	Fri Feb 24 11:17:53 2017 +0100
@@ -42,7 +42,9 @@
 typedef struct keyfile_user   KeyfileUser;
     
 enum KeyfileHashType {
-    KEYFILE_SSHA = 0
+    KEYFILE_SSHA = 0,
+    KEYFILE_SSHA256,
+    KEYFILE_SSHA512
 };
 
 struct keyfile {

mercurial