Szyfr Cztery kwadraty opiera się na zasadzie szyfrowania Playfair. Jednak podobieństwo kończy się na samej metodzie pobierania kolejnych liter. Do szyfrowanie potrzebne są dwa klucze. Dla standardowego alfabetu łacińskiego, w którym pomija się literę J, tworzy się dwie tabelki o rozmiarach 5 x 5. Każdą z tabelek wypełnia się alfabetem. Każda litera alfabetu może wystąpić tylko raz w obrębie jednej tabelki. Do zaszyfrowania danych potrzebna jest dodatkowa tabelka 2 x 2. W jej lewy górny oraz prawy dolny róg wpisuje sie alfabet w formie tabelki. Prawy górny zastępuje pierwszy klucz, a pozostałe wolne pole wpisuje się drugi klucz.
Podczas szyfrowania danych należy pobrać dwie kolejne litery z szyfrowanego tekstu, a następnie znalezienia pozycji (x1, y1) pierwszej litery w lewej, górnej części. W ten sam sposób należy zapisać pozycję (x2, y2) drugiej litery w prawej dolnej części. Pierwszą literę z pary należy zastąpić poprzez znak na pozycji (x2, y1), a drugi na znak na pozycji (x1, y2). W przypadku, gdy zostaje pojedyncza litera do zaszyfrowania można zostawić ją niezaszyfrowaną.
Załóżmy, że szyfrujemy tekst złożony z dużych liter alfabetu łacińskiego bez litery J. Kluczami szyfrującymi będą: LVGTZAKBRFIEYHOPWQDUMCNXS oraz IUTBOVACZKDWNEYLFSXHRPGQM. Wtedy zapisując wszystko w tabelce otrzymujemy:
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | |
---|---|---|---|---|---|---|---|---|---|---|
1 | A | B | C | D | E | L | V | G | T | Z |
2 | F | G | H | I | K | A | K | B | R | F |
3 | L | M | N | O | P | I | E | Y | H | O |
4 | Q | R | S | T | U | P | W | Q | D | U |
5 | V | W | X | Y | Z | M | C | N | X | S |
6 | I | U | T | B | O | A | B | C | D | E |
7 | V | A | C | Z | K | F | G | H | I | K |
8 | D | W | N | E | Y | L | M | N | O | P |
9 | L | F | S | X | H | Q | R | S | T | U |
10 | R | P | G | Q | M | V | W | X | Y | Z |
Szyfrując słowo TEST, na początek należy wziąć dwie pierwsze litery TE. Litery T należy szukać w lewym górnym rogu, a litery E w prawym dolnym. Pozycja litery T to (4, 4), a litery E to (6,10). Wystarczy teraz odczytać literę na pozycji (4, 10): U oraz na pozycji (6, 4): B. Dla kolejnej pary należy wykonać te same czynności. Ostatecznie uzyskuje się w ten sposób szyfrogram UBDS.
Do deszyfrowania można stworzyć nową tabelkę, albo posłużyć się starą. Użycie tej samej tabelki oszczędza czas, dlatego zaprezentuje tą metodę jako pierwszą. Podczas deszyfrowanie ponownie litery bierze się parami. Tym razem jednak pierwszą literę szuka się w prawej górnej części, a drugą w lewej dolnej. Pozycja pierwszej to (x2, y1), a drugiej to (x1, y2). Na tej podstawie łatwo znaleźć litery tekstu jawnego - są kolejno na pozycjach (x1, y1) i (x2, y2).
Druga metoda deszyfrowania polega na zaszyfrowaniu szyfrogramu tabelą odwrotną. Tabelę odwrotną uzyskuje się poprzez zamianę lewej górnej części z prawą górną i analogicznie z dolnymi częściami. Szyfrując przy pomocy w tej tabelki wykonuje się czynności identyczne z poprzednią metodą. Ta metoda ma jednak zaletę, że nie trzeba robić czynności od tyłu, a wystarczy wykonać te same co przy szyfrowaniu.
Program będzie przyjmował cztery linijki tekstu na wejściu: pierwszy określi alfabet, dwa kolejne to klucze szyfrujące, a ostatnia czwarta linijka to tekst do zaszyfrowania. Dane nie będą przechowywane w tabelce. Przed rozpoczęciem potrzebne będą dwie dodatkowe funkcje. Pierwsza z nich posłuży do wyszukiwania znaku w tabelce:
Druga funkcja cross() posłuży do wyliczania pozycji nowej litery. Ze względu na fakt, że dysponować będziemy indeksami litery w alfabecie, bądź którymś kluczu to funkcja przyjmie dwa argumenty i0 i i1, które będą indeksami litery w określonej części. Na tej podstawie zostanie wyliczony indeks litery z innej części.
Przykładowo jeśli wywołamy cross(i0,i1), gdzie i0 to indeks litery w lewej, górnej części, a i1 indeks litery z prawej, dolnej to uzyskamy indeks litery z prawej górnej części, aby uzyskać z lewej dolnej wystarczy zamienić i0 i i1 miejscami.
Szyfrowanie i deszyfrowanie różni się tylko sposobem zapisu danych w tabelce, dlatego można napisać wspólną funkcją dla obu operacji. Będą się natomiast różnić sposobem jej wywoływania.
(1.) Funkcja przyjmuje: txt - tekst do zaszyfrowania. (2.) Alokacja pamięci pod wynik i (3.) skopiowanie całej zawartości tekstu jawnego. (4.) Dla każdej kolejnej pary liter: wyliczane są indeksy (5.) pierwsze i (6.) drugiej litery z pary. Następnie (7. - 8.) pobierane są nowe znaki i zastępują odpowiednie znaki w wynik. (11.) Na koniec funkcja zwraca wynik.
Teraz wystarczy, aby zaszyfrować przy pomocy pierwszej wersji tabelki:
Z kolei szyfrogram zaszyfrować tabelą odwrotną w celu rozszyfrowania:
Program można przetestować przy pomocy poniższej funkcji main():
Napisz program tak, aby sprawdzał poprawność danych wejściowych tj. czy klucze są permutacjami alfabetu oraz czy alfabet też jest poprawny (nie zawiera zduplikowanych liter). Jeśli tak nie jest program powinien wypisać na ekran, że wprowadzone dane są niepoprawne z wyszczególnieniem co jest nieprawidłowe.
Przykładowo dla danych, gdzie pierwszy klucz zawiera dwie litery L:
Program ma stwierdzić, że: