@@ -2,14 +2,14 @@ private import cpp
22private import experimental.semmle.code.cpp.models.interfaces.SimpleRangeAnalysisExpr
33private import semmle.code.cpp.rangeanalysis.RangeAnalysisUtils
44
5- float evaluateConstantExpr ( Expr e ) {
6- result = e .getValue ( ) . toFloat ( )
5+ QlBuiltins :: BigInt evaluateConstantExpr ( Expr e ) {
6+ result = parseAsBigInt ( e .getValue ( ) )
77 or
88 // This handles when a constant value is put into a variable
99 // and the variable is used later
1010 exists ( SsaDefinition defn , StackVariable sv |
1111 defn .getAUse ( sv ) = e and
12- result = defn .getDefiningValue ( sv ) .getValue ( ) . toFloat ( )
12+ result = parseAsBigInt ( defn .getDefiningValue ( sv ) .getValue ( ) )
1313 )
1414}
1515
@@ -18,16 +18,18 @@ float evaluateConstantExpr(Expr e) {
1818// architecture where the shift value is masked with 0b00011111, but we can't
1919// assume the architecture).
2020bindingset [ val]
21- private predicate isValidShiftExprShift ( float val , Expr l ) {
22- val >= 0 and
21+ private predicate isValidShiftExprShift ( QlBuiltins :: BigInt val , Expr l ) {
22+ val >= 0 . toBigInt ( ) and
2323 // We use getFullyConverted because the spec says to use the *promoted* left operand
24- val < ( l .getFullyConverted ( ) .getUnderlyingType ( ) .getSize ( ) * 8 )
24+ val < ( l .getFullyConverted ( ) .getUnderlyingType ( ) .getSize ( ) * 8 ) . toBigInt ( )
2525}
2626
2727bindingset [ val, shift, max_val]
28- private predicate canLShiftOverflow ( int val , int shift , int max_val ) {
28+ private predicate canLShiftOverflow (
29+ QlBuiltins:: BigInt val , QlBuiltins:: BigInt shift , QlBuiltins:: BigInt max_val
30+ ) {
2931 // val << shift = val * 2^shift > max_val => val > max_val/2^shift = max_val >> b
30- val > max_val .bitShiftRight ( shift )
32+ val > max_val .bitShiftRightSigned ( shift . toInt ( ) )
3133}
3234
3335/**
@@ -65,7 +67,7 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
6567 exists ( evaluateConstantExpr ( l ) ) and not exists ( evaluateConstantExpr ( r ) )
6668 or
6769 // If the right operand is a constant, check if it is a valid shift expression
68- exists ( float constROp |
70+ exists ( QlBuiltins :: BigInt constROp |
6971 constROp = evaluateConstantExpr ( r ) and isValidShiftExprShift ( constROp , l )
7072 )
7173 )
@@ -82,8 +84,11 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
8284 result = this .( AssignRShiftExpr ) .getRValue ( )
8385 }
8486
85- override float getLowerBounds ( ) {
86- exists ( int lLower , int lUpper , int rLower , int rUpper |
87+ override QlBuiltins:: BigInt getLowerBounds ( ) {
88+ exists (
89+ QlBuiltins:: BigInt lLower , QlBuiltins:: BigInt lUpper , QlBuiltins:: BigInt rLower ,
90+ QlBuiltins:: BigInt rUpper
91+ |
8792 lLower = getFullyConvertedLowerBounds ( this .getLeftOperand ( ) ) and
8893 lUpper = getFullyConvertedUpperBounds ( this .getLeftOperand ( ) ) and
8994 rLower = getFullyConvertedLowerBounds ( this .getRightOperand ( ) ) and
@@ -92,7 +97,7 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
9297 rLower <= rUpper
9398 |
9499 if
95- lLower < 0
100+ lLower < 0 . toBigInt ( )
96101 or
97102 not (
98103 isValidShiftExprShift ( rLower , this .getLeftOperand ( ) ) and
@@ -105,12 +110,15 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
105110 result = exprMinVal ( this )
106111 else
107112 // We can get the smallest value by shifting the smallest bound by the largest bound
108- result = lLower .bitShiftRight ( rUpper )
113+ result = lLower .bitShiftRightSigned ( rUpper . toInt ( ) )
109114 )
110115 }
111116
112- override float getUpperBounds ( ) {
113- exists ( int lLower , int lUpper , int rLower , int rUpper |
117+ override QlBuiltins:: BigInt getUpperBounds ( ) {
118+ exists (
119+ QlBuiltins:: BigInt lLower , QlBuiltins:: BigInt lUpper , QlBuiltins:: BigInt rLower ,
120+ QlBuiltins:: BigInt rUpper
121+ |
114122 lLower = getFullyConvertedLowerBounds ( this .getLeftOperand ( ) ) and
115123 lUpper = getFullyConvertedUpperBounds ( this .getLeftOperand ( ) ) and
116124 rLower = getFullyConvertedLowerBounds ( this .getRightOperand ( ) ) and
@@ -119,7 +127,7 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
119127 rLower <= rUpper
120128 |
121129 if
122- lLower < 0
130+ lLower < 0 . toBigInt ( )
123131 or
124132 not (
125133 isValidShiftExprShift ( rLower , this .getLeftOperand ( ) ) and
@@ -132,7 +140,7 @@ class ConstantRShiftExprRange extends SimpleRangeAnalysisExpr {
132140 result = exprMaxVal ( this )
133141 else
134142 // We can get the largest value by shifting the largest bound by the smallest bound
135- result = lUpper .bitShiftRight ( rLower )
143+ result = lUpper .bitShiftRightSigned ( rLower . toInt ( ) )
136144 )
137145 }
138146
@@ -178,7 +186,7 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
178186 exists ( evaluateConstantExpr ( l ) ) and not exists ( evaluateConstantExpr ( r ) )
179187 or
180188 // If the right operand is a constant, check if it is a valid shift expression
181- exists ( float constROp |
189+ exists ( QlBuiltins :: BigInt constROp |
182190 constROp = evaluateConstantExpr ( r ) and isValidShiftExprShift ( constROp , l )
183191 )
184192 )
@@ -195,8 +203,11 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
195203 result = this .( AssignLShiftExpr ) .getRValue ( )
196204 }
197205
198- override float getLowerBounds ( ) {
199- exists ( int lLower , int lUpper , int rLower , int rUpper |
206+ override QlBuiltins:: BigInt getLowerBounds ( ) {
207+ exists (
208+ QlBuiltins:: BigInt lLower , QlBuiltins:: BigInt lUpper , QlBuiltins:: BigInt rLower ,
209+ QlBuiltins:: BigInt rUpper
210+ |
200211 lLower = getFullyConvertedLowerBounds ( this .getLeftOperand ( ) ) and
201212 lUpper = getFullyConvertedUpperBounds ( this .getLeftOperand ( ) ) and
202213 rLower = getFullyConvertedLowerBounds ( this .getRightOperand ( ) ) and
@@ -205,7 +216,7 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
205216 rLower <= rUpper
206217 |
207218 if
208- lLower < 0
219+ lLower < 0 . toBigInt ( )
209220 or
210221 not (
211222 isValidShiftExprShift ( rLower , this .getLeftOperand ( ) ) and
@@ -222,12 +233,15 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
222233 // If necessary, we may be able to improve this bound in the future
223234 if canLShiftOverflow ( lUpper , rUpper , exprMaxVal ( this ) )
224235 then result = exprMinVal ( this )
225- else result = lLower .bitShiftLeft ( rLower )
236+ else result = lLower .bitShiftLeft ( rLower . toInt ( ) )
226237 )
227238 }
228239
229- override float getUpperBounds ( ) {
230- exists ( int lLower , int lUpper , int rLower , int rUpper |
240+ override QlBuiltins:: BigInt getUpperBounds ( ) {
241+ exists (
242+ QlBuiltins:: BigInt lLower , QlBuiltins:: BigInt lUpper , QlBuiltins:: BigInt rLower ,
243+ QlBuiltins:: BigInt rUpper
244+ |
231245 lLower = getFullyConvertedLowerBounds ( this .getLeftOperand ( ) ) and
232246 lUpper = getFullyConvertedUpperBounds ( this .getLeftOperand ( ) ) and
233247 rLower = getFullyConvertedLowerBounds ( this .getRightOperand ( ) ) and
@@ -236,7 +250,7 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
236250 rLower <= rUpper
237251 |
238252 if
239- lLower < 0
253+ lLower < 0 . toBigInt ( )
240254 or
241255 not (
242256 isValidShiftExprShift ( rLower , this .getLeftOperand ( ) ) and
@@ -253,7 +267,7 @@ class ConstantLShiftExprRange extends SimpleRangeAnalysisExpr {
253267 // If necessary, we may be able to improve this bound in the future
254268 if canLShiftOverflow ( lUpper , rUpper , exprMaxVal ( this ) )
255269 then result = exprMaxVal ( this )
256- else result = lUpper .bitShiftLeft ( rUpper )
270+ else result = lUpper .bitShiftLeft ( rUpper . toInt ( ) )
257271 )
258272 }
259273
0 commit comments