Marine Library  1.0
C++ library for Linux Networking Development
encrypt_aes.hh
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2016 Zhao DAI <daidodo@gmail.com>
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or any
7  * later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program. If not, see accompanying file LICENSE.txt
16  * or <http://www.gnu.org/licenses/>.
17  */
18 
27 #ifndef DOZERG_ENCRYPTOR_AES_H_20080306
28 #define DOZERG_ENCRYPTOR_AES_H_20080306
29 
30 #include <string>
31 #include <vector>
32 #include <cstring> //memset
33 #include <openssl/aes.h>
34 #include "tools/ssl.hh" //Md5
35 
36 NS_SERVER_BEGIN
37 
44 {
45  typedef unsigned char __Char;
46  static const size_t kKeyLen = 16;
47  CEncryptorAes(const CEncryptorAes &); //disable copy and assignment
48  CEncryptorAes & operator =(const CEncryptorAes &);
49 public:
52  L128 = 128,
53  L192 = 192,
54  L256 = 256
55  };
62  : intens_(L128)
63  {}
69  CEncryptorAes(const std::string & key, EKeyIntensity intensity)
70  : key_(key)
71  , intens_(intensity)
72  {
73  updateKeys();
74  }
79  void setIntensity(EKeyIntensity intensity){
80  intens_ = intensity;
81  updateKeys();
82  }
88  void setKey(const std::string & key){
89  key_ = key;
90  updateKeys();
91  }
98  void setKeyAndIntensity(const std::string & key, EKeyIntensity intensity){
99  key_ = key;
100  intens_ = intensity;
101  updateKeys();
102  }
118  int encrypt(const std::vector<char> & input, std::vector<char> & output, size_t from = 0) const{
119  return encryptTemplate(input, output, from);
120  }
121  int encrypt(const std::vector<signed char> & input, std::vector<signed char> & output, size_t from = 0) const{
122  return encryptTemplate(input, output, from);
123  }
124  int encrypt(const std::vector<unsigned char> & input, std::vector<unsigned char> & output, size_t from = 0) const{
125  return encryptTemplate(input, output, from);
126  }
127  int encrypt(const std::string & input, std::string & output, size_t from = 0) const{
128  return encryptTemplate(input, output, from);
129  }
147  int decrypt(const std::vector<char> & input, std::vector<char> & output, size_t from = 0) const{
148  return decryptTemplate(input, output, from);
149  }
150  int decrypt(const std::vector<signed char> & input, std::vector<signed char> & output, size_t from = 0) const{
151  return decryptTemplate(input, output, from);
152  }
153  int decrypt(const std::vector<unsigned char> & input, std::vector<unsigned char> & output, size_t from = 0) const{
154  return decryptTemplate(input, output, from);
155  }
156  int decrypt(const std::string & input, std::string & output, size_t from = 0) const{
157  return decryptTemplate(input, output, from);
158  }
160 private:
161  void updateKeys(){
162  std::string md5 = tools::Md5(key_);
163  AES_set_encrypt_key(reinterpret_cast<const __Char *>(&md5[0]), intens_, &enKey_);
164  AES_set_decrypt_key(reinterpret_cast<const __Char *>(&md5[0]), intens_, &deKey_);
165  }
166  template<class Buffer>
167  int encryptTemplate(const Buffer & input, Buffer & output, size_t from) const{
168  size_t inlen = input.size();
169  if(inlen < from)
170  return -1;
171  inlen -= from;
172  output.resize(from + (inlen / AES_BLOCK_SIZE + 1) * AES_BLOCK_SIZE);
173  std::copy(input.begin(), input.begin() + from, output.begin());
174  for(;inlen >= AES_BLOCK_SIZE;inlen -= AES_BLOCK_SIZE, from += AES_BLOCK_SIZE)
175  AES_encrypt(
176  reinterpret_cast<const __Char *>(&input[from]),
177  reinterpret_cast<__Char *>(&output[from]),
178  &enKey_);
179  unsigned char tmp[AES_BLOCK_SIZE];
180  memset(tmp, AES_BLOCK_SIZE - inlen, AES_BLOCK_SIZE);
181  memcpy(tmp, &input[from], inlen);
182  AES_encrypt(tmp, reinterpret_cast<__Char *>(&output[from]), &enKey_);
183  return 0;
184  }
185  template<class Buffer>
186  int decryptTemplate(const Buffer & input, Buffer & output, size_t from) const{
187  size_t inlen = input.size();
188  if(inlen < from || (inlen - from) % AES_BLOCK_SIZE != 0)
189  return -1;
190  output.resize(inlen);
191  std::copy(input.begin(), input.begin() + from, output.begin());
192  for(inlen -= from;inlen;inlen -= AES_BLOCK_SIZE, from += AES_BLOCK_SIZE)
193  AES_decrypt(
194  reinterpret_cast<const __Char *>(&input[from]),
195  reinterpret_cast<__Char *>(&output[from]),
196  &deKey_);
197  inlen = *output.rbegin();
198  if(inlen == 0 || inlen > AES_BLOCK_SIZE)
199  return -2;
200  output.resize(output.size() - inlen);
201  return 0;
202  }
203  std::string key_;
204  EKeyIntensity intens_;
205  AES_KEY enKey_;
206  AES_KEY deKey_;
207 };
208 
209 NS_SERVER_END
210 
211 #endif
void setKey(const std::string &key)
Set encryption key (password).
Definition: encrypt_aes.hh:88
void setKeyAndIntensity(const std::string &key, EKeyIntensity intensity)
Set encryption key (password) and key size.
Definition: encrypt_aes.hh:98
void setIntensity(EKeyIntensity intensity)
Set key size.
Definition: encrypt_aes.hh:79
CEncryptorAes()
Construct a default object.
Definition: encrypt_aes.hh:61
EKeyIntensity
Key sizes.
Definition: encrypt_aes.hh:51
CEncryptorAes(const std::string &key, EKeyIntensity intensity)
Construct an object.
Definition: encrypt_aes.hh:69
A convenient interface for Advanced Encryption Standard (AES) algorithm.
Definition: encrypt_aes.hh:43