From: Martin Willi Date: Fri, 17 Apr 2015 12:08:14 +0000 (+0200) Subject: iv-gen: Ensure external sequential IVs are actually sequential X-Git-Tag: 5.3.1~7 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=d0ed1079;p=thirdparty%2Fstrongswan.git iv-gen: Ensure external sequential IVs are actually sequential We allow gaps in IVs, but ensure that an IV is never used more than once. --- diff --git a/src/libstrongswan/crypto/iv/iv_gen_seq.c b/src/libstrongswan/crypto/iv/iv_gen_seq.c index 98d0c15a60..70f1fce389 100644 --- a/src/libstrongswan/crypto/iv/iv_gen_seq.c +++ b/src/libstrongswan/crypto/iv/iv_gen_seq.c @@ -15,6 +15,11 @@ #include "iv_gen_seq.h" +/** + * Magic value for the initial IV state + */ +#define SEQ_IV_INIT_STATE (~(u_int64_t)0) + typedef struct private_iv_gen_t private_iv_gen_t; /** @@ -27,6 +32,11 @@ struct private_iv_gen_t { */ iv_gen_t public; + /** + * Previously passed sequence number to enforce uniqueness + */ + u_int64_t prev; + /** * Salt to mask counter */ @@ -43,6 +53,15 @@ METHOD(iv_gen_t, get_iv, bool, { return FALSE; } + if (this->prev != SEQ_IV_INIT_STATE && seq <= this->prev) + { + return FALSE; + } + if (seq == SEQ_IV_INIT_STATE) + { + return FALSE; + } + this->prev = seq; if (len > sizeof(u_int64_t)) { len = sizeof(u_int64_t); @@ -84,6 +103,7 @@ iv_gen_t *iv_gen_seq_create() .allocate_iv = _allocate_iv, .destroy = _destroy, }, + .prev = SEQ_IV_INIT_STATE, ); rng = lib->crypto->create_rng(lib->crypto, RNG_STRONG); diff --git a/src/libstrongswan/crypto/iv/iv_gen_seq.h b/src/libstrongswan/crypto/iv/iv_gen_seq.h index 329dcca05c..43ff4f65e0 100644 --- a/src/libstrongswan/crypto/iv/iv_gen_seq.h +++ b/src/libstrongswan/crypto/iv/iv_gen_seq.h @@ -25,6 +25,9 @@ /** * Create an IV generator that generates sequential IVs (counter). * + * The passed external IV must be larger than the one passed to any previous + * call. + * * @return IV generator */ iv_gen_t *iv_gen_seq_create();