Home | History | Annotate | Download | only in crypto
      1 /*
      2  * RC4 stream cipher
      3  * Copyright (c) 2002-2005, Jouni Malinen <j (at) w1.fi>
      4  *
      5  * This program is free software; you can redistribute it and/or modify
      6  * it under the terms of the GNU General Public License version 2 as
      7  * published by the Free Software Foundation.
      8  *
      9  * Alternatively, this software may be distributed under the terms of BSD
     10  * license.
     11  *
     12  * See README and COPYING for more details.
     13  */
     14 
     15 #include "includes.h"
     16 
     17 #include "common.h"
     18 #include "crypto.h"
     19 
     20 #define S_SWAP(a,b) do { u8 t = S[a]; S[a] = S[b]; S[b] = t; } while(0)
     21 
     22 int rc4_skip(const u8 *key, size_t keylen, size_t skip,
     23 	     u8 *data, size_t data_len)
     24 {
     25 	u32 i, j, k;
     26 	u8 S[256], *pos;
     27 	size_t kpos;
     28 
     29 	/* Setup RC4 state */
     30 	for (i = 0; i < 256; i++)
     31 		S[i] = i;
     32 	j = 0;
     33 	kpos = 0;
     34 	for (i = 0; i < 256; i++) {
     35 		j = (j + S[i] + key[kpos]) & 0xff;
     36 		kpos++;
     37 		if (kpos >= keylen)
     38 			kpos = 0;
     39 		S_SWAP(i, j);
     40 	}
     41 
     42 	/* Skip the start of the stream */
     43 	i = j = 0;
     44 	for (k = 0; k < skip; k++) {
     45 		i = (i + 1) & 0xff;
     46 		j = (j + S[i]) & 0xff;
     47 		S_SWAP(i, j);
     48 	}
     49 
     50 	/* Apply RC4 to data */
     51 	pos = data;
     52 	for (k = 0; k < data_len; k++) {
     53 		i = (i + 1) & 0xff;
     54 		j = (j + S[i]) & 0xff;
     55 		S_SWAP(i, j);
     56 		*pos++ ^= S[(S[i] + S[j]) & 0xff];
     57 	}
     58 
     59 	return 0;
     60 }
     61