From 2be652fea52eaf3e25671c4b2ddd5ff4f1a10342 Mon Sep 17 00:00:00 2001 From: Paul Wouters Date: Thu, 3 Jul 2014 12:37:21 -0400 Subject: [PATCH] kernel_alg_esp_enc_ok(): improve key size handling - If ealg is not registered, don't return "ok" (also already spotted by Hugh) - If key_len is specified, enforce some size restrictions (this duplicates code elsewhere and should be split off in a separate function) --- lib/libswan/kernel_alg.c | 49 ++++++++++++++++++++++++---------------- 1 file changed, 30 insertions(+), 19 deletions(-) diff --git a/lib/libswan/kernel_alg.c b/lib/libswan/kernel_alg.c index 277bc430cea..3417337f8e8 100644 --- a/lib/libswan/kernel_alg.c +++ b/lib/libswan/kernel_alg.c @@ -153,42 +153,53 @@ err_t kernel_alg_esp_enc_ok(int alg_id, unsigned int key_len) * test #1: encrypt algo must be present */ if (!ESP_EALG_PRESENT(alg_id)) { - /* - * ??? why is this OK? - * Perhaps: ugh = "alg not present in system"; - */ DBG(DBG_KERNEL, DBG_log("kernel_alg_esp_enc_ok(%d,%d): alg not present in system", alg_id, key_len); ); + ugh = "esp alg not present in system"; } else { struct sadb_alg *alg_p = &esp_ealg[alg_id]; passert(alg_p != NULL); - if (alg_id == ESP_AES_GCM_8 || - alg_id == ESP_AES_GCM_12 || - alg_id == ESP_AES_GCM_16) { - if (key_len != 128 && key_len != 192 && - key_len != 256) { + switch (alg_id) { + case ESP_AES_GCM_8: + case ESP_AES_GCM_12: + case ESP_AES_GCM_16: + case ESP_AES_CCM_8: + case ESP_AES_CCM_12: + case ESP_AES_CCM_16: + case ESP_AES_CTR: + case ESP_CAMELLIA: + if (key_len && (key_len != 128 && key_len != 192 && + key_len != 256)) { ugh = builddiag("kernel_alg_db_add() key_len is incorrect: alg_id=%d, key_len=%d, alg_minbits=%d, alg_maxbits=%d", alg_id, key_len, alg_p->sadb_alg_minbits, alg_p->sadb_alg_maxbits); } - } - - /* - * test #2: if key_len specified, it must be in range - */ - if (ugh == NULL && key_len != 0 && - (key_len < alg_p->sadb_alg_minbits || - key_len > alg_p->sadb_alg_maxbits)) { - - ugh = builddiag("kernel_alg_db_add() key_len not in range: alg_id=%d, key_len=%d, alg_minbits=%d, alg_maxbits=%d", + break; + case ESP_SEED_CBC: + case ESP_CAST: + if (key_len != 128) { + ugh = builddiag("kernel_alg_db_add() key_len is incorrect: alg_id=%d, key_len=%d, alg_minbits=%d, alg_maxbits=%d", + alg_id, key_len, + alg_p->sadb_alg_minbits, + alg_p->sadb_alg_maxbits); + } + break; + default: + /* old behaviour - not necc. correct */ + if (key_len != 0 && (key_len < alg_p->sadb_alg_minbits + || key_len > alg_p->sadb_alg_maxbits)) { + ugh = builddiag("kernel_alg_db_add() key_len not in range: alg_id=%d, key_len=%d, alg_minbits=%d, alg_maxbits=%d", alg_id, key_len, alg_p->sadb_alg_minbits, alg_p->sadb_alg_maxbits); + } + } + if (ugh != NULL) { DBG(DBG_KERNEL, DBG_log("kernel_alg_esp_enc_ok(%d,%d): %s alg_id=%d, alg_ivlen=%d, alg_minbits=%d, alg_maxbits=%d, res=%d",