Реализовал программу для шифрования по алгоритму RSA, всё работает правильно. Только у меня выполняется кодирование согласно таблице кодировки Windows 1251. По заданию же необходимо, чтобы было только 32 символа (заглавные русские буквы). И чтобы они имели порядковые номера от 1 до 32 соответственно (как в алфавите). Пытаюсь так сделать, но не выходит.
В данной программе ещё всё хорошо работает с английскими буквами и с цифрами, а с кириллицей нет.
Подскажите, пожалуйста, как можно это реализовать?
Полный код программы:
#include <iostream>
#include <math.h>
#include <string.h>
#include <string>
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <conio.h>
using namespace std;
bool isPrime(long int prime);
long int calculateE(long int t);
long int greatestCommonDivisor(long int e, long int t);
long int calculateD(long int e, long int t);
long int encrypt(long int i, long int e, long int n);
long int decrypt(long int i, long int d, long int n);
int main()
{
//setlocale(LC_ALL, "Russian");
SetConsoleCP(1251);
SetConsoleOutputCP(1251);
long int p, q, n, t, e, d;
long int encryptedText[100];
memset(encryptedText, 0, sizeof(encryptedText));
long int decryptedText[100];
memset(decryptedText, 0, sizeof(decryptedText));
bool flag;
string msg;
// Cоздание открытого и секретного ключей
// 1. Выбираются два различных случайных простых числа p и q заданного размера
do
{
cout << "Введите простое число p:";
cin >> p;
flag = isPrime(p);
if (flag == false)
{
cout << "\nОшибка ввода (Данное число не является простым)\n" << endl;
}
} while (flag == false);
do
{
cout << "Введите простое число q:";
cin >> q;
flag = isPrime(q);
if (flag == false)
{
cout << "\nОшибка ввода (Данное число не является простым)\n" << endl;
}
} while (flag == false);
// 2. Вычисляется их произведение n = p*q, которое называется модулем.
n = p * q;
cout << "\nРезультат произведения n = p*q = " << n << endl;
// 3. Вычисляется значение функции Эйлера от числа n: φ(n) = (p−1)⋅(q−1)
t = (p - 1) * (q - 1);
cout << "Результат вычисления функции Эйлера: t = " << t << endl;
// 4. Выбирается целое число e ( 1 < e < φ(n) ), взаимно простое со значением функции Эйлера (t)
// Число e называется открытой экспонентой
e = calculateE(t);
// 5. Вычисляется число d, мультипликативно обратное к числу e по модулю φ(n), то есть число, удовлетворяющее сравнению:
// d ⋅ e ≡ 1 (mod φ(n))
d = calculateD(e, t);
// 6. Пара {e, n} публикуется в качестве открытого ключа RSA
cout << "\nОткрытый ключ (e = " << e << ", n = " << n << ")" << endl;
// 7. Пара {d, n} играет роль закрытого ключа RSA и держится в секрете
cout << "Закрытый ключ (d = " << d << ", n = " << n << ")" << endl;
cout << "\nВведите сообщение: " << endl;
cin.ignore();
getline(std::cin, msg);
cout << "\nВаше сообщение: " << msg << endl;
// encryption
for (long int i = 0; i < msg.length(); i++)
{
encryptedText[i] = encrypt(msg[i], e, n);
}
cout << "\nЗашифрованное сообщение:";
for (long int i = 0; i < msg.length(); i++)
{
printf("%c", (char)encryptedText[i]);
}
//decryption
for (long int i = 0; i < msg.length(); i++)
{
decryptedText[i] = decrypt(encryptedText[i], d, n);
}
cout << "\n\nРасшифрованное сообщение:";
for (long int i = 0; i < msg.length(); i++)
{
printf("%c", (char)decryptedText[i]);
}
cout << endl << endl;
_getch();
return 0;
}
bool isPrime(long int prime)
{
long int i, j;
j = (long int)sqrt((long double)prime);
for (i = 2; i <= j; i++)
{
if (prime % i == 0)
{
return false;
}
}
return true;
}
long int calculateE(long int t)
{
// Выбирается целое число e ( 1 < e < t ) // взаимно простое со значением функции Эйлера (t)
long int e;
for (e = 2; e < t; e++)
{
if (greatestCommonDivisor(e, t) == 1)
{
return e;
}
}
return -1;
}
long int greatestCommonDivisor(long int e, long int t)
{
while (e > 0)
{
long int myTemp;
myTemp = e;
e = t % e;
t = myTemp;
}
return t;
}
long int calculateD(long int e, long int t)
{
// Вычисляется число d, мультипликативно обратное к числу e по модулю φ(n), то есть число, удовлетворяющее сравнению:
// d ⋅ e ≡ 1 (mod φ(n))
long int d;
long int k = 1;
while (1)
{
k = k + t;
if (k % e == 0)
{
d = (k / e);
return d;
}
}
}
long int encrypt(long int i, long int e, long int n)
{
long int current, result;
current = i - 65;
result = 1;
for (long int j = 0; j < e; j++)
{
result = result * current;
result = result % n;
}
return result;
}
long int decrypt(long int i, long int d, long int n)
{
long int current, result;
current = i;
result = 1;
for (long int j = 0; j < d; j++)
{
result = result * current;
result = result % n;
}