aboutsummaryrefslogtreecommitdiffstats
path: root/crypto/lrw.c
diff options
context:
space:
mode:
Diffstat (limited to 'crypto/lrw.c')
-rw-r--r--crypto/lrw.c61
1 files changed, 40 insertions, 21 deletions
diff --git a/crypto/lrw.c b/crypto/lrw.c
index bee60226f723..91c17fa18374 100644
--- a/crypto/lrw.c
+++ b/crypto/lrw.c
@@ -29,8 +29,7 @@
29 29
30#define LRW_BLOCK_SIZE 16 30#define LRW_BLOCK_SIZE 16
31 31
32struct priv { 32struct lrw_table_ctx {
33 struct crypto_cipher *child;
34 /* optimizes multiplying a random (non incrementing, as at the 33 /* optimizes multiplying a random (non incrementing, as at the
35 * start of a new sector) value with key2, we could also have 34 * start of a new sector) value with key2, we could also have
36 * used 4k optimization tables or no optimization at all. In the 35 * used 4k optimization tables or no optimization at all. In the
@@ -45,6 +44,11 @@ struct priv {
45 be128 mulinc[128]; 44 be128 mulinc[128];
46}; 45};
47 46
47struct priv {
48 struct crypto_cipher *child;
49 struct lrw_table_ctx table;
50};
51
48static inline void setbit128_bbe(void *b, int bit) 52static inline void setbit128_bbe(void *b, int bit)
49{ 53{
50 __set_bit(bit ^ (0x80 - 54 __set_bit(bit ^ (0x80 -
@@ -56,28 +60,16 @@ static inline void setbit128_bbe(void *b, int bit)
56 ), b); 60 ), b);
57} 61}
58 62
59static int setkey(struct crypto_tfm *parent, const u8 *key, 63static int lrw_init_table(struct lrw_table_ctx *ctx, const u8 *tweak)
60 unsigned int keylen)
61{ 64{
62 struct priv *ctx = crypto_tfm_ctx(parent);
63 struct crypto_cipher *child = ctx->child;
64 int err, i;
65 be128 tmp = { 0 }; 65 be128 tmp = { 0 };
66 int bsize = LRW_BLOCK_SIZE; 66 int i;
67
68 crypto_cipher_clear_flags(child, CRYPTO_TFM_REQ_MASK);
69 crypto_cipher_set_flags(child, crypto_tfm_get_flags(parent) &
70 CRYPTO_TFM_REQ_MASK);
71 if ((err = crypto_cipher_setkey(child, key, keylen - bsize)))
72 return err;
73 crypto_tfm_set_flags(parent, crypto_cipher_get_flags(child) &
74 CRYPTO_TFM_RES_MASK);
75 67
76 if (ctx->table) 68 if (ctx->table)
77 gf128mul_free_64k(ctx->table); 69 gf128mul_free_64k(ctx->table);
78 70
79 /* initialize multiplication table for Key2 */ 71 /* initialize multiplication table for Key2 */
80 ctx->table = gf128mul_init_64k_bbe((be128 *)(key + keylen - bsize)); 72 ctx->table = gf128mul_init_64k_bbe((be128 *)tweak);
81 if (!ctx->table) 73 if (!ctx->table)
82 return -ENOMEM; 74 return -ENOMEM;
83 75
@@ -91,6 +83,32 @@ static int setkey(struct crypto_tfm *parent, const u8 *key,
91 return 0; 83 return 0;
92} 84}
93 85
86static void lrw_free_table(struct lrw_table_ctx *ctx)
87{
88 if (ctx->table)
89 gf128mul_free_64k(ctx->table);
90}
91
92static int setkey(struct crypto_tfm *parent, const u8 *key,
93 unsigned int keylen)
94{
95 struct priv *ctx = crypto_tfm_ctx(parent);
96 struct crypto_cipher *child = ctx->child;
97 int err, bsize = LRW_BLOCK_SIZE;
98 const u8 *tweak = key + keylen - bsize;
99
100 crypto_cipher_clear_flags(child, CRYPTO_TFM_REQ_MASK);
101 crypto_cipher_set_flags(child, crypto_tfm_get_flags(parent) &
102 CRYPTO_TFM_REQ_MASK);
103 err = crypto_cipher_setkey(child, key, keylen - bsize);
104 if (err)
105 return err;
106 crypto_tfm_set_flags(parent, crypto_cipher_get_flags(child) &
107 CRYPTO_TFM_RES_MASK);
108
109 return lrw_init_table(&ctx->table, tweak);
110}
111
94struct sinfo { 112struct sinfo {
95 be128 t; 113 be128 t;
96 struct crypto_tfm *tfm; 114 struct crypto_tfm *tfm;
@@ -157,7 +175,7 @@ static int crypt(struct blkcipher_desc *d,
157 s.t = *iv; 175 s.t = *iv;
158 176
159 /* T <- I*Key2 */ 177 /* T <- I*Key2 */
160 gf128mul_64k_bbe(&s.t, ctx->table); 178 gf128mul_64k_bbe(&s.t, ctx->table.table);
161 179
162 goto first; 180 goto first;
163 181
@@ -165,7 +183,8 @@ static int crypt(struct blkcipher_desc *d,
165 do { 183 do {
166 /* T <- I*Key2, using the optimization 184 /* T <- I*Key2, using the optimization
167 * discussed in the specification */ 185 * discussed in the specification */
168 be128_xor(&s.t, &s.t, &ctx->mulinc[get_index128(iv)]); 186 be128_xor(&s.t, &s.t,
187 &ctx->table.mulinc[get_index128(iv)]);
169 inc(iv); 188 inc(iv);
170 189
171first: 190first:
@@ -233,8 +252,8 @@ static int init_tfm(struct crypto_tfm *tfm)
233static void exit_tfm(struct crypto_tfm *tfm) 252static void exit_tfm(struct crypto_tfm *tfm)
234{ 253{
235 struct priv *ctx = crypto_tfm_ctx(tfm); 254 struct priv *ctx = crypto_tfm_ctx(tfm);
236 if (ctx->table) 255
237 gf128mul_free_64k(ctx->table); 256 lrw_free_table(&ctx->table);
238 crypto_free_cipher(ctx->child); 257 crypto_free_cipher(ctx->child);
239} 258}
240 259