diff options
-rw-r--r-- | drivers/md/dm-crypt.c | 23 |
1 files changed, 14 insertions, 9 deletions
diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c index facf859b9b87..0d8686505e51 100644 --- a/drivers/md/dm-crypt.c +++ b/drivers/md/dm-crypt.c | |||
@@ -86,7 +86,10 @@ struct crypt_config { | |||
86 | */ | 86 | */ |
87 | struct crypt_iv_operations *iv_gen_ops; | 87 | struct crypt_iv_operations *iv_gen_ops; |
88 | char *iv_mode; | 88 | char *iv_mode; |
89 | struct crypto_cipher *iv_gen_private; | 89 | union { |
90 | struct crypto_cipher *essiv_tfm; | ||
91 | int benbi_shift; | ||
92 | } iv_gen_private; | ||
90 | sector_t iv_offset; | 93 | sector_t iv_offset; |
91 | unsigned int iv_size; | 94 | unsigned int iv_size; |
92 | 95 | ||
@@ -195,21 +198,21 @@ static int crypt_iv_essiv_ctr(struct crypt_config *cc, struct dm_target *ti, | |||
195 | } | 198 | } |
196 | kfree(salt); | 199 | kfree(salt); |
197 | 200 | ||
198 | cc->iv_gen_private = essiv_tfm; | 201 | cc->iv_gen_private.essiv_tfm = essiv_tfm; |
199 | return 0; | 202 | return 0; |
200 | } | 203 | } |
201 | 204 | ||
202 | static void crypt_iv_essiv_dtr(struct crypt_config *cc) | 205 | static void crypt_iv_essiv_dtr(struct crypt_config *cc) |
203 | { | 206 | { |
204 | crypto_free_cipher(cc->iv_gen_private); | 207 | crypto_free_cipher(cc->iv_gen_private.essiv_tfm); |
205 | cc->iv_gen_private = NULL; | 208 | cc->iv_gen_private.essiv_tfm = NULL; |
206 | } | 209 | } |
207 | 210 | ||
208 | static int crypt_iv_essiv_gen(struct crypt_config *cc, u8 *iv, sector_t sector) | 211 | static int crypt_iv_essiv_gen(struct crypt_config *cc, u8 *iv, sector_t sector) |
209 | { | 212 | { |
210 | memset(iv, 0, cc->iv_size); | 213 | memset(iv, 0, cc->iv_size); |
211 | *(u64 *)iv = cpu_to_le64(sector); | 214 | *(u64 *)iv = cpu_to_le64(sector); |
212 | crypto_cipher_encrypt_one(cc->iv_gen_private, iv, iv); | 215 | crypto_cipher_encrypt_one(cc->iv_gen_private.essiv_tfm, iv, iv); |
213 | return 0; | 216 | return 0; |
214 | } | 217 | } |
215 | 218 | ||
@@ -232,21 +235,23 @@ static int crypt_iv_benbi_ctr(struct crypt_config *cc, struct dm_target *ti, | |||
232 | return -EINVAL; | 235 | return -EINVAL; |
233 | } | 236 | } |
234 | 237 | ||
235 | cc->iv_gen_private = (void *)(9 - log); | 238 | cc->iv_gen_private.benbi_shift = 9 - log; |
236 | 239 | ||
237 | return 0; | 240 | return 0; |
238 | } | 241 | } |
239 | 242 | ||
240 | static void crypt_iv_benbi_dtr(struct crypt_config *cc) | 243 | static void crypt_iv_benbi_dtr(struct crypt_config *cc) |
241 | { | 244 | { |
242 | cc->iv_gen_private = NULL; | ||
243 | } | 245 | } |
244 | 246 | ||
245 | static int crypt_iv_benbi_gen(struct crypt_config *cc, u8 *iv, sector_t sector) | 247 | static int crypt_iv_benbi_gen(struct crypt_config *cc, u8 *iv, sector_t sector) |
246 | { | 248 | { |
249 | __be64 val; | ||
250 | |||
247 | memset(iv, 0, cc->iv_size - sizeof(u64)); /* rest is cleared below */ | 251 | memset(iv, 0, cc->iv_size - sizeof(u64)); /* rest is cleared below */ |
248 | put_unaligned(cpu_to_be64(((u64)sector << (u32)cc->iv_gen_private) + 1), | 252 | |
249 | (__be64 *)(iv + cc->iv_size - sizeof(u64))); | 253 | val = cpu_to_be64(((u64)sector << cc->iv_gen_private.benbi_shift) + 1); |
254 | put_unaligned(val, (__be64 *)(iv + cc->iv_size - sizeof(u64))); | ||
250 | 255 | ||
251 | return 0; | 256 | return 0; |
252 | } | 257 | } |