People often ask me "How did you learn how to hack?" The answer: by reading. This page is a collection of the blog posts and other articles that I have accumulated over the years of my journey. Enjoy!
Commit is used for the finalized proof within a block being accepted and bundling the block ID with a set of signatures. Each commit signature is a validator's vote attesting to that block. Commit structure stores the entirety of the block information. The signatures are a list of CommitSig objects, each containing an address, timestamp, and signature. When performing commit signature verification, the index of the signature is used to find the amount of voting power. When computing the median time, the validator address is used instead. If the address is not present in the current validator set, then it's simply skipped. ValidatorAddress doesn't matter; it's only the index of the signature. So, the submitter of a block can use an invalid ValidatorAddress to force the lookup of an invalid value for the median time difference! The example exploit makes the attacker's validator address the ONLY valid address and index, allowing them to set the block timestamp arbitrarily.