cybersecurity · intermediate · ~20 min
Implement correct PKCS#7 padding validation — the check whose mistakes cause padding oracles.
Block ciphers pad the final block with PKCS#7: if p bytes of padding are needed, every one of those bytes has the value p (1..block). Implement
int pkcs7_unpad(const unsigned char *buf, size_t n, size_t block)
returning the length without padding, or -1 if the padding is invalid. Valid input requires n > 0, n % block == 0, the last byte p in 1..block, and the last p bytes all equal p. (Sloppy validation here is the root of padding-oracle attacks.)
#include <stddef.h>
int pkcs7_unpad(const unsigned char *buf, size_t n, size_t block) {
/* TODO: validate n>0 and n%block==0; let p=last byte; require 1<=p<=block
and the last p bytes all == p. Return n-p, or -1 if invalid. */
(void)buf;(void)n;(void)block; return -1;
}
Only checking the last byte (not all p bytes); allowing p=0 or p>block; not requiring a block multiple.
Full block of padding (p==block -> length 0). p out of range. n not a multiple of block. Empty buffer.
O(block).
Solve this exercise in the browser editor — compile and run against the test harness, no setup required.