Skip to content

Check current receiver typestate across loops - #384

Open
CatarinaGamboa wants to merge 1 commit into
mainfrom
fix/338-zero-iteration
Open

CatarinaGamboa wants to merge 1 commit into
mainfrom
fix/338-zero-iteration

Conversation

@CatarinaGamboa

Copy link
Copy Markdown
Collaborator

A state change inside a loop must not establish the receiver state after a loop that can run zero times. Main already havocs local receivers, but calls on explicit and implicit this skipped receiver state checking entirely. For example, while (n > 0) { this.mark(); n--; } this.reset(); incorrectly passed.

Initialize each instance method's receiver from its declared entry states, resolve current this and unqualified super through the same receiver predicate, and include that receiver in loop havoc. Qualified outer receivers retain their existing handling. State-preserving methods with multiple entry alternatives check the union of those preconditions, so a wrapper accepting either state can call another method accepting either state.

Add passing and failing regressions for local receivers in while/for/foreach loops, explicit and implicit this, later iterations, direct receiver calls, unconditional transitions after loops, and multiple state-preserving entry alternatives.

Validation: mvn -pl liquidjava-verifier test — 389 tests, zero failures or errors.

Precision remains conservative: loops forget changed receiver state, and methods with alternative transitions that change state still require one applicable alternative to be provable. This change does not initialize constructor receivers or expand instance methods named main.

Closes #338.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Soundness: after a loop, the state is taken from the loop body as if it ran at least once

2 participants