XOR-Verschlüsselung ist die Anwendung eines Schlüssels durch ein bitweises exklusives ODER auf den ursprünglichen Text. Der bitweise exklusive Mechanismus ist wie folgt:
X | UND | X⊕Y |
---|---|---|
0 | 0 | 0 |
0 | 1 | 1 |
1 | 0 | 1 |
1 | 1 | 0 |
Wenn also ein exklusives ODER ausgeführt wird, gibt es immer einen Nullwert, wenn die Variablen dieselben Werte hatten.
Die Besonderheit von XOR besteht darin, dass dieselbe Funktion Daten sowohl verschlüsseln als auch entschlüsseln kann. Dies ist eine einfache Datenverschlüsselungsmethode, die bei einem ausreichend großen Chiffretext oder einem großen Passwortwörterbuch ziemlich schnell gebrochen werden kann. Dennoch kann es bereits für eine kleine Erstdatensicherung genutzt werden.
Im Zusammenhang mit Qt ist die Verwendung von XOR nicht anders, als wenn das Programm ohne Verwendung von Qt geschrieben wurde. Anders stellt sich hier die Frage, wie Daten zur Verschlüsselung korrekt aus QString-Objekten extrahiert werden, beispielsweise wenn der Text in QTextEdit eingegeben wurde.
Dazu schreiben wir ein Programm, das Folgendes enthält:
- QTextEdit, das den zu verschlüsselnden Text eingibt.
- QLineEdit, in dem der Verschlüsselungsschlüssel eingegeben wird.
- QPushButton, in dessen Click-Handler-Slot die Datenverschlüsselung/-entschlüsselung durchgeführt wird. Auch hier stelle ich fest, dass die Methode gleich verwendet wird.
Das Programm wird wie folgt aussehen:
Projektstruktur
Das Projekt wird mit CMake geschrieben, daher sieht die Struktur wie folgt aus:
- CMakeLists.txt
- main.cpp
- EncoderWidget.h
- EncoderWidget.cpp
Verschlüsselungs-/Entschlüsselungsfunktion
Um die Verschlüsselung / Entschlüsselung zu implementieren, müssen Sie:
- Vorhandensein eines Char-Arrays mit Anfangsdaten
- Die Länge des Arrays mit den Originaldaten
- Schlüssel als Char-Array
- Schlüssellänge
- Sowie ein Array mit Ausgabedaten.
const char* input; int inputLength; const char* key; int keyLength; char output[inputLength]; for (int i = 0; i < inputLength + 1; ++i) { output[i] = input[i] ^ key[i % keyLength + 1]; }
Slot-Handler zum Ausführen der Verschlüsselung
Wie bereits erwähnt, ist es zur Verschlüsselung des Textes notwendig, die Daten korrekt aus den Eingabefeldern zu extrahieren. Dazu müssen Sie den Text in Form eines Strings QString an QByteArray übergeben, aus dem Daten in Form von const char* extrahiert werden. Und nehmen Sie auch die Länge dieser Daten.
Hier gibt es einen Punkt. Die Daten von QString zu QByteArray werden mit der toLatin1()-Methode konvertiert, die die Daten in eine ASCII-Tabelle konvertiert, was zu einer Datenverfälschung führt, wenn der Text in Kyrillisch geschrieben wurde. Das heißt, dieser Verschlüsselungsansatz wird relevant, wenn nur Zeichen aus der ASCII-Tabelle verwendet werden, beispielsweise für Login und Passwort.
void EncoderWidget::encodeDecode() { const char* input = m_textEdit->toPlainText().toLatin1().data(); int inputLength = m_textEdit->toPlainText().toLatin1().length(); const char* key = m_keyLineEdit->text().toLatin1().data(); int keyLength = m_keyLineEdit->text().toLatin1().length(); char output[inputLength]; for (int i = 0; i < inputLength + 1; ++i) { output[i] = input[i] ^ key[i % keyLength + 1]; } m_textEdit->setText(QString::fromLatin1(output, inputLength)); }
Insgesamt
Das Projekt kann unter folgendem Link heruntergeladen werden.
Шифрует/дешифрует текст от 8 символов, так и должно быть?
Не обратил внимания на это, Проверял с большим текстом.. По идее не должно.
Хоть пост и старый, но хочется понять. В случае xor шифрования символов мы может получить специальнвй символ(к примеру \0 или \n)? И, если, к примеру, нам нужно записать в текстовый файл эти данные, то мы при следующем считывании можем получить проблемы с считыванием?
в контексте этой статьи с символом \n, то есть символом новой строки проблем быть не должно, поскольку он точно присутствует в таблице символов ASCII, касательно \0 смотрите в таблице символов ASCII, если есть соответствующий символ.
А так, по идее можно доработать и для юникода и для любой другой кодировки, тогда проблем быть не должно.
Здравствуйте, не очень понимаю, почему в строках
добавляется единица к inputLength и keyLength?