"Fossies" - the Fresh Open Source Software Archive

Member "libmcrypt-2.5.8/modules/modes/ctr.c" (15 Jan 2003, 6125 Bytes) of package /linux/privat/old/libmcrypt-2.5.8.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "ctr.c" see the Fossies "Dox" file reference documentation.

    1 /*
    2  * Copyright (C) 2002 Nikos Mavroyanopoulos
    3  * 
    4  * This library is free software; you can redistribute it and/or modify it 
    5  * under the terms of the GNU Library General Public License as published 
    6  * by the Free Software Foundation; either version 2 of the License, or 
    7  * (at your option) any later version.
    8  *
    9  * This library is distributed in the hope that it will be useful,
   10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
   11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   12  * Library General Public License for more details.
   13  *
   14  * You should have received a copy of the GNU Library General Public
   15  * License along with this library; if not, write to the
   16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
   17  * Boston, MA 02111-1307, USA.
   18  */
   19 
   20 #include <libdefs.h>
   21 #include <mcrypt_modules.h>
   22 
   23 #define _init_mcrypt ctr_LTX__init_mcrypt
   24 #define _mcrypt_set_state ctr_LTX__mcrypt_set_state
   25 #define _mcrypt_get_state ctr_LTX__mcrypt_get_state
   26 #define _end_mcrypt ctr_LTX__end_mcrypt
   27 #define _mcrypt ctr_LTX__mcrypt
   28 #define _mdecrypt ctr_LTX__mdecrypt
   29 #define _has_iv ctr_LTX__has_iv
   30 #define _is_block_mode ctr_LTX__is_block_mode
   31 #define _is_block_algorithm_mode ctr_LTX__is_block_algorithm_mode
   32 #define _mcrypt_get_modes_name ctr_LTX__mcrypt_get_modes_name
   33 #define _mcrypt_mode_get_size ctr_LTX__mcrypt_mode_get_size
   34 #define _mcrypt_mode_version ctr_LTX__mcrypt_mode_version
   35 
   36 typedef struct ctr_buf {
   37     byte* enc_counter;
   38     byte* c_counter;
   39     int c_counter_pos;
   40     int blocksize;
   41 } CTR_BUFFER;
   42 
   43 /* CTR MODE */
   44 
   45 /* This function will add one to the given number (as a byte string).
   46  * has been reached.
   47  */
   48 static void increase_counter( byte *x, int x_size) {
   49 register int i, y=0;
   50 
   51     for (i=x_size-1;i>=0;i--) {
   52         y = 0;
   53         if ( x[i] == 0xff) {
   54             x[i] = 0;
   55             y = 1;
   56         } else x[i]++;
   57 
   58         if (y==0) break;
   59     }
   60 
   61     return;
   62 }
   63 
   64 
   65 /* size holds the size of the IV (counter in this mode).
   66  * This is the block size.
   67  */
   68 int _init_mcrypt( CTR_BUFFER* buf, void *key, int lenofkey, void *IV, int size)
   69 {
   70     buf->c_counter = buf->enc_counter = NULL;
   71     
   72 /* For ctr */
   73     buf->c_counter_pos = 0;
   74     buf->blocksize = size;
   75 
   76     buf->c_counter=calloc( 1, size);
   77     if (buf->c_counter==NULL) goto freeall;
   78 
   79     buf->enc_counter=calloc( 1, size);
   80     if (buf->enc_counter==NULL) goto freeall;
   81     
   82     if (IV!=NULL) {
   83     memcpy(buf->enc_counter, IV, size);
   84     memcpy(buf->c_counter, IV, size);
   85     }
   86 
   87 /* End ctr */
   88 
   89     return 0;
   90     freeall:
   91         free(buf->c_counter);
   92         free(buf->enc_counter);
   93         return -1;
   94 }
   95 
   96 int _mcrypt_set_state( CTR_BUFFER* buf, byte *IV, int size)
   97 {
   98     buf->c_counter_pos = IV[0];
   99     memcpy(buf->c_counter, &IV[1], size-1);
  100     memcpy(buf->enc_counter, &IV[1], size-1);
  101 
  102     return 0;
  103 }
  104 
  105 int _mcrypt_get_state( CTR_BUFFER* buf, byte *IV, int *size)
  106 {
  107     if (*size < buf->blocksize + 1) {
  108         *size = buf->blocksize + 1;
  109         return -1;
  110     }
  111     *size = buf->blocksize + 1;
  112 
  113     IV[0] = buf->c_counter_pos;
  114     memcpy( &IV[1], buf->c_counter, buf->blocksize);
  115 
  116     return 0;
  117 }
  118 
  119 
  120 void _end_mcrypt( CTR_BUFFER* buf) {
  121     free(buf->c_counter);
  122     free(buf->enc_counter);
  123 }
  124 
  125 inline static
  126 void xor_stuff( CTR_BUFFER *buf, void* akey, void (*func)(void*,void*), byte* plain,  int blocksize, int xor_size) 
  127 {
  128     void (*_mcrypt_block_encrypt) (void *, void *);
  129 
  130     _mcrypt_block_encrypt = func;
  131 
  132     if (xor_size == blocksize) {
  133         if (buf->c_counter_pos == 0) {
  134 
  135             memcpy( buf->enc_counter, buf->c_counter, blocksize);
  136             _mcrypt_block_encrypt(akey, buf->enc_counter);
  137 
  138             memxor( plain, buf->enc_counter, blocksize);
  139 
  140             increase_counter( buf->c_counter, blocksize);
  141 
  142 
  143         } else {
  144             int size = blocksize - buf->c_counter_pos;
  145 
  146             memxor( plain, &buf->enc_counter[buf->c_counter_pos],
  147                 size);
  148         
  149             increase_counter( buf->c_counter, blocksize);
  150 
  151             memcpy( buf->enc_counter, buf->c_counter, blocksize);
  152             _mcrypt_block_encrypt(akey, buf->enc_counter);
  153 
  154             memxor( &plain[size], buf->enc_counter,
  155                 buf->c_counter_pos);
  156 
  157             /* buf->c_counter_pos remains the same */
  158 
  159         }
  160     } else { /* xor_size != blocksize */
  161         if (buf->c_counter_pos == 0) {
  162             memcpy( buf->enc_counter, buf->c_counter, blocksize);
  163             _mcrypt_block_encrypt(akey, buf->enc_counter);
  164 
  165             memxor( plain, buf->enc_counter, xor_size);
  166             buf->c_counter_pos = xor_size;
  167         } else {
  168             int size = blocksize - buf->c_counter_pos;
  169             int min_size =  size < xor_size ? size: xor_size;
  170 
  171             memxor( plain, &buf->enc_counter[buf->c_counter_pos],
  172                 min_size); 
  173 
  174             buf->c_counter_pos += min_size;
  175 
  176             if (min_size >= xor_size)
  177                 return;
  178 
  179             increase_counter( buf->c_counter, blocksize);
  180 
  181             memcpy( buf->enc_counter, buf->c_counter, blocksize);
  182             _mcrypt_block_encrypt(akey, buf->enc_counter);
  183 
  184             memxor( &plain[min_size], buf->enc_counter,
  185                 xor_size - min_size);
  186 
  187             buf->c_counter_pos = xor_size - min_size;
  188 
  189         }
  190     
  191     }
  192     return;
  193 }
  194 
  195 int _mcrypt( CTR_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
  196 {               /* plaintext can be any size */
  197     byte *plain;
  198     word32 *fplain = plaintext;
  199     int i, j=0;
  200     int modlen;
  201 
  202     plain = plaintext;
  203     for (j = 0; j < len / blocksize; j++) {
  204 
  205         xor_stuff( buf, akey, func, plain, blocksize, blocksize);
  206 
  207         plain += blocksize;
  208 
  209 /* Put the new register */
  210 
  211     }
  212     modlen = len % blocksize;
  213     if (modlen > 0) {
  214         /* This is only usefull if encrypting the
  215          * final block. Otherwise you'll not be
  216          * able to decrypt it.
  217          */
  218 
  219         xor_stuff( buf, akey, func, plain, blocksize, modlen);
  220 
  221     }
  222     
  223     return 0;
  224 }
  225 
  226 
  227 int _mdecrypt( CTR_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
  228 {               /* plaintext can be any size */
  229     return _mcrypt( buf, plaintext, len, blocksize, akey, func, func2);
  230 }
  231 
  232 int _has_iv() { return 1; }
  233 int _is_block_mode() { return 0; }
  234 int _is_block_algorithm_mode() { return 1; }
  235 const char *_mcrypt_get_modes_name() { return "CTR";}
  236 int _mcrypt_mode_get_size () {return sizeof(CTR_BUFFER);}
  237 
  238 
  239 word32 _mcrypt_mode_version() {
  240     return 20020307;
  241 }
  242 
  243 #ifdef WIN32
  244 # ifdef USE_LTDL
  245 WIN32DLL_DEFINE int main (void)
  246 {
  247        /* empty main function to avoid linker error (see cygwin FAQ) */
  248 }
  249 # endif
  250 #endif