# How to break CBC cipher with partly known plaintext?

I'm learning some IT security and during practice I found an exercise I couldn't solve.

I have an encrypted message with block cipher in CBC mode. The blocks are one byte long and the first block is an IV. I know 80% of the plaintext which is a form but there are missing parts. I don't know anything about the encryption function.

Which attack method should I use, and where to start?
I know, that $$C_1=Enc_k (M_1\oplus C_0)$$. I know $$C_1$$, $$M_1$$ and $$C_0$$, the IV.

• Encryption process in CBC mode is performed as \begin{align} C_1 &= Enc_k(P_1 \oplus IV)\\ C_i &= Enc_k(P_i \oplus C_{i-1}),\;\; 1 < i \leq nb, \end{align} where $nb$ is the number of blocks. Your question is not clear. – kelalaka Mar 3 '20 at 19:01
• Yes, this is the precise formula, I worked according to this. – user312442 Mar 3 '20 at 20:24
• But you use $\oplus$ instead of Encryption! – kelalaka Mar 3 '20 at 20:26
• OMG, you are right! Sorry about that. But how should I start then? I edited the post. – user312442 Mar 3 '20 at 20:41
• I thought that was simple XOR, but that was wrong. The hint was, that the IV is the first byte of the ciphertext. Is it possible to find out the algorithm from this? – user312442 Mar 3 '20 at 21:20

$$\mathrm{Enc}_k$$ always transforms the same block value to the same block value. Since blocks are only one byte long, there are only 256 different block values. So you can build a table of those from the parts of the plaintext that you know. Once you've built that table, you can use it in the reverse direction to calculate $$\mathrm{Dec}_k$$.

$$\begin{array}{l|l} x & \mathrm{Enc}_k(x) \\ \hline 0 & \_ \\ 1 & \_ \\ \vdots \\ 255 & \_ \\ \end{array}$$

Knowing $$M_1$$, the equation $$C_1 = \mathrm{Enc}_k(M_1 \oplus C_0)$$ gives you one entry in the table. More generally, whenever you know the value $$M_i$$, the equation $$C_{i+1} = \mathrm{Enc}_k(M_{i+1} \oplus C_i)$$ gives you one entry in the table. Some positions may call $$\mathrm{Enc}_k$$ on the same input as another position, so it may take more than 256 known bytes in the plaintext, but with a few hundred bytes of known plaintext the probability of missing entries decreases rapidly¹ since the inputs for different values of $$i$$ are essentially random.

If there are missing values in the table, you can narrow things down in two ways. First, since $$\mathrm{Enc}_k$$ is a permutation, all the values in the second column are distinct. Second, all the $$M_i$$ are probably printable characters, which limits the possibilities. Within the scope of the exercise, I'd expect that if there are any blanks, they're easy to fill in with a little hand-driven calculation.

The core of the problem is the 8-bit block. An 8-bit block is far, far too short. In the real world, older block ciphers such as DES and ((X)X)TEA have 64-bit blocks, and modern block ciphers have 128-bit blocks. Even with a 64-bit block, such a table attack is unlikely to give any useful results (the table would require 128 EiB of sttorage, and you'd need roughly that amount of guessable plaintext with a known ciphertext to build it). 64-bit blocks are vulnerable to a sparse version of this attack where you hope that $$\mathrm{Enc}_k$$ has been called twice on the same input, and this reveals something about the message (if $$C_i = C_j$$ then $$M_i \oplus C_{i-1} = M_j \oplus C_{j-1}$$, which reveals the value of $$M_i \oplus M_j$$, and in particular reveals $$M_j$$ if you know $$M_i$$). And you only need about $$2^{32}$$ blocks of message to have a decent chance of a repeated block value (birthday bound), which makes this attack practical (most famously as Sweet32).

CBC itself with a block cipher with a decent-size block and with a random IV is secure even against chosen-plaintext attacks (IND-CPA). However, it is not at all secure against adaptative chosen-plaintext attacks, where the attacker can submit some plaintext to encrypt after seeing the previous portion of the ciphertext.

In the adaptative case, I know $$C_i$$ and am allowed to submit $$M_{i+1}$$ which lets me learn $$C_{i+1} = \mathrm{Enc}_k(M_{i+1} \oplus C_i)$$. So I choose $$M_{i+1} = C_i \oplus x$$ and this way I can learn $$\mathrm{Enc}_k(x)$$ for an arbitrary $$x$$. If I've guessed a plausible value for $$M_j$$ for some $$j$$, this lets me verify this guess by testing whether $$C_{i+1} = C_j$$.

CBC as used in practice is not secure in general because it requires padding, since CBC can only encrypt a whole number of blocks. Padding is vulnerable to padding oracle attacks in scenarios where the attacker can submit chosen ciphertext. This is why CBC is deprecated, especially for communication. (It can be ok for storage where the adversary might be able to see ciphertext, e.g. from leaked backups, but has no way to inject ciphertext.)

¹ Unless $$\mathrm{Enc}_k$$ has some correlation with $$M$$.

• The solution was indeed the content leak: there were several matching blocks (since the block length is so small), and I knew many parts of the plaintext, so I could figure it out one by one (a few were missing, but still good enough). Thank you for your help! – user312442 Mar 4 '20 at 12:26