Skip to content

Commit 6cc1c23

Browse files
committed
C++: Add some SideEffect models.
1 parent 935b8d9 commit 6cc1c23

File tree

3 files changed

+43
-12
lines changed

3 files changed

+43
-12
lines changed

cpp/ql/src/semmle/code/cpp/models/implementations/Strcat.qll

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import semmle.code.cpp.models.interfaces.ArrayFunction
22
import semmle.code.cpp.models.interfaces.DataFlow
33
import semmle.code.cpp.models.interfaces.Taint
4+
import semmle.code.cpp.models.interfaces.SideEffect
45

56
/**
67
* The standard function `strcat` and its wide, sized, and Microsoft variants.
78
*/
8-
class StrcatFunction extends TaintFunction, DataFlowFunction, ArrayFunction {
9+
class StrcatFunction extends TaintFunction, DataFlowFunction, ArrayFunction, SideEffectFunction {
910
StrcatFunction() {
1011
exists(string name | name = getName() |
1112
name = "strcat" or // strcat(dst, src)
@@ -56,4 +57,19 @@ class StrcatFunction extends TaintFunction, DataFlowFunction, ArrayFunction {
5657
override predicate hasArrayWithNullTerminator(int param) { param = 1 }
5758

5859
override predicate hasArrayWithUnknownSize(int param) { param = 0 }
60+
61+
override predicate hasOnlySpecificReadSideEffects() { any() }
62+
63+
override predicate hasOnlySpecificWriteSideEffects() { any() }
64+
65+
predicate hasSpecificWriteSideEffect(ParameterIndex i, boolean buffer, boolean mustWrite) {
66+
i = 0 and
67+
buffer = true and
68+
mustWrite = false
69+
}
70+
71+
predicate hasSpecificReadSideEffect(ParameterIndex i, boolean buffer) {
72+
(i = 0 or i = 1) and
73+
buffer = true
74+
}
5975
}

cpp/ql/src/semmle/code/cpp/models/implementations/Strcpy.qll

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
11
import semmle.code.cpp.models.interfaces.ArrayFunction
22
import semmle.code.cpp.models.interfaces.DataFlow
33
import semmle.code.cpp.models.interfaces.Taint
4+
import semmle.code.cpp.models.interfaces.SideEffect
45

56
/**
67
* The standard function `strcpy` and its wide, sized, and Microsoft variants.
78
*/
8-
class StrcpyFunction extends ArrayFunction, DataFlowFunction, TaintFunction {
9+
class StrcpyFunction extends ArrayFunction, DataFlowFunction, TaintFunction, SideEffectFunction {
910
StrcpyFunction() {
1011
this.hasName("strcpy") or
1112
this.hasName("_mbscpy") or
@@ -74,4 +75,23 @@ class StrcpyFunction extends ArrayFunction, DataFlowFunction, TaintFunction {
7475
output.isReturnValueDeref()
7576
)
7677
}
78+
79+
override predicate hasOnlySpecificReadSideEffects() { any() }
80+
81+
override predicate hasOnlySpecificWriteSideEffects() { any() }
82+
83+
predicate hasSpecificWriteSideEffect(ParameterIndex i, boolean buffer, boolean mustWrite) {
84+
i = 0 and
85+
buffer = true and
86+
mustWrite = true
87+
}
88+
89+
predicate hasSpecificReadSideEffect(ParameterIndex i, boolean buffer) {
90+
i = 1 and
91+
buffer = true
92+
}
93+
94+
ParameterIndex getParameterSizeIndex(ParameterIndex i) {
95+
hasArrayWithVariableSize(i, result)
96+
}
7797
}

cpp/ql/test/library-tests/ir/ir/raw_ir.expected

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6259,23 +6259,18 @@ ir.cpp:
62596259
# 1230| r1230_5(char *) = Load : &:r1230_4, ~mu1227_4
62606260
# 1230| r1230_6(char *) = Convert : r1230_5
62616261
# 1230| r1230_7(char *) = Call : func:r1230_1, 0:r1230_3, 1:r1230_6
6262-
# 1230| mu1230_8(unknown) = ^CallSideEffect : ~mu1227_4
6263-
# 1230| v1230_9(void) = ^BufferReadSideEffect[0] : &:r1230_3, ~mu1227_4
6264-
# 1230| v1230_10(void) = ^BufferReadSideEffect[1] : &:r1230_6, ~mu1227_4
6265-
# 1230| mu1230_11(unknown) = ^BufferMayWriteSideEffect[0] : &:r1230_3
6266-
# 1230| mu1230_12(unknown) = ^BufferMayWriteSideEffect[1] : &:r1230_6
6262+
# 1230| v1230_8(void) = ^BufferReadSideEffect[1] : &:r1230_6, ~mu1227_4
6263+
# 1230| mu1230_9(unknown) = ^BufferMustWriteSideEffect[0] : &:r1230_3
62676264
# 1231| r1231_1(glval<unknown>) = FunctionAddress[strcat] :
62686265
# 1231| r1231_2(glval<char[1024]>) = VariableAddress[buffer] :
62696266
# 1231| r1231_3(char *) = Convert : r1231_2
62706267
# 1231| r1231_4(glval<char *>) = VariableAddress[s2] :
62716268
# 1231| r1231_5(char *) = Load : &:r1231_4, ~mu1227_4
62726269
# 1231| r1231_6(char *) = Convert : r1231_5
62736270
# 1231| r1231_7(char *) = Call : func:r1231_1, 0:r1231_3, 1:r1231_6
6274-
# 1231| mu1231_8(unknown) = ^CallSideEffect : ~mu1227_4
6275-
# 1231| v1231_9(void) = ^BufferReadSideEffect[0] : &:r1231_3, ~mu1227_4
6276-
# 1231| v1231_10(void) = ^BufferReadSideEffect[1] : &:r1231_6, ~mu1227_4
6277-
# 1231| mu1231_11(unknown) = ^BufferMayWriteSideEffect[0] : &:r1231_3
6278-
# 1231| mu1231_12(unknown) = ^BufferMayWriteSideEffect[1] : &:r1231_6
6271+
# 1231| v1231_8(void) = ^BufferReadSideEffect[0] : &:r1231_3, ~mu1227_4
6272+
# 1231| v1231_9(void) = ^BufferReadSideEffect[1] : &:r1231_6, ~mu1227_4
6273+
# 1231| mu1231_10(unknown) = ^BufferMayWriteSideEffect[0] : &:r1231_3
62796274
# 1232| v1232_1(void) = NoOp :
62806275
# 1227| v1227_13(void) = ReturnIndirection : &:r1227_7, ~mu1227_4
62816276
# 1227| v1227_14(void) = ReturnIndirection : &:r1227_11, ~mu1227_4

0 commit comments

Comments
 (0)