Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

crypto: ecrdsa - Migrate to sig_alg backend

A sig_alg backend has just been introduced with the intent of moving all
asymmetric sign/verify algorithms to it one by one.

Migrate ecrdsa.c to the new backend.

One benefit of the new API is the use of kernel buffers instead of
sglists, which avoids the overhead of copying signature and digest
sglists back into kernel buffers. ecrdsa.c is thus simplified quite
a bit.

Signed-off-by: Lukas Wunner <lukas@wunner.de>
Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

authored by

Lukas Wunner and committed by
Herbert Xu
ae117924 ef132350

+28 -41
+1 -1
crypto/Kconfig
··· 302 302 config CRYPTO_ECRDSA 303 303 tristate "EC-RDSA (Elliptic Curve Russian Digital Signature Algorithm)" 304 304 select CRYPTO_ECC 305 - select CRYPTO_AKCIPHER 305 + select CRYPTO_SIG 306 306 select CRYPTO_STREEBOG 307 307 select OID_REGISTRY 308 308 select ASN1
+24 -32
crypto/ecrdsa.c
··· 18 18 19 19 #include <linux/module.h> 20 20 #include <linux/crypto.h> 21 + #include <crypto/sig.h> 21 22 #include <crypto/streebog.h> 22 - #include <crypto/internal/akcipher.h> 23 23 #include <crypto/internal/ecc.h> 24 - #include <crypto/akcipher.h> 24 + #include <crypto/internal/sig.h> 25 25 #include <linux/oid_registry.h> 26 - #include <linux/scatterlist.h> 27 26 #include "ecrdsa_params.asn1.h" 28 27 #include "ecrdsa_pub_key.asn1.h" 29 28 #include "ecrdsa_defs.h" ··· 67 68 } 68 69 } 69 70 70 - static int ecrdsa_verify(struct akcipher_request *req) 71 + static int ecrdsa_verify(struct crypto_sig *tfm, 72 + const void *src, unsigned int slen, 73 + const void *digest, unsigned int dlen) 71 74 { 72 - struct crypto_akcipher *tfm = crypto_akcipher_reqtfm(req); 73 - struct ecrdsa_ctx *ctx = akcipher_tfm_ctx(tfm); 74 - unsigned char sig[ECRDSA_MAX_SIG_SIZE]; 75 - unsigned char digest[STREEBOG512_DIGEST_SIZE]; 76 - unsigned int ndigits = req->dst_len / sizeof(u64); 75 + struct ecrdsa_ctx *ctx = crypto_sig_ctx(tfm); 76 + unsigned int ndigits = dlen / sizeof(u64); 77 77 u64 r[ECRDSA_MAX_DIGITS]; /* witness (r) */ 78 78 u64 _r[ECRDSA_MAX_DIGITS]; /* -r */ 79 79 u64 s[ECRDSA_MAX_DIGITS]; /* second part of sig (s) */ ··· 89 91 */ 90 92 if (!ctx->curve || 91 93 !ctx->digest || 92 - !req->src || 94 + !src || 95 + !digest || 93 96 !ctx->pub_key.x || 94 - req->dst_len != ctx->digest_len || 95 - req->dst_len != ctx->curve->g.ndigits * sizeof(u64) || 97 + dlen != ctx->digest_len || 98 + dlen != ctx->curve->g.ndigits * sizeof(u64) || 96 99 ctx->pub_key.ndigits != ctx->curve->g.ndigits || 97 - req->dst_len * 2 != req->src_len || 98 - WARN_ON(req->src_len > sizeof(sig)) || 99 - WARN_ON(req->dst_len > sizeof(digest))) 100 + dlen * 2 != slen || 101 + WARN_ON(slen > ECRDSA_MAX_SIG_SIZE) || 102 + WARN_ON(dlen > STREEBOG512_DIGEST_SIZE)) 100 103 return -EBADMSG; 101 104 102 - sg_copy_to_buffer(req->src, sg_nents_for_len(req->src, req->src_len), 103 - sig, req->src_len); 104 - sg_pcopy_to_buffer(req->src, 105 - sg_nents_for_len(req->src, 106 - req->src_len + req->dst_len), 107 - digest, req->dst_len, req->src_len); 108 - 109 - vli_from_be64(s, sig, ndigits); 110 - vli_from_be64(r, sig + ndigits * sizeof(u64), ndigits); 105 + vli_from_be64(s, src, ndigits); 106 + vli_from_be64(r, src + ndigits * sizeof(u64), ndigits); 111 107 112 108 /* Step 1: verify that 0 < r < q, 0 < s < q */ 113 109 if (vli_is_zero(r, ndigits) || ··· 180 188 } 181 189 182 190 /* Parse BER encoded subjectPublicKey. */ 183 - static int ecrdsa_set_pub_key(struct crypto_akcipher *tfm, const void *key, 191 + static int ecrdsa_set_pub_key(struct crypto_sig *tfm, const void *key, 184 192 unsigned int keylen) 185 193 { 186 - struct ecrdsa_ctx *ctx = akcipher_tfm_ctx(tfm); 194 + struct ecrdsa_ctx *ctx = crypto_sig_ctx(tfm); 187 195 unsigned int ndigits; 188 196 u32 algo, paramlen; 189 197 u8 *params; ··· 241 249 return 0; 242 250 } 243 251 244 - static unsigned int ecrdsa_max_size(struct crypto_akcipher *tfm) 252 + static unsigned int ecrdsa_max_size(struct crypto_sig *tfm) 245 253 { 246 - struct ecrdsa_ctx *ctx = akcipher_tfm_ctx(tfm); 254 + struct ecrdsa_ctx *ctx = crypto_sig_ctx(tfm); 247 255 248 256 /* 249 257 * Verify doesn't need any output, so it's just informational ··· 252 260 return ctx->pub_key.ndigits * sizeof(u64); 253 261 } 254 262 255 - static void ecrdsa_exit_tfm(struct crypto_akcipher *tfm) 263 + static void ecrdsa_exit_tfm(struct crypto_sig *tfm) 256 264 { 257 265 } 258 266 259 - static struct akcipher_alg ecrdsa_alg = { 267 + static struct sig_alg ecrdsa_alg = { 260 268 .verify = ecrdsa_verify, 261 269 .set_pub_key = ecrdsa_set_pub_key, 262 270 .max_size = ecrdsa_max_size, ··· 272 280 273 281 static int __init ecrdsa_mod_init(void) 274 282 { 275 - return crypto_register_akcipher(&ecrdsa_alg); 283 + return crypto_register_sig(&ecrdsa_alg); 276 284 } 277 285 278 286 static void __exit ecrdsa_mod_fini(void) 279 287 { 280 - crypto_unregister_akcipher(&ecrdsa_alg); 288 + crypto_unregister_sig(&ecrdsa_alg); 281 289 } 282 290 283 291 module_init(ecrdsa_mod_init);
+2 -2
crypto/testmgr.c
··· 5268 5268 } 5269 5269 }, { 5270 5270 .alg = "ecrdsa", 5271 - .test = alg_test_akcipher, 5271 + .test = alg_test_sig, 5272 5272 .suite = { 5273 - .akcipher = __VECS(ecrdsa_tv_template) 5273 + .sig = __VECS(ecrdsa_tv_template) 5274 5274 } 5275 5275 }, { 5276 5276 .alg = "essiv(authenc(hmac(sha256),cbc(aes)),sha256)",
+1 -6
crypto/testmgr.h
··· 1119 1119 /* 1120 1120 * EC-RDSA test vectors are generated by gost-engine. 1121 1121 */ 1122 - static const struct akcipher_testvec ecrdsa_tv_template[] = { 1122 + static const struct sig_testvec ecrdsa_tv_template[] = { 1123 1123 { 1124 1124 .key = 1125 1125 "\x04\x40\xd5\xa7\x77\xf9\x26\x2f\x8c\xbd\xcc\xe3\x1f\x01\x94\x05" ··· 1144 1144 "\x79\xd2\x76\x64\xa3\xbd\x66\x10\x79\x05\x5a\x06\x42\xec\xb9\xc9", 1145 1145 .m_size = 32, 1146 1146 .public_key_vec = true, 1147 - .siggen_sigver_test = true, 1148 1147 }, 1149 1148 { 1150 1149 .key = ··· 1169 1170 "\x11\x23\x4a\x70\x43\x52\x7a\x68\x11\x65\x45\x37\xbb\x25\xb7\x40", 1170 1171 .m_size = 32, 1171 1172 .public_key_vec = true, 1172 - .siggen_sigver_test = true, 1173 1173 }, 1174 1174 { 1175 1175 .key = ··· 1194 1196 "\x9f\x16\xc6\x1c\xb1\x3f\x84\x41\x69\xec\x34\xfd\xf1\xf9\xa3\x39", 1195 1197 .m_size = 32, 1196 1198 .public_key_vec = true, 1197 - .siggen_sigver_test = true, 1198 1199 }, 1199 1200 { 1200 1201 .key = ··· 1228 1231 "\xa8\xf6\x80\x01\xb9\x27\xac\xd8\x45\x96\x66\xa1\xee\x48\x08\x3f", 1229 1232 .m_size = 64, 1230 1233 .public_key_vec = true, 1231 - .siggen_sigver_test = true, 1232 1234 }, 1233 1235 { 1234 1236 .key = ··· 1262 1266 "\x6d\xf4\xd2\x45\xc2\x83\xa0\x42\x95\x05\x9d\x89\x8e\x0a\xca\xcc", 1263 1267 .m_size = 64, 1264 1268 .public_key_vec = true, 1265 - .siggen_sigver_test = true, 1266 1269 }, 1267 1270 }; 1268 1271