codeql-development-mcp-server 2.24.3 → 2.25.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. package/dist/codeql-development-mcp-server.js +48111 -49526
  2. package/dist/codeql-development-mcp-server.js.map +4 -4
  3. package/package.json +9 -9
  4. package/ql/actions/tools/src/PrintCFG/PrintCFG.ql +1 -3
  5. package/ql/actions/tools/src/codeql-pack.lock.yml +14 -14
  6. package/ql/actions/tools/src/codeql-pack.yml +2 -2
  7. package/ql/cpp/tools/src/CallGraphFrom/CallGraphFrom.ql +6 -20
  8. package/ql/cpp/tools/src/CallGraphFromTo/CallGraphFromTo.md +47 -0
  9. package/ql/cpp/tools/src/CallGraphFromTo/CallGraphFromTo.ql +77 -0
  10. package/ql/cpp/tools/src/CallGraphTo/CallGraphTo.ql +6 -20
  11. package/ql/cpp/tools/src/ExternalPredicates.qll +14 -0
  12. package/ql/cpp/tools/src/PrintAST/PrintAST.ql +9 -20
  13. package/ql/cpp/tools/src/PrintCFG/PrintCFG.ql +1 -3
  14. package/ql/cpp/tools/src/codeql-pack.lock.yml +12 -12
  15. package/ql/cpp/tools/src/codeql-pack.yml +2 -2
  16. package/ql/csharp/tools/src/CallGraphFrom/CallGraphFrom.ql +4 -19
  17. package/ql/csharp/tools/src/CallGraphFromTo/CallGraphFromTo.md +49 -0
  18. package/ql/csharp/tools/src/CallGraphFromTo/CallGraphFromTo.ql +64 -0
  19. package/ql/csharp/tools/src/CallGraphTo/CallGraphTo.ql +4 -19
  20. package/ql/csharp/tools/src/ExternalPredicates.qll +14 -0
  21. package/ql/csharp/tools/src/PrintAST/PrintAST.ql +9 -17
  22. package/ql/csharp/tools/src/codeql-pack.lock.yml +10 -10
  23. package/ql/csharp/tools/src/codeql-pack.yml +2 -2
  24. package/ql/go/tools/src/CallGraphFrom/CallGraphFrom.ql +4 -19
  25. package/ql/go/tools/src/CallGraphFromTo/CallGraphFromTo.md +47 -0
  26. package/ql/go/tools/src/CallGraphFromTo/CallGraphFromTo.ql +53 -0
  27. package/ql/go/tools/src/CallGraphTo/CallGraphTo.ql +4 -20
  28. package/ql/go/tools/src/ExternalPredicates.qll +14 -0
  29. package/ql/go/tools/src/PrintAST/PrintAST.ql +132 -22
  30. package/ql/go/tools/src/codeql-pack.lock.yml +10 -10
  31. package/ql/go/tools/src/codeql-pack.yml +2 -2
  32. package/ql/java/tools/src/CallGraphFrom/CallGraphFrom.ql +4 -19
  33. package/ql/java/tools/src/CallGraphFromTo/CallGraphFromTo.md +49 -0
  34. package/ql/java/tools/src/CallGraphFromTo/CallGraphFromTo.ql +64 -0
  35. package/ql/java/tools/src/CallGraphTo/CallGraphTo.ql +4 -19
  36. package/ql/java/tools/src/ExternalPredicates.qll +14 -0
  37. package/ql/java/tools/src/PrintAST/PrintAST.ql +9 -17
  38. package/ql/java/tools/src/PrintCFG/PrintCFG.ql +11 -10
  39. package/ql/java/tools/src/codeql-pack.lock.yml +14 -14
  40. package/ql/java/tools/src/codeql-pack.yml +2 -2
  41. package/ql/javascript/tools/src/CallGraphFrom/CallGraphFrom.ql +4 -19
  42. package/ql/javascript/tools/src/CallGraphFromTo/CallGraphFromTo.md +47 -0
  43. package/ql/javascript/tools/src/CallGraphFromTo/CallGraphFromTo.ql +69 -0
  44. package/ql/javascript/tools/src/CallGraphTo/CallGraphTo.ql +4 -20
  45. package/ql/javascript/tools/src/ExternalPredicates.qll +14 -0
  46. package/ql/javascript/tools/src/PrintAST/PrintAST.ql +9 -20
  47. package/ql/javascript/tools/src/PrintCFG/PrintCFG.ql +1 -3
  48. package/ql/javascript/tools/src/codeql-pack.lock.yml +13 -13
  49. package/ql/javascript/tools/src/codeql-pack.yml +2 -2
  50. package/ql/python/tools/src/CallGraphFrom/CallGraphFrom.ql +3 -17
  51. package/ql/python/tools/src/CallGraphFromTo/CallGraphFromTo.md +46 -0
  52. package/ql/python/tools/src/CallGraphFromTo/CallGraphFromTo.ql +71 -0
  53. package/ql/python/tools/src/CallGraphTo/CallGraphTo.ql +6 -22
  54. package/ql/python/tools/src/ExternalPredicates.qll +14 -0
  55. package/ql/python/tools/src/PrintAST/PrintAST.ql +9 -20
  56. package/ql/python/tools/src/PrintCFG/PrintCFG.ql +1 -3
  57. package/ql/python/tools/src/codeql-pack.lock.yml +13 -13
  58. package/ql/python/tools/src/codeql-pack.yml +2 -2
  59. package/ql/ruby/tools/src/CallGraphFrom/CallGraphFrom.ql +4 -19
  60. package/ql/ruby/tools/src/CallGraphFromTo/CallGraphFromTo.md +48 -0
  61. package/ql/ruby/tools/src/CallGraphFromTo/CallGraphFromTo.ql +50 -0
  62. package/ql/ruby/tools/src/CallGraphTo/CallGraphTo.ql +4 -20
  63. package/ql/ruby/tools/src/ExternalPredicates.qll +14 -0
  64. package/ql/ruby/tools/src/PrintAST/PrintAST.ql +9 -17
  65. package/ql/ruby/tools/src/PrintCFG/PrintCFG.ql +1 -3
  66. package/ql/ruby/tools/src/codeql-pack.lock.yml +10 -10
  67. package/ql/ruby/tools/src/codeql-pack.yml +2 -2
  68. package/ql/swift/tools/src/CallGraphFrom/CallGraphFrom.ql +7 -16
  69. package/ql/swift/tools/src/CallGraphFromTo/CallGraphFromTo.md +47 -0
  70. package/ql/swift/tools/src/CallGraphFromTo/CallGraphFromTo.ql +80 -0
  71. package/ql/swift/tools/src/CallGraphTo/CallGraphTo.ql +8 -14
  72. package/ql/swift/tools/src/ExternalPredicates.qll +14 -0
  73. package/ql/swift/tools/src/PrintAST/PrintAST.ql +5 -15
  74. package/ql/swift/tools/src/PrintCFG/PrintCFG.ql +5 -15
  75. package/ql/swift/tools/src/codeql-pack.lock.yml +10 -10
  76. package/ql/swift/tools/src/codeql-pack.yml +2 -2
