Skip to content

Commit ea8f25e

Browse files
committed
Distinguishing between Modulo and Remainder #231
1 parent 5c6628e commit ea8f25e

File tree

69 files changed

+395
-103
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

69 files changed

+395
-103
lines changed

lisa/lisa-core/src/main/java/it/unive/lisa/analysis/dataflow/ConstantPropagation.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
import it.unive.lisa.symbolic.value.ValueExpression;
1616
import it.unive.lisa.symbolic.value.operator.AdditionOperator;
1717
import it.unive.lisa.symbolic.value.operator.DivisionOperator;
18-
import it.unive.lisa.symbolic.value.operator.ModuleOperator;
18+
import it.unive.lisa.symbolic.value.operator.ModuloOperator;
1919
import it.unive.lisa.symbolic.value.operator.MultiplicationOperator;
2020
import it.unive.lisa.symbolic.value.operator.SubtractionOperator;
2121
import it.unive.lisa.symbolic.value.operator.unary.NumericNegation;
@@ -102,7 +102,7 @@ private static Integer eval(SymbolicExpression e, DefiniteForwardDataflowDomain<
102102
return left + right;
103103
if (binary.getOperator() instanceof DivisionOperator)
104104
return left == 0 ? null : (int) left / right;
105-
if (binary.getOperator() instanceof ModuleOperator)
105+
if (binary.getOperator() instanceof ModuloOperator)
106106
return right == 0 ? null : left % right;
107107
if (binary.getOperator() instanceof MultiplicationOperator)
108108
return left * right;

lisa/lisa-core/src/main/java/it/unive/lisa/analysis/numeric/IntegerConstantPropagation.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
import it.unive.lisa.symbolic.value.ValueExpression;
1515
import it.unive.lisa.symbolic.value.operator.AdditionOperator;
1616
import it.unive.lisa.symbolic.value.operator.DivisionOperator;
17-
import it.unive.lisa.symbolic.value.operator.ModuleOperator;
17+
import it.unive.lisa.symbolic.value.operator.ModuloOperator;
1818
import it.unive.lisa.symbolic.value.operator.MultiplicationOperator;
1919
import it.unive.lisa.symbolic.value.operator.SubtractionOperator;
2020
import it.unive.lisa.symbolic.value.operator.binary.BinaryOperator;
@@ -140,7 +140,7 @@ else if (left.isTop() || right.isTop() || left.value % right.value != 0)
140140
return top();
141141
else
142142
return new IntegerConstantPropagation(left.value / right.value);
143-
else if (operator instanceof ModuleOperator)
143+
else if (operator instanceof ModuloOperator)
144144
return left.isTop() || right.isTop() ? top() : new IntegerConstantPropagation(left.value % right.value);
145145
else if (operator instanceof MultiplicationOperator)
146146
return left.isTop() || right.isTop() ? top() : new IntegerConstantPropagation(left.value * right.value);

lisa/lisa-core/src/main/java/it/unive/lisa/analysis/numeric/Parity.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
import it.unive.lisa.symbolic.value.ValueExpression;
1414
import it.unive.lisa.symbolic.value.operator.AdditionOperator;
1515
import it.unive.lisa.symbolic.value.operator.DivisionOperator;
16-
import it.unive.lisa.symbolic.value.operator.ModuleOperator;
16+
import it.unive.lisa.symbolic.value.operator.ModuloOperator;
1717
import it.unive.lisa.symbolic.value.operator.MultiplicationOperator;
1818
import it.unive.lisa.symbolic.value.operator.SubtractionOperator;
1919
import it.unive.lisa.symbolic.value.operator.binary.BinaryOperator;
@@ -159,7 +159,7 @@ else if (operator instanceof DivisionOperator)
159159
return right.isOdd() ? ODD : EVEN;
160160
else
161161
return right.isOdd() ? EVEN : TOP;
162-
else if (operator instanceof ModuleOperator)
162+
else if (operator instanceof ModuloOperator)
163163
return TOP;
164164

165165
return TOP;

lisa/lisa-core/src/main/java/it/unive/lisa/analysis/numeric/Sign.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
import it.unive.lisa.symbolic.value.ValueExpression;
1515
import it.unive.lisa.symbolic.value.operator.AdditionOperator;
1616
import it.unive.lisa.symbolic.value.operator.DivisionOperator;
17+
import it.unive.lisa.symbolic.value.operator.ModuloOperator;
1718
import it.unive.lisa.symbolic.value.operator.MultiplicationOperator;
1819
import it.unive.lisa.symbolic.value.operator.SubtractionOperator;
1920
import it.unive.lisa.symbolic.value.operator.binary.BinaryOperator;
@@ -213,7 +214,7 @@ else if (left.equals(right))
213214
return left.isTop() ? left : POS;
214215
else
215216
return top();
216-
else if (operator instanceof it.unive.lisa.symbolic.value.operator.ModuleOperator)
217+
else if (operator instanceof ModuloOperator)
217218
return top();
218219
else if (operator instanceof MultiplicationOperator)
219220
if (left.isZero() || right.isZero())
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
package it.unive.lisa.program.cfg.statement.numeric;
2+
3+
import it.unive.lisa.analysis.AbstractState;
4+
import it.unive.lisa.analysis.AnalysisState;
5+
import it.unive.lisa.analysis.SemanticException;
6+
import it.unive.lisa.analysis.StatementStore;
7+
import it.unive.lisa.analysis.heap.HeapDomain;
8+
import it.unive.lisa.analysis.value.TypeDomain;
9+
import it.unive.lisa.analysis.value.ValueDomain;
10+
import it.unive.lisa.interprocedural.InterproceduralAnalysis;
11+
import it.unive.lisa.program.cfg.CFG;
12+
import it.unive.lisa.program.cfg.CodeLocation;
13+
import it.unive.lisa.program.cfg.statement.Expression;
14+
import it.unive.lisa.symbolic.SymbolicExpression;
15+
import it.unive.lisa.symbolic.value.BinaryExpression;
16+
import it.unive.lisa.symbolic.value.operator.binary.NumericNonOverflowingMod;
17+
import it.unive.lisa.type.NumericType;
18+
import it.unive.lisa.type.Type;
19+
import it.unive.lisa.type.TypeSystem;
20+
21+
/**
22+
* An expression modeling the modulo operation ({@code %}, returning the
23+
* remainder of the division between the two operands and taking the sign of the
24+
* divisor). Both operands' types must be instances of {@link NumericType}. The
25+
* type of this expression is the common numerical type of its operands,
26+
* according to the type inference.
27+
*
28+
* @author <a href="mailto:[email protected]">Luca Negrini</a>
29+
*/
30+
public class Modulo extends it.unive.lisa.program.cfg.statement.BinaryExpression {
31+
32+
/**
33+
* Builds the modulo.
34+
*
35+
* @param cfg the {@link CFG} where this operation lies
36+
* @param location the location where this literal is defined
37+
* @param left the left-hand side of this operation
38+
* @param right the right-hand side of this operation
39+
*/
40+
public Modulo(CFG cfg, CodeLocation location, Expression left, Expression right) {
41+
super(cfg, location, "%", left, right);
42+
}
43+
44+
@Override
45+
public <A extends AbstractState<A, H, V, T>,
46+
H extends HeapDomain<H>,
47+
V extends ValueDomain<V>,
48+
T extends TypeDomain<T>> AnalysisState<A, H, V, T> binarySemantics(
49+
InterproceduralAnalysis<A, H, V, T> interprocedural,
50+
AnalysisState<A, H, V, T> state,
51+
SymbolicExpression left,
52+
SymbolicExpression right,
53+
StatementStore<A, H, V, T> expressions)
54+
throws SemanticException {
55+
TypeSystem types = getProgram().getTypes();
56+
if (left.getRuntimeTypes(types).stream().noneMatch(Type::isNumericType))
57+
return state.bottom();
58+
if (right.getRuntimeTypes(types).stream().noneMatch(Type::isNumericType))
59+
return state.bottom();
60+
61+
return state.smallStepSemantics(
62+
new BinaryExpression(
63+
getStaticType(),
64+
left,
65+
right,
66+
NumericNonOverflowingMod.INSTANCE,
67+
getLocation()),
68+
this);
69+
}
70+
}

lisa/lisa-sdk/src/main/java/it/unive/lisa/program/cfg/statement/numeric/Remainder.java

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -13,23 +13,24 @@
1313
import it.unive.lisa.program.cfg.statement.Expression;
1414
import it.unive.lisa.symbolic.SymbolicExpression;
1515
import it.unive.lisa.symbolic.value.BinaryExpression;
16-
import it.unive.lisa.symbolic.value.operator.binary.NumericNonOverflowingMod;
16+
import it.unive.lisa.symbolic.value.operator.binary.NumericNonOverflowingRem;
1717
import it.unive.lisa.type.NumericType;
1818
import it.unive.lisa.type.Type;
1919
import it.unive.lisa.type.TypeSystem;
2020

2121
/**
22-
* An expression modeling the remainder operation ({@code %}). Both operands'
23-
* types must be instances of {@link NumericType}. The type of this expression
24-
* is the common numerical type of its operands, according to the type
25-
* inference.
22+
* An expression modeling the remainder operation ({@code %}, returning the
23+
* remainder of the division between the two operands and taking the sign of the
24+
* dividend). Both operands' types must be instances of {@link NumericType}. The
25+
* type of this expression is the common numerical type of its operands,
26+
* according to the type inference.
2627
*
2728
* @author <a href="mailto:[email protected]">Luca Negrini</a>
2829
*/
2930
public class Remainder extends it.unive.lisa.program.cfg.statement.BinaryExpression {
3031

3132
/**
32-
* Builds the module.
33+
* Builds the remainder.
3334
*
3435
* @param cfg the {@link CFG} where this operation lies
3536
* @param location the location where this literal is defined
@@ -62,7 +63,7 @@ T extends TypeDomain<T>> AnalysisState<A, H, V, T> binarySemantics(
6263
getStaticType(),
6364
left,
6465
right,
65-
NumericNonOverflowingMod.INSTANCE,
66+
NumericNonOverflowingRem.INSTANCE,
6667
getLocation()),
6768
this);
6869
}

lisa/lisa-sdk/src/main/java/it/unive/lisa/symbolic/value/operator/ModuleOperator.java

Lines changed: 0 additions & 10 deletions
This file was deleted.
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
package it.unive.lisa.symbolic.value.operator;
2+
3+
/**
4+
* An operation that performs a modulo (the remainder of the division between
5+
* the two operands and taking the sign of the divisor) between its operands.
6+
*
7+
* @author <a href="mailto:[email protected]">Luca Negrini</a>
8+
*/
9+
public interface ModuloOperator extends ArithmeticOperator {
10+
11+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
package it.unive.lisa.symbolic.value.operator;
2+
3+
/**
4+
* An operation that performs a remainder (the remainder of the division between
5+
* the two operands and taking the sign of the dividend) between its operands.
6+
*
7+
* @author <a href="mailto:[email protected]">Luca Negrini</a>
8+
*/
9+
public interface RemainderOperator extends ArithmeticOperator {
10+
11+
}

lisa/lisa-sdk/src/main/java/it/unive/lisa/symbolic/value/operator/binary/BitwiseAnd.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ public class BitwiseAnd extends NumericOperation implements BitwiseOperator {
2424
public static final BitwiseAnd INSTANCE = new BitwiseAnd();
2525

2626
/**
27-
* Builds the type. This constructor is visible to allow subclassing:
27+
* Builds the operator. This constructor is visible to allow subclassing:
2828
* instances of this class should be unique, and the singleton can be
2929
* retrieved through field {@link #INSTANCE}.
3030
*/

0 commit comments

Comments
 (0)