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

📄 common.cpp

📁 这学期刚学密码学
💻 CPP
字号:
// Common.cpp : implementation file
//

#include "stdafx.h"
#include "RSA Tool.h"
#include "Common.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// CCommon property page

IMPLEMENT_DYNCREATE(CCommon, CPropertyPage)

CCommon::CCommon() : CPropertyPage(CCommon::IDD)
{
	//{{AFX_DATA_INIT(CCommon)
	m_keylen = 0;
	m_cit = _T("");
	m_clt = _T("");
	IsEncrypt = 1;
	SameCipher = 0;
	//}}AFX_DATA_INIT
}

CCommon::~CCommon()
{
}

void CCommon::DoDataExchange(CDataExchange* pDX)
{
	CPropertyPage::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CCommon)
	DDX_Control(pDX, IDC_CLTR, m_CLTR);
	DDX_Control(pDX, IDC_TIME, m_Showtime);
	DDX_Control(pDX, IDC_Q, m_Q);
	DDX_Control(pDX, IDC_P, m_P);
	DDX_Control(pDX, IDC_N, m_N);
	DDX_Control(pDX, IDC_E, m_E);
	DDX_Control(pDX, IDC_D, m_D);
	DDX_Control(pDX, IDC_CLT, m_CLT);
	DDX_Control(pDX, IDC_KEYLEN, m_KEYLEN);
	DDX_Control(pDX, IDC_CIT, m_CIT);
	DDX_CBIndex(pDX, IDC_KEYLEN, m_keylen);
	DDX_Text(pDX, IDC_CIT, m_cit);
	DDX_Text(pDX, IDC_CLT, m_clt);
	//}}AFX_DATA_MAP
}


BEGIN_MESSAGE_MAP(CCommon, CPropertyPage)
	//{{AFX_MSG_MAP(CCommon)
	ON_BN_CLICKED(IDC_GENERATEKYS, OnGeneratekys)
	ON_BN_CLICKED(IDC_ENCRYPT, OnEncrypt)
	ON_BN_CLICKED(IDC_DECRYPT, OnDecrypt)
	ON_BN_CLICKED(IDC_CLEAR, OnClear)
	ON_WM_CTLCOLOR()
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CCommon message handlers

void CCommon::OnGeneratekys() 
{
	CBigNumber bnP, bnQ, bnE, bnN, bnD, bnCMP;
	SYSTEMTIME before, after;
	char elapsed[10];
	char strP[MAX_PATH], strQ[MAX_PATH], strE[MAX_PATH], strN[350], strD[350];
	
	int len=2;
	
	for(int i = 0; i < m_KEYLEN.GetCurSel(); i++)
	{
		len *= 2;
	}
	//初始化
	
	GetLocalTime(&before);
	P.Init(0);
	Q.Init(0);
	N.Init(0);
	EUL.Init(0);
	E.Init(0);
	D.Init(0);
	bnP.Init(0);
	bnQ.Init(0);
	bnE.Init(0);
	
	// 生成指定bit的大数
	P.GetPrime(len);
	Q.GetPrime(len);
	bnP.Init(P);
	bnQ.Init(Q);
		
	bnP.BigNumberToString(strP);	// 把数组形式的大数转化成字符串	
	bnQ.BigNumberToString(strQ);	
	N.Init(bnP.Mul(bnQ));	// 计算 N = P * Q
	bnN.Init(N);
	bnN.BigNumberToString(strN);
	
	bnP.Init(P);
	bnQ.Init(Q);
	bnP.m_ulValue[0]--;		// P - 1	
	bnQ.m_ulValue[0]--;		// Q - 1
	EUL.Init(bnP.Mul(bnQ));	// EUL = (P-1) * (Q-1)
	
	do{
		bnE.GetPrime(len);	// 产生指定位数的公钥,这里以素数作为公钥,可以节省时间,但公钥的范围小了
		bnCMP.Init(0);
	}while(((N.Mod(bnE)).Cmp(bnCMP)) == 0);	// 产生的数与欧拉函数值除1外还有其他公因子
	
	E.Init(bnE);
	bnE.BigNumberToString(strE);	
	
	D.Init(E.SolEqu(EUL));	// 计算私钥	
	bnD.Init(D);
	bnD.BigNumberToString(strD);	
	GetLocalTime(&after);	// 计算花费时间
	memset(elapsed, 0, 10);
	bnP.GetElapsedTime(elapsed, before, after);
	m_Showtime.SetWindowText(elapsed);
	m_P.SetWindowText(strP);	// 在对话框中输出大数
	m_Q.SetWindowText(strQ);
	m_N.SetWindowText(strN);
	m_E.SetWindowText(strE);
	m_D.SetWindowText(strD);	
}

