ahcbcpad.c revision 65c4736d9c0ebc6d9b1d991593b55566909da9cd
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews/* Copyright (C) RSA Data Security, Inc. created 1993, 1996. This is an
1413616670fcb95b9ef236351502e4884ddca8bfTinderbox User unpublished work protected as such under copyright law. This work
fcb54ce0a4f7377486df5bec83b3aa4711bf4131Mark Andrews contains proprietary, confidential, and trade secret information of
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence RSA Data Security, Inc. Use, disclosure or reproduction without the
ec5347e2c775f027573ce5648b910361aa926c01Automatic Updater express written authorization of RSA Data Security, Inc. is
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews prohibited.
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews */
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews/* Define this so that the type of the 'this' pointer in the
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews virtual functions will be correct for this derived class.
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews */
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrewsstruct AHSecretCBCPad;
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews#define THIS_ENCRYPT_DECRYPT struct AHSecretCBCPad
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews
dafcb997e390efa4423883dafd100c975c4095d6Mark Andrews#include "global.h"
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#include "bsafe2.h"
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews#include "bkey.h"
28a8f5b0de57d269cf2845c69cb6abe18cbd3b3aMark Andrews#include "balg.h"
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein#include "ahcbcpad.h"
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff#define GENERATE_BREAK(type) { \
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff status = type; \
de153390f5a1f6d4fa86af91d4cae772d9846ca0Mark Andrews break; \
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff }
822f6cdabb1edd44472c7a758b5cae71376fa9beBrian Wellington
ebfcb6cf66283096ebda1503b6cc042ce86b6bedBrian Wellington/* Inherit the base class destructor, block size,
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews and decrypt init and update routines.
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence */
242bba8991b030b7764f0bdca3922d75c34ea51eAndreas Gustafssonstatic AHEncryptDecryptVTable V_TABLE = {
25a66b4e41e2b0a2af4840749bac80ae78c678bfMark Andrews AHChooseEncryptDestructor, AHChooseEncryptGetBlockLen,
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence AHSecretCBCPadEncryptInit, AHChooseEncryptDecryptInit,
21f1794606dce19928cf455029e173321f166380Mark Andrews AHSecretCBCPadEncryptUpdate, AHChooseEncryptDecryptUpdate,
973a19342597823f111fce6a8cd5adfd0e2e7c0dMark Andrews AHSecretCBCPadEncryptFinal, AHSecretCBCPadDecryptFinal
0c310d16b05ee94743d33f6920907edee6084fc8Michael Graff};
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid LawrenceAHSecretCBCPad *AHSecretCBCPadConstructor2 (handler, infoType, info)
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid LawrenceAHSecretCBCPad *handler;
058e44186b74531402c1f99088eb9dbe4926f8daMark Andrewsstruct B_AlgorithmInfoType *infoType;
28b863e609ff2d97b78663b46894494cfa2ea411Mark AndrewsPOINTER info;
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence{
21825a8d005ccc2dfaf12889bf9eef3413555277Brian Wellington if (handler == (AHSecretCBCPad *)NULL_PTR) {
307d2084502eddc7ce921e5ce439aec3531d90e0Tatuya JINMEI 神明達哉 /* This constructor is being used to do a new */
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence if ((handler = (AHSecretCBCPad *)T_malloc (sizeof (*handler)))
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews == (AHSecretCBCPad *)NULL_PTR)
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews return (handler);
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence }
a98551ef592e9be6008e0141ceeb32efd586c5efMark Andrews
1a69a1a78cfaa86f3b68bbc965232b7876d4da2aDavid Lawrence /* Construct base class with the infoType and info. */
54c26ab21c61c6d6b1e484bb88dc3ac263845d17Mark Andrews AHChooseEncryptConstructor2
3ddd92da6651bc72aa79a04195ad389d86fd1a66Andreas Gustafsson (&handler->chooseEncryptDecrypt, infoType, info);
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson
5fc7ba3e1ac5d72239e9971e0f469dd5796738f9Andreas Gustafsson handler->chooseEncryptDecrypt.encryptDecrypt.vTable = &V_TABLE;
5d51e67c3b4f35c1be742574aacc1d88fe6ed444Mark Andrews return (handler);
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews}
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrewsint AHSecretCBCPadEncryptInit (handler, key, chooser, surrenderContext)
9ac7076ebad044afb15e9e2687e3696868778538Mark AndrewsAHSecretCBCPad *handler;
9ac7076ebad044afb15e9e2687e3696868778538Mark AndrewsB_Key *key;
9ac7076ebad044afb15e9e2687e3696868778538Mark AndrewsB_ALGORITHM_CHOOSER chooser;
c46f10e4a1702191b003cf8f8fc5059c15d29c48Mark AndrewsA_SURRENDER_CTX *surrenderContext;
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews{
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews /* For encryption, we need to track the input length */
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews handler->_inputRemainder = 0;
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews return (AHChooseEncryptEncryptInit
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews (handler, key, chooser, surrenderContext));
9ac7076ebad044afb15e9e2687e3696868778538Mark Andrews}
eb6bd543c7d072efdca509eb17f8f301c1467b53Mark Andrews
deaaf94332abbfdb3aff53675546acfed16e5eb6Mark Andrewsint AHSecretCBCPadEncryptUpdate
c46f10e4a1702191b003cf8f8fc5059c15d29c48Mark Andrews (handler, partOut, partOutLen, maxPartOutLen, partIn, partInLen,
c46f10e4a1702191b003cf8f8fc5059c15d29c48Mark Andrews randomAlgorithm, surrenderContext)
0b056755b2f423ba5f6adac8f7851d78f7d11437David LawrenceAHSecretCBCPad *handler;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned char *partOut;
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrewsunsigned int *partOutLen;
bddfe77128b0f16af263ff149db40f0d885f43d0Mark Andrewsunsigned int maxPartOutLen;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned char *partIn;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned int partInLen;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David LawrenceB_Algorithm *randomAlgorithm;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David LawrenceA_SURRENDER_CTX *surrenderContext;
0b056755b2f423ba5f6adac8f7851d78f7d11437David Lawrence{
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence /* For encryption, we need to track the input length */
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews handler->_inputRemainder = (handler->_inputRemainder + partInLen) % 8;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence return (AHChooseEncryptEncryptUpdate
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence (handler, partOut, partOutLen, maxPartOutLen, partIn, partInLen,
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence randomAlgorithm, surrenderContext));
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence}
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence
0b056755b2f423ba5f6adac8f7851d78f7d11437David Lawrenceint AHSecretCBCPadEncryptFinal
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence (handler, partOut, partOutLen, maxPartOutLen, randomAlgorithm,
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence surrenderContext)
6d12fdf96621801e80f3f4c2a8a569fe48766a20David LawrenceAHSecretCBCPad *handler;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned char *partOut;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned int *partOutLen;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrenceunsigned int maxPartOutLen;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David LawrenceB_Algorithm *randomAlgorithm;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David LawrenceA_SURRENDER_CTX *surrenderContext;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence{
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence int status;
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence unsigned char finalBuffer[8];
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews unsigned int padLen, dummyPartOutLen;
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews padLen = 8 - handler->_inputRemainder;
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews T_memset ((POINTER)finalBuffer, padLen, padLen);
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews
2047977ce2dfcfe3a0fa2d638c3242841310fad3Mark Andrews /* Add the pad bytes. This should force the output of the final block.
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein */
40f53fa8d9c6a4fc38c0014495e7a42b08f52481David Lawrence if ((status = AHChooseEncryptEncryptUpdate
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson (handler, partOut, partOutLen, maxPartOutLen, finalBuffer, padLen,
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson randomAlgorithm, surrenderContext)) != 0)
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson return (status);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein /* The encrypt final operation should have no output. */
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein if ((status = AHChooseEncryptEncryptFinal
ab023a65562e62b85a824509d829b6fad87e00b1Rob Austein (handler, (unsigned char *)NULL_PTR, &dummyPartOutLen, 0,
e672951ed28b2e9cc7a19c3d7fa4a258382f981cAutomatic Updater (B_Algorithm *)NULL_PTR, (A_SURRENDER_CTX *)NULL_PTR)) != 0)
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson return (status);
0c8649cea98afc061dd2938fd315df53b8fc35caAndreas Gustafsson
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence /* Restart the context. */
2383eb527269d333df4222da20e4b422c3662daaEvan Hunt handler->_inputRemainder = 0;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence /* No need to zeroize the finalBuffer since it only contains pad bytes. */
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (0);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence}
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrenceint AHSecretCBCPadDecryptFinal
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence (handler, partOut, partOutLen, maxPartOutLen, randomAlgorithm,
9fe8cca06537c45375c1e1d36b82501caf0ae090Francis Dupont surrenderContext)
7712d1660a308ec3de17f1ddbbf801eb0d663f3eEvan HuntAHSecretCBCPad *handler;
9fe8cca06537c45375c1e1d36b82501caf0ae090Francis Dupontunsigned char *partOut;
9fe8cca06537c45375c1e1d36b82501caf0ae090Francis Dupontunsigned int *partOutLen;
7712d1660a308ec3de17f1ddbbf801eb0d663f3eEvan Huntunsigned int maxPartOutLen;
9fe8cca06537c45375c1e1d36b82501caf0ae090Francis DupontB_Algorithm *randomAlgorithm;
8abddcd3f24476b945419659e7cb73bcb970886bDavid LawrenceA_SURRENDER_CTX *surrenderContext;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence{
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence int status;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned char finalBuffer[16], *padBuffer;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence unsigned int padLen, localPartOutLen, i;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence do {
6d12fdf96621801e80f3f4c2a8a569fe48766a20David Lawrence /* For now, the DecrypyFinal operations is set to output 16 bytes.
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence */
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington if ((status = AHChooseEncryptDecryptFinal
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington (handler, finalBuffer, &localPartOutLen, sizeof (finalBuffer),
330705066b03f6ce0bc08a4bbfc5d2418038c68dBrian Wellington randomAlgorithm, surrenderContext)) != 0)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence break;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if (localPartOutLen == 8)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence padBuffer = finalBuffer;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence else if (localPartOutLen == 16)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence padBuffer = finalBuffer + 8;
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence else
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence GENERATE_BREAK (BE_INPUT_LEN);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence /* Check that padding is one 1 to eight 8's.
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence */
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if ((padLen = (unsigned int)padBuffer[7]) == 0 || padLen > 8)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence GENERATE_BREAK (BE_INPUT_DATA);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence for (i = 8 - padLen; i < 8; i++) {
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if ((unsigned int)padBuffer[i] != padLen)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence GENERATE_BREAK (BE_INPUT_DATA);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence }
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence if ((*partOutLen = localPartOutLen - padLen) > maxPartOutLen)
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence GENERATE_BREAK (BE_OUTPUT_LEN);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence T_memcpy
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence ((POINTER)partOut, (POINTER)finalBuffer, *partOutLen);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence } while (0);
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence T_memset ((POINTER)finalBuffer, 0, sizeof (finalBuffer));
8abddcd3f24476b945419659e7cb73bcb970886bDavid Lawrence return (status);
6098d364b690cb9dabf96e9664c4689c8559bd2eMark Andrews}
6098d364b690cb9dabf96e9664c4689c8559bd2eMark Andrews
6098d364b690cb9dabf96e9664c4689c8559bd2eMark Andrews