⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 haval.cpp

📁 300中加密方法
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// haval.cpp - modified by Wei Dai from Yuliang Zheng's HAVAL.c
// distributed with Yuliang Zheng's permission

/*
 *  Reference:
 *       Y. Zheng, J. Pieprzyk and J. Seberry:
 *       ``HAVAL --- a one-way hashing algorithm with variable
 *       length of output'', Advances in Cryptology --- AUSCRYPT'92,
 *       Lecture Notes in Computer Science, Springer-Verlag, 1993.
 *
 *  Author:     Yuliang Zheng
 *              Department of Computer Science
 *              University of Wollongong
 *              Wollongong, NSW 2522, Australia
 *              Email: yuliang@cs.uow.edu.au
 *              Voice: +61 42 21 4331 (office)
 */

#include "pch.h"
#include "haval.h"

NAMESPACE_BEGIN(CryptoPP)

HAVAL::HAVAL(unsigned int digestSize, unsigned int pass)
	: IteratedHash<word32>(DATASIZE, DIGESTSIZE),
	  digestSize(digestSize), pass(pass)
{
	assert(digestSize >= 16 && digestSize <= 32 && digestSize%4==0);
	assert(pass >= 3 && pass <= 5);

	Init();
}

void HAVAL::Init()
{
	countLo = countHi = 0;

	digest[0] = 0x243F6A88;
	digest[1] = 0x85A308D3;
	digest[2] = 0x13198A2E;
	digest[3] = 0x03707344;
	digest[4] = 0xA4093822;
	digest[5] = 0x299F31D0;
	digest[6] = 0x082EFA98;
	digest[7] = 0xEC4E6C89;
}

inline void HAVAL::vTransform(word32 *buf, const word32 *in)
{
	if (pass==3)
		HAVAL3::Transform(buf, in);
	else if (pass==4)
		HAVAL4::Transform(buf, in);
	else
		HAVAL5::Transform(buf, in);
}

void HAVAL::HashBlock(const word32 *input)
{
#ifdef IS_LITTLE_ENDIAN
	vTransform(digest, input);
#else
	byteReverse(data.ptr, input, (unsigned int)DATASIZE);
	vTransform(digest, data);
#endif
}

void HAVAL::Final (byte *hash)
{
	PadLastBlock(118, 1);	// first byte of padding for HAVAL is 1 instead of 0x80
	CorrectEndianess(data, data, 120);

	data[29] &= 0xffff;
	data[29] |= ((word32)digestSize<<25) | ((word32)pass<<19) | ((word32)VERSION<<16);
	data[30] = countLo;
	data[31] = countHi;

	vTransform(digest, data);
	Tailor(digestSize*8);
	CorrectEndianess(digest, digest, digestSize);
	memcpy(hash, digest, digestSize);

	Init();		// reinit for next use
}

