tolerate broken CMS/PKCS7 implementations using signature OID instead of digest
[oweals/openssl.git] / crypto / engine / eng_cryptodev.c
index be7ed6bb3f808c036859a1c5e4fd11a3e8d17fcb..1a1e1c2655ac8a06e9428738c034394d79860ed9 100644 (file)
@@ -12,9 +12,6 @@
  * 2. Redistributions in binary form must reproduce the above copyright
  *    notice, this list of conditions and the following disclaimer in the
  *    documentation and/or other materials provided with the distribution.
- * 3. Neither the name of the author nor the names of contributors
- *    may be used to endorse or promote products derived from this software
- *    without specific prior written permission.
  *
  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY
  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 #include <openssl/objects.h>
 #include <openssl/engine.h>
 #include <openssl/evp.h>
-
-#ifndef __OpenBSD__
-
-void
-ENGINE_load_cryptodev(void)
-{
-       /* This is a NOP unless __OpenBSD__ is defined */
-       return;
-}
-
-#else /* __OpenBSD__ */
-
-#include <sys/types.h>
+#include <openssl/bn.h>
+#include <openssl/dsa.h>
+#include <openssl/rsa.h>
+#include <openssl/dh.h>
+#include <openssl/err.h>
+
+#if (defined(__unix__) || defined(unix)) && !defined(USG) && \
+       (defined(OpenBSD) || defined(__FreeBSD__))
 #include <sys/param.h>
+# if (OpenBSD >= 200112) || ((__FreeBSD_version >= 470101 && __FreeBSD_version < 500000) || __FreeBSD_version >= 500041)
+#  define HAVE_CRYPTODEV
+# endif
+# if (OpenBSD >= 200110)
+#  define HAVE_SYSLOG_R
+# endif
+#endif
 
-#if OpenBSD < 200112
+#ifndef HAVE_CRYPTODEV
 
 void
 ENGINE_load_cryptodev(void)
 {
-       /* This is a NOP unless we have release 3.0 (released december 2001) */
+       /* This is a NOP on platforms without /dev/crypto */
        return;
 }
 
-#else /* OpenBSD 3.0 or above */
-
+#else 
+#include <sys/types.h>
 #include <crypto/cryptodev.h>
 #include <sys/ioctl.h>
 #include <errno.h>
@@ -83,7 +83,7 @@ static int cryptodev_max_iv(int cipher);
 static int cryptodev_key_length_valid(int cipher, int len);
 static int cipher_nid_to_cryptodev(int nid);
 static int get_cryptodev_ciphers(const int **cnids);
-static int get_cryptodev_digests(const int **cnids);
+/*static int get_cryptodev_digests(const int **cnids);*/
 static int cryptodev_usable_ciphers(const int **nids);
 static int cryptodev_usable_digests(const int **nids);
 static int cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
@@ -104,8 +104,8 @@ static int cryptodev_asym(struct crypt_kop *kop, int rlen, BIGNUM *r,
 static int cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a,
     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx);
 static int cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I,
