@2017libin
2019-12-16T13:07:43.000000Z
字数 1841
阅读 61
密码学
使用笨方法,按照书上所说的三步走,还没想出更加高效的实现方法。输入一个十六进制数并输出相应的s_box中的值,进行简单的查表操作就可以了。具体代码如下。
#include <iostream>#include <iomanip>using namespace std;int C = 0X63;int s_box[16][16];int x, y, d;int q = 0, r = 0;//定义G(2^8)中的 x*2int mul2(int x) {if (x & 0x80) return ((x << 1) ^ 27) & 255; //&255表示 只取一个字节else return (x << 1) & 255;}//G(2^8)乘法int mul(int x, int y) {int r = 0, tmp = x;while (y) {if (y % 2) r ^= tmp; //加法取模相当于亦或tmp = mul2(tmp);y /= 2;}return r;}//获取最高位1的位置int hight_index(int x) {if (!x) return 0; //x等于0,返回0。表示不存在最高位的1int index = 1;while (x >> 1) {x = x >> 1;++index;}return index;}//G(2^n)除法void divi(int a, int b) {int tmp = 0;r = 0; q = 0;while (b <= a) {tmp = 1;int indexB = hight_index(b), indexA = hight_index(a);int dis = indexA - indexB;tmp = tmp << dis;q += tmp;a = a ^ (tmp*b);}r = a;}//ax + by = d = gcd(a,b), 其中a>bint egcd(int a, int b) {int x1 = 1, y1 = 0, x2 = 0, y2 = 1;int tmp_x, tmp_y;while (b) {divi(a, b);tmp_x = x2;tmp_y = y2;x2 = x1 ^ mul(x2, q); //1式 减去 (2式 * q), 接着轮换系数y2 = y1 ^ mul(y2, q);x1 = tmp_x;y1 = tmp_y;a = b;b = r;}return y1;}// ---------------------------------------- 分割线 -------------------------------//第二步:对s_box中的每个元素求逆元void inverseSBox() {for (int i = 0; i < 16; ++i)for (int j = 0; j < 16; ++j)s_box[i][j] = egcd(283, s_box[i][j]);}int getIndexBit(int x, int index) {return (x >> index) & 1;}int transform(int x) {int trans_x = 0;for (int i = 0; i < 8; ++i) {int tmp = 0;tmp = getIndexBit(x, i) ^ getIndexBit(x, (i + 4) % 8) ^ getIndexBit(x, (i + 5) % 8) ^ getIndexBit(x, (i + 6) % 8) ^ getIndexBit(x, (i + 7) % 8) ^ getIndexBit(C, i);trans_x = trans_x | (tmp << i);}return trans_x;}//第三步:对s_box中的元素进行变化void transformSBox() {for (int i = 0; i < 16; ++i) {for (int j = 0; j < 16; ++j) {s_box[i][j] = transform(s_box[i][j]);}}}void printSBox() {for (int i = 0; i < 16; ++i) {for (int j = 0; j < 16; ++j)cout << hex << setw(3) << s_box[i][j] << " ";cout << endl;}}int main() {for (int i = 0; i < 16; ++i)for (int j = 0; j < 16; ++j)cin >> hex >> s_box[i][j];inverseSBox();transformSBox();printSBox();//输入一个值并输出相应的s_box值int xy;cin >> hex >> xy;int xx = (xy >> 4) & 15;int yy = xy & 15;cout << hex << xy << "对应的s_box值为" << s_box[xx][yy] << endl;system("pause");return 0;}
