An attacker discovers a padding vulnerability.

Overview

This post presents a lab-based demonstration of a padding oracle attack targeting AES-CBC with PKCS#7 padding. The aim is to illustrate how an oracle that reveals padding errors can be leveraged to decrypt ciphertext—and even encrypt arbitrary plaintext—within a controlled environment, using publicly available tooling.
https://en.wikipedia.org/wiki/Block_cipher_mode_of_operation#Cipher_block_chaining_(CBC)

A “Padding Oracle” tells you whether or not the request failed due to the ciphertext being wrong, or if it is the padding that is wrong.

Lab Setup & Observations

An application accepts an encrypted blob (e.g., as part of a filename for a file downloader function).

Depending on the validity of the encrypted blob (if it decrypts properly, or if a padding oracle is thrown), we see the following behavior:

Valid ciphertext → HTTP 200 OK
Invalid ciphertext (decryption error) → HTTP 500 Internal Server Error
Valid ciphertext, but incorrect padding → HTTP 404 Not Found

These distinctions constitute a padding oracle, enabling block-level cryptographic manipulation.

Exploitation Using PadBuster

1. Identify the Oracle

The user places an order on the application. The user receives an email with the following link. Make sure to test all these endpoints!

http://topup.webhacklab.com/download.aspx?invoice=hul3Q5QtPwN+QtRuWybGHp0izAtNYvrz8n3OpJzMujmpsUktDkcKCBcsJjMKD5BzilKEpLFcnOFznJj8raOVKw==

We visit the link and download an invoice.


We base64 decode it and it looks like encrypted data.

The user submits the request and the PDF invoice is downloaded.

The user alters a single character at the end of the string. This is to create an error in padding in the final block.

We know that the word “Padding” comes up in the response whenever this case is hit. That’s our padding oracle.

2. Decrypt Existing Data
We can use padbuster to decrypt the ciphertext by basically brute forcing every one block at a time and checking the padding. This drastically reduces the key space.

    padbuster.pl "http://topup.webhacklab.com/download.aspx?invoice=ovlTyB363VbzIPh921FK4QCn6gavqYLVAF2eN8hDkaDX5hkVAJy4wOOph3WB/41MBBW5DgCuyEUNjEtNkLFN0g==" "ovlTyB363VbzIPh921FK4QCn6gavqYLVAF2eN8hDkaDX5hkVAJy4wOOph3WB/41MBBW5DgCuyEUNjEtNkLFN0g==" 16 -encoding 0 -error "Padding"

    We find the decrypted ciphertext! It’s a pdf. We knew that already.

    3. Encrypt Arbitrary Plaintext
    Next, we exploit the CBC nature by knowing that we can remove blocks from the end and substitute our own.

    We then reused the oracle to encrypt a chosen plaintext, specifically, the string ../../web.config. This was done by submitting modified ciphertext blocks via PadBuster and observing padding-error responses to derive a valid encrypted blob.

    padbuster.pl "http://topup.webhacklab.com/download.aspx?invoice=ovlTyB363VbzIPh921FK4QCn6gavqYLVAF2eN8hDkaDX5hkVAJy4wOOph3WB/41MBBW5DgCuyEUNjEtNkLFN0g==" "ovlTyB363VbzIPh921FK4QCn6gavqYLVAF2eN8hDkaDX5hkVAJy4wOOph3WB/41MBBW5DgCuyEUNjEtNkLFN0g==" 16 -encoding 0 -error "Padding" -plaintext ../../web.config

    We use -encoding 0 for base64. We specify the response that shows the padding error as “Padding”.

    4. Obtain Target File

    By substituting our crafted ciphertext into the download endpoint, we were able to retrieve the web.config file, revealing a plaintext database connection string.

    Leave a Reply

    Your email address will not be published. Required fields are marked *

    Post comment