Botan  2.11.0
Crypto and TLS for C++11
Public Member Functions | Static Public Member Functions | List of all members
Botan::Scrypt_Family Class Referencefinal

#include <scrypt.h>

Inheritance diagram for Botan::Scrypt_Family:
Botan::PasswordHashFamily

Public Member Functions

std::unique_ptr< PasswordHashdefault_params () const override
 
std::unique_ptr< PasswordHashfrom_iterations (size_t iter) const override
 
std::unique_ptr< PasswordHashfrom_params (size_t N, size_t r, size_t p) const override
 
std::string name () const override
 
std::unique_ptr< PasswordHashtune (size_t output_length, std::chrono::milliseconds msec, size_t max_memory) const override
 

Static Public Member Functions

static std::unique_ptr< PasswordHashFamilycreate (const std::string &algo_spec, const std::string &provider="")
 
static std::unique_ptr< PasswordHashFamilycreate_or_throw (const std::string &algo_spec, const std::string &provider="")
 
static std::vector< std::string > providers (const std::string &algo_spec)
 

Detailed Description

Definition at line 51 of file scrypt.h.

Member Function Documentation

◆ create()

std::unique_ptr< PasswordHashFamily > Botan::PasswordHashFamily::create ( const std::string &  algo_spec,
const std::string &  provider = "" 
)
staticinherited

Create an instance based on a name If provider is empty then best available is chosen.

Parameters
algo_specalgorithm name
providerprovider implementation to choose
Returns
a null pointer if the algo/provider combination cannot be found

Definition at line 33 of file pwdhash.cpp.

References Botan::SCAN_Name::algo_name(), Botan::SCAN_Name::arg(), Botan::SCAN_Name::arg_count(), BOTAN_UNUSED, Botan::HashFunction::create(), Botan::MessageAuthenticationCode::create(), and hash.

Referenced by botan_pwdhash(), botan_pwdhash_timed(), and Botan::PasswordHashFamily::create_or_throw().

35  {
36  const SCAN_Name req(algo_spec);
37 
38 #if defined(BOTAN_HAS_PBKDF2)
39  if(req.algo_name() == "PBKDF2")
40  {
41  // TODO OpenSSL
42 
43  if(provider.empty() || provider == "base")
44  {
45  if(auto mac = MessageAuthenticationCode::create(req.arg(0)))
46  return std::unique_ptr<PasswordHashFamily>(new PBKDF2_Family(mac.release()));
47 
48  if(auto mac = MessageAuthenticationCode::create("HMAC(" + req.arg(0) + ")"))
49  return std::unique_ptr<PasswordHashFamily>(new PBKDF2_Family(mac.release()));
50  }
51 
52  return nullptr;
53  }
54 #endif
55 
56 #if defined(BOTAN_HAS_SCRYPT)
57  if(req.algo_name() == "Scrypt")
58  {
59  return std::unique_ptr<PasswordHashFamily>(new Scrypt_Family);
60  }
61 #endif
62 
63 #if defined(BOTAN_HAS_ARGON2)
64  if(req.algo_name() == "Argon2d")
65  {
66  return std::unique_ptr<PasswordHashFamily>(new Argon2_Family(0));
67  }
68  else if(req.algo_name() == "Argon2i")
69  {
70  return std::unique_ptr<PasswordHashFamily>(new Argon2_Family(1));
71  }
72  else if(req.algo_name() == "Argon2id")
73  {
74  return std::unique_ptr<PasswordHashFamily>(new Argon2_Family(2));
75  }
76 #endif
77 
78 #if defined(BOTAN_HAS_PBKDF_BCRYPT)
79  if(req.algo_name() == "Bcrypt-PBKDF")
80  {
81  return std::unique_ptr<PasswordHashFamily>(new Bcrypt_PBKDF_Family);
82  }
83 #endif
84 
85 #if defined(BOTAN_HAS_PGP_S2K)
86  if(req.algo_name() == "OpenPGP-S2K" && req.arg_count() == 1)
87  {
88  if(auto hash = HashFunction::create(req.arg(0)))
89  {
90  return std::unique_ptr<PasswordHashFamily>(new RFC4880_S2K_Family(hash.release()));
91  }
92  }
93 #endif
94 
95  BOTAN_UNUSED(req);
96  BOTAN_UNUSED(provider);
97 
98  return nullptr;
99  }
static std::unique_ptr< MessageAuthenticationCode > create(const std::string &algo_spec, const std::string &provider="")
Definition: mac.cpp:46
static std::unique_ptr< HashFunction > create(const std::string &algo_spec, const std::string &provider="")
Definition: hash.cpp:110
#define BOTAN_UNUSED(...)
Definition: assert.h:142
MechanismType hash

