]> git.ipfire.org Git - thirdparty/ipxe.git/commitdiff
[crypto] Use private data field for public-key algorithms master
authorMichael Brown <mcb30@ipxe.org>
Fri, 19 Jun 2026 13:53:03 +0000 (14:53 +0100)
committerMichael Brown <mcb30@ipxe.org>
Fri, 19 Jun 2026 13:54:03 +0000 (14:54 +0100)
Following the example of commit 25072c1 ("[crypto] Use private data
field for key exchange algorithms"), extend the definition of a
public-key algorithm to include an opaque private data field, and use
this to eliminate the wrapper functions for PKCS#1 and RSA-PSS.

Signed-off-by: Michael Brown <mcb30@ipxe.org>
src/crypto/crypto_null.c
src/crypto/ecdsa.c
src/crypto/rsa.c
src/include/ipxe/crypto.h

index a8d4519f80f11d96b29a7b19ed2e5823ee4847b3..d0f6a1a99ce964c94a3dfce102930d2d5f2d8aeb 100644 (file)
@@ -104,36 +104,47 @@ struct cipher_algorithm cipher_null = {
        .auth = cipher_null_auth,
 };
 
-int pubkey_null_encrypt ( const struct asn1_cursor *key __unused,
+int pubkey_null_encrypt ( struct pubkey_algorithm *pubkey __unused,
+                         const struct asn1_cursor *key __unused,
                          const struct asn1_cursor *plaintext __unused,
                          struct asn1_builder *ciphertext __unused ) {
        return -ENOTTY;
 }
 
-int pubkey_null_decrypt ( const struct asn1_cursor *key __unused,
+int pubkey_null_decrypt ( struct pubkey_algorithm *pubkey __unused,
+                         const struct asn1_cursor *key __unused,
                          const struct asn1_cursor *ciphertext __unused,
                          struct asn1_builder *plaintext __unused ) {
        return -ENOTTY;
 }
 
-int pubkey_null_sign ( const struct asn1_cursor *key __unused,
+int pubkey_null_sign ( struct pubkey_algorithm *pubkey __unused,
+                      const struct asn1_cursor *key __unused,
                       struct digest_algorithm *digest __unused,
                       const void *value __unused,
                       struct asn1_builder *signature __unused ) {
        return -ENOTTY;
 }
 
-int pubkey_null_verify ( const struct asn1_cursor *key __unused,
+int pubkey_null_verify ( struct pubkey_algorithm *pubkey __unused,
+                        const struct asn1_cursor *key __unused,
                         struct digest_algorithm *digest __unused,
                         const void *value __unused,
                         const struct asn1_cursor *signature __unused ) {
        return -ENOTTY;
 }
 
+int pubkey_null_match ( struct pubkey_algorithm *pubkey __unused,
+                       const struct asn1_cursor *private_key __unused,
+                       const struct asn1_cursor *public_key __unused ) {
+       return -ENOTTY;
+}
+
 struct pubkey_algorithm pubkey_null = {
        .name = "null",
        .encrypt = pubkey_null_encrypt,
        .decrypt = pubkey_null_decrypt,
        .sign = pubkey_null_sign,
        .verify = pubkey_null_verify,
+       .match = pubkey_null_match,
 };
index 5be4b4b21599e20cd41b3b87a7dd600a5995d79f..364d8d66e4537fe2873702aa1a102a33ff8b5813 100644 (file)
@@ -768,13 +768,15 @@ static int ecdsa_verify_rs ( struct ecdsa_context *ctx ) {
 /**
  * Sign digest value using ECDSA
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v digest           Digest algorithm
  * @v value            Digest value
  * @v signature                Signature
  * @ret rc             Return status code
  */
-static int ecdsa_sign ( const struct asn1_cursor *key,
+static int ecdsa_sign ( struct pubkey_algorithm *pubkey __unused,
+                       const struct asn1_cursor *key,
                        struct digest_algorithm *digest, const void *value,
                        struct asn1_builder *signature ) {
        struct ecdsa_context ctx;
@@ -824,13 +826,15 @@ static int ecdsa_sign ( const struct asn1_cursor *key,
 /**
  * Verify signed digest using ECDSA
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v digest           Digest algorithm
  * @v value            Digest value
  * @v signature                Signature
  * @ret rc             Return status code
  */
-static int ecdsa_verify ( const struct asn1_cursor *key,
+static int ecdsa_verify ( struct pubkey_algorithm *pubkey __unused,
+                         const struct asn1_cursor *key,
                          struct digest_algorithm *digest, const void *value,
                          const struct asn1_cursor *signature ) {
        struct ecdsa_context ctx;
@@ -872,30 +876,32 @@ static int ecdsa_verify ( const struct asn1_cursor *key,
 /**
  * Check for matching ECDSA public/private key pair
  *
+ * @v pubkey           Public-key algorithm
  * @v private_key      Private key
  * @v public_key       Public key
  * @ret rc             Return status code
  */
-static int ecdsa_match ( const struct asn1_cursor *private_key,
+static int ecdsa_match ( struct pubkey_algorithm *pubkey __unused,
+                        const struct asn1_cursor *private_key,
                         const struct asn1_cursor *public_key ) {
        struct elliptic_curve *curve;
-       struct ecdsa_key privkey;
-       struct ecdsa_key pubkey;
+       struct ecdsa_key private;
+       struct ecdsa_key public;
        int rc;
 
        /* Parse keys */
-       if ( ( rc = ecdsa_parse_key ( &privkey, private_key ) ) != 0 )
+       if ( ( rc = ecdsa_parse_key ( &private, private_key ) ) != 0 )
                return rc;
-       if ( ( rc = ecdsa_parse_key ( &pubkey, public_key ) ) != 0 )
+       if ( ( rc = ecdsa_parse_key ( &public, public_key ) ) != 0 )
                return rc;
 
        /* Compare curves */
-       if ( privkey.curve != pubkey.curve )
+       if ( private.curve != public.curve )
                return -ENOTTY;
-       curve = privkey.curve;
+       curve = private.curve;
 
        /* Compare public curve points */
-       if ( memcmp ( privkey.public, pubkey.public, curve->pointsize ) != 0 )
+       if ( memcmp ( private.public, public.public, curve->pointsize ) != 0 )
                return -ENOTTY;
 
        return 0;
index e62eb02a4c50330e44c3eab25f0778fa3b03a6e6..9454b29ba460c3cc932bb30df6b6ee3896e9110e 100644 (file)
@@ -323,12 +323,14 @@ static void rsa_cipher ( struct rsa_context *context,
 /**
  * Encrypt using RSA PKCS#1
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v plaintext                Plaintext
  * @v ciphertext       Ciphertext
  * @ret ciphertext_len Length of ciphertext, or negative error
  */
-static int rsa_pkcs1_encrypt ( const struct asn1_cursor *key,
+static int rsa_pkcs1_encrypt ( struct pubkey_algorithm *pubkey __unused,
+                              const struct asn1_cursor *key,
                               const struct asn1_cursor *plaintext,
                               struct asn1_builder *ciphertext ) {
        struct rsa_context context;
@@ -400,12 +402,14 @@ static int rsa_pkcs1_encrypt ( const struct asn1_cursor *key,
 /**
  * Decrypt using RSA PKCS#1
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v ciphertext       Ciphertext
  * @v plaintext                Plaintext
  * @ret rc             Return status code
  */
-static int rsa_pkcs1_decrypt ( const struct asn1_cursor *key,
+static int rsa_pkcs1_decrypt ( struct pubkey_algorithm *pubkey __unused,
+                              const struct asn1_cursor *key,
                               const struct asn1_cursor *ciphertext,
                               struct asn1_builder *plaintext ) {
        struct rsa_context context;
@@ -667,16 +671,18 @@ static int rsa_pss_encode ( struct rsa_context *context,
 /**
  * Sign digest value using RSA
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v digest           Digest algorithm
  * @v value            Digest value
  * @v signature                Signature
- * @v encode           Encoding method
  * @ret rc             Return status code
  */
-static int rsa_sign ( const struct asn1_cursor *key,
+static int rsa_sign ( struct pubkey_algorithm *pubkey,
+                     const struct asn1_cursor *key,
                      struct digest_algorithm *digest, const void *value,
-                     struct asn1_builder *signature, rsa_encode_t *encode ) {
+                     struct asn1_builder *signature ) {
+       rsa_encode_t *encode = pubkey->priv;
        struct rsa_context context;
        int rc;
 
@@ -717,17 +723,18 @@ static int rsa_sign ( const struct asn1_cursor *key,
 /**
  * Verify signed digest value using RSA
  *
+ * @v pubkey           Public-key algorithm
  * @v key              Key
  * @v digest           Digest algorithm
  * @v value            Digest value
  * @v signature                Signature
- * @v encoding         Encoding method
  * @ret rc             Return status code
  */
-static int rsa_verify ( const struct asn1_cursor *key,
+static int rsa_verify ( struct pubkey_algorithm *pubkey,
+                       const struct asn1_cursor *key,
                        struct digest_algorithm *digest, const void *value,
-                       const struct asn1_cursor *signature,
-                       rsa_encode_t *encode ) {
+                       const struct asn1_cursor *signature ) {
+       rsa_encode_t *encode = pubkey->priv;
        struct rsa_context context;
        void *temp;
        void *expected;
@@ -792,79 +799,16 @@ static int rsa_verify ( const struct asn1_cursor *key,
        return rc;
 }
 
-/**
- * Sign digest value using RSA PKCS#1
- *
- * @v key              Key
- * @v digest           Digest algorithm
- * @v value            Digest value
- * @v signature                Signature
- * @ret rc             Return status code
- */
-static int rsa_pkcs1_sign ( const struct asn1_cursor *key,
-                           struct digest_algorithm *digest, const void *value,
-                           struct asn1_builder *signature ) {
-
-       return rsa_sign ( key, digest, value, signature, rsa_pkcs1_encode );
-}
-
-/**
- * Verify signed digest value using RSA PKCS#1
- *
- * @v key              Key
- * @v digest           Digest algorithm
- * @v value            Digest value
- * @v signature                Signature
- * @ret rc             Return status code
- */
-static int rsa_pkcs1_verify ( const struct asn1_cursor *key,
-                             struct digest_algorithm *digest,
-                             const void *value,
-                             const struct asn1_cursor *signature ) {
-
-       return rsa_verify ( key, digest, value, signature, rsa_pkcs1_encode );
-}
-
-/**
- * Sign digest value using RSA PSS
- *
- * @v key              Key
- * @v digest           Digest algorithm
- * @v value            Digest value
- * @v signature                Signature
- * @ret rc             Return status code
- */
-static int rsa_pss_sign ( const struct asn1_cursor *key,
-                         struct digest_algorithm *digest, const void *value,
-                         struct asn1_builder *signature ) {
-
-       return rsa_sign ( key, digest, value, signature, rsa_pss_encode );
-}
-
-/**
- * Verify signed digest value using RSA PSS
- *
- * @v key              Key
- * @v digest           Digest algorithm
- * @v value            Digest value
- * @v signature                Signature
- * @ret rc             Return status code
- */
-static int rsa_pss_verify ( const struct asn1_cursor *key,
-                           struct digest_algorithm *digest, const void *value,
-                           const struct asn1_cursor *signature ) {
-
-       return rsa_verify ( key, digest, value, signature, rsa_pss_encode );
-}
-
 /**
  * Check for matching RSA public/private key pair
  *
+ * @v pubkey           Public-key algorithm
  * @v private_key      Private key
  * @v public_key       Public key
  * @ret rc             Return status code
  */
-static int rsa_match ( const struct asn1_cursor *private_key,
+static int rsa_match ( struct pubkey_algorithm *pubkey __unused,
+                      const struct asn1_cursor *private_key,
                       const struct asn1_cursor *public_key ) {
        struct asn1_cursor private_modulus;
        struct asn1_cursor private_exponent;
@@ -892,9 +836,10 @@ struct pubkey_algorithm rsa_algorithm = {
        .name           = "rsa",
        .encrypt        = rsa_pkcs1_encrypt,
        .decrypt        = rsa_pkcs1_decrypt,
-       .sign           = rsa_pkcs1_sign,
-       .verify         = rsa_pkcs1_verify,
+       .sign           = rsa_sign,
+       .verify         = rsa_verify,
        .match          = rsa_match,
+       .priv           = rsa_pkcs1_encode,
 };
 
 /** RSA-PSS public-key algorithm */
@@ -902,9 +847,10 @@ struct pubkey_algorithm rsa_pss_algorithm = {
        .name           = "rsa_pss",
        .encrypt        = pubkey_null_encrypt,
        .decrypt        = pubkey_null_decrypt,
-       .sign           = rsa_pss_sign,
-       .verify         = rsa_pss_verify,
+       .sign           = rsa_sign,
+       .verify         = rsa_verify,
        .match          = rsa_match,
+       .priv           = rsa_pss_encode,
 };
 
 /* Drag in objects via rsa_algorithm */
index d2e0d18db711ccd2077d4c48053db4d64cc9f365..2ee3794c7c348eeffd4197183e50007300b49ffc 100644 (file)
@@ -142,54 +142,66 @@ struct pubkey_algorithm {
        const char *name;
        /** Encrypt
         *
+        * @v pubkey            Public key algorithm
         * @v key               Key
         * @v plaintext         Plaintext
         * @v ciphertext        Ciphertext
         * @ret rc              Return status code
         */
-       int ( * encrypt ) ( const struct asn1_cursor *key,
+       int ( * encrypt ) ( struct pubkey_algorithm *pubkey,
+                           const struct asn1_cursor *key,
                            const struct asn1_cursor *plaintext,
                            struct asn1_builder *ciphertext );
        /** Decrypt
         *
+        * @v pubkey            Public key algorithm
         * @v key               Key
         * @v ciphertext        Ciphertext
         * @v plaintext         Plaintext
         * @ret rc              Return status code
         */
-       int ( * decrypt ) ( const struct asn1_cursor *key,
+       int ( * decrypt ) ( struct pubkey_algorithm *pubkey,
+                           const struct asn1_cursor *key,
                            const struct asn1_cursor *ciphertext,
                            struct asn1_builder *plaintext );
        /** Sign digest value
         *
+        * @v pubkey            Public key algorithm
         * @v key               Key
         * @v digest            Digest algorithm
         * @v value             Digest value
         * @v signature         Signature
         * @ret rc              Return status code
         */
-       int ( * sign ) ( const struct asn1_cursor *key,
+       int ( * sign ) ( struct pubkey_algorithm *pubkey,
+                        const struct asn1_cursor *key,
                         struct digest_algorithm *digest, const void *value,
                         struct asn1_builder *builder );
        /** Verify signed digest value
         *
+        * @v pubkey            Public key algorithm
         * @v key               Key
         * @v digest            Digest algorithm
         * @v value             Digest value
         * @v signature         Signature
         * @ret rc              Return status code
         */
-       int ( * verify ) ( const struct asn1_cursor *key,
+       int ( * verify ) ( struct pubkey_algorithm *pubkey,
+                          const struct asn1_cursor *key,
                           struct digest_algorithm *digest, const void *value,
                           const struct asn1_cursor *signature );
        /** Check that public key matches private key
         *
+        * @v pubkey            Public key algorithm
         * @v private_key       Private key
         * @v public_key        Public key
         * @ret rc              Return status code
         */
-       int ( * match ) ( const struct asn1_cursor *private_key,
+       int ( * match ) ( struct pubkey_algorithm *pubkey,
+                         const struct asn1_cursor *private_key,
                          const struct asn1_cursor *public_key );
+       /** Algorithm private data */
+       void *priv;
 };
 
 /** A key exchange algorithm */
@@ -347,35 +359,35 @@ static inline __attribute__ (( always_inline )) int
 pubkey_encrypt ( struct pubkey_algorithm *pubkey, const struct asn1_cursor *key,
                 const struct asn1_cursor *plaintext,
                 struct asn1_builder *ciphertext ) {
-       return pubkey->encrypt ( key, plaintext, ciphertext );
+       return pubkey->encrypt ( pubkey, key, plaintext, ciphertext );
 }
 
 static inline __attribute__ (( always_inline )) int
 pubkey_decrypt ( struct pubkey_algorithm *pubkey, const struct asn1_cursor *key,
                 const struct asn1_cursor *ciphertext,
                 struct asn1_builder *plaintext ) {
-       return pubkey->decrypt ( key, ciphertext, plaintext );
+       return pubkey->decrypt ( pubkey, key, ciphertext, plaintext );
 }
 
 static inline __attribute__ (( always_inline )) int
 pubkey_sign ( struct pubkey_algorithm *pubkey, const struct asn1_cursor *key,
              struct digest_algorithm *digest, const void *value,
              struct asn1_builder *signature ) {
-       return pubkey->sign ( key, digest, value, signature );
+       return pubkey->sign ( pubkey, key, digest, value, signature );
 }
 
 static inline __attribute__ (( always_inline )) int
 pubkey_verify ( struct pubkey_algorithm *pubkey, const struct asn1_cursor *key,
                struct digest_algorithm *digest, const void *value,
                const struct asn1_cursor *signature ) {
-       return pubkey->verify ( key, digest, value, signature );
+       return pubkey->verify ( pubkey, key, digest, value, signature );
 }
 
 static inline __attribute__ (( always_inline )) int
 pubkey_match ( struct pubkey_algorithm *pubkey,
               const struct asn1_cursor *private_key,
               const struct asn1_cursor *public_key ) {
-       return pubkey->match ( private_key, public_key );
+       return pubkey->match ( pubkey, private_key, public_key );
 }
 
 static inline __attribute__ (( always_inline )) void
@@ -424,20 +436,27 @@ extern void cipher_null_decrypt ( struct cipher_algorithm *cipher, void *ctx,
 extern void cipher_null_auth ( struct cipher_algorithm *cipher, void *ctx,
                               void *auth );
 
-extern int pubkey_null_encrypt ( const struct asn1_cursor *key,
+extern int pubkey_null_encrypt ( struct pubkey_algorithm *pubkey,
+                                const struct asn1_cursor *key,
                                 const struct asn1_cursor *plaintext,
                                 struct asn1_builder *ciphertext );
-extern int pubkey_null_decrypt ( const struct asn1_cursor *key,
+extern int pubkey_null_decrypt ( struct pubkey_algorithm *pubkey,
+                                const struct asn1_cursor *key,
                                 const struct asn1_cursor *ciphertext,
                                 struct asn1_builder *plaintext );
-extern int pubkey_null_sign ( const struct asn1_cursor *key,
+extern int pubkey_null_sign ( struct pubkey_algorithm *pubkey,
+                             const struct asn1_cursor *key,
                              struct digest_algorithm *digest,
                              const void *value,
                              struct asn1_builder *signature );
-extern int pubkey_null_verify ( const struct asn1_cursor *key,
+extern int pubkey_null_verify ( struct pubkey_algorithm *pubkey,
+                               const struct asn1_cursor *key,
                                struct digest_algorithm *digest,
                                const void *value,
                                const struct asn1_cursor *signature );
+extern int pubkey_null_match ( struct pubkey_algorithm *pubkey,
+                              const struct asn1_cursor *private_key,
+                              const struct asn1_cursor *public_key );
 
 extern struct digest_algorithm digest_null;
 extern struct cipher_algorithm cipher_null;