|
18 | 18 |
|
19 | 19 | import cpp
|
20 | 20 | import semmle.code.cpp.ir.dataflow.DataFlow
|
21 |
| -import DataFlow::PathGraph |
| 21 | +import CastToPointerArithFlow::PathGraph |
22 | 22 |
|
23 | 23 | Type getFullyConvertedType(DataFlow::Node node) {
|
24 | 24 | result = node.asExpr().getFullyConverted().getUnspecifiedType()
|
25 | 25 | }
|
26 | 26 |
|
27 |
| -class CastToPointerArithFlow extends DataFlow::Configuration { |
28 |
| - CastToPointerArithFlow() { this = "CastToPointerArithFlow" } |
| 27 | +module CastToPointerArithFlowConfig implements DataFlow::StateConfigSig { |
| 28 | + class FlowState = Type; |
29 | 29 |
|
30 |
| - override predicate isSource(DataFlow::Node node, DataFlow::FlowState state) { |
| 30 | + predicate isSource(DataFlow::Node node, FlowState state) { |
31 | 31 | not node.asExpr() instanceof Conversion and
|
32 | 32 | exists(Type baseType1, Type baseType2 |
|
33 | 33 | hasBaseType(node.asExpr(), baseType1) and
|
34 | 34 | hasBaseType(node.asExpr().getConversion*(), baseType2) and
|
35 | 35 | introducesNewField(baseType1, baseType2)
|
36 | 36 | ) and
|
37 |
| - getFullyConvertedType(node).getName() = state |
| 37 | + getFullyConvertedType(node) = state |
38 | 38 | }
|
39 | 39 |
|
40 |
| - override predicate isSink(DataFlow::Node node, DataFlow::FlowState state) { |
| 40 | + predicate isSink(DataFlow::Node node, FlowState state) { |
41 | 41 | (
|
42 | 42 | exists(PointerAddExpr pae | pae.getAnOperand() = node.asExpr()) or
|
43 | 43 | exists(ArrayExpr ae | ae.getArrayBase() = node.asExpr())
|
44 | 44 | ) and
|
45 |
| - getFullyConvertedType(node).getName() = state |
| 45 | + getFullyConvertedType(node) = state |
| 46 | + } |
| 47 | + |
| 48 | + predicate isBarrier(DataFlow::Node node, FlowState state) { none() } |
| 49 | + |
| 50 | + predicate isAdditionalFlowStep( |
| 51 | + DataFlow::Node node1, FlowState state1, DataFlow::Node node2, FlowState state2 |
| 52 | + ) { |
| 53 | + none() |
46 | 54 | }
|
47 | 55 | }
|
48 | 56 |
|
@@ -72,15 +80,9 @@ predicate introducesNewField(Class derived, Class base) {
|
72 | 80 | )
|
73 | 81 | }
|
74 | 82 |
|
75 |
| -pragma[nomagic] |
76 |
| -predicate hasFullyConvertedType(DataFlow::PathNode node, Type t) { |
77 |
| - getFullyConvertedType(node.getNode()) = t |
78 |
| -} |
| 83 | +module CastToPointerArithFlow = DataFlow::MakeWithState<CastToPointerArithFlowConfig>; |
79 | 84 |
|
80 |
| -from DataFlow::PathNode source, DataFlow::PathNode sink, CastToPointerArithFlow cfg, Type t |
81 |
| -where |
82 |
| - cfg.hasFlowPath(pragma[only_bind_into](source), pragma[only_bind_into](sink)) and |
83 |
| - hasFullyConvertedType(source, t) and |
84 |
| - hasFullyConvertedType(sink, t) |
| 85 | +from CastToPointerArithFlow::PathNode source, CastToPointerArithFlow::PathNode sink |
| 86 | +where CastToPointerArithFlow::hasFlowPath(source, sink) |
85 | 87 | select sink, source, sink, "This pointer arithmetic may be done with the wrong type because of $@.",
|
86 | 88 | source, "this cast"
|
0 commit comments