summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/anytun.cpp2
-rw-r--r--src/keyDerivation.cpp82
-rw-r--r--src/keyDerivation.h11
-rw-r--r--src/options.cpp53
-rw-r--r--src/options.h3
5 files changed, 136 insertions, 15 deletions
diff --git a/src/anytun.cpp b/src/anytun.cpp
index 06113b2..a2d7f05 100644
--- a/src/anytun.cpp
+++ b/src/anytun.cpp
@@ -82,7 +82,7 @@ void createConnection(const PacketSourceEndpoint & remote_end, window_size_t seq
SeqWindow* seq = new SeqWindow(seqSize);
seq_nr_t seq_nr_=0;
KeyDerivation * kd = KeyDerivationFactory::create(gOpt.getKdPrf());
- kd->init(gOpt.getKey(), gOpt.getSalt());
+ kd->init(gOpt.getKey(), gOpt.getSalt(), gOpt.getPassphrase());
kd->setLogKDRate(gOpt.getLdKdr());
cLog.msg(Log::PRIO_NOTICE) << "added connection remote host " << remote_end;
diff --git a/src/keyDerivation.cpp b/src/keyDerivation.cpp
index dbe5dee..48db034 100644
--- a/src/keyDerivation.cpp
+++ b/src/keyDerivation.cpp
@@ -41,6 +41,10 @@
#include <sstream>
#include <string>
+#ifdef USE_SSL_CRYPTO
+#include <openssl/sha.h>
+#endif
+
void KeyDerivation::setLogKDRate(const int8_t log_rate)
{
WritersLock lock(mutex_);
@@ -49,6 +53,66 @@ void KeyDerivation::setLogKDRate(const int8_t log_rate)
ld_kdr_ = sizeof(seq_nr_t) * 8;
}
+#ifndef NO_PASSPHRASE
+void KeyDerivation::calcMasterKey(std::string passphrase, u_int16_t length)
+{
+ cLog.msg(Log::PRIO_NOTICE) << "KeyDerivation: calculating master key from passphrase";
+ if(!length) {
+ cLog.msg(Log::PRIO_ERR) << "KeyDerivation: bad master key length";
+ return;
+ }
+
+#ifndef USE_SSL_CRYPTO
+ if(length > gcry_md_get_algo_dlen(GCRY_MD_SHA256)) {
+#else
+ if(length > SHA256_DIGEST_LENGTH) {
+#endif
+ cLog.msg(Log::PRIO_ERR) << "KeyDerivation: master key too long for passphrase algorithm";
+ return;
+ }
+
+#ifndef USE_SSL_CRYPTO
+ Buffer digest(gcry_md_get_algo_dlen(GCRY_MD_SHA256));
+ gcry_md_hash_buffer(GCRY_MD_SHA256, digest.getBuf(), passphrase.c_str(), passphrase.length());
+#else
+ Buffer digest(u_int32_t(SHA256_DIGEST_LENGTH));
+ SHA256(reinterpret_cast<const unsigned char*>(passphrase.c_str()), passphrase.length(), digest.getBuf());
+#endif
+ master_key_.setLength(length);
+
+ memcpy(master_key_.getBuf(), &digest.getBuf()[digest.getLength() - master_key_.getLength()], master_key_.getLength());
+}
+
+void KeyDerivation::calcMasterSalt(std::string passphrase, u_int16_t length)
+{
+ cLog.msg(Log::PRIO_NOTICE) << "KeyDerivation: calculating master salt from passphrase";
+ if(!length) {
+ cLog.msg(Log::PRIO_ERR) << "KeyDerivation: bad master salt length";
+ return;
+ }
+
+#ifndef USE_SSL_CRYPTO
+ if(length > gcry_md_get_algo_dlen(GCRY_MD_SHA1)) {
+#else
+ if(length > SHA_DIGEST_LENGTH) {
+#endif
+ cLog.msg(Log::PRIO_ERR) << "KeyDerivation: master key too long for passphrase algorithm";
+ return;
+ }
+
+#ifndef USE_SSL_CRYPTO
+ Buffer digest(gcry_md_get_algo_dlen(GCRY_MD_SHA1));
+ gcry_md_hash_buffer(GCRY_MD_SHA1, digest.getBuf(), passphrase.c_str(), passphrase.length());
+#else
+ Buffer digest(u_int32_t(SHA_DIGEST_LENGTH));
+ SHA1(reinterpret_cast<const unsigned char*>(passphrase.c_str()), passphrase.length(), digest.getBuf());
+#endif
+ master_salt_.setLength(length);
+
+ memcpy(master_salt_.getBuf(), &digest.getBuf()[digest.getLength() - master_salt_.getLength()], master_salt_.getLength());
+}
+#endif
+
//****** NullKeyDerivation ******
bool NullKeyDerivation::generate(kd_dir_t dir, satp_prf_label_t label, seq_nr_t seq_nr, Buffer& key)
@@ -86,13 +150,25 @@ AesIcmKeyDerivation::~AesIcmKeyDerivation()
#endif
}
-void AesIcmKeyDerivation::init(Buffer key, Buffer salt)
+void AesIcmKeyDerivation::init(Buffer key, Buffer salt, std::string passphrase)
{
WritersLock lock(mutex_);
-
+
is_initialized_ = false;
- master_salt_ = SyncBuffer(salt);
+#ifndef NO_PASSPHRASE
+ if(passphrase != "" && !key.getLength())
+ calcMasterKey(passphrase, key_length_/8);
+ else
+ master_key_ = SyncBuffer(key);
+
+ if(passphrase != "" && !salt.getLength())
+ calcMasterSalt(passphrase, SALT_LENGTH);
+ else
+ master_salt_ = SyncBuffer(salt);
+#else
master_key_ = SyncBuffer(key);
+ master_salt_ = SyncBuffer(salt);
+#endif
updateMasterKey();
}
diff --git a/src/keyDerivation.h b/src/keyDerivation.h
index 926d35f..518a498 100644
--- a/src/keyDerivation.h
+++ b/src/keyDerivation.h
@@ -73,7 +73,7 @@ public:
void setLogKDRate(const int8_t ld_rate);
- virtual void init(Buffer key, Buffer salt) = 0;
+ virtual void init(Buffer key, Buffer salt, std::string passphrase = "") = 0;
virtual bool generate(kd_dir_t dir, satp_prf_label_t label, seq_nr_t seq_nr, Buffer& key) = 0;
virtual std::string printType() { return "GenericKeyDerivation"; };
@@ -81,6 +81,11 @@ public:
protected:
virtual void updateMasterKey() = 0;
+#ifndef NO_PASSPHRASE
+ void calcMasterKey(std::string passphrase, u_int16_t length);
+ void calcMasterSalt(std::string passphrase, u_int16_t length);
+#endif
+
KeyDerivation(const KeyDerivation & src);
friend class boost::serialization::access;
template<class Archive>
@@ -113,7 +118,7 @@ public:
NullKeyDerivation() {};
~NullKeyDerivation() {};
- void init(Buffer key, Buffer salt) {};
+ void init(Buffer key, Buffer salt, std::string passphrase = "") {};
bool generate(kd_dir_t dir, satp_prf_label_t label, seq_nr_t seq_nr, Buffer& key);
std::string printType() { return "NullKeyDerivation"; };
@@ -144,7 +149,7 @@ public:
static const u_int16_t CTR_LENGTH = 16;
static const u_int16_t SALT_LENGTH = 14;
- void init(Buffer key, Buffer salt);
+ void init(Buffer key, Buffer salt, std::string passphrase = "");
bool generate(kd_dir_t dir, satp_prf_label_t label, seq_nr_t seq_nr, Buffer& key);
std::string printType();
diff --git a/src/options.cpp b/src/options.cpp
index 40182c4..d241eae 100644
--- a/src/options.cpp
+++ b/src/options.cpp
@@ -238,6 +238,26 @@ Options::~Options()
i+=2; \
}
+#define PARSE_CSLIST_PARAM(SHORT, LONG, LIST, TYPE) \
+ else if(str == SHORT || str == LONG) \
+ { \
+ if(argc < 1) \
+ throw syntax_error(str, str.length()); \
+ if(argv[i+1][0] == '-') { \
+ u_int32_t pos = str.length() + 1; \
+ throw syntax_error(str.append(" ").append(argv[i+1]), pos); \
+ } \
+ std::stringstream tmp(argv[i+1]); \
+ while (tmp.good()) \
+ { \
+ std::string tmp_line; \
+ getline(tmp,tmp_line,','); \
+ LIST.push_back(TYPE(tmp_line)); \
+ } \
+ argc--; \
+ i++; \
+ }
+
#define PARSE_HEXSTRING_PARAM_SEC(SHORT, LONG, VALUE) \
else if(str == SHORT || str == LONG) \
{ \
@@ -254,7 +274,7 @@ Options::~Options()
i++; \
}
-#define PARSE_CSLIST_PARAM(SHORT, LONG, LIST, TYPE) \
+#define PARSE_PHRASE_PARAM_SEC(SHORT, LONG, VALUE) \
else if(str == SHORT || str == LONG) \
{ \
if(argc < 1) \
@@ -263,13 +283,10 @@ Options::~Options()
u_int32_t pos = str.length() + 1; \
throw syntax_error(str.append(" ").append(argv[i+1]), pos); \
} \
- std::stringstream tmp(argv[i+1]); \
- while (tmp.good()) \
- { \
- std::string tmp_line; \
- getline(tmp,tmp_line,','); \
- LIST.push_back(TYPE(tmp_line)); \
- } \
+ std::stringstream tmp; \
+ VALUE = argv[i+1]; \
+ for(size_t j=0; j < strlen(argv[i+1]); ++j) \
+ argv[i+1][j] = '#'; \
argc--; \
i++; \
}
@@ -320,6 +337,9 @@ bool Options::parse(int argc, char* argv[])
PARSE_SCALAR_PARAM("-a","--auth-algo", auth_algo_)
PARSE_SCALAR_PARAM("-k","--kd-prf", kd_prf_)
PARSE_SIGNED_INT_PARAM("-l","--ld-kdr", ld_kdr_tmp)
+#ifndef NO_PASSPHRASE
+ PARSE_PHRASE_PARAM_SEC("-E","--passphrase", passphrase_)
+#endif
PARSE_HEXSTRING_PARAM_SEC("-K","--key", key_)
PARSE_HEXSTRING_PARAM_SEC("-A","--salt", salt_)
else
@@ -380,6 +400,9 @@ void Options::printUsage()
std::cout << " [-a|--auth-algo] <algo type> message authentication algorithm" << std::endl;
std::cout << " [-k|--kd-prf] <kd-prf type> key derivation pseudo random function" << std::endl;
std::cout << " [-l|--ld-kdr] <ld-kdr> log2 of key derivation rate" << std::endl;
+#ifndef NO_PASSPHRASE
+ std::cout << " [-E|--passphrase] <pass phrase> a passprhase to generate master key and salt from" << std::endl;
+#endif
std::cout << " [-K|--key] <master key> master key to use for encryption" << std::endl;
std::cout << " [-A|--salt] <master salt> master salt to use for encryption" << std::endl;
}
@@ -429,6 +452,7 @@ void Options::printOptions()
std::cout << "auth_algo = '" << auth_algo_ << "'" << std::endl;
std::cout << "kd_prf = '" << kd_prf_ << "'" << std::endl;
std::cout << "ld_kdr = " << static_cast<int32_t>(ld_kdr_) << std::endl;
+ std::cout << "passphrase = '" << passphrase_ << "'" << std::endl;
std::cout << "key = " << key_.getHexDumpOneLine() << std::endl;
std::cout << "salt = " << salt_.getHexDumpOneLine() << std::endl;
}
@@ -808,6 +832,19 @@ Options& Options::setLdKdr(int8_t l)
return *this;
}
+std::string Options::getPassphrase()
+{
+ ReadersLock lock(mutex);
+ return passphrase_;
+}
+
+Options& Options::setPassphrase(std::string p)
+{
+ WritersLock lock(mutex);
+ passphrase_ = p;
+ return *this;
+}
+
Buffer Options::getKey()
{
ReadersLock lock(mutex);
diff --git a/src/options.h b/src/options.h
index 5167878..694526e 100644
--- a/src/options.h
+++ b/src/options.h
@@ -146,6 +146,8 @@ public:
Options& setKdPrf(std::string k);
int8_t getLdKdr();
Options& setLdKdr(int8_t l);
+ std::string getPassphrase();
+ Options& setPassphrase(std::string p);
Options& setKey(std::string k);
Buffer getKey();
Options& setSalt(std::string s);
@@ -201,6 +203,7 @@ private:
std::string auth_algo_;
std::string kd_prf_;
int8_t ld_kdr_;
+ std::string passphrase_;
Buffer key_;
Buffer salt_;
};