1 // This may look like C code, but it's really -*- C++ -*-
2 /*
3  * Copyright (C) 2011 Emweb bv, Herent, Belgium.
4  *
5  * See the LICENSE file for terms of use.
6  */
7 #ifndef WT_AUTH_HASH_FUNCTION
8 #define WT_AUTH_HASH_FUNCTION
9 
10 #include <string>
11 #include <Wt/WDllDefs.h>
12 
13 namespace Wt {
14   namespace Auth {
15 
16 /*! \class HashFunction Wt/Auth/HashFunction.h
17  *  \brief An abstract cryptographic hash function interface.
18  *
19  * A cryptographic hash function computes a hash value from a message,
20  * for which it is hard to guess another message that generates the
21  * same hash.
22  *
23  * These hash functions are intended for short messages, typically
24  * passwords or random tokens, and thus not suitable for computing the
25  * hash value of a large document.
26  *
27  * When used for passwords, to avoid dictionary attacks, the hash
28  * functions accept also a random salt which is hashed together with
29  * the password. Not all hash functions are adequate for passwords
30  * hashes.
31  *
32  * \ingroup auth
33  */
34 class WT_API HashFunction
35 {
36 public:
37   /*! \brief Destructor.
38    */
39   virtual ~HashFunction();
40 
41   /*! \brief Returns the name for this hash function.
42    *
43    * This should return a (short) name that uniquely identifies this
44    * hash function.
45    */
46   virtual std::string name() const = 0;
47 
48   /*! \brief Computes the hash of a message + salt.
49    *
50    * The message is usually an ASCII or UTF-8 string.
51    *
52    * The \p salt and the computed hash are encoded in printable
53    * characters. This is usually ASCII-encoded \if cpp (as for the UNIX crypt()
54    * functions) \endif or could be Base64-encoded.
55    */
56   virtual std::string compute(const std::string& msg, const std::string& salt)
57     const = 0;
58 
59   /*! \brief Verifies a message with the salted hash
60    *
61    * The base implementation will recompute the hash of the message with
62    * the given salt, and compare it to the \p hash.
63    *
64    * Some methods however store the salt and additional settings in
65    * the \p hash, and this information is thus needed to verify the message
66    * hash.
67    */
68   virtual bool verify(const std::string& msg,
69 		      const std::string& salt,
70 		      const std::string& hash) const;
71 };
72 
73 /*! \class MD5HashFunction Wt/Auth/HashFunction.h
74  *  \brief A cryptograhpic hash function implemented using MD5.
75  *
76  * This hash function is useful for creating token hashes, but
77  * should not be used for password hashes.
78  *
79  * \ingroup auth
80  */
81 class WT_API MD5HashFunction : public HashFunction
82 {
83 public:
84   /*! \brief Returns the name for this hash function.
85    *
86    * Returns <tt>"MD5"</tt>.
87    */
88   virtual std::string name() const override;
89 
90   virtual std::string compute(const std::string& msg,
91 			      const std::string& salt) const override;
92 };
93 
94 #ifndef WT_TARGET_JAVA
95 /*! \class SHA1HashFunction Wt/Auth/HashFunction.h
96  *  \brief A cryptographic hash function implemented using SHA1.
97  *
98  * This hash function is only available if %Wt was compiled with
99  * OpenSSL support.
100  *
101  * This hash function is useful for creating token hashes, but
102  * should not be used for password hashes.
103  *
104  * \ingroup auth
105  */
106 class WT_API SHA1HashFunction final : public HashFunction
107 {
108 public:
109   /*! \brief Returns the name for this hash function.
110    *
111    * Returns <tt>"SHA1"</tt>.
112    */
113   virtual std::string name() const override;
114 
115   virtual std::string compute(const std::string& msg,
116 			      const std::string& salt) const override;
117 };
118 #endif
119 
120 /*! \class BCryptHashFunction Wt/Auth/HashFunction.h
121  *  \brief An cryptographic hash function that implements bcrypt.
122  *
123  * This hashing function is intended for password hashes. In addition
124  * to be collision-resistant, the bcrypt algorithm has a parameter
125  * which makes the computation more computationally intensive. In this
126  * way, a dictionary-based attack on a compromised hash is also less
127  * feasible.
128  *
129  * \ingroup auth
130  */
131 class WT_API BCryptHashFunction final : public HashFunction
132 {
133 public:
134   /*! \brief Constructor.
135    *
136    * The \p count parameter controls the number of iterations, and
137    * thus the computational complexity. With a value of 0, a small
138    * default is chosen. The computational complexity increases
139    * exponentionally with increasing values of \p count. The parameter
140    * only affects new hashes computed with compute(), and its value is
141    * stored in the computed hash.
142    *
143    * The value of \p count needs to be 0, or in the range 4-31.
144    */
145   BCryptHashFunction(int count = 0);
146 
147   /*! \brief Returns the name for this hash function.
148    *
149    * Returns <tt>"bcrypt"</tt>.
150    */
151   virtual std::string name() const override;
152 
153   virtual std::string compute(const std::string& msg,
154 			      const std::string& salt) const override;
155 
156   virtual bool verify(const std::string& msg,
157 		      const std::string& salt,
158 		      const std::string& hash) const override;
159 
160 private:
161   int count_;
162 };
163 
164   }
165 }
166 
167 #endif // WT_AUTH_HASH_FUNCTION
168