Złożoność obliczeniowa/Wykład 15: Kryptografia a złożoność
Funkcje jednokierunkowe
W dotychczasowych rozważaniach naszym celem było znalezienie możliwie efektywnego rozwiązania dla zadanych problemów; nadmierna złożoność problemu była przez nas traktowana jako cecha niepożądana, gdyż utrudniająca nasze zadanie. W tym rozdziale nasze podejście będzie odmienne; duża złożoność będzie dla nas cechą bardzo cenną. Będzie nas przy tym w mniejszym niż dotychczas stopniu interesować złożoność pesymistyczna -- w końcu nie satysfakcjonuje nas "gwarancja", mówiąca że "jeżeli osoba podsłuchująca będzie miała pecha to odszyfrowanie wiadomości będzie dla niej zadaniem czasochłonnym". Wolelibyśmy, żeby odszyfrowywanie wiadomości przez osoby nieuprawnione było czasochłonne praktycznie zawsze -- tak, by próba podsłuchiwania dawała szansę sukcesu bardzo bliską zeru. Duża pesymistyczna złożoność nie będzie zatem warunkiem wystarczającym bycia dobrym kryptosystemem; przyda nam się jednak w charakterze warunku koniecznego.
Definicja
Niech . Mówimy, że jest funkcją jednokierunkową wtedy i tylko wtedy gdy:
- jest różnowartościowa,
- istnieje pewna stała taka, że ,
- jest obliczalna w czasie wielomianowym (czyli należy do klasy ),
- nie istnieje wielomianowy algorytm obliczający odwrotność funkcji
-- czyli znajdujący dla słowa słowo , takie że lub stwierdzający, że takie słowo nie istnieje.
Warto zauważyć, że powyższa definicja niejawnie zakłada prawdziwość zdania .
Ćwiczenie
Niech spełnia pierwsze trzy warunki podane w definicji funkcji jednokierunkowej. Pokaż, że obliczanie odwrotności funkcji jest problemem z klasy .
Z drugiej strony nierówność wcale nie gwaratuje istnienia funkcji jednokierunkowych; jak się okazuje istnienie tego typu funkcji jest ściśle powiązane z pewną klasą złożoności, którą przedstawiamy poniżej.
Definicja Jednoznaczną maszyną Turinga
nazywamy niedeterministyczną maszynę Turinga taką, że dla każdego słowa wejściowego istnieje co najwyżej jedna akceptująca ścieżka obliczeń.
Definicja
Klasa to klasa problemów rozstrzygalnych za pomocą jednoznacznych maszyn Turinga w czasie wielomianowym.
Klasę , podobnie jak klasę , można zdefiniować z użyciem pojęcia świadka:
{12pt} {12pt}
W językach z klasy każde słowo ma dokładnie jednego świadka. Dowód równoważności powyższych definicji jest analogiczny jak w przypadku klasy .
Jest jasne, że -- maszyny deterministyczne są specjalnymi przypadkami maszyn jednoznacznych. Dość powszechny jest pogląd, że obie powyższe relacje zawierania są właściwe (to znaczy nie zachodzi równość).
Pokażemy teraz bardzo ciekawy związek pomiędzy klasą a funkcjami jednokierunkowymi.
Twierdzenie
Funkcje jednokierunkowe istnieją
Dowód
Zaczniemy od dowodu w kierunku . Załóżmy, że istnieje pewna funkcja jednokierunkowa . Możemy wtedy zdefiniować następujący język:
{12pt} {12pt}
przy czym mówimy, że wtedy i tylko wtedy gdy
- , lub
- i w porządku leksykograficznym występuje nie później niż
.
Łatwo można zauważyć, że - maszyna rozwiązująca ten problem najpierw "zgaduje" słowo o wielkości nie większej niż , po czym sprawdza, czy w ustalonym porządku występuje ono nie później niż i czy zachodzi . Z własności funkcji jednokierunkowych -- konkretnie z różnowartościowości -- wynika, że maszyna ta ma co najwyżej jedną akceptującą ścieżkę postępowania.
Chcemy teraz pokazać, że . Załóżmy zatem nie wprost, że istnieje jakiś wielomianowy algorytm rozwiązujący . Wykorzystamy go teraz do obliczenia odwrotności funkcji w czasie wielomianowym. W pierwszym kroku zapytamy algorytm, czy (przez oznaczamy tutaj ciąg symboli ) - jeżeli otrzymamy odpowiedź "nie" to korzystając z definicji funkcji jednokierunkowej możemy od razu stwierdzić, że nie istnieje słowo takie, że . Jeżeli otrzymamy odpowiedź "tak" to z użyciem co najwyżej zapytań do naszego algorytmu jesteśmy w stanie ustalić długość szukanego słowa (pytamy kolejno o , , itd. aż do momentu gdy uzyskamy odpowiedź "nie"). Gdy znamy już długość słowa pozostaje nam już tylko obliczyć kolejne jego bity. Pierwszy bit otrzymamy pytając o parę -- odpowiedź "tak" oznacza, że pierwszym bitem jest 0. Aby uzyskać drugi bit zapytamy -- w zależności od pierwszej odpowiedzi -- o lub . Kolejne bity odgadujemy w analogiczny sposób -- łącznie zatem wykonamy algorytm dla razy. W ten sposób uzyskamy deterministycznty algorytm odwracający funkcję w czasie wielomianowym.
Doszliśmy więc do sprzeczności z definicją funkcji jednokierunkowej, co oznacza, że istnienie funkcji jednokierunkowych implikuje nierówność .
Załóżmy teraz, że istnieje język , rozpoznawany przez jednoznaczną maszynę . Zdefiniujmy funkcję w następujący sposób:
- jeżeli jest zakodowaną parą słów oraz
jest (jedynym) świadkiem przynależności słowa do , to
{12pt} , {12pt}
- w przeciwnym przypadku
{12pt} , {12pt}
Widzimy, że pierwszy symbol wartości funkcji gwarantuje nam jej różnowartościowość. Spełniony jest również drugi warunek z definicji funkcji jednokierunkowej -- świadek dla słowa nie może być nadmiernie długi (bo jego długość jest wielomianowo zależna od długości ), a zatem nie może nadmiernie "skracać" słów. Funkcja jest też obliczalna w czasie wielomianowym -- wystarczy deterministycznie zweryfikować świadka, tak jak zrobiłaby to maszyna . Pozostaje nam zatem tylko pokazanie, że funkcja odwrotna do nie jest obliczalna w czasie wielomianowym. Gdyby tak jednak było, to moglibyśmy rozpoznawać język w czasie wielomianowym: Aby sprawdzić, czy wystarczy zastosować odwrotność funkcji do słowa ; jeżeli to dostaniemy odpowiedź mówiącą, że nie można odwrócić; w przeciwnym przypadku otrzymamy świadka przynależności do języka .

