Crypt-Sodium-XS

 view release on metacpan or  search on metacpan

inc/pwhash.xs  view on Meta::CPAN

MODULE = Crypt::Sodium::XS PACKAGE = Crypt::Sodium::XS::pwhash

void _define_constants()
  PREINIT:
  HV *stash = gv_stashpv("Crypt::Sodium::XS::pwhash", 0);

  PPCODE:
  newCONSTSUB(stash, "pwhash_BYTES_MAX", newSVuv(crypto_pwhash_BYTES_MAX));
  newCONSTSUB(stash, "pwhash_argon2i_BYTES_MAX",
              newSVuv(crypto_pwhash_argon2i_BYTES_MAX));
  newCONSTSUB(stash, "pwhash_argon2id_BYTES_MAX",
              newSVuv(crypto_pwhash_argon2id_BYTES_MAX));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_BYTES_MAX",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_BYTES_MAX));
  newCONSTSUB(stash, "pwhash_BYTES_MIN", newSVuv(crypto_pwhash_BYTES_MIN));
  newCONSTSUB(stash, "pwhash_argon2i_BYTES_MIN",
              newSVuv(crypto_pwhash_argon2i_BYTES_MIN));
  newCONSTSUB(stash, "pwhash_argon2id_BYTES_MIN",
              newSVuv(crypto_pwhash_argon2id_BYTES_MIN));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_BYTES_MIN",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_BYTES_MIN));
  newCONSTSUB(stash, "pwhash_MEMLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_MEMLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_argon2i_MEMLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_argon2i_MEMLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_argon2id_MEMLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_argon2id_MEMLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_MEMLIMIT_MAX",
              newSVuv(crypto_pwhash_MEMLIMIT_MAX));
  newCONSTSUB(stash, "pwhash_argon2i_MEMLIMIT_MAX",
              newSVuv(crypto_pwhash_argon2i_MEMLIMIT_MAX));
  newCONSTSUB(stash, "pwhash_argon2id_MEMLIMIT_MAX",
              newSVuv(crypto_pwhash_argon2id_MEMLIMIT_MAX));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_MEMLIMIT_MAX",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_MAX));
  newCONSTSUB(stash, "pwhash_MEMLIMIT_MIN",
              newSVuv(crypto_pwhash_MEMLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_argon2i_MEMLIMIT_MIN",
              newSVuv(crypto_pwhash_argon2i_MEMLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_argon2id_MEMLIMIT_MIN",
              newSVuv(crypto_pwhash_argon2id_MEMLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_MEMLIMIT_MIN",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_MEMLIMIT_MODERATE",
              newSVuv(crypto_pwhash_MEMLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_argon2i_MEMLIMIT_MODERATE",
              newSVuv(crypto_pwhash_argon2i_MEMLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_argon2id_MEMLIMIT_MODERATE",
              newSVuv(crypto_pwhash_argon2id_MEMLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_MEMLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_MEMLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_argon2i_MEMLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_argon2i_MEMLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_argon2id_MEMLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_argon2id_MEMLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_MEMLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_OPSLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_OPSLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_argon2i_OPSLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_argon2i_OPSLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_argon2id_OPSLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_argon2id_OPSLIMIT_INTERACTIVE));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_OPSLIMIT_INTERACTIVE",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_INTERACTIVE));

inc/pwhash.xs  view on Meta::CPAN

  newCONSTSUB(stash, "pwhash_OPSLIMIT_MIN",
              newSVuv(crypto_pwhash_OPSLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_argon2i_OPSLIMIT_MIN",
              newSVuv(crypto_pwhash_argon2i_OPSLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_argon2id_OPSLIMIT_MIN",
              newSVuv(crypto_pwhash_argon2id_OPSLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_OPSLIMIT_MIN",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_MIN));
  newCONSTSUB(stash, "pwhash_OPSLIMIT_MODERATE",
              newSVuv(crypto_pwhash_OPSLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_argon2i_OPSLIMIT_MODERATE",
              newSVuv(crypto_pwhash_argon2i_OPSLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_argon2id_OPSLIMIT_MODERATE",
              newSVuv(crypto_pwhash_argon2id_OPSLIMIT_MODERATE));
  newCONSTSUB(stash, "pwhash_OPSLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_OPSLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_argon2i_OPSLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_argon2i_OPSLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_argon2id_OPSLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_argon2id_OPSLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_OPSLIMIT_SENSITIVE",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_SENSITIVE));
  newCONSTSUB(stash, "pwhash_PASSWD_MAX", newSVuv(crypto_pwhash_PASSWD_MAX));
  newCONSTSUB(stash, "pwhash_argon2i_PASSWD_MAX",
              newSVuv(crypto_pwhash_argon2i_PASSWD_MAX));
  newCONSTSUB(stash, "pwhash_argon2id_PASSWD_MAX",
              newSVuv(crypto_pwhash_argon2id_PASSWD_MAX));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_PASSWD_MAX",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_PASSWD_MAX));
  newCONSTSUB(stash, "pwhash_PASSWD_MIN", newSVuv(crypto_pwhash_PASSWD_MIN));
  newCONSTSUB(stash, "pwhash_argon2i_PASSWD_MIN",
              newSVuv(crypto_pwhash_argon2i_PASSWD_MIN));
  newCONSTSUB(stash, "pwhash_argon2id_PASSWD_MIN",
              newSVuv(crypto_pwhash_argon2id_PASSWD_MIN));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_PASSWD_MIN",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_PASSWD_MIN));
  newCONSTSUB(stash, "pwhash_SALTBYTES", newSVuv(crypto_pwhash_SALTBYTES));
  newCONSTSUB(stash, "pwhash_argon2i_SALTBYTES",
              newSVuv(crypto_pwhash_argon2i_SALTBYTES));
  newCONSTSUB(stash, "pwhash_argon2id_SALTBYTES",
              newSVuv(crypto_pwhash_argon2id_SALTBYTES));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_SALTBYTES",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_SALTBYTES));
  newCONSTSUB(stash, "pwhash_STRBYTES", newSVuv(crypto_pwhash_STRBYTES));
  newCONSTSUB(stash, "pwhash_argon2i_STRBYTES",
              newSVuv(crypto_pwhash_argon2i_STRBYTES));
  newCONSTSUB(stash, "pwhash_argon2id_STRBYTES",
              newSVuv(crypto_pwhash_argon2id_STRBYTES));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_STRBYTES",
              newSVuv(crypto_pwhash_scryptsalsa208sha256_STRBYTES));
  newCONSTSUB(stash, "pwhash_STRPREFIX", newSVpvs(crypto_pwhash_STRPREFIX));
  newCONSTSUB(stash, "pwhash_argon2i_STRPREFIX",
              newSVpvs(crypto_pwhash_argon2i_STRPREFIX));
  newCONSTSUB(stash, "pwhash_argon2id_STRPREFIX",
              newSVpvs(crypto_pwhash_argon2id_STRPREFIX));
  newCONSTSUB(stash, "pwhash_scryptsalsa208sha256_STRPREFIX",
              newSVpvs(crypto_pwhash_scryptsalsa208sha256_STRPREFIX));
  newCONSTSUB(stash, "pwhash_PRIMITIVE", newSVpvs(crypto_pwhash_PRIMITIVE));

void pwhash_scryptsalsa208sha256_MEMLIMIT_MODERATE()
  PPCODE:
  croak("This primitive does not support MEMLIMIT_MODERATE");

void pwhash_scryptsalsa208sha256_OPSLIMIT_MODERATE()
  PPCODE:
  croak("This primitive does not support OPSLIMIT_MODERATE");

SV * pwhash( \
  SV * passphrase, \
  SV * salt, \
  STRLEN out_len = 0, \
  STRLEN opslimit = 0, \
  STRLEN memlimit = 0, \
  U32 flags = 0 \
)

  ALIAS:
  pwhash_argon2i = 1
  pwhash_argon2id = 2
  pwhash_scryptsalsa208sha256 = 3

  PREINIT:
  protmem *out_pm, *pw_pm = NULL;
  unsigned char *salt_buf, *pw_buf;
  STRLEN salt_len, pw_len, salt_req_len;
  int alg = 0, ret;
  U32 new_flags = g_protmem_default_flags_key;
  size_t out_min, out_max;
  size_t opslimit_def, opslimit_min, opslimit_max;
  size_t memlimit_def, memlimit_min, memlimit_max;

  CODE:
  switch(ix) {
    case 1:
      alg = crypto_pwhash_ALG_ARGON2I13;
      out_min = crypto_pwhash_argon2i_BYTES_MIN;
      out_max = crypto_pwhash_argon2i_BYTES_MAX;
      salt_req_len = crypto_pwhash_argon2i_SALTBYTES;
      opslimit_def = crypto_pwhash_argon2i_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_argon2i_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_argon2i_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_argon2i_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_argon2i_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_argon2i_MEMLIMIT_MAX;
      break;
    case 2:
      alg = crypto_pwhash_ALG_ARGON2ID13;
      out_min = crypto_pwhash_argon2id_BYTES_MIN;
      out_max = crypto_pwhash_argon2id_BYTES_MAX;
      salt_req_len = crypto_pwhash_argon2id_SALTBYTES;
      opslimit_def = crypto_pwhash_argon2id_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_argon2id_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_argon2id_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_argon2id_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_argon2id_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_argon2id_MEMLIMIT_MAX;
      break;
    case 3:
      out_min = crypto_pwhash_scryptsalsa208sha256_BYTES_MIN;
      out_max = crypto_pwhash_scryptsalsa208sha256_BYTES_MAX;
      salt_req_len = crypto_pwhash_scryptsalsa208sha256_SALTBYTES;
      opslimit_def = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE;

inc/pwhash.xs  view on Meta::CPAN

  if (sv_derived_from(passphrase, MEMVAULT_CLASS)) {
    pw_pm = protmem_get(aTHX_ passphrase, MEMVAULT_CLASS);
    pw_buf = pw_pm->pm_ptr;
    pw_len = pw_pm->size;
  }
  else
    pw_buf = (unsigned char *)SvPVbyte(passphrase, pw_len);

  Newx(out_buf, out_len + 1, unsigned char);
  if (out_buf == NULL)
    croak("pwhash_str: Failed to allocate protmem");
  out_buf[out_len] = '\0';

  if (pw_pm && protmem_grant(aTHX_ pw_pm, PROTMEM_FLAG_MPROTECT_RO) != 0) {
    Safefree(out_buf);
    croak("pwhash_str: Failed to grant passphrase protmem RO");
  }

  if (ix == 3)
    ret = crypto_pwhash_scryptsalsa208sha256_str((char *)out_buf, (char *)pw_buf,
                                                 pw_len, opslimit, memlimit);
  else
    ret = crypto_pwhash_str_alg((char *)out_buf, (char *)pw_buf, pw_len,
                                opslimit, memlimit, alg);

  /* unlike the rest of the api, no argument for actual output length. >:| */
  out_len = strlen((char *)out_buf);

  if (pw_pm && protmem_release(aTHX_ pw_pm, PROTMEM_FLAG_MPROTECT_RO) != 0) {
    Safefree(out_buf);
    croak("pwhash_str: Failed to release passphrase protmem RO");
  }

  if (ret != 0) {
    Safefree(out_buf);
    croak("pwhash_str: pwhash_str failed (out of memory?)");
  }

  RETVAL = newSV(0);
  sv_usepvn_flags(RETVAL, (char *)out_buf, out_len, SV_HAS_TRAILING_NUL);

  OUTPUT:
  RETVAL

void pwhash_str_needs_rehash(SV * str, STRLEN opslimit = 0, STRLEN memlimit = 0)

  ALIAS:
  pwhash_argon2i_str_needs_rehash = 1
  pwhash_argon2id_str_needs_rehash = 2
  pwhash_scryptsalsa208sha256_str_needs_rehash = 3

  PREINIT:
  protmem *str_pm = NULL;
  char *str_buf;
  size_t opslimit_def, opslimit_min, opslimit_max;
  size_t memlimit_def, memlimit_min, memlimit_max;
  STRLEN str_len;
  int ret;
  int (*func)(const char *, unsigned long long, size_t);

  PPCODE:
  switch(ix) {
    case 1:
      opslimit_def = crypto_pwhash_argon2i_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_argon2i_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_argon2i_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_argon2i_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_argon2i_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_argon2i_MEMLIMIT_MAX;
      func = crypto_pwhash_argon2i_str_needs_rehash;
      break;
    case 2:
      opslimit_def = crypto_pwhash_argon2id_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_argon2id_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_argon2id_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_argon2id_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_argon2id_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_argon2id_MEMLIMIT_MAX;
      func = crypto_pwhash_argon2id_str_needs_rehash;
      break;
    case 3:
      opslimit_def = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_scryptsalsa208sha256_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_MAX;
      func = crypto_pwhash_scryptsalsa208sha256_str_needs_rehash;
      break;
    default:
      opslimit_def = crypto_pwhash_OPSLIMIT_INTERACTIVE;
      opslimit_min = crypto_pwhash_OPSLIMIT_MIN;
      opslimit_max = crypto_pwhash_OPSLIMIT_MAX;
      memlimit_def = crypto_pwhash_MEMLIMIT_INTERACTIVE;
      memlimit_min = crypto_pwhash_MEMLIMIT_MIN;
      memlimit_max = crypto_pwhash_MEMLIMIT_MAX;
      func = crypto_pwhash_str_needs_rehash;
  }

  if (opslimit == 0)
    opslimit = opslimit_def;
  else {
    if (opslimit < opslimit_min || opslimit > opslimit_max)
      croak("pwhash_str_needs_rehash: Invalid opslimit %lu", opslimit);
  }
  if (memlimit == 0)
    memlimit = memlimit_def;
  else {
    if (memlimit < memlimit_min || memlimit > memlimit_max)
      croak("pwhash_str_needs_rehash: Invalid memlimit %lu", memlimit);
  }

  if (sv_derived_from(str, MEMVAULT_CLASS)) {
    str_pm = protmem_get(aTHX_ str, MEMVAULT_CLASS);
    str_buf = str_pm->pm_ptr;
    str_len = str_pm->size;
  }
  else
    str_buf = SvPVbyte(str, str_len);
  if (str_buf[str_len] != '\0')
    croak("pwhash_str_needs_rehash: Invalid hash string");



( run in 0.546 second using v1.01-cache-2.11-cpan-71847e10f99 )