- x={
- a7,a6,a5,a4,a3,a2,a1,a0
- b7,b6,b5,b4,b3,b2,b1,b0
- c7,c6,c5,c4,c3,c2,c1,c0
- d7,d6,d5,d4,d3,d2,d1,d0
- }
- y={
- e7,e6,e5,e4,e3,e2,e1,e0
- f7,f6,f5,f4,f3,f2,f1,f0
- g7,g6,g5,g4,g3,g2,g1,g0
- h7,h6,h5,h4,h3,h2,h1,h0
- }
要将他们转化成如下的形式- x={
- a7,b7,c7,d7,e7,f7,g7,h7
- a6,b6,c6,d6,e6,f6,g6,h6
- a5,b5,c5,d5,e5,f5,g5,h5
- a4,b4,c4,d4,e4,f4,g4,h4
- }
- y={
- a3,b3,c3,d3,e3,f3,g3,h3
- a2,b2,c2,d2,e2,f2,g2,h2
- a1,b1,c1,d1,e1,f1,g1,h1
- a0,b0,c0,d0,e0,f0,g0,h0
- }
可以看到转化后x中只有n7,n6,n5,n4部分,y中只有n3,n2,n1,n0的部分(n取a,b,c,d,e,f,g,h)
那么,我们可以用位运算,先把这些位的高低部分分离出来,分别放在x和y中
即
x1 = (x&0xf0f0f0f0) | ((y>>4)&0x0f0f0f0f)
y1 = ((x<<4)&0xf0f0f0f0) | (y&0x0f0f0f0f)
这个时候x1,y1变为- x1={
- a7,a6,a5,a4,e7,e6,e5,e4
- b7,b6,b5,b4,f7,f6,f5,f4
- c7,c6,c5,c4,g7,g6,g5,g4
- d7,d6,d5,d4,h7,h6,h5,h4
- }
- y2={
- a3,a2,a1,a0,e3,e2,e1,e0
- b3,b2,b1,b0,f3,f2,f1,f0
- c3,c2,c1,c0,g3,g2,g1,g0
- d3,d2,d1,d0,h3,h2,h1,h0
- }
这个时候再看x内部的情况
我们需要把n7,n6放在x的前面,n5,n4放在x的后面
用上面的方式放的话就是这样的
x2 = (x1 & 0xcccc0000) | ((x1<<14) & 0x33330000) | ((x1>>14) & 0x0000cccc) | (x1&0x00003333);
这个时候x1变成x2- x2={
- a7,a6,c7,c6,e7,e6,g7,g6
- b7,b6,d7,d6,f7,f6,h7,h6
- a5,a4,c5,c4,e5,e4,g5,g4
- b5,b4,d5,d4,f5,f4,h5,h4
- }
其实这一步的目的是把(a5,a4-c7,c6),(e5,e4-g7,g6),(b5,b4-d7,d6),(f5,f4-h7,h6)这些位交換位置
对于单个的位a,b交换,有这样的算法
t = a^b
a = t^a
b = t^b
对于多个位也可以用这样的算法
t = (a5,a4^c7,c6),(e5,e4^g7,g6),(b5,b4^d7,d6),(f5,f4^h7,h6) ==> x1^(x1>>14)&0xcccc; 这个时候t里面就只包含了这些位的异或信息- t={
- a5^c7,a4^c6,0,0,e5^g7,e4^g6,0,0,
- b5^d7,b4^d6,0,0,f5^h7,f4^h6,0,0,
- }
下面取出c7,c6,g7,g6,d7,d6,h7,h6
x2 = x1 ^ t<<14
再取出a5,a4,e5,e4,b5,b4,f5,f4
x2 = x1^t
合并后就是
x2 = x1 ^ t ^ (t<<14)
最后一步把n7放在第一排,n6放在第二排的算法推导后可以得到
t = (x2 ^ (x2 >> 7)) & 0x00AA00AA; x3 = x2 ^ t ^ (t << 7);
最后写成代码就是
- void transpose8(unsigned char A[8], int m, int n, unsigned char B[8]) {
- unsigned long x,y,t;
- x = A[0]|(A[1]<<8)|(A[2]<<16)|(A[3]<<24);
- y = A[4]|(A[5]<<8)|(A[6]<<16)|(A[7]<<24);
- t = x;
- x = (x&0xf0f0f0f0) | ((y>>4)&0x0f0f0f0f);
- y = ((t<<4)&0xf0f0f0f0) | (y&0x0f0f0f0f);
- t = x^(x>>14) & 0x0000cccc; x = x^t^(t<<14);
- t = y^(y>>14) & 0x0000cccc; y = y^t^(t<<14);
- t = x^(x>>7) & 0x00AA00AA; x = x^t^(t<<7);
- t = y^(y>>7) & 0x00AA00AA; y = y^t^(t<<7);
- B[0] = x; B[1] = x>>8; B[2] = x>>16; B[3] = x>>24;
- B[4] = y; B[5] = y>>8; B[6] = y>>16; B[7] = y>>24;