Na dzień dzisiejszy nie znamy oczywiście funkcji, o której wiedzielibyśmy, że jest jednokierunkowa; istnienie takiej funkcji natychmiastowo implikuje przecież nierówność . Jest jednak kilku "kandydatów" na funkcje jednokierunkowe -- to znaczy funkcji, dla których nie znamy efektywnego algorytmu pozwalającego na ich odwrócenie. Jedną z takich funkcji jest funkcja . Argumentami tej funkcji są dwie liczby pierwsze wraz ze swoimi certyfikatami pierwszości. Wartością funkcji jest iloczyn tych dwóch liczb. Bardziej formalnie:
- jeżeli , gdzie a i
to certyfikaty pierwszości odpowiednio dla i , to
{12pt} {12pt}
- w przeciwnym przypadku
{12pt} {12pt}
Korzystamy tutaj z faktu, że możemy wymusić jednoznaczną reprezentację certyfikatu pierwszości dla danej liczby, oraz że certyfikaty mają rozmiar wielomianowo zależny od rozmiaru certyfikowanych liczb. jest zatem różnowartościowa i nie "skraca" nadmiernie słowa wejściowego.
Łatwo zauważyć, gdzie tkwi trudność w odwracaniu tej funkcji -- nie znamy efektywnego algorytmu potrafiącego faktoryzować iloczyn dwóch liczb pierwszych; znane nam obecnie algorytmy stają się niepraktyczne już przy iloczynach liczb pierwszych o długości kilkuset bitów.
Drugi ze znanych nam "kandydatów na funkcję jednokierunkową" również oparty jest na zagadnieniu z dziedziny teorii liczb -- problemie logarytmu dyskretnego. Funkcję tą można zdefiniować w następujący sposób:
- dla postaci , gdzie jest liczbą
pierwszą, certyfikatem jej pierwszości, jest najmniejszym generatorem grupy cyklicznej , a jest liczbą naturalną z zakresu
{12pt} {12pt}
- dla pozostałych
{12pt} {12pt}
W tym przypadku aby odwrócić funkcję musielibyśmy na podstawie liczb , i umieć obliczyć wartość . Również dla tego, znanego od wielu lat, problemu nie znamy wydajnego rozwiązania.
Jak zauważyliśmy we wprowadzeniu do tego rozdziału w kryptografii duża złożoność pesymistyczna próby zdekodowania zaszyfrowanej wiadomości nie jest własnością wystarczającą. Z tego powodu przytoczymy alternatywną definicję funkcji jednokierunkowych, lepiej odwzorowującą nasze oczekiwania. Należy pamiętać, że definicja ta jest istotnie różna od definicji podanej wcześniej.
Definicja
Niech . Mówimy, że jest funkcją jednokierunkową wtedy i tylko wtedy gdy:
- jest obliczalna w czasie wielomianowym,
- nie jest stale równa (słowu pustemu),
- istnieje pewna stała taka, że ,
- jeżeli i są słowami nad alfabetem i ,
to lub ,
- dla każdej losowej maszyny Turinga działającej w czasie wielomianowym,
każdej liczby i dostatecznie dużej liczby , jeżeli jest losowym słowem ze zbioru , to
{12pt} {12pt}
W tej definicji zrezygnowaliśmy z wymagania o różnowartościowości funkcji; zamiast tego dopuszczamy, aby różne słowa dawały jako wynik wartość , którą możemy traktować jako odpowiedź mówiącą, że wejście jest nieprawidłowe; dla przykładu przy adaptowaniu funkcji do powyższej definicji, w przypadku gdy lub nie będą liczbami pierwszymi, lub gdy lub nie będą odpowiednimi certyfikatami, funkcja zwróci wartość . Zauważmy, że w powyższej definicji interesuje nas tylko trudność odszyfrowania wartości funkcji dla poprawnych wejść -- to znaczy w przypadku dla par liczb, które są pierwsze i których pierwszość jest potwierdzana przez i . Funkcje jak i -- po odpowiednim ich zmodyfikowaniu w sposób przedstawiony powyżej -- są poważnymi "kandydatami" na funkcje jednokierunkowe również w sensie definicji opisanej w poprzednim paragrafie.
Warto się w tym momencie zastanowić, w jaki sposób funkcje jednokierunkowe mogą się przydać w kryptografii. Otóż widzimy, że jedna ze stron -- zwyczajowo zwana Alicją -- może wydajnie zaszyfrować swoją wiadomość, na przykład używając ją jako argument do funkcji . Niestety druga strona -- zazwyczaj zwana Bob -- może mieć duże trudności z odszyfrowaniem wiadomości. W tej sytuacji fakt, że osoba podsłuchująca -- Cecylia -- niczego ciekawego się nie dowie, stanowi słabe pocieszenie.
Widzimy zatem, że aby zapewnić poufność komunikacji pochodzącej od Alicji, ale również możliwość odebrania tej wiadomości, Bob musi posiadać pewną tajną wiedzę, pozwalającą na wydajne odwrócenie funkcji szyfrującej. Zdefiniujemy teraz pewną modyfikację pojęcia funkcji jednokierunkowej, mającą szersze zastosowanie w kryptografii.
Definicja
Niech . Mówimy, że jest funkcją z wytrychem wtedy i tylko wtedy gdy istnieje losowa maszyna Turinga oraz funkcja taka, że:
- funkcje i są obliczalne w czasie wielomianowym,
- oczekuje na wejściu słowa nad alfabetem , zwraca zakodowaną
parę słów nad alfabetem i działa w czasie wielomianowym,
- istnieje stała taka, że
jeżeli stanowi wynik działania maszyny dla słowa , natomiast jest słowem o długości nie większej niż , to ,
- jeżeli stanowi wynik działania maszyny dla
słowa , natomiast i są słowami o długości nie większej niż , to ,
- dla każdej losowej maszyny Turinga , każdej liczby i dostatecznie
dużej liczby , jeżeli stanowi wynik działania maszyny dla słowa , jest losowym słowem nad alfabetem nie dłuższym niż , to
{12pt} {12pt}
- Dla każdego , każdego słowa nie dłuższego niż i każdej pary
mogącej być wynikiem działania maszyny dla słowa wejściowego
{12pt} {12pt}
Funkcje z wytrychem mogą zostać wykorzystane w celu stworzenia systemów kryptograficznych z kluczem publicznym. Sposób postępowania jest w tym przypadku następujący:
- Bob ustala długość przekazywanych wiadomości () oraz parametr
wyznaczający prawdopodobieństwo odszyfrowania pojedynczej wiadomości (),
- Bob uruchamia maszynę i otrzymuje parę słów .
Słowo staje się dostępnym dla wszystkich kluczem publicznym, natomiast pozostaje tajemnicą znaną tylko Bobowi,
- Alicja, chcąc wysłać wiadomość do Boba, używa znanego jej klucza
publicznego . Własności funkcji z wytrychem sprawiają, że odszyfrowanie wiadomości jest łatwe dla Boba, natomiast trudne dla osób trzecich nie znających klucza .
Najbardziej znanym systemem kryptograficznym opartym na powyższej zasadzie jest system RSA. Pamiętajmy przy tym, że nie znamy formalnego dowodu, mówiącego, że RSA spełnia warunki określone w definicji funkcji z wytrychem.
Prześledźmy teraz w jaki sposób zdefiniowane są , i dla systemu RSA.
Zadaniem maszyny jest wygenerowanie pary kluczy. W tym celu losuje ona dwie liczby pierwsze i , z których każda ma długość większą niż (gdzie to długość przekazywanych wiadomości). Następnie oblicza ona liczbę oraz wartość funkcji Eulera dla tej liczby: . W kolejnym kroku znajdowana jest dowolna liczba z zakresu , względnie pierwsza z . Dla liczby znajdywana jest następnie liczba z zakresu taka, że
{12pt} {12pt}
Istnienie takiej liczby spowodowane jest faktem, że i są względnie pierwsze; liczbę można efektywnie obliczyć z użyciem uogólnionego algorytmu Euklidesa.
W tym momencie można już zdefiniować parę kluczy: Kluczem publicznym jest para liczb oraz . Kluczem prywatnym jest para liczb oraz . Szyfrowanie słowa wygląda następująco:
{12pt} {12pt}
przy czym wiadomość traktujemy jako binarny zapis pewnej liczby naturalnej. Dekodowanie słowa określone jest w praktycznie identyczny sposób:
{12pt} {12pt}
Wystarczy teraz przypomnieć sobie, że iloczyn jest postaci , dla pewnej liczby całkowitej . W związku z tym
{12pt} {12pt}
Widzimy zatem, że funkcja poprawnie dekoduje słowa zaszyfrowane z użyciem funkcji -- Bob będzie zatem w stanie odtworzyć wiadomość wysłaną przez Alicję.
Systemy dowodów interaktywnych
W ostatnim fragmencie niniejszego kursu zajmiemy się klasą złożoności, będącą uogólnieniem klas i . W tym celu zdefiniujemy pojęcie systemu dowodów interaktywnych.
Definicja Systemem dowodów interaktywnych
nazywamy parę funkcji oraz o sygnaturach:
{12pt} {12pt} {12pt}
taką, że funkcja jest obliczalna na maszynie Turinga.
Działanie systemu dowodów interaktywnych polega na wymianie komunikatów między funkcjami i , przy czym funkcja (z angielskiego prover) stara się "przekonać" funkcję (verifier) o tym, że słowo wejściowe należy do rozpatrywanego języka, natomiast ostateczna decyzja w tej sprawie należy do .
Komunikacja odbywa się naprzemiennie: Funkcja generuje wiadomość, przekazywaną funkcji jako argument; funkcja z kolei generuje odpowiedź przekazywaną funkcji w następnej iteracji. Taka komunikacja odbywa się do momentu zaakceptowania lub odrzucenia słowa wejściowego przez funkcję . W każdym kroku obie funkcje mają do dyspozycji zarówno słowo wejściowe, jak również pełną historię przekazanych dotychczas wiadomości.
Określmy teraz, co dokładnie oznaczają argumenty funkcji i . Argumenty funkcji będziemy oznaczać w następujący sposób:
{12pt} {12pt}
Mają one następujące znaczenie:
- to słowo wejściowe,
- jest losowym ciągiem bitów,
- to konkatenacja dotychczasowych wiadomości,
które zostały przekazane w procesie komunikacji (wiadomości o indeksach nieparzystych sa wynikami działania funkcji , natomiast wiadomości o indeksach parzystych sa wynikami działania funkcji ).
Zwróćmy uwagę, że ma do dyspozycji losowe słowo ; w praktyce oznacza to, że o funkcji będziemy myśleć jako o pewnej losowej maszynie Turinga.
Zakładamy, że zarówno jak i są stałe w kolejnych iteracjach; słowo jest zatem losowane jednokrotnie, przed rozpoczęciem procesu komunikacji. Warto też zauważyć, że słowa i całkowicie determinują działanie systemu.
Argumenty funkcji będziemy oznaczać następująco:
{12pt} {12pt}
Ich znaczenie jest identyczne jak w przypadku argumentów funkcji , nie ma wśród nich jednak słowa losowego.
Możemy w tym momencie zdefiniować klasę :
Definicja
Niech . Mówimy, że wtedy i tylko wtedy gdy istnieje system dowodów interaktywnych oraz wielomiany i takie, że dla każdego słowa wejściowego oraz losowego słowa o długości :
- system daje odpowiedź po co najwyżej krokach,
- w każdej iteracji czas działania maszyny obliczającej funkcję jest
ograniczony od góry przez ,
- długość każdej wiadomości jest nie większa niż ,
- jeżeli to prawdopodobieństwo zaakceptowania słowa przez system
wynosi co najmniej ,
- jeżeli oraz jest dowolną funkcją o sygnaturze zgodnej
z , zwracającą wiadomości nie dłuższe niż , to system spełnia powyższe założenia na ilość iteracji, czas działania i długość wiadomości oraz akceptuje słowo z prawdopodobieństwem nie większym niż .
O systemie mówimy, że rozpoznaje język w czasie wielomianowym.
Innymi słowy jeżeli słowo należy do języka, to z dużym prawdopodobieństwem da się przekonać o tej przynależności przez pewną ustaloną funkcję . Jeżeli jednak nie należy do , to nie da się oszukać żadnej funkcji ze zbyt dużym prawdopodobieństwem.
Zwróćmy jeszcze uwagę, że branie pod uwagę tylko takich funkcji , które nie zwracają zbyt długich słów nie jest istotnym ograniczeniem; funkcja może w każdym kroku sprawdzać, czy odpowiedź funkcji nie jest zbyt długa i jeśli tak to odrzucać słowo. W dalszej części rozdziału będziemy zakładali takie właśnie zachowanie funkcji .
Widzimy zatem, że funkcja musi być zabezpieczona przed oszustwami; jeżeli mogłaby zaufać funkcji to mogłaby rozwiązać każdy problem decyzyjny -- wystarczyłoby po prostu skorzystać z nieograniczonej mocy obliczeniowej . W naszym przypadku jednak nie wystarczy aby tylko rozwiązała problem decyzyjny -- musi jeszcze przekonać do swojego rozwiązania.
Przykład
Rozważmy problem . Jest on zdefiniowany następująco:
{12pt} grafy i nie są izomorficzne {12pt}
Łatwo sie przekonać, że problem izomorfizmu grafów jest w klasie -- wystarczy zgadnąć odpowiednią permutację wierzchołków, po czym zweryfikować ją w trywialny sposób. należy zatem do . Nie jest jednak obecnie znana odpowiedź na pytanie o przynależność tego problemu do klasy . Pokażemy teraz, w jaki sposób można rozwiązać za pomocą systemów dowodów interaktywnych, pokazując przynależność tego problemu do klasy .
System działa w prosty sposób: W kolejnych iteracjach funkcja wybiera losowo jeden z grafów, a następnie w losowy sposób permutuje jego wierzchołki. Taki graf jest przekazywany jako wiadomość do funkcji . Zadaniem funkcji jest rozpoznanie, który z wyjściowych grafów został wylosowany i przekształcony przez .
Ćwiczenie
Zdefiniuj, w jakich przypadkach powinien zaakceptować, a w jakich odrzucić wejściową parę grafów. Oblicz, ile iteracji jest potrzebnych, aby system rozpoznawał język w czasie wielomianowym zgodnie z wcześniejszą definicją.
Ćwiczenie
Pokaż, że klasa jest zawarta w klasie .
Ćwiczenie
Rozpatrzmy takie systemy dowodów interaktywnych, w których funkcje nie zależą od argumentu (słowa losowego). Jaką klasę języków rozpoznają takie systemy, przy założeniach o złożoności analogicznych jak w przypadku klasy ?
Możemy w tym momencie przypuszczać, że klasa jest znacząco większa od klasy . Nie wiemy obecnie czy przypuszczenie to jest prawdziwe; przemawia jednak za nim poniższe twierdzenie.
Twierdzenie
Dowód
Ćwiczenie
Wyjaśnij, czemu w protokole potrzebowaliśmy ciała o co najmniej elementach.