使用c语言实现DH秘钥分配算法

使用c语言实现DH秘钥分配算法

DH算法原理

密钥分配

    • 选择一个大素数p, 选择一个整数g(g < p);
    • 通信方A选择一个随机数a,并发送  mod p 给 通信方B;
    • 通信方B选择一个随机数b,并发送  mod p 给 通信方A;
    • 通信方A计算k1 = ( mod p)a mod p;
    • 通信方B计算k2 = ( mod p)b mod p;
    • 由此,k1 = k2。
DH.h
#pragma once
#include <tommath.h>
#include <time.h>
#include <iostream>
#include <Windows.h>

using namespace std;

#define SUBKEY_LENGTH 78  //  >512 bit

void Create_number(mp_int *number, int mode);
int Miller_rabin(mp_int *number);
void Create_prime_number(mp_int *number);
void initial();
void mp_print(mp_int *number);
void Write_num_2_File(char *file_name, mp_int *num);
DH.cpp
#include "DH.h"

mp_int two;
mp_int five;
mp_int zero;
mp_int one;

void Create_number(mp_int *number, int mode)
{
	int i;

	srand((unsigned)time(NULL));

	char temp_number[SUBKEY_LENGTH + 1];

	temp_number[0] = rand() % 9 + 1 + 48;

	if (0 == mode)
	{
		int temp;
		for (i = 1; i <= SUBKEY_LENGTH - 2; i++)
			temp_number[i] = rand() % 10 + 48;

		temp = rand() % 10;
		if (0 == temp % 2)
			temp++;

		if (5 == temp)
			temp = 7;

		temp_number[SUBKEY_LENGTH - 1] = temp + 48;

		temp_number[SUBKEY_LENGTH] = '\0';
	}
	else if (1 == mode)
	{
		int digit = rand() % (SUBKEY_LENGTH - 2) + 2;

		for (i = 1; i <= digit - 1; i++)
			temp_number[i] = rand() % 10 + 48;

		temp_number[digit] = '\0';
	}

	mp_read_radix(number, temp_number, 10);
}


int Miller_rabin(mp_int *number)
{
	int result;
	mp_int base;
	mp_init_size(&base, SUBKEY_LENGTH);

	Create_number(&base, 1);

	mp_prime_miller_rabin(number, &base, &result);

	mp_clear(&base);

	return result;
}


void Create_prime_number(mp_int *number)
{
	mp_int r;
	mp_init(&r);

	int time = 100;
	int result;
	int i;

	Create_number(number, 0);

	while (1)
	{
		mp_prime_is_divisible(number, &result);

		if (0 != result)
		{
			do
			{
				mp_add(number, &two, number);
				mp_mod(number, &five, &r);
			} while (MP_EQ == mp_cmp_mag(&zero, &r));

			continue;
		}

		for (i = 0; i < time; i++)
		{
			if (!Miller_rabin(number))
				break;
		}

		if (i == time)
			return;
		else
		{
			do
			{
				mp_add(number, &two, number);
				mp_mod(number, &five, &r);
			} while (MP_EQ == mp_cmp_mag(&zero, &r));
		}
	}
}


void initial()
{
	mp_init_set_int(&two, 2);
	mp_init_set_int(&five, 5);
	mp_init_set_int(&zero, 0);
	mp_init_set_int(&one, 1);
}


void mp_print(mp_int *number)
{
	char str[SUBKEY_LENGTH * 2 + 1];
	mp_toradix(number, str, 10);
	cout << str << endl;
}


void Write_num_2_File(char *file_name, mp_int *num)
{
	remove(file_name);
	FILE *fp = fopen(file_name, "w+");

	if (NULL == fp)
	{
		cout << "open file error!" << endl;
		return;
	}

	char str[SUBKEY_LENGTH * 2];
	
	mp_toradix(num, str, 10);

	fprintf(fp, "%s", str);

	fclose(fp);
}
main.h
#pragma once
#include "DH.h"
main.cpp
#include "main.h"


int main()
{
	initial();

	mp_int p, g, a, b, ka, kb;

	mp_init_size(&p, SUBKEY_LENGTH);
	mp_init_size(&g, SUBKEY_LENGTH);
	mp_init_size(&a, SUBKEY_LENGTH);
	mp_init_size(&b, SUBKEY_LENGTH);
	mp_init_size(&ka, SUBKEY_LENGTH);
	mp_init_size(&kb, SUBKEY_LENGTH);

	Create_prime_number(&p);

	Create_number(&g, 1);
	Sleep(1000);
	
	Create_number(&a, 1);
	Sleep(1000);

	Create_number(&b, 1);
	
	mp_exptmod(&g, &a, &p, &ka);
	mp_exptmod(&g, &b, &p, &kb);

	cout << "p: ";
	mp_print(&p);
	cout << "g: ";
	mp_print(&g);
	cout << "a: ";
	mp_print(&a);
	cout << "b: ";
	mp_print(&b);

	cout << "ka: ";
	mp_print(&ka);
	cout << "kb: ";
	mp_print(&kb);
	
	Write_num_2_File("d:\\DH_p.txt", &p);
	Write_num_2_File("d:\\DH_g.txt", &g);
	Write_num_2_File("d:\\DH_a.txt", &a);
	Write_num_2_File("d:\\DH_b.txt", &b);
	Write_num_2_File("d:\\DH_ka.txt", &ka);
	Write_num_2_File("d:\\DH_kb.txt", &kb);

	mp_clear_multi(&p, &g, &a, &b, &ka, &kb, NULL);

	return 0;
}

  • 11
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值