You could use a slight variant of Encrypt-last-block CBC-MAC (ECBC-MAC) with a random single-character permutation plus a one-time pad character per MAC tag "digit". ECBC-MAC is easy to compute by hand and you can make MAC tags arbitrarily large — I'll explain how below.
Generating MAC Keys
You and your partner agree to use one-time pads (OTPs) to communicate. Plaintext and ciphertext use the same alphabet $A$. (In your example, $|A|=28$.)
For each OTP key, generate and attach a MAC key:
Decide how many symbols ("digits") the MAC tag should have. Call that number $N$. Each symbol increases confidence but also increases the amount of work you have to do; thus:
MAC Size (Symbols) |
Probability a Forgery Succeeds |
When $|A|=28$ |
1 |
$1/|A|$ |
3.5714% |
2 |
$1/|A|^2$ |
0.1276% |
3 |
$1/|A|^3$ |
0.0046% |
... |
... |
... |
$N$ |
$1/|A|^N$ |
|
For each MAC symbol $n$ in $1,...,N$, generate:
- A random permutation of all $A$ alphabet symbols. All permutations must be equally likely — consider a Fisher-Yates shuffle, which you can do by hand, perhaps with the aid of dice or playing cards.
- A random symbol from $A$, chosen uniformly at random, which will function like an OTP key.
Example MAC Key
Example MAC key for your alphabet ($|A|=28$) and MAC length $N=2$:
MAC Symbol Number |
Permutation |
Extra Random Symbol |
1 |
QCKJGEYMTBHPVZ DRL.UWIOXSFNA |
T |
2 |
MFR.QVOETHIUKSBLAC DZWXYJGNP |
G |
MAC Key Requirements
These MAC keys share some OTP key requirements — namely:
- MAC keys must never be reused. Every authenticated message will need its own randomly-generated MAC key.
- Generate MAC keys uniformly at random.
- Keep MAC keys absolutely secret.
- Securely distribute MAC keys.
- Destroy MAC keys after using them. If you're verifying a message's MAC tag, you MUST destroy the MAC key afterwards regardless of whether verification succeeds or fails. (If you reject the message but keep the key, you could inadvertently give the adversary an oracle as well as permit replay attacks.)
Calculating MACs
MAC Plaintext or Ciphertext?
You can MAC plaintext or ciphertext — there's no difference in security because you'll essentially OTP-encrypt the MAC tag.
- MACing plaintext will help message recipients detect encryption and decryption errors but force them to decrypt messages first.
- MACing ciphertext won't catch decryption errors, but recipients can verify messages before decrypting.
Pick one and make sure your recipients know which to use.
Calculating a MAC
Let's assume (for demonstration purposes) that you MAC ciphertext. Encrypt your message using a OTP key; then compute the ciphertext's MAC using the OTP key's associated MAC key thus:
- Check the length $N$ of the MAC the key generates. For each $n$ in $1,...,N$, do the following:
- Set $x \leftarrow 0$.
- For each ciphertext symbol $s_i$ (reading the ciphertext left-to-right):
- Let $f_n(x)$ be the symbol at zero-based index $x$ in the $n$th permutation. Set $x \leftarrow f_n(x + s_i \mod |A|)$. This assumes that the first symbol in your alphabet has numerical value $0$, the second $1$, and so on.
- Set $x \leftarrow x + e_n \mod |A|$, where $e_n$ is the $n$th extra random symbol from the MAC key. This effectively encrypts $x$ using a OTP.
- $x$ is now the $n$th symbol of the encrypted message's MAC tag.
- Destroy the MAC key along with the message's OTP key — it's a one-time key.
Message verification uses the same process.
Example
Let's say your ciphertext is AUTXQ
, $A$ is the English alphabet plus space and full stop ($|A|=28$), and the MAC key is the example one above ($N=2$). Then:
- For the first symbol in the MAC tag ($n=1$), the permutation is
QCKJGEYMTBHPVZ DRL.UWIOXSFNA
and the extra random symbol $e_1$ is 'T'.
- Set $x \leftarrow 0$.
- $s_0 = 0$ (the symbol 'A'). Set $x \leftarrow f_1(x + s_0 \mod 28) = f_1(0) = 16$ (the symbol 'Q').
- $s_1 = 20$ (the symbol 'U'). Set $x \leftarrow f_1(x + s_1 \mod 28) = f_1(8) = 19$ (the symbol 'T').
- $s_2 = 19$ (the symbol 'T'). Set $x \leftarrow f_1(x + s_2 \mod 28) = f_1(10) = 7$ (the symbol 'H').
- $s_3 = 23$ (the symbol 'X'). Set $x \leftarrow f_1(x + s_3 \mod 28) = f_1(2) = 10$ (the symbol 'K').
- $s_4 = 16$ (the symbol 'Q'). Set $x \leftarrow f_1(x + s_4 \mod 28) = f_1(26) = 13$ (the symbol 'N').
- Finally, set $x \leftarrow x + e_1 \mod 28 = 13 + 19\mod28 = 4$, which is the symbol 'E'. Thus the first symbol of the MAC tag is 'E'.
- Do a similar thing for the second MAC tag symbol ($n=2$). The permutation is
MFR.QVOETHIUKSBLAC DZWXYJGNP
and the extra random symbol $e_2$ is 'G'.
- Set $x \leftarrow 0$.
- $s_0 = 0$ (the symbol 'A'). Set $x \leftarrow f_2(x + s_0 \mod 28) = f_2(0) = 12$ (the symbol 'M').
- $s_1 = 20$ (the symbol 'U'). Set $x \leftarrow f_2(x + s_1 \mod 28) = f_2(4) = 16$ (the symbol 'Q').
- $s_2 = 19$ (the symbol 'T'). Set $x \leftarrow f_2(x + s_2 \mod 28) = f_2(7) = 4$ (the symbol 'E').
- $s_3 = 23$ (the symbol 'X'). Set $x \leftarrow f_2(x + s_3 \mod 28) = f_2(27) = 15$ (the symbol 'P').
- $s_4 = 16$ (the symbol 'Q'). Set $x \leftarrow f_2(x + s_4 \mod 28) = f_2(3) = 27$ (the symbol '.').
- Finally, set $x \leftarrow x + e_2 \mod 28 = 27 + 6\mod28 = 5$, which is the symbol 'F'. Thus the second symbol of the MAC tag is 'F'.
- The complete MAC tag is "EF".
Security
Each of the $N$ symbols of a MAC tag is an instance of ECBC-MAC using a random one-symbol permutation as a block cipher and encrypting the last "block" (the final $x$ value) using a OTP. MAC keys are used once, then destroyed. Recipients destroy their MAC keys regardless of whether verification succeeds or fails.
- There are $(|A|\cdot |A|!)^N$ unique MAC keys and $|A|^N$ unique MAC tags.
- Encrypting the MAC tag using an OTP provides perfect secrecy for the tag. Adversaries cannot know the tag you calculated prior to encrypting it with the OTP just by looking at it; therefore, they have to rely on structural weaknesses in CBC-MAC to guess MAC tags.
- However, several papers (see 1 and 2 for examples) proved that:
- if the block cipher used in CBC-MAC is a pseudorandom function, then CBC-MAC is a pseudorandom function; and
- the advantage a computationally unbounded adversary has for forging a CBC-MAC that uses a random function as a block cipher over guessing that random function is less than or equal to $3q^{2}
m^{2}/2^{l+1}$, where $q$ is the number of MAC-generating oracle queries the adversary makes, $m$ is the message length (in blocks), and $l$ is the number of bits in the MAC tag. (A similar bound applies if the random function is a random permutation, as in our construction.)
$m$ is the length of our encrypted message (because our "block cipher" is a one-symbol permutation) and $l$ is very small in our construction, $\log_2(|A|)$, so this seems like a terrible MAC to use. But note that the advantage is proportional to $q$.
- However, because we encrypt our CBC-MAC using a OTP and use our MAC keys exactly once, destroying them after use (regardless of whether verification succeeds or fails), adversaries cannot make oracle queries: $q = 0$. (Readers might object that eavesdropping on a message provides one oracle query — one example of a message with a valid MAC tag — but OTP-encrypting the MAC tag hides the CBC-MAC value, in effect denying the adversary even one oracle query.) Adversaries can try to forge a valid message, but they get only one chance because the recipient always destroys his/her OTP and MAC keys.
- Therefore, adversaries have no advantage over simply guessing MAC keys or MAC tags. MAC keys are larger than MAC tags, so intelligent adversaries would try to guess MAC tags; thus the probability that an adversary can forge a valid message in a man-in-the-middle attack is $1/|A|^N$.
If any of the assumptions above or MAC key requirements outlined earlier is violated, these guarantees no longer hold.
Also, you cannot use this scheme if multiple recipients share a MAC key. If there are $R>1$ recipients, an adversary could treat $R-1$ of them like oracles (if the recipients act in ways that reveal whether forgeries succeed or fail) and possibly forge a valid message for recipient $R$.
UPDATE: If $|A|=2$, then this scheme reduces to bit-by-bit XOR, which allows adversaries to arbitrarily permute ciphertext symbols without affecting MAC tags. If $|A|=2$, create a two-bit block permutation (block cipher) — a permutation of $\{0,1,2,3\}$ — and process ciphertext bits two at a time, adding padding if necessary.
Update: Using OTP to encrypt the CBC-MAC tag achieves two things: It prevents adversaries from cryptanalyzing the tag directly or using it to cryptanalyze CBC-MAC (perfect secrecy) and it prevents message extension attacks by transforming CBC-MAC into ECBC-MAC.
A Note on Practicality
Large $|A|$ (such as $28$ as in the OP's question) makes generating and using random permutations by hand more difficult. Transforming plaintexts to and from a decimal code (even A = $0$, B = $1$, and so on) reduces $|A|$ to $10$, creating MAC keys that are easier to use.
Update: Possible Improvements
Generating Only One Permutation
I thought of a possible improvement: Instead of generating $N$ random permutations, generate one, then choose $N$ symbols from $A$ uniformly at random (with replacement). Call each of these random symbols $v_n$ for $n$ in $1,...,N$. You still need to generate a OTP of length $N$ as before. Do this MAC calculation instead (a slight variation on the original):
- Check the length $N$ of the MAC the key generates. For each $n$ in $1,...,N$, do the following:
- Set $x \leftarrow v_n$.
- For each ciphertext symbol $s_i$ (reading the ciphertext left-to-right):
- Let $f(x)$ be the symbol at zero-based index $x$ in the random permutation. Set $x \leftarrow f(x + s_i \mod |A|)$. This assumes that the first symbol in your alphabet has numerical value $0$, the second $1$, and so on.
- $x$ is now the $n$th symbol of the encrypted message's MAC tag.
- Encrypt the MAC tag with the MAC key's OTP.
- Destroy the MAC key along with the message's OTP key — it's a one-time key.
This scheme has $|A|^{2N} \cdot |A|!$ unique keys — high, but far shorter than the original scheme's keys. The security analysis still applies: The CBC-MAC "block cipher" is a truly random single-symbol permutation. Adversaries cannot query a MAC-generating oracle (due to random one-time MAC keys and OTP-encryption of MAC tags), so they're forced to guess either keys or MAC tags. There are still fewer possible tags than there are keys, so adversaries will still guess tags: The probability of a successful forgery is still $1/|A|^N$.
Generating a Random Function
Consider the improvement above (generate only one permutation of $A$). CBC-MAC has similar security bounds (with advantage over guessing random functions proportional to $q$) if the underlying block cipher is a random function; therefore, if $|A|$ is such that picking $|A|$ symbols of $A$ uniformly at random (with replacement) is faster than permuting $A$, the random permutation can instead be a random function $f:A\rightarrow A$.
This is especially nice when $|A|=10$: Roll a 10-sided die ten times to generate the random function.
In this case, the number of unique keys is $|A|^{|A|+2N}$. This is a much larger keyspace than the single-permutation scheme, but it provides similar security.