/* rc4.c */
/*
* This source code of RC4 algorithm is rewritten by Jeff Chen.
*/
#include "rc4.h"
/*
* This source code of RC4 algorithm is rewritten by Jeff Chen.
*/
/* 密钥长度为KL字节 */
void RC4_KSA(UCHAR *rc4key, int KL, RC4_STATE *state)
{
/*
* 注意: i不能定义为UCHAR, 否则
* for (i = 0; i < 256; i++)是死循环
*/
int i;
UCHAR j, tmp;
UCHAR *s = state->S;
/* Initialization */
state->i = 0; state->j = 0;
for (i = 0; i < 256; i++) s[i] = i;
/* Scrambling */
j = 0;
for (i = 0; i < 256; i++)
{
j += s[i] + rc4key[i % KL]; // 自动丢弃j的高字节部分
tmp = s[i]; s[i] = s[j]; s[j] = tmp;
}
}
/* 密钥长度固定为16字节 */
void RC4_KSA_128(UCHAR *rc4key, RC4_STATE *state)
{
/*
* 注意: i不能定义为UCHAR, 否则
* for (i = 0; i < 256; i++)是死循环
*/
int i;
UCHAR j, tmp;
UCHAR *s = state->S;
/* Initialization */
state->i = 0; state->j = 0;
for (i = 0; i < 256; i++) s[i] = i;
/* Scrambling */
j = 0;
for (i = 0; i < 256; i++)
{
j += s[i] + rc4key[i & 0x0f]; // 自动丢弃j的高字节部分
tmp = s[i]; s[i] = s[j]; s[j] = tmp;
}
}
/* output one byte of keystream */
UCHAR RC4_PRGA(RC4_STATE *state)
{
UCHAR *s, *i, *j, tmp;
s = state->S;
i = &(state->i);
j = &(state->j);
++*i;
*j += s[*i];
tmp = s[*i]; s[*i] = s[*j]; s[*j] = tmp;
return s[(s[*i] + s[*j]) & 0xff]; // 注意: 必须加上 "& 0xff"
}
/*
Combine the two stage of rc4 algorithm.
output kslen bytes of keystream.
here keylen is the byte length of rc4 key.
*/
void RC4(UCHAR *rc4key, int keylen, UCHAR *keystream, int kslen)
{
int n;
RC4_STATE state;
if (keylen == 16) RC4_KSA_128(rc4key, &state);
else RC4_KSA(rc4key, keylen, &state);
for (n = 0; n < kslen; n++)
keystream[n] = RC4_PRGA(&state);
}