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

📄 rsaprojectdlg.cpp

📁 /* RSA Demo 1.0 版 * 版权所有 (C) 2004 赵春生 * 2004.04.25 * http://timw.yeah.net * http://timw.126.com * 本程
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// If they both exist,the input file is read and converted into numbers.
// These numbers are divided into blocks smaller the modulus n that is given by
// the public key file. Each block is then encrypted independently following the 
// RSA algorithm c = m^e mod n, with e the encryption exponent fixed to 3 here.       


void CRSAProjectDlg::OnEncrypt() 
{

    Big t,m,y,n,nr,nl;
    ifstream public_key;
    ifstream input_file;
    ofstream output_file;

    static char line[500];
    static char buff[256];
    static char pbname[256],ifname[256],ofname[256];

	/* Open the public key file */
	UpdateData(TRUE);
	strcpy(ifname,m_FILE_ENC);	
	strcpy(pbname,m_PBK_ENC);
	UpdateData(FALSE);

	if (strlen(ifname) < 0) {
		AfxMessageBox("The input file name or is invalid.");
		return;
	}

	if (strlen(pbname) < 0) {
		AfxMessageBox("The public key file name or is invalid. Default file chosen.");
		strcpy(pbname,"");
		strcat(pbname,"defaultpublic.key");
	}

	public_key.open(pbname);
	if (!public_key) {
		AfxMessageBox("Unable to open public key file.");
		return;
	}

	/* Retrieve the modulus n from the public key file */
    BOOL last;
    int i,inputpt,keylength;
    miracl *mip=&precision;
    mip->IOBASE=16;
	public_key >> n;
	
	/* We have to find the key length that will enable us to seperate the message in acceptable blocks */
	/* This method to calculate this length was found in the documentation provided by Miracl          */
    nr=root(n,3);
    nl=nr*nr*nr-nr*nr;
	keylength=bits(nl)/7;

	/* Create the name for the output file. All ciphertexts are rsa files.*/
    strcpy(ofname,ifname);
    remove(ofname);
    strcat(ofname,".rsa");


	input_file.open(ifname,ios::in|ios::nocreate); 
	if (!input_file) {
		AfxMessageBox("Unable to open input file.");
		return;
	}

	output_file.open(ofname);
    inputpt=0;
    last=FALSE;

	/* We start the encryption by encoding the text line by line until the end of the file. */
	while (!last) { 
        
		input_file.getline(&line[inputpt],132);					// We retrieve a 
        if (input_file.eof() || input_file.fail()) last=TRUE;	// We have reached the end of the file
        strcat(line,"\n");

        inputpt=strlen(line);
        if (inputpt<keylength && !last) continue;

		/* When we have read as much as the key length, we can start to encrypt. */
        while (inputpt >= keylength) { 
            for (i = 0; i < keylength ; i++) {
                buff[i]=line[i];
			}

            buff[keylength]='\0';

            for (i = keylength; i <= inputpt ; i++) {
                line[i-keylength]=line[i];
			}

            inputpt -= keylength;
            
			mip->IOBASE=128;
            m=buff;
            
			/* Encrypt the block */
			t=pow(m,3,n);

            mip->IOBASE=16;
            output_file << t << endl;
        }

		/* The last block is usually smaller than the key length. */
        if (last && inputpt>0) { 

            mip->IOBASE=128;
            m=line;
            
			/* One technique we saw in the miracl documentation was too complete with random numbers */
			if (m < nr) { 
                m+=nr*(nr*nr-rand(nr));
            }

            t=pow(m,3,n);

            mip->IOBASE=16;

            output_file << t << endl;
        }
    }

	AfxMessageBox("Encryption successfully ended.");
	return;

}


/* Function to allow the user to visualize the ciphertext to decrypt and the decrypted text */
void CRSAProjectDlg::OnOpenDC() 
{
	static char buff[256];
    static char pbname[256],ifname[256],ofname[256];

	if(m_DCT.GetCheck() == TRUE) {
		UpdateData(TRUE);
		strcpy(ifname,m_FILE_DEC);
		UpdateData(FALSE);

		if (strlen(ifname)< 0) {
			AfxMessageBox("The plaintext file name is is invalid.");
			return;
		}
    
		strcat(buff, "Notepad.exe \"");
		strcat(ifname,"\"");
		strcat(buff,ifname);
		WinExec(buff, SW_SHOWNORMAL); 
		strcpy(ifname,"");
		strcpy(buff,"");
	}

	if( m_DT.GetCheck() == TRUE ) {

		UpdateData(TRUE);
		strcpy(ifname,m_FILE_DEC);
		UpdateData(FALSE);

		strcpy(ofname,ifname);
		remove(ofname);
		strcat(ofname,".out");

		if (strlen(ofname)< 0) {
			AfxMessageBox("The ciphertext file name is invalid.");
			return;
		}
    
		strcat(buff, "Notepad.exe \"");
		strcat(ofname,"\"");
		strcat(buff,ofname);
		WinExec(buff, SW_SHOWNORMAL); 
		strcpy(ifname,"");
		strcpy(ofname,"");
		strcpy(buff,"");
	}

	return;
	
}


