Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.77/13: Рейтинг темы: голосов - 13, средняя оценка - 4.77
0 / 0 / 1
Регистрация: 15.12.2015
Сообщений: 19

Алгоритм RSA Дешифровка русских символов в ANCII

22.12.2015, 08:49. Показов 2628. Ответов 8
Метки rsa (Все метки)

Студворк — интернет-сервис помощи студентам
Пишу учебный алгоритм шифрования RSA, чтобы затем его распараллелить с помощью OMP.
Проблемой с кодировкой ANCII на этом форуме сталкивалась не я одна, но решить ее подобным образом у меня не получается.
Реализую в VS2012, Windows Form.

MyForm.cpp
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
unsigned char* StringToChar(String^ str)
{
    IntPtr ptrToNativeString = System::Runtime::InteropServices::Marshal::StringToHGlobalAnsi(str);
    return (unsigned char*)(ptrToNativeString.ToPointer());
}
unsigned int* StringToInt(String^ str, int &length)
{
    String^ sepStr = " \n";
    array<Char>^separator = sepStr->ToCharArray();
    array<String^>^split = nullptr;
    str = str->TrimEnd();
    split = str->Split(separator);
 
    length = split->Length;
    unsigned int* resultArray = new unsigned int[length];
    for (int i = 0; i < length; i++)
        resultArray[i] = Convert::ToInt32(split[i]);
    return resultArray;
}
void CryptRSA::MyForm::btnCrypt_Click(System::Object^ sender, System::EventArgs^ e)
{
    if (!String::IsNullOrWhiteSpace(txtCrypt->Text))
    {
        String^ txt = txtCrypt->Text;
        int length = txt->Length;
        if (length <= MAX)
        {
            //Преобразование string в массив char
            unsigned char *Text = new unsigned char[length];
            Text = StringToChar(txt);
            
            GenerateKeys();
 
            //Вывод зашифрованного текста
            unsigned int *cryptoCode = new unsigned int[length];
            cryptoCode = serial->Crypt(Text, length);
            //delete [] Text;
 
            String^ outStr;
            for (int i = 0; i < length; i++)
                outStr = String::Format(outStr+"{0} ", cryptoCode[i]);
            txtEncrypt->Text = outStr;
            stripCryptLbl->Text="Текст зашифрован";
    }
    else
    {
        MessageBox::Show("Не найден текст для шифрования", "Алгоритм RSA",
            MessageBoxButtons::OK, MessageBoxIcon::Error);
    }
}
void CryptRSA::MyForm::btnEncrypt_Click(System::Object^ sender, System::EventArgs^ e)
{
    if (!String::IsNullOrWhiteSpace(txtEncrypt->Text))
    {
        String^ code = txtEncrypt->Text;
        int length = 0;
        unsigned int *arrayCode = StringToInt(code, length);
        
        char *Text = serial->Encrypt(arrayCode, length);
        String^ outStr;
        for (int i = 0; i < length; i++)
            outStr = String::Format(outStr+"{0}", Text[i]);
        txtCrypt->Text = outStr;
        stripCryptLbl->Text="Текст дешифрован";
 
    }
    else
    {
        MessageBox::Show("Не найден текст для дешифрования", "Алгоритм RSA",
            MessageBoxButtons::OK, MessageBoxIcon::Error);
    }
}

SerialRSA.cpp
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
unsigned int* SerialRSA::Crypt(unsigned char* Text, int lenght)
{
    //Массив для хранения шифротекста.
    unsigned int *CryptoText = new unsigned int [lenght];
 
    //Получение из введённых данных десятичного кода ASCII и
    //дальнейшее его преобразование по формуле c = (ASCIIcode^e)%n.
    int c;
    for (int j = 0; j < lenght; j++)
    {
        c = 1;
        unsigned int i = 0;
        int ASCIIcode = (static_cast<int>(Text[j]));
        while (i<e)
        {
            c = c*ASCIIcode;
            c = c%n;
            i++;
        }
        CryptoText[j] = c;
    }
    return CryptoText;
}
 
char* SerialRSA::Encrypt(unsigned int* Code, int lenght)
{
    //Массив для хранения шифротекста.
    char *Tdecrypt = new char[lenght];
 
    //Расшифровка полученного кода по формуле m = (Codei^d)%n и перевод его в десятичный код ASCII.
    int m;
    for (int j = 0; j < lenght; j++)
    {
        m = 1;
        unsigned int i = 0;
        while (i<d)
        {
            m = m*Code[j];
            m = m%n;
            i++;
        }
        Tdecrypt[j] = static_cast<char>(m);
    }
    return Tdecrypt;
}
Суть проблемы: в textbox ввожу "ма", шифрую, при расшифровке получаю "-20-32" (причем в отладчике "-20" это "м", а выводится не то, что хочется). Как сделать так, чтобы выводилось правильно?
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
22.12.2015, 08:49
Ответы с готовыми решениями:

Алгоритм RSA на JAVA шифровка/дешифровка
Доброе время суток, форумчане! На днях выдали лабораторное задание, которое сказали реализовать на джаве, с которым я знакома пару недель!...

Неверная дешифровка RSA
try: input = raw_input except NameError: pass try: chr = unichr except NameError: pass p = int(input('Введите...

RSA дешифровка, проверка на успешность
Можно ли , используя класс RSACryptoServiceProvider проверить правильно ли были расшифрованы данные? Или же придется хешировать начальные...

8
7804 / 6568 / 2988
Регистрация: 14.04.2014
Сообщений: 28,705
22.12.2015, 15:06
Во-первых, encrypt означает "зашифровать", а у тебя функция расшифровывает, значит должно быть decrypt.
Проблемы вы себе сами создаёте, используя кодировки из прошлого века. Если ты перед шифрованием преобразуешь в ANSI, то нужно делать обратное преобразование после расшифровки, т. к. форма ANSI не понимает.
0
0 / 0 / 1
Регистрация: 15.12.2015
Сообщений: 19
27.12.2015, 15:02  [ТС]
Проблемы вы себе сами создаёте, используя кодировки из прошлого века.
Автоматическое преобразование символ->код, код->символ я нашла только для ANSII, а как сделать для utf-8, к примеру (это же считается более современной кодировкой, верно), я так и не нашла доступного примера.
Если ты перед шифрованием преобразуешь в ANSI, то нужно делать обратное преобразование после расшифровки, т. к. форма ANSI не понимает.
В функцию Crypt (или как вы сказали, правильнее Encrypt) приходит массив символов Text, для каждого элемента которого в цикле происходит преобразование:
C++
1
int ASCIIcode = (static_cast<int>(Text[j]));
и далее идет сам алгоритм шифрования.
И при расшифровке: сначала алгоритм, а последняя операция в цикле - преобразование:
C++
1
Tdecrypt[j] = static_cast<char>(m);
Что не так?
0
7804 / 6568 / 2988
Регистрация: 14.04.2014
Сообщений: 28,705
27.12.2015, 15:11
Вот здесь ты конвертируешь перед зашифрованием:
C++
1
2
3
4
5
unsigned char* StringToChar(String^ str)
{
    IntPtr ptrToNativeString = System::Runtime::InteropServices::Marshal::StringToHGlobalAnsi(str);
    return (unsigned char*)(ptrToNativeString.ToPointer());
}
Надо делать обратное после расшифровки. Из ANSI в нормальную кодировку.
Цитата Сообщение от Annushkash Посмотреть сообщение
как сделать для utf-8
Ну просто берёшь и зашифровываешь отдельные байты как если бы это была обычная ANSI-строка.
0
0 / 0 / 1
Регистрация: 15.12.2015
Сообщений: 19
27.12.2015, 21:40  [ТС]
В этой функции я не конвертирую, а преобразую строку в массив символов. И в таком случае - как сделать обратно Вы не подскажите? Я видела в msdn преобразование только в одну сторону.

Ну просто берёшь и зашифровываешь отдельные байты как если бы это была обычная ANSI-строка.
А можно на примере? Или ссылку какую-нить?..
0
7804 / 6568 / 2988
Регистрация: 14.04.2014
Сообщений: 28,705
27.12.2015, 22:26
Лучший ответ Сообщение было отмечено Annushkash как решение

Решение

Цитата Сообщение от Annushkash Посмотреть сообщение
В этой функции я не конвертирую, а преобразую строку в массив символов
И конвертируешь тоже. Описание прочитай.
Обратное преобразование - Marshal::PtrToStringAnsi
https://msdn.microsoft.com/ru-... 10%29.aspx
1
0 / 0 / 1
Регистрация: 15.12.2015
Сообщений: 19
28.12.2015, 10:36  [ТС]
Спасибо за ответ! Это действительно то, что было нужно.
Я добавила новый метод:
C++
1
2
3
4
String^ CharToString(char* c)
{
    return System::Runtime::InteropServices::Marshal::PtrToStringAnsi((IntPtr) c);
}
Но... кажется я неверно преобразую или это просто побочный эффект?
Я шифрую строку "ма", а дешифруется "маээээ««««««««оюоюоюоюою"
0
7804 / 6568 / 2988
Регистрация: 14.04.2014
Сообщений: 28,705
28.12.2015, 16:11
Ты неправильно работаешь с памятью. Предварительно выделять её не нужно - это делает StringToHGlobalAnsi(). А вот освобождать нужно самостоятельно:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
void CryptRSA::MyForm::btnCrypt_Click(System::Object^ sender, System::EventArgs^ e)
{
    if (!String::IsNullOrWhiteSpace(txtCrypt->Text))
    {
        String^ txt = txtCrypt->Text;
        int length = txt->Length;
        if (length <= MAX)
        {
            //Преобразование string в массив char
            unsigned char *Text = StringToChar(txt);
            
            GenerateKeys();
 
            //Вывод зашифрованного текста
            unsigned int *cryptoCode = new unsigned int[length];
            cryptoCode = serial->Crypt(Text, length);
 
            System::Runtime::InteropServices::Marshal::FreeHGlobal(IntPtr(Text));
 
            String^ outStr;
            for (int i = 0; i < length; i++)
                outStr = String::Format(outStr+"{0} ", cryptoCode[i]);
            txtEncrypt->Text = outStr;
            stripCryptLbl->Text="Текст зашифрован";
    }
    else
    {
        MessageBox::Show("Не найден текст для шифрования", "Алгоритм RSA",
            MessageBoxButtons::OK, MessageBoxIcon::Error);
    }
}
Что касается лишних символов, ты не выделяешь место и не устанавливаешь конец строки при расшифровке:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
char* SerialRSA::Encrypt(unsigned int* Code, int lenght)
{
    //Массив для хранения шифротекста.
 
    char *Tdecrypt = new char[lenght + 1];
 
    //Расшифровка полученного кода по формуле m = (Codei^d)%n и перевод его в десятичный код ASCII.
    int m;
    for (int j = 0; j < lenght; j++)
    {
        m = 1;
        unsigned int i = 0;
        while (i<d)
        {
            m = m*Code[j];
            m = m%n;
            i++;
        }
        Tdecrypt[j] = static_cast<char>(m);
    }
 
    Tdecrypt[length] = '\0';
 
    return Tdecrypt;
}
1
0 / 0 / 1
Регистрация: 15.12.2015
Сообщений: 19
27.01.2016, 11:11  [ТС]
Спасибо за помощь!
В приложении код проекта (я делала последовательный и параллельный (OMP) алгоритм RSA), несколько не оптимизированный и у меня осталась еще пара вопросов, но тем не менее, вдруг кому-то поможет мой код...
По крайней мере, проблема при шифрации/дешифрации с кодировкой разрешена.
Вложения
Тип файла: zip CryptRSA.zip (10.2 Кб, 37 просмотров)
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
27.01.2016, 11:11
Помогаю со студенческими работами здесь

Алгоритм RSA. Если открытый текст больше 20 символов, то текст не расшифровывается
Есть реализованный алгоритм RSA на Delphi. Все работает нормально. Но только если открытый текст больше 20 символов, то текст не...

Как настроить ввод русских символов и в дальнейшем вывод этих символов
Подскажите как в этом коде настроить ввод русских символов и в дальнейшем вывод этих символов. Данный код выводит лишь всякую ерунду место...

Чтение русских символов. Отрицательные значения у символов
Добрый вечер. Считую файл .txt. Но русские буквы получают отрицательное значение. И в итоге при попытке перевести в String не распознаются....

RSA алгоритм
можете объяснить как правильно использовать сие алгоритм в C# с использование встроенных классов. если не сложно, объясните на примере...

Алгоритм RSA
Задание написать шифратор/дешифратор алгоритмом RSA. Подсчет всего нужно я совершил, но вот не знаю какой тип данных юзнуть. Даже в...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Новые блоги и статьи
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка.
Programma_Boinc 23.12.2025
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка. Рецензия / Мнение Это мой обзор планшета X220 с точки зрения школьника. Недавно я решила попытаться уменьшить свой. . .
PhpStorm 2025.3: WSL Terminal всегда стартует в ~
and_y87 14.12.2025
PhpStorm 2025. 3: WSL Terminal всегда стартует в ~ (home), игнорируя директорию проекта Симптом: После обновления до PhpStorm 2025. 3 встроенный терминал WSL открывается в домашней директории. . .
Как объединить две одинаковые БД Access с разными данными
VikBal 11.12.2025
Помогите пожалуйста !! Как объединить 2 одинаковые БД Access с разными данными.
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru