aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--crypto/algapi.c6
-rw-r--r--crypto/api.c39
-rw-r--r--crypto/cryptomgr.c7
-rw-r--r--crypto/internal.h6
4 files changed, 40 insertions, 18 deletions
diff --git a/crypto/algapi.c b/crypto/algapi.c
index f0df85fc1f50..acea250677c0 100644
--- a/crypto/algapi.c
+++ b/crypto/algapi.c
@@ -21,12 +21,12 @@
21 21
22static LIST_HEAD(crypto_template_list); 22static LIST_HEAD(crypto_template_list);
23 23
24void crypto_larval_error(const char *name) 24void crypto_larval_error(const char *name, u32 type, u32 mask)
25{ 25{
26 struct crypto_alg *alg; 26 struct crypto_alg *alg;
27 27
28 down_read(&crypto_alg_sem); 28 down_read(&crypto_alg_sem);
29 alg = __crypto_alg_lookup(name); 29 alg = __crypto_alg_lookup(name, type, mask);
30 up_read(&crypto_alg_sem); 30 up_read(&crypto_alg_sem);
31 31
32 if (alg) { 32 if (alg) {
@@ -87,6 +87,8 @@ static int __crypto_register_alg(struct crypto_alg *alg)
87 !strcmp(alg->cra_driver_name, q->cra_name))) { 87 !strcmp(alg->cra_driver_name, q->cra_name))) {
88 struct crypto_larval *larval = (void *)q; 88 struct crypto_larval *larval = (void *)q;
89 89
90 if ((q->cra_flags ^ alg->cra_flags) & larval->mask)
91 continue;
90 if (!crypto_mod_get(alg)) 92 if (!crypto_mod_get(alg))
91 continue; 93 continue;
92 larval->adult = alg; 94 larval->adult = alg;
diff --git a/crypto/api.c b/crypto/api.c
index 67cd6f87b74a..ddf6a767acdd 100644
--- a/crypto/api.c
+++ b/crypto/api.c
@@ -57,7 +57,7 @@ void crypto_mod_put(struct crypto_alg *alg)
57} 57}
58EXPORT_SYMBOL_GPL(crypto_mod_put); 58EXPORT_SYMBOL_GPL(crypto_mod_put);
59 59
60struct crypto_alg *__crypto_alg_lookup(const char *name) 60struct crypto_alg *__crypto_alg_lookup(const char *name, u32 type, u32 mask)
61{ 61{
62 struct crypto_alg *q, *alg = NULL; 62 struct crypto_alg *q, *alg = NULL;
63 int best = -2; 63 int best = -2;
@@ -65,6 +65,13 @@ struct crypto_alg *__crypto_alg_lookup(const char *name)
65 list_for_each_entry(q, &crypto_alg_list, cra_list) { 65 list_for_each_entry(q, &crypto_alg_list, cra_list) {
66 int exact, fuzzy; 66 int exact, fuzzy;
67 67
68 if ((q->cra_flags ^ type) & mask)
69 continue;
70
71 if (crypto_is_larval(q) &&
72 ((struct crypto_larval *)q)->mask != mask)
73 continue;
74
68 exact = !strcmp(q->cra_driver_name, name); 75 exact = !strcmp(q->cra_driver_name, name);
69 fuzzy = !strcmp(q->cra_name, name); 76 fuzzy = !strcmp(q->cra_name, name);
70 if (!exact && !(fuzzy && q->cra_priority > best)) 77 if (!exact && !(fuzzy && q->cra_priority > best))
@@ -96,7 +103,8 @@ static void crypto_larval_destroy(struct crypto_alg *alg)
96 kfree(larval); 103 kfree(larval);
97} 104}
98 105
99static struct crypto_alg *crypto_larval_alloc(const char *name) 106static struct crypto_alg *crypto_larval_alloc(const char *name, u32 type,
107 u32 mask)
100{ 108{
101 struct crypto_alg *alg; 109 struct crypto_alg *alg;
102 struct crypto_larval *larval; 110 struct crypto_larval *larval;
@@ -105,7 +113,8 @@ static struct crypto_alg *crypto_larval_alloc(const char *name)
105 if (!larval) 113 if (!larval)
106 return NULL; 114 return NULL;
107 115
108 larval->alg.cra_flags = CRYPTO_ALG_LARVAL; 116 larval->mask = mask;
117 larval->alg.cra_flags = CRYPTO_ALG_LARVAL | type;
109 larval->alg.cra_priority = -1; 118 larval->alg.cra_priority = -1;
110 larval->alg.cra_destroy = crypto_larval_destroy; 119 larval->alg.cra_destroy = crypto_larval_destroy;
111 120
@@ -114,7 +123,7 @@ static struct crypto_alg *crypto_larval_alloc(const char *name)
114 init_completion(&larval->completion); 123 init_completion(&larval->completion);
115 124
116 down_write(&crypto_alg_sem); 125 down_write(&crypto_alg_sem);
117 alg = __crypto_alg_lookup(name); 126 alg = __crypto_alg_lookup(name, type, mask);
118 if (!alg) { 127 if (!alg) {
119 alg = &larval->alg; 128 alg = &larval->alg;
120 list_add(&alg->cra_list, &crypto_alg_list); 129 list_add(&alg->cra_list, &crypto_alg_list);
@@ -151,7 +160,8 @@ static struct crypto_alg *crypto_larval_wait(struct crypto_alg *alg)
151 return alg; 160 return alg;
152} 161}
153 162
154static struct crypto_alg *crypto_alg_lookup(const char *name) 163static struct crypto_alg *crypto_alg_lookup(const char *name, u32 type,
164 u32 mask)
155{ 165{
156 struct crypto_alg *alg; 166 struct crypto_alg *alg;
157 167
@@ -159,25 +169,27 @@ static struct crypto_alg *crypto_alg_lookup(const char *name)
159 return NULL; 169 return NULL;
160 170
161 down_read(&crypto_alg_sem); 171 down_read(&crypto_alg_sem);
162 alg = __crypto_alg_lookup(name); 172 alg = __crypto_alg_lookup(name, type, mask);
163 up_read(&crypto_alg_sem); 173 up_read(&crypto_alg_sem);
164 174
165 return alg; 175 return alg;
166} 176}
167 177
168/* A far more intelligent version of this is planned. For now, just 178struct crypto_alg *crypto_alg_mod_lookup(const char *name, u32 type, u32 mask)
169 * try an exact match on the name of the algorithm. */
170static struct crypto_alg *crypto_alg_mod_lookup(const char *name)
171{ 179{
172 struct crypto_alg *alg; 180 struct crypto_alg *alg;
173 struct crypto_alg *larval; 181 struct crypto_alg *larval;
174 int ok; 182 int ok;
175 183
176 alg = try_then_request_module(crypto_alg_lookup(name), name); 184 mask &= ~CRYPTO_ALG_LARVAL;
185 type &= mask;
186
187 alg = try_then_request_module(crypto_alg_lookup(name, type, mask),
188 name);
177 if (alg) 189 if (alg)
178 return crypto_is_larval(alg) ? crypto_larval_wait(alg) : alg; 190 return crypto_is_larval(alg) ? crypto_larval_wait(alg) : alg;
179 191
180 larval = crypto_larval_alloc(name); 192 larval = crypto_larval_alloc(name, type, mask);
181 if (!larval || !crypto_is_larval(larval)) 193 if (!larval || !crypto_is_larval(larval))
182 return larval; 194 return larval;
183 195
@@ -196,6 +208,7 @@ static struct crypto_alg *crypto_alg_mod_lookup(const char *name)
196 crypto_larval_kill(larval); 208 crypto_larval_kill(larval);
197 return alg; 209 return alg;
198} 210}
211EXPORT_SYMBOL_GPL(crypto_alg_mod_lookup);
199 212
200static int crypto_init_flags(struct crypto_tfm *tfm, u32 flags) 213static int crypto_init_flags(struct crypto_tfm *tfm, u32 flags)
201{ 214{
@@ -291,7 +304,7 @@ struct crypto_tfm *crypto_alloc_tfm(const char *name, u32 flags)
291 struct crypto_alg *alg; 304 struct crypto_alg *alg;
292 unsigned int tfm_size; 305 unsigned int tfm_size;
293 306
294 alg = crypto_alg_mod_lookup(name); 307 alg = crypto_alg_mod_lookup(name, 0, 0);
295 if (alg == NULL) 308 if (alg == NULL)
296 goto out; 309 goto out;
297 310
@@ -346,7 +359,7 @@ void crypto_free_tfm(struct crypto_tfm *tfm)
346int crypto_alg_available(const char *name, u32 flags) 359int crypto_alg_available(const char *name, u32 flags)
347{ 360{
348 int ret = 0; 361 int ret = 0;
349 struct crypto_alg *alg = crypto_alg_mod_lookup(name); 362 struct crypto_alg *alg = crypto_alg_mod_lookup(name, 0, 0);
350 363
351 if (alg) { 364 if (alg) {
352 crypto_mod_put(alg); 365 crypto_mod_put(alg);
diff --git a/crypto/cryptomgr.c b/crypto/cryptomgr.c
index e0ebe1b44b99..ae54942e3b31 100644
--- a/crypto/cryptomgr.c
+++ b/crypto/cryptomgr.c
@@ -31,6 +31,8 @@ struct cryptomgr_param {
31 } alg; 31 } alg;
32 32
33 struct { 33 struct {
34 u32 type;
35 u32 mask;
34 char name[CRYPTO_MAX_ALG_NAME]; 36 char name[CRYPTO_MAX_ALG_NAME];
35 } larval; 37 } larval;
36 38
@@ -62,7 +64,8 @@ out:
62 return; 64 return;
63 65
64err: 66err:
65 crypto_larval_error(param->larval.name); 67 crypto_larval_error(param->larval.name, param->larval.type,
68 param->larval.mask);
66 goto out; 69 goto out;
67} 70}
68 71
@@ -101,6 +104,8 @@ static int cryptomgr_schedule_probe(struct crypto_larval *larval)
101 param->alg.data.name[len] = 0; 104 param->alg.data.name[len] = 0;
102 105
103 memcpy(param->larval.name, larval->alg.cra_name, CRYPTO_MAX_ALG_NAME); 106 memcpy(param->larval.name, larval->alg.cra_name, CRYPTO_MAX_ALG_NAME);
107 param->larval.type = larval->alg.cra_flags;
108 param->larval.mask = larval->mask;
104 109
105 INIT_WORK(&param->work, cryptomgr_probe, param); 110 INIT_WORK(&param->work, cryptomgr_probe, param);
106 schedule_work(&param->work); 111 schedule_work(&param->work);
diff --git a/crypto/internal.h b/crypto/internal.h
index 3a08d25fba45..c08d93bdadc4 100644
--- a/crypto/internal.h
+++ b/crypto/internal.h
@@ -43,6 +43,7 @@ struct crypto_larval {
43 struct crypto_alg alg; 43 struct crypto_alg alg;
44 struct crypto_alg *adult; 44 struct crypto_alg *adult;
45 struct completion completion; 45 struct completion completion;
46 u32 mask;
46}; 47};
47 48
48extern struct list_head crypto_alg_list; 49extern struct list_head crypto_alg_list;
@@ -124,7 +125,8 @@ static inline unsigned int crypto_compress_ctxsize(struct crypto_alg *alg,
124 125
125struct crypto_alg *crypto_mod_get(struct crypto_alg *alg); 126struct crypto_alg *crypto_mod_get(struct crypto_alg *alg);
126void crypto_mod_put(struct crypto_alg *alg); 127void crypto_mod_put(struct crypto_alg *alg);
127struct crypto_alg *__crypto_alg_lookup(const char *name); 128struct crypto_alg *__crypto_alg_lookup(const char *name, u32 type, u32 mask);
129struct crypto_alg *crypto_alg_mod_lookup(const char *name, u32 type, u32 mask);
128 130
129int crypto_init_digest_flags(struct crypto_tfm *tfm, u32 flags); 131int crypto_init_digest_flags(struct crypto_tfm *tfm, u32 flags);
130int crypto_init_cipher_flags(struct crypto_tfm *tfm, u32 flags); 132int crypto_init_cipher_flags(struct crypto_tfm *tfm, u32 flags);
@@ -138,7 +140,7 @@ void crypto_exit_digest_ops(struct crypto_tfm *tfm);
138void crypto_exit_cipher_ops(struct crypto_tfm *tfm); 140void crypto_exit_cipher_ops(struct crypto_tfm *tfm);
139void crypto_exit_compress_ops(struct crypto_tfm *tfm); 141void crypto_exit_compress_ops(struct crypto_tfm *tfm);
140 142
141void crypto_larval_error(const char *name); 143void crypto_larval_error(const char *name, u32 type, u32 mask);
142 144
143int crypto_register_instance(struct crypto_template *tmpl, 145int crypto_register_instance(struct crypto_template *tmpl,
144 struct crypto_instance *inst); 146 struct crypto_instance *inst);