// tailor the last output
void HAVAL::Tailor(unsigned int FPTLEN)
{
	word32 temp;

	switch (FPTLEN)
	{
	case 128:
		temp = (digest[7] & 0x000000FF) | 
			   (digest[6] & 0xFF000000) | 
			   (digest[5] & 0x00FF0000) | 
			   (digest[4] & 0x0000FF00);
		digest[0] += rotr(temp,  8U);

		temp = (digest[7] & 0x0000FF00) | 
			   (digest[6] & 0x000000FF) | 
			   (digest[5] & 0xFF000000) | 
			   (digest[4] & 0x00FF0000);
		digest[1] += rotr(temp, 16U);

		temp  = (digest[7] & 0x00FF0000) | 
				(digest[6] & 0x0000FF00) | 
				(digest[5] & 0x000000FF) | 
				(digest[4] & 0xFF000000);
		digest[2] += rotr(temp, 24U);

		temp = (digest[7] & 0xFF000000) | 
			   (digest[6] & 0x00FF0000) | 
			   (digest[5] & 0x0000FF00) | 
			   (digest[4] & 0x000000FF);
		digest[3] += temp;
		break;

	case 160:
		temp = (digest[7] &  (word32)0x3F) | 
			   (digest[6] & ((word32)0x7F << 25)) |  
			   (digest[5] & ((word32)0x3F << 19));
		digest[0] += rotr(temp, 19U);

		temp = (digest[7] & ((word32)0x3F <<  6)) | 
			   (digest[6] &  (word32)0x3F) |  
			   (digest[5] & ((word32)0x7F << 25));
		digest[1] += rotr(temp, 25U);

		temp = (digest[7] & ((word32)0x7F << 12)) | 
			   (digest[6] & ((word32)0x3F <<  6)) |  
			   (digest[5] &  (word32)0x3F);
		digest[2] += temp;

		temp = (digest[7] & ((word32)0x3F << 19)) | 
			   (digest[6] & ((word32)0x7F << 12)) |  
			   (digest[5] & ((word32)0x3F <<  6));
		digest[3] += temp >> 6; 

		temp = (digest[7] & ((word32)0x7F << 25)) | 
			   (digest[6] & ((word32)0x3F << 19)) |  
			   (digest[5] & ((word32)0x7F << 12));
		digest[4] += temp >> 12;
		break;

	case 192:
		temp = (digest[7] &  (word32)0x1F) | 
			   (digest[6] & ((word32)0x3F << 26));
		digest[0] += rotr(temp, 26U);

		temp = (digest[7] & ((word32)0x1F <<  5)) | 
			   (digest[6] &  (word32)0x1F);
		digest[1] += temp;

		temp = (digest[7] & ((word32)0x3F << 10)) | 
			   (digest[6] & ((word32)0x1F <<  5));
		digest[2] += temp >> 5;

		temp = (digest[7] & ((word32)0x1F << 16)) | 
			   (digest[6] & ((word32)0x3F << 10));
		digest[3] += temp >> 10;

		temp = (digest[7] & ((word32)0x1F << 21)) | 
			   (digest[6] & ((word32)0x1F << 16));
		digest[4] += temp >> 16;

		temp = (digest[7] & ((word32)0x3F << 26)) | 
			   (digest[6] & ((word32)0x1F << 21));
		digest[5] += temp >> 21;
		break;

	case 224:
		digest[0] += (digest[7] >> 27) & 0x1F;
		digest[1] += (digest[7] >> 22) & 0x1F;
		digest[2] += (digest[7] >> 18) & 0x0F;
		digest[3] += (digest[7] >> 13) & 0x1F;
		digest[4] += (digest[7] >>  9) & 0x0F;
		digest[5] += (digest[7] >>  4) & 0x1F;
		digest[6] +=  digest[7]        & 0x0F;
		break;

	case 256:
		break;

	default:
		assert(false);
	}
}

/*
#define f_1(x6, x5, x4, x3, x2, x1, x0)          \
		   ((x1) & ((x0) ^ (x4)) ^ (x2) & (x5) ^ \
			(x3) & (x6) ^ (x0))
*/

#define f_1(x6, x5, x4, x3, x2, x1, x0)          \
	((x1&(x0^x4)) ^ (x2&x5) ^ (x3&x6) ^ x0)

/*
#define f_2(x6, x5, x4, x3, x2, x1, x0)                         \
		   ((x2) & ((x1) & ~(x3) ^ (x4) & (x5) ^ (x6) ^ (x0)) ^ \
			(x4) & ((x1) ^ (x5)) ^ (x3) & (x5) ^ (x0))
*/

#define f_2(x6, x5, x4, x3, x2, x1, x0)                         \
	(((x4&x5)|x2) ^ (x0|x2) ^ (x2&((x1&~x3)^x6)) ^ (x3&x5) ^ (x1&x4))

/*
#define f_3(x6, x5, x4, x3, x2, x1, x0)          \
		   ((x3) & ((x1) & (x2) ^ (x6) ^ (x0)) ^ \
			(x1) & (x4) ^ (x2) & (x5) ^ (x0))
*/

#define f_3(x6, x5, x4, x3, x2, x1, x0)          \
	((x3 & ((x1&x2) ^ x6 ^ x0)) ^ (x1&x4) ^ (x2&x5) ^ x0)

/*
#define f_4(x6, x5, x4, x3, x2, x1, x0)                                 \
		   ((x4) & ((x5) & ~(x2) ^ (x3) & ~(x6) ^ (x1) ^ (x6) ^ (x0)) ^ \
			(x3) & ((x1) & (x2) ^ (x5) ^ (x6)) ^                        \
			(x2) & (x6) ^ (x0))
*/

#define f_4(x6, x5, x4, x3, x2, x1, x0)          \
	((((~x2&x5)^(x3|x6)^x1^x0)&x4) ^ (((x1&x2)^x5^x6)&x3) ^ (x2&x6) ^ x0)


/*
#define f_5(x6, x5, x4, x3, x2, x1, x0)             \
		   ((x0) & ((x1) & (x2) & (x3) ^ ~(x5)) ^   \
			(x1) & (x4) ^ (x2) & (x5) ^ (x3) & (x6))
*/

#define f_5(x6, x5, x4, x3, x2, x1, x0)          \
	((((x0&x2&x3)^x4)&x1) ^ ((x0^x2)&x5) ^ (x3&x6) ^ x0)

/*
 * Permutations phi_{i,j}, i=3,4,5, j=1,...,i.
 *
 * PASS = 3:

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -