Commit e4bec827 authored by David S. Miller's avatar David S. Miller

[IPSEC] esp: Defer output IV initialization to first use.

First of all, if the xfrm_state only gets used for input
packets this entropy is a complete waste.

Secondly, it is often the case that a configuration loads
many rules (perhaps even dynamically) and they don't all
necessarily ever get used.

This get_random_bytes() call was showing up in the profiles
for xfrm_state inserts which is how I noticed this.
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 44e36b42
...@@ -15,13 +15,14 @@ struct esp_data ...@@ -15,13 +15,14 @@ struct esp_data
struct { struct {
u8 *key; /* Key */ u8 *key; /* Key */
int key_len; /* Key length */ int key_len; /* Key length */
u8 *ivec; /* ivec buffer */ int padlen; /* 0..255 */
/* ivlen is offset from enc_data, where encrypted data start. /* ivlen is offset from enc_data, where encrypted data start.
* It is logically different of crypto_tfm_alg_ivsize(tfm). * It is logically different of crypto_tfm_alg_ivsize(tfm).
* We assume that it is either zero (no ivec), or * We assume that it is either zero (no ivec), or
* >= crypto_tfm_alg_ivsize(tfm). */ * >= crypto_tfm_alg_ivsize(tfm). */
int ivlen; int ivlen;
int padlen; /* 0..255 */ int ivinitted;
u8 *ivec; /* ivec buffer */
struct crypto_blkcipher *tfm; /* crypto handle */ struct crypto_blkcipher *tfm; /* crypto handle */
} conf; } conf;
......
...@@ -95,8 +95,13 @@ static int esp_output(struct xfrm_state *x, struct sk_buff *skb) ...@@ -95,8 +95,13 @@ static int esp_output(struct xfrm_state *x, struct sk_buff *skb)
esph->seq_no = htonl(++x->replay.oseq); esph->seq_no = htonl(++x->replay.oseq);
xfrm_aevent_doreplay(x); xfrm_aevent_doreplay(x);
if (esp->conf.ivlen) if (esp->conf.ivlen) {
if (unlikely(!esp->conf.ivinitted)) {
get_random_bytes(esp->conf.ivec, esp->conf.ivlen);
esp->conf.ivinitted = 1;
}
crypto_blkcipher_set_iv(tfm, esp->conf.ivec, esp->conf.ivlen); crypto_blkcipher_set_iv(tfm, esp->conf.ivec, esp->conf.ivlen);
}
do { do {
struct scatterlist *sg = &esp->sgbuf[0]; struct scatterlist *sg = &esp->sgbuf[0];
...@@ -378,7 +383,7 @@ static int esp_init_state(struct xfrm_state *x) ...@@ -378,7 +383,7 @@ static int esp_init_state(struct xfrm_state *x)
esp->conf.ivec = kmalloc(esp->conf.ivlen, GFP_KERNEL); esp->conf.ivec = kmalloc(esp->conf.ivlen, GFP_KERNEL);
if (unlikely(esp->conf.ivec == NULL)) if (unlikely(esp->conf.ivec == NULL))
goto error; goto error;
get_random_bytes(esp->conf.ivec, esp->conf.ivlen); esp->conf.ivinitted = 0;
} }
if (crypto_blkcipher_setkey(tfm, esp->conf.key, esp->conf.key_len)) if (crypto_blkcipher_setkey(tfm, esp->conf.key, esp->conf.key_len))
goto error; goto error;
......
...@@ -99,8 +99,13 @@ static int esp6_output(struct xfrm_state *x, struct sk_buff *skb) ...@@ -99,8 +99,13 @@ static int esp6_output(struct xfrm_state *x, struct sk_buff *skb)
esph->seq_no = htonl(++x->replay.oseq); esph->seq_no = htonl(++x->replay.oseq);
xfrm_aevent_doreplay(x); xfrm_aevent_doreplay(x);
if (esp->conf.ivlen) if (esp->conf.ivlen) {
if (unlikely(!esp->conf.ivinitted)) {
get_random_bytes(esp->conf.ivec, esp->conf.ivlen);
esp->conf.ivinitted = 1;
}
crypto_blkcipher_set_iv(tfm, esp->conf.ivec, esp->conf.ivlen); crypto_blkcipher_set_iv(tfm, esp->conf.ivec, esp->conf.ivlen);
}
do { do {
struct scatterlist *sg = &esp->sgbuf[0]; struct scatterlist *sg = &esp->sgbuf[0];
...@@ -353,7 +358,7 @@ static int esp6_init_state(struct xfrm_state *x) ...@@ -353,7 +358,7 @@ static int esp6_init_state(struct xfrm_state *x)
esp->conf.ivec = kmalloc(esp->conf.ivlen, GFP_KERNEL); esp->conf.ivec = kmalloc(esp->conf.ivlen, GFP_KERNEL);
if (unlikely(esp->conf.ivec == NULL)) if (unlikely(esp->conf.ivec == NULL))
goto error; goto error;
get_random_bytes(esp->conf.ivec, esp->conf.ivlen); esp->conf.ivinitted = 0;
} }
if (crypto_blkcipher_setkey(tfm, esp->conf.key, esp->conf.key_len)) if (crypto_blkcipher_setkey(tfm, esp->conf.key, esp->conf.key_len))
goto error; goto error;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment