|
121 | 121 | + isNeutralReturn(...) |
122 | 122 | + isBulkGetterLike(...) |
123 | 123 |
|
124 | | - These are imported by: |
| 124 | + These are imported by: |
125 | 125 | - CaptureSinkModels.ql |
126 | 126 | - CaptureSummaryModels.ql |
127 | 127 | - CaptureContentSummaryModels.ql |
128 | 128 | - CaptureHeuristicSummaryModels.ql |
129 | 129 |
|
130 | | - - Design: Three Modeling Targets |
| 130 | + Design: Three Modeling Targets |
131 | 131 | | Module | Implements | Purpose | |
132 | 132 | | ---------------------------- | ------------------------------- | ------------------------------------------------ | |
133 | | - | `SummaryModelGeneratorInput` | `SummaryModelGeneratorInputSig` | Models pass-through or computed summaries | |
134 | | - | `SourceModelGeneratorInput` | `SourceModelGeneratorInputSig` | Models user-controlled or origin taint sources | |
135 | | - | `SinkModelGeneratorInput` | `SinkModelGeneratorInputSig` | Models taint sinks (e.g., logging, SQL, network) | |
| 133 | + | =SummaryModelGeneratorInput= | =SummaryModelGeneratorInputSig= | Models pass-through or computed summaries | |
| 134 | + | =SourceModelGeneratorInput= | =SourceModelGeneratorInputSig= | Models user-controlled or origin taint sources | |
| 135 | + | =SinkModelGeneratorInput= | =SinkModelGeneratorInputSig= | Models taint sinks (e.g., logging, SQL, network) | |
136 | 136 |
|
137 | | - - Shared Input System |
| 137 | + Shared Input System |
138 | 138 | ModelGeneratorCommonInput provides: |
139 | 139 | - Name formatting |
140 | 140 | - Type filtering (isRelevantType) |
|
143 | 143 |
|
144 | 144 | This gives a stable data interface to the rest of the system. |
145 | 145 |
|
146 | | - - Filtering logic |
| 146 | + Filtering logic |
147 | 147 | #+BEGIN_SRC java |
148 | 148 | private predicate relevant(Callable api) { |
149 | 149 | api.isPublic() and |
|
187 | 187 | This query defines: |
188 | 188 | #+BEGIN_SRC java |
189 | 189 | from PublicEndpointFromSource endpoint, boolean supported, string type |
190 | | - where |
| 190 | + where |
191 | 191 | supported = isSupported(endpoint) and |
192 | 192 | type = supportedType(endpoint) |
193 | | - select endpoint, endpoint.getPackageName(), endpoint.getTypeName(), endpoint.getName(), |
| 193 | + select endpoint, endpoint.getPackageName(), endpoint.getTypeName(), endpoint.getName(), |
194 | 194 | endpoint.getParameterTypes(), supported, |
195 | 195 | endpoint.getCompilationUnit().getParentContainer().getBaseName(), type |
196 | 196 | #+END_SRC |
197 | 197 |
|
198 | | - There is a direct connection between output columns in the model editor: |
| 198 | + There is a direct connection between this query and output columns in the model |
| 199 | + editor: |
199 | 200 | - =supported = true= → shows in the UI as /"Method already modeled"/ |
200 | 201 | - =supported = false= → shown as /"Unmodeled"/ |
201 | 202 |
|
202 | 203 | ** Files Created or Modified by the Modeling Workflow |
203 | | - - Upon launching ==CodeQL: Method modeling==, a new pack manifest is created: |
204 | | - [[../.github/codeql/extensions/jedis-db-local-java/codeql-pack.yml]] |
| 204 | + - Upon launching =CodeQL: Method modeling=, a new pack manifest is created: |
| 205 | + [[../.github/codeql/extensions/jedis-db-local-java/codeql-pack.yml][codeql-pack.yml]] |
205 | 206 | - After selecting methods and saving, modeling results are written to: |
206 | | - [[../.github/codeql/extensions/jedis-db-local-java/models/redis.clients.jedis.model.yml]] |
| 207 | + [[../.github/codeql/extensions/jedis-db-local-java/models/redis.clients.jedis.model.yml][redis.clients.jedis.model.yml]] |
207 | 208 |
|
208 | 209 | ** Workspace Configuration Required |
209 | | - |
210 | | - WHAT SETTING? |
211 | | - |
212 | 210 | To ensure that these model extensions are applied during query runs, include |
213 | | - this setting in the workspace configuration file [[../qllab.code-workspace]] |
| 211 | + the setting |
| 212 | + : "codeQL.runningQueries.useExtensionPacks": "all" |
| 213 | + in the workspace configuration file [[../qllab.code-workspace]] |
214 | 214 |
|
215 | 215 | In some environments (e.g., older VS Code versions), you may also need to |
216 | 216 | replicate this setting in [[../.vscode/settings.json]] |
|
301 | 301 |
|
302 | 302 | These files indicate active use of injection-related taint tracking in the C++ suite as well. |
303 | 303 |
|
304 | | -* TODO for java, the sqltainted query will find the sink, not the source yet. |
305 | | - [[../ql/java/ql/src/Security/CWE/CWE-089/SqlTainted.ql]] |
306 | | - |
307 | | -* TODO Modeling sqlite as dependency |
308 | | - The tree [[../codeql-sqlite-java/]] contains a trivial sample taken from a workshop. It |
309 | | - uses =sqlite-jdbc-3.36.0.1.jar=, so we can use it to illustrate modeling on a |
310 | | - smaller example. This one is unusual; the function |
311 | | - java.io.Console.readLine() is already modeled, but as a taint step, not a |
312 | | - source. We need it as source. The model editor won't show it at all because it |
313 | | - is already modeled, |
314 | | - |
315 | | - |
316 | | - |
317 | | -* TODO vulnerable sample, sqlite |
318 | | - For .eval() to show in a query, it has to be used in an application. So we |
319 | | - modify src-sqlite/AddUser.java for jedis. |
| 304 | +* TODO Modeling Gaps in SqlTainted.ql (Java) |
| 305 | + The built-in SQL injection query |
| 306 | + [[../ql/java/ql/src/Security/CWE/CWE-089/SqlTainted.ql]] correctly identifies the |
| 307 | + sink in the Jedis sample, but not the source. This is because |
| 308 | + =java.io.Console.readLine()= is modeled as a taint *step*, not a *source*. Since |
| 309 | + the model editor excludes functions that are already modeled in any capacity, |
| 310 | + this function is not visible for editing. |
| 311 | + |
| 312 | + To detect the source, we must override or supplement the model manually—either |
| 313 | + by using the models-as-data mechanism or extending =Customizations.qll= with a |
| 314 | + new source declaration. |
| 315 | + |
| 316 | +* TODO Modeling SQLite as a Dependency |
| 317 | + The directory [[../codeql-sqlite-java/]] contains a minimal Java sample derived from |
| 318 | + a prior workshop. It uses =sqlite-jdbc-3.36.0.1.jar= and serves as a small-scale |
| 319 | + test case for dependency-based modeling. This example is especially useful for |
| 320 | + illustrating subtle modeling issues. |
| 321 | + |
| 322 | + In particular, it uses =java.io.Console.readLine()=, which is already modeled as |
| 323 | + a taint *step*. However, for SQL injection tracking, we need it to act as a |
| 324 | + *source*. Because of its preexisting status, it does not appear in the model |
| 325 | + editor. To handle this, we must add a manual source override—either as a raw |
| 326 | + YAML model or as a hardcoded entry via =Customizations.qll=. |
| 327 | + |
| 328 | +* TODO Creating a Vulnerable SQLite Sample for Query Visibility |
| 329 | + To ensure that taint-based queries (e.g., SqlTainted.ql) identify vulnerable |
| 330 | + behavior, the sink function -- such as =.eval()= or =sqlite3_exec()= -- must |
| 331 | + actually be invoked in application code. It is not sufficient for the function |
| 332 | + to merely exist in a linked library or dependency. CodeQL analysis only |
| 333 | + considers *reachable* code in the source tree. |
| 334 | + |
| 335 | + To address this, we modify the file [[../codeql-sqlite-java/AddUser.java]] to |
| 336 | + include a realistic, vulnerable flow that mimics typical usage patterns. For |
| 337 | + example, the program should: |
| 338 | + |
| 339 | + 1. Accept user input (e.g., via =System.in=, =BufferedReader=, or |
| 340 | + =Console.readLine()=), |
| 341 | + 2. Store it in a variable without sanitization, |
| 342 | + 3. Construct an SQL query using string concatenation, |
| 343 | + 4. Call =eval()= or =sqlite3_exec()= with the tainted query. |
| 344 | + |
| 345 | + This guarantees that the sink is both *present* and *exercised*, allowing |
| 346 | + built-in and custom CodeQL queries to detect the dataflow path from source to |
| 347 | + sink. |
| 348 | + |
| 349 | + The same flow structure used in the Jedis version can be reused here. That way, |
| 350 | + we maintain consistency across modeling examples while switching the underlying |
| 351 | + dependency from Redis to SQLite. |
320 | 352 |
|
0 commit comments