/* Function to allow the user to visualize the plaintext and the ciphertext after encryption */
void CRSAProjectDlg::OnOpenEC() 
{
	static char buff[256];
    static char pbname[256],ifname[256],ofname[256];

	if( m_PT.GetCheck() == TRUE ) {

		UpdateData(TRUE);
		strcpy(ifname,m_FILE_ENC);
		UpdateData(FALSE);

		if (strlen(ifname)< 0) {
			AfxMessageBox("The plaintext file name is is invalid.");
			return;
		}
    
		strcat(buff, "Notepad.exe \"");
		strcat(ifname,"\"");
		strcat(buff,ifname);
		WinExec(buff, SW_SHOWNORMAL); 
		strcpy(ifname,"");
		strcpy(buff,"");
	}

	if( m_CT.GetCheck() == TRUE ) {

		UpdateData(TRUE);
		strcpy(ifname,m_FILE_ENC);
		UpdateData(FALSE);

		strcpy(ofname,ifname);
		remove(ofname);
		strcat(ofname,".rsa");

		if (strlen(ofname)< 0) {
			AfxMessageBox("The ciphertext file name is invalid.");
			return;
		}
    
		strcat(buff, "Notepad.exe \"");
		strcat(ofname,"\"");
		strcat(buff,ofname);
		WinExec(buff, SW_SHOWNORMAL); 
		strcpy(ifname,"");
		strcpy(ofname,"");
		strcpy(buff,"");
	}

	return;	
}

/**** Decryption function ****/
// This function first retrieves the name of the input file to decrypt and the private files. 

void CRSAProjectDlg::OnDecrypt() 
{
	/* Use the private keys to decrypt */
    int i;
    Big t,ep[NP],c,n,p[NP],d[NP],nr,nl;

    ifstream private_key;
    ifstream input_file;
    ofstream output_file;
    char prname[256],ifname[256],ofname[256];

	/* Open the public key file */
	UpdateData(TRUE);
	strcpy(ifname,m_FILE_DEC);	
	strcpy(prname,m_PRK_DEC);
	UpdateData(FALSE);

	if (strlen(prname)<0 || strlen(ifname)< 0) {
		AfxMessageBox("The input/private key file name or is invalid.");
		return;
	}

	private_key.open(prname);
	if (!private_key) {
		AfxMessageBox("Unable to open private key file.");
		return;
	}


    BOOL fout;	// Boolean that helps determine whether an output name is correct or not
    miracl *mip=&precision;
    mip->IOBASE=16;

	/* We store the private keys (prime numbers) in an array of Bigs of size 2. */
    for (i=0;i<NP;i++) {
        private_key >> p[i];
    }
	
	/* We calculate the modulus n = p*q */
    n=1;
    for (i=0;i<NP;i++) {
        n*=p[i];
    }

	/* We know have to calculate d the decryption exponent. We know that de = 1 mod (p-1)(q-1)       */
	/* THanks to the Chinese Remainder Theorem, we know that d = 1/e mod (p-1) and d = 1/e mod (q-1) */
    /* So the following method translates this idea with e = 3. This code was given in Miracl library*/
    for (i = 0; i < NP; i++) { 
        d[i]=(2*(p[i]-1)+1)/3;
    }

    /* Like in the encryption part. We have to determine the key length to be able to divide the text */
	/* into blocks that we can decrypt one by one.													  */

	nr=root(n,3);
    nl=nr*nr*nr-nr*nr;

	/* We create the name of the output file that is the decrypted text. All the decrypted files are .out files.*/
	strcpy(ofname,ifname);

	remove(ifname);
    strcat(ifname,".rsa");

	remove(ofname);
    strcat(ofname,".out");


    fout=FALSE;
    if (strlen(ofname)>0) { 
        fout=TRUE;
        output_file.open(ofname);
    }

    input_file.open(ifname,ios::in|ios::nocreate);
    if (!input_file) {
		AfxMessageBox("Decryption: Unable to open input file.");
        return;
    }
    
	Crt chinese(NP,p);   /* We use chinese remainder thereom */

	/* We enter an infinite loop that will only stop when we reach the end of the text c = 0 */
	forever {

        mip->IOBASE=16;
        input_file >> c;	// We retrieve a Big number from the file to decrypt
        
		if (c==0) break;	// The end of the file has been reached. We then stop.

        for (i=0;i<NP;i++) {
            ep[i]=pow(c,d[i],p[i]);	// m1 = c^d (mod p) and m2 = c^d (mod q)
		}

        t = chinese.eval(ep);			// We evaluate t the decrypted text with the Chinese Remainder Theorem.
		// A congruence mod a composite number n can be broken into simultaneous congruences mod each prme power factor of n.
		// Then we can recombine the resulting information.

        if (t >= nl) t%=nr;

        mip->IOBASE=128;
        if (fout) output_file << t;

    }

	AfxMessageBox("Decryption successfully completed.");
    return;

}


/* Function that calls another application that generates key files suitable for e = 3 */
/* The basic source code was provided by Miracl */
void CRSAProjectDlg::OnGenerate() 
{
	WinExec("PrimeGen.exe",SW_SHOWNORMAL);
	return;
}

⌨️ 快捷键说明

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