◆ create_or_throw()

std::unique_ptr< PasswordHashFamily > Botan::PasswordHashFamily::create_or_throw ( const std::string &  algo_spec,
const std::string &  provider = "" 
)
staticinherited

Create an instance based on a name, or throw if the algo/provider combination cannot be found. If provider is empty then best available is chosen.

Definition at line 103 of file pwdhash.cpp.

References Botan::PasswordHashFamily::create().

105  {
106  if(auto pbkdf = PasswordHashFamily::create(algo, provider))
107  {
108  return pbkdf;
109  }
110  throw Lookup_Error("PasswordHashFamily", algo, provider);
111  }
static std::unique_ptr< PasswordHashFamily > create(const std::string &algo_spec, const std::string &provider="")
Definition: pwdhash.cpp:33

◆ default_params()

std::unique_ptr< PasswordHash > Botan::Scrypt_Family::default_params ( ) const
overridevirtual

Return some default parameter set for this PBKDF that should be good enough for most users. The value returned may change over time as processing power and attacks improve.

Implements Botan::PasswordHashFamily.

Definition at line 24 of file scrypt.cpp.

Referenced by tune().

25  {
26  return std::unique_ptr<PasswordHash>(new Scrypt(32768, 8, 1));
27  }

◆ from_iterations()

std::unique_ptr< PasswordHash > Botan::Scrypt_Family::from_iterations ( size_t  iterations) const
overridevirtual

Return a parameter chosen based on a rough approximation with the specified iteration count. The exact value this returns for a particular algorithm may change from over time. Think of it as an alternative to tune, where time is expressed in terms of PBKDF2 iterations rather than milliseconds.

Implements Botan::PasswordHashFamily.

Definition at line 110 of file scrypt.cpp.

111  {
112  const size_t r = 8;
113  const size_t p = 1;
114 
115  size_t N = 8192;
116 
117  if(iter > 50000)
118  N = 16384;
119  if(iter > 100000)
120  N = 32768;
121  if(iter > 150000)
122  N = 65536;
123 
124  return std::unique_ptr<PasswordHash>(new Scrypt(N, r, p));
125  }

◆ from_params()

std::unique_ptr< PasswordHash > Botan::Scrypt_Family::from_params ( size_t  i1,
size_t  i2,
size_t  i3 
) const
overridevirtual

Create a password hash using some scheme specific format. Eg PBKDF2 and PGP-S2K set iterations in i1 Scrypt uses N,r,p in i{1-3} Bcrypt-PBKDF just has iterations Argon2{i,d,id} would use iterations, memory, parallelism for i{1-3}, and Argon2 type is part of the family.

Values not needed should be set to 0

Implements Botan::PasswordHashFamily.

Definition at line 105 of file scrypt.cpp.

106  {
107  return std::unique_ptr<PasswordHash>(new Scrypt(N, r, p));
108  }

◆ name()

std::string Botan::Scrypt_Family::name ( ) const
overridevirtual
Returns
name of this PasswordHash

Implements Botan::PasswordHashFamily.

Definition at line 19 of file scrypt.cpp.

20  {
21  return "Scrypt";
22  }

◆ providers()

std::vector< std::string > Botan::PasswordHashFamily::providers ( const std::string &  algo_spec)
staticinherited
Returns
list of available providers for this algorithm, empty if not available

Definition at line 113 of file pwdhash.cpp.

