Skip to content

Commit

Permalink
Register function generates a shard for the mail realm.
Browse files Browse the repository at this point in the history
  • Loading branch information
ladar committed Oct 13, 2016
1 parent 17591cc commit e552a21
Show file tree
Hide file tree
Showing 7 changed files with 120 additions and 50 deletions.
22 changes: 11 additions & 11 deletions check/magma/providers/stacie_check.c
Original file line number Diff line number Diff line change
Expand Up @@ -262,8 +262,8 @@ bool_t check_stacie_determinism(void) {
res1 = res2 = NULL;*/


if (!(res1 = stacie_entropy_seed_derive(STACIE_ROUNDS_MIN, password, salt)) ||
!(res2 = stacie_entropy_seed_derive(STACIE_ROUNDS_MIN, password, salt)) ||
if (!(res1 = stacie_entropy_seed_derive(STACIE_KEY_ROUNDS_MIN, password, salt)) ||
!(res2 = stacie_entropy_seed_derive(STACIE_KEY_ROUNDS_MIN, password, salt)) ||
st_cmp_cs_eq(res1, res2)) {
st_cleanup(res1, res2);
return false;
Expand All @@ -274,8 +274,8 @@ bool_t check_stacie_determinism(void) {
res1 = res2 = NULL;

// Run deterministic tests on the hash derivation stage.
if (!(res1 = stacie_hashed_key_derive(base, STACIE_ROUNDS_MIN, username, password, salt)) ||
!(res2 = stacie_hashed_key_derive(base, STACIE_ROUNDS_MIN, username, password, salt)) ||
if (!(res1 = stacie_hashed_key_derive(base, STACIE_KEY_ROUNDS_MIN, username, password, salt)) ||
!(res2 = stacie_hashed_key_derive(base, STACIE_KEY_ROUNDS_MIN, username, password, salt)) ||
st_cmp_cs_eq(res1, res2)) {
st_cleanup(res1, res2, base);
return false;
Expand Down Expand Up @@ -363,27 +363,27 @@ bool_t check_stacie_parameters(void) {
return false;
}

if ((res = stacie_entropy_seed_derive(STACIE_ROUNDS_MIN, temp_st, NULL))) {
if ((res = stacie_entropy_seed_derive(STACIE_KEY_ROUNDS_MIN, temp_st, NULL))) {
st_free(res);
return false;
}

if ((res = stacie_entropy_seed_derive(STACIE_ROUNDS_MIN, temp_st, temp_st64))) {
if ((res = stacie_entropy_seed_derive(STACIE_KEY_ROUNDS_MIN, temp_st, temp_st64))) {
st_free(res);
return false;
}

if ((res = stacie_entropy_seed_derive(STACIE_ROUNDS_MIN, temp_st, temp_st))) {
if ((res = stacie_entropy_seed_derive(STACIE_KEY_ROUNDS_MIN, temp_st, temp_st))) {
st_free(res);
return false;
}

if ((res = stacie_hashed_key_derive(NULL, STACIE_ROUNDS_MIN, temp_st, temp_st, NULL))) {
if ((res = stacie_hashed_key_derive(NULL, STACIE_KEY_ROUNDS_MIN, temp_st, temp_st, NULL))) {
st_free(res);
return false;
}

if ((res = stacie_hashed_key_derive(temp_st, STACIE_ROUNDS_MIN, temp_st, temp_st, NULL))) {
if ((res = stacie_hashed_key_derive(temp_st, STACIE_KEY_ROUNDS_MIN, temp_st, temp_st, NULL))) {
st_free(res);
return false;
}
Expand All @@ -398,12 +398,12 @@ bool_t check_stacie_parameters(void) {
return false;
}

if ((res = stacie_hashed_key_derive(temp_st64, STACIE_ROUNDS_MIN, NULL, temp_st, NULL))) {
if ((res = stacie_hashed_key_derive(temp_st64, STACIE_KEY_ROUNDS_MIN, NULL, temp_st, NULL))) {
st_free(res);
return false;
}

if ((res = stacie_hashed_key_derive(temp_st64, STACIE_ROUNDS_MIN, temp_st, NULL, NULL))) {
if ((res = stacie_hashed_key_derive(temp_st64, STACIE_KEY_ROUNDS_MIN, temp_st, NULL, NULL))) {
st_free(res);
return false;
}
Expand Down
8 changes: 4 additions & 4 deletions dev/scripts/parsers/queries.sh
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,9 @@ cd $BASE/../../../

MAGMA_DIST=`pwd`

QUERIES=`printf "#define QUERIES_INIT"; cat $MAGMA_DIST/src/queries.h | grep "\#define" | egrep -v "MAGMA_DATA_QUERIES_H|INIT" | grep -v "//" | awk -F' ' '{ print $2 }' | egrep "^[A-Z_]+$" | awk -F' ' '{ print "\t\t\t\t\t\t\t\t\t\t\t" $1 ", \\\\" }' | head --bytes=-4 | tail --bytes=+11`
STMTS=`printf "\n\n#define STMTS_INIT"; cat $MAGMA_DIST/src/queries.h | grep "\#define" | egrep -v "MAGMA_DATA_QUERIES_H|INIT" | grep -v "//" | awk -F' ' '{ print $2 }' | egrep "^[A-Z_]+$" | awk -F' ' '{ print "\t\t\t\t\t\t\t\t\t\t\t**" tolower($1) ", \\\\" }' | head --bytes=-4 | tail --bytes=+10`
QUERIES=`printf "#define QUERIES_INIT\t\t\t\t\t"; cat $MAGMA_DIST/src/queries.h | grep "\#define" | egrep -v "MAGMA_DATA_QUERIES_H|INIT" | grep -v "//" | awk -F' ' '{ print $2 }' | egrep "^[A-Z_]+$" | awk -F' ' '{ print "\t\t\t\t\t\t\t\t\t\t\t" $1 ", \\\\" }' | head --bytes=-4 | tail --bytes=+11`
STMTS=`printf "\n\n#define STMTS_INIT\t\t\t\t\t"; cat $MAGMA_DIST/src/queries.h | grep "\#define" | egrep -v "MAGMA_DATA_QUERIES_H|INIT" | grep -v "//" | awk -F' ' '{ print $2 }' | egrep "^[A-Z_]+$" | awk -F' ' '{ print "\t\t\t\t\t\t\t\t\t\t\t**" tolower($1) ", \\\\" }' | head --bytes=-4 | tail --bytes=+10`

#printf "$QUERIES$STMTS\n" | xclip -in -selection clipboard
printf "$QUERIES$STMTS\n" | clipit
printf "$QUERIES\n\n$STMTS"
printf "$QUERIES\n\n$STMTS"
6 changes: 2 additions & 4 deletions res/sql/Migration.sql
Original file line number Diff line number Diff line change
Expand Up @@ -61,14 +61,12 @@ CREATE TABLE `User_Keys` (

DROP TABLE IF EXISTS `User_Realms`;
CREATE TABLE `User_Realms` (
`realmnum` bigint(20) unsigned NOT NULL AUTO_INCREMENT,
`usernum` bigint(20) unsigned NOT NULL DEFAULT '0',
`serialnum` smallint(5) NOT NULL DEFAULT '0',
`serial` smallint(5) NOT NULL DEFAULT '0',
`label` VARCHAR(16) NOT NULL,
`shard` VARCHAR(86) NOT NULL,
PRIMARY KEY (`realmnum`),
PRIMARY KEY (`usernum`, `serial`, `label`),
KEY `IX_USERNUM` (`usernum`),
UNIQUE KEY `UNIQ_USERNUM_SERIALNUM_REALM` (`usernum`, `serialnum`, `realm`),
CONSTRAINT `User_Realms_ibfk_1` FOREIGN KEY (`usernum`) REFERENCES `Users` (`usernum`) ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=latin1 MAX_ROWS=4294967295 AVG_ROW_LENGTH=100 COMMENT='User shard values for the different realms.';

12 changes: 7 additions & 5 deletions src/providers/cryptography/cryptography.h
Original file line number Diff line number Diff line change
Expand Up @@ -31,19 +31,20 @@

// The STACIE number constants for clamping hash rounds between 8 and 16,777,216, which represents the number of possible
// values for an unsigned 24 bit integer, if you include 0. In other words 0 to 16,777,215 equals 16,777,216.
#define STACIE_ROUNDS_MIN 8
#define STACIE_ROUNDS_MAX 16777216
#define STACIE_KEY_ROUNDS_MIN 8
#define STACIE_KEY_ROUNDS_MAX 16777216

// The STACIE token derivation stage uses a fixed number of hash rounds, and that number is dictated by this parameter.
#define STACIE_ROUNDS_TOKENS 8
#define STACIE_TOKEN_ROUNDS 8

// This STACIE implementation will always use salt and nonce values which are 128 bytes in length.
#define STACIE_SALT_LENGTH 128
#define STACIE_NONCE_LENGTH 128

// This STACIE implementation uses SHA-2/512 resulting in keys and tokens of 64 bytes in length.
// This STACIE implementation uses SHA-2/512 resulting in key, token, and shard lengths of 64 bytes.
#define STACIE_KEY_LENGTH 64
#define STACIE_TOKEN_LENGTH 64
#define STACIE_SHARD_LENDTH 64

// This STACIE implementation only supports realm encryption of buffers up to 16,777,215 bytews in length.
#define STACIE_ENCRYPT_MIN 1
Expand Down Expand Up @@ -215,13 +216,14 @@ stringer_t * stacie_hashed_key_derive(stringer_t *base, uint32_t rounds, string
stringer_t * stacie_hashed_token_derive(stringer_t *base, stringer_t *username, stringer_t *salt, stringer_t *nonce);
stringer_t * stacie_nonce_create(void);
stringer_t * stacie_realm_cipher_key(stringer_t *realm_key);
stringer_t * stacie_realm_decrypt(stringer_t *vector_key, stringer_t *tag_key, stringer_t *cipher_key, stringer_t *ciphertext);
stringer_t * stacie_realm_decrypt(stringer_t *vector_key, stringer_t *tag_key, stringer_t *cipher_key, stringer_t *buffer);
stringer_t * stacie_realm_encrypt(uint16_t serial, stringer_t *vector_key, stringer_t *tag_key, stringer_t *cipher_key, stringer_t *buffer);
stringer_t * stacie_realm_key_derive(stringer_t *master_key, stringer_t *realm, stringer_t *shard);
stringer_t * stacie_realm_tag_key(stringer_t *realm_key);
stringer_t * stacie_realm_vector_key(stringer_t *realm_key);
uint32_t stacie_rounds_calculate(stringer_t *password, uint32_t bonus);
stringer_t * stacie_salt_create(void);
stringer_t * stacie_shard_create(void);

/// symmetric.c
stringer_t * symmetric_decrypt(cipher_t *cipher, stringer_t *vector, stringer_t *key, stringer_t *input);
Expand Down
39 changes: 32 additions & 7 deletions src/providers/cryptography/stacie.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,28 @@

#include "magma.h"

/**
* @brief Generates a random shard of precisely 64 bytes, suitable for use with a STACIE realm.
*
* @note The master key is combined with the realm serial number, label and a random shard value to create the realm key.
*
* @return A managed string holding the freshly generated shard in binary form. The result must be freed by the caller.
*
*/
stringer_t * stacie_shard_create(void) {

stringer_t *result = NULL;

// We call cleanup on the result pointer just in case the allocation succeeds but the random write operation fails.
if (!(result = st_alloc(STACIE_SHARD_LENDTH)) || rand_write(result) != STACIE_SHARD_LENDTH) {
log_pedantic("Failed to create a random shard value.");
st_cleanup(result);
return NULL;
}

return result;
}

/**
* @brief Generates a random salt of precisely 128 bytes, suitable for use with STACIE authentication scheme.
*
Expand Down Expand Up @@ -112,7 +134,7 @@ uint32_t stacie_rounds_calculate(stringer_t *password, uint32_t bonus) {
// variation of the clamp function is used to avoid being tricked into an overflow situation. Magma should never pass
// in an illegal value, but we protect against overflows just in case somebody decides to copy this code without
// realizing they should be checking their values higher up the stack.
return (uint32_t)uint64_clamp(STACIE_ROUNDS_MIN, STACIE_ROUNDS_MAX, (dynamic + bonus));
return (uint32_t)uint64_clamp(STACIE_KEY_ROUNDS_MIN, STACIE_KEY_ROUNDS_MAX, (dynamic + bonus));
}

/**
Expand Down Expand Up @@ -143,7 +165,7 @@ stringer_t * stacie_entropy_seed_derive(uint32_t rounds, stringer_t *password, s
const EVP_MD *digest = EVP_sha512_d();

// Sanity check the rounds value.
if (rounds < STACIE_ROUNDS_MIN || rounds > STACIE_ROUNDS_MAX) {
if (rounds < STACIE_KEY_ROUNDS_MIN || rounds > STACIE_KEY_ROUNDS_MAX) {
log_error("An invalid value for rounds was passed to the STACIE seed derivation function. { rounds = %u }", rounds);
return NULL;
}
Expand Down Expand Up @@ -247,7 +269,7 @@ stringer_t * stacie_hashed_key_derive(stringer_t *base, uint32_t rounds, stringe
const EVP_MD *digest = EVP_sha512_d();

// Sanity check the rounds value.
if (rounds < STACIE_ROUNDS_MIN || rounds > STACIE_ROUNDS_MAX) {
if (rounds < STACIE_KEY_ROUNDS_MIN || rounds > STACIE_KEY_ROUNDS_MAX) {
log_error("An invalid value for rounds was passed to The STACIE key derivation function. { rounds = %u }", rounds);
return NULL;
}
Expand Down Expand Up @@ -422,7 +444,7 @@ stringer_t * stacie_hashed_token_derive(stringer_t *base, stringer_t *username,
// Initialize the context. We only need to do this once.
EVP_MD_CTX_init_d(&ctx);

for (uint32_t count = 0; count < STACIE_ROUNDS_TOKENS; count++) {
for (uint32_t count = 0; count < STACIE_TOKEN_ROUNDS; count++) {

// Store the counter as a big endian number.
count_data = htobe32(count);
Expand Down Expand Up @@ -501,16 +523,19 @@ stringer_t * stacie_realm_key_derive(stringer_t *master_key, stringer_t *realm,
log_error("The STACIE realm key derivation failed because the hash function wasn't available.");
return NULL;
}

// What's the point of going any further if the master key is empty?
else if (st_empty_out(master_key, &key_data, &key_len) || key_len != 64) {
else if (st_empty_out(master_key, &key_data, &key_len) || key_len != STACIE_KEY_LENGTH) {
log_error("The STACIE realm key derivation failed because the master key was empty.");
return NULL;
}
// This implementation requires the base value to be 64 bytes in length,

// This implementation requires the realm label to be less than 16
else if (st_empty_out(realm, &realm_data, &realm_len)) {
log_error("The STACIE realm key derivation failed because the name value was empty.");
log_error("The STACIE realm key derivation failed because the realm label was empty.");
return NULL;
}

// And the shard value, which must also be 64 bytes in length.
else if (st_empty_out(shard, &shard_data, &shard_len) || shard_len != 64) {
log_error("The STACIE realm key derivation failed because the shard value was empty.");
Expand Down
8 changes: 5 additions & 3 deletions src/queries.h
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,7 @@
#define REGISTER_CHECK_USERNAME "SELECT usernum FROM Users WHERE userid = ?"
#define REGISTER_INSERT_USER "INSERT INTO Users (`userid`, `legacy`, `plan`, `quota`, `plan_expiration`) VALUES (?, ?, ?, ?, ?)"
#define REGISTER_INSERT_STACIE_USER "INSERT INTO Users (`userid`, `salt`, `auth`, `bonus`, `plan`, `quota`, `plan_expiration`) VALUES (?, ?, ?, ?, ?, ?, ?)"
#define REGISTER_INSERT_STACIE_REALMS "INSERT INTO User_Realms (`usernum`, `serial`, `label`, `shard`) VALUES (?, ?, ?, ?)"
#define REGISTER_INSERT_PROFILE "INSERT INTO Profile (`usernum`) VALUES (?)"
#define REGISTER_INSERT_FOLDERS "INSERT INTO Folders (`usernum`) VALUES (?)"
#define REGISTER_INSERT_FOLDER_NAME "INSERT INTO Folders (`usernum`, `foldername`) VALUES (?, ?)"
Expand Down Expand Up @@ -174,7 +175,7 @@
*
*/

#define QUERIES_INIT SELECT_DOMAINS, \
#define QUERIES_INIT SELECT_DOMAINS, \
SELECT_CONFIG, \
SELECT_HOST_NUMBER, \
DELETE_OBJECT, \
Expand Down Expand Up @@ -251,6 +252,7 @@
REGISTER_CHECK_USERNAME, \
REGISTER_INSERT_USER, \
REGISTER_INSERT_STACIE_USER, \
REGISTER_INSERT_STACIE_REALMS, \
REGISTER_INSERT_PROFILE, \
REGISTER_INSERT_FOLDERS, \
REGISTER_INSERT_FOLDER_NAME, \
Expand All @@ -277,7 +279,7 @@
META_FETCH_STORAGE_KEYS, \
META_INSERT_STORAGE_KEYS

#define STMTS_INIT **select_domains, \
#define STMTS_INIT **select_domains, \
**select_config, \
**select_host_number, \
**delete_object, \
Expand Down Expand Up @@ -354,6 +356,7 @@
**register_check_username, \
**register_insert_user, \
**register_insert_stacie_user, \
**register_insert_stacie_realms, \
**register_insert_profile, \
**register_insert_folders, \
**register_insert_folder_name, \
Expand All @@ -380,7 +383,6 @@
**meta_fetch_storage_keys, \
**meta_insert_storage_keys


extern chr_t *queries[];
struct { MYSQL_STMT STMTS_INIT; } stmts __attribute__ ((common));

Expand Down
Loading

0 comments on commit e552a21

Please sign in to comment.