轻量级密码算法GFIT C代码

本文详细介绍了轻量级密码GIFT的算法原理及其实现过程,包括输入明文和密钥,进行SboxGS替换,比特位置映射,使用LFSR生成轮常数,更新密钥状态,以及多次迭代加密过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

轻量级密码GFIT介绍以及其C实现

GIFT的算法:
n={ 64,128 },k=128,r={28,40}分别为{GIFT-64,GIFT-128}。
(1) 输入n位的明文, k位的密钥.
(2) S ← SubCells(S)。Sbox GS的替换
(3) S ← PermBits(S)。从密码状态的比特位置i映射到比特位置P(i),bP(i) ← bi, ∀i ∈ {0,…,n − 1}。
(4) Ci ← f(Ci−1)。轮常数是使用6位仿射LFSR生成,其状态表示为(c5,c4,c3,c2,c1,c0)。它的更新功能定义为:(c5,c4,c3,c2,c1,c0) ← (c4,c3,c2,c1,c0,c5 ⊕ c4 ⊕ 1)。六位被初始化为零,并在被用在给定轮之前被更新。
(5) RK ← K。K = k7||k6||…||k0作为密钥状态,其中ki是16位。按k7||k6||…||k1||k0 ← k1 ≫ 2||k0 ≫ 12||…||k3||k2, 方式更新密钥状态,其中>>i 是16位字内的i位右移。
(6) S ← AddRoundKey(S,K,Ci)。1. 中间结果和Ci异或.bn-1←bn-1⊕1, b23←b23⊕c5,b19 ←b19⊕c4, b15 ←b15⊕c3, b11 ← b11⊕c2,b7 ← b7⊕c1 ,b3 ← b3⊕c0. 2. 中间结果和K异或.
(7) 重复执行(2)(3)(3)r次
(8) 输出密文C。

GIFT的流程图如下:
在这里插入图片描述

#include "stdafx.h"
#include<stdio.h>
#include<string.h>
#include"inttypes.h"
typedef uint8_t byte;
static const byte sbox[16] = {
	0x01, 0x0a, 0x04, 0x0c,
	0x06, 0x0f, 0x03, 0x09,
	0x02, 0x0d, 0x0b, 0x07,
	0x05, 0x00, 0x08, 0x0e
};
static  byte rPx[64] = {
	0,17,34,51,48,1,18,35,32,49,2,19,16,33,50,3,
	4,21,38,55,52,5,22,39,36,53,6,23,20,37,54,7,
	8,25,42,59,56,9,26,43,40,57,10,27,24,41,58,11,
	12,29,46,63,60,13,30,47,44,61,14,31,28,45,62,15
};
void printfs(const byte*s, int j = 16)
{
	for (int i = 0; i < j; i++)
	{
		printf("%X ", s[i]);
		if (i % 4 == 3) puts("");
	}
}
void Subcells(byte*s)
{
	for (int i = 0; i < 16; i++)
		s[i] = sbox[s[i]];
}
void Exchang(byte*s)
{
	int i;
	byte rowl, col, shift, rowl1;
	byte g[16];
	memset(g, 0, sizeof(g));
	for (i = 0; i < 64; i++)
	{                      
		rowl = i / 4;   
		col = i % 4;   
		shift = 0x01;  
		shift <<=col;
      rowl1 = rPx[i] / 4;
    	if (shift&s[rowl1])
	   g[rowl] |= shift;
	}
	memcpy(s, g, sizeof(g));
}
void addkeys(byte*k, byte*s)
{
	int i;
	byte p,shift,shift1,q,a,b;
	byte tmp;
	shift = 0x01;
	shift1 = 0x02;
	for (i = 0; i < 16; i++)
	{
		int 	j = i / 8;
		int  m = i;
		if (i >= 8) m = i - 8;
		p = k[j];
		a = (p >> m)&shift;
		q = k[j + 2];
		if ((i == 0) | (i == 8)) b = (q << 1)&shift1;
		else  b = (q >> (m - 1)&shift1);

	  if (a== shift)
	  {
		  if ((s[i] & shift) == a)
			  s[i]  = s[i] & 0x0e;
		  else
			  s[i] |= (s[i] & shift) ^ a;
	  }
	  if (b == shift1)
	  {
		  if ((s[i] & shift1) == b)
			  s[i] = s[i] & 0x0d;
		  else
			  s[i] |= (s[i] & shift1) ^ b ;
	  }
	}

}
void Updatekeys(byte*k)
{

	byte tmp[16], tmp1[16];
	for (int i = 0; i < 16; i++)
		tmp[i] =tmp1[i] = k[i];
	k[15] = ((tmp[3] >> 2) | (tmp[2] << 6)) & 0xff;
	k[14] = ((tmp1[3] << 6) | (tmp1[2] >> 2)) & 0xff;
	k[13] = ((tmp[1] << 4) | (tmp[0] >> 4)) & 0xff;
	k[12] = ((tmp1[1] >> 4) | (tmp1[0] << 4)) & 0xff;
	for (int j = 0; j < 12; j++) k[j] = tmp[j + 4];
}
void UpdateConstant(byte*c)
{
	byte a, c5, c4, c0;
	a = *c;
	c5 = (a >> 5) & 0x01;
	c4 = (a >> 4) & 0x01;
	c0 = c5 ^ c4 ^ 1;
	*c= ((*c<< 1) & 0x3f) | c0;

}
void addLFSR(byte*s, byte*c)
{
	byte a, b;
	byte shift = 0x08;
	a = *c;
	for (int i = 0; i < 6; i++)
	{
		b = ((a >> i) << 3)&shift;
		if (b == shift)
		{
			if ((s[i] & shift) == b)
				s[i] = s[i] & 0x07;
			else s[i] |= (s[i] & shift) ^ b;
		}
	}
	if (s[15] & shift)
		s[15] = s[15] & 0x07;
	else s[15] |= (s[15] & shift) ^ shift;

}
void Ercrypt(byte*s, byte*k)
{
	byte *Constants;
	byte a = 0x00;
	Constants = &a;
	int i;
	for (i = 0; i < 28; i++)
	{
		Subcells(s);
		Exchang(s);
		addkeys(k, s);
		UpdateConstant(Constants);
		addLFSR(s, Constants);
		Updatekeys(k);
	}
}

int main()
{
	byte k[16], p[16];
	for (int i = 0; i < 16; i++)
		p[i] = 0x0f;
	for (int i = 0; i < 16; i++)
		k[i] = 0xff;
	
	puts("Plaintext:"); printfs(p); puts("");
	puts("key:"); printfs(k, 16);    puts("");
	puts("Ercrypt:");
	Ercrypt(p, k);
	printfs(p);
	return 0;
}


评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值