NFTBridge
60,000 USDC
View results
Submission Details
Severity: medium
Invalid

Incomplete list traversal

Summary

When an entry in the middle of the list is disabled, the function will stop traversing, missing valid entries that come after.

Vulnerability Details

fn get_white_listed_collections(self: @ContractState) -> Span<ContractAddress> {
let mut white_listed = array![];
let mut current = self.white_listed_head.read();
loop {
if current.is_zero() {
break;
}
let (enabled, next) = self.white_listed_list.read(current);
if !enabled {
break;
} else {
white_listed.append(current);
current = next;
}

https://github.com/Cyfrin/2024-07-ark-project/blob/273b7b94986d3914d5ee737c99a59ec8728b1517/apps/blockchain/starknet/src/bridge.cairo#L330C8-L343C18

The above is implementing a linked list where self.white_listed_head points to the first element of the list. Each element in the list is stored in self.white_listed_list. Each element contains two pieces of information: an enabled flag and a next pointer. The next pointer points to the next element in the list. And it ends when current becomes zero (null pointer in this context).

The issue lies in this part of the code:

if !enabled {
break;
} else {
white_listed.append(current);
current = next;
}

https://github.com/Cyfrin/2024-07-ark-project/blob/273b7b94986d3914d5ee737c99a59ec8728b1517/apps/blockchain/starknet/src/bridge.cairo#L338C15-L343C18

The function breaks the loop as soon as it encounters a disabled entry. This can lead to incomplete list traversal.

Imagine we have a linked list like this: A (enabled) -> B (enabled) -> C (disabled) -> D (enabled) -> E (enabled) -> null

  • The function starts at A, sees it's enabled, adds it to the list, and moves to B.

  • It sees B is enabled, adds it to the list, and moves to C.

  • When it reaches C, it sees that C is disabled. At this point, instead of skipping C and moving to D, the function breaks the loop entirely.

  • As a result, D and E are never reached, even though they are enabled and should be included in the white list.

  • The function returns only [A, B] instead of the complete list of enabled addresses [A, B, D, E].

Impact

The function will return an incomplete list of white-listed collections.

Tools Used

Manual review

Recommendations

Modify the loop to continue even when encountering a disabled entry:

loop {
if current.is_zero() {
break;
}
let (enabled, next) = self.white_listed_list.read(current);
if enabled {
white_listed.append(current);
}
current = next;
}
Updates

Lead Judging Commences

n0kto Lead Judge 11 months ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.