Allow specifying algorithm for pwhash

This commit is contained in:
Nicolas goy 2020-04-17 14:31:35 +02:00
parent 5f95ee314f
commit 00f895b488
4 changed files with 53 additions and 7 deletions

View File

@ -287,7 +287,7 @@ static ErlNifFunc nif_funcs[] = {
{"crypto_verify_32", 2, enacl_crypto_verify_32},
{"sodium_memzero", 1, enif_sodium_memzero},
erl_nif_dirty_job_cpu_bound_macro("crypto_pwhash", 4, enacl_crypto_pwhash),
erl_nif_dirty_job_cpu_bound_macro("crypto_pwhash", 5, enacl_crypto_pwhash),
erl_nif_dirty_job_cpu_bound_macro("crypto_pwhash_str", 3,
enacl_crypto_pwhash_str),
erl_nif_dirty_job_cpu_bound_macro("crypto_pwhash_str_verify", 2,

View File

@ -57,16 +57,44 @@ static size_t enacl_pwhash_memlimit(ErlNifEnv *env, ERL_NIF_TERM arg) {
return 0;
}
static int enacl_pwhash_alg(ErlNifEnv *env, ERL_NIF_TERM arg) {
ERL_NIF_TERM a;
int r;
if (enif_is_atom(env, arg)) {
a = enif_make_atom(env, "default");
if (enif_is_identical(a, arg)) {
return crypto_pwhash_ALG_DEFAULT;
}
a = enif_make_atom(env, "argon2i13");
if (enif_is_identical(a, arg)) {
return crypto_pwhash_ALG_ARGON2I13;
}
a = enif_make_atom(env, "argon2id13");
if (enif_is_identical(a, arg)) {
return crypto_pwhash_ALG_ARGON2ID13;
}
} else if (enif_get_int(env, arg, &r)) {
return r;
}
return 0;
}
ERL_NIF_TERM enacl_crypto_pwhash(ErlNifEnv *env, int argc,
ERL_NIF_TERM const argv[]) {
ErlNifBinary h, p, s;
size_t o, m;
int alg;
// Validate the arguments
if ((argc != 4) || (!enif_inspect_iolist_as_binary(env, argv[0], &p)) ||
if ((argc != 5) || (!enif_inspect_iolist_as_binary(env, argv[0], &p)) ||
(!enif_inspect_binary(env, argv[1], &s)) ||
!(o = enacl_pwhash_opslimit(env, argv[2])) ||
!(m = enacl_pwhash_memlimit(env, argv[3]))) {
!(m = enacl_pwhash_memlimit(env, argv[3])) ||
!(alg = enacl_pwhash_alg(env, argv[4]))) {
return enif_make_badarg(env);
}
@ -87,7 +115,7 @@ ERL_NIF_TERM enacl_crypto_pwhash(ErlNifEnv *env, int argc,
}
if (crypto_pwhash(h.data, h.size, (char *)p.data, p.size, s.data, o, m,
crypto_pwhash_ALG_DEFAULT) != 0) {
alg) != 0) {
/* out of memory */
enif_release_binary(&h);
return enacl_internal_error(env);

View File

@ -116,6 +116,8 @@
shorthash_size/0,
shorthash/2,
pwhash/5,
pwhash/4,
pwhash_str/3,
@ -395,6 +397,7 @@ generichash_final(State) ->
enacl_nif:crypto_generichash_final(State).
-type pwhash_limit() :: interactive | moderate | sensitive | pos_integer().
-type pwhash_alg() :: default | argon2i13 | argon2id13 | pos_integer().
%% @doc pwhash/2 hash a password
%%
%% This function generates a fixed size salted hash of a user defined password.
@ -416,7 +419,22 @@ pwhash(Password, Salt) ->
Ops :: pwhash_limit(),
Mem :: pwhash_limit().
pwhash(Password, Salt, Ops, Mem) ->
enacl_nif:crypto_pwhash(Password, Salt, Ops, Mem).
enacl_nif:crypto_pwhash(Password, Salt, Ops, Mem, default).
%% @doc pwhash/5 hash a password
%%
%% This function generates a fixed size salted hash of a user defined password given Ops and Mem
%% limits.
%% @end
-spec pwhash(Password, Salt, Ops, Mem, Alg) -> binary()
when
Password :: iodata(),
Salt :: binary(),
Ops :: pwhash_limit(),
Mem :: pwhash_limit(),
Alg :: pwhash_alg().
pwhash(Password, Salt, Ops, Mem, Alg) ->
enacl_nif:crypto_pwhash(Password, Salt, Ops, Mem, Alg).
%% @doc pwhash_str/1 generates a ASCII encoded hash of a password
%%

View File

@ -147,7 +147,7 @@
%% Password Hashing - Argon2 Algorithm
-export([
crypto_pwhash/4,
crypto_pwhash/5,
crypto_pwhash_str/3,
crypto_pwhash_str_verify/2
]).
@ -238,7 +238,7 @@ crypto_secretstream_xchacha20poly1305_init_pull(_Header, _Key) -> erlang:nif_err
crypto_secretstream_xchacha20poly1305_pull(_Ref, _CipherText, _AD) -> erlang:nif_error(nif_not_loaded).
crypto_secretstream_xchacha20poly1305_rekey(_Ref) -> erlang:nif_error(nif_not_loaded).
crypto_pwhash(_Password, _Salt, _Ops, _Mem) -> erlang:nif_error(nif_not_loaded).
crypto_pwhash(_Password, _Salt, _Ops, _Mem, _Alg) -> erlang:nif_error(nif_not_loaded).
crypto_pwhash_str(_Password, _Ops, _Mem) -> erlang:nif_error(nif_not_loaded).
crypto_pwhash_str_verify(_HashedPassword, _Password) -> erlang:nif_error(nif_not_loaded).