@@ -8,18 +8,13 @@
8
8
 
9
9
  import csharp
10
10
  import semmle.code.csharp.PrintAst
11
-
12
- /**
13
- * Gets the source files to generate AST from.
14
- * Can be a single file path or comma-separated list of file paths.
15
- */
16
- external string selectedSourceFiles();
11
+ import ExternalPredicates
17
12
 
18
13
  /**
19
14
  * Gets a single source file from the comma-separated list.
20
15
  */
21
16
  string getSelectedSourceFile() {
22
- result = selectedSourceFiles().splitAt(",").trim()
17
+ exists(string s | selectedSourceFiles(s) | result = s.splitAt(",").trim())
23
18
  }
24
19
 
25
20
  /**
@@ -30,11 +25,14 @@ File getSelectedFile() {
30
25
  selectedFile = getSelectedSourceFile() and
31
26
  (
32
27
  // Match by exact relative path from source root
33
- result.getRelativePath() = selectedFile or
28
+ result.getRelativePath() = selectedFile
29
+ or
34
30
  // Match by file name if no path separators
35
- (not selectedFile.matches("%/%") and result.getBaseName() = selectedFile) or
31
+ not selectedFile.matches("%/%") and result.getBaseName() = selectedFile
32
+ or
36
33
  // Match by ending path component
37
- result.getAbsolutePath().suffix(result.getAbsolutePath().length() - selectedFile.length()) = selectedFile
34
+ result.getAbsolutePath().suffix(result.getAbsolutePath().length() - selectedFile.length()) =
35
+ selectedFile
38
36
  )
39
37
  )
40
38
  }
@@ -46,12 +44,6 @@ File getSelectedFile() {
46
44
  class Cfg extends PrintAstConfiguration {
47
45
  override predicate shouldPrint(Element e, Location l) {
48
46
  super.shouldPrint(e, l) and
49
- (
50
- // Use external predicate if available
51
- l.getFile() = getSelectedFile()
52
- or
53
- // Fallback for unit tests: include all files
54
- not exists(getSelectedFile())
55
- )
47
+ l.getFile() = getSelectedFile()
56
48
  }
57
49
  }
@@ -2,23 +2,23 @@
2
2
  lockVersion: 1.0.0
3
3
  dependencies:
4
4
  codeql/controlflow:
5
- version: 2.0.25
5
+ version: 2.0.28
6
6
  codeql/csharp-all:
7
- version: 5.4.6
7
+ version: 5.4.9
8
8
  codeql/dataflow:
9
- version: 2.0.25
9
+ version: 2.1.0
10
10
  codeql/mad:
11
- version: 1.0.41
11
+ version: 1.0.44
12
12
  codeql/ssa:
13
- version: 2.0.17
13
+ version: 2.0.20
14
14
  codeql/threat-models:
15
- version: 1.0.41
15
+ version: 1.0.44
16
16
  codeql/tutorial:
17
- version: 1.0.41
17
+ version: 1.0.44
18
18
  codeql/typetracking:
19
- version: 2.0.25
20
- codeql/util:
21
19
  version: 2.0.28
20
+ codeql/util:
21
+ version: 2.0.31
22
22
  codeql/xml:
23
- version: 1.0.41
23
+ version: 1.0.44
24
24
  compiled: false
@@ -1,6 +1,6 @@
1
1
  name: advanced-security/ql-mcp-csharp-tools-src
2
- version: 2.24.3
2
+ version: 2.25.0
3
3
  description: 'Queries for codeql-development-mcp-server tools for csharp language'
4
4
  library: false
5
5
  dependencies:
6
- codeql/csharp-all: 5.4.6
6
+ codeql/csharp-all: 5.4.9
@@ -8,32 +8,17 @@
8
8
  */
