Vulnerability : Inconsistent Balance Tracking Leads to Potential DoS
Root + Impact
Description
The contract uses a state variable balance to manually track the funds in the resource account. This internal counter can become out of sync with the true APT balance, and the claim_pizza_slice function relies on this potentially inaccurate balance for its E_INSUFFICIENT_FUND check.
public entry fun fund_pizza_drop(owner: &signer, amount: u64) acquires ModuleData, State {
    // ...
    coin::transfer<AptosCoin>(owner, resource_addr, amount);
@>  state.balance = state.balance + amount;
}
public entry fun claim_pizza_slice(user: &signer) acquires ModuleData, State {
    // ...
@>  assert!(state.balance >= amount, E_INSUFFICIENT_FUND);
    // ...
@>  state.balance = state.balance - amount;
}
Risk
Likelihood:
- 
This will occur when funds are transferred directly to the resource account's address, bypassing the fund_pizza_dropfunction.
 
- 
The contract's internal state will not reflect the new funds, leading to incorrect validation. 
Impact:
- Denial of Service (DoS): If the internal - balanceis incorrectly lower than the actual balance, legitimate users will be blocked from claiming their airdrop, as the assertion- state.balance >= amountwill fail even when enough funds are present.
 
Proof of Concept
A mismatch between the tracked and actual balance can lock legitimate users out of their funds.
     public entry fun claim_pizza_slice(user: &signer) acquires ModuleData, State {
         let user_addr = signer::address_of(user);
         let state = borrow_global_mut<State>(get_resource_address());
-        // ...
-        // Check if contract has sufficient balance
-        assert!(state.balance >= amount, E_INSUFFICIENT_FUND);
+        // POC:
+        // 1. Internal state.balance is 0.
+        // 2. 10,000 APT is sent directly to the resource account. Actual balance is 10,000.
+        // 3. User tries to claim. The check `assert!(0 >= 300, ...)` fails, blocking the claim.
     }
Recommended Mitigation
Remove the manual balance variable and check the real-time balance of the resource account directly.
- // In the `State` struct:
- balance: u64,
- // In `fund_pizza_drop`:
- state.balance = state.balance + amount;
- // In `claim_pizza_slice`:
- assert!(state.balance >= amount, E_INSUFFICIENT_FUND);
- state.balance = state.balance - amount;
+ // In `claim_pizza_slice`:
+ assert!(get_actual_apt_balance() >= amount, E_INSUFFICIENT_FUND);