S盒的构造及C语言实现
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
S盒的构造及C语言实现
在AES算法中,字节代换的设计是加密算法设计的主要部分之一.其设计不仅考虑到抗差分密码分析和线性密码分析,而且还考虑到抗代数计算的攻击,目的是保证整个密码系统的安全性.字节代换要求Nr轮的加密过程都要对状态矩阵中的字节求其在有限域GF(2。
)上的乘法逆元和作GF(2)上的仿射变换,以使它的差分均匀性和线性偏差都达到最佳,这就要多次用到大运算量的非线性字节变换操作.由于在有限域GF(2。
)上共有256个元素,而每个元素在特定的模运算下存在逆元,我们则可以预先通过一定的算法计算出每个元素的乘法逆元,再经相应的仿射变换后做成一个8位输入8位输出的s盒,供各轮字节代换和密钥操作的调用,从而可以缩短明文加密时间,提高整体加密效率.
2.1 有限域GF(2。
)乘法逆元
算法中,状态的每一个字节的8位二进制数都可以以多项式的形式表示成有限域GF(2 )上的元
素,如,表示成多项式的形式:
要计算上的乘法,必须先确定一个上的8次不可约多项式m(x ),对于AES
密码,这个8次不可约多项式确定为: (十六进制表示为
“11B”).有限域GF(2 )上的乘法取逆可用:表示,a(x)是用多
项式表示的状态字节,为乘法取逆后的输出.
2.2 GF(2)仿射变换
仿射变换对状态字节在有限域GF(2。
)上的乘法逆元进行字节变换操作,设输入字节为
,经过仿射变换后的输出字节为,则有下面
的变换关系:
为二进制数01100011或十六进制的63.用矩阵表示的仿射变换为:
此矩阵运算,实际可以转换成字节的位运算:矩阵第一行由低位到高位二进制为:[1 0 0 0 1 1 1 1],换成16进制为:0xF1。
类似的,剩下的几行可以顺次表示成:0xe3,0xc7,0x8f,0x1f,0x3e,0x7c,0xf8。
这些十六进制数存放在数组b[]中。
实现上述矩阵的乘法就可以转化成
B1=b[0]&Ai+b[1]&Ai+…+b[7]&Ai+0x63.此公式中的加法为异或运算。
由此,由下面程序可实现S盒的替换。
2.3 s盒的C语言实现
unsigned char S_BOX[256] = {0};//用于存储S盒
void gen_table(void)//实现S盒函数
{
unsigned char pow_tab[256];
unsigned char log_tab[256];
unsigned char mid_tab[256];
unsigned char sbx_tab[256];
unsigned char b[8] = {0xf1,0xe3,0xc7,0x8f,0x1f,0x3e,0x7c,0xf8};
int i,j,k,p;
//求0-255的可逆项
for (i =0,p=1;i<256;i++)
{
pow_tab[i] = p;
log_tab[p] = i;
p = p^(p<<1)^(p&0x80?0x11b:0) ;
}
for (i = 0;i<256;i++)
{
mid_tab[i] = (i?pow_tab[255-log_tab[i]]:0);
}
//求0-255的可逆项并存储在mid_tab中
for (i = 0;i<256;i++)
{
int t = 0,m = 0,mid = 0,tab = 0;
for (j =0;j<8;j++)
{
m=mid=(b[j]&mid_tab[i]);//实现公式中的b[0]&Ai+b[1]&Ai+…+b[7]&Ai
for (k=0;k<8;k++)
{
int n=(mid>>1) ;
if (m!=(n<<1))
{
t++;
}
mid = n;
m = mid;
}
if (t%2>0)
{
int temp = 1;
for (k=0;k<j;k++)
{
temp = temp<<1;
}
tab +=temp;
}
t = 0;
}
sbx_tab[i] = tab^0x63;//实现公式中的+0x63
}
//以下是拷贝存储并打印相关信息
memcpy(S_BOX,sbx_tab,256);
printf("*************不可约简多项式的可逆项************\n");
for (i=1;i<=256;i++)
{
printf("%.2X ",mid_tab[i-1]);
if (i%16 == 0)
{
printf("\n");
}
}
printf("\n");
printf("**********************S-Box*********************\n");
for (i=1;i<=256;i++)
{
printf("%.2X ",S_BOX[i-1]);
if (i%16 == 0)
{
printf("\n");
}
}
}
2.4 s盒的应用举例
例如,在实际当中要对十六进制数7b进行字节代换。
7b表示成二进制是01111011,对应的多项式,由欧几里德扩充算法算出其逆元多项式。
,即逆元为十六进制数06,对06进行仿射变换,将其二进制表示00000110代入仿射变换矩阵中得到输出00100001,十六进制数为21,此21就是十六进制数7b进行字节代换的结果.在这一过程中多次用到了大运算量的非线性字节变换操作,而采用S盒进行字节代换时,只须将十六进制数7b作为S盒的输入,直接查表得到代换结果为21.计算机进行查表运算的速度是很快的,因此S盒的使用加快了字节代换的速度,提高了AES整体加密效率.。