1 /* =================================================================== 2 * 3 * Copyright (c) 2014, Legrandin <helderijs@gmail.com> 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in 14 * the documentation and/or other materials provided with the 15 * distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 18 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 19 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 20 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 21 * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 22 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 23 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 24 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 25 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 27 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 28 * POSSIBILITY OF SUCH DAMAGE. 29 * =================================================================== 30 */ 31 32 #include <stdlib.h> 33 34 #include "block_base.h" 35 36 #define CIPHER_STATE_TYPE _PASTE2(MODULE_NAME, _State) 37 #define CIPHER_ENCRYPT _PASTE2(MODULE_NAME, _encrypt) 38 #define CIPHER_DECRYPT _PASTE2(MODULE_NAME, _decrypt) 39 #define CIPHER_STOP_OPERATION _PASTE2(MODULE_NAME, _stop_operation) 40 #define CIPHER_START_OPERATION _PASTE2(MODULE_NAME, _start_operation) 41 42 typedef struct { 43 BlockBase base_state; 44 struct block_state algo_state; 45 } CIPHER_STATE_TYPE; 46 47 static int CIPHER_ENCRYPT 48 (const BlockBase *state, const uint8_t *in, uint8_t *out, size_t data_len) 49 { 50 size_t block_len; 51 52 if ((state == NULL) || (in == NULL) || (out == NULL)) 53 return ERR_NULL; 54 55 block_len = state->block_len; 56 57 for (; data_len>=block_len; data_len-=block_len) { 58 block_encrypt(&((CIPHER_STATE_TYPE*)state)->algo_state, (uint8_t*)in, out); 59 in += block_len; 60 out += block_len; 61 } 62 63 if (data_len) 64 return ERR_NOT_ENOUGH_DATA; 65 66 return 0; 67 } 68 69 static int CIPHER_DECRYPT 70 (const BlockBase *state, const uint8_t *in, uint8_t *out, size_t data_len) 71 { 72 size_t block_len; 73 74 if ((state == NULL) || (in == NULL) || (out == NULL)) 75 return ERR_NULL; 76 77 block_len = state->block_len; 78 79 for (; data_len>=block_len; data_len-=block_len) { 80 block_decrypt(&((CIPHER_STATE_TYPE*)state)->algo_state, (uint8_t*)in, out); 81 in += block_len; 82 out += block_len; 83 } 84 85 if (data_len) 86 return ERR_NOT_ENOUGH_DATA; 87 88 return 0; 89 } 90 91 EXPORT_SYM int CIPHER_STOP_OPERATION(BlockBase *state) 92 { 93 if (NULL == state) 94 return ERR_NULL; 95 96 block_finalize(&((CIPHER_STATE_TYPE*)state)->algo_state); 97 free(state); 98 return 0; 99 } 100 101 #ifndef NON_STANDARD_START_OPERATION 102 EXPORT_SYM int CIPHER_START_OPERATION(const uint8_t key[], size_t key_len, CIPHER_STATE_TYPE **pResult) 103 { 104 BlockBase *block_base; 105 int res; 106 107 if ((key == NULL) || (pResult == NULL)) 108 return ERR_NULL; 109 110 *pResult = calloc(1, sizeof(CIPHER_STATE_TYPE)); 111 if (NULL == *pResult) 112 return ERR_MEMORY; 113 114 block_base = &((*pResult)->base_state); 115 block_base->encrypt = &CIPHER_ENCRYPT; 116 block_base->decrypt = &CIPHER_DECRYPT; 117 block_base->destructor = &CIPHER_STOP_OPERATION; 118 block_base->block_len = BLOCK_SIZE; 119 120 res = block_init(&(*pResult)->algo_state, (unsigned char*)key, key_len); 121 if (res) { 122 free(*pResult); 123 *pResult = NULL; 124 } 125 126 return res; 127 } 128 #endif 129