Skip to content

Commit 7fa6894

Browse files
committed
C++: Ensure that product dataflow library enters/leaves through the same call.
1 parent 2e5a048 commit 7fa6894

File tree

2 files changed

+40
-8
lines changed

2 files changed

+40
-8
lines changed

cpp/ql/lib/experimental/semmle/code/cpp/dataflow/ProductFlow.qll

Lines changed: 40 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
import semmle.code.cpp.ir.dataflow.DataFlow
2+
private import semmle.code.cpp.ir.dataflow.internal.DataFlowPrivate
3+
private import semmle.code.cpp.ir.dataflow.internal.DataFlowUtil
24
private import codeql.util.Unit
35

46
module ProductFlow {
@@ -352,32 +354,63 @@ module ProductFlow {
352354
pragma[only_bind_out](succ.getNode().getEnclosingCallable())
353355
}
354356

357+
newtype TKind =
358+
TInto(DataFlowCall call) {
359+
[any(Flow1::PathNode n).getNode(), any(Flow2::PathNode n).getNode()]
360+
.(ArgumentNode)
361+
.getCall() = call
362+
} or
363+
TOutOf(DataFlowCall call) {
364+
[any(Flow1::PathNode n).getNode(), any(Flow2::PathNode n).getNode()].(OutNode).getCall() =
365+
call
366+
}
367+
355368
pragma[nomagic]
356369
private predicate interprocEdge1(
357-
Declaration predDecl, Declaration succDecl, Flow1::PathNode pred1, Flow1::PathNode succ1
370+
Declaration predDecl, Declaration succDecl, Flow1::PathNode pred1, Flow1::PathNode succ1,
371+
TKind kind
358372
) {
359373
Flow1::PathGraph::edges(pred1, succ1) and
360374
predDecl != succDecl and
361375
pred1.getNode().getEnclosingCallable() = predDecl and
362-
succ1.getNode().getEnclosingCallable() = succDecl
376+
succ1.getNode().getEnclosingCallable() = succDecl and
377+
exists(DataFlowCall call |
378+
kind = TInto(call) and
379+
pred1.getNode().(ArgumentNode).getCall() = call and
380+
succ1.getNode() instanceof ParameterNode
381+
or
382+
kind = TOutOf(call) and
383+
succ1.getNode().(OutNode).getCall() = call and
384+
pred1.getNode() instanceof ReturnNode
385+
)
363386
}
364387

365388
pragma[nomagic]
366389
private predicate interprocEdge2(
367-
Declaration predDecl, Declaration succDecl, Flow2::PathNode pred2, Flow2::PathNode succ2
390+
Declaration predDecl, Declaration succDecl, Flow2::PathNode pred2, Flow2::PathNode succ2,
391+
TKind kind
368392
) {
369393
Flow2::PathGraph::edges(pred2, succ2) and
370394
predDecl != succDecl and
371395
pred2.getNode().getEnclosingCallable() = predDecl and
372-
succ2.getNode().getEnclosingCallable() = succDecl
396+
succ2.getNode().getEnclosingCallable() = succDecl and
397+
exists(DataFlowCall call |
398+
kind = TInto(call) and
399+
pred2.getNode().(ArgumentNode).getCall() = call and
400+
succ2.getNode() instanceof ParameterNode
401+
or
402+
kind = TOutOf(call) and
403+
succ2.getNode().(OutNode).getCall() = call and
404+
pred2.getNode() instanceof ReturnNode
405+
)
373406
}
374407

375408
private predicate interprocEdgePair(
376409
Flow1::PathNode pred1, Flow2::PathNode pred2, Flow1::PathNode succ1, Flow2::PathNode succ2
377410
) {
378-
exists(Declaration predDecl, Declaration succDecl |
379-
interprocEdge1(predDecl, succDecl, pred1, succ1) and
380-
interprocEdge2(predDecl, succDecl, pred2, succ2)
411+
exists(Declaration predDecl, Declaration succDecl, TKind kind |
412+
interprocEdge1(predDecl, succDecl, pred1, succ1, kind) and
413+
interprocEdge2(predDecl, succDecl, pred2, succ2, kind)
381414
)
382415
}
383416

cpp/ql/test/experimental/query-tests/Security/CWE/CWE-119/OverrunWriteProductFlow.expected

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -398,4 +398,3 @@ subpaths
398398
| test.cpp:199:9:199:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:199:22:199:27 | string | This write may overflow $@ by 2 elements. | test.cpp:199:22:199:27 | string | string |
399399
| test.cpp:203:9:203:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:203:22:203:27 | string | This write may overflow $@ by 2 elements. | test.cpp:203:22:203:27 | string | string |
400400
| test.cpp:207:9:207:15 | call to strncpy | test.cpp:147:19:147:24 | call to malloc | test.cpp:207:22:207:27 | string | This write may overflow $@ by 3 elements. | test.cpp:207:22:207:27 | string | string |
401-
| test.cpp:216:3:216:8 | call to memset | test.cpp:220:43:220:48 | call to malloc | test.cpp:216:10:216:10 | p | This write may overflow $@ by 5 elements. | test.cpp:216:10:216:10 | p | p |

0 commit comments

Comments
 (0)