114  {
115  return probe_providers_of<PasswordHashFamily>(algo_spec, { "base", "openssl" });
116  }

◆ tune()

std::unique_ptr< PasswordHash > Botan::Scrypt_Family::tune ( size_t  output_length,
std::chrono::milliseconds  msec,
size_t  max_memory_usage_mb 
) const
overridevirtual

Return a new parameter set tuned for this machine

Parameters
output_lengthhow long the output length will be
msecthe desired execution time in milliseconds
max_memory_usage_mbsome password hash functions can use a tunable amount of memory, in this case max_memory_usage limits the amount of RAM the returned parameters will require, in mebibytes (2**20 bytes). It may require some small amount above the request. Set to zero to place no limit at all.

Implements Botan::PasswordHashFamily.

Definition at line 29 of file scrypt.cpp.

References BOTAN_UNUSED, default_params(), Botan::Timer::events(), Botan::Timer::run_until_elapsed(), Botan::scrypt(), Botan::scrypt_memory_usage(), and Botan::Timer::value().

32  {
33  BOTAN_UNUSED(output_length);
34 
35  /*
36  * Some rough relations between scrypt parameters and runtime.
37  * Denote here by stime(N,r,p) the msec it takes to run scrypt.
38  *
39  * Emperically for smaller sizes:
40  * stime(N,8*r,p) / stime(N,r,p) is ~ 6-7
41  * stime(N,r,8*p) / stime(N,r,8*p) is ~ 7
42  * stime(2*N,r,p) / stime(N,r,p) is ~ 2
43  *
44  * Compute stime(8192,1,1) as baseline and extrapolate
45  */
46 
47  const size_t max_memory_usage = max_memory_usage_mb * 1024 * 1024;
48  // Starting parameters
49  size_t N = 8192;
50  size_t r = 1;
51  size_t p = 1;
52 
53  Timer timer("Scrypt");
54  const auto tune_time = BOTAN_PBKDF_TUNING_TIME;
55 
56  timer.run_until_elapsed(tune_time, [&]() {
57  uint8_t output[32] = { 0 };
58  scrypt(output, sizeof(output), "test", 4, nullptr, 0, N, r, p);
59  });
60 
61  // No timer events seems strange, perhaps something is wrong - give
62  // up on this and just return default params
63  if(timer.events() == 0)
64  return default_params();
65 
66  // nsec per eval of scrypt with initial params
67  const uint64_t measured_time = timer.value() / timer.events();
68 
69  const uint64_t target_nsec = msec.count() * static_cast<uint64_t>(1000000);
70 
71  uint64_t est_nsec = measured_time;
72 
73  // First move increase r by 8x if possible
74 
75  if(max_memory_usage == 0 || scrypt_memory_usage(N, r, p)*8 < max_memory_usage)
76  {
77  if(target_nsec / est_nsec >= 5)
78  {
79  r *= 8;
80  est_nsec *= 5;
81  }
82  }
83 
84  // Now double N as many times as we can
85 
86  while(max_memory_usage == 0 || scrypt_memory_usage(N, r, p)*2 < max_memory_usage)
87  {
88  if(target_nsec / est_nsec >= 2)
89  {
90  N *= 2;
91  est_nsec *= 2;
92  }
93  else
94  break;
95  }
96 
97  // If we have extra runtime budget, increment p
98 
99  if(target_nsec / est_nsec > 2)
100  p *= std::min<size_t>(1024, static_cast<size_t>(target_nsec / est_nsec));
101 
102  return std::unique_ptr<PasswordHash>(new Scrypt(N, r, p));
103  }
std::unique_ptr< PasswordHash > default_params() const override
Definition: scrypt.cpp:24
size_t scrypt_memory_usage(size_t N, size_t r, size_t p)
Definition: scrypt.h:118
#define BOTAN_UNUSED(...)
Definition: assert.h:142
void scrypt(uint8_t output[], size_t output_len, const char *password, size_t password_len, const uint8_t salt[], size_t salt_len, size_t N, size_t r, size_t p)
Definition: scrypt.cpp:211

The documentation for this class was generated from the following files: