This commit is contained in:
jude 2023-04-20 13:19:37 +01:00
parent f9805c4806
commit 4c1bcf370f
2 changed files with 115 additions and 47 deletions

Binary file not shown.

View File

@ -10,6 +10,9 @@
% reflect on achievemtns, difficulties, novelty etc.
% diagrams maybe
\usepackage{algorithmicx}
\usepackage{algpseudocode}
\usepackage[toc,page]{appendix}
\usepackage{Bath-CS-Dissertation}
\usepackage{amsmath}
\usepackage{amssymb}
@ -47,8 +50,6 @@
\begin{document}
\hypersetup{pageanchor=false}
\renewcommand{\thesection}{\arabic{section}}
\setcounter{page}{0}
\pagenumbering{arabic}
@ -64,7 +65,26 @@
%
%\clearpage
\section{Outline}
\begin{table}[htp]
\begin{tabularx}{\textwidth}{c X}
\toprule
Symbol & Meaning
\\
\midrule
$|a|$ & Bit length of value $a$ \\
$\left(\frac{a}{b}\right)$ & Jacobi symbol for $a, b$ \\
$\frac{a}{b}$ & Regular division \\
$\mathbb{Z}_k$ & Additive group of integers modulo $k$ \\
$\mathbb{Z}^*_k$ & Multiplicative group of units modulo $k$ \\
$\gcd(a, b)$ & Greatest common divisor of $a, b$ \\
$\lcm(a, b)$ & Least common multiple of $a, b$ \\
$\phi$ & Euler's totient function \\
$\lambda$ & Carmichael's totient function \\
\bottomrule
\end{tabularx}
\end{table}
\chapter{Outline}
Risk is a strategy game developed by Albert Lamorisse in 1957. It is a highly competitive game, in which players battle for control over regions of a world map by stationing units within their territories in order to launch attacks on neighbouring territories that are not in their control.
@ -237,7 +257,7 @@ The main concern is the issue of time complexity of Paillier. Theoretic results
The first is in the selection of public parameter $g$. The original paper suggests a choice of $g = 2$, however the choice of $g = 1 + n$ is very common, as the exponentiation $g^m = 1 + mn$ by binomial theorem.
Another optimisation is that of Jurik \cite[Section~2.3.1]{Jurik2003ExtensionsTT}: Jurik proposes that the public-key is instead $(n, g, h)$, where $h$ is the generator of the group $\mathbb{Z}^*_{n}[+1]$ (the group of units with Jacobi symbol $+1$). Then, an encryption $c'$ of a message $m$ is computed as \begin{align*}
Another optimisation is that of Jurik \cite[Section~2.3.1]{Jurik2003ExtensionsTT}: Jurik proposes that the public-key is instead $(n, g, h)$, where $h$ is the generator of the group $\mathbb{Z}^*_{n}[+]$ (the group of units with Jacobi symbol $+1$). Then, an encryption $c'$ of a message $m$ is computed as \begin{align*}
c' = g^m (h^r \mod n)^n\mod n^2
\end{align*}
for some random $r \in \mathbb{Z}^*_{n}$.
@ -246,7 +266,7 @@ The optimisation comes in two parts: firstly, the mantissa is smaller, resulting
(h^r \mod n)^n \mod n^2 = h_n^r \mod n^2
\end{align*}
Exponentials of the fixed base $h_n$ can then be pre-computed to accelerate exponentiation by arbitrary $r$. For example, one might pre-compute $h_n^{2^0} \mod n, h_n^{2^1} \mod n, h_n^{2^2} \mod n, \dots, h_n^{2^n} \mod n$. This reduces exponentiation to up to $n$ multiplications.
Exponentials of the fixed base $h_n$ can then be pre-computed to speed up exponentiation by arbitrary $r$.
Jurik states that the optimised form can lead to a theoretic four times speedup over Paillier's original form.
@ -275,7 +295,7 @@ The downside of using the Fiat-Shamir heuristic in our implementation is that an
Another approach to the problem is to use set membership, which is a widely considered problem in zero-proof literature. In this case, each region would be associated with a set of units from a public "pool" of units. Then, a player needs to prove the cardinality of a set, and the uniqueness/distinctness of its members. A number of constructs exist for analysing and proving in obscured sets.
\section{Implementation}
\chapter{Implementation}
The implementation provided uses WebSockets as the communication primitive. This is therefore a centralised implementation. However, no verification occurs in the server code, which instead simply "echoes" messages received to all connected clients.
@ -287,20 +307,18 @@ Despite this approach being centralised, it does emulate a fully peer-to-peer en
In particular, the final point allows for the use of purely JSON messages, which are readily parsed and processed by the client-side JavaScript.
\begin{landscape}
\begin{tikzpicture}[every node/.style={anchor=north west, outer sep=0.1cm}]
\begin{landscape}\begin{tikzpicture}[every node/.style={anchor=north west}]
% Create outlines
\node[
rectangle,
dashed,
draw,
minimum width=0.5\hsize-4pt,
minimum height=0.5\textheight-4pt,
align=right
] at (0, 0.5\textheight+4pt) {};
minimum height=0.5\textheight-4pt,
align=right,
] at (0, 0.5\textheight) {};
\node[anchor=south west] at (0, 0) {Setup};
\node[anchor=south west] at (0, 2pt) {Setup};
\node[
rectangle,
@ -309,30 +327,55 @@ In particular, the final point allows for the use of purely JSON messages, which
minimum width=0.5\hsize-4pt,
minimum height=0.5\textheight-4pt,
align=right
] at (0, 0) {};
] at (0, -2pt) {};
\node[anchor=south west] at (0, -0.5\textheight-4pt) {Pre-game};
\node[anchor=south west] at (0, -0.5\textheight) {Pre-game};
\node[
rectangle,
dashed,
draw,
minimum width=0.5\hsize-4pt,
minimum height=\textheight,
minimum height=\textheight-2pt,
align=right,
] at (0.5\hsize+4pt, 0.5\textheight+4pt) {};
] at (0.5\hsize+2pt, 0.5\textheight) {};
% This node doesnt position correctly......
\node[anchor=south west] at (0.5\hsize+4pt, -0.5\textheight-2pt) {Game};
\node[anchor=south west] at (0.5\hsize+4pt, -0.5\textheight+2pt) {Game};
% Player connect handling
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm] (Connect) at (8pt, 0.5\textheight-4pt) {Player connects};
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Connect) at (56pt, 0.5\textheight-4pt) {Player connects};
\node[draw=black!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Addplayer) at (56pt, 0.5\textheight-36pt) {Add player $P_i$};
\draw[very thick,->] (Connect) -- (Addplayer);
\node[draw=green!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Announce) at (56pt, 0.5\textheight-68pt) {Announce self};
\draw[very thick,->] (Addplayer) -- (Announce);
\node[draw=black!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Starttimer) at (56pt, 0.5\textheight-100pt) {Start timer $T_i$};
\draw[very thick,->] (Announce) -- (Starttimer);
% Player disconnect handling
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm] (Connect) at (8pt, 0.5\textheight-4pt) {Player connects};
\end{tikzpicture}
\end{landscape}
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Disconnect) at (170pt, 0.5\textheight-4pt) {Player disconnects};
\node[draw=red!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Removeplayer) at (170pt, 0.5\textheight-36pt) {Remove player $P_i$};
\draw[very thick,dashed,->] (Starttimer)-- (170pt, 0.5\textheight-109.5pt)-- node[right] {Timer expires} ++(Removeplayer);
\draw[very thick,->] (Disconnect) -- (Removeplayer);
% Player keep-alive handling
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Keepalive) at (290pt, 0.5\textheight-4pt) {Player keep-alives};
\node[draw=black!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Resettimer) at (290pt, 0.5\textheight-36pt) {Reset timer $T_i$};
\draw[very thick,->] (Keepalive) -- (Resettimer);
% Player ready handling
\node[draw=blue!50,rectangle,very thick,rounded corners=0.1mm,anchor=north] (Ready) at (170pt, 80pt) {Player becomes ready};
\end{tikzpicture}\end{landscape}
\subsection{Message structure}
@ -344,7 +387,7 @@ Each message is also signed to verify the author. This is a standard application
Players trust RSA keys on a trust-on-first-use (TOFU) basis. TOFU is the same protocol as used by Gemini \cite{projectgemini}. The main issue with TOFU is that if a malicious party intercepts the first communication, they may substitute the RSA credentials transmitted by the intended party, resulting in a man-in-the-middle attack.
\subsection{Paillier cryptosystem}
\section{Paillier cryptosystem}
ECMAScript typically stores integers as floating point numbers, giving precision up to $2^{53}$. This is clearly inappropriate for the generation of sufficiently large primes for the Paillier cryptosystem.
@ -419,26 +462,49 @@ Finally, to get the public parameter $h$, we compute $h = -x^2 \mod n$ for some
This gives us our public key $(n, g, h)$.
%todo got up to here
\subsection{Encryption}
In the original Paillier scheme, ciphertexts are computed as $c = g^m r^n \mod n^2$ for $r < n$ some random secret value. To make this easier to compute, we can compute the equivalent value $c = (r^n \mod n^2) \cdot (g^m \mod n^2) \mod n^2$.
In the original Paillier scheme, ciphertexts are computed as $E(m, r) = c = g^m r^n \mod n^2$ for $r < n$ some random secret value. In Jurik's form, ciphertexts are computed as \begin{align*}
E'(m, r) = c' = g^m(h^r \bmod n)^n \equiv g^m(h^n \bmod n)^r \mod n^2
\end{align*}
Jurik remarks that $E'(m, r) = E(m, h^r \bmod n)$.
To achieve a better speed-up, pre-computation of the fixed base $h^n \bmod n$ is used. By pre-computing powers of the powers of two, exponentiation is reduced to at most $|r|$ multiplications. Let $h[i] = h^{(2^i)} \bmod n$. Then, the following algorithm computes ${h^b \bmod n}$.
\begin{algorithmic}
\Function{FixedBaseExp}{$b$}
\State $index \gets 0$
\State $counter \gets 1$
\While{$b \neq 0$}
\If {$b \equiv 1 \mod 2$}
\State $ctr \gets ctr \times h[i]$
\State $ctr \gets ctr \bmod n$
\EndIf
\State $i \gets i + 1$
\State $b \gets \lfloor \frac{b}{2} \rfloor$
\EndWhile
\EndFunction
\end{algorithmic}
%todo got up to here
\subsection{Private key}
The private key is the value of the Carmichael function $\lambda = \lambda(n)$, defined as the exponent of the group $\mathbb{Z}^*_n$. From the Chinese remainder theorem, $\lambda(n) = \lambda(pq)$ can be computed as $\lcm(\lambda(p), \lambda(q))$. From Carmichael's theorem, this is equivalent to $\lcm(\phi(p), \phi(q))$, where $\phi$ is Euler's totient function. Hence, from the definition of Euler's totient function, and as $p, q$ are equal length, $\lambda = (p - 1)(q - 1) = \phi(n)$.
The private key is the value of the Carmichael function $\lambda = \lambda(n)$, defined as the exponent of the group $\mathbb{Z}^*_n$. From the Chinese remainder theorem, $\lambda(n) = \lambda(pq)$ can be computed as $\lcm(\lambda(p), \lambda(q))$. From Carmichael's theorem, this is equivalent to $\lcm(\phi(p), \phi(q))$. Hence, from the definition of $\phi$, and as $p, q$ are equal length, $\lambda = (p - 1)(q - 1) = \phi(n)$.
We are also interested in the ability to compute $\mu = \lambda^{-1} \mod n$ as part of decryption. Fortunately, this is easy, as from Euler's theorem, $\lambda^{\phi(n)} \equiv 1 \mod n$, and so we propose $\mu = \lambda^{\phi(n) - 1} \mod n$. As $\phi(n)$ is well-known to us, we get $\mu = \lambda^{(p - 1)(q - 1)} \mod n$, a relatively straight-forward computation.
We are also interested in the ability to compute $\mu = \lambda^{-1} \mod n$ as part of decryption. Fortunately, this is easy, as from Euler's theorem, $\lambda^{\phi(n)} \equiv 1 \mod n$, and so we propose $\mu = \lambda^{\phi(n) - 1} \mod n$. As $\phi(n)$ is easily computable with knowledge of $p, q$, we get ${\mu = \lambda^{(p - 1)(q - 1)} \mod n}$, a relatively straight-forward computation.
\subsection{Decryption}
Let $c$ be the ciphertext. The corresponding plaintext is computed as $m = L(c^\lambda \mod n^2) \cdot \mu \mod n$, where $L(x) = \frac{x - 1}{n}$. This operation can be optimised by applying Chinese remainder theorem. However, in the application presented, decryption is not used and is only useful as a debugging measure. So this need not be optimised.
Let $c$ be the ciphertext. The corresponding plaintext is computed as \begin{align*}
m = L(c^\lambda \mod n^2) \cdot \mu \mod n,
\end{align*} where $L(x) = \frac{x - 1}{n}$. This operation can be optimised by applying Chinese remainder theorem. However, in the application presented, decryption is not used and is only useful as a debugging measure. So this need not be optimised.
\subsection{Implementation details}
Paillier is implemented by four classes: \texttt{PubKey}, \texttt{PrivKey}, \texttt{Ciphertext}, and \texttt{ReadOnlyCiphertext}. \texttt{PubKey.encrypt} converts a \texttt{BigInt} into either a \texttt{Ciphertext} or a \texttt{ReadOnlyCiphertext} by the encryption function above. The distinction between these is that a \texttt{ReadOnlyCiphertext} does not know the random $r$ that was used to form it, and so is created by decrypting a ciphertext that originated with another peer. A regular \texttt{Ciphertext} maintains knowledge of $r$ and the plaintext it enciphers. This makes it capable of proving by the scheme presented below.
\subsection{Shared random values}
\section{Shared random values}
A large part of Risk involves random behaviour dictated by rolling some number of dice. To achieve this, some fair protocol must be used to generate random values consistently across each peer without any peer being able to manipulate the outcomes.
@ -507,9 +573,9 @@ Random values are used in two places. \begin{itemize}
\item Rolling dice.
\end{itemize}
As this protocol must run many times during a game, we consider each operation of the protocol as a "session", each of which has a unique name that is derived from the context. This has another benefit as the unique name can then be used with the Web Lock API to prevent race conditions that may occur due to this protocol running asynchronously.
As this protocol must run many times during a game, we consider each operation of the protocol as a "session", each of which has a unique name that is derived from the context. This has another benefit as the unique name can then be used with the Web Locks API to prevent race conditions that may occur due to this protocol running asynchronously.
\subsection{Proof system}
\section{Proof system}
The first proof to discuss is the honest-verifier protocol to prove knowledge that a ciphertext is an encryption of zero \cite[Section~5.2]{damgard2003}.
@ -639,7 +705,9 @@ It is preferred that these proofs can be performed with only a few communication
We can apply the Fiat-Shamir heuristic to make proofs of zero non-interactive \cite{fiatshamir}. In place of a random oracle, we use a cryptographic hash function. We take the hash of some public parameters to prevent cheating by searching for some values that hash in a preferable manner. In this case, selecting $e = H(g, m, a)$ is a valid choice. To get a hash of desired length, an extendable output function such as SHAKE256 could be used \cite{FIPS202}. The library jsSHA \cite{jssha} provides an implementation of SHAKE256 that works within a browser.
\section{Review}
\chapter{Review}
\section{Theoretic considerations}
\subsection{Random oracles}
@ -649,11 +717,19 @@ The random oracle model is used for two guarantees. The first is in the construc
The second is to associate a non-random value with a random value. In practice, a cryptographic hash function such as SHAKE is used. This gives appropriately pseudo-random outputs that appear truly random, and additionally are assumed to be preimage resistant: a necessary property when constructing non-interactive proofs in order to prevent a prover manipulating the signature used to derive the proof.
\subsection{Efficiency}
\subsection{Quantum resistance}
\subsubsection{Storage complexity}
Paillier is broken if factoring large numbers is computationally feasible \cite[Theorem~9]{paillier1999public}. Therefore, it is vulnerable to the same quantum threat as RSA is, known as Shor's algorithm \cite{shor_1997}. Alternative homomorphic encryption schemes are available, which are believed to be quantum-resistant, as they are based on lattice methods (e.g, \cite{fhe}).
In this section, let $N$ be the size in bits of the modulus $n$. This is likely one of 1024, 2048, or 4096; depending on the size of the primes used to form the modulus.
\subsection{Honest-verifier}
The proof of zero is honest-verifier \cite[Section~5.2]{damgard2003}. However, applying the Fiat-Shamir heuristic converts such a proof into a general zero-knowledge proof \cite[Section~5]{fiatshamir}. This means that, supposing the choice of transform used is appropriate, \hyperref[protocol1]{Protocol~\ref*{protocol1}} should also be general zero-knowledge. However, the interactive proofs performed as part of the game are still only honest-verifier, and a malicious verifier may be able to extract additional information from the prover (such as the blinding value used).
\section{Efficiency}
\subsection{Storage complexity}
In this section, let $N = |n|$. This is likely one of 1024, 2048, or 4096; depending on the size of the primes used to form the modulus.
Paillier ciphertexts are constant size, each $2N$ in size (as they are taken modulo $n^2$). This is small enough for the memory and network limitations of today.
@ -674,7 +750,7 @@ This is all in an ideal situation without compression or signatures: in the impl
\textbf{Smaller key size.} The size of ciphertexts depends directly on the size of the key. Using a smaller key will reduce the size of the ciphertexts linearly.
\subsubsection{Time complexity}
\subsection{Time complexity}
Theoretic timing results versus RSA are backed experimentally by my implementation. The following benchmarking code was executed.
@ -774,15 +850,7 @@ All measurements were taken on Brave 1.50.114 (Chromium 112.0.5615.49) 64-bit, u
\end{landscape}
\subsection{Quantum resistance}
Paillier is broken if factoring large numbers is computationally feasible \cite[Theorem~9]{paillier1999public}. Therefore, it is vulnerable to the same quantum threat as RSA is, known as Shor's algorithm \cite{shor_1997}. Alternative homomorphic encryption schemes are available, which are believed to be quantum-resistant, as they are based on lattice methods (e.g, \cite{fhe}).
\subsection{Honest-verifier}
The proof of zero is honest-verifier \cite[Section~5.2]{damgard2003}. However, applying the Fiat-Shamir heuristic converts such a proof into a general zero-knowledge proof \cite[Section~5]{fiatshamir}. This means that, supposing the choice of transform used is appropriate, \hyperref[protocol1]{Protocol~\ref*{protocol1}} should also be general zero-knowledge. However, the interactive proofs performed as part of the game are still only honest-verifier, and a malicious verifier may be able to extract additional information from the prover (such as the blinding value used).
\section{Wider application}
\chapter{Wider application}
Peer-to-peer software is an area of software that has fallen somewhat out of interest in more recent years, as online service providers can afford to run their own centralised servers (although no doubt interest still exists: some users are preferring federated services over centralised services, such as Mastodon, Matrix, XMPP).
However, peer-to-peer solutions still have many benefits to end users: mainly being greater user freedom. I believe that the content presented here shows clear ways to expand peer-to-peer systems, and reduce dependence on centralised services.
@ -807,7 +875,7 @@ The ability to prove the contents of a dataset to a second party without guarant
Another consideration in this domain is the use of homomorphic encryption schemes to allow a third party to process data without actually viewing the data. This protects the data from viewing by the third party, and the processing methods from viewing by the first party. For example, common statistical functions such as regression can be performed on data that is encrypted under fully homomorphic encryption schemes.
\section{Limitations}
\chapter{Limitations}
Finally, I present a summary of other limitations that I encountered.