8#include <botan/passhash9.h>
9#include <botan/loadstor.h>
10#include <botan/libstate.h>
11#include <botan/pbkdf2.h>
12#include <botan/b64_filt.h>
13#include <botan/pipe.h>
19const std::string MAGIC_PREFIX =
"$9$";
21const size_t WORKFACTOR_BYTES = 2;
22const size_t ALGID_BYTES = 1;
23const size_t SALT_BYTES = 12;
24const size_t PASSHASH9_PBKDF_OUTPUT_LEN = 24;
26const size_t WORK_FACTOR_SCALE = 10000;
35 return af.make_mac(
"HMAC(SHA-1)");
37 return af.make_mac(
"HMAC(SHA-256)");
39 return af.make_mac(
"CMAC(Blowfish)");
64 const size_t kdf_iterations = WORK_FACTOR_SCALE * work_factor;
69 &salt[0], salt.
size(),
78 pipe.
write(pbkdf2_output);
86 const size_t BINARY_LENGTH =
89 PASSHASH9_PBKDF_OUTPUT_LEN +
92 const size_t BASE64_LENGTH =
93 MAGIC_PREFIX.size() + (BINARY_LENGTH * 8) / 6;
95 if(hash.size() != BASE64_LENGTH)
98 for(
size_t i = 0; i != MAGIC_PREFIX.size(); ++i)
99 if(hash[i] != MAGIC_PREFIX[i])
104 pipe.
write(hash.c_str() + MAGIC_PREFIX.size());
109 if(bin.
size() != BINARY_LENGTH)
112 byte alg_id = bin[0];
114 const size_t kdf_iterations =
117 if(kdf_iterations == 0)
128 PASSHASH9_PBKDF_OUTPUT_LEN,
130 &bin[ALGID_BYTES + WORKFACTOR_BYTES], SALT_BYTES,
134 &bin[ALGID_BYTES + WORKFACTOR_BYTES + SALT_BYTES],
135 PASSHASH9_PBKDF_OUTPUT_LEN);
Algorithm_Factory & algorithm_factory() const
SecureVector< byte > bits_of() const
OctetString derive_key(size_t output_len, const std::string &passphrase, const byte salt[], size_t salt_len, size_t iterations) const
SecureVector< byte > read_all(message_id msg=DEFAULT_MESSAGE)
void write(const byte in[], size_t length)
std::string read_all_as_string(message_id=DEFAULT_MESSAGE)
virtual void randomize(byte output[], size_t length)=0
byte get_byte(size_t byte_num, T input)
T load_be(const byte in[], size_t off)
std::string to_string(u64bit n, size_t min_len)
std::invalid_argument Invalid_Argument
bool check_passhash9(const std::string &pass, const std::string &hash)
Library_State & global_state()
std::string generate_passhash9(const std::string &pass, RandomNumberGenerator &rng, u16bit work_factor, byte alg_id)
bool same_mem(const T *p1, const T *p2, size_t n)