Home | History | Annotate | Line # | Download | only in engines
e_padlock.c revision 1.1.1.2
      1 /*
      2  * Copyright 2004-2019 The OpenSSL Project Authors. All Rights Reserved.
      3  *
      4  * Licensed under the OpenSSL license (the "License").  You may not use
      5  * this file except in compliance with the License.  You can obtain a copy
      6  * in the file LICENSE in the source distribution or at
      7  * https://www.openssl.org/source/license.html
      8  */
      9 
     10 #include <stdio.h>
     11 #include <string.h>
     12 
     13 #include <openssl/opensslconf.h>
     14 #include <openssl/crypto.h>
     15 #include <openssl/engine.h>
     16 #include <openssl/evp.h>
     17 #include <openssl/aes.h>
     18 #include <openssl/rand.h>
     19 #include <openssl/err.h>
     20 #include <openssl/modes.h>
     21 
     22 #ifndef OPENSSL_NO_HW
     23 # ifndef OPENSSL_NO_HW_PADLOCK
     24 
     25 /* Attempt to have a single source for both 0.9.7 and 0.9.8 :-) */
     26 #  if (OPENSSL_VERSION_NUMBER >= 0x00908000L)
     27 #   ifndef OPENSSL_NO_DYNAMIC_ENGINE
     28 #    define DYNAMIC_ENGINE
     29 #   endif
     30 #  elif (OPENSSL_VERSION_NUMBER >= 0x00907000L)
     31 #   ifdef ENGINE_DYNAMIC_SUPPORT
     32 #    define DYNAMIC_ENGINE
     33 #   endif
     34 #  else
     35 #   error "Only OpenSSL >= 0.9.7 is supported"
     36 #  endif
     37 
     38 /*
     39  * VIA PadLock AES is available *ONLY* on some x86 CPUs. Not only that it
     40  * doesn't exist elsewhere, but it even can't be compiled on other platforms!
     41  */
     42 
     43 #  undef COMPILE_HW_PADLOCK
     44 #  if defined(PADLOCK_ASM)
     45 #   define COMPILE_HW_PADLOCK
     46 #   ifdef OPENSSL_NO_DYNAMIC_ENGINE
     47 static ENGINE *ENGINE_padlock(void);
     48 #   endif
     49 #  endif
     50 
     51 #  ifdef OPENSSL_NO_DYNAMIC_ENGINE
     52 void engine_load_padlock_int(void);
     53 void engine_load_padlock_int(void)
     54 {
     55 /* On non-x86 CPUs it just returns. */
     56 #   ifdef COMPILE_HW_PADLOCK
     57     ENGINE *toadd = ENGINE_padlock();
     58     if (!toadd)
     59         return;
     60     ENGINE_add(toadd);
     61     ENGINE_free(toadd);
     62     ERR_clear_error();
     63 #   endif
     64 }
     65 
     66 #  endif
     67 
     68 #  ifdef COMPILE_HW_PADLOCK
     69 
     70 /* Function for ENGINE detection and control */
     71 static int padlock_available(void);
     72 static int padlock_init(ENGINE *e);
     73 
     74 /* RNG Stuff */
     75 static RAND_METHOD padlock_rand;
     76 
     77 /* Cipher Stuff */
     78 static int padlock_ciphers(ENGINE *e, const EVP_CIPHER **cipher,
     79                            const int **nids, int nid);
     80 
     81 /* Engine names */
     82 static const char *padlock_id = "padlock";
     83 static char padlock_name[100];
     84 
     85 /* Available features */
     86 static int padlock_use_ace = 0; /* Advanced Cryptography Engine */
     87 static int padlock_use_rng = 0; /* Random Number Generator */
     88 
     89 /* ===== Engine "management" functions ===== */
     90 
     91 /* Prepare the ENGINE structure for registration */
     92 static int padlock_bind_helper(ENGINE *e)
     93 {
     94     /* Check available features */
     95     padlock_available();
     96 
     97     /*
     98      * RNG is currently disabled for reasons discussed in commentary just
     99      * before padlock_rand_bytes function.
    100      */
    101     padlock_use_rng = 0;
    102 
    103     /* Generate a nice engine name with available features */
    104     BIO_snprintf(padlock_name, sizeof(padlock_name),
    105                  "VIA PadLock (%s, %s)",
    106                  padlock_use_rng ? "RNG" : "no-RNG",
    107                  padlock_use_ace ? "ACE" : "no-ACE");
    108 
    109     /* Register everything or return with an error */
    110     if (!ENGINE_set_id(e, padlock_id) ||
    111         !ENGINE_set_name(e, padlock_name) ||
    112         !ENGINE_set_init_function(e, padlock_init) ||
    113         (padlock_use_ace && !ENGINE_set_ciphers(e, padlock_ciphers)) ||
    114         (padlock_use_rng && !ENGINE_set_RAND(e, &padlock_rand))) {
    115         return 0;
    116     }
    117 
    118     /* Everything looks good */
    119     return 1;
    120 }
    121 
    122 #   ifdef OPENSSL_NO_DYNAMIC_ENGINE
    123 /* Constructor */
    124 static ENGINE *ENGINE_padlock(void)
    125 {
    126     ENGINE *eng = ENGINE_new();
    127 
    128     if (eng == NULL) {
    129         return NULL;
    130     }
    131 
    132     if (!padlock_bind_helper(eng)) {
    133         ENGINE_free(eng);
    134         return NULL;
    135     }
    136 
    137     return eng;
    138 }
    139 #   endif
    140 
    141 /* Check availability of the engine */
    142 static int padlock_init(ENGINE *e)
    143 {
    144     return (padlock_use_rng || padlock_use_ace);
    145 }
    146 
    147 /*
    148  * This stuff is needed if this ENGINE is being compiled into a
    149  * self-contained shared-library.
    150  */
    151 #   ifndef OPENSSL_NO_DYNAMIC_ENGINE
    152 static int padlock_bind_fn(ENGINE *e, const char *id)
    153 {
    154     if (id && (strcmp(id, padlock_id) != 0)) {
    155         return 0;
    156     }
    157 
    158     if (!padlock_bind_helper(e)) {
    159         return 0;
    160     }
    161 
    162     return 1;
    163 }
    164 
    165 IMPLEMENT_DYNAMIC_CHECK_FN()
    166 IMPLEMENT_DYNAMIC_BIND_FN(padlock_bind_fn)
    167 #   endif                       /* !OPENSSL_NO_DYNAMIC_ENGINE */
    168 /* ===== Here comes the "real" engine ===== */
    169 
    170 /* Some AES-related constants */
    171 #   define AES_BLOCK_SIZE          16
    172 #   define AES_KEY_SIZE_128        16
    173 #   define AES_KEY_SIZE_192        24
    174 #   define AES_KEY_SIZE_256        32
    175     /*
    176      * Here we store the status information relevant to the current context.
    177      */
    178     /*
    179      * BIG FAT WARNING: Inline assembler in PADLOCK_XCRYPT_ASM() depends on
    180      * the order of items in this structure.  Don't blindly modify, reorder,
    181      * etc!
    182      */
    183 struct padlock_cipher_data {
    184     unsigned char iv[AES_BLOCK_SIZE]; /* Initialization vector */
    185     union {
    186         unsigned int pad[4];
    187         struct {
    188             int rounds:4;
    189             int dgst:1;         /* n/a in C3 */
    190             int align:1;        /* n/a in C3 */
    191             int ciphr:1;        /* n/a in C3 */
    192             unsigned int keygen:1;
    193             int interm:1;
    194             unsigned int encdec:1;
    195             int ksize:2;
    196         } b;
    197     } cword;                    /* Control word */
    198     AES_KEY ks;                 /* Encryption key */
    199 };
    200 
    201 /* Interface to assembler module */
    202 unsigned int padlock_capability(void);
    203 void padlock_key_bswap(AES_KEY *key);
    204 void padlock_verify_context(struct padlock_cipher_data *ctx);
    205 void padlock_reload_key(void);
    206 void padlock_aes_block(void *out, const void *inp,
    207                        struct padlock_cipher_data *ctx);
    208 int padlock_ecb_encrypt(void *out, const void *inp,
    209                         struct padlock_cipher_data *ctx, size_t len);
    210 int padlock_cbc_encrypt(void *out, const void *inp,
    211                         struct padlock_cipher_data *ctx, size_t len);
    212 int padlock_cfb_encrypt(void *out, const void *inp,
    213                         struct padlock_cipher_data *ctx, size_t len);
    214 int padlock_ofb_encrypt(void *out, const void *inp,
    215                         struct padlock_cipher_data *ctx, size_t len);
    216 int padlock_ctr32_encrypt(void *out, const void *inp,
    217                           struct padlock_cipher_data *ctx, size_t len);
    218 int padlock_xstore(void *out, int edx);
    219 void padlock_sha1_oneshot(void *ctx, const void *inp, size_t len);
    220 void padlock_sha1(void *ctx, const void *inp, size_t len);
    221 void padlock_sha256_oneshot(void *ctx, const void *inp, size_t len);
    222 void padlock_sha256(void *ctx, const void *inp, size_t len);
    223 
    224 /*
    225  * Load supported features of the CPU to see if the PadLock is available.
    226  */
    227 static int padlock_available(void)
    228 {
    229     unsigned int edx = padlock_capability();
    230 
    231     /* Fill up some flags */
    232     padlock_use_ace = ((edx & (0x3 << 6)) == (0x3 << 6));
    233     padlock_use_rng = ((edx & (0x3 << 2)) == (0x3 << 2));
    234 
    235     return padlock_use_ace + padlock_use_rng;
    236 }
    237 
    238 /* ===== AES encryption/decryption ===== */
    239 
    240 #   if defined(NID_aes_128_cfb128) && ! defined (NID_aes_128_cfb)
    241 #    define NID_aes_128_cfb NID_aes_128_cfb128
    242 #   endif
    243 
    244 #   if defined(NID_aes_128_ofb128) && ! defined (NID_aes_128_ofb)
    245 #    define NID_aes_128_ofb NID_aes_128_ofb128
    246 #   endif
    247 
    248 #   if defined(NID_aes_192_cfb128) && ! defined (NID_aes_192_cfb)
    249 #    define NID_aes_192_cfb NID_aes_192_cfb128
    250 #   endif
    251 
    252 #   if defined(NID_aes_192_ofb128) && ! defined (NID_aes_192_ofb)
    253 #    define NID_aes_192_ofb NID_aes_192_ofb128
    254 #   endif
    255 
    256 #   if defined(NID_aes_256_cfb128) && ! defined (NID_aes_256_cfb)
    257 #    define NID_aes_256_cfb NID_aes_256_cfb128
    258 #   endif
    259 
    260 #   if defined(NID_aes_256_ofb128) && ! defined (NID_aes_256_ofb)
    261 #    define NID_aes_256_ofb NID_aes_256_ofb128
    262 #   endif
    263 
    264 /* List of supported ciphers. */
    265 static const int padlock_cipher_nids[] = {
    266     NID_aes_128_ecb,
    267     NID_aes_128_cbc,
    268     NID_aes_128_cfb,
    269     NID_aes_128_ofb,
    270     NID_aes_128_ctr,
    271 
    272     NID_aes_192_ecb,
    273     NID_aes_192_cbc,
    274     NID_aes_192_cfb,
    275     NID_aes_192_ofb,
    276     NID_aes_192_ctr,
    277 
    278     NID_aes_256_ecb,
    279     NID_aes_256_cbc,
    280     NID_aes_256_cfb,
    281     NID_aes_256_ofb,
    282     NID_aes_256_ctr
    283 };
    284 
    285 static int padlock_cipher_nids_num = (sizeof(padlock_cipher_nids) /
    286                                       sizeof(padlock_cipher_nids[0]));
    287 
    288 /* Function prototypes ... */
    289 static int padlock_aes_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
    290                                 const unsigned char *iv, int enc);
    291 
    292 #   define NEAREST_ALIGNED(ptr) ( (unsigned char *)(ptr) +         \
    293         ( (0x10 - ((size_t)(ptr) & 0x0F)) & 0x0F )      )
    294 #   define ALIGNED_CIPHER_DATA(ctx) ((struct padlock_cipher_data *)\
    295         NEAREST_ALIGNED(EVP_CIPHER_CTX_get_cipher_data(ctx)))
    296 
    297 static int
    298 padlock_ecb_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out_arg,
    299                    const unsigned char *in_arg, size_t nbytes)
    300 {
    301     return padlock_ecb_encrypt(out_arg, in_arg,
    302                                ALIGNED_CIPHER_DATA(ctx), nbytes);
    303 }
    304 
    305 static int
    306 padlock_cbc_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out_arg,
    307                    const unsigned char *in_arg, size_t nbytes)
    308 {
    309     struct padlock_cipher_data *cdata = ALIGNED_CIPHER_DATA(ctx);
    310     int ret;
    311 
    312     memcpy(cdata->iv, EVP_CIPHER_CTX_iv(ctx), AES_BLOCK_SIZE);
    313     if ((ret = padlock_cbc_encrypt(out_arg, in_arg, cdata, nbytes)))
    314         memcpy(EVP_CIPHER_CTX_iv_noconst(ctx), cdata->iv, AES_BLOCK_SIZE);
    315     return ret;
    316 }
    317 
    318 static int
    319 padlock_cfb_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out_arg,
    320                    const unsigned char *in_arg, size_t nbytes)
    321 {
    322     struct padlock_cipher_data *cdata = ALIGNED_CIPHER_DATA(ctx);
    323     size_t chunk;
    324 
    325     if ((chunk = EVP_CIPHER_CTX_num(ctx))) {   /* borrow chunk variable */
    326         unsigned char *ivp = EVP_CIPHER_CTX_iv_noconst(ctx);
    327 
    328         if (chunk >= AES_BLOCK_SIZE)
    329             return 0;           /* bogus value */
    330 
    331         if (EVP_CIPHER_CTX_encrypting(ctx))
    332             while (chunk < AES_BLOCK_SIZE && nbytes != 0) {
    333                 ivp[chunk] = *(out_arg++) = *(in_arg++) ^ ivp[chunk];
    334                 chunk++, nbytes--;
    335         } else
    336             while (chunk < AES_BLOCK_SIZE && nbytes != 0) {
    337                 unsigned char c = *(in_arg++);
    338                 *(out_arg++) = c ^ ivp[chunk];
    339                 ivp[chunk++] = c, nbytes--;
    340             }
    341 
    342         EVP_CIPHER_CTX_set_num(ctx, chunk % AES_BLOCK_SIZE);
    343     }
    344 
    345     if (nbytes == 0)
    346         return 1;
    347 
    348     memcpy(cdata->iv, EVP_CIPHER_CTX_iv(ctx), AES_BLOCK_SIZE);
    349 
    350     if ((chunk = nbytes & ~(AES_BLOCK_SIZE - 1))) {
    351         if (!padlock_cfb_encrypt(out_arg, in_arg, cdata, chunk))
    352             return 0;
    353         nbytes -= chunk;
    354     }
    355 
    356     if (nbytes) {
    357         unsigned char *ivp = cdata->iv;
    358 
    359         out_arg += chunk;
    360         in_arg += chunk;
    361         EVP_CIPHER_CTX_set_num(ctx, nbytes);
    362         if (cdata->cword.b.encdec) {
    363             cdata->cword.b.encdec = 0;
    364             padlock_reload_key();
    365             padlock_aes_block(ivp, ivp, cdata);
    366             cdata->cword.b.encdec = 1;
    367             padlock_reload_key();
    368             while (nbytes) {
    369                 unsigned char c = *(in_arg++);
    370                 *(out_arg++) = c ^ *ivp;
    371                 *(ivp++) = c, nbytes--;
    372             }
    373         } else {
    374             padlock_reload_key();
    375             padlock_aes_block(ivp, ivp, cdata);
    376             padlock_reload_key();
    377             while (nbytes) {
    378                 *ivp = *(out_arg++) = *(in_arg++) ^ *ivp;
    379                 ivp++, nbytes--;
    380             }
    381         }
    382     }
    383 
    384     memcpy(EVP_CIPHER_CTX_iv_noconst(ctx), cdata->iv, AES_BLOCK_SIZE);
    385 
    386     return 1;
    387 }
    388 
    389 static int
    390 padlock_ofb_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out_arg,
    391                    const unsigned char *in_arg, size_t nbytes)
    392 {
    393     struct padlock_cipher_data *cdata = ALIGNED_CIPHER_DATA(ctx);
    394     size_t chunk;
    395 
    396     /*
    397      * ctx->num is maintained in byte-oriented modes, such as CFB and OFB...
    398      */
    399     if ((chunk = EVP_CIPHER_CTX_num(ctx))) {   /* borrow chunk variable */
    400         unsigned char *ivp = EVP_CIPHER_CTX_iv_noconst(ctx);
    401 
    402         if (chunk >= AES_BLOCK_SIZE)
    403             return 0;           /* bogus value */
    404 
    405         while (chunk < AES_BLOCK_SIZE && nbytes != 0) {
    406             *(out_arg++) = *(in_arg++) ^ ivp[chunk];
    407             chunk++, nbytes--;
    408         }
    409 
    410         EVP_CIPHER_CTX_set_num(ctx, chunk % AES_BLOCK_SIZE);
    411     }
    412 
    413     if (nbytes == 0)
    414         return 1;
    415 
    416     memcpy(cdata->iv, EVP_CIPHER_CTX_iv(ctx), AES_BLOCK_SIZE);
    417 
    418     if ((chunk = nbytes & ~(AES_BLOCK_SIZE - 1))) {
    419         if (!padlock_ofb_encrypt(out_arg, in_arg, cdata, chunk))
    420             return 0;
    421         nbytes -= chunk;
    422     }
    423 
    424     if (nbytes) {
    425         unsigned char *ivp = cdata->iv;
    426 
    427         out_arg += chunk;
    428         in_arg += chunk;
    429         EVP_CIPHER_CTX_set_num(ctx, nbytes);
    430         padlock_reload_key();   /* empirically found */
    431         padlock_aes_block(ivp, ivp, cdata);
    432         padlock_reload_key();   /* empirically found */
    433         while (nbytes) {
    434             *(out_arg++) = *(in_arg++) ^ *ivp;
    435             ivp++, nbytes--;
    436         }
    437     }
    438 
    439     memcpy(EVP_CIPHER_CTX_iv_noconst(ctx), cdata->iv, AES_BLOCK_SIZE);
    440 
    441     return 1;
    442 }
    443 
    444 static void padlock_ctr32_encrypt_glue(const unsigned char *in,
    445                                        unsigned char *out, size_t blocks,
    446                                        struct padlock_cipher_data *ctx,
    447                                        const unsigned char *ivec)
    448 {
    449     memcpy(ctx->iv, ivec, AES_BLOCK_SIZE);
    450     padlock_ctr32_encrypt(out, in, ctx, AES_BLOCK_SIZE * blocks);
    451 }
    452 
    453 static int
    454 padlock_ctr_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out_arg,
    455                    const unsigned char *in_arg, size_t nbytes)
    456 {
    457     struct padlock_cipher_data *cdata = ALIGNED_CIPHER_DATA(ctx);
    458     unsigned int num = EVP_CIPHER_CTX_num(ctx);
    459 
    460     CRYPTO_ctr128_encrypt_ctr32(in_arg, out_arg, nbytes,
    461                                 cdata, EVP_CIPHER_CTX_iv_noconst(ctx),
    462                                 EVP_CIPHER_CTX_buf_noconst(ctx), &num,
    463                                 (ctr128_f) padlock_ctr32_encrypt_glue);
    464 
    465     EVP_CIPHER_CTX_set_num(ctx, (size_t)num);
    466     return 1;
    467 }
    468 
    469 #   define EVP_CIPHER_block_size_ECB       AES_BLOCK_SIZE
    470 #   define EVP_CIPHER_block_size_CBC       AES_BLOCK_SIZE
    471 #   define EVP_CIPHER_block_size_OFB       1
    472 #   define EVP_CIPHER_block_size_CFB       1
    473 #   define EVP_CIPHER_block_size_CTR       1
    474 
    475 /*
    476  * Declaring so many ciphers by hand would be a pain. Instead introduce a bit
    477  * of preprocessor magic :-)
    478  */
    479 #   define DECLARE_AES_EVP(ksize,lmode,umode)      \
    480 static EVP_CIPHER *_hidden_aes_##ksize##_##lmode = NULL; \
    481 static const EVP_CIPHER *padlock_aes_##ksize##_##lmode(void) \
    482 {                                                                       \
    483     if (_hidden_aes_##ksize##_##lmode == NULL                           \
    484         && ((_hidden_aes_##ksize##_##lmode =                            \
    485              EVP_CIPHER_meth_new(NID_aes_##ksize##_##lmode,             \
    486                                  EVP_CIPHER_block_size_##umode,         \
    487                                  AES_KEY_SIZE_##ksize)) == NULL         \
    488             || !EVP_CIPHER_meth_set_iv_length(_hidden_aes_##ksize##_##lmode, \
    489                                               AES_BLOCK_SIZE)           \
    490             || !EVP_CIPHER_meth_set_flags(_hidden_aes_##ksize##_##lmode, \
    491                                           0 | EVP_CIPH_##umode##_MODE)  \
    492             || !EVP_CIPHER_meth_set_init(_hidden_aes_##ksize##_##lmode, \
    493                                          padlock_aes_init_key)          \
    494             || !EVP_CIPHER_meth_set_do_cipher(_hidden_aes_##ksize##_##lmode, \
    495                                               padlock_##lmode##_cipher) \
    496             || !EVP_CIPHER_meth_set_impl_ctx_size(_hidden_aes_##ksize##_##lmode, \
    497                                                   sizeof(struct padlock_cipher_data) + 16) \
    498             || !EVP_CIPHER_meth_set_set_asn1_params(_hidden_aes_##ksize##_##lmode, \
    499                                                     EVP_CIPHER_set_asn1_iv) \
    500             || !EVP_CIPHER_meth_set_get_asn1_params(_hidden_aes_##ksize##_##lmode, \
    501                                                     EVP_CIPHER_get_asn1_iv))) { \
    502         EVP_CIPHER_meth_free(_hidden_aes_##ksize##_##lmode);            \
    503         _hidden_aes_##ksize##_##lmode = NULL;                           \
    504     }                                                                   \
    505     return _hidden_aes_##ksize##_##lmode;                               \
    506 }
    507 
    508 DECLARE_AES_EVP(128, ecb, ECB)
    509 DECLARE_AES_EVP(128, cbc, CBC)
    510 DECLARE_AES_EVP(128, cfb, CFB)
    511 DECLARE_AES_EVP(128, ofb, OFB)
    512 DECLARE_AES_EVP(128, ctr, CTR)
    513 
    514 DECLARE_AES_EVP(192, ecb, ECB)
    515 DECLARE_AES_EVP(192, cbc, CBC)
    516 DECLARE_AES_EVP(192, cfb, CFB)
    517 DECLARE_AES_EVP(192, ofb, OFB)
    518 DECLARE_AES_EVP(192, ctr, CTR)
    519 
    520 DECLARE_AES_EVP(256, ecb, ECB)
    521 DECLARE_AES_EVP(256, cbc, CBC)
    522 DECLARE_AES_EVP(256, cfb, CFB)
    523 DECLARE_AES_EVP(256, ofb, OFB)
    524 DECLARE_AES_EVP(256, ctr, CTR)
    525 
    526 static int
    527 padlock_ciphers(ENGINE *e, const EVP_CIPHER **cipher, const int **nids,
    528                 int nid)
    529 {
    530     /* No specific cipher => return a list of supported nids ... */
    531     if (!cipher) {
    532         *nids = padlock_cipher_nids;
    533         return padlock_cipher_nids_num;
    534     }
    535 
    536     /* ... or the requested "cipher" otherwise */
    537     switch (nid) {
    538     case NID_aes_128_ecb:
    539         *cipher = padlock_aes_128_ecb();
    540         break;
    541     case NID_aes_128_cbc:
    542         *cipher = padlock_aes_128_cbc();
    543         break;
    544     case NID_aes_128_cfb:
    545         *cipher = padlock_aes_128_cfb();
    546         break;
    547     case NID_aes_128_ofb:
    548         *cipher = padlock_aes_128_ofb();
    549         break;
    550     case NID_aes_128_ctr:
    551         *cipher = padlock_aes_128_ctr();
    552         break;
    553 
    554     case NID_aes_192_ecb:
    555         *cipher = padlock_aes_192_ecb();
    556         break;
    557     case NID_aes_192_cbc:
    558         *cipher = padlock_aes_192_cbc();
    559         break;
    560     case NID_aes_192_cfb:
    561         *cipher = padlock_aes_192_cfb();
    562         break;
    563     case NID_aes_192_ofb:
    564         *cipher = padlock_aes_192_ofb();
    565         break;
    566     case NID_aes_192_ctr:
    567         *cipher = padlock_aes_192_ctr();
    568         break;
    569 
    570     case NID_aes_256_ecb:
    571         *cipher = padlock_aes_256_ecb();
    572         break;
    573     case NID_aes_256_cbc:
    574         *cipher = padlock_aes_256_cbc();
    575         break;
    576     case NID_aes_256_cfb:
    577         *cipher = padlock_aes_256_cfb();
    578         break;
    579     case NID_aes_256_ofb:
    580         *cipher = padlock_aes_256_ofb();
    581         break;
    582     case NID_aes_256_ctr:
    583         *cipher = padlock_aes_256_ctr();
    584         break;
    585 
    586     default:
    587         /* Sorry, we don't support this NID */
    588         *cipher = NULL;
    589         return 0;
    590     }
    591 
    592     return 1;
    593 }
    594 
    595 /* Prepare the encryption key for PadLock usage */
    596 static int
    597 padlock_aes_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
    598                      const unsigned char *iv, int enc)
    599 {
    600     struct padlock_cipher_data *cdata;
    601     int key_len = EVP_CIPHER_CTX_key_length(ctx) * 8;
    602     unsigned long mode = EVP_CIPHER_CTX_mode(ctx);
    603 
    604     if (key == NULL)
    605         return 0;               /* ERROR */
    606 
    607     cdata = ALIGNED_CIPHER_DATA(ctx);
    608     memset(cdata, 0, sizeof(*cdata));
    609 
    610     /* Prepare Control word. */
    611     if (mode == EVP_CIPH_OFB_MODE || mode == EVP_CIPH_CTR_MODE)
    612         cdata->cword.b.encdec = 0;
    613     else
    614         cdata->cword.b.encdec = (EVP_CIPHER_CTX_encrypting(ctx) == 0);
    615     cdata->cword.b.rounds = 10 + (key_len - 128) / 32;
    616     cdata->cword.b.ksize = (key_len - 128) / 64;
    617 
    618     switch (key_len) {
    619     case 128:
    620         /*
    621          * PadLock can generate an extended key for AES128 in hardware
    622          */
    623         memcpy(cdata->ks.rd_key, key, AES_KEY_SIZE_128);
    624         cdata->cword.b.keygen = 0;
    625         break;
    626 
    627     case 192:
    628     case 256:
    629         /*
    630          * Generate an extended AES key in software. Needed for AES192/AES256
    631          */
    632         /*
    633          * Well, the above applies to Stepping 8 CPUs and is listed as
    634          * hardware errata. They most likely will fix it at some point and
    635          * then a check for stepping would be due here.
    636          */
    637         if ((mode == EVP_CIPH_ECB_MODE || mode == EVP_CIPH_CBC_MODE)
    638             && !enc)
    639             AES_set_decrypt_key(key, key_len, &cdata->ks);
    640         else
    641             AES_set_encrypt_key(key, key_len, &cdata->ks);
    642 #   ifndef AES_ASM
    643         /*
    644          * OpenSSL C functions use byte-swapped extended key.
    645          */
    646         padlock_key_bswap(&cdata->ks);
    647 #   endif
    648         cdata->cword.b.keygen = 1;
    649         break;
    650 
    651     default:
    652         /* ERROR */
    653         return 0;
    654     }
    655 
    656     /*
    657      * This is done to cover for cases when user reuses the
    658      * context for new key. The catch is that if we don't do
    659      * this, padlock_eas_cipher might proceed with old key...
    660      */
    661     padlock_reload_key();
    662 
    663     return 1;
    664 }
    665 
    666 /* ===== Random Number Generator ===== */
    667 /*
    668  * This code is not engaged. The reason is that it does not comply
    669  * with recommendations for VIA RNG usage for secure applications
    670  * (posted at http://www.via.com.tw/en/viac3/c3.jsp) nor does it
    671  * provide meaningful error control...
    672  */
    673 /*
    674  * Wrapper that provides an interface between the API and the raw PadLock
    675  * RNG
    676  */
    677 static int padlock_rand_bytes(unsigned char *output, int count)
    678 {
    679     unsigned int eax, buf;
    680 
    681     while (count >= 8) {
    682         eax = padlock_xstore(output, 0);
    683         if (!(eax & (1 << 6)))
    684             return 0;           /* RNG disabled */
    685         /* this ---vv--- covers DC bias, Raw Bits and String Filter */
    686         if (eax & (0x1F << 10))
    687             return 0;
    688         if ((eax & 0x1F) == 0)
    689             continue;           /* no data, retry... */
    690         if ((eax & 0x1F) != 8)
    691             return 0;           /* fatal failure...  */
    692         output += 8;
    693         count -= 8;
    694     }
    695     while (count > 0) {
    696         eax = padlock_xstore(&buf, 3);
    697         if (!(eax & (1 << 6)))
    698             return 0;           /* RNG disabled */
    699         /* this ---vv--- covers DC bias, Raw Bits and String Filter */
    700         if (eax & (0x1F << 10))
    701             return 0;
    702         if ((eax & 0x1F) == 0)
    703             continue;           /* no data, retry... */
    704         if ((eax & 0x1F) != 1)
    705             return 0;           /* fatal failure...  */
    706         *output++ = (unsigned char)buf;
    707         count--;
    708     }
    709     OPENSSL_cleanse(&buf, sizeof(buf));
    710 
    711     return 1;
    712 }
    713 
    714 /* Dummy but necessary function */
    715 static int padlock_rand_status(void)
    716 {
    717     return 1;
    718 }
    719 
    720 /* Prepare structure for registration */
    721 static RAND_METHOD padlock_rand = {
    722     NULL,                       /* seed */
    723     padlock_rand_bytes,         /* bytes */
    724     NULL,                       /* cleanup */
    725     NULL,                       /* add */
    726     padlock_rand_bytes,         /* pseudorand */
    727     padlock_rand_status,        /* rand status */
    728 };
    729 
    730 #  endif                        /* COMPILE_HW_PADLOCK */
    731 # endif                         /* !OPENSSL_NO_HW_PADLOCK */
    732 #endif                          /* !OPENSSL_NO_HW */
    733 
    734 #if defined(OPENSSL_NO_HW) || defined(OPENSSL_NO_HW_PADLOCK) \
    735         || !defined(COMPILE_HW_PADLOCK)
    736 # ifndef OPENSSL_NO_DYNAMIC_ENGINE
    737 OPENSSL_EXPORT
    738     int bind_engine(ENGINE *e, const char *id, const dynamic_fns *fns);
    739 OPENSSL_EXPORT
    740     int bind_engine(ENGINE *e, const char *id, const dynamic_fns *fns)
    741 {
    742     return 0;
    743 }
    744 
    745 IMPLEMENT_DYNAMIC_CHECK_FN()
    746 # endif
    747 #endif
    748