Refactored key-derivation code into a separate file + some code clean-up.
This commit is contained in:
parent
102233a237
commit
a656e9de37
@ -44,11 +44,14 @@
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="src\junk.c" />
|
||||
<ClCompile Include="src\keygen.c" />
|
||||
<ClCompile Include="src\slunkcrypt.c" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="include\slunkcrypt.h" />
|
||||
<ClInclude Include="include\slunkcrypt.hpp" />
|
||||
<ClInclude Include="src\compiler.h" />
|
||||
<ClInclude Include="src\keygen.h" />
|
||||
<ClInclude Include="src\version.h" />
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
|
@ -21,6 +21,9 @@
|
||||
<ClCompile Include="src\junk.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\keygen.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="include\slunkcrypt.h">
|
||||
@ -32,5 +35,11 @@
|
||||
<ClInclude Include="include\slunkcrypt.hpp">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\keygen.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\compiler.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
</Project>
|
26
libslunkcrypt/src/compiler.h
Normal file
26
libslunkcrypt/src/compiler.h
Normal file
@ -0,0 +1,26 @@
|
||||
/******************************************************************************/
|
||||
/* SlunkCrypt, by LoRd_MuldeR <MuldeR2@GMX.de> */
|
||||
/* This work has been released under the CC0 1.0 Universal license! */
|
||||
/******************************************************************************/
|
||||
|
||||
#ifndef INC_SLUNKCRYPT_COMPILER_H
|
||||
#define INC_SLUNKCRYPT_COMPILER_H
|
||||
|
||||
/* Intel(R) oneAPI DPC++/C++ Compiler */
|
||||
#if defined(__INTEL_LLVM_COMPILER) && (!defined(__GNUC__))
|
||||
# define __GNUC__ 9
|
||||
#endif
|
||||
|
||||
/* Compiler compatibility */
|
||||
#if defined(_MSC_VER) && (!defined(__GNUC__))
|
||||
# define INLINE __inline
|
||||
# define UNUSED __pragma(warning(suppress: 4189))
|
||||
#elif defined(__GNUC__)
|
||||
# define INLINE __inline__
|
||||
# define UNUSED __attribute__((unused))
|
||||
#else
|
||||
# define INLINE inline
|
||||
# define UNUSED
|
||||
#endif
|
||||
|
||||
#endif
|
@ -11,14 +11,18 @@
|
||||
#endif
|
||||
|
||||
/* Internal */
|
||||
#include "../include/slunkcrypt.h"
|
||||
#include "slunkcrypt.h"
|
||||
#include "compiler.h"
|
||||
|
||||
/* CRT */
|
||||
#include <string.h>
|
||||
#include <fcntl.h>
|
||||
#include <limits.h>
|
||||
|
||||
/* Platform compatibility */
|
||||
// ==========================================================================
|
||||
// Platform compatibility
|
||||
// ==========================================================================
|
||||
|
||||
#ifdef _WIN32
|
||||
# include <Windows.h>
|
||||
#else
|
||||
@ -26,11 +30,30 @@
|
||||
# include <pthread.h>
|
||||
#endif
|
||||
|
||||
/* Compiler compatibility */
|
||||
/* detect destructor support */
|
||||
#undef ATTRIB_DESTRUCTOR
|
||||
#if defined(__GNUC__) || defined(__clang__)
|
||||
# define HAVE_DESTRUCTOR 1
|
||||
#else
|
||||
# define HAVE_DESTRUCTOR 0
|
||||
# define ATTRIB_DESTRUCTOR __attribute__((destructor))
|
||||
#endif
|
||||
|
||||
/* detect getrandom() support */
|
||||
#undef SYS_GETRANDOM
|
||||
#if defined(__GLIBC__) && (__GLIBC__ >= 2) && (__GLIBC_MINOR__ >= 25)
|
||||
# define SYS_GETRANDOM 1
|
||||
# include <sys/random.h>
|
||||
#elif defined(__FreeBSD__) && (__FreeBSD__ >= 12)
|
||||
# define SYS_GETRANDOM 1
|
||||
# include <sys/random.h>
|
||||
#endif
|
||||
|
||||
/* detect explicit_bzero() support */
|
||||
#undef EXPLICIT_BZERO
|
||||
#if defined(_WIN32) && defined(SecureZeroMemory)
|
||||
# define EXPLICIT_BZERO SecureZeroMemory
|
||||
#elif defined(__GLIBC__) && (__GLIBC__ >= 2) && (__GLIBC_MINOR__ >= 25)
|
||||
# define EXPLICIT_BZERO explicit_bzero
|
||||
#elif defined(__FreeBSD__) && (__FreeBSD__ >= 11)
|
||||
# define EXPLICIT_BZERO explicit_bzero
|
||||
#endif
|
||||
|
||||
// ==========================================================================
|
||||
@ -68,28 +91,13 @@ static void win32_call_once(CALL_ONCE_TYPE *const control, void (*init_routine)(
|
||||
// Random bytes
|
||||
// ==========================================================================
|
||||
|
||||
#ifdef _WIN32
|
||||
# define HAVE_GETRANDOM 0
|
||||
#else
|
||||
# if defined(__GLIBC__) && (__GLIBC__ >= 2) && (__GLIBC_MINOR__ >= 25)
|
||||
# define HAVE_GETRANDOM 1
|
||||
# elif defined(__FreeBSD__) && (__FreeBSD__ >= 12)
|
||||
# define HAVE_GETRANDOM 1
|
||||
# else
|
||||
# define HAVE_GETRANDOM 0
|
||||
# endif
|
||||
#endif
|
||||
#if HAVE_GETRANDOM
|
||||
# include <sys/random.h>
|
||||
#endif
|
||||
|
||||
/* Global state */
|
||||
static CALL_ONCE_TYPE s_random_is_initialized = CALL_ONCE_INIT;
|
||||
#if defined(_WIN32)
|
||||
typedef BOOLEAN(WINAPI *rtl_genrandom_t)(void *buffer, ULONG buff_size);
|
||||
static HMODULE s_dll_advapi32 = NULL;
|
||||
static rtl_genrandom_t s_rtl_genrandom = NULL;
|
||||
#elif !HAVE_GETRANDOM
|
||||
typedef BOOLEAN(WINAPI *rtlgenrandom_t)(void *buffer, ULONG buff_size);
|
||||
static HMODULE s_advapi32 = NULL;
|
||||
static rtlgenrandom_t s_rtlgenrandom = NULL;
|
||||
#elif !defined(SYS_GETRANDOM)
|
||||
static const char *const DEV_RANDOM[] = { "/dev/urandom", "/dev/arandom", "/dev/random", NULL };
|
||||
static int s_random_fd = -1;
|
||||
#endif
|
||||
@ -98,13 +106,13 @@ static int s_random_fd = -1;
|
||||
static void exit_random_source(void)
|
||||
{
|
||||
#if defined(_WIN32)
|
||||
s_rtl_genrandom = NULL;
|
||||
if (s_dll_advapi32)
|
||||
s_rtlgenrandom = NULL;
|
||||
if (s_advapi32)
|
||||
{
|
||||
FreeLibrary(s_dll_advapi32);
|
||||
s_dll_advapi32 = NULL;
|
||||
FreeLibrary(s_advapi32);
|
||||
s_advapi32 = NULL;
|
||||
}
|
||||
#elif !HAVE_GETRANDOM
|
||||
#elif !defined(SYS_GETRANDOM)
|
||||
if (s_random_fd >= 0)
|
||||
{
|
||||
close(s_random_fd);
|
||||
@ -117,11 +125,11 @@ static void exit_random_source(void)
|
||||
static void init_random_source(void)
|
||||
{
|
||||
#if defined(_WIN32)
|
||||
if ((s_dll_advapi32 = LoadLibraryW(L"advapi32.dll")))
|
||||
if ((s_advapi32 = LoadLibraryW(L"advapi32.dll")))
|
||||
{
|
||||
s_rtl_genrandom = (rtl_genrandom_t)GetProcAddress(s_dll_advapi32, "SystemFunction036");
|
||||
s_rtlgenrandom = (rtlgenrandom_t) GetProcAddress(s_advapi32, "SystemFunction036");
|
||||
}
|
||||
#elif !HAVE_GETRANDOM
|
||||
#elif !defined(SYS_GETRANDOM)
|
||||
for (size_t i = 0U; DEV_RANDOM[i]; ++i)
|
||||
{
|
||||
if ((s_random_fd = open(DEV_RANDOM[i], O_RDONLY)) >= 0)
|
||||
@ -130,7 +138,7 @@ static void init_random_source(void)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#if !HAVE_DESTRUCTOR
|
||||
#if !defined(ATTRIB_DESTRUCTOR)
|
||||
atexit(exit_random_source);
|
||||
#endif
|
||||
}
|
||||
@ -140,12 +148,12 @@ size_t slunkcrypt_random_bytes(uint8_t* const buffer, const size_t length)
|
||||
{
|
||||
CALL_ONCE(&s_random_is_initialized, init_random_source);
|
||||
#if defined(_WIN32)
|
||||
if (s_rtl_genrandom)
|
||||
if (s_rtlgenrandom)
|
||||
{
|
||||
const ULONG buff_size = (ULONG)length;
|
||||
return s_rtl_genrandom(buffer, buff_size) ? buff_size : 0U;
|
||||
return s_rtlgenrandom(buffer, buff_size) ? buff_size : 0U;
|
||||
}
|
||||
#elif HAVE_GETRANDOM
|
||||
#elif defined(SYS_GETRANDOM)
|
||||
const ssize_t result = getrandom(buffer, length, 0U);
|
||||
return (result < 0) ? 0U : ((size_t)result);
|
||||
#else
|
||||
@ -162,29 +170,12 @@ size_t slunkcrypt_random_bytes(uint8_t* const buffer, const size_t length)
|
||||
// Zero memory
|
||||
// ==========================================================================
|
||||
|
||||
#ifdef _WIN32
|
||||
# ifdef SecureZeroMemory
|
||||
# define HAVE_EXPLICIT_BZERO 1
|
||||
# define explicit_bzero SecureZeroMemory
|
||||
# else
|
||||
# define HAVE_EXPLICIT_BZERO 0
|
||||
# endif
|
||||
#else
|
||||
# if defined(__GLIBC__) && (__GLIBC__ >= 2) && (__GLIBC_MINOR__ >= 25)
|
||||
# define HAVE_EXPLICIT_BZERO 1
|
||||
# elif defined(__FreeBSD__) && (__FreeBSD__ >= 11)
|
||||
# define HAVE_EXPLICIT_BZERO 1
|
||||
# else
|
||||
# define HAVE_EXPLICIT_BZERO 0
|
||||
# endif
|
||||
#endif
|
||||
|
||||
void slunkcrypt_bzero(void* const buffer, const size_t length)
|
||||
{
|
||||
if ((buffer) && (length > 0U))
|
||||
{
|
||||
#if HAVE_EXPLICIT_BZERO
|
||||
explicit_bzero(buffer, length);
|
||||
#if defined(EXPLICIT_BZERO)
|
||||
EXPLICIT_BZERO(buffer, length);
|
||||
#else
|
||||
volatile uint8_t* ptr = (volatile uint8_t*) buffer;
|
||||
for (size_t i = 0U; i < length; ++i)
|
||||
@ -199,8 +190,8 @@ void slunkcrypt_bzero(void* const buffer, const size_t length)
|
||||
// Destructor
|
||||
// ==========================================================================
|
||||
|
||||
#if HAVE_DESTRUCTOR
|
||||
__attribute__((destructor)) void slunkcrypt_destructor()
|
||||
#if defined(ATTRIB_DESTRUCTOR)
|
||||
ATTRIB_DESTRUCTOR void slunkcrypt_destructor()
|
||||
{
|
||||
exit_random_source();
|
||||
}
|
||||
|
101
libslunkcrypt/src/keygen.c
Normal file
101
libslunkcrypt/src/keygen.c
Normal file
@ -0,0 +1,101 @@
|
||||
/******************************************************************************/
|
||||
/* SlunkCrypt, by LoRd_MuldeR <MuldeR2@GMX.de> */
|
||||
/* This work has been released under the CC0 1.0 Universal license! */
|
||||
/******************************************************************************/
|
||||
|
||||
/* Internal */
|
||||
#include "keygen.h"
|
||||
#include "compiler.h"
|
||||
|
||||
/* CRT */
|
||||
#include <limits.h>
|
||||
|
||||
/* Type */
|
||||
typedef struct
|
||||
{
|
||||
uint64_t hi, lo;
|
||||
}
|
||||
uint128_t;
|
||||
|
||||
// ==========================================================================
|
||||
// 128-Bit math support
|
||||
// ==========================================================================
|
||||
|
||||
#define READ_U128(X) ((((__uint128_t)(X).hi) << 64U) | ((__uint128_t)(X).lo))
|
||||
|
||||
static INLINE void multiply_u128(uint128_t *const out, const uint128_t lhs, const uint128_t rhs)
|
||||
{
|
||||
#if defined(__GNUC__) && defined(__SIZEOF_INT128__)
|
||||
const __uint128_t tmp = READ_U128(lhs) * READ_U128(rhs);
|
||||
out->hi = (uint64_t)(tmp >> 64U);
|
||||
out->lo = (uint64_t)(tmp & 0xFFFFFFFFFFFFFFFF);
|
||||
#else
|
||||
const uint64_t lolo = (lhs.lo & 0xFFFFFFFF) * (rhs.lo & 0xFFFFFFFF);
|
||||
const uint64_t hilo = (lhs.lo >> 32U) * (rhs.lo & 0xFFFFFFFF);
|
||||
const uint64_t lohi = (lhs.lo & 0xFFFFFFFF) * (rhs.lo >> 32U);
|
||||
const uint64_t hihi = (lhs.lo >> 32U) * (rhs.lo >> 32U);
|
||||
const uint64_t crss = (lolo >> 32U) + (hilo & 0xFFFFFFFF) + lohi;
|
||||
out->hi = (hilo >> 32U) + (crss >> 32) + hihi;
|
||||
out->lo = (crss << 32U) | (lolo & 0xFFFFFFFF);
|
||||
out->hi += (lhs.hi * rhs.lo) + (lhs.lo * rhs.hi); /* 128x128=128 */
|
||||
#endif
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// Hash function
|
||||
// ==========================================================================
|
||||
|
||||
static const uint128_t HASH_OFFSETBASE_128 = { 0x6C62272E07BB0142, 0x62B821756295C58D };
|
||||
static const uint128_t HASH_MAGICPRIME_128 = { 0x0000000001000000, 0x000000000000013B };
|
||||
|
||||
static INLINE void hash_update_u64(uint128_t* const hash, uint64_t value)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0U; i < sizeof(uint64_t); ++i, value >>= CHAR_BIT)
|
||||
{
|
||||
hash->lo ^= (uint8_t)(value & 0xFF);
|
||||
multiply_u128(hash, *hash, HASH_MAGICPRIME_128);
|
||||
}
|
||||
}
|
||||
|
||||
static INLINE void hash_update_str(uint128_t *const hash, const uint8_t *const data, const size_t data_len)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0U; i < data_len; ++i)
|
||||
{
|
||||
hash->lo ^= data[i];
|
||||
multiply_u128(hash, *hash, HASH_MAGICPRIME_128);
|
||||
}
|
||||
}
|
||||
|
||||
static INLINE uint128_t hash_code(const uint128_t *const seed, const uint8_t *const data, const size_t data_len)
|
||||
{
|
||||
uint128_t hash = HASH_OFFSETBASE_128;
|
||||
hash_update_u64(&hash, seed->lo);
|
||||
hash_update_u64(&hash, seed->hi);
|
||||
hash_update_str(&hash, data, data_len);
|
||||
return hash;
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// Key derivation
|
||||
// ==========================================================================
|
||||
|
||||
static INLINE uint64_t keygen_loop(uint64_t seed, const uint64_t i, const uint8_t *const passwd, const size_t passwd_len)
|
||||
{
|
||||
uint128_t hash = { seed, i };
|
||||
size_t u;
|
||||
for (u = 0U, seed = 0U; u < 99971U; ++u)
|
||||
{
|
||||
hash = hash_code(&hash, passwd, passwd_len);
|
||||
seed ^= hash.hi ^ hash.lo;
|
||||
}
|
||||
return seed;
|
||||
}
|
||||
|
||||
void slunkcrypt_keygen(keydata_t *const key, const uint64_t salt, const uint16_t pepper, const uint8_t *const passwd, const size_t passwd_len)
|
||||
{
|
||||
key->a = keygen_loop(salt, 0x162603FA1CDA99D3 + (uint64_t)pepper, passwd, passwd_len);
|
||||
key->b = keygen_loop(salt, 0xBFDEC4A6C1A46E09 + (uint64_t)pepper, passwd, passwd_len);
|
||||
key->c = keygen_loop(salt, 0x6BA17D11624973EE + (uint64_t)pepper, passwd, passwd_len);
|
||||
}
|
20
libslunkcrypt/src/keygen.h
Normal file
20
libslunkcrypt/src/keygen.h
Normal file
@ -0,0 +1,20 @@
|
||||
/******************************************************************************/
|
||||
/* SlunkCrypt, by LoRd_MuldeR <MuldeR2@GMX.de> */
|
||||
/* This work has been released under the CC0 1.0 Universal license! */
|
||||
/******************************************************************************/
|
||||
|
||||
#ifndef INC_SLUNKCRYPT_KEYGEN_H
|
||||
#define INC_SLUNKCRYPT_KEYGEN_H
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint64_t a, b, c;
|
||||
}
|
||||
keydata_t;
|
||||
|
||||
void slunkcrypt_keygen(keydata_t *const key, const uint64_t salt, const uint16_t pepper, const uint8_t* const passwd, const size_t passwd_len);
|
||||
|
||||
#endif
|
@ -4,32 +4,16 @@
|
||||
/******************************************************************************/
|
||||
|
||||
/* Internal */
|
||||
#include "../include/slunkcrypt.h"
|
||||
#include "slunkcrypt.h"
|
||||
#include "compiler.h"
|
||||
#include "keygen.h"
|
||||
#include "version.h"
|
||||
|
||||
/* CRT */
|
||||
#include <string.h>
|
||||
#include <limits.h>
|
||||
#include <assert.h>
|
||||
|
||||
/* Intel(R) oneAPI DPC++/C++ Compiler */
|
||||
#if defined(__INTEL_LLVM_COMPILER) && (!defined(__GNUC__))
|
||||
# define __GNUC__ 9
|
||||
#endif
|
||||
|
||||
/* Compiler compatibility */
|
||||
#if defined(_MSC_VER) && (!defined(__GNUC__))
|
||||
# define INLINE __inline
|
||||
# define UNUSED __pragma(warning(suppress: 4189))
|
||||
#elif defined(__GNUC__)
|
||||
# define INLINE __inline__
|
||||
# define UNUSED __attribute__((unused))
|
||||
#else
|
||||
# define INLINE inline
|
||||
# define UNUSED
|
||||
#endif
|
||||
|
||||
/* Version info */
|
||||
/* Version */
|
||||
const uint16_t SLUNKCRYPT_VERSION_MAJOR = LIB_VERSION_MAJOR;
|
||||
const uint16_t SLUNKCRYPT_VERSION_MINOR = LIB_VERSION_MINOR;
|
||||
const uint16_t SLUNKCRYPT_VERSION_PATCH = LIB_VERSION_PATCH;
|
||||
@ -42,12 +26,6 @@ const char *const SLUNKCRYPT_BUILD = __DATE__ ", " __TIME__;
|
||||
// Data structures
|
||||
// ==========================================================================
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint64_t hi, lo;
|
||||
}
|
||||
uint128_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint32_t x, y, z, w, v, d;
|
||||
@ -92,108 +70,19 @@ static INLINE uint32_t upper_u64(const uint64_t value)
|
||||
return (uint32_t)(value >> 32U);
|
||||
}
|
||||
|
||||
static INLINE uint8_t byte_u64(const uint64_t value, const size_t off)
|
||||
{
|
||||
assert(off < sizeof(uint64_t));
|
||||
return (uint8_t)((value >> (CHAR_BIT * off)) & 0xFF);
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// 128-Bit math support
|
||||
// ==========================================================================
|
||||
|
||||
#define READ_U128(X) ((((__uint128_t)(X).hi) << 64U) | ((__uint128_t)(X).lo))
|
||||
|
||||
static INLINE void multiply_u128(uint128_t *const out, const uint128_t lhs, const uint128_t rhs)
|
||||
{
|
||||
#if defined(__GNUC__) && defined(__SIZEOF_INT128__)
|
||||
const __uint128_t tmp = READ_U128(lhs) * READ_U128(rhs);
|
||||
out->hi = (uint64_t)(tmp >> 64U);
|
||||
out->lo = (uint64_t)(tmp & 0xFFFFFFFFFFFFFFFF);
|
||||
#else
|
||||
const uint64_t lolo = (lhs.lo & 0xFFFFFFFF) * (rhs.lo & 0xFFFFFFFF);
|
||||
const uint64_t hilo = (lhs.lo >> 32U) * (rhs.lo & 0xFFFFFFFF);
|
||||
const uint64_t lohi = (lhs.lo & 0xFFFFFFFF) * (rhs.lo >> 32U);
|
||||
const uint64_t hihi = (lhs.lo >> 32U) * (rhs.lo >> 32U);
|
||||
const uint64_t crss = (lolo >> 32U) + (hilo & 0xFFFFFFFF) + lohi;
|
||||
out->hi = (hilo >> 32U) + (crss >> 32) + hihi;
|
||||
out->lo = (crss << 32U) | (lolo & 0xFFFFFFFF);
|
||||
out->hi += (lhs.hi * rhs.lo) + (lhs.lo * rhs.hi); /* 128x128=128 */
|
||||
#endif
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// Hash function
|
||||
// ==========================================================================
|
||||
|
||||
static const uint128_t HASH_OFFSETBASE_128 = { 0x6C62272E07BB0142, 0x62B821756295C58D };
|
||||
static const uint128_t HASH_MAGICPRIME_128 = { 0x0000000001000000, 0x000000000000013B };
|
||||
|
||||
static INLINE void hash_update_str(uint128_t *const hash, const uint8_t *const data, const size_t data_len)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0U; i < data_len; ++i)
|
||||
{
|
||||
hash->lo ^= data[i];
|
||||
multiply_u128(hash, *hash, HASH_MAGICPRIME_128);
|
||||
}
|
||||
}
|
||||
|
||||
static INLINE void hash_update_u64(uint128_t *const hash, const uint64_t value)
|
||||
{
|
||||
size_t i;
|
||||
for (i = 0U; i < sizeof(uint64_t); ++i)
|
||||
{
|
||||
hash->lo ^= byte_u64(value, i);
|
||||
multiply_u128(hash, *hash, HASH_MAGICPRIME_128);
|
||||
}
|
||||
}
|
||||
|
||||
static INLINE uint128_t hash_code(const uint128_t *const salt, const uint8_t *const data, const size_t data_len)
|
||||
{
|
||||
uint128_t hash = HASH_OFFSETBASE_128;
|
||||
hash_update_u64(&hash, salt->lo);
|
||||
hash_update_u64(&hash, salt->hi);
|
||||
hash_update_str(&hash, data, data_len);
|
||||
return hash;
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// Key derivation
|
||||
// ==========================================================================
|
||||
|
||||
static INLINE uint64_t keygen_loop(uint64_t salt, const uint64_t pepper, const uint8_t *const passwd, const size_t passwd_len)
|
||||
{
|
||||
uint128_t hash = { salt, pepper };
|
||||
size_t u;
|
||||
for (u = 0U, salt = 0U; u < 99971U; ++u)
|
||||
{
|
||||
hash = hash_code(&hash, passwd, passwd_len);
|
||||
salt ^= hash.hi ^ hash.lo;
|
||||
}
|
||||
return salt;
|
||||
}
|
||||
|
||||
static INLINE void generate_key(uint64_t *const key, const uint64_t salt, const uint16_t pepper, const uint8_t *const passwd, const size_t passwd_len)
|
||||
{
|
||||
key[0U] = keygen_loop(salt, 0x162603FA1CDA99D3 + (uint64_t)pepper, passwd, passwd_len);
|
||||
key[1U] = keygen_loop(salt, 0xBFDEC4A6C1A46E09 + (uint64_t)pepper, passwd, passwd_len);
|
||||
key[2U] = keygen_loop(salt, 0x6BA17D11624973EE + (uint64_t)pepper, passwd, passwd_len);
|
||||
}
|
||||
|
||||
// ==========================================================================
|
||||
// Deterministic random bit generator
|
||||
// ==========================================================================
|
||||
|
||||
static INLINE void random_init(rand_state_t *const state, const uint64_t *const key)
|
||||
static INLINE void random_init(rand_state_t *const state, const keydata_t *const key)
|
||||
{
|
||||
slunkcrypt_bzero(state, sizeof(rand_state_t));
|
||||
state->x = lower_u64(key[0U]);
|
||||
state->y = upper_u64(key[0U]);
|
||||
state->z = lower_u64(key[1U]);
|
||||
state->w = upper_u64(key[1U]);
|
||||
state->v = lower_u64(key[2U]);
|
||||
state->d = upper_u64(key[2U]);
|
||||
state->x = lower_u64(key->a);
|
||||
state->y = upper_u64(key->a);
|
||||
state->z = lower_u64(key->b);
|
||||
state->w = upper_u64(key->b);
|
||||
state->v = lower_u64(key->c);
|
||||
state->d = upper_u64(key->c);
|
||||
}
|
||||
|
||||
static INLINE uint32_t random_next(rand_state_t *const state)
|
||||
@ -210,12 +99,12 @@ static INLINE uint32_t random_next(rand_state_t *const state)
|
||||
static INLINE void random_seed(rand_state_t *const state, uint64_t salt, const uint16_t pepper, const uint8_t *const passwd, const size_t passwd_len)
|
||||
{
|
||||
size_t i;
|
||||
uint64_t key[3U];
|
||||
keydata_t key;
|
||||
do
|
||||
{
|
||||
generate_key(key, salt++, pepper, passwd, passwd_len);
|
||||
random_init(state, key);
|
||||
slunkcrypt_bzero(&key, 3U * sizeof(uint64_t));
|
||||
slunkcrypt_keygen(&key, salt++, pepper, passwd, passwd_len);
|
||||
random_init(state, &key);
|
||||
slunkcrypt_bzero(&key, sizeof(keydata_t));
|
||||
}
|
||||
while (!(state->x || state->y || state->z || state->w || state->v));
|
||||
for (i = 0U; i < 97U; ++i)
|
||||
|
Loading…
Reference in New Issue
Block a user