C++ code to generate a key of 1024 bits that Encrypt and Decrypt a file one char
ID: 3737370 • Letter: C
Question
C++ code to generate a key of 1024 bits that Encrypt and Decrypt a file one character at a time using the RSA algorithm. The decrypted file should be the same as the plaintext. The public key and private key should be in its own file, to later go back and use a key to decrypt a file? C++ code to generate a key of 1024 bits that Encrypt and Decrypt a file one character at a time using the RSA algorithm. The decrypted file should be the same as the plaintext. The public key and private key should be in its own file, to later go back and use a key to decrypt a file?Explanation / Answer
#include <string>
#include <iostream>
#include <fstream>
// CryptoPP
#include "sha.h"
#include "rsa.h"
#include "hex.h"
#include "osrng.h"
#include "secblock.h"
#include "aes.h"
#include "modes.h"
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
if (argc == 1)
{
cout << "Usage:" << endl
<< "To encrypt an RSA ciphertext: type "RSATestCPP rsa"" << endl
<< "To decrypt an AES ciphertext: type "RSATestCPP aes"" << endl;
return 0;
}
if (argc != 2)
{
cout << "Unknown option" << endl;
return 0;
}
if (string(argv[1]) == "rsa")
{
string strPublicKey;
ifstream fi("pubkey.txt", ios::in | ios::binary);
if (!fi)
{
cout << "Can't open pubkey.txt" << endl;
return 0;
}
char buf[8192];
while (fi)
{
fi.read(buf, 8192);
strPublicKey.append(buf, fi.gcount());
}
if (strPublicKey.size() <= 128)
{
cout << "Invalid public key size" << endl;
return 1;
}
CryptoPP::RSAES_OAEP_SHA_Encryptor pub;
CryptoPP::Integer nModulus((const byte*)(strPublicKey.data()), 128);
CryptoPP::RSAFunction& r = pub.AccessKey();
r.SetModulus(nModulus);
CryptoPP::Integer nExponent((const byte*)(strPublicKey.data()) + 128, strPublicKey.size() - 128);
r.SetPublicExponent(nExponent);
byte key[16];
byte IV[16];
CryptoPP::OS_GenerateRandomBlock(false, key, 16);
CryptoPP::OS_GenerateRandomBlock(false, IV, 16);
string strPlainText((char*)key, 16);
strPlainText.append((char*)IV, 16);
CryptoPP::AutoSeededRandomPool randPool;
string strCipherText;
CryptoPP::StringSource(
strPlainText,
true,
new CryptoPP::PK_EncryptorFilter(
randPool,
pub,
new CryptoPP::StringSink(strCipherText)
)
);
ofstream out("cipher.txt", ios::out | ios::binary);
if (!out)
{
cout << "Can't open cipher.txt" << endl;
return 0;
}
out.write(strCipherText.data(), strCipherText.size());
ofstream out2("aeskey.txt", ios::out | ios::binary);
if (!out2)
{
cout << "Can't open aeskey.txt" << endl;
return 0;
}
out2.write(strPlainText.data(), strPlainText.size());
cout << "Done" << endl;
return 0;
}
string strAES;
ifstream fi("aescipher.txt", ios::in | ios::binary);
if (!fi)
{
cout << "Can't open aescipher.txt" << endl;
return 0;
}
char buf[8192];
while (fi)
{
fi.read(buf, 8192);
strAES.append(buf, fi.gcount());
}
string strTmp;
ifstream fi2("aeskey.txt", ios::in | ios::binary);
if (!fi2)
{
cout << "Can't open aeskey.txt" << endl;
return 0;
}
while (fi2)
{
fi2.read(buf, 8192);
strTmp.append(buf, fi2.gcount());
}
if (strTmp.size() != 16 + 16)
{
cout << "Invalid key/IV size" << endl;
return 1;
}
byte pDst[16];
CryptoPP::CBC_Mode<CryptoPP::AES>::Decryption d;
d.SetKeyWithIV((const byte*)strTmp.data(), 16, (const byte*)(strTmp.data() + 16));
d.ProcessData((byte*)pDst, (const byte*)(strAES.data()), strAES.size());
// Stripping PKCS#7 padding bytes
unsigned int dwDstSize = strAES.size() - (unsigned int)(pDst[strAES.size() - 1]);
if (dwDstSize >= 16)
{
cout << "Invalid plaintext size: " << dwDstSize << " bytes" << endl;
return 1;
}
string strPlainText((char*)pDst, dwDstSize);
cout << "plaintext: " << strPlainText << " (" << dwDstSize << " bytes)" << endl;
return 0;
}
Related Questions
drjack9650@gmail.com
Navigate
Integrity-first tutoring: explanations and feedback only — we do not complete graded work. Learn more.