Botan 3.13.0
Crypto and TLS for C&
pwdhash.cpp
Go to the documentation of this file.
1/*
2* (C) 2018 Ribose Inc
3*
4* Botan is released under the Simplified BSD License (see license.txt)
5*/
6
7#include <botan/pwdhash.h>
8
9#include <botan/assert.h>
10#include <botan/exceptn.h>
11#include <botan/internal/scan_name.h>
12
13#if defined(BOTAN_HAS_PBKDF2)
14 #include <botan/pbkdf2.h>
15#endif
16
17#if defined(BOTAN_HAS_PGP_S2K)
18 #include <botan/pgp_s2k.h>
19#endif
20
21#if defined(BOTAN_HAS_SCRYPT)
22 #include <botan/scrypt.h>
23#endif
24
25#if defined(BOTAN_HAS_ARGON2)
26 #include <botan/argon2.h>
27#endif
28
29#if defined(BOTAN_HAS_PBKDF_BCRYPT)
30 #include <botan/bcrypt_pbkdf.h>
31#endif
32
33#if defined(BOTAN_HAS_PKCS12_KDF)
34 #include <botan/internal/pkcs12_kdf.h>
35#endif
36
37namespace Botan {
38
39void PasswordHash::derive_key(uint8_t out[],
40 size_t out_len,
41 const char* password,
42 size_t password_len,
43 const uint8_t salt[],
44 size_t salt_len,
45 const uint8_t ad[],
46 size_t ad_len,
47 const uint8_t key[],
48 size_t key_len) const {
49 BOTAN_UNUSED(ad, key);
50
51 if(ad_len == 0 && key_len == 0) {
52 return this->derive_key(out, out_len, password, password_len, salt, salt_len);
53 } else {
54 throw Not_Implemented("PasswordHash " + this->to_string() + " does not support AD or key");
55 }
56}
57
58std::unique_ptr<PasswordHashFamily> PasswordHashFamily::create(std::string_view algo_spec, std::string_view provider) {
59 const SCAN_Name req(algo_spec);
60
61#if defined(BOTAN_HAS_PBKDF2)
62 if(req.algo_name() == "PBKDF2") {
63 if(provider.empty() || provider == "base") {
64 if(auto mac = MessageAuthenticationCode::create("HMAC(" + req.arg(0) + ")")) {
65 return std::make_unique<PBKDF2_Family>(std::move(mac));
66 }
67
68 if(auto mac = MessageAuthenticationCode::create(req.arg(0))) {
69 return std::make_unique<PBKDF2_Family>(std::move(mac));
70 }
71 }
72
73 return nullptr;
74 }
75#endif
76
77#if defined(BOTAN_HAS_SCRYPT)
78 if(req.algo_name() == "Scrypt") {
79 return std::make_unique<Scrypt_Family>();
80 }
81#endif
82
83#if defined(BOTAN_HAS_ARGON2)
84 if(req.algo_name() == "Argon2d") {
85 return std::make_unique<Argon2_Family>(static_cast<uint8_t>(0));
86 } else if(req.algo_name() == "Argon2i") {
87 return std::make_unique<Argon2_Family>(static_cast<uint8_t>(1));
88 } else if(req.algo_name() == "Argon2id") {
89 return std::make_unique<Argon2_Family>(static_cast<uint8_t>(2));
90 }
91#endif
92
93#if defined(BOTAN_HAS_PBKDF_BCRYPT)
94 if(req.algo_name() == "Bcrypt-PBKDF") {
95 return std::make_unique<Bcrypt_PBKDF_Family>();
96 }
97#endif
98
99#if defined(BOTAN_HAS_PGP_S2K)
100 if(req.algo_name() == "OpenPGP-S2K" && req.arg_count() == 1) {
101 if(auto hash = HashFunction::create(req.arg(0))) {
102 return std::make_unique<RFC4880_S2K_Family>(std::move(hash));
103 }
104 }
105#endif
106
107#if defined(BOTAN_HAS_PKCS12_KDF)
108 if(req.algo_name() == "PKCS12-KDF" && req.arg_count() == 2) {
109 if(auto hash = HashFunction::create(req.arg(0))) {
110 const auto id_param = req.arg_as_integer(1);
111 return std::make_unique<PKCS12_KDF_Family>(std::move(hash), id_param);
112 }
113 }
114#endif
115
116 BOTAN_UNUSED(req);
117 BOTAN_UNUSED(provider);
118
119 return nullptr;
120}
121
122//static
123std::unique_ptr<PasswordHashFamily> PasswordHashFamily::create_or_throw(std::string_view algo,
124 std::string_view provider) {
125 if(auto pbkdf = PasswordHashFamily::create(algo, provider)) {
126 return pbkdf;
127 }
128 throw Lookup_Error("PasswordHashFamily", algo, provider);
129}
130
131std::vector<std::string> PasswordHashFamily::providers(std::string_view algo_spec) {
133}
134
135} // namespace Botan
#define BOTAN_UNUSED
Definition assert.h:144
static std::unique_ptr< HashFunction > create(std::string_view algo_spec, std::string_view provider="")
Definition hash.cpp:111
static std::unique_ptr< MessageAuthenticationCode > create(std::string_view algo_spec, std::string_view provider="")
Definition mac.cpp:50
static std::unique_ptr< PasswordHashFamily > create_or_throw(std::string_view algo_spec, std::string_view provider="")
Definition pwdhash.cpp:123
static std::vector< std::string > providers(std::string_view algo_spec)
Definition pwdhash.cpp:131
static std::unique_ptr< PasswordHashFamily > create(std::string_view algo_spec, std::string_view provider="")
Definition pwdhash.cpp:58
virtual void derive_key(uint8_t out[], size_t out_len, const char *password, size_t password_len, const uint8_t salt[], size_t salt_len) const =0
virtual std::string to_string() const =0
std::string arg(size_t i) const
size_t arg_count() const
Definition scan_name.h:43
const std::string & algo_name() const
Definition scan_name.h:38
size_t arg_as_integer(size_t i, size_t def_value) const
std::vector< std::string > probe_providers_of(std::string_view algo_spec, const std::vector< std::string > &possible={"base"})
Definition scan_name.h:99