-    RSA *rsa);
-static int cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa);
+    RSA *rsa, BN_CTX *ctx);
+static int cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx);
 static int cryptodev_dsa_bn_mod_exp(DSA *dsa, BIGNUM *r, BIGNUM *a,
     const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx);
 static int cryptodev_dsa_dsa_mod_exp(DSA *dsa, BIGNUM *t1, BIGNUM *g,
@@ -143,6 +143,7 @@ static struct {
        { 0,                            NID_undef,              0,       0, },
 };
 
+#if 0
 static struct {
        int     id;
        int     nid;
@@ -155,6 +156,7 @@ static struct {
        { CRYPTO_SHA1,                  NID_undef,              },
        { 0,                            NID_undef,              },
 };
+#endif
 
 /*
  * Return a fd if /dev/crypto seems usable, 0 otherwise.
@@ -264,7 +266,7 @@ get_cryptodev_ciphers(const int **cnids)
        int fd, i, count = 0;
 
        if ((fd = get_dev_crypto()) < 0) {
-               *nids = NULL;
+               *cnids = NULL;
                return (0);
        }
        memset(&sess, 0, sizeof(sess));
@@ -289,6 +291,7 @@ get_cryptodev_ciphers(const int **cnids)
        return (count);
 }
 
+#if 0  /* unused */
 /*
  * Find out what digests /dev/crypto will let us have a session for.
  * XXX note, that some of these openssl doesn't deal with yet!
@@ -303,7 +306,7 @@ get_cryptodev_digests(const int **cnids)
        int fd, i, count = 0;
 
        if ((fd = get_dev_crypto()) < 0) {
-               *nids = NULL;
+               *cnids = NULL;
                return (0);
        }
        memset(&sess, 0, sizeof(sess));
@@ -325,6 +328,8 @@ get_cryptodev_digests(const int **cnids)
        return (count);
 }
 
+#endif
+
 /*
  * Find the useable ciphers|digests from dev/crypto - this is the first
  * thing called by the engine init crud which determines what it
@@ -378,7 +383,7 @@ cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
        struct crypt_op cryp;
        struct dev_crypto_state *state = ctx->cipher_data;
        struct session_op *sess = &state->d_sess;
-       void *iiv;
+       const void *iiv;
        unsigned char save_iv[EVP_MAX_IV_LENGTH];
 
        if (state->d_fd < 0)
@@ -402,7 +407,7 @@ cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
        if (ctx->cipher->iv_len) {
                cryp.iv = (caddr_t) ctx->iv;
                if (!ctx->encrypt) {
-                       iiv = (void *) in + inl - ctx->cipher->iv_len;
+                       iiv = in + inl - ctx->cipher->iv_len;
                        memcpy(save_iv, iiv, ctx->cipher->iv_len);
                }
        } else
@@ -417,7 +422,7 @@ cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
 
        if (ctx->cipher->iv_len) {
                if (ctx->encrypt)
-                       iiv = (void *) out + inl - ctx->cipher->iv_len;
+                       iiv = out + inl - ctx->cipher->iv_len;
                else
                        iiv = save_iv;
                memcpy(ctx->iv, iiv, ctx->cipher->iv_len);
@@ -447,7 +452,7 @@ cryptodev_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
        if ((state->d_fd = get_dev_crypto()) < 0)
                return (0);
 
-       sess->key = (unsigned char *)key;
+       sess->key = (char *)key;
        sess->keylen = ctx->key_len;
        sess->cipher = cipher;
 
@@ -629,7 +634,7 @@ static int
 bn2crparam(const BIGNUM *a, struct crparam *crp)
 {
        int i, j, k;
-       ssize_t words, bytes, bits;
+       ssize_t bytes, bits;
        u_char *b;
 
        crp->crp_p = NULL;
@@ -642,7 +647,7 @@ bn2crparam(const BIGNUM *a, struct crparam *crp)
        if (b == NULL)
                return (1);
 
-       crp->crp_p = b;
+       crp->crp_p = (char *)b;
        crp->crp_nbits = bits;
 
        for (i = 0, j = 0; i < a->top; i++) {
@@ -760,19 +765,16 @@ err:
 }
 
 static int
-cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa)
+cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
 {
        int r;
-       BN_CTX *ctx;
 
-       ctx = BN_CTX_new();
        r = cryptodev_bn_mod_exp(r0, I, rsa->d, rsa->n, ctx, NULL);
-       BN_CTX_free(ctx);
        return (r);
 }
 
 static int
-cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa)
+cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
 {
        struct crypt_kop kop;
        int ret = 1;
@@ -801,7 +803,7 @@ cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa)
 
        if (cryptodev_asym(&kop, BN_num_bytes(rsa->n), r0, 0, NULL) == -1) {
                const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
-               ret = (*meth->rsa_mod_exp)(r0, I, rsa);
+               ret = (*meth->rsa_mod_exp)(r0, I, rsa, ctx);
        }
 err:
        zapparams(&kop);
@@ -877,7 +879,6 @@ cryptodev_dsa_do_sign(const unsigned char *dgst, int dlen, DSA *dsa)
                goto err;
        }
 
-       printf("bar\n");
        memset(&kop, 0, sizeof kop);
        kop.crk_op = CRK_DSA_SIGN;
 
@@ -999,7 +1000,7 @@ cryptodev_dh_compute_key(unsigned char *key, const BIGNUM *pub_key, DH *dh)
                goto err;
        kop.crk_iparams = 3;
 
-       kop.crk_param[3].crp_p = key;
+       kop.crk_param[3].crp_p = (char *)key;
        kop.crk_param[3].crp_nbits = keylen * 8;
        kop.crk_oparams = 1;
 
@@ -1032,12 +1033,18 @@ static DH_METHOD cryptodev_dh = {
 static int
 cryptodev_ctrl(ENGINE *e, int cmd, long i, void *p, void (*f)())
 {
+#ifdef HAVE_SYSLOG_R
        struct syslog_data sd = SYSLOG_DATA_INIT;
+#endif
 
        switch (cmd) {
        default:
+#ifdef HAVE_SYSLOG_R
                syslog_r(LOG_ERR, &sd,
                    "cryptodev_ctrl: unknown command %d", cmd);
+#else
+               syslog(LOG_ERR, "cryptodev_ctrl: unknown command %d", cmd);
+#endif
                break;
        }
        return (1);
@@ -1051,20 +1058,23 @@ ENGINE_load_cryptodev(void)
 
        if (engine == NULL)
                return;
-       if ((fd = get_dev_crypto()) < 0)
+       if ((fd = get_dev_crypto()) < 0) {
+               ENGINE_free(engine);
                return;
+       }
 
        /*
         * find out what asymmetric crypto algorithms we support
         */
        if (ioctl(fd, CIOCASYMFEAT, &cryptodev_asymfeat) == -1) {
                close(fd);
+               ENGINE_free(engine);
                return;
        }
        close(fd);
 
        if (!ENGINE_set_id(engine, "cryptodev") ||
-           !ENGINE_set_name(engine, "OpenBSD cryptodev engine") ||
+           !ENGINE_set_name(engine, "BSD cryptodev engine") ||
            !ENGINE_set_ciphers(engine, cryptodev_engine_ciphers) ||
            !ENGINE_set_digests(engine, cryptodev_engine_digests) ||
            !ENGINE_set_ctrl_function(engine, cryptodev_ctrl) ||
@@ -1126,5 +1136,4 @@ ENGINE_load_cryptodev(void)
        ERR_clear_error();
 }
 
-#endif /* OpenBSD 3.0 or above */
-#endif /* __OpenBSD__ */
+#endif /* HAVE_CRYPTODEV */