POK
|
00001 /* 00002 * POK header 00003 * 00004 * The following file is a part of the POK project. Any modification should 00005 * made according to the POK licence. You CANNOT use this file or a part of 00006 * this file is this part of a file for your own project 00007 * 00008 * For more information on the POK licence, please see our LICENCE FILE 00009 * 00010 * Please follow the coding guidelines described in doc/CODING_GUIDELINES 00011 * 00012 * Copyright (c) 2007-2009 POK team 00013 * 00014 * Created by julien on Fri Dec 11 16:32:31 2009 00015 */ 00016 00017 /* crypto/bf/bf_enc.c */ 00018 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 00019 * All rights reserved. 00020 * 00021 * This package is an SSL implementation written 00022 * by Eric Young (eay@cryptsoft.com). 00023 * The implementation was written so as to conform with Netscapes SSL. 00024 * 00025 * This library is free for commercial and non-commercial use as long as 00026 * the following conditions are aheared to. The following conditions 00027 * apply to all code found in this distribution, be it the RC4, RSA, 00028 * lhash, DES, etc., code; not just the SSL code. The SSL documentation 00029 * included with this distribution is covered by the same copyright terms 00030 * except that the holder is Tim Hudson (tjh@cryptsoft.com). 00031 * 00032 * Copyright remains Eric Young's, and as such any Copyright notices in 00033 * the code are not to be removed. 00034 * If this package is used in a product, Eric Young should be given attribution 00035 * as the author of the parts of the library used. 00036 * This can be in the form of a textual message at program startup or 00037 * in documentation (online or textual) provided with the package. 00038 * 00039 * Redistribution and use in source and binary forms, with or without 00040 * modification, are permitted provided that the following conditions 00041 * are met: 00042 * 1. Redistributions of source code must retain the copyright 00043 * notice, this list of conditions and the following disclaimer. 00044 * 2. Redistributions in binary form must reproduce the above copyright 00045 * notice, this list of conditions and the following disclaimer in the 00046 * documentation and/or other materials provided with the distribution. 00047 * 3. All advertising materials mentioning features or use of this software 00048 * must display the following acknowledgement: 00049 * "This product includes cryptographic software written by 00050 * Eric Young (eay@cryptsoft.com)" 00051 * The word 'cryptographic' can be left out if the rouines from the library 00052 * being used are not cryptographic related :-). 00053 * 4. If you include any Windows specific code (or a derivative thereof) from 00054 * the apps directory (application code) you must include an acknowledgement: 00055 * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" 00056 * 00057 * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND 00058 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00059 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 00060 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 00061 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 00062 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 00063 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 00064 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 00065 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 00066 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 00067 * SUCH DAMAGE. 00068 * 00069 * The licence and distribution terms for any publically available version or 00070 * derivative of this code cannot be changed. i.e. this code cannot simply be 00071 * copied and put under another distribution licence 00072 * [including the GNU Public Licence.] 00073 */ 00074 00075 #ifdef POK_NEEDS_PROTOCOLS_BLOWFISH 00076 00077 #include "blowfish.h" 00078 #include "bf_locl.h" 00079 00080 /* Blowfish as implemented from 'Blowfish: Springer-Verlag paper' 00081 * (From LECTURE NOTES IN COMPUTER SCIENCE 809, FAST SOFTWARE ENCRYPTION, 00082 * CAMBRIDGE SECURITY WORKSHOP, CAMBRIDGE, U.K., DECEMBER 9-11, 1993) 00083 */ 00084 00085 #if (BF_ROUNDS != 16) && (BF_ROUNDS != 20) 00086 #error If you set BF_ROUNDS to some value other than 16 or 20, you will have \ 00087 to modify the code. 00088 #endif 00089 00090 void BF_encrypt(BF_LONG *data, const BF_KEY *key) 00091 { 00092 #ifndef BF_PTR2 00093 register BF_LONG l,r; 00094 register const BF_LONG *p,*s; 00095 00096 p=key->P; 00097 s= &(key->S[0]); 00098 l=data[0]; 00099 r=data[1]; 00100 00101 l^=p[0]; 00102 BF_ENC(r,l,s,p[ 1]); 00103 BF_ENC(l,r,s,p[ 2]); 00104 BF_ENC(r,l,s,p[ 3]); 00105 BF_ENC(l,r,s,p[ 4]); 00106 BF_ENC(r,l,s,p[ 5]); 00107 BF_ENC(l,r,s,p[ 6]); 00108 BF_ENC(r,l,s,p[ 7]); 00109 BF_ENC(l,r,s,p[ 8]); 00110 BF_ENC(r,l,s,p[ 9]); 00111 BF_ENC(l,r,s,p[10]); 00112 BF_ENC(r,l,s,p[11]); 00113 BF_ENC(l,r,s,p[12]); 00114 BF_ENC(r,l,s,p[13]); 00115 BF_ENC(l,r,s,p[14]); 00116 BF_ENC(r,l,s,p[15]); 00117 BF_ENC(l,r,s,p[16]); 00118 #if BF_ROUNDS == 20 00119 BF_ENC(r,l,s,p[17]); 00120 BF_ENC(l,r,s,p[18]); 00121 BF_ENC(r,l,s,p[19]); 00122 BF_ENC(l,r,s,p[20]); 00123 #endif 00124 r^=p[BF_ROUNDS+1]; 00125 00126 data[1]=l&0xffffffffL; 00127 data[0]=r&0xffffffffL; 00128 #else 00129 register BF_LONG l,r,t,*k; 00130 00131 l=data[0]; 00132 r=data[1]; 00133 k=(BF_LONG*)key; 00134 00135 l^=k[0]; 00136 BF_ENC(r,l,k, 1); 00137 BF_ENC(l,r,k, 2); 00138 BF_ENC(r,l,k, 3); 00139 BF_ENC(l,r,k, 4); 00140 BF_ENC(r,l,k, 5); 00141 BF_ENC(l,r,k, 6); 00142 BF_ENC(r,l,k, 7); 00143 BF_ENC(l,r,k, 8); 00144 BF_ENC(r,l,k, 9); 00145 BF_ENC(l,r,k,10); 00146 BF_ENC(r,l,k,11); 00147 BF_ENC(l,r,k,12); 00148 BF_ENC(r,l,k,13); 00149 BF_ENC(l,r,k,14); 00150 BF_ENC(r,l,k,15); 00151 BF_ENC(l,r,k,16); 00152 #if BF_ROUNDS == 20 00153 BF_ENC(r,l,k,17); 00154 BF_ENC(l,r,k,18); 00155 BF_ENC(r,l,k,19); 00156 BF_ENC(l,r,k,20); 00157 #endif 00158 r^=k[BF_ROUNDS+1]; 00159 00160 data[1]=l&0xffffffffL; 00161 data[0]=r&0xffffffffL; 00162 #endif 00163 } 00164 00165 #ifndef BF_DEFAULT_OPTIONS 00166 00167 void BF_decrypt(BF_LONG *data, const BF_KEY *key) 00168 { 00169 #ifndef BF_PTR2 00170 register BF_LONG l,r; 00171 register const BF_LONG *p,*s; 00172 00173 p=key->P; 00174 s= &(key->S[0]); 00175 l=data[0]; 00176 r=data[1]; 00177 00178 l^=p[BF_ROUNDS+1]; 00179 #if BF_ROUNDS == 20 00180 BF_ENC(r,l,s,p[20]); 00181 BF_ENC(l,r,s,p[19]); 00182 BF_ENC(r,l,s,p[18]); 00183 BF_ENC(l,r,s,p[17]); 00184 #endif 00185 BF_ENC(r,l,s,p[16]); 00186 BF_ENC(l,r,s,p[15]); 00187 BF_ENC(r,l,s,p[14]); 00188 BF_ENC(l,r,s,p[13]); 00189 BF_ENC(r,l,s,p[12]); 00190 BF_ENC(l,r,s,p[11]); 00191 BF_ENC(r,l,s,p[10]); 00192 BF_ENC(l,r,s,p[ 9]); 00193 BF_ENC(r,l,s,p[ 8]); 00194 BF_ENC(l,r,s,p[ 7]); 00195 BF_ENC(r,l,s,p[ 6]); 00196 BF_ENC(l,r,s,p[ 5]); 00197 BF_ENC(r,l,s,p[ 4]); 00198 BF_ENC(l,r,s,p[ 3]); 00199 BF_ENC(r,l,s,p[ 2]); 00200 BF_ENC(l,r,s,p[ 1]); 00201 r^=p[0]; 00202 00203 data[1]=l&0xffffffffL; 00204 data[0]=r&0xffffffffL; 00205 #else 00206 register BF_LONG l,r,t,*k; 00207 00208 l=data[0]; 00209 r=data[1]; 00210 k=(BF_LONG *)key; 00211 00212 l^=k[BF_ROUNDS+1]; 00213 #if BF_ROUNDS == 20 00214 BF_ENC(r,l,k,20); 00215 BF_ENC(l,r,k,19); 00216 BF_ENC(r,l,k,18); 00217 BF_ENC(l,r,k,17); 00218 #endif 00219 BF_ENC(r,l,k,16); 00220 BF_ENC(l,r,k,15); 00221 BF_ENC(r,l,k,14); 00222 BF_ENC(l,r,k,13); 00223 BF_ENC(r,l,k,12); 00224 BF_ENC(l,r,k,11); 00225 BF_ENC(r,l,k,10); 00226 BF_ENC(l,r,k, 9); 00227 BF_ENC(r,l,k, 8); 00228 BF_ENC(l,r,k, 7); 00229 BF_ENC(r,l,k, 6); 00230 BF_ENC(l,r,k, 5); 00231 BF_ENC(r,l,k, 4); 00232 BF_ENC(l,r,k, 3); 00233 BF_ENC(r,l,k, 2); 00234 BF_ENC(l,r,k, 1); 00235 r^=k[0]; 00236 00237 data[1]=l&0xffffffffL; 00238 data[0]=r&0xffffffffL; 00239 #endif 00240 } 00241 00242 void BF_cbc_encrypt(const unsigned char *in, unsigned char *out, long length, 00243 const BF_KEY *schedule, unsigned char *ivec, int encrypt) 00244 { 00245 register BF_LONG tin0,tin1; 00246 register BF_LONG tout0,tout1,xor0,xor1; 00247 register long l=length; 00248 BF_LONG tin[2]; 00249 00250 if (encrypt) 00251 { 00252 n2l(ivec,tout0); 00253 n2l(ivec,tout1); 00254 ivec-=8; 00255 for (l-=8; l>=0; l-=8) 00256 { 00257 n2l(in,tin0); 00258 n2l(in,tin1); 00259 tin0^=tout0; 00260 tin1^=tout1; 00261 tin[0]=tin0; 00262 tin[1]=tin1; 00263 BF_encrypt(tin,schedule); 00264 tout0=tin[0]; 00265 tout1=tin[1]; 00266 l2n(tout0,out); 00267 l2n(tout1,out); 00268 } 00269 if (l != -8) 00270 { 00271 n2ln(in,tin0,tin1,l+8); 00272 tin0^=tout0; 00273 tin1^=tout1; 00274 tin[0]=tin0; 00275 tin[1]=tin1; 00276 BF_encrypt(tin,schedule); 00277 tout0=tin[0]; 00278 tout1=tin[1]; 00279 l2n(tout0,out); 00280 l2n(tout1,out); 00281 } 00282 l2n(tout0,ivec); 00283 l2n(tout1,ivec); 00284 } 00285 else 00286 { 00287 n2l(ivec,xor0); 00288 n2l(ivec,xor1); 00289 ivec-=8; 00290 for (l-=8; l>=0; l-=8) 00291 { 00292 n2l(in,tin0); 00293 n2l(in,tin1); 00294 tin[0]=tin0; 00295 tin[1]=tin1; 00296 BF_decrypt(tin,schedule); 00297 tout0=tin[0]^xor0; 00298 tout1=tin[1]^xor1; 00299 l2n(tout0,out); 00300 l2n(tout1,out); 00301 xor0=tin0; 00302 xor1=tin1; 00303 } 00304 if (l != -8) 00305 { 00306 n2l(in,tin0); 00307 n2l(in,tin1); 00308 tin[0]=tin0; 00309 tin[1]=tin1; 00310 BF_decrypt(tin,schedule); 00311 tout0=tin[0]^xor0; 00312 tout1=tin[1]^xor1; 00313 l2nn(tout0,tout1,out,l+8); 00314 xor0=tin0; 00315 xor1=tin1; 00316 } 00317 l2n(xor0,ivec); 00318 l2n(xor1,ivec); 00319 } 00320 tin0=tin1=tout0=tout1=xor0=xor1=0; 00321 tin[0]=tin[1]=0; 00322 } 00323 00324 00325 void BF_ecb_encrypt(const unsigned char *in, unsigned char *out, 00326 const BF_KEY *key, int encrypt) 00327 { 00328 BF_LONG l,d[2]; 00329 00330 n2l(in,l); d[0]=l; 00331 n2l(in,l); d[1]=l; 00332 if (encrypt) 00333 BF_encrypt(d,key); 00334 else 00335 BF_decrypt(d,key); 00336 l=d[0]; l2n(l,out); 00337 l=d[1]; l2n(l,out); 00338 l=d[0]=d[1]=0; 00339 } 00340 00341 00342 #endif 00343 00344 #endif /* POK_NEEDS_PROTOCOLS */