9
9
 
10
10
  import go
11
-
12
- /**
13
- * Gets the source function name for which to generate the call graph.
14
- * Can be a single function name or comma-separated list of function names.
15
- */
16
- external string sourceFunction();
11
+ import ExternalPredicates
17
12
 
18
13
  /**
19
14
  * Gets a single source function name from the comma-separated list.
20
15
  */
21
16
  string getSourceFunctionName() {
22
- result = sourceFunction().splitAt(",").trim()
17
+ exists(string s | sourceFunction(s) | result = s.splitAt(",").trim())
23
18
  }
24
19
 
25
20
  from CallExpr call, FuncDecl source
26
21
  where
27
22
  call.getEnclosingFunction() = source and
28
- (
29
- // Use external predicate if available
30
- source.getName() = getSourceFunctionName()
31
- or
32
- // Fallback for unit tests: include test files
33
- (
34
- not exists(getSourceFunctionName()) and
35
- source.getFile().getParentContainer().getParentContainer().getBaseName() = "test"
36
- )
37
- )
38
- select call,
39
- "Call from `" + source.getName() + "` to `" + call.getTarget().getName() + "`"
23
+ source.getName() = getSourceFunctionName()
24
+ select call, "Call from `" + source.getName() + "` to `" + call.getTarget().getName() + "`"
@@ -0,0 +1,47 @@
1
+ # CallGraphFromTo for Go
2
+
3
+ Displays calls on reachable paths from a source function to a target function, showing transitive call graph connectivity.
4
+
5
+ ## Overview
6
+
7
+ This query identifies all function calls that lie on any transitive call path from a specified source function to a specified target function. Given both a source and target function name, it reports each call site along the connecting paths, which is useful for understanding indirect call chains, security-relevant data flow paths, and function reachability.
8
+
9
+ The query uses transitive closure (`calls*`) to determine reachability, then reports only the direct call sites that contribute to paths between the source and target. It accepts function names via extensible predicates (`sourceFunction` and `targetFunction`) populated via CodeQL data extensions / model packs (see `ExternalPredicates.qll`).
10
+
11
+ ## Use Cases
12
+
13
+ This query is primarily used for:
14
+
15
+ - Determining if a call path exists between two functions
16
+ - Mapping indirect call chains from a source to a target function
17
+ - Analyzing security-relevant paths (e.g., from user input handlers to sensitive operations)
18
+ - Understanding transitive dependencies between functions
19
+
20
+ ## Example
21
+
22
+ The following Go code demonstrates a transitive call chain from `source` through `intermediate` to `target`:
23
+
24
+ ```go
25
+ func target() {}
26
+
27
+ func intermediate() {
28
+ target()
29
+ }
30
+
31
+ func source() {
32
+ intermediate()
33
+ }
34
+ ```
35
+
36
+ Running with `sourceFunction = "source"` and `targetFunction = "target"` produces results showing each call site on the path with a message like: "Reachable call from `source` to `intermediate`".
37
+
38
+ ## Output Format
39
+
40
+ The query is a `@kind problem` query producing rows of:
41
+
42
+ - ``select call, "Reachable call from `caller` to `callee`"``
43
+
44
+ ## References
45
+
46
+ - [Go Functions](https://go.dev/doc/effective_go#functions)
47
+ - [CodeQL Call Graph Analysis](https://codeql.github.com/docs/writing-codeql-queries/about-data-flow-analysis/)
@@ -0,0 +1,53 @@
1
+ /**
2
+ * @name Call Graph From To for go
3
+ * @description Displays calls on reachable paths from a source function to a target function, showing transitive call graph connectivity.
4
+ * @id go/tools/call-graph-from-to
5
+ * @kind problem
6
+ * @problem.severity recommendation
7
+ * @tags call-graph
8
+ */
9
+
10
+ import go
11
+ import ExternalPredicates
12
+
13
+ /**
14
+ * Gets a single source function name from the comma-separated list.
15
+ */
16
+ string getSourceFunctionName() {
17
+ exists(string s | sourceFunction(s) | result = s.splitAt(",").trim())
18
+ }
19
+
20
+ /**
21
+ * Gets a single target function name from the comma-separated list.
22
+ */
23
+ string getTargetFunctionName() {
24
+ exists(string s | targetFunction(s) | result = s.splitAt(",").trim())
25
+ }
26
+
27
+ /**
28
+ * Holds if function `caller` directly calls function `callee` by name.
29
+ */
30
+ predicate calls(FuncDecl caller_, FuncDecl callee_) {
31
+ exists(CallExpr c |
32
+ c.getEnclosingFunction() = caller_ and
33
+ c.getTarget().getName() = callee_.getName()
34
+ )
35
+ }
36
+
37
+ from CallExpr call, FuncDecl caller
38
+ where
39
+ call.getEnclosingFunction() = caller and
40
+ exists(
41
+ // Use external predicates if available: show calls on paths from source to target
42
+ FuncDecl source, FuncDecl target
43
+ |
44
+ source.getName() = getSourceFunctionName() and
45
+ target.getName() = getTargetFunctionName() and
46
+ calls*(source, caller) and
47
+ exists(FuncDecl callee |
48
+ call.getTarget().getName() = callee.getName() and
49
+ calls*(callee, target)
50
+ )
51
+ )
52
+ select call,
53
+ "Reachable call from `" + caller.getName() + "` to `" + call.getTarget().getName() + "`"
@@ -8,18 +8,13 @@
8
8
  */
9
9
 
10
10
  import go
11
-
12
- /**
13
- * Gets the target function name for which to generate the call graph.
14
- * Can be a single function name or comma-separated list of function names.
15
- */
16
- external string targetFunction();
11
+ import ExternalPredicates
17
12
 
18
13
  /**
19
14
  * Gets a single target function name from the comma-separated list.
20
15
  */
21
16
  string getTargetFunctionName() {
22
- result = targetFunction().splitAt(",").trim()
17
+ exists(string s | targetFunction(s) | result = s.splitAt(",").trim())
23
18
  }
24
19
 
25
20
  /**
@@ -32,16 +27,5 @@ string getCallerName(CallExpr call) {
32
27
  }
33
28
 
34
29
  from CallExpr call
35
- where
36
- (
37
- // Use external predicate if available
38
- call.getTarget().getName() = getTargetFunctionName()
39
- or
40
- // Fallback for unit tests: include test files
41
- (
42
- not exists(getTargetFunctionName()) and
43
- call.getFile().getParentContainer().getParentContainer().getBaseName() = "test"
44
- )
45
- )
46
- select call,
47
- "Call to `" + call.getTarget().getName() + "` from `" + getCallerName(call) + "`"
30
+ where call.getTarget().getName() = getTargetFunctionName()
31
+ select call, "Call to `" + call.getTarget().getName() + "` from `" + getCallerName(call) + "`"
@@ -0,0 +1,14 @@
1
+ /**
2
+ * Shared extensible predicate declarations for MCP server tools queries.
3
+ * Values are provided via dataExtensions YAML files during testing,
4
+ * or via a temporary data extension pack at runtime from the MCP server.
5
+ */
6
+
7
+ /** Holds for each source function name for call graph analysis. */
8
+ extensible predicate sourceFunction(string name);
9
+
10
+ /** Holds for each target function name for call graph analysis. */
11
+ extensible predicate targetFunction(string name);
12
+
13
+ /** Holds for each selected source file path for AST/CFG printing. */
14
+ extensible predicate selectedSourceFiles(string path);
@@ -7,19 +7,13 @@
7
7
  */
8
8
 
9
9
  import go
10
- import semmle.go.PrintAst
11
-
12
- /**
13
- * Gets the source files to generate AST from.
14
- * Can be a single file path or comma-separated list of file paths.
15
- */
16
- external string selectedSourceFiles();
10
+ import ExternalPredicates
17
11
 
18
12
  /**
19
13
  * Gets a single source file from the comma-separated list.
20
14
  */
21
15
  string getSelectedSourceFile() {
22
- result = selectedSourceFiles().splitAt(",").trim()
16
+ exists(string s | selectedSourceFiles(s) | result = s.splitAt(",").trim())
23
17
  }
24
18
 
25
19
  /**
@@ -30,29 +24,145 @@ File getSelectedFile() {
30
24
  selectedFile = getSelectedSourceFile() and
31
25
  (
32
26
  // Match by exact relative path from source root
33
- result.getRelativePath() = selectedFile or
27
+ result.getRelativePath() = selectedFile
28
+ or
34
29
  // Match by file name if no path separators
35
- (not selectedFile.matches("%/%") and result.getBaseName() = selectedFile) or
30
+ not selectedFile.matches("%/%") and result.getBaseName() = selectedFile
31
+ or
36
32
  // Match by ending path component
37
- result.getAbsolutePath().suffix(result.getAbsolutePath().length() - selectedFile.length()) = selectedFile
33
+ result.getAbsolutePath().suffix(result.getAbsolutePath().length() - selectedFile.length()) =
34
+ selectedFile
38
35
  )
39
36
  )
40
37
  }
41
38
 
42
39
  /**
43
- * Configuration for PrintAST that uses external predicates to specify source files.
44
- * Falls back to test file selection when external predicates are not available.
40
+ * Holds if the given file should be printed.
41
+ * Uses the external predicate if available, otherwise falls back to test files.
42
+ */
43
+ private predicate isSelectedFile(File file) { file = getSelectedFile() }
44
+
45
+ // Standalone PrintAST implementation for Go.
46
+ //
47
+ // This avoids extending the library's `PrintAstConfiguration` (which is inside
48
+ // an `overlay[local]` module in `go-all`) by directly using the Go AST API.
49
+ // File filtering is applied at the source level for efficiency.
50
+ /** Gets the enclosing function declaration for `n`, if any. */
51
+ private FuncDecl getEnclosingFunctionDecl(AstNode n) { result = n.getParent*() }
52
+
53
+ /**
54
+ * Holds if `ast` should be included in the printed AST.
55
+ * Restricts to selected files and excludes comments for deterministic output.
56
+ */
57
+ private predicate shouldPrint(AstNode ast) {
58
+ isSelectedFile(ast.getFile()) and
59
+ // Print nodes without an enclosing function (e.g. file headers)
60
+ forall(FuncDecl f | f = getEnclosingFunctionDecl(ast) | isSelectedFile(f.getFile())) and
61
+ // Exclude comments for deterministic output
62
+ not ast instanceof Comment and
63
+ not ast instanceof CommentGroup and
64
+ exists(ast.getLocation())
65
+ }
66
+
67
+ /** Gets the QL class label for an AST node. */
68
+ private string qlClass(AstNode el) { result = "[" + concat(el.getAPrimaryQlClass(), ", ") + "] " }
69
+
70
+ /** Gets the default string representation for an AST node. */
71
+ private string nodeToString(AstNode ast) {
72
+ if ast instanceof File
73
+ then result = qlClass(ast) + ast.(File).getRelativePath()
74
+ else result = qlClass(ast) + ast.toString()
75
+ }
76
+
77
+ /**
78
+ * Gets the child at `childIndex` for `ast`, with special handling
79
+ * for `File` nodes (package name expression is moved to index 0).
80
+ * Comments are excluded from the child list.
45
81
  */
46
- class Cfg extends PrintAstConfiguration {
47
- override predicate shouldPrintFunction(FuncDecl func) { this.shouldPrintFile(func.getFile()) }
82
+ private AstNode getChild(AstNode ast, int childIndex) {
83
+ if ast instanceof File and exists(ast.(File).getPackageNameExpr())
84
+ then
85
+ exists(AstNode packageNode, int oldPackageIndex |
86
+ ast.getUniquelyNumberedChild(oldPackageIndex) = packageNode and
87
+ packageNode = ast.(File).getPackageNameExpr() and
88
+ (
89
+ childIndex = 0 and result = packageNode
90
+ or
91
+ result =
92
+ rank[childIndex](AstNode node, int i |
93
+ node = ast.getUniquelyNumberedChild(i) and
94
+ i != oldPackageIndex and
95
+ not node instanceof Comment and
96
+ not node instanceof CommentGroup
97
+ |
98
+ node order by i
99
+ )
100
+ )
101
+ )
102
+ else
103
+ result =
104
+ rank[childIndex](AstNode node, int i |
105
+ node = ast.getUniquelyNumberedChild(i) and
106
+ not node instanceof Comment and
107
+ not node instanceof CommentGroup
108
+ |
109
+ node order by i
110
+ )
111
+ }
112
+
113
+ /** Gets the edge label from `ast` to its child at `childIndex`. */
114
+ private string getChildEdgeLabel(AstNode ast, int childIndex) {
115
+ exists(getChild(ast, childIndex)) and
116
+ if
117
+ ast instanceof File and
118
+ exists(ast.(File).getPackageNameExpr()) and
119
+ getChild(ast, childIndex) = ast.(File).getPackageNameExpr()
120
+ then result = "package"
121
+ else result = childIndex.toString()
122
+ }
48
123
 
49
- override predicate shouldPrintFile(File file) {
50
- // Use external predicate if available
51
- file = getSelectedFile()
124
+ /** Holds if `node` belongs to the output tree, and its property `key` has the given `value`. */
125
+ query predicate nodes(AstNode node, string key, string value) {
126
+ shouldPrint(node) and
127
+ (
128
+ key = "semmle.label" and value = nodeToString(node)
129
+ or
130
+ node instanceof Expr and
131
+ (
132
+ key = "Value" and
133
+ value = qlClass(node) + node.(Expr).getExactValue()
134
+ or
135
+ key = "Type" and
136
+ not node.(Expr).getType() instanceof InvalidType and
137
+ value = node.(Expr).getType().pp()
138
+ )
52
139
  or
53
- // Fallback for unit tests: include specific test files
54
- (not exists(getSelectedFile()) and file.getBaseName() = "Example1.go")
55
- }
140
+ node instanceof File and
141
+ key = "semmle.order" and
142
+ value =
143
+ any(int i |
144
+ node = rank[i](File fn | isSelectedFile(fn) | fn order by fn.getRelativePath())
145
+ |
146
+ i
147
+ ).toString()
148
+ )
149
+ }
150
+
151
+ /** Holds if `target` is a child of `source` in the AST. */
152
+ query predicate edges(AstNode source, AstNode target, string key, string value) {
153
+ shouldPrint(source) and
154
+ shouldPrint(target) and
155
+ exists(int childIndex |
156
+ target = getChild(source, childIndex) and
157
+ (
158
+ key = "semmle.label" and value = getChildEdgeLabel(source, childIndex)
159
+ or
160
+ key = "semmle.order" and value = childIndex.toString()
161
+ )
162
+ )
163
+ }
56
164
 
57
- override predicate shouldPrintComments(File file) { none() }
165
+ /** Holds if property `key` of the graph has the given `value`. */
166
+ query predicate graphProperties(string key, string value) {
167
+ key = "semmle.graphKind" and value = "tree"
58
168
  }
@@ -2,23 +2,23 @@
2
2
  lockVersion: 1.0.0
3
3
  dependencies:
4
4
  codeql/concepts:
5
- version: 0.0.15
5
+ version: 0.0.18
6
6
  codeql/controlflow:
7
- version: 2.0.25
7
+ version: 2.0.28
8
8
  codeql/dataflow:
9
- version: 2.0.25
9
+ version: 2.1.0
10
10
  codeql/go-all:
11
- version: 6.0.1
11
+ version: 7.0.2
12
12
  codeql/mad:
13
- version: 1.0.41
13
+ version: 1.0.44
14
14
  codeql/ssa:
15
- version: 2.0.17
15
+ version: 2.0.20
16
16
  codeql/threat-models:
17
- version: 1.0.41
17
+ version: 1.0.44
18
18
  codeql/tutorial:
19
- version: 1.0.41
19
+ version: 1.0.44
20
20
  codeql/typetracking:
21
- version: 2.0.25
22
- codeql/util:
23
21
  version: 2.0.28
22
+ codeql/util:
23
+ version: 2.0.31
24
24
  compiled: false
@@ -1,6 +1,6 @@
1
1
  name: advanced-security/ql-mcp-go-tools-src
2
- version: 2.24.3
2
+ version: 2.25.0
3
3
  description: 'Queries for codeql-development-mcp-server tools for go language'
4
4
  library: false
5
5
  dependencies:
6
- codeql/go-all: 6.0.1
6
+ codeql/go-all: 7.0.2
@@ -8,18 +8,13 @@
8
8
  */
9
9
 
10
10
  import java
11
-
12
- /**
13
- * Gets the source method name for which to generate the call graph.
14
- * Can be a single method name or comma-separated list of method names.
15
- */
16
- external string sourceFunction();
11
+ import ExternalPredicates
17
12
 
18
13
  /**
19
14
  * Gets a single source method name from the comma-separated list.
20
15
  */
21
16
  string getSourceFunctionName() {
22
- result = sourceFunction().splitAt(",").trim()
17
+ exists(string s | sourceFunction(s) | result = s.splitAt(",").trim())
23
18
  }
24
19
 
25
20
  /**
@@ -36,15 +31,5 @@ from Call call, Callable source, Callable callee
36
31
  where
37
32
  call.getCaller() = source and
38
33
  call.getCallee() = callee and
39
- (
40
- // Use external predicate if available
41
- source = getSourceFunction()
42
- or
43
- // Fallback for unit tests: include test files
44
- (
45
- not exists(getSourceFunction()) and
46
- source.getFile().getParentContainer().getParentContainer().getBaseName() = "test"
47
- )
48
- )
49
- select call,
50
- "Call from `" + source.getName() + "` to `" + callee.getName() + "`"
34
+ source = getSourceFunction()
35
+ select call, "Call from `" + source.getName() + "` to `" + callee.getName() + "`"
@@ -0,0 +1,49 @@
1
+ # CallGraphFromTo for Java
2
+
3
+ Displays calls on reachable paths from a source method to a target method, showing transitive call graph connectivity.
4
+
5
+ ## Overview
6
+
7
+ This query identifies all method calls that lie on any transitive call path from a specified source method to a specified target method. Given both a source and target method name, it reports each call site along the connecting paths, which is useful for understanding indirect call chains, security-relevant data flow paths, and method reachability.
8
+
9
+ The query uses transitive closure (`calls*`) to determine reachability, then reports only the direct call sites that contribute to paths between the source and target. It accepts method names via extensible predicates (`sourceFunction` and `targetFunction`) populated via CodeQL data extensions / model packs (see `ExternalPredicates.qll`).
10
+
11
+ ## Use Cases
12
+
13
+ This query is primarily used for:
14
+
15
+ - Determining if a call path exists between two methods
16
+ - Mapping indirect call chains from a source to a target method
17
+ - Analyzing security-relevant paths (e.g., from user input handlers to sensitive operations)
18
+ - Understanding transitive dependencies between methods
19
+
20
+ ## Example
21
+
22
+ The following Java code demonstrates a transitive call chain from `source` through `intermediate` to `target`:
23
+
24
+ ```java
25
+ class Example {
26
+ void target() {}
27
+
28
+ void intermediate() {
29
+ target();
30
+ }
31
+
32
+ void source() {
33
+ intermediate();
34
+ }
35
+ }
36
+ ```
37
+
38
+ Running with `sourceFunction = "source"` and `targetFunction = "target"` produces results showing each call site on the path with a message like: "Reachable call from `source` to `intermediate`".
39
+
40
+ ## Output Format
41
+
42
+ The query is a `@kind problem` query producing rows of:
43
+
44
+ - ``select call, "Reachable call from `caller` to `callee`"``
45
+
46
+ ## References
47
+
48
+ - [Java Methods](https://docs.oracle.com/javase/tutorial/java/javaOO/methods.html)
49
+ - [CodeQL Call Graph Analysis](https://codeql.github.com/docs/writing-codeql-queries/about-data-flow-analysis/)
@@ -0,0 +1,64 @@
1
+ /**
2
+ * @name Call Graph From To for java
3
+ * @description Displays calls on reachable paths from a source method to a target method, showing transitive call graph connectivity.
4
+ * @id java/tools/call-graph-from-to
5
+ * @kind problem
6
+ * @problem.severity recommendation
7
+ * @tags call-graph
8
+ */
9
+
10
+ import java
11
+ import ExternalPredicates
12
+
13
+ /**
14
+ * Gets a single source method name from the comma-separated list.
15
+ */
16
+ string getSourceFunctionName() {
17
+ exists(string s | sourceFunction(s) | result = s.splitAt(",").trim())
18
+ }
19
+
20
+ /**
21
+ * Gets a single target method name from the comma-separated list.
22
+ */
23
+ string getTargetFunctionName() {
24
+ exists(string s | targetFunction(s) | result = s.splitAt(",").trim())
25
+ }
26
+
27
+ /**
28
+ * Gets a method by matching against the selected source method names.
29
+ */
30
+ Callable getSourceFunction() {
31
+ exists(string selectedFunc |
32
+ selectedFunc = getSourceFunctionName() and
33
+ result.getName() = selectedFunc
34
+ )
35
+ }
36
+
37
+ /**
38
+ * Gets a method by matching against the selected target method names.
39
+ */
40
+ Callable getTargetFunction() {
41
+ exists(string selectedFunc |
42
+ selectedFunc = getTargetFunctionName() and
43
+ result.getName() = selectedFunc
44
+ )
45
+ }
46
+
47
+ /**
48
+ * Holds if callable `caller` directly calls callable `callee`.
49
+ */
50
+ predicate calls(Callable caller_, Callable callee_) {
51
+ exists(Call c | c.getCaller() = caller_ and c.getCallee() = callee_)
52
+ }
53
+
54
+ from Call call, Callable caller, Callable callee
55
+ where
56
+ call.getCaller() = caller and
57
+ call.getCallee() = callee and
58
+ exists(Callable source, Callable target |
59
+ source = getSourceFunction() and
60
+ target = getTargetFunction() and
61
+ calls*(source, caller) and
62
+ calls*(callee, target)
63
+ )
64
+ select call, "Reachable call from `" + caller.getName() + "` to `" + callee.getName() + "`"