Skip to content

Commit bdab785

Browse files
authored
Add files via upload
1 parent 87ee784 commit bdab785

File tree

3 files changed

+195
-0
lines changed

3 files changed

+195
-0
lines changed
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
...
2+
int i1;
3+
char c1;
4+
...
5+
if((c1<50)&&(c>10))
6+
switch(c1){
7+
case 300: // BAD: the code will not be executed
8+
...
9+
if((i1<5)&&(i1>0))
10+
switch(i1){ // BAD
11+
case 21: // BAD: the code will not be executed
12+
...
13+
switch(c1){
14+
...
15+
dafault: // BAD: maybe it will be right `default`
16+
...
17+
}
18+
19+
...
20+
switch(c1){
21+
i1=c1*2; // BAD: the code will not be executed
22+
case 12:
23+
...
24+
switch(c1){ // GOOD
25+
case 12:
26+
break;
27+
case 10:
28+
break;
29+
case 9:
30+
break;
31+
default:
32+
break;
33+
}
34+
...
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
<!DOCTYPE qhelp PUBLIC
2+
"-//Semmle//qhelp//EN"
3+
"qhelp.dtd">
4+
<qhelp>
5+
<overview>
6+
<p>Finding places the dangerous use of a switch.</p>
7+
8+
9+
</overview>
10+
11+
<example>
12+
<p>The following example demonstrates fallacious and fixed methods of using switch.</p>
13+
<sample src="FindIncorrectlyUsedSwitch.c" />
14+
15+
</example>
16+
<references>
17+
18+
<li>
19+
CERT C Coding Standard:
20+
<a href="https://wiki.sei.cmu.edu/confluence/display/c/MSC12-C.+Detect+and+remove+code+that+has+no+effect+or+is+never+executed">MSC12-C. Detect and remove code that has no effect or is never executed</a>.
21+
</li>
22+
23+
</references>
24+
</qhelp>
Lines changed: 137 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,137 @@
1+
/**
2+
* @name Operator Find Incorrectly Used Switch
3+
* @description --Finding places the dangerous use of a switch.
4+
* --For example, when the range of values for a condition does not cover all of the selection values..
5+
* @kind problem
6+
* @id cpp/operator-find-incorrectly-used-switch
7+
* @problem.severity warning
8+
* @precision medium
9+
* @tags correctness
10+
* security
11+
* external/cwe/cwe-561
12+
* external/cwe/cwe-691
13+
* external/cwe/cwe-478
14+
*/
15+
16+
import cpp
17+
import semmle.code.cpp.rangeanalysis.SimpleRangeAnalysis
18+
import semmle.code.cpp.commons.Exclusions
19+
20+
/** Holds if the range contains no boundary values. */
21+
predicate isRealRange(Expr exp) {
22+
upperBound(exp).toString() != "18446744073709551616" and
23+
upperBound(exp).toString() != "9223372036854775807" and
24+
upperBound(exp).toString() != "4294967295" and
25+
upperBound(exp).toString() != "Infinity" and
26+
upperBound(exp).toString() != "NaN" and
27+
lowerBound(exp).toString() != "-9223372036854775808" and
28+
lowerBound(exp).toString() != "-4294967296" and
29+
lowerBound(exp).toString() != "-Infinity" and
30+
lowerBound(exp).toString() != "NaN" and
31+
upperBound(exp) != 2147483647 and
32+
upperBound(exp) != 268435455 and
33+
upperBound(exp) != 33554431 and
34+
upperBound(exp) != 8388607 and
35+
upperBound(exp) != 65535 and
36+
upperBound(exp) != 32767 and
37+
upperBound(exp) != 255 and
38+
upperBound(exp) != 127 and
39+
lowerBound(exp) != -2147483648 and
40+
lowerBound(exp) != -268435456 and
41+
lowerBound(exp) != -33554432 and
42+
lowerBound(exp) != -8388608 and
43+
lowerBound(exp) != -65536 and
44+
lowerBound(exp) != -32768 and
45+
lowerBound(exp) != -128
46+
or
47+
lowerBound(exp) = 0 and
48+
upperBound(exp) = 1
49+
}
50+
51+
/** Holds if the range of values for the condition is less than the choices. */
52+
predicate isNotAllSelected(SwitchStmt swtmp) {
53+
not swtmp.getExpr().isConstant() and
54+
exists(int i |
55+
i != 0 and
56+
(
57+
i = lowerBound(swtmp.getASwitchCase().getExpr()) and
58+
upperBound(swtmp.getExpr()) < i
59+
or
60+
(
61+
i = upperBound(swtmp.getASwitchCase().getExpr()) or
62+
i = upperBound(swtmp.getASwitchCase().getEndExpr())
63+
) and
64+
lowerBound(swtmp.getExpr()) > i
65+
)
66+
)
67+
}
68+
69+
/** Holds if the range of values for the condition is greater than the selection. */
70+
predicate isConditionBig(SwitchStmt swtmp) {
71+
not swtmp.hasDefaultCase() and
72+
not exists(int iu, int il |
73+
(
74+
iu = upperBound(swtmp.getASwitchCase().getExpr()) or
75+
iu = upperBound(swtmp.getASwitchCase().getEndExpr())
76+
) and
77+
upperBound(swtmp.getExpr()) = iu and
78+
(
79+
il = lowerBound(swtmp.getASwitchCase().getExpr()) or
80+
il = lowerBound(swtmp.getASwitchCase().getEndExpr())
81+
) and
82+
lowerBound(swtmp.getExpr()) = il
83+
)
84+
}
85+
86+
/** Holds if there are labels inside the block with names similar to `default` or `case`. */
87+
predicate isWrongLableName(SwitchStmt swtmp) {
88+
not swtmp.hasDefaultCase() and
89+
exists(LabelStmt lb |
90+
(
91+
(
92+
lb.getName().charAt(0) = "d" or
93+
lb.getName().charAt(0) = "c"
94+
) and
95+
(
96+
lb.getName().charAt(1) = "e" or
97+
lb.getName().charAt(1) = "a"
98+
) and
99+
(
100+
lb.getName().charAt(2) = "f" or
101+
lb.getName().charAt(2) = "s"
102+
)
103+
) and
104+
lb.getEnclosingStmt().getParentStmt*() = swtmp.getStmt() and
105+
not exists(GotoStmt gs | gs.getName() = lb.getName())
106+
)
107+
}
108+
109+
/** Holds if the block contains code before the first `case`. */
110+
predicate isCodeBeforeCase(SwitchStmt swtmp) {
111+
exists(Expr exp |
112+
exp.getEnclosingStmt().getParentStmt*() = swtmp.getStmt() and
113+
not exists(Stmt sttmp, SwitchCase sctmp |
114+
sttmp = swtmp.getASwitchCase().getAStmt() and
115+
sctmp = swtmp.getASwitchCase() and
116+
(
117+
exp.getEnclosingStmt().getParentStmt*() = sttmp or
118+
exp.getEnclosingStmt() = sctmp
119+
)
120+
)
121+
)
122+
}
123+
124+
from SwitchStmt sw, string msg
125+
where
126+
isRealRange(sw.getExpr()) and
127+
isRealRange(sw.getExpr().getAChild*()) and
128+
(
129+
isNotAllSelected(sw) and msg = "The range of condition values is less than the selection."
130+
or
131+
isConditionBig(sw) and msg = "The range of condition values is wider than the choices."
132+
)
133+
or
134+
isWrongLableName(sw) and msg = "Possibly erroneous label name."
135+
or
136+
isCodeBeforeCase(sw) and msg = "Code before case will not be executed."
137+
select sw, msg

0 commit comments

Comments
 (0)