JavaScripts › Verschlüsselungen
XcxxsV-Verschlüsselungsprogramm
Verschlüsselt einen Text mit einem selbst gewählten Geheimwort — und entschlüsselt ihn mit demselben Wort wieder.
Dieses Verschlüsselungsprogramm hat unser User X303 eingeschickt. Ihr gebt ein beliebiges Wort oder einen ganzen Satz ein und legt dazu einen selbst gewählten Schlüssel fest — ein „Geheimwort“, das nur ihr und der Empfänger kennt. Aus beidem entsteht eine Zeichenfolge, mit der ein Mitleser ohne das Geheimwort nichts anfangen kann.
Zum Ausprobieren tragt ihr oben einen Text und darunter das Geheimwort ein. „Verschlüsseln“ schreibt das Ergebnis in das untere Feld — von dort könnt ihr es kopieren und weitergeben. Zum Zurückrechnen kopiert ihr die verschlüsselte Zeichenfolge wieder in das obere Feld, tragt dasselbe Geheimwort ein und klickt auf „Entschlüsseln“. Stimmt der Schlüssel nicht mit dem ursprünglichen überein, kommt nur Buchstabensalat heraus — genau das ist der Sinn der Sache.
Technisch arbeitet das Script nach dem Prinzip des Vigenère-Chiffres: Jedes Zeichen des Textes wird um so viele Stellen weitergeschoben, wie es der Position des zugehörigen Schlüsselzeichens entspricht. Ist das Geheimwort kürzer als der Text, beginnt es einfach wieder von vorn. Gerechnet wird hier mit einer Vorlage aus 67 Zeichen — Klein- und Großbuchstaben, Ziffern und ein paar Satzzeichen. Alles, was darin nicht vorkommt (Leerzeichen, Umlaute, Zeilenumbrüche), behandelt das Script als Position 0 und gibt es beim Entschlüsseln als Leerzeichen zurück. Für Leerzeichen geht die Rechnung damit sauber auf, Umlaute überleben den Weg hin und zurück aber nicht.
Als Spielerei unter Freunden ist das Verfahren bestens geeignet, für ernsthafte Geheimnisse taugt es nicht: Ein wiederholtes Schlüsselwort lässt sich mit statistischen Methoden knacken, das ist seit dem 19. Jahrhundert bekannt. Wer sich für die Familie dieser Verfahren interessiert, findet bei uns auch das klassische Vigenere Quadrat, das viel einfachere Atbash und die ROT13 Verschlüsselung.
Zum Entschlüsseln die Zeichenfolge zurück ins Feld „Text“ kopieren und dasselbe Geheimwort verwenden.
So funktioniert das Script
Das Script hat vier Teile: eine Zeichentabelle, die jedem Zeichen eine Nummer gibt, eine kleine Hilfsfunktion zum Nachschlagen dieser Nummer, je eine Funktion zum Ver- und zum Entschlüsseln und zum Schluss die Verdrahtung mit den beiden Knöpfen. Alles steckt in einer sofort ausgeführten Funktion, damit die Namen darin nicht mit anderen Scripts auf derselben Seite kollidieren.
const MAXW = 67;
const Tabelle = "#abcdefghijklmnopqrstuvwxyz01234ABCDEFGHIJKLMNOPQRSTUVWXYZ56789+-*,.";
Tabelle ist das Alphabet dieses Verfahrens. Die Stelle, an der ein Zeichen in dieser Zeichenkette steht, ist seine Nummer: # hat die 0, a die 1, b die 2 und so weiter. MAXW gibt an, mit wie vielen dieser Zeichen gerechnet wird — mit 67, also mit allen bis auf das letzte. Die Zeichenkette ist ein Zeichen länger — der Punkt ganz am Ende bleibt also außen vor und wird wie ein unbekanntes Zeichen behandelt. Das ist eine Eigenart des Originals, die wir bewusst beibehalten haben.
function wert(zeichen) {
const i = Tabelle.indexOf(zeichen);
return (i < 0 || i >= MAXW) ? 0 : i;
}
indexOf() sucht ein Zeichen in der Tabelle und liefert dessen Position — oder -1, wenn es gar nicht vorkommt. Genau das passiert bei Leerzeichen, Umlauten und allem anderen, was nicht in der Tabelle steht: Solche Zeichen bekommen ersatzweise die Nummer 0. Der Ausdruck mit dem Fragezeichen ist eine Kurzschreibweise für eine if-Abfrage und heißt: „Wenn die Bedingung stimmt, nimm den Wert vor dem Doppelpunkt, sonst den dahinter.“
const sw = wert(geheimwort.charAt(i % slen));
const tw = wert(eingabetext.charAt(i));
ergebnis += Tabelle.charAt((tw + sw) % MAXW);
Das ist der Kern der Verschlüsselung, ausgeführt für jedes Zeichen des Textes. tw ist die Nummer des Textzeichens, sw die des passenden Schlüsselzeichens. Beide werden addiert — die Summe ist die Nummer des Ausgabezeichens, das mit charAt() aus der Tabelle geholt wird.
Zwei Rechenzeichen lohnen einen zweiten Blick. % ist der Rest einer Division: i % slen lässt den Zähler beim Schlüsselwort immer wieder von vorn beginnen, sobald er über dessen Länge hinausläuft — aus dem Geheimwort „Kaktus“ wird also „KaktusKaktusKaktus…“, so lang der Text auch ist. Und % MAXW am Ende sorgt dafür, dass die Tabelle ein Ring ist: Läuft die Summe über das letzte Zeichen hinaus, geht es vorn wieder los.
const ew = (MAXW - sw + tw) % MAXW;
ergebnis += (ew === 0) ? " " : Tabelle.charAt(ew);
Beim Entschlüsseln wird die Verschiebung wieder abgezogen. Statt tw - sw zu rechnen — was negativ werden könnte, und mit negativen Zahlen verhält sich % in JavaScript unerwartet — addiert das Script MAXW dazu und nimmt erst dann den Rest. Das Ergebnis ist dasselbe, aber garantiert nicht negativ.
Die zweite Zeile ist der Grund, warum Leerzeichen den Weg hin und zurück überstehen: Ein Leerzeichen steht nicht in der Tabelle, wird beim Verschlüsseln also als 0 behandelt — und die 0 wird beim Entschlüsseln nicht in das Tabellenzeichen #, sondern zurück in ein Leerzeichen übersetzt.
document.getElementById("xc-verschluesseln").addEventListener("click", function () {
ausfuehren(verschluesseln);
});
Zum Schluss werden die Knöpfe verbunden. ausfuehren() liest beide Eingabefelder, meldet fehlende Angaben freundlich in der Ergebnisfläche und schickt Text und Geheimwort sonst an die übergebene Funktion. Dass eine Funktion hier wie ein Wert an eine andere Funktion weitergereicht wird, ist in JavaScript völlig normal — so brauchen beide Knöpfe nur eine gemeinsame Auswerteroutine. Das Script steht dabei unter dem Formular, damit Felder und Knöpfe schon existieren, wenn es läuft.
Zum Anpassen: Die Zeichenvorlage in Tabelle dürft ihr um eigene Zeichen erweitern — dann müsst ihr nur MAXW entsprechend anpassen. Wichtig ist, dass Sender und Empfänger dieselbe Tabelle und dasselbe Geheimwort verwenden, sonst passt die Rückrechnung nicht.
Script für die eigene Homepage
Kopiert euch den kompletten Code und fügt ihn an der Stelle eurer Seite ein, an der das Script erscheinen soll. Er läuft ohne weitere Dateien und ohne fremde Server.