# Help understanding how to decrypt cipher

I am trying to create a padding oracle attack to decrypt a cipher that is encrypted with cbc and PKCS#7 padding.

My first step is just to try and decrypt the second block.

I have read a lot about it, and have started to code the first step of the attack, where I edit last byte in the first block and send it to the oracle. But there is a point of the attack/decryption method I'm a bit confused about regarding the xor of the bytes.

The part I don't understand completely is the math on how manipulating the last byte in the first block result in the last byte in the decrypted byte to turns out to be 0x01, 0x02 etc.

I haven't figured out how the math for that works, for what I have researched it should just be to xor OriginalByte xor TestByte xor 1.

Should that be equal to 0x01?

Here I have a string "TestBlockForStackBBBBBBBBBBBa31", it is 31 bytes. That means that it has to get padded with 1 to make it equal to 32 bytes so it fits inside 16 byte blocks. The string byte is as following (without encryption):

54657374426C6F636B466F72537461636B4242424242424242424242613331


Then we decrypt the string with the key and IV below using cbc and PKCS#7.

byte[] Key = new byte[]{1, 2, 3, 4, 5, 6, 7, 8, 9, 9, 9, 9, 9, 9, 9, 9};
//we don't need key the key under the attach, only under encryption.
byte[] IV  = new byte[]{2, 3, 2, 3, 2, 3, 2, 3, 2, 2, 2, 2, 2, 2, 2, 2 };


We then get this result:

Ciphertext:  ;fŒ˜ÆOgÄ:VûÎ{Ž+6iXK¿îMŠžÌš

Cipher bytes: 3B668C98C64F67C43A56FBCE7B8E150E9D2B1F3669584BBFEE4D8A0E189ECC9A


Under the padding oracle attack I edit the last byte in the first block

(3B668C98C64F67C43A56FBCE7B8E15 0E <--).


I know that when I edit the last byte in the first block to 0D the decryption result will have a 0x01 at the end. The first block is then going to look like this:

3B668C98C64F67C43A56FBCE7B8E150D


And what I then send to the oracle in this case DecryptStringFromBytes (code can be found in RijndaelManaged.CreateDecryptor Method) is the following first the edited chiper 3B668C98C64F67C43A56FBCE7B8E150D9D2B1F3669584BBFEE4D8A0E189ECC9A, then the key that is only 0 (Key = new byte[16]), then the same iv as above.

It then returns that the padding is valid. I did go into the function BCryptDecrypt (used inside the decryption call) and set a breakpoint to confirm this, and it is indeed 0x01.

The output bytes from the call BCryptDecrypt is then like this:

 [0]  0x95    byte        [1] 0x28    byte        [2] 0xE5    byte        [3] 0x18    byte
[4]  0x90    byte        [5] 0x8E    byte        [6] 0x31    byte        [7] 0xFF    byte
[8]  0xF0    byte        [9] 0x28    byte       [10] 0x86    byte       [11] 0x7B    byte
[12]  0x9D    byte       [13] 0x63    byte       [14] 0x2F    byte       [15] 0x01    byte


The decrypted file result that returns from the decrypter to the user looks like this:

Text :  ?????xi?G?w?T}!y?(???1??(?{?c/ Bytes :
3F3F3F3F3F78693F473F773F547D21793F283F183F3F313F3F283F7B3F632F (Thay
have removed the 0x01 and the bytes is a bit different, maybe something
with how I formatted it or it does something more before returning the
bytes?)


So my questions are:

• How does the info I did send turn out to be 0x01 at the end?
• What do I need to xor to the result to get the plaintext/byte?
• I do think this question is fundamentally on-topic here, even if it's a bit messy in some places. I feel like there really should be a canonical question for "how to carry out a CBC padding oracle attack step by step", but the only existing one I could find is this one, which is... not that great. :/ – Ilmari Karonen May 15 '19 at 16:52
• @IlmariKaronen I have recently written a full text (in a different context) of how this works in general, I'll probably write something up later today (here and / or in a more generic Q/A). – SEJPM May 15 '19 at 18:18
• @SEJPM That had been very nice. Maybe you can link to the thing you did write :) If you are going to write more. Can you please make a eksempel showcasing what happens to the bytes. Using eksempel ciphers etc. Most article i have read does just explain with letters, without really explain good enough what does letters mean. That can be hard for people that are new to this and are looking to learn, at least for me. It had been much more easy to use the bytes from a chipper instead of the letters. The ideal thing had been to combane this two. – yostart123 May 15 '19 at 19:56
• @SEJPM I am really going to appreciate it, and i don't think i am the only one that is going to. <3 – yostart123 May 15 '19 at 19:56
• Something about your example is weird: The ciphertext is 32 bytes, it should be 48 bytes (including the IV) or does .NET transport that one out-of-band? – SEJPM May 15 '19 at 20:43