| Package Name | Ecosystem | Vulnerable Versions | First Patched Version |
|---|---|---|---|
| github.com/cometbft/cometbft | go | <= 0.37.15 | 0.37.16 |
| github.com/cometbft/cometbft | go | >= 0.38.0-alpha.1, <= 0.38.18 | 0.38.19 |
The vulnerability exists in CometBFT's handling of the BitArray data structure, which is used in various peer-to-peer messages. The root cause is a failure to validate that the BitArray's internal state is consistent, specifically that the length of its Elems slice (which holds the bit data) corresponds correctly to the number of Bits it claims to represent.
An attacker can craft a network message, such as NewValidBlockMessage, ProposalPOLMessage, or VoteSetBitsMessage, containing a BitArray with this inconsistency. The analysis of the patches shows that the ValidateBasic methods for these message types in consensus/reactor.go were missing the necessary validation for their BitArray fields.
When a vulnerable node receives such a message, it accepts the malformed BitArray. Subsequent operations on this BitArray, such as those performed by bits.BitArray.setIndex or bits.BitArray.getNumTrueIndices, would then result in an out-of-bounds memory access, causing the node process to panic and crash. Because these messages are gossiped to other peers before being fully processed, the vulnerability could be used to trigger a cascading failure across the network, leading to a halt.
The patches rectify this by first introducing a ValidateBasic method on the BitArray type itself to check for the inconsistency. Secondly, they add calls to this new validation method within the ValidateBasic methods of the message types that carry BitArrays, ensuring that invalid messages are rejected upon receipt. Finally, defensive guards were added to the internal BitArray methods (setIndex, getNumTrueIndices) as a secondary protection against panics.
consensus.NewValidBlockMessage.ValidateBasicconsensus/reactor.go
consensus.ProposalPOLMessage.ValidateBasicconsensus/reactor.go
consensus.VoteSetBitsMessage.ValidateBasicconsensus/reactor.go
bits.BitArray.setIndexlibs/bits/bit_array.go
bits.BitArray.getNumTrueIndiceslibs/bits/bit_array.go
Ongoing coverage of React2Shell