summaryrefslogtreecommitdiff
path: root/src/key_derivation.c
diff options
context:
space:
mode:
authorChristian Pointner <equinox@anytun.org>2009-01-02 19:49:51 +0000
committerChristian Pointner <equinox@anytun.org>2009-01-02 19:49:51 +0000
commitc0cfc1ff73049c4f420fdc70002f6f2c068d34dd (patch)
tree1bb22c9f3fdcb6706941e492f334ad1c16bd858a /src/key_derivation.c
parentsome cleanup at key derivation (diff)
some improvements in key derivation
note this is no longer compatible to anytun and currently not compliant to the rfc (but probably will)
Diffstat (limited to 'src/key_derivation.c')
-rw-r--r--src/key_derivation.c122
1 files changed, 52 insertions, 70 deletions
diff --git a/src/key_derivation.c b/src/key_derivation.c
index 44ae667..3977993 100644
--- a/src/key_derivation.c
+++ b/src/key_derivation.c
@@ -60,15 +60,17 @@ int key_derivation_init(key_derivation_t* kd, const char* type, int8_t ld_kdr, u
}
kd->ld_kdr_ = ld_kdr;
- if(ld_kdr > (sizeof(seq_nr_t) * 8))
+ if(ld_kdr > (int8_t)(sizeof(seq_nr_t) * 8))
kd->ld_kdr_ = sizeof(seq_nr_t) * 8;
+
kd->key_length_ = key_len * sizeof(key[0]) * 8;
kd->handle_ = 0;
int i;
for(i = 0; i<KD_LABEL_COUNT; ++i) {
- kd->key_store_[i].buf_ = NULL;
- kd->key_store_[i].length_ = 0;
+ kd->key_store_[i].key_.buf_ = NULL;
+ kd->key_store_[i].key_.length_ = 0;
+ kd->key_store_[i].r_ = 0;
}
if(!key) {
@@ -123,8 +125,8 @@ void key_derivation_close(key_derivation_t* kd)
int i;
for(i = 0; i<KD_LABEL_COUNT; ++i) {
- if(kd->key_store_[i].buf_)
- free(kd->key_store_[i].buf_);
+ if(kd->key_store_[i].key_.buf_)
+ free(kd->key_store_[i].key_.buf_);
}
}
@@ -200,75 +202,50 @@ void key_derivation_aesctr_close(key_derivation_t* kd)
gcry_cipher_close(kd->handle_);
}
-int key_derivation_aesctr_calc_ctr(key_derivation_t* kd, buffer_t* result, satp_prf_label_t label, seq_nr_t seq_nr)
+int key_derivation_aesctr_calc_ctr(key_derivation_t* kd, key_store_t* result, satp_prf_label_t label, seq_nr_t seq_nr)
{
if(!kd || !result)
return -1;
- result->buf_ = NULL;
- result->length_ = 0;
+ seq_nr_t r = 0;
+ if(kd->ld_kdr_ >= 0)
+ r = seq_nr >> kd->ld_kdr_;
- mpz_t ctr, key_id, r, seq;
+ if(kd->key_store_[label].key_.buf_ && kd->key_store_[label].r_ == r) {
+ if(!r || (seq_nr % r))
+ return 0;
+ }
+ result->r_ = r;
+
+ mpz_t ctr, key_id;
mpz_init2(ctr, 128);
mpz_init2(key_id, 128);
- mpz_init2(r, 128);
- mpz_init2(seq, (sizeof(seq_nr_t) * 8));
-
- mpz_set_ui(seq, seq_nr);
int faked_msb = 0;
- if(!kd->master_salt_.buf_[0])
+ if(!kd->master_salt_.buf_[0]) {
kd->master_salt_.buf_[0] = 1;
-
- if(kd->ld_kdr_ == -1)
- mpz_set_ui(r, 0);
- else
- mpz_fdiv_q_2exp(r, seq, kd->ld_kdr_);
-
- if(kd->key_store_[label].buf_) {
- if(!mpz_cmp_ui(r, 0)) {
- mpz_clear(seq);
- mpz_clear(ctr);
- mpz_clear(key_id);
- mpz_clear(r);
- return 0;
- }
-
- mpz_t mod;
- mpz_init2(mod, (sizeof(seq_nr_t) * 8));
- mpz_fdiv_r(mod, seq, r);
- if(mpz_cmp_ui(mod, 0)) {
- mpz_clear(seq);
- mpz_clear(mod);
- mpz_clear(ctr);
- mpz_clear(key_id);
- mpz_clear(r);
- return 0;
- }
- mpz_clear(mod);
+ faked_msb = 1;
}
+ mpz_import(ctr, kd->master_salt_.length_, 1, 1, 0, 0, kd->master_salt_.buf_);
mpz_set_ui(key_id, label);
- mpz_mul_2exp(key_id, key_id, (sizeof(seq_nr_t) * 8));
- mpz_add(key_id, key_id, r);
-
- mpz_import(ctr, kd->master_salt_.length_, 1, 1, 0, 0, kd->master_salt_.buf_);
+ mpz_mul_2exp(key_id, key_id, (sizeof(r) * 8));
+ mpz_add_ui(key_id, key_id, r);
mpz_xor(ctr, ctr, key_id);
mpz_mul_2exp(ctr, ctr, 16);
- if(result->buf_)
- free(result->buf_);
- result->buf_ = mpz_export(NULL, (size_t*)&(result->length_), 1, 1, 0, 0, ctr);
+ if(result->key_.buf_)
+ free(result->key_.buf_);
+ result->key_.buf_ = mpz_export(NULL, (size_t*)&(result->key_.length_), 1, 1, 0, 0, ctr);
+
if(faked_msb) {
kd->master_salt_.buf_[0] = 0;
- result->buf_[0] = 0;
+ result->key_.buf_[0] = 0;
}
- mpz_clear(seq);
mpz_clear(ctr);
mpz_clear(key_id);
- mpz_clear(r);
return 1;
}
@@ -280,21 +257,22 @@ int key_derivation_aesctr_generate(key_derivation_t* kd, satp_prf_label_t label,
return -1;
}
- buffer_t ctr;
- ctr.buf_ = NULL;
- ctr.length_ = 0;
+ key_store_t ctr;
+ ctr.key_.buf_ = NULL;
+ ctr.key_.length_ = 0;
+ ctr.r_ = 0;
int ret = key_derivation_aesctr_calc_ctr(kd, &ctr, label, seq_nr);
if(ret < 0) {
log_printf(ERR, "failed to calculate key derivation CTR");
return -1;
}
else if(!ret) {
- if(len > kd->key_store_[label].length_) {
+ if(len > kd->key_store_[label].key_.length_) {
log_printf(WARNING, "stored (old) key for label 0x%02X is too short, filling with zeros", label);
memset(key, 0, len);
- len = kd->key_store_[label].length_;
+ len = kd->key_store_[label].key_.length_;
}
- memcpy(key, kd->key_store_[label].buf_, len);
+ memcpy(key, kd->key_store_[label].key_.buf_, len);
return 0;
}
@@ -304,8 +282,8 @@ int key_derivation_aesctr_generate(key_derivation_t* kd, satp_prf_label_t label,
return -1;
}
- err = gcry_cipher_setctr(kd->handle_, ctr.buf_, ctr.length_);
- free(ctr.buf_);
+ err = gcry_cipher_setctr(kd->handle_, ctr.key_.buf_, ctr.key_.length_);
+ free(ctr.key_.buf_);
if(err) {
log_printf(ERR, "failed to set key derivation CTR: %s/%s", gcry_strerror(err), gcry_strsource(err));
@@ -319,26 +297,30 @@ int key_derivation_aesctr_generate(key_derivation_t* kd, satp_prf_label_t label,
return -1;
}
- if(!kd->key_store_[label].buf_) {
- kd->key_store_[label].length_ = 0;
- kd->key_store_[label].buf_ = malloc(len);
- if(!kd->key_store_[label].buf_) {
+ if(!kd->ld_kdr_)
+ return 1;
+
+ if(!kd->key_store_[label].key_.buf_) {
+ kd->key_store_[label].key_.length_ = 0;
+ kd->key_store_[label].key_.buf_ = malloc(len);
+ if(!kd->key_store_[label].key_.buf_) {
log_printf(ERR, "memory error at key derivation");
return -2;
}
- kd->key_store_[label].length_ = len;
+ kd->key_store_[label].key_.length_ = len;
}
- else if(kd->key_store_[label].length_ < len) {
- u_int8_t* tmp = realloc(kd->key_store_[label].buf_, len);
+ else if(kd->key_store_[label].key_.length_ < len) {
+ u_int8_t* tmp = realloc(kd->key_store_[label].key_.buf_, len);
if(!tmp) {
log_printf(ERR, "memory error at key derivation");
return -2;
}
- kd->key_store_[label].buf_ = tmp;
- kd->key_store_[label].length_ = len;
+ kd->key_store_[label].key_.buf_ = tmp;
+ kd->key_store_[label].key_.length_ = len;
}
- memcpy(kd->key_store_[label].buf_, key, len);
+ memcpy(kd->key_store_[label].key_.buf_, key, len);
+ kd->key_store_[label].r_ = ctr.r_;
- return 0;
+ return 1;
}