void CCommon::OnEncrypt() 
{
	char szCipher[350];
	CString strCipher, strClt, szBuf, strTemp, strBlock, strResult;
	CBigNumber bnPlain, bnCipher, pk, bnResult;		
	unsigned BlockSize = 12;	// 分组长度12字节,96比特
	unsigned long PlainSize;				// 明文转化成数字后的长度
	unsigned long Blocks = 0;					// 分组数
	BOOL finished = TRUE;		// 加密完成与否的标志
	unsigned long i = 0, j = 0, k = 0, nIndex = 0;
	SYSTEMTIME before, after;
	char elapsed[10];

	GetLocalTime(&before);
	
	m_cit = "";
	bnPlain.Init(0);
	m_CLT.GetWindowText(strClt);	// 获取用户输入的明文
	PlainSize = (unsigned long)strClt.GetLength();	// 计算明文长度
	
	if (E.Cmp(bnPlain) == 0){
		AfxMessageBox("请先产生密钥!");
		return ;
	}	
	
	if (PlainSize == 0){
		AfxMessageBox("请输入明文!");
		return ;
	}
	
	if (PlainSize % 12 != 0)	// 计算分组数
		Blocks = PlainSize / (unsigned long)BlockSize + 1;
	else
		Blocks = PlainSize / (unsigned long)BlockSize;
	
	iCount = Blocks;
	iLength = new unsigned long[iCount];	// 动态分配空间保存每次加密后的密文长度
	bnCipher.Init(0);	
	char temp1[MAX_PATH];
	char temp2[MAX_PATH];
	while(finished){		
		
		if (PlainSize - i < BlockSize)	// 最后剩下的长度不足一个分组
			BlockSize = PlainSize - i;
		strBlock = strClt.Mid(i, BlockSize);	// 获取分组
		bnPlain.StringToChars(temp1, strBlock);
		bnPlain.CharsToNumber(temp2, temp1);	// 把数字化的分组转换成字符串
		strResult = temp2;
		bnResult.Init(0);
		bnResult.StringToBigNumber(strResult);	// 把字符串转换成大数
		bnCipher.Init(bnResult.RsaEn(E, N));	// 加密
		memset(szCipher, 0, MAX_PATH);
		bnCipher.BigNumberToString(szCipher);	// 把大数转换成数字		
	
		iLength[j++] = strlen(szCipher);	// 得到每个密文分组的长度
		strTemp += szCipher;	// 把密文连接在一起,可能包含结束符
		
		i += BlockSize;			
		
		if ((unsigned long)i >= PlainSize)
			finished = FALSE;		
		
	}

	IsEncrypt = 0;	
	GetLocalTime(&after);	// 计算花费时间
	pk.GetElapsedTime(elapsed, before, after);
	m_Showtime.SetWindowText(elapsed);	
	m_CIT.SetWindowText(strTemp);
	
}

void CCommon::OnDecrypt() 
{
	if (IsEncrypt != 0 && SameCipher == 0){
		AfxMessageBox("请先进行加密!");
		return ;
	}
	
	if (SameCipher == 1){
		AfxMessageBox("已解密过相同的密文!");
		return ;
	}
	unsigned i = 0;
	CString strCipher, strPlain, strTemp, strResult, strBuf;
	CBigNumber bncit, bnclt;
	int nIndex = 0;
	SYSTEMTIME before, after;
	char elapsed[10];
	char szPlain[MAX_PATH];
	char szBuf[MAX_PATH];
		
	GetLocalTime(&before);	
	bncit.Init(0);
	bnclt.Init(0);
	
	m_CIT.GetWindowText(strCipher);	// 得到密文
	while(i < iCount){
		
		strTemp = strCipher.Mid(nIndex, iLength[i]);	// 获取与加密后长度对应的密文
		nIndex += iLength[i];
		
		// iLength[i]里面是保存的每次读取的字节数
		bncit.Init(0);
		bncit.StringToBigNumber(strTemp);	// 把字符串转换成大数
		
		bnclt.Init(bncit.RsaEn(D, N));	// 解密
		memset(szPlain, 0, MAX_PATH);
		memset(szBuf, 0, MAX_PATH);
		bnclt.BigNumberToString(szPlain);	// 把大数转换成数字
		bnclt.NumberToChars(szBuf, szPlain);		// 把数字转换成明文
		
		if (m_cit.GetLength() > 0){
			m_cit.Delete(m_cit.GetLength()-1, 1);
		}
		m_cit += szBuf;	// 连接明文
		m_cit += '0';	// 后移一个字节,以防前一个字节被替代,我发现m_cit的最后一个字节会被替换掉,但不知道原因。
		
		i++;
	}
	m_cit.SetAt(m_cit.GetLength()-1, '\0');
	strPlain = m_cit;
	IsEncrypt = 1;		// 此时不能再解密
	delete []iLength;	

	m_CLTR.SetWindowText(strPlain);
	GetLocalTime(&after);
	bncit.GetElapsedTime(elapsed, before, after);
	m_Showtime.SetWindowText(elapsed);
	
}

void CCommon::OnClear() 
{
	m_CLT.SetWindowText("");	// 用空串代替
	m_CIT.SetWindowText("");
	P.Init(0);	// 清零
	Q.Init(0);
	N.Init(0);
	D.Init(0);
	E.Init(0);
	EUL.Init(0);
	m_P.SetWindowText("");
	m_Q.SetWindowText("");
	m_N.SetWindowText("");
	m_E.SetWindowText("");
	m_D.SetWindowText("");
	m_CLTR.SetWindowText("");
	m_CLT.SetWindowText("");
	m_CIT.SetWindowText("");
	m_Showtime.SetWindowText("");	
}

HBRUSH CCommon::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor) 
{
	HBRUSH hbr = CPropertyPage::OnCtlColor(pDC, pWnd, nCtlColor);
	COLORREF bkcolor;

	if (pWnd->GetDlgCtrlID() == IDC_CLT) {
		bkcolor = RGB(0, 255, 0);
		HBRUSH hBrush = CreateSolidBrush(bkcolor);
		pDC->SetBkColor(bkcolor);
		return hBrush;
	} 
	return hbr;
}

⌨️ 快捷键说明

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