Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
123 changes: 123 additions & 0 deletions liquidjava-example/src/main/java/testSuite/CorrectNullChecks.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
package testSuite;

import java.util.ArrayList;
import java.util.Date;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class CorrectNullChecks {

void testNullInteger() {
Integer i = null;

@Refinement("_ == null")
Integer i1 = i;

i = 123;

@Refinement("_ != null")
Integer i2 = i;
}

void testNullString() {
String s = null;

@Refinement("_ == null")
String s1 = s;

s = "hello";

@Refinement("_ != null")
String s2 = s;
}

void testNulls() {
@Refinement("_ == null")
String s = null;

@Refinement("_ == null")
Integer i = null;

@Refinement("_ == null")
Boolean b = null;

@Refinement("_ == null")
Double d = null;

@Refinement("_ == null")
Long l = null;

@Refinement("_ == null")
Float f = null;

@Refinement("_ == null")
Date dt = null;

@Refinement("_ == null")
ArrayList<String> lst = null;
}

void testNonNulls() {
@Refinement("_ != null")
String s = "hello";

@Refinement("_ != null")
Integer i = 123;

@Refinement("_ != null")
Boolean b = true;

@Refinement("_ != null")
Double d = 1.0;

@Refinement("_ != null")
Long l = 2L;

@Refinement("_ != null")
Float f = 1.0f;

@Refinement("_ != null")
Date dt = new Date();

@Refinement("_ != null")
ArrayList<String> lst = new ArrayList<>();
}

void testNullChecksInMethods() {
@Refinement("_ != null")
String x = returnNotNullIf(null);

@Refinement("_ != null")
String y = returnNotNullTernary(null);

@Refinement("_ != null")
String z = returnNotNullParam("not null");

@Refinement("_ == null")
String w = returnNull();
}

@Refinement("_ != null")
String returnNotNullIf(String s) {
if (s == null)
s = "default";

return s;
}

@Refinement("_ != null")
String returnNotNullTernary(String s) {
return s != null ? s : "default";
}

@Refinement("_ != null")
String returnNotNullParam(@Refinement("_ != null") String s) {
return s;
}

@Refinement("_ == null")
String returnNull() {
return null;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorAliasNotFound {

public static void main(String[] args) {
Expand Down
12 changes: 12 additions & 0 deletions liquidjava-example/src/main/java/testSuite/ErrorBoxedBoolean.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorBoxedBoolean {
public static void main(String[] args) {
@Refinement("_ == true")
Boolean b = false;
}
}
12 changes: 12 additions & 0 deletions liquidjava-example/src/main/java/testSuite/ErrorBoxedDouble.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorBoxedDouble {
public static void main(String[] args) {
@Refinement("_ > 0")
Double d = -1.0;
}
}
12 changes: 12 additions & 0 deletions liquidjava-example/src/main/java/testSuite/ErrorBoxedInteger.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorBoxedInteger {
public static void main(String[] args) {
@Refinement("_ > 0")
Integer j = -1;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorGhostNotFound {

public void test() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorLongUsagePredicates1 {
void testUUID(){
@Refinement("((v/4096) % 16) == 2")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorLongUsagePredicates2 {
void testLargeSubtractionWrong() {
@Refinement("v - 9007199254740992 == 2")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorLongUsagePredicates3 {
void testWrongSign() {
@Refinement("v < 0")
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorNullCheckAssignNonNull {
public static void main(String[] args) {
@Refinement("_ == null")
String s = "not null";
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorNullCheckAssignNull {
public static void main(String[] args) {
@Refinement("_ != null")
String s = null;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorNullCheckAssignNullAfter {
public static void main(String[] args) {
@Refinement("_ != null")
String s = "not null";
s = null; // error
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
// Refinement Error
package testSuite;

import java.util.Date;

import liquidjava.specification.Refinement;

@SuppressWarnings("unused")
public class ErrorNullCheckAssignNullObject {
public static void main(String[] args) {
@Refinement("_ != null")
Date date = null;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Refinement Error
package testSuite;

import liquidjava.specification.Refinement;

public class ErrorNullCheckMethod {

@Refinement("_ != null")
String returnNotNull(String s) {
return s; // error: s can be null
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package testSuite.classes.atomic_reference_correct;

import liquidjava.specification.ExternalRefinementsFor;
import liquidjava.specification.StateRefinement;
import liquidjava.specification.StateSet;

@StateSet({"empty", "holding"})
@ExternalRefinementsFor("java.util.concurrent.atomic.AtomicReference")
public interface AtomicReferenceRefinements<V> {

@StateRefinement(to="initialValue == null ? empty(this) : holding(this)")
public void AtomicReference(V initialValue);

@StateRefinement(from="holding(this)")
public V get();

@StateRefinement(to="newValue == null ? empty(this) : holding(this)")
public void set(V newValue);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package testSuite.classes.atomic_reference_correct;

import java.util.concurrent.atomic.AtomicReference;

@SuppressWarnings("unused")
public class AtomicReferenceTest {

public void testOk() {
AtomicReference<String> ref = new AtomicReference<>("hello");
String s = ref.get();

ref.set("world");
String s2 = ref.get();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
State Refinement Error
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
package testSuite.classes.atomic_reference_error;

import liquidjava.specification.ExternalRefinementsFor;
import liquidjava.specification.StateRefinement;
import liquidjava.specification.StateSet;

@StateSet({"empty", "holding"})
@ExternalRefinementsFor("java.util.concurrent.atomic.AtomicReference")
public interface AtomicReferenceRefinements<V> {

@StateRefinement(to="initialValue == null ? empty(this) : holding(this)")
public void AtomicReference(V initialValue);

@StateRefinement(from="holding(this)")
public V get();

@StateRefinement(to="newValue == null ? empty(this) : holding(this)")
public void set(V newValue);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package testSuite.classes.atomic_reference_error;

import java.util.concurrent.atomic.AtomicReference;

@SuppressWarnings("unused")
public class AtomicReferenceTest {

public void testError() {
AtomicReference<String> ref = new AtomicReference<>(null);
String s = ref.get(); // error
}
}

4 changes: 3 additions & 1 deletion liquidjava-verifier/src/main/antlr4/rj/grammar/RJ.g4
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,8 @@ literal:
BOOL
| STRING
| INT
| REAL;
| REAL
| NULL;

//----------------------- Declarations -----------------------

Expand Down Expand Up @@ -89,6 +90,7 @@ BOOLOP : '=='|'!='|'>='|'>'|'<='|'<';
ARITHOP : '+'|'*'|'/'|'%';//|'-';

BOOL : 'true' | 'false';
NULL : 'null';
ID_UPPER: ([A-Z][a-zA-Z0-9]*);
OBJECT_TYPE:
(([a-zA-Z][a-zA-Z0-9]+) ('.' [a-zA-Z][a-zA-Z0-9]*)+);
Expand Down
Loading