Compare commits

..

97 Commits

Author SHA1 Message Date
Alex Eyers-Taylor
2c3442d4eb Fix a bad join order on locations. 2025-04-25 15:09:41 +01:00
Alex Eyers-Taylor
29fcbe3c8f Swift extract predicates to improve TTE to avoid loop invariant code. 2025-04-25 15:09:41 +01:00
Alex Eyers-Taylor
5ba6904e91 Use late inline to deal with bad join orders from type tracking. 2025-04-25 15:09:40 +01:00
Alex Eyers-Taylor
1cf1acbbc6 Ruby: Avoid a forced CP. 2025-04-25 15:09:40 +01:00
Alex Eyers-Taylor
7096abe0a9 CPP: Add noinline so size estimates are better. 2025-04-25 15:09:40 +01:00
Alex Eyers-Taylor
15a26fd2ee Extarct to predicate for RTJO 2025-04-25 15:09:40 +01:00
Alex Eyers-Taylor
25c47922ec CPP: Pull rank into predicate for RTJO. 2025-04-25 15:09:39 +01:00
Alex Eyers-Taylor
672d896a80 CPP: Manually flip TC for RTJO. 2025-04-25 15:09:39 +01:00
Alex Eyers-Taylor
34ab6b3919 Reduce number of negations in some cases. 2025-04-25 15:09:39 +01:00
Tamás Vajk
3437210d32 Merge pull request #19355 from tamasvajk/test/add-query-suite-tests
Add query suite integration tests for swift, actions, csharp, go, javascript, ruby, rust
2025-04-25 15:37:51 +02:00
Chuan-kai Lin
ed690972d4 Merge pull request #19379 from github/cklin/python-polynomial-redos
Python: disable diff-informed PolynomialReDoS.ql
2025-04-25 06:21:47 -07:00
Tamas Vajk
998e64baf3 Fix failing C# test 2025-04-25 14:06:18 +02:00
Tamás Vajk
c54b684132 Apply suggestions from code review - code quality improvements
Co-authored-by: Paolo Tranquilli <redsun82@github.com>
2025-04-25 14:06:17 +02:00
Tamas Vajk
a4a24470c8 Add query suite inclusion tests for actions, csharp, go, javascript, ruby, rust 2025-04-25 14:06:17 +02:00
Tamas Vajk
522dd51416 Improve query suite test based on feedback 2025-04-25 14:06:16 +02:00
Tamas Vajk
4c9aee2cc7 Add query suite tests for swift with shared logic 2025-04-25 14:06:15 +02:00
Tom Hvitved
432435f1a6 Merge pull request #19358 from hvitved/rust/path-resolution-perf-tweaks
Rust: Path resolution performance tweaks
2025-04-25 14:01:47 +02:00
Jeroen Ketema
8b95e0ee4a Merge pull request #19315 from github/redsun82/swift-6.1
Swift: make extractor compile again after 6.1 upgrade
2025-04-25 12:34:39 +02:00
Jeroen Ketema
e8eac810b4 Swift: Commit external sources to git LFS 2025-04-25 11:56:28 +02:00
Chuan-kai Lin
6c1e80df3a Python: disable diff-informed PolynomialReDoS.ql
This commit disabled diff-informed for PolynomialReDoS.ql because it
could miss some alerts within diff ranges.
2025-04-24 14:57:06 -07:00
Ian Lynagh
f9172ff493 Merge pull request #19368 from igfoo/igfoo/add-check-for-buildmode-none
C++: Add exception for build-mode-none in various queries
2025-04-24 20:30:09 +01:00
Jeroen Ketema
5920925041 Merge pull request #19363 from jketema/platform
Update list of supported platforms
2025-04-24 19:11:31 +02:00
Jeroen Ketema
a5a21b1ddd Swift: Guard 'getCaptures' in fillClosureExpr 2025-04-24 17:42:59 +02:00
Paolo Tranquilli
21170a1f6d Merge pull request #19370 from github/redsun82/go-remove-invalid-toolchain-diagnostic
Go: remove invalid toolchain version diagnostics
2025-04-24 17:32:34 +02:00
Jeroen Ketema
21c97085a1 Merge pull request #19361 from jketema/fieldflow
Dataflow: Make default field flow branch limit configurable per language
2025-04-24 16:45:49 +02:00
Jeroen Ketema
55a8a4444d Merge pull request #19365 from jketema/c23
C++: Claim beta support for C23 and C++23
2025-04-24 16:13:39 +02:00
Paolo Tranquilli
69b87a63b8 Go: remove invalid toolchain version diagnostics
This diagnostic was introduced by https://github.com/github/codeql/pull/15979.
However in the meantime the Go team [has backtracked](https://github.com/golang/go/issues/62278#issuecomment-2062002018)
on their decision, which leads to confusing alerts for user (e.g. https://github.com/github/codeql-action/issues/2868).
Even using Go toolchains from 1.21 to 1.22 we weren't immediately able
to reproduce the problem that this diagnostics was meant to guard
against. Therefore it was deemed simpler to just remove it.

_En passant_ the `Makefile` now accepts `rtjo` not being set.
2025-04-24 14:41:05 +02:00
Ian Lynagh
0cd859c559 C++: qlformat 2025-04-24 12:48:21 +01:00
Alexander Eyers-Taylor
ea83ecf802 Merge pull request #19327 from d10c/d10c/rtjo-csharp-jo-fix
C#: Join order fix
2025-04-24 12:34:22 +01:00
Ian Lynagh
063bff073b C++: Add checks for build mode in various queries
Adds a check for the absence of build-mode-none in
    cpp/wrong-type-format-argument
    cpp/comparison-with-wider-type
    cpp/integer-multiplication-cast-to-long
    cpp/implicit-function-declaration
    cpp/suspicious-add-sizeof
2025-04-24 12:15:31 +01:00
Jeroen Ketema
42c4252a3d C++: Claim beta support for C23 and C++23
All features we can support, we currently do support.
2025-04-24 11:44:16 +02:00
Jeroen Ketema
0357f3959b Update list of supported platforms
I've effectively sync'ed this with the list of runners that are publicly
available. I did not yet add Windows 2025, as it is my understanding is that
we haven't really done any testing on that yet.
2025-04-24 11:28:09 +02:00
Jeroen Ketema
46b21af3ef Dataflow: Make default field flow branch limit configurable per language 2025-04-24 11:02:49 +02:00
Jeroen Ketema
4093afbaab Merge pull request #19290 from jketema/typeof
C++: Support C23 `typeof` and `typeof_unqual`
2025-04-24 10:12:46 +02:00
Michael Nebel
17f58c90bd Merge pull request #19148 from michaelnebel/csharp/invalid-string-format
C#: Improve `cs/invalid-string-formatting` and add to the Code Quality suite.
2025-04-24 10:03:06 +02:00
Michael Nebel
65ac951964 C#: Remove all Sink tags after rebase. 2025-04-24 08:54:53 +02:00
Michael Nebel
dcf11c2d4b C#: Match up sources, alerts and sinks in the tests. 2025-04-24 08:54:51 +02:00
Michael Nebel
b6d2f14b9b C#: Add change note. 2025-04-24 08:54:49 +02:00
Michael Nebel
22ae3e7992 C#: Update string format item parameter expected test case. 2025-04-24 08:54:48 +02:00
Michael Nebel
f2dddd6d5c C#: Hide the abstract FormatMethod class. 2025-04-24 08:54:47 +02:00
Michael Nebel
6de5920172 C#: Update test expected output. 2025-04-24 08:54:45 +02:00
Michael Nebel
042c7e5186 C#: Generalize array logic to params collection like types. 2025-04-24 08:54:43 +02:00
Michael Nebel
930bb6b515 C#: Add FP for string.Format using params collection. 2025-04-24 08:54:42 +02:00
Michael Nebel
39abd5c004 C#: Update test expected output. 2025-04-24 08:54:40 +02:00
Michael Nebel
f31235db43 C#: Improve format logic to take CompositeFormat and generics into account. 2025-04-24 08:54:39 +02:00
Michael Nebel
11dffc6647 C#: Add more invalid-string-formatting testcases. 2025-04-24 08:54:37 +02:00
Michael Nebel
8fb5fe97aa C#: Update test expected output. 2025-04-24 08:54:36 +02:00
Michael Nebel
1d9d8780b3 C#: Remove some false positives and add more true positives for cs/invalid-string-format. 2025-04-24 08:54:34 +02:00
Michael Nebel
f73b7429c6 C#: Remove false positive example. 2025-04-24 08:54:33 +02:00
Michael Nebel
175e4ecb74 C#: Add more format testcases. 2025-04-24 08:54:31 +02:00
Michael Nebel
327ddb07a1 C#: Re-factor FormatMethod. 2025-04-24 08:54:30 +02:00
Michael Nebel
9cfd6e30b9 C#: Convert testing of cs/invalid-string-formatting to inline expectations and adjust some of the testcases. 2025-04-24 08:54:28 +02:00
Michael Nebel
68f93492b1 C#: Add cs/invalid-string-formatting to the codeql quality suite. 2025-04-24 08:54:27 +02:00
Michael Nebel
91f1183dfd Merge pull request #19354 from michaelnebel/csharp/matchlinenumbersonsinks
Shared: Match line information on Alert and Sink locations.
2025-04-24 08:53:01 +02:00
Tom Hvitved
e72aba76f6 Rust: Path resolution performance tweaks 2025-04-23 19:49:20 +02:00
Jeroen Ketema
cad695868d C++: Add change note 2025-04-23 17:51:06 +02:00
Jeroen Ketema
8086ef48c7 Swift: Add change note 2025-04-23 17:10:57 +02:00
Jeroen Ketema
eea963e3f4 Swift: Add upgrade and downgrade scripts 2025-04-23 17:10:57 +02:00
Jeroen Ketema
a74b38c0ec Swift: Replace deprecated @_moveOnly in test by ~Copyable 2025-04-23 17:10:57 +02:00
Jeroen Ketema
59faf9fbdf Swift: Update errors test
The representation of the errors seems to have changed somewhat in Swift 6.1.
2025-04-23 17:10:57 +02:00
Jeroen Ketema
10d86c9708 Swift: Disable parts of tests that crash with Swift 6.1 2025-04-23 17:10:56 +02:00
Jeroen Ketema
9a21b0dc5c Swift: Update SuccessfullyExtractedLines for external code being extracted 2025-04-23 17:10:56 +02:00
Jeroen Ketema
e135f5ddf6 Swift: Update ObjectLiteralExpr test
The entities now have proper error types instead of missing types.
2025-04-23 17:10:56 +02:00
Jeroen Ketema
b6076c0481 Swift: Update test results for ParenType no longer being extracted 2025-04-23 17:10:55 +02:00
Jeroen Ketema
1b21e4c667 Swift: Update test results for IfConfigDecl no longer being extracted 2025-04-23 17:10:55 +02:00
Jeroen Ketema
36672f44b9 Swift: Take inverses into account when mangling ProtocolCompositionTypes 2025-04-23 17:10:55 +02:00
Paolo Tranquilli
7834a3d9e4 Swift: expand mangling of ExistentialMetatypeType 2025-04-23 17:10:55 +02:00
Jeroen Ketema
30242ed6fb Swift: Remove "to do" comment 2025-04-23 17:10:54 +02:00
Jeroen Ketema
4fc5a73bac Swift: Update mangling of OpenedArchetypeType 2025-04-23 17:10:54 +02:00
Paolo Tranquilli
1ac47a892b Swift: make extractor compile again after 6.1 upgrade 2025-04-23 17:10:54 +02:00
Jeroen Ketema
0c313463b4 C++: Update stats file 2025-04-23 16:56:59 +02:00
Jeroen Ketema
a3e0c15c10 C++: Add upgrade and downgrade scripts 2025-04-23 16:56:57 +02:00
Jeroen Ketema
e97f9495d0 C++: Update expected test results 2025-04-23 16:56:56 +02:00
Jeroen Ketema
df3282c204 C++: Support C23 typeof and typeof_unqual 2025-04-23 16:56:47 +02:00
Michael Nebel
2e0ce44fde Javascript: Update test files. 2025-04-23 15:41:41 +02:00
Geoffrey White
37bcedcf11 Merge pull request #19353 from geoffw0/modelnoise2
Rust: Remove unnecessary predicate.
2025-04-23 12:34:40 +01:00
Tom Hvitved
4abdc13f79 Merge pull request #19193 from hvitved/rust/path-resolution-where-clause
Rust: Take `where` clauses into account in path resolution
2025-04-23 13:00:58 +02:00
Michael Nebel
617f4729d8 Shared: Match line information on Alert and Sink locations. 2025-04-23 12:35:17 +02:00
Mathias Vorreiter Pedersen
808141f7e8 Merge pull request #19295 from MathiasVP/cpp-add-mad-generation-library
C++: Instantiate model generation library
2025-04-23 11:32:16 +01:00
Geoffrey White
d6f1bd9792 Rust: Remove unnecessary predicate. 2025-04-23 11:24:29 +01:00
Mathias Vorreiter Pedersen
9e9a580d02 C++: Add MaD generation test with union content. 2025-04-23 11:11:17 +01:00
Mathias Vorreiter Pedersen
07d8f8dd0d C++: Add an empty model to prevent a warning. 2025-04-23 10:24:17 +01:00
Mathias Vorreiter Pedersen
3fd760c632 C++: Move 'InlineMadTest.qll' out of 'lib/utils/test' and into 'test' since C++ has no external packs depending on MaD testing. 2025-04-20 16:49:02 +01:00
Mathias Vorreiter Pedersen
6fcf56e6e1 C++: Add more tests. 2025-04-20 16:49:00 +01:00
Mathias Vorreiter Pedersen
f6f5f97109 C++: Also make protected members irrelevant. 2025-04-20 16:48:58 +01:00
Mathias Vorreiter Pedersen
e55f94c364 C++: Move contents of 'isUninterestingForDataFlowModels' to 'relevant' 2025-04-20 16:48:56 +01:00
Mathias Vorreiter Pedersen
9cba91c682 C++: Add another entry to 'qlpack' for external models. 2025-04-20 16:48:54 +01:00
Mathias Vorreiter Pedersen
0ce6ab5444 Remove an unnecessary if. 2025-04-20 16:48:53 +01:00
Mathias Vorreiter Pedersen
5462dcdf75 C++: Make final member functions not extensible. 2025-04-20 16:48:51 +01:00
Mathias Vorreiter Pedersen
1f43e51be4 C++: Fix ql-for-ql findings. 2025-04-20 16:48:49 +01:00
Mathias Vorreiter Pedersen
1465058da0 C++: Add copy-pasted files from C#. 2025-04-20 16:48:47 +01:00
Mathias Vorreiter Pedersen
09ebd6e87d C++: Instantiate inline expectation test framework to test model generation. 2025-04-20 16:48:45 +01:00
Mathias Vorreiter Pedersen
f241e4b537 C++: Add tests that will soon succeed. 2025-04-20 16:48:43 +01:00
Mathias Vorreiter Pedersen
3d48b23428 C++: Instantiate model generation library. 2025-04-20 16:48:41 +01:00
Nora Dimitrijević
7f5b48d485 C#: Fix join order in ExternalFlow::interpretElement/6 (only affects RTJO mode) 2025-04-17 15:52:13 +02:00
Tom Hvitved
e26695fc51 Rust: Take where clauses into account in path resolution 2025-04-11 09:28:08 +02:00
Tom Hvitved
cc85a09b39 Rust: Add AI-generated test for path resolution of where clauses 2025-04-11 09:24:09 +02:00
235 changed files with 28812 additions and 3823 deletions

View File

@@ -0,0 +1,17 @@
ql/actions/ql/src/Security/CWE-077/EnvPathInjectionCritical.ql
ql/actions/ql/src/Security/CWE-077/EnvVarInjectionCritical.ql
ql/actions/ql/src/Security/CWE-094/CodeInjectionCritical.ql
ql/actions/ql/src/Security/CWE-1395/UseOfKnownVulnerableAction.ql
ql/actions/ql/src/Security/CWE-275/MissingActionsPermissions.ql
ql/actions/ql/src/Security/CWE-285/ImproperAccessControl.ql
ql/actions/ql/src/Security/CWE-312/ExcessiveSecretsExposure.ql
ql/actions/ql/src/Security/CWE-312/SecretsInArtifacts.ql
ql/actions/ql/src/Security/CWE-312/UnmaskedSecretExposure.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaCodeInjection.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaDirectCache.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaPoisonableStep.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUCritical.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUHigh.ql
ql/actions/ql/src/Security/CWE-829/ArtifactPoisoningCritical.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutCritical.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutHigh.ql

View File

@@ -0,0 +1,33 @@
ql/actions/ql/src/Debug/SyntaxError.ql
ql/actions/ql/src/Models/CompositeActionsSinks.ql
ql/actions/ql/src/Models/CompositeActionsSources.ql
ql/actions/ql/src/Models/CompositeActionsSummaries.ql
ql/actions/ql/src/Models/ReusableWorkflowsSinks.ql
ql/actions/ql/src/Models/ReusableWorkflowsSources.ql
ql/actions/ql/src/Models/ReusableWorkflowsSummaries.ql
ql/actions/ql/src/Security/CWE-077/EnvPathInjectionCritical.ql
ql/actions/ql/src/Security/CWE-077/EnvPathInjectionMedium.ql
ql/actions/ql/src/Security/CWE-077/EnvVarInjectionCritical.ql
ql/actions/ql/src/Security/CWE-077/EnvVarInjectionMedium.ql
ql/actions/ql/src/Security/CWE-094/CodeInjectionCritical.ql
ql/actions/ql/src/Security/CWE-094/CodeInjectionMedium.ql
ql/actions/ql/src/Security/CWE-1395/UseOfKnownVulnerableAction.ql
ql/actions/ql/src/Security/CWE-275/MissingActionsPermissions.ql
ql/actions/ql/src/Security/CWE-285/ImproperAccessControl.ql
ql/actions/ql/src/Security/CWE-312/ExcessiveSecretsExposure.ql
ql/actions/ql/src/Security/CWE-312/SecretsInArtifacts.ql
ql/actions/ql/src/Security/CWE-312/UnmaskedSecretExposure.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaCodeInjection.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaDirectCache.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaPoisonableStep.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUCritical.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUHigh.ql
ql/actions/ql/src/Security/CWE-571/ExpressionIsAlwaysTrueCritical.ql
ql/actions/ql/src/Security/CWE-571/ExpressionIsAlwaysTrueHigh.ql
ql/actions/ql/src/Security/CWE-829/ArtifactPoisoningCritical.ql
ql/actions/ql/src/Security/CWE-829/ArtifactPoisoningMedium.ql
ql/actions/ql/src/Security/CWE-829/UnpinnedActionsTag.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutCritical.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutHigh.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutMedium.ql
ql/actions/ql/src/Violations Of Best Practice/CodeQL/UnnecessaryUseOfAdvancedConfig.ql

View File

@@ -0,0 +1,23 @@
ql/actions/ql/src/Security/CWE-077/EnvPathInjectionCritical.ql
ql/actions/ql/src/Security/CWE-077/EnvPathInjectionMedium.ql
ql/actions/ql/src/Security/CWE-077/EnvVarInjectionCritical.ql
ql/actions/ql/src/Security/CWE-077/EnvVarInjectionMedium.ql
ql/actions/ql/src/Security/CWE-094/CodeInjectionCritical.ql
ql/actions/ql/src/Security/CWE-094/CodeInjectionMedium.ql
ql/actions/ql/src/Security/CWE-1395/UseOfKnownVulnerableAction.ql
ql/actions/ql/src/Security/CWE-275/MissingActionsPermissions.ql
ql/actions/ql/src/Security/CWE-285/ImproperAccessControl.ql
ql/actions/ql/src/Security/CWE-312/ExcessiveSecretsExposure.ql
ql/actions/ql/src/Security/CWE-312/SecretsInArtifacts.ql
ql/actions/ql/src/Security/CWE-312/UnmaskedSecretExposure.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaCodeInjection.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaDirectCache.ql
ql/actions/ql/src/Security/CWE-349/CachePoisoningViaPoisonableStep.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUCritical.ql
ql/actions/ql/src/Security/CWE-367/UntrustedCheckoutTOCTOUHigh.ql
ql/actions/ql/src/Security/CWE-829/ArtifactPoisoningCritical.ql
ql/actions/ql/src/Security/CWE-829/ArtifactPoisoningMedium.ql
ql/actions/ql/src/Security/CWE-829/UnpinnedActionsTag.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutCritical.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutHigh.ql
ql/actions/ql/src/Security/CWE-829/UntrustedCheckoutMedium.ql

View File

@@ -0,0 +1,11 @@
ql/actions/ql/src/Debug/partial.ql
ql/actions/ql/src/experimental/Security/CWE-074/OutputClobberingHigh.ql
ql/actions/ql/src/experimental/Security/CWE-078/CommandInjectionCritical.ql
ql/actions/ql/src/experimental/Security/CWE-078/CommandInjectionMedium.ql
ql/actions/ql/src/experimental/Security/CWE-088/ArgumentInjectionCritical.ql
ql/actions/ql/src/experimental/Security/CWE-088/ArgumentInjectionMedium.ql
ql/actions/ql/src/experimental/Security/CWE-200/SecretExfiltration.ql
ql/actions/ql/src/experimental/Security/CWE-284/CodeExecutionOnSelfHostedRunner.ql
ql/actions/ql/src/experimental/Security/CWE-829/ArtifactPoisoningPathTraversal.ql
ql/actions/ql/src/experimental/Security/CWE-829/UnversionedImmutableAction.ql
ql/actions/ql/src/experimental/Security/CWE-918/RequestForgery.ql

View File

@@ -0,0 +1,14 @@
import runs_on
import pytest
from query_suites import *
well_known_query_suites = ['actions-code-quality.qls', 'actions-security-and-quality.qls', 'actions-security-extended.qls', 'actions-code-scanning.qls']
@runs_on.posix
@pytest.mark.parametrize("query_suite", well_known_query_suites)
def test(codeql, actions, check_query_suite, query_suite):
check_query_suite(query_suite)
@runs_on.posix
def test_not_included_queries(codeql, actions, check_queries_not_included):
check_queries_not_included('actions', well_known_query_suites)

View File

@@ -0,0 +1,11 @@
class Type extends @type {
string toString() { none() }
}
class Expr extends @expr {
string toString() { none() }
}
from Type decltype, Expr expr, Type basetype, boolean parentheses
where decltypes(decltype, expr, _, basetype, parentheses)
select decltype, expr, basetype, parentheses

View File

@@ -0,0 +1,19 @@
class Type extends @type {
string toString() { none() }
}
predicate derivedType(Type type, string name, int kind, Type type_id) {
derivedtypes(type, name, kind, type_id)
}
predicate typeTransformation(Type type, string name, int kind, Type type_id) {
type_operators(type, _, _, type_id) and
name = "" and
kind = 3 // @type_with_specifiers
}
from Type type, string name, int kind, Type type_id
where
derivedType(type, name, kind, type_id) or
typeTransformation(type, name, kind, type_id)
select type, name, kind, type_id

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,5 @@
description: Support C23 typeof and typeof_unqual
compatibility: backwards
decltypes.rel: run decltypes.qlo
derivedtypes.rel: run derivedtypes.qlo
type_operators.rel: delete

View File

@@ -0,0 +1,5 @@
---
category: feature
---
* New classes `TypeofType`, `TypeofExprType`, and `TypeofTypeType` were introduced, which represent the C23 `typeof` and `typeof_unqual` operators. The `TypeofExprType` class represents the variant taking an expression as its argument. The `TypeofTypeType` class represents the variant taking a type as its argument.
* A new class `IntrinsicTransformedType` was introduced, which represents the type transforming intrinsics supported by clang, gcc, and MSVC.

View File

@@ -0,0 +1,5 @@
extensions:
- addsTo:
pack: codeql/cpp-all
extensible: summaryModel
data: []

View File

@@ -16,6 +16,7 @@ dependencies:
codeql/xml: ${workspace}
dataExtensions:
- ext/*.model.yml
- ext/generated/*.model.yml
- ext/deallocation/*.model.yml
- ext/allocation/*.model.yml
warnOnImplicitThis: true

View File

@@ -88,6 +88,7 @@ class Declaration extends Locatable, @declaration {
*
* See the 3-argument `hasQualifiedName` for examples.
*/
pragma[noinline]
predicate hasQualifiedName(string namespaceQualifier, string baseName) {
this.hasQualifiedName(namespaceQualifier, "", baseName)
}

View File

@@ -176,6 +176,30 @@ private class DecltypeDumpType extends DumpType, Decltype {
}
}
private class TypeofDumpType extends DumpType, TypeofType {
override string getTypeSpecifier() { result = this.getBaseType().(DumpType).getTypeSpecifier() }
override string getDeclaratorPrefix() {
result = this.getBaseType().(DumpType).getDeclaratorPrefix()
}
override string getDeclaratorSuffix() {
result = this.getBaseType().(DumpType).getDeclaratorSuffix()
}
}
private class IntrinsicTransformedDumpType extends DumpType, IntrinsicTransformedType {
override string getTypeSpecifier() { result = this.getBaseType().(DumpType).getTypeSpecifier() }
override string getDeclaratorPrefix() {
result = this.getBaseType().(DumpType).getDeclaratorPrefix()
}
override string getDeclaratorSuffix() {
result = this.getBaseType().(DumpType).getDeclaratorSuffix()
}
}
private class PointerIshDumpType extends DerivedDumpType {
PointerIshDumpType() {
this instanceof PointerType or

View File

@@ -92,8 +92,9 @@ class Type extends Locatable, @type {
/**
* Gets this type after typedefs have been resolved.
*
* The result of this predicate will be the type itself, except in the case of a TypedefType or a Decltype,
* in which case the result will be type which results from (possibly recursively) resolving typedefs.
* The result of this predicate will be the type itself, except in the case of a TypedefType, a Decltype,
* or a TypeofType, in which case the result will be type which results from (possibly recursively)
* resolving typedefs.
*/
pragma[nomagic]
Type getUnderlyingType() { result = this }
@@ -1117,18 +1118,20 @@ class DerivedType extends Type, @derivedtype {
* decltype(a) b;
* ```
*/
class Decltype extends Type, @decltype {
class Decltype extends Type {
Decltype() { decltypes(underlyingElement(this), _, 0, _, _) }
override string getAPrimaryQlClass() { result = "Decltype" }
/**
* The expression whose type is being obtained by this decltype.
* Gets the expression whose type is being obtained by this decltype.
*/
Expr getExpr() { decltypes(underlyingElement(this), unresolveElement(result), _, _) }
Expr getExpr() { decltypes(underlyingElement(this), unresolveElement(result), _, _, _) }
/**
* The type immediately yielded by this decltype.
* Gets the type immediately yielded by this decltype.
*/
Type getBaseType() { decltypes(underlyingElement(this), _, unresolveElement(result), _) }
Type getBaseType() { decltypes(underlyingElement(this), _, _, unresolveElement(result), _) }
/**
* Whether an extra pair of parentheses around the expression would change the semantics of this decltype.
@@ -1142,7 +1145,7 @@ class Decltype extends Type, @decltype {
* ```
* Please consult the C++11 standard for more details.
*/
predicate parenthesesWouldChangeMeaning() { decltypes(underlyingElement(this), _, _, true) }
predicate parenthesesWouldChangeMeaning() { decltypes(underlyingElement(this), _, _, _, true) }
override Type getUnderlyingType() { result = this.getBaseType().getUnderlyingType() }
@@ -1183,6 +1186,215 @@ class Decltype extends Type, @decltype {
}
}
/**
* An instance of the C23 `typeof` or `typeof_unqual` operator. For example:
* ```
* int a;
* typeof(a) b;
* typeof_unqual(const int) b;
* ```
*/
class TypeofType extends Type {
TypeofType() {
decltypes(underlyingElement(this), _, 1, _, _) or
type_operators(underlyingElement(this), _, 0, _)
}
/**
* Gets the type immediately yielded by this typeof.
*/
Type getBaseType() {
decltypes(underlyingElement(this), _, _, unresolveElement(result), _)
or
type_operators(underlyingElement(this), _, _, unresolveElement(result))
}
override Type getUnderlyingType() { result = this.getBaseType().getUnderlyingType() }
override Type stripTopLevelSpecifiers() { result = this.getBaseType().stripTopLevelSpecifiers() }
override Type stripType() { result = this.getBaseType().stripType() }
override Type resolveTypedefs() { result = this.getBaseType().resolveTypedefs() }
override string toString() { result = "typeof(...)" }
override string getName() { none() }
override int getSize() { result = this.getBaseType().getSize() }
override int getAlignment() { result = this.getBaseType().getAlignment() }
override int getPointerIndirectionLevel() {
result = this.getBaseType().getPointerIndirectionLevel()
}
override string explain() {
result = "typeof resulting in {" + this.getBaseType().explain() + "}"
}
override predicate involvesReference() { this.getBaseType().involvesReference() }
override predicate involvesTemplateParameter() { this.getBaseType().involvesTemplateParameter() }
override predicate isDeeplyConst() { this.getBaseType().isDeeplyConst() }
override predicate isDeeplyConstBelow() { this.getBaseType().isDeeplyConstBelow() }
override Specifier internal_getAnAdditionalSpecifier() {
result = this.getBaseType().getASpecifier()
}
}
/**
* An instance of the C23 `typeof` or `typeof_unqual` operator taking an expression
* as its argument. For example:
* ```
* int a;
* typeof(a) b;
* ```
*/
class TypeofExprType extends TypeofType {
TypeofExprType() { decltypes(underlyingElement(this), _, 1, _, _) }
override string getAPrimaryQlClass() { result = "TypeofExprType" }
/**
* Gets the expression whose type is being obtained by this typeof.
*/
Expr getExpr() { decltypes(underlyingElement(this), unresolveElement(result), _, _, _) }
override Location getLocation() { result = this.getExpr().getLocation() }
}
/**
* A type obtained by C23 `typeof` or `typeof_unqual` operator taking a type as its
* argument. For example:
* ```
* typeof_unqual(const int) b;
* ```
*/
class TypeofTypeType extends TypeofType {
TypeofTypeType() { type_operators(underlyingElement(this), _, 0, _) }
/**
* Gets the expression whose type is being obtained by this typeof.
*/
Type getType() { type_operators(underlyingElement(this), unresolveElement(result), _, _) }
override string getAPrimaryQlClass() { result = "TypeofTypeType" }
override string toString() { result = "typeof(...)" }
}
/**
* A type obtained by applying a type transforming intrinsic. For example:
* ```
* __make_unsigned(int) x;
* ```
*/
class IntrinsicTransformedType extends Type {
int intrinsic;
IntrinsicTransformedType() {
type_operators(underlyingElement(this), _, intrinsic, _) and
intrinsic in [1 .. 19]
}
override string getAPrimaryQlClass() { result = "IntrinsicTransformedType" }
override string toString() { result = this.getIntrinsicName() + "(...)" }
/**
* Gets the type immediately yielded by this transformation.
*/
Type getBaseType() { type_operators(underlyingElement(this), _, _, unresolveElement(result)) }
/**
* Gets the type that is transformed.
*/
Type getType() { type_operators(underlyingElement(this), unresolveElement(result), _, _) }
/**
* Gets the name of the intrinsic used to transform the type.
*/
string getIntrinsicName() {
intrinsic = 1 and result = "__underlying_type"
or
intrinsic = 2 and result = "__bases"
or
intrinsic = 3 and result = "__direct_bases"
or
intrinsic = 4 and result = "__add_lvalue_reference"
or
intrinsic = 5 and result = "__add_pointer"
or
intrinsic = 6 and result = "__add_rvalue_reference"
or
intrinsic = 7 and result = "__decay"
or
intrinsic = 8 and result = "__make_signed"
or
intrinsic = 9 and result = "__make_unsigned"
or
intrinsic = 10 and result = "__remove_all_extents"
or
intrinsic = 11 and result = "__remove_const"
or
intrinsic = 12 and result = "__remove_cv"
or
intrinsic = 13 and result = "__remove_cvref"
or
intrinsic = 14 and result = "__remove_extent"
or
intrinsic = 15 and result = "__remove_pointer"
or
intrinsic = 16 and result = "__remove_reference_t"
or
intrinsic = 17 and result = "__remove_restrict"
or
intrinsic = 18 and result = "__remove_volatile"
or
intrinsic = 19 and result = "__remove_reference"
}
override Type getUnderlyingType() { result = this.getBaseType().getUnderlyingType() }
override Type stripTopLevelSpecifiers() { result = this.getBaseType().stripTopLevelSpecifiers() }
override Type stripType() { result = this.getBaseType().stripType() }
override Type resolveTypedefs() { result = this.getBaseType().resolveTypedefs() }
override string getName() { none() }
override int getSize() { result = this.getBaseType().getSize() }
override int getAlignment() { result = this.getBaseType().getAlignment() }
override int getPointerIndirectionLevel() {
result = this.getBaseType().getPointerIndirectionLevel()
}
override string explain() {
result =
"application of " + this.getIntrinsicName() + " resulting in {" + this.getBaseType().explain()
+ "}"
}
override predicate involvesReference() { this.getBaseType().involvesReference() }
override predicate involvesTemplateParameter() { this.getBaseType().involvesTemplateParameter() }
override predicate isDeeplyConst() { this.getBaseType().isDeeplyConst() }
override predicate isDeeplyConstBelow() { this.getBaseType().isDeeplyConstBelow() }
override Specifier internal_getAnAdditionalSpecifier() {
result = this.getBaseType().getASpecifier()
}
}
/**
* A C/C++ pointer type. See 4.9.1.
* ```

View File

@@ -310,6 +310,8 @@ class Expr extends StmtParent, @expr {
or
exists(Decltype d | d.getExpr() = this.getParentWithConversions*())
or
exists(TypeofExprType t | t.getExpr() = this.getParentWithConversions*())
or
exists(ConstexprIfStmt constIf |
constIf.getControllingExpr() = this.getParentWithConversions*()
)

View File

@@ -2011,13 +2011,23 @@ module ExprFlowCached {
localFlowStep(n1, n2)
}
/**
* Holds if `asExpr(n1)` doesn't have a result and `n1` flows to `n2` in a single
* dataflow step.
*
* i.e. this is the transpose of `localStepFromNonExpr`
*/
private predicate localStepFromNonExprR(Node n2, Node n1) {
localStepFromNonExpr(n1, n2)
}
/**
* Holds if `asExpr(n1)` doesn't have a result, `asExpr(n2) = e2` and
* `n2` is the first node reachable from `n1` such that `asExpr(n2)` exists.
*/
pragma[nomagic]
private predicate localStepsToExpr(Node n1, Node n2, Expr e2) {
localStepFromNonExpr*(n1, n2) and
localStepFromNonExprR*(n2, n1) and
e2 = asExprInternal(n2)
}

View File

@@ -815,10 +815,15 @@ private predicate isRelatableMemoryLocation(VariableMemoryLocation vml) {
vml.getStartBitOffset() != Ints::unknown()
}
pragma[noinline]
private int getRank(VirtualVariable vvar, IntValue offset) {
offset = rank[result](IntValue offset_ | isRelevantOffset(vvar, offset_))
}
private predicate isCoveredOffset(Allocation var, int offsetRank, VariableMemoryLocation vml) {
exists(int startRank, int endRank, VirtualVariable vvar |
vml.getStartBitOffset() = rank[startRank](IntValue offset_ | isRelevantOffset(vvar, offset_)) and
vml.getEndBitOffset() = rank[endRank](IntValue offset_ | isRelevantOffset(vvar, offset_)) and
startRank = getRank(vvar, vml.getStartBitOffset()) and
endRank = getRank(vvar, vml.getEndBitOffset()) and
var = vml.getAnAllocation() and
vvar = vml.getVirtualVariable() and
isRelatableMemoryLocation(vml) and

View File

@@ -16,6 +16,10 @@ private predicate isDeeplyConst(Type t) {
or
isDeeplyConst(t.(Decltype).getBaseType())
or
isDeeplyConst(t.(TypeofType).getBaseType())
or
isDeeplyConst(t.(IntrinsicTransformedType).getBaseType())
or
isDeeplyConst(t.(ReferenceType).getBaseType())
or
exists(SpecifiedType specType | specType = t |
@@ -36,6 +40,10 @@ private predicate isDeeplyConstBelow(Type t) {
or
isDeeplyConstBelow(t.(Decltype).getBaseType())
or
isDeeplyConstBelow(t.(TypeofType).getBaseType())
or
isDeeplyConstBelow(t.(IntrinsicTransformedType).getBaseType())
or
isDeeplyConst(t.(PointerType).getBaseType())
or
isDeeplyConst(t.(ReferenceType).getBaseType())

View File

@@ -117,27 +117,29 @@ class TranslatedStaticStorageDurationVarInit extends TranslatedRootElement,
* directly accessed by the function.
*/
final predicate hasUserVariable(Variable varUsed, CppType type) {
(
(
varUsed instanceof GlobalOrNamespaceVariable
or
varUsed instanceof StaticLocalVariable
or
varUsed instanceof MemberVariable and not varUsed instanceof Field
) and
exists(VariableAccess access |
access.getTarget() = varUsed and
getEnclosingVariable(access) = var
)
or
var = varUsed
or
varUsed.(LocalScopeVariable).getEnclosingElement*() = var
or
varUsed.(Parameter).getCatchBlock().getEnclosingElement*() = var
) and
this.hasUserVariable1(varUsed) and
type = getTypeForPRValue(getVariableType(varUsed))
}
private predicate hasUserVariable1(Variable varUsed) {
(
varUsed instanceof GlobalOrNamespaceVariable
or
varUsed instanceof StaticLocalVariable
or
varUsed instanceof MemberVariable and not varUsed instanceof Field
) and
exists(VariableAccess access |
access.getTarget() = varUsed and
getEnclosingVariable(access) = var
)
or
var = varUsed
or
varUsed.(LocalScopeVariable).getEnclosingElement*() = var
or
varUsed.(Parameter).getCatchBlock().getEnclosingElement*() = var
}
}
TranslatedStaticStorageDurationVarInit getTranslatedVarInit(Variable var) { result.getAst() = var }

View File

@@ -743,15 +743,17 @@ typedefbase(
);
/**
* An instance of the C++11 `decltype` operator. For example:
* An instance of the C++11 `decltype` operator or C23 `typeof`/`typeof_unqual`
* operator taking an expression as its argument. For example:
* ```
* int a;
* decltype(1+a) b;
* typeof(1+a) c;
* ```
* Here `expr` is `1+a`.
*
* Sometimes an additional pair of parentheses around the expression
* would change the semantics of this decltype, e.g.
* changes the semantics of the decltype, e.g.
* ```
* struct A { double x; };
* const A* a = new A();
@@ -761,14 +763,55 @@ typedefbase(
* (Please consult the C++11 standard for more details).
* `parentheses_would_change_meaning` is `true` iff that is the case.
*/
/*
case @decltype.kind of
| 0 = @decltype
| 1 = @typeof // The frontend does not differentiate between typeof and typeof_unqual
;
*/
#keyset[id, expr]
decltypes(
int id: @decltype,
int expr: @expr ref,
int kind: int ref,
int base_type: @type ref,
boolean parentheses_would_change_meaning: boolean ref
);
/*
case @type_operator.kind of
| 0 = @typeof // The frontend does not differentiate between typeof and typeof_unqual
| 1 = @underlying_type
| 2 = @bases
| 3 = @direct_bases
| 4 = @add_lvalue_reference
| 5 = @add_pointer
| 6 = @add_rvalue_reference
| 7 = @decay
| 8 = @make_signed
| 9 = @make_unsigned
| 10 = @remove_all_extents
| 11 = @remove_const
| 12 = @remove_cv
| 13 = @remove_cvref
| 14 = @remove_extent
| 15 = @remove_pointer
| 16 = @remove_reference_t
| 17 = @remove_restrict
| 18 = @remove_volatile
| 19 = @remove_reference
;
*/
type_operators(
unique int id: @type_operator,
int arg_type: @type ref,
int kind: int ref,
int base_type: @type ref
)
/*
case @usertype.kind of
| 0 = @unknown_usertype
@@ -1103,10 +1146,10 @@ stmtattributes(
@type = @builtintype
| @derivedtype
| @usertype
/* TODO | @fixedpointtype */
| @routinetype
| @ptrtomember
| @decltype;
| @decltype
| @type_operator;
unspecifiedtype(
unique int type_id: @type ref,

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,11 @@
class Type extends @type {
string toString() { none() }
}
class Expr extends @expr {
string toString() { none() }
}
from Type decltype, Expr expr, Type basetype, boolean parentheses
where decltypes(decltype, expr, basetype, parentheses)
select decltype, expr, 0, basetype, parentheses

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,3 @@
description: Support C23 typeof and typeof_unqual
compatibility: partial
decltypes.rel: run decltypes.qlo

View File

@@ -179,6 +179,7 @@ predicate overflows(MulExpr me, Type t) {
from MulExpr me, Type t1, Type t2
where
not any(Compilation c).buildModeNone() and
t1 = me.getType().getUnderlyingType() and
t2 = me.getConversion().getType().getUnderlyingType() and
t1.getSize() < t2.getSize() and

View File

@@ -154,6 +154,7 @@ int sizeof_IntType() { exists(IntType it | result = it.getSize()) }
from FormattingFunctionCall ffc, int n, Expr arg, Type expected, Type actual
where
not any(Compilation c).buildModeNone() and
(
formattingFunctionCallExpectedType(ffc, n, expected) and
formattingFunctionCallActualType(ffc, n, arg, actual) and

View File

@@ -47,11 +47,17 @@ Type stripType(Type t) {
or
result = stripType(t.(Decltype).getBaseType())
or
result = stripType(t.(TypeofType).getBaseType())
or
result = stripType(t.(IntrinsicTransformedType).getBaseType())
or
not t instanceof TypedefType and
not t instanceof ArrayType and
not t instanceof ReferenceType and
not t instanceof SpecifiedType and
not t instanceof Decltype and
not t instanceof TypeofType and
not t instanceof IntrinsicTransformedType and
result = t
}

View File

@@ -38,6 +38,7 @@ predicate isCompiledAsC(File f) {
from FunctionDeclarationEntry fdeIm, FunctionCall fc
where
not any(Compilation c).buildModeNone() and
isCompiledAsC(fdeIm.getFile()) and
not isFromMacroDefinition(fc) and
fdeIm.isImplicit() and

View File

@@ -51,6 +51,7 @@ int getComparisonSizeAdjustment(Expr e) {
from Loop l, RelationalOperation rel, VariableAccess small, Expr large
where
not any(Compilation c).buildModeNone() and
small = rel.getLesserOperand() and
large = rel.getGreaterOperand() and
rel = l.getCondition().getAChild*() and

View File

@@ -24,10 +24,12 @@ private predicate isCharSzPtrExpr(Expr e) {
from Expr sizeofExpr, Expr e
where
not any(Compilation c).buildModeNone() and
// If we see an addWithSizeof then we expect the type of
// the pointer expression to be `char*` or `void*`. Otherwise it
// is probably a mistake.
addWithSizeof(e, sizeofExpr, _) and not isCharSzPtrExpr(e)
addWithSizeof(e, sizeofExpr, _) and
not isCharSzPtrExpr(e)
select sizeofExpr,
"Suspicious sizeof offset in a pointer arithmetic expression. The type of the pointer is $@.",
e.getFullyConverted().getType() as t, t.toString()

View File

@@ -44,6 +44,8 @@ class UsingWhileAfterWhile extends WhileStmt {
}
}
/**
* Using arithmetic in a condition.
*/
@@ -55,15 +57,15 @@ class UsingArithmeticInComparison extends BinaryArithmeticOperation {
*/
UsingArithmeticInComparison() {
this.getParent*() instanceof IfStmt and
not this.getAChild*().isConstant() and
not this.getParent*() instanceof Call and
not this.getParent*() instanceof AssignExpr and
not this.getParent*() instanceof ArrayExpr and
not this.getParent*() instanceof RemExpr and
not this.getParent*() instanceof AssignBitwiseOperation and
not this.getParent*() instanceof AssignArithmeticOperation and
not this.getParent*() instanceof EqualityOperation and
not this.getParent*() instanceof RelationalOperation
not (this.getAChild*().isConstant() or
this.getParent*() instanceof Call or
this.getParent*() instanceof AssignExpr or
this.getParent*() instanceof ArrayExpr or
this.getParent*() instanceof RemExpr or
this.getParent*() instanceof AssignBitwiseOperation or
this.getParent*() instanceof AssignArithmeticOperation or
this.getParent*() instanceof EqualityOperation or
this.getParent*() instanceof RelationalOperation)
}
/** Holds when the expression is inside the loop body. */

View File

@@ -0,0 +1,13 @@
/**
* @name Capture content based summary models.
* @description Finds applicable content based summary models to be used by other queries.
* @kind diagnostic
* @id cpp/utils/modelgenerator/contentbased-summary-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSummaryTargetApi api, string flow
where flow = ContentSensitive::captureFlow(api, _)
select flow order by flow

View File

@@ -0,0 +1,13 @@
/**
* @name Capture mixed neutral models.
* @description Finds neutral models to be used by other queries.
* @kind diagnostic
* @id cpp/utils/modelgenerator/mixed-neutral-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSummaryTargetApi api, string noflow
where noflow = captureMixedNeutral(api)
select noflow order by noflow

View File

@@ -0,0 +1,13 @@
/**
* @name Capture mixed summary models.
* @description Finds applicable summary models to be used by other queries.
* @kind diagnostic
* @id cpp/utils/modelgenerator/mixed-summary-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSummaryTargetApi api, string flow
where flow = captureMixedFlow(api, _)
select flow order by flow

View File

@@ -0,0 +1,13 @@
/**
* @name Capture neutral models.
* @description Finds neutral models to be used by other queries.
* @kind diagnostic
* @id cpp/utils/modelgenerator/neutral-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSummaryTargetApi api, string noflow
where noflow = captureNoFlow(api)
select noflow order by noflow

View File

@@ -0,0 +1,13 @@
/**
* @name Capture sink models.
* @description Finds public methods that act as sinks as they flow into a known sink.
* @kind diagnostic
* @id cpp/utils/modelgenerator/sink-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSinkTargetApi api, string sink
where sink = captureSink(api)
select sink order by sink

View File

@@ -0,0 +1,13 @@
/**
* @name Capture source models.
* @description Finds APIs that act as sources as they expose already known sources.
* @kind diagnostic
* @id cpp/utils/modelgenerator/source-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSourceTargetApi api, string source
where source = captureSource(api)
select source order by source

View File

@@ -0,0 +1,13 @@
/**
* @name Capture summary models.
* @description Finds applicable summary models to be used by other queries.
* @kind diagnostic
* @id cpp/utils/modelgenerator/summary-models
* @tags modelgenerator
*/
import internal.CaptureModels
from DataFlowSummaryTargetApi api, string flow
where flow = captureFlow(api)
select flow order by flow

View File

@@ -0,0 +1,15 @@
#!/usr/bin/python3
import sys
import os.path
import subprocess
# Add Model as Data script directory to sys.path.
gitroot = subprocess.check_output(["git", "rev-parse", "--show-toplevel"]).decode("utf-8").strip()
madpath = os.path.join(gitroot, "misc/scripts/models-as-data/")
sys.path.append(madpath)
import generate_flow_model as model
language = "cpp"
model.Generator.make(language).run()

View File

@@ -0,0 +1,404 @@
/**
* Provides predicates related to capturing summary models of the Standard or a 3rd party library.
*/
private import cpp
private import semmle.code.cpp.ir.IR
private import semmle.code.cpp.dataflow.ExternalFlow as ExternalFlow
private import semmle.code.cpp.ir.dataflow.internal.DataFlowImplCommon as DataFlowImplCommon
private import semmle.code.cpp.ir.dataflow.internal.DataFlowImplSpecific
private import semmle.code.cpp.ir.dataflow.internal.DataFlowPrivate as DataFlowPrivate
private import semmle.code.cpp.dataflow.internal.FlowSummaryImpl as FlowSummaryImpl
private import semmle.code.cpp.ir.dataflow.internal.TaintTrackingImplSpecific
private import semmle.code.cpp.dataflow.new.TaintTracking
private import codeql.mad.modelgenerator.internal.ModelGeneratorImpl
module ModelGeneratorInput implements ModelGeneratorInputSig<Location, CppDataFlow> {
class Type = DataFlowPrivate::DataFlowType;
// Note: This also includes `this`
class Parameter = DataFlow::ParameterNode;
class Callable = Declaration;
class NodeExtended extends DataFlow::Node {
Callable getAsExprEnclosingCallable() { result = this.asExpr().getEnclosingDeclaration() }
}
Parameter asParameter(NodeExtended n) { result = n }
Callable getEnclosingCallable(NodeExtended n) {
result = n.getEnclosingCallable().asSourceCallable()
}
Callable getAsExprEnclosingCallable(NodeExtended n) {
result = n.asExpr().getEnclosingDeclaration()
}
/** Gets `api` if it is relevant. */
private Callable liftedImpl(Callable api) { result = api and relevant(api) }
private predicate hasManualSummaryModel(Callable api) {
api = any(FlowSummaryImpl::Public::SummarizedCallable sc | sc.applyManualModel()) or
api = any(FlowSummaryImpl::Public::NeutralSummaryCallable sc | sc.hasManualModel())
}
private predicate hasManualSourceModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSourceCallable sc | sc.hasManualModel())
}
private predicate hasManualSinkModel(Callable api) {
api = any(FlowSummaryImpl::Public::NeutralSinkCallable sc | sc.hasManualModel())
}
/**
* Holds if `f` is a "private" function.
*
* A "private" function does not contribute any models as it is assumed
* to be an implementation detail of some other "public" function for which
* we will generate a summary.
*/
private predicate isPrivateOrProtected(Function f) {
f.getNamespace().getParentNamespace*().isAnonymous()
or
exists(MemberFunction mf | mf = f |
mf.isPrivate()
or
mf.isProtected()
)
or
f.isStatic()
}
private predicate isUninterestingForModels(Callable api) {
// Note: This also makes all global/static-local variables
// not relevant (which is good!)
not api.(Function).hasDefinition()
or
isPrivateOrProtected(api)
or
api instanceof Destructor
or
api = any(LambdaExpression lambda).getLambdaFunction()
or
api.isFromUninstantiatedTemplate(_)
}
private predicate relevant(Callable api) {
api.fromSource() and
not isUninterestingForModels(api)
}
class SummaryTargetApi extends Callable {
private Callable lift;
SummaryTargetApi() {
lift = liftedImpl(this) and
not hasManualSummaryModel(lift)
}
Callable lift() { result = lift }
predicate isRelevant() {
relevant(this) and
not hasManualSummaryModel(this)
}
}
class SourceOrSinkTargetApi extends Callable {
SourceOrSinkTargetApi() { relevant(this) }
}
class SinkTargetApi extends SourceOrSinkTargetApi {
SinkTargetApi() { not hasManualSinkModel(this) }
}
class SourceTargetApi extends SourceOrSinkTargetApi {
SourceTargetApi() { not hasManualSourceModel(this) }
}
class InstanceParameterNode extends DataFlow::ParameterNode {
InstanceParameterNode() {
DataFlowPrivate::nodeHasInstruction(this,
any(InitializeParameterInstruction i | i.hasIndex(-1)), 1)
}
}
private predicate isFinalMemberFunction(MemberFunction mf) {
mf.isFinal()
or
mf.getDeclaringType().isFinal()
}
/**
* Holds if the summary generated for `c` should also apply to overrides
* of `c`.
*/
private string isExtensible(Callable c) {
if isFinalMemberFunction(c) then result = "false" else result = "true"
}
/**
* Gets the string representing the list of template parameters declared
* by `template`.
*
* `template` must either be:
* - An uninstantiated template, or
* - A declaration that is not from a template instantiation.
*/
private string templateParams(Declaration template) {
exists(string params |
params =
concat(int i |
|
template.getTemplateArgument(i).(TypeTemplateParameter).getName(), "," order by i
)
|
if params = "" then result = "" else result = "<" + params + ">"
)
}
/**
* Gets the string representing the list of parameters declared
* by `functionTemplate`.
*
* `functionTemplate` must either be:
* - An uninstantiated template, or
* - A declaration that is not from a template instantiation.
*/
private string params(Function functionTemplate) {
exists(string params |
params =
concat(int i |
|
ExternalFlow::getParameterTypeWithoutTemplateArguments(functionTemplate, i, true), ","
order by
i
) and
result = "(" + params + ")"
)
}
/**
* Holds if the callable `c` is:
* - In the namespace represented by `namespace`, and
* - Has a declaring type represented by `type`, and
* - Has the name `name`, and
* - Has a list of parameters represented by `params`
*
* This is the predicate that computes the columns that it put into the MaD
* row for `callable`.
*/
private predicate qualifiedName(
Callable callable, string namespace, string type, string name, string params
) {
exists(
Function functionTemplate, string typeWithoutTemplateArgs, string nameWithoutTemplateArgs
|
functionTemplate = ExternalFlow::getFullyTemplatedFunction(callable) and
functionTemplate.hasQualifiedName(namespace, typeWithoutTemplateArgs, nameWithoutTemplateArgs) and
nameWithoutTemplateArgs = functionTemplate.getName() and
name = nameWithoutTemplateArgs + templateParams(functionTemplate) and
params = params(functionTemplate)
|
exists(Class classTemplate |
classTemplate = functionTemplate.getDeclaringType() and
type = typeWithoutTemplateArgs + templateParams(classTemplate)
)
or
not exists(functionTemplate.getDeclaringType()) and
type = ""
)
}
predicate isRelevantType(Type t) { any() }
Type getUnderlyingContentType(DataFlow::ContentSet c) {
result = c.(DataFlow::FieldContent).getField().getUnspecifiedType() or
result = c.(DataFlow::UnionContent).getUnion().getUnspecifiedType()
}
string qualifierString() { result = "Argument[-1]" }
private predicate parameterContentAccessImpl(Parameter p, string argument) {
exists(int indirectionIndex, int argumentIndex, DataFlowPrivate::Position pos |
p.isSourceParameterOf(_, pos) and
pos.getArgumentIndex() = argumentIndex and
argumentIndex != -1 and // handled elsewhere
pos.getIndirectionIndex() = indirectionIndex
|
indirectionIndex = 0 and
argument = "Argument[" + argumentIndex + "]"
or
indirectionIndex > 0 and
argument = "Argument[" + DataFlow::repeatStars(indirectionIndex) + argumentIndex + "]"
)
}
string parameterAccess(Parameter p) { parameterContentAccessImpl(p, result) }
string parameterContentAccess(Parameter p) { parameterContentAccessImpl(p, result) }
bindingset[c]
string paramReturnNodeAsOutput(Callable c, DataFlowPrivate::Position pos) {
exists(Parameter p |
p.isSourceParameterOf(c, pos) and
result = parameterAccess(p)
)
or
pos.getArgumentIndex() = -1 and
result = qualifierString() and
pos.getIndirectionIndex() = 1
}
bindingset[c]
string paramReturnNodeAsContentOutput(Callable c, DataFlowPrivate::ParameterPosition pos) {
result = paramReturnNodeAsOutput(c, pos)
}
pragma[nomagic]
Callable returnNodeEnclosingCallable(DataFlow::Node ret) {
result = DataFlowImplCommon::getNodeEnclosingCallable(ret).asSourceCallable()
}
/** Holds if this instance access is to an enclosing instance of type `t`. */
pragma[nomagic]
private predicate isEnclosingInstanceAccess(DataFlowPrivate::ReturnNode n, Class t) {
n.getKind().isIndirectReturn(-1) and
t = n.getType().stripType() and
t != n.getEnclosingCallable().asSourceCallable().(Function).getDeclaringType()
}
pragma[nomagic]
predicate isOwnInstanceAccessNode(DataFlowPrivate::ReturnNode node) {
node.getKind().isIndirectReturn(-1) and
not isEnclosingInstanceAccess(node, _)
}
predicate sinkModelSanitizer(DataFlow::Node node) { none() }
predicate apiSource(DataFlow::Node source) {
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1)
or
source instanceof DataFlow::ParameterNode
}
string getInputArgument(DataFlow::Node source) {
exists(DataFlowPrivate::Position pos, int argumentIndex, int indirectionIndex |
source.(DataFlow::ParameterNode).isParameterOf(_, pos) and
argumentIndex = pos.getArgumentIndex() and
indirectionIndex = pos.getIndirectionIndex() and
result = "Argument[" + DataFlow::repeatStars(indirectionIndex) + argumentIndex + "]"
)
or
DataFlowPrivate::nodeHasOperand(source, any(DataFlow::FieldAddress fa), 1) and
result = qualifierString()
}
string getReturnValueString(DataFlowPrivate::ReturnKind k) {
k.isNormalReturn() and
exists(int indirectionIndex | indirectionIndex = k.getIndirectionIndex() |
indirectionIndex = 0 and
result = "ReturnValue"
or
indirectionIndex > 0 and
result = "ReturnValue[" + DataFlow::repeatStars(indirectionIndex) + "]"
)
}
predicate irrelevantSourceSinkApi(Callable source, SourceTargetApi api) { none() }
bindingset[kind]
predicate isRelevantSourceKind(string kind) { any() }
bindingset[kind]
predicate isRelevantSinkKind(string kind) { any() }
predicate containerContent(DataFlow::ContentSet cs) { cs instanceof DataFlow::ElementContent }
predicate isAdditionalContentFlowStep(DataFlow::Node node1, DataFlow::Node node2) {
TaintTracking::defaultAdditionalTaintStep(node1, node2, _) and
not exists(DataFlow::Content f |
DataFlowPrivate::readStep(node1, f, node2) and containerContent(f)
)
}
predicate isField(DataFlow::ContentSet cs) {
exists(DataFlow::Content c | cs.isSingleton(c) |
c instanceof DataFlow::FieldContent or
c instanceof DataFlow::UnionContent
)
}
predicate isCallback(DataFlow::ContentSet c) { none() }
string getSyntheticName(DataFlow::ContentSet c) {
exists(Field f |
not f.isPublic() and
f = c.(DataFlow::FieldContent).getField() and
result = f.getName()
)
}
string printContent(DataFlow::ContentSet c) {
exists(int indirectionIndex, string name, string kind |
exists(DataFlow::UnionContent uc |
c.isSingleton(uc) and
name = uc.getUnion().getName() and
indirectionIndex = uc.getIndirectionIndex() and
// Note: We don't actually support the union string in MaD, but we should do that eventually
kind = "Union["
)
or
exists(DataFlow::FieldContent fc |
c.isSingleton(fc) and
name = fc.getField().getName() and
indirectionIndex = fc.getIndirectionIndex() and
kind = "Field["
)
|
result = kind + DataFlow::repeatStars(indirectionIndex) + name + "]"
)
or
exists(DataFlow::ElementContent ec |
c.isSingleton(ec) and
result = "Element[" + ec.getIndirectionIndex() + "]"
)
}
predicate isUninterestingForDataFlowModels(Callable api) { none() }
predicate isUninterestingForHeuristicDataFlowModels(Callable api) {
isUninterestingForDataFlowModels(api)
}
string partialModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and result = isExtensible(api) // extensible
or
i = 3 and qualifiedName(api, _, _, result, _) // name
or
i = 4 and qualifiedName(api, _, _, _, result) // parameters
or
i = 5 and result = "" and exists(api) // ext
}
string partialNeutralModelRow(Callable api, int i) {
i = 0 and qualifiedName(api, result, _, _, _) // namespace
or
i = 1 and qualifiedName(api, _, result, _, _) // type
or
i = 2 and qualifiedName(api, _, _, result, _) // name
or
i = 3 and qualifiedName(api, _, _, _, result) // parameters
}
predicate sourceNode = ExternalFlow::sourceNode/2;
predicate sinkNode = ExternalFlow::sinkNode/2;
}
import MakeModelGenerator<Location, CppDataFlow, CppTaintTracking, ModelGeneratorInput>

View File

@@ -0,0 +1,13 @@
private import cpp as Cpp
private import codeql.mad.modelgenerator.internal.ModelPrinting
private import CaptureModels::ModelGeneratorInput as ModelGeneratorInput
private module ModelPrintingLang implements ModelPrintingLangSig {
class Callable = Cpp::Declaration;
predicate partialModelRow = ModelGeneratorInput::partialModelRow/2;
predicate partialNeutralModelRow = ModelGeneratorInput::partialNeutralModelRow/2;
}
import ModelPrintingImpl<ModelPrintingLang>

View File

@@ -0,0 +1,2 @@
unexpectedModel
expectedModel

View File

@@ -0,0 +1,6 @@
extensions:
- addsTo:
pack: codeql/cpp-all
extensible: summaryModel
data:
- [ "models", "ManuallyModelled", False, "hasSummary", "(void *)", "", "Argument[0]", "ReturnValue", "value", "manual"]

View File

@@ -0,0 +1,11 @@
import cpp
import utils.modelgenerator.internal.CaptureModels
import InlineModelsAsDataTest
module InlineMadTestConfig implements InlineMadTestConfigSig {
string getCapturedModel(MadRelevantFunction c) { result = ContentSensitive::captureFlow(c, _) }
string getKind() { result = "contentbased-summary" }
}
import InlineMadTest<InlineMadTestConfig>

View File

@@ -0,0 +1,2 @@
unexpectedModel
expectedModel

View File

@@ -0,0 +1,6 @@
extensions:
- addsTo:
pack: codeql/cpp-all
extensible: summaryModel
data:
- [ "Models", "ManuallyModelled", False, "hasSummary", "(void *)", "", "Argument[0]", "ReturnValue", "value", "manual"]

View File

@@ -0,0 +1,11 @@
import cpp
import utils.modelgenerator.internal.CaptureModels
import InlineModelsAsDataTest
module InlineMadTestConfig implements InlineMadTestConfigSig {
string getCapturedModel(MadRelevantFunction c) { result = captureFlow(c) }
string getKind() { result = "summary" }
}
import InlineMadTest<InlineMadTestConfig>

View File

@@ -0,0 +1,34 @@
private import cpp
private import codeql.mad.test.InlineMadTest
class MadRelevantFunction extends Function {
MadRelevantFunction() { not this.isFromUninstantiatedTemplate(_) }
}
private module InlineMadTestLang implements InlineMadTestLangSig {
class Callable = MadRelevantFunction;
/**
* Holds if `c` is the closest `Callable` that succeeds `comment` in the file.
*/
private predicate hasClosestCallable(CppStyleComment comment, Callable c) {
c =
min(Callable cand, int dist |
// This has no good join order, but should hopefully be good enough for tests.
cand.getFile() = comment.getFile() and
dist = cand.getLocation().getStartLine() - comment.getLocation().getStartLine() and
dist > 0
|
cand order by dist
)
}
string getComment(Callable c) {
exists(CppStyleComment comment |
hasClosestCallable(comment, c) and
result = comment.getContents().suffix(2)
)
}
}
import InlineMadTestImpl<InlineMadTestLang>

View File

@@ -0,0 +1,201 @@
using size_t = decltype(sizeof(int));
size_t strlen(const char* str);
char* strcpy(char* dest, const char* src);
namespace Models {
struct BasicFlow {
int* tainted;
//No model as destructors are excluded from model generation.
~BasicFlow() = default;
//summary=Models;BasicFlow;true;returnThis;(int *);;Argument[-1];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnThis;(int *);;Argument[-1];ReturnValue[*];value;dfc-generated
BasicFlow* returnThis(int* input) {
return this;
}
//summary=Models;BasicFlow;true;returnParam0;(int *,int *);;Argument[0];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnParam0;(int *,int *);;Argument[*0];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnParam0;(int *,int *);;Argument[0];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnParam0;(int *,int *);;Argument[*0];ReturnValue[*];value;dfc-generated
int* returnParam0(int* input0, int* input1) {
return input0;
}
//summary=Models;BasicFlow;true;returnParam1;(int *,int *);;Argument[1];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnParam1;(int *,int *);;Argument[*1];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnParam1;(int *,int *);;Argument[1];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnParam1;(int *,int *);;Argument[*1];ReturnValue[*];value;dfc-generated
int* returnParam1(int* input0, int* input1) {
return input1;
}
//summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[1];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[*1];ReturnValue[*];taint;df-generated
//summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[2];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[*2];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[1];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[*1];ReturnValue[*];value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[2];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnParamMultiple;(bool,int *,int *);;Argument[*2];ReturnValue[*];value;dfc-generated
int* returnParamMultiple(bool b, int* input0, int* input1) {
return b ? input0 : input1;
}
//summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[0];Argument[*1];taint;df-generated
//summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[0];ReturnValue[*];taint;df-generated
//summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[*0];ReturnValue[*];taint;df-generated
//summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[1];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[*0];Argument[*1];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[0];Argument[*1];taint;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[0];ReturnValue[*];taint;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[*0];ReturnValue[*];value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[1];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnSubstring;(const char *,char *);;Argument[*0];Argument[*1];value;dfc-generated
char* returnSubstring(const char* source, char* dest) {
return strcpy(dest, source + 1);
}
//summary=Models;BasicFlow;true;setField;(int *);;Argument[0];Argument[-1];taint;df-generated
//summary=Models;BasicFlow;true;setField;(int *);;Argument[*0];Argument[-1];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;setField;(int *);;Argument[0];Argument[-1].Field[*tainted];value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;setField;(int *);;Argument[*0];Argument[-1].Field[**tainted];value;dfc-generated
void setField(int* s) {
tainted = s;
}
//summary=Models;BasicFlow;true;returnField;();;Argument[-1];ReturnValue;taint;df-generated
//summary=Models;BasicFlow;true;returnField;();;Argument[-1];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;BasicFlow;true;returnField;();;Argument[-1].Field[*tainted];ReturnValue;value;dfc-generated
//contentbased-summary=Models;BasicFlow;true;returnField;();;Argument[-1].Field[**tainted];ReturnValue[*];value;dfc-generated
int* returnField() {
return tainted;
}
};
template<typename T>
struct TemplatedFlow {
T tainted;
//summary=Models;TemplatedFlow<T>;true;template_returnThis;(T);;Argument[-1];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;template_returnThis;(T);;Argument[-1];ReturnValue[*];value;dfc-generated
TemplatedFlow<T>* template_returnThis(T input) {
return this;
}
//summary=Models;TemplatedFlow<T>;true;template_returnParam0;(T *,T *);;Argument[0];ReturnValue;taint;df-generated
//summary=Models;TemplatedFlow<T>;true;template_returnParam0;(T *,T *);;Argument[*0];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;template_returnParam0;(T *,T *);;Argument[0];ReturnValue;value;dfc-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;template_returnParam0;(T *,T *);;Argument[*0];ReturnValue[*];value;dfc-generated
T* template_returnParam0(T* input0, T* input1) {
return input0;
}
//summary=Models;TemplatedFlow<T>;true;template_setField;(T);;Argument[0];Argument[-1];taint;df-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;template_setField;(T);;Argument[0];Argument[-1].Field[*tainted];value;dfc-generated
void template_setField(T s) {
tainted = s;
}
//summary=Models;TemplatedFlow<T>;true;template_returnField;();;Argument[-1];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;template_returnField;();;Argument[-1].Field[*tainted];ReturnValue[*];value;dfc-generated
T& template_returnField() {
return tainted;
}
//summary=Models;TemplatedFlow<T>;true;templated_function<U>;(U *,T *);;Argument[0];ReturnValue;taint;df-generated
//summary=Models;TemplatedFlow<T>;true;templated_function<U>;(U *,T *);;Argument[*0];ReturnValue[*];taint;df-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;templated_function<U>;(U *,T *);;Argument[0];ReturnValue;value;dfc-generated
//contentbased-summary=Models;TemplatedFlow<T>;true;templated_function<U>;(U *,T *);;Argument[*0];ReturnValue[*];value;dfc-generated
template<typename U>
U* templated_function(U* u, T* t) {
return u;
}
};
void test_templated_flow() {
// Ensure that we have an instantiation of the templated class
TemplatedFlow<int> intFlow;
intFlow.template_returnThis(0);
intFlow.template_returnParam0(nullptr, nullptr);
intFlow.template_setField(0);
intFlow.template_returnField();
intFlow.templated_function<int>(nullptr, nullptr);
}
}
//summary=;;true;toplevel_function;(int *);;Argument[0];ReturnValue;taint;df-generated
//summary=;;true;toplevel_function;(int *);;Argument[*0];ReturnValue;taint;df-generated
//contentbased-summary=;;true;toplevel_function;(int *);;Argument[0];ReturnValue;taint;dfc-generated
//contentbased-summary=;;true;toplevel_function;(int *);;Argument[*0];ReturnValue;value;dfc-generated
int toplevel_function(int* p) {
return *p;
}
//No model as static functions are excluded from model generation.
static int static_toplevel_function(int* p) {
return *p;
}
struct NonFinalStruct {
//summary=;NonFinalStruct;true;public_not_final_member_function;(int);;Argument[0];ReturnValue;taint;df-generated
//contentbased-summary=;NonFinalStruct;true;public_not_final_member_function;(int);;Argument[0];ReturnValue;value;dfc-generated
virtual int public_not_final_member_function(int x) {
return x;
}
//summary=;NonFinalStruct;false;public_final_member_function;(int);;Argument[0];ReturnValue;taint;df-generated
//contentbased-summary=;NonFinalStruct;false;public_final_member_function;(int);;Argument[0];ReturnValue;value;dfc-generated
virtual int public_final_member_function(int x) final {
return x;
}
private:
//No model as private members are excluded from model generation.
int private_member_function(int x) {
return x;
}
protected:
//No model as protected members are excluded from model generation.
int protected_member_function(int x) {
return x;
}
};
struct FinalStruct final {
//summary=;FinalStruct;false;public_not_final_member_function_2;(int);;Argument[0];ReturnValue;taint;df-generated
//contentbased-summary=;FinalStruct;false;public_not_final_member_function_2;(int);;Argument[0];ReturnValue;value;dfc-generated
virtual int public_not_final_member_function_2(int x) {
return x;
}
//summary=;FinalStruct;false;public_final_member_function_2;(int);;Argument[0];ReturnValue;taint;df-generated
//contentbased-summary=;FinalStruct;false;public_final_member_function_2;(int);;Argument[0];ReturnValue;value;dfc-generated
virtual int public_final_member_function_2(int x) final {
return x;
}
};
union U {
int x, y;
};
//summary=;;true;get_x_from_union;(U *);;Argument[0];ReturnValue;taint;df-generated
//summary=;;true;get_x_from_union;(U *);;Argument[*0];ReturnValue;taint;df-generated
//contentbased-summary=;;true;get_x_from_union;(U *);;Argument[0];ReturnValue;taint;dfc-generated
//contentbased-summary=;;true;get_x_from_union;(U *);;Argument[*0].Union[*U];ReturnValue;value;dfc-generated
int get_x_from_union(U* u) {
return u->x;
}
//summary=;;true;set_x_in_union;(U *,int);;Argument[1];Argument[*0];taint;df-generated
//contentbased-summary=;;true;set_x_in_union;(U *,int);;Argument[1];Argument[*0].Union[*U];value;dfc-generated
void set_x_in_union(U* u, int x) {
u->x = x;
}

View File

@@ -1,5 +1,7 @@
| cpp.cpp:3:5:3:51 | declaration | 0 | cpp.cpp:3:19:3:24 | twisty |
| cpp.cpp:3:5:3:51 | declaration | 0 | cpp.cpp:3:43:3:48 | twisty |
| cpp.cpp:3:15:3:27 | declaration | 0 | cpp.cpp:3:19:3:24 | twisty |
| cpp.cpp:3:15:3:27 | declaration | 0 | cpp.cpp:3:43:3:48 | twisty |
| cpp.cpp:5:5:5:62 | declaration | 0 | cpp.cpp:5:61:5:61 | i |
| cpp.cpp:5:38:5:51 | declaration | 0 | cpp.cpp:5:44:5:44 | t |
| declstmt.c:7:5:7:19 | declaration | 0 | declstmt.c:7:9:7:12 | fun1 |

View File

@@ -1,4 +1,5 @@
| cpp.cpp:3:5:3:51 | declaration | 0 | cpp.cpp:3:43:3:48 | declaration of twisty |
| cpp.cpp:3:15:3:27 | declaration | 0 | cpp.cpp:3:19:3:24 | declaration of twisty |
| cpp.cpp:5:5:5:62 | declaration | 0 | cpp.cpp:5:61:5:61 | definition of i |
| cpp.cpp:5:38:5:51 | declaration | 0 | cpp.cpp:5:44:5:44 | declaration of t |
| declstmt.c:7:5:7:19 | declaration | 0 | declstmt.c:7:9:7:12 | definition of fun1 |

View File

@@ -1,2 +1,3 @@
| file://:0:0:0:0 | 0 | file://:0:0:0:0 | int |
| test.c:7:20:7:21 | E | file://:0:0:0:0 | int |
| test.c:7:14:7:14 | E | file://:0:0:0:0 | int |
| test.c:7:20:7:21 | E | test.c:7:14:7:14 | typeof(...) |

View File

@@ -8,7 +8,10 @@ uniqueEnclosingCallable
| misc.c:210:24:210:24 | 0 | Node should have one enclosing callable but has 0. |
| misc.c:210:24:210:28 | ... + ... | Node should have one enclosing callable but has 0. |
| misc.c:210:28:210:28 | 1 | Node should have one enclosing callable but has 0. |
| stmt_in_type.cpp:3:12:3:40 | (statement expression) | Node should have one enclosing callable but has 0. |
| stmt_in_type.cpp:3:29:3:34 | call to twisty | Node should have one enclosing callable but has 0. |
uniqueCallEnclosingCallable
| stmt_in_type.cpp:3:29:3:34 | call to twisty | Call should have one enclosing callable but has 0. |
uniqueType
uniqueNodeLocation
| file://:0:0:0:0 | (unnamed parameter 2) | Node should have one location but has 0. |

View File

@@ -0,0 +1,13 @@
ql/csharp/ql/src/API Abuse/FormatInvalid.ql
ql/csharp/ql/src/API Abuse/NoDisposeCallOnLocalIDisposable.ql
ql/csharp/ql/src/Bad Practices/Control-Flow/ConstantCondition.ql
ql/csharp/ql/src/Dead Code/DeadStoreOfLocal.ql
ql/csharp/ql/src/Likely Bugs/Collections/ContainerLengthCmpOffByOne.ql
ql/csharp/ql/src/Likely Bugs/Collections/ContainerSizeCmpZero.ql
ql/csharp/ql/src/Likely Bugs/DangerousNonShortCircuitLogic.ql
ql/csharp/ql/src/Likely Bugs/ReferenceEqualsOnValueTypes.ql
ql/csharp/ql/src/Likely Bugs/SelfAssignment.ql
ql/csharp/ql/src/Likely Bugs/UncheckedCastInEquals.ql
ql/csharp/ql/src/Performance/UseTryGetValue.ql
ql/csharp/ql/src/Useless code/DefaultToString.ql
ql/csharp/ql/src/Useless code/IntGetHashCode.ql

View File

@@ -0,0 +1,57 @@
ql/csharp/ql/src/Diagnostics/CompilerError.ql
ql/csharp/ql/src/Diagnostics/CompilerMessage.ql
ql/csharp/ql/src/Diagnostics/DiagnosticExtractionErrors.ql
ql/csharp/ql/src/Diagnostics/ExtractedFiles.ql
ql/csharp/ql/src/Diagnostics/ExtractorError.ql
ql/csharp/ql/src/Diagnostics/ExtractorMessage.ql
ql/csharp/ql/src/Metrics/Summaries/LinesOfCode.ql
ql/csharp/ql/src/Security Features/CWE-011/ASPNetDebug.ql
ql/csharp/ql/src/Security Features/CWE-016/ASPNetPagesValidateRequest.ql
ql/csharp/ql/src/Security Features/CWE-022/TaintedPath.ql
ql/csharp/ql/src/Security Features/CWE-022/ZipSlip.ql
ql/csharp/ql/src/Security Features/CWE-078/CommandInjection.ql
ql/csharp/ql/src/Security Features/CWE-079/XSS.ql
ql/csharp/ql/src/Security Features/CWE-089/SqlInjection.ql
ql/csharp/ql/src/Security Features/CWE-090/LDAPInjection.ql
ql/csharp/ql/src/Security Features/CWE-091/XMLInjection.ql
ql/csharp/ql/src/Security Features/CWE-094/CodeInjection.ql
ql/csharp/ql/src/Security Features/CWE-099/ResourceInjection.ql
ql/csharp/ql/src/Security Features/CWE-114/AssemblyPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-117/LogForging.ql
ql/csharp/ql/src/Security Features/CWE-119/LocalUnvalidatedArithmetic.ql
ql/csharp/ql/src/Security Features/CWE-134/UncontrolledFormatString.ql
ql/csharp/ql/src/Security Features/CWE-201/ExposureInTransmittedData.ql
ql/csharp/ql/src/Security Features/CWE-209/ExceptionInformationExposure.ql
ql/csharp/ql/src/Security Features/CWE-248/MissingASPNETGlobalErrorHandler.ql
ql/csharp/ql/src/Security Features/CWE-312/CleartextStorage.ql
ql/csharp/ql/src/Security Features/CWE-352/MissingAntiForgeryTokenValidation.ql
ql/csharp/ql/src/Security Features/CWE-359/ExposureOfPrivateInformation.ql
ql/csharp/ql/src/Security Features/CWE-384/AbandonSession.ql
ql/csharp/ql/src/Security Features/CWE-451/MissingXFrameOptions.ql
ql/csharp/ql/src/Security Features/CWE-502/DeserializedDelegate.ql
ql/csharp/ql/src/Security Features/CWE-502/UnsafeDeserializationUntrustedInput.ql
ql/csharp/ql/src/Security Features/CWE-548/ASPNetDirectoryListing.ql
ql/csharp/ql/src/Security Features/CWE-601/UrlRedirect.ql
ql/csharp/ql/src/Security Features/CWE-611/UntrustedDataInsecureXml.ql
ql/csharp/ql/src/Security Features/CWE-614/RequireSSL.ql
ql/csharp/ql/src/Security Features/CWE-643/XPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-730/ReDoS.ql
ql/csharp/ql/src/Security Features/CWE-730/RegexInjection.ql
ql/csharp/ql/src/Security Features/CWE-807/ConditionalBypass.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadDomain.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadPath.ql
ql/csharp/ql/src/Security Features/Encryption using ECB.ql
ql/csharp/ql/src/Security Features/HeaderCheckingDisabled.ql
ql/csharp/ql/src/Security Features/InadequateRSAPadding.ql
ql/csharp/ql/src/Security Features/InsecureRandomness.ql
ql/csharp/ql/src/Security Features/InsufficientKeySize.ql
ql/csharp/ql/src/Security Features/PersistentCookie.ql
ql/csharp/ql/src/Security Features/WeakEncryption.ql
ql/csharp/ql/src/Telemetry/DatabaseQualityDiagnostics.ql
ql/csharp/ql/src/Telemetry/ExternalLibraryUsage.ql
ql/csharp/ql/src/Telemetry/ExtractorInformation.ql
ql/csharp/ql/src/Telemetry/SupportedExternalApis.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSinks.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSources.ql
ql/csharp/ql/src/Telemetry/SupportedExternalTaint.ql
ql/csharp/ql/src/Telemetry/UnsupportedExternalAPIs.ql

View File

@@ -0,0 +1,173 @@
ql/csharp/ql/src/API Abuse/CallToGCCollect.ql
ql/csharp/ql/src/API Abuse/CallToObsoleteMethod.ql
ql/csharp/ql/src/API Abuse/ClassDoesNotImplementEquals.ql
ql/csharp/ql/src/API Abuse/ClassImplementsICloneable.ql
ql/csharp/ql/src/API Abuse/DisposeNotCalledOnException.ql
ql/csharp/ql/src/API Abuse/FormatInvalid.ql
ql/csharp/ql/src/API Abuse/InconsistentEqualsGetHashCode.ql
ql/csharp/ql/src/API Abuse/IncorrectCompareToSignature.ql
ql/csharp/ql/src/API Abuse/IncorrectEqualsSignature.ql
ql/csharp/ql/src/API Abuse/NoDisposeCallOnLocalIDisposable.ql
ql/csharp/ql/src/API Abuse/NullArgumentToEquals.ql
ql/csharp/ql/src/ASP/BlockCodeResponseWrite.ql
ql/csharp/ql/src/Architecture/Refactoring Opportunities/InappropriateIntimacy.ql
ql/csharp/ql/src/Bad Practices/CallsUnmanagedCode.ql
ql/csharp/ql/src/Bad Practices/CatchOfNullReferenceException.ql
ql/csharp/ql/src/Bad Practices/Control-Flow/ConstantCondition.ql
ql/csharp/ql/src/Bad Practices/Declarations/LocalScopeVariableShadowsMember.ql
ql/csharp/ql/src/Bad Practices/Declarations/TooManyRefParameters.ql
ql/csharp/ql/src/Bad Practices/EmptyCatchBlock.ql
ql/csharp/ql/src/Bad Practices/ErroneousClassCompare.ql
ql/csharp/ql/src/Bad Practices/Implementation Hiding/AbstractToConcreteCollection.ql
ql/csharp/ql/src/Bad Practices/Implementation Hiding/ExposeRepresentation.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/FieldMasksSuperField.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/SameNameAsSuper.ql
ql/csharp/ql/src/Bad Practices/PathCombine.ql
ql/csharp/ql/src/Bad Practices/UnmanagedCodeCheck.ql
ql/csharp/ql/src/Bad Practices/VirtualCallInConstructorOrDestructor.ql
ql/csharp/ql/src/CSI/CompareIdenticalValues.ql
ql/csharp/ql/src/CSI/NullAlways.ql
ql/csharp/ql/src/CSI/NullMaybe.ql
ql/csharp/ql/src/Complexity/BlockWithTooManyStatements.ql
ql/csharp/ql/src/Complexity/ComplexCondition.ql
ql/csharp/ql/src/Concurrency/FutileSyncOnField.ql
ql/csharp/ql/src/Concurrency/LockOrder.ql
ql/csharp/ql/src/Concurrency/LockThis.ql
ql/csharp/ql/src/Concurrency/LockedWait.ql
ql/csharp/ql/src/Concurrency/SynchSetUnsynchGet.ql
ql/csharp/ql/src/Concurrency/UnsafeLazyInitialization.ql
ql/csharp/ql/src/Concurrency/UnsynchronizedStaticAccess.ql
ql/csharp/ql/src/Configuration/EmptyPasswordInConfigurationFile.ql
ql/csharp/ql/src/Configuration/PasswordInConfigurationFile.ql
ql/csharp/ql/src/Dead Code/DeadStoreOfLocal.ql
ql/csharp/ql/src/Diagnostics/CompilerError.ql
ql/csharp/ql/src/Diagnostics/CompilerMessage.ql
ql/csharp/ql/src/Diagnostics/DiagnosticExtractionErrors.ql
ql/csharp/ql/src/Diagnostics/ExtractedFiles.ql
ql/csharp/ql/src/Diagnostics/ExtractorError.ql
ql/csharp/ql/src/Diagnostics/ExtractorMessage.ql
ql/csharp/ql/src/Documentation/XmldocMissingSummary.ql
ql/csharp/ql/src/Input Validation/UseOfFileUpload.ql
ql/csharp/ql/src/Input Validation/ValueShadowing.ql
ql/csharp/ql/src/Input Validation/ValueShadowingServerVariable.ql
ql/csharp/ql/src/Language Abuse/CastThisToTypeParameter.ql
ql/csharp/ql/src/Language Abuse/CatchOfGenericException.ql
ql/csharp/ql/src/Language Abuse/ChainedIs.ql
ql/csharp/ql/src/Language Abuse/DubiousDowncastOfThis.ql
ql/csharp/ql/src/Language Abuse/DubiousTypeTestOfThis.ql
ql/csharp/ql/src/Language Abuse/MissedReadonlyOpportunity.ql
ql/csharp/ql/src/Language Abuse/MissedTernaryOpportunity.ql
ql/csharp/ql/src/Language Abuse/MissedUsingOpportunity.ql
ql/csharp/ql/src/Language Abuse/NestedIf.ql
ql/csharp/ql/src/Language Abuse/RethrowException.ql
ql/csharp/ql/src/Language Abuse/SimplifyBoolExpr.ql
ql/csharp/ql/src/Language Abuse/UnusedPropertyValue.ql
ql/csharp/ql/src/Language Abuse/UselessCastToSelf.ql
ql/csharp/ql/src/Language Abuse/UselessNullCoalescingExpression.ql
ql/csharp/ql/src/Language Abuse/UselessTypeTest.ql
ql/csharp/ql/src/Language Abuse/UselessUpcast.ql
ql/csharp/ql/src/Likely Bugs/Collections/ContainerLengthCmpOffByOne.ql
ql/csharp/ql/src/Likely Bugs/Collections/ContainerSizeCmpZero.ql
ql/csharp/ql/src/Likely Bugs/Collections/ReadOnlyContainer.ql
ql/csharp/ql/src/Likely Bugs/Collections/WriteOnlyContainer.ql
ql/csharp/ql/src/Likely Bugs/ConstantComparison.ql
ql/csharp/ql/src/Likely Bugs/DangerousNonShortCircuitLogic.ql
ql/csharp/ql/src/Likely Bugs/Dynamic/BadDynamicCall.ql
ql/csharp/ql/src/Likely Bugs/EqualityCheckOnFloats.ql
ql/csharp/ql/src/Likely Bugs/EqualsArray.ql
ql/csharp/ql/src/Likely Bugs/EqualsUsesAs.ql
ql/csharp/ql/src/Likely Bugs/EqualsUsesIs.ql
ql/csharp/ql/src/Likely Bugs/HashedButNoHash.ql
ql/csharp/ql/src/Likely Bugs/ImpossibleArrayCast.ql
ql/csharp/ql/src/Likely Bugs/IncomparableEquals.ql
ql/csharp/ql/src/Likely Bugs/InconsistentCompareTo.ql
ql/csharp/ql/src/Likely Bugs/LeapYear/UnsafeYearConstruction.ql
ql/csharp/ql/src/Likely Bugs/MishandlingJapaneseEra.ql
ql/csharp/ql/src/Likely Bugs/NestedLoopsSameVariable.ql
ql/csharp/ql/src/Likely Bugs/ObjectComparison.ql
ql/csharp/ql/src/Likely Bugs/PossibleLossOfPrecision.ql
ql/csharp/ql/src/Likely Bugs/RecursiveEquals.ql
ql/csharp/ql/src/Likely Bugs/RecursiveOperatorEquals.ql
ql/csharp/ql/src/Likely Bugs/ReferenceEqualsOnValueTypes.ql
ql/csharp/ql/src/Likely Bugs/SelfAssignment.ql
ql/csharp/ql/src/Likely Bugs/Statements/EmptyBlock.ql
ql/csharp/ql/src/Likely Bugs/Statements/EmptyLockStatement.ql
ql/csharp/ql/src/Likely Bugs/Statements/UseBraces.ql
ql/csharp/ql/src/Likely Bugs/StaticFieldWrittenByInstance.ql
ql/csharp/ql/src/Likely Bugs/StringBuilderCharInit.ql
ql/csharp/ql/src/Likely Bugs/ThreadUnsafeICryptoTransform.ql
ql/csharp/ql/src/Likely Bugs/ThreadUnsafeICryptoTransformLambda.ql
ql/csharp/ql/src/Likely Bugs/UncheckedCastInEquals.ql
ql/csharp/ql/src/Linq/BadMultipleIteration.ql
ql/csharp/ql/src/Linq/MissedAllOpportunity.ql
ql/csharp/ql/src/Linq/MissedCastOpportunity.ql
ql/csharp/ql/src/Linq/MissedOfTypeOpportunity.ql
ql/csharp/ql/src/Linq/MissedSelectOpportunity.ql
ql/csharp/ql/src/Linq/MissedWhereOpportunity.ql
ql/csharp/ql/src/Linq/RedundantSelect.ql
ql/csharp/ql/src/Metrics/Summaries/LinesOfCode.ql
ql/csharp/ql/src/Performance/StringBuilderInLoop.ql
ql/csharp/ql/src/Performance/StringConcatenationInLoop.ql
ql/csharp/ql/src/Performance/UseTryGetValue.ql
ql/csharp/ql/src/Security Features/CWE-011/ASPNetDebug.ql
ql/csharp/ql/src/Security Features/CWE-016/ASPNetPagesValidateRequest.ql
ql/csharp/ql/src/Security Features/CWE-020/RuntimeChecksBypass.ql
ql/csharp/ql/src/Security Features/CWE-022/TaintedPath.ql
ql/csharp/ql/src/Security Features/CWE-022/ZipSlip.ql
ql/csharp/ql/src/Security Features/CWE-078/CommandInjection.ql
ql/csharp/ql/src/Security Features/CWE-079/XSS.ql
ql/csharp/ql/src/Security Features/CWE-089/SqlInjection.ql
ql/csharp/ql/src/Security Features/CWE-090/LDAPInjection.ql
ql/csharp/ql/src/Security Features/CWE-091/XMLInjection.ql
ql/csharp/ql/src/Security Features/CWE-094/CodeInjection.ql
ql/csharp/ql/src/Security Features/CWE-099/ResourceInjection.ql
ql/csharp/ql/src/Security Features/CWE-112/MissingXMLValidation.ql
ql/csharp/ql/src/Security Features/CWE-114/AssemblyPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-117/LogForging.ql
ql/csharp/ql/src/Security Features/CWE-119/LocalUnvalidatedArithmetic.ql
ql/csharp/ql/src/Security Features/CWE-134/UncontrolledFormatString.ql
ql/csharp/ql/src/Security Features/CWE-201/ExposureInTransmittedData.ql
ql/csharp/ql/src/Security Features/CWE-209/ExceptionInformationExposure.ql
ql/csharp/ql/src/Security Features/CWE-248/MissingASPNETGlobalErrorHandler.ql
ql/csharp/ql/src/Security Features/CWE-285/MissingAccessControl.ql
ql/csharp/ql/src/Security Features/CWE-312/CleartextStorage.ql
ql/csharp/ql/src/Security Features/CWE-327/InsecureSQLConnection.ql
ql/csharp/ql/src/Security Features/CWE-352/MissingAntiForgeryTokenValidation.ql
ql/csharp/ql/src/Security Features/CWE-359/ExposureOfPrivateInformation.ql
ql/csharp/ql/src/Security Features/CWE-384/AbandonSession.ql
ql/csharp/ql/src/Security Features/CWE-451/MissingXFrameOptions.ql
ql/csharp/ql/src/Security Features/CWE-502/DeserializedDelegate.ql
ql/csharp/ql/src/Security Features/CWE-502/UnsafeDeserializationUntrustedInput.ql
ql/csharp/ql/src/Security Features/CWE-548/ASPNetDirectoryListing.ql
ql/csharp/ql/src/Security Features/CWE-601/UrlRedirect.ql
ql/csharp/ql/src/Security Features/CWE-611/UntrustedDataInsecureXml.ql
ql/csharp/ql/src/Security Features/CWE-614/RequireSSL.ql
ql/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql
ql/csharp/ql/src/Security Features/CWE-643/XPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-730/ReDoS.ql
ql/csharp/ql/src/Security Features/CWE-730/RegexInjection.ql
ql/csharp/ql/src/Security Features/CWE-798/HardcodedConnectionString.ql
ql/csharp/ql/src/Security Features/CWE-798/HardcodedCredentials.ql
ql/csharp/ql/src/Security Features/CWE-807/ConditionalBypass.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadDomain.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadPath.ql
ql/csharp/ql/src/Security Features/Encryption using ECB.ql
ql/csharp/ql/src/Security Features/HeaderCheckingDisabled.ql
ql/csharp/ql/src/Security Features/InadequateRSAPadding.ql
ql/csharp/ql/src/Security Features/InsecureRandomness.ql
ql/csharp/ql/src/Security Features/InsufficientKeySize.ql
ql/csharp/ql/src/Security Features/PersistentCookie.ql
ql/csharp/ql/src/Security Features/WeakEncryption.ql
ql/csharp/ql/src/Telemetry/DatabaseQualityDiagnostics.ql
ql/csharp/ql/src/Telemetry/ExternalLibraryUsage.ql
ql/csharp/ql/src/Telemetry/ExtractorInformation.ql
ql/csharp/ql/src/Telemetry/SupportedExternalApis.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSinks.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSources.ql
ql/csharp/ql/src/Telemetry/SupportedExternalTaint.ql
ql/csharp/ql/src/Telemetry/UnsupportedExternalAPIs.ql
ql/csharp/ql/src/Useless code/DefaultToString.ql
ql/csharp/ql/src/Useless code/FutileConditional.ql
ql/csharp/ql/src/Useless code/IntGetHashCode.ql
ql/csharp/ql/src/Useless code/RedundantToStringCall.ql
ql/csharp/ql/src/Useless code/UnusedLabel.ql

View File

@@ -0,0 +1,71 @@
ql/csharp/ql/src/Configuration/EmptyPasswordInConfigurationFile.ql
ql/csharp/ql/src/Configuration/PasswordInConfigurationFile.ql
ql/csharp/ql/src/Diagnostics/CompilerError.ql
ql/csharp/ql/src/Diagnostics/CompilerMessage.ql
ql/csharp/ql/src/Diagnostics/DiagnosticExtractionErrors.ql
ql/csharp/ql/src/Diagnostics/ExtractedFiles.ql
ql/csharp/ql/src/Diagnostics/ExtractorError.ql
ql/csharp/ql/src/Diagnostics/ExtractorMessage.ql
ql/csharp/ql/src/Input Validation/UseOfFileUpload.ql
ql/csharp/ql/src/Input Validation/ValueShadowing.ql
ql/csharp/ql/src/Input Validation/ValueShadowingServerVariable.ql
ql/csharp/ql/src/Likely Bugs/ThreadUnsafeICryptoTransform.ql
ql/csharp/ql/src/Likely Bugs/ThreadUnsafeICryptoTransformLambda.ql
ql/csharp/ql/src/Metrics/Summaries/LinesOfCode.ql
ql/csharp/ql/src/Security Features/CWE-011/ASPNetDebug.ql
ql/csharp/ql/src/Security Features/CWE-016/ASPNetPagesValidateRequest.ql
ql/csharp/ql/src/Security Features/CWE-020/RuntimeChecksBypass.ql
ql/csharp/ql/src/Security Features/CWE-022/TaintedPath.ql
ql/csharp/ql/src/Security Features/CWE-022/ZipSlip.ql
ql/csharp/ql/src/Security Features/CWE-078/CommandInjection.ql
ql/csharp/ql/src/Security Features/CWE-079/XSS.ql
ql/csharp/ql/src/Security Features/CWE-089/SqlInjection.ql
ql/csharp/ql/src/Security Features/CWE-090/LDAPInjection.ql
ql/csharp/ql/src/Security Features/CWE-091/XMLInjection.ql
ql/csharp/ql/src/Security Features/CWE-094/CodeInjection.ql
ql/csharp/ql/src/Security Features/CWE-099/ResourceInjection.ql
ql/csharp/ql/src/Security Features/CWE-112/MissingXMLValidation.ql
ql/csharp/ql/src/Security Features/CWE-114/AssemblyPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-117/LogForging.ql
ql/csharp/ql/src/Security Features/CWE-119/LocalUnvalidatedArithmetic.ql
ql/csharp/ql/src/Security Features/CWE-134/UncontrolledFormatString.ql
ql/csharp/ql/src/Security Features/CWE-201/ExposureInTransmittedData.ql
ql/csharp/ql/src/Security Features/CWE-209/ExceptionInformationExposure.ql
ql/csharp/ql/src/Security Features/CWE-248/MissingASPNETGlobalErrorHandler.ql
ql/csharp/ql/src/Security Features/CWE-285/MissingAccessControl.ql
ql/csharp/ql/src/Security Features/CWE-312/CleartextStorage.ql
ql/csharp/ql/src/Security Features/CWE-327/InsecureSQLConnection.ql
ql/csharp/ql/src/Security Features/CWE-352/MissingAntiForgeryTokenValidation.ql
ql/csharp/ql/src/Security Features/CWE-359/ExposureOfPrivateInformation.ql
ql/csharp/ql/src/Security Features/CWE-384/AbandonSession.ql
ql/csharp/ql/src/Security Features/CWE-451/MissingXFrameOptions.ql
ql/csharp/ql/src/Security Features/CWE-502/DeserializedDelegate.ql
ql/csharp/ql/src/Security Features/CWE-502/UnsafeDeserializationUntrustedInput.ql
ql/csharp/ql/src/Security Features/CWE-548/ASPNetDirectoryListing.ql
ql/csharp/ql/src/Security Features/CWE-601/UrlRedirect.ql
ql/csharp/ql/src/Security Features/CWE-611/UntrustedDataInsecureXml.ql
ql/csharp/ql/src/Security Features/CWE-614/RequireSSL.ql
ql/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql
ql/csharp/ql/src/Security Features/CWE-643/XPathInjection.ql
ql/csharp/ql/src/Security Features/CWE-730/ReDoS.ql
ql/csharp/ql/src/Security Features/CWE-730/RegexInjection.ql
ql/csharp/ql/src/Security Features/CWE-798/HardcodedConnectionString.ql
ql/csharp/ql/src/Security Features/CWE-798/HardcodedCredentials.ql
ql/csharp/ql/src/Security Features/CWE-807/ConditionalBypass.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadDomain.ql
ql/csharp/ql/src/Security Features/CookieWithOverlyBroadPath.ql
ql/csharp/ql/src/Security Features/Encryption using ECB.ql
ql/csharp/ql/src/Security Features/HeaderCheckingDisabled.ql
ql/csharp/ql/src/Security Features/InadequateRSAPadding.ql
ql/csharp/ql/src/Security Features/InsecureRandomness.ql
ql/csharp/ql/src/Security Features/InsufficientKeySize.ql
ql/csharp/ql/src/Security Features/PersistentCookie.ql
ql/csharp/ql/src/Security Features/WeakEncryption.ql
ql/csharp/ql/src/Telemetry/DatabaseQualityDiagnostics.ql
ql/csharp/ql/src/Telemetry/ExternalLibraryUsage.ql
ql/csharp/ql/src/Telemetry/ExtractorInformation.ql
ql/csharp/ql/src/Telemetry/SupportedExternalApis.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSinks.ql
ql/csharp/ql/src/Telemetry/SupportedExternalSources.ql
ql/csharp/ql/src/Telemetry/SupportedExternalTaint.ql
ql/csharp/ql/src/Telemetry/UnsupportedExternalAPIs.ql

View File

@@ -0,0 +1,128 @@
ql/csharp/ql/src/API Abuse/MissingDisposeCall.ql
ql/csharp/ql/src/API Abuse/MissingDisposeMethod.ql
ql/csharp/ql/src/API Abuse/NonOverridingMethod.ql
ql/csharp/ql/src/API Abuse/UncheckedReturnValue.ql
ql/csharp/ql/src/ASP/ComplexInlineCode.ql
ql/csharp/ql/src/ASP/NonInternationalizedText.ql
ql/csharp/ql/src/ASP/SplitControlStructure.ql
ql/csharp/ql/src/AlertSuppression.ql
ql/csharp/ql/src/Architecture/Dependencies/MutualDependency.ql
ql/csharp/ql/src/Architecture/Refactoring Opportunities/FeatureEnvy.ql
ql/csharp/ql/src/Bad Practices/Comments/CommentedOutCode.ql
ql/csharp/ql/src/Bad Practices/Comments/TodoComments.ql
ql/csharp/ql/src/Bad Practices/Declarations/EmptyInterface.ql
ql/csharp/ql/src/Bad Practices/Declarations/NoConstantsOnly.ql
ql/csharp/ql/src/Bad Practices/Implementation Hiding/StaticArray.ql
ql/csharp/ql/src/Bad Practices/LeftoverDebugCode.ql
ql/csharp/ql/src/Bad Practices/Magic Constants/MagicConstantsNumbers.ql
ql/csharp/ql/src/Bad Practices/Magic Constants/MagicConstantsString.ql
ql/csharp/ql/src/Bad Practices/Magic Constants/MagicNumbersUseConstant.ql
ql/csharp/ql/src/Bad Practices/Magic Constants/MagicStringsUseConstant.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/ConfusingMethodNames.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/ConfusingOverridesNames.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/ConstantNaming.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/ControlNamePrefixes.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/DefaultControlNames.ql
ql/csharp/ql/src/Bad Practices/Naming Conventions/VariableNameTooShort.ql
ql/csharp/ql/src/Bad Practices/UseOfHtmlInputHidden.ql
ql/csharp/ql/src/Bad Practices/UseOfSystemOutputStream.ql
ql/csharp/ql/src/Dead Code/DeadRefTypes.ql
ql/csharp/ql/src/Dead Code/NonAssignedFields.ql
ql/csharp/ql/src/Dead Code/UnusedField.ql
ql/csharp/ql/src/Dead Code/UnusedMethod.ql
ql/csharp/ql/src/Documentation/XmldocExtraParam.ql
ql/csharp/ql/src/Documentation/XmldocExtraTypeParam.ql
ql/csharp/ql/src/Documentation/XmldocMissing.ql
ql/csharp/ql/src/Documentation/XmldocMissingException.ql
ql/csharp/ql/src/Documentation/XmldocMissingParam.ql
ql/csharp/ql/src/Documentation/XmldocMissingReturn.ql
ql/csharp/ql/src/Documentation/XmldocMissingTypeParam.ql
ql/csharp/ql/src/Language Abuse/ForeachCapture.ql
ql/csharp/ql/src/Language Abuse/UselessIsBeforeAs.ql
ql/csharp/ql/src/Likely Bugs/BadCheckOdd.ql
ql/csharp/ql/src/Likely Bugs/RandomUsedOnce.ql
ql/csharp/ql/src/Metrics/Callables/CCyclomaticComplexity.ql
ql/csharp/ql/src/Metrics/Callables/CLinesOfCode.ql
ql/csharp/ql/src/Metrics/Callables/CLinesOfComment.ql
ql/csharp/ql/src/Metrics/Callables/CNumberOfParameters.ql
ql/csharp/ql/src/Metrics/Callables/CNumberOfStatements.ql
ql/csharp/ql/src/Metrics/Callables/CPercentageOfComments.ql
ql/csharp/ql/src/Metrics/Callables/StatementNestingDepth.ql
ql/csharp/ql/src/Metrics/Dependencies/ExternalDependencies.ql
ql/csharp/ql/src/Metrics/Dependencies/ExternalDependenciesSourceLinks.ql
ql/csharp/ql/src/Metrics/Files/FCommentRatio.ql
ql/csharp/ql/src/Metrics/Files/FCyclomaticComplexity.ql
ql/csharp/ql/src/Metrics/Files/FLines.ql
ql/csharp/ql/src/Metrics/Files/FLinesOfCode.ql
ql/csharp/ql/src/Metrics/Files/FLinesOfComment.ql
ql/csharp/ql/src/Metrics/Files/FLinesOfCommentedCode.ql
ql/csharp/ql/src/Metrics/Files/FNumberOfClasses.ql
ql/csharp/ql/src/Metrics/Files/FNumberOfInterfaces.ql
ql/csharp/ql/src/Metrics/Files/FNumberOfStructs.ql
ql/csharp/ql/src/Metrics/Files/FNumberOfTests.ql
ql/csharp/ql/src/Metrics/Files/FNumberOfUsingNamespaces.ql
ql/csharp/ql/src/Metrics/Files/FSelfContainedness.ql
ql/csharp/ql/src/Metrics/RefTypes/TAfferentCoupling.ql
ql/csharp/ql/src/Metrics/RefTypes/TEfferentCoupling.ql
ql/csharp/ql/src/Metrics/RefTypes/TInheritanceDepth.ql
ql/csharp/ql/src/Metrics/RefTypes/TLackOfCohesionCK.ql
ql/csharp/ql/src/Metrics/RefTypes/TLackOfCohesionHS.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfCallables.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfEvents.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfFields.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfIndexers.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfNonConstFields.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfProperties.ql
ql/csharp/ql/src/Metrics/RefTypes/TNumberOfStatements.ql
ql/csharp/ql/src/Metrics/RefTypes/TResponse.ql
ql/csharp/ql/src/Metrics/RefTypes/TSizeOfAPI.ql
ql/csharp/ql/src/Metrics/RefTypes/TSpecialisationIndex.ql
ql/csharp/ql/src/Metrics/RefTypes/TUnmanagedCode.ql
ql/csharp/ql/src/Metrics/Summaries/FrameworkCoverage.ql
ql/csharp/ql/src/Metrics/internal/ExtractorDiagnostics.ql
ql/csharp/ql/src/Security Features/CWE-016/ASPNetMaxRequestLength.ql
ql/csharp/ql/src/Security Features/CWE-016/ASPNetRequestValidationMode.ql
ql/csharp/ql/src/Security Features/CWE-020/ExternalAPIsUsedWithUntrustedData.ql
ql/csharp/ql/src/Security Features/CWE-020/UntrustedDataToExternalAPI.ql
ql/csharp/ql/src/Security Features/CWE-321/HardcodedEncryptionKey.ql
ql/csharp/ql/src/Security Features/CWE-321/HardcodedSymmetricEncryptionKey.ql
ql/csharp/ql/src/Security Features/CWE-327/DontInstallRootCert.ql
ql/csharp/ql/src/Security Features/CWE-502/UnsafeDeserialization.ql
ql/csharp/ql/src/Security Features/CWE-611/UseXmlSecureResolver.ql
ql/csharp/ql/src/Security Features/CWE-838/InappropriateEncoding.ql
ql/csharp/ql/src/Useless code/PointlessForwardingMethod.ql
ql/csharp/ql/src/definitions.ql
ql/csharp/ql/src/experimental/CWE-099/TaintedWebClient.ql
ql/csharp/ql/src/experimental/CWE-918/RequestForgery.ql
ql/csharp/ql/src/experimental/Security Features/CWE-1004/CookieWithoutHttpOnly.ql
ql/csharp/ql/src/experimental/Security Features/CWE-327/Azure/UnsafeUsageOfClientSideEncryptionVersion.ql
ql/csharp/ql/src/experimental/Security Features/CWE-614/CookieWithoutSecure.ql
ql/csharp/ql/src/experimental/Security Features/CWE-759/HashWithoutSalt.ql
ql/csharp/ql/src/experimental/Security Features/JsonWebTokenHandler/delegated-security-validations-always-return-true.ql
ql/csharp/ql/src/experimental/Security Features/JsonWebTokenHandler/security-validation-disabled.ql
ql/csharp/ql/src/experimental/Security Features/Serialization/DefiningDatasetRelatedType.ql
ql/csharp/ql/src/experimental/Security Features/Serialization/DefiningPotentiallyUnsafeXmlSerializer.ql
ql/csharp/ql/src/experimental/Security Features/Serialization/UnsafeTypeUsedDataContractSerializer.ql
ql/csharp/ql/src/experimental/Security Features/Serialization/XmlDeserializationWithDataSet.ql
ql/csharp/ql/src/experimental/Security Features/backdoor/DangerousNativeFunctionCall.ql
ql/csharp/ql/src/experimental/Security Features/backdoor/PotentialTimeBomb.ql
ql/csharp/ql/src/experimental/Security Features/backdoor/ProcessNameToHashTaintFlow.ql
ql/csharp/ql/src/filters/ClassifyFiles.ql
ql/csharp/ql/src/meta/frameworks/Coverage.ql
ql/csharp/ql/src/meta/frameworks/UnsupportedExternalAPIs.ql
ql/csharp/ql/src/utils/modelconverter/ExtractNeutrals.ql
ql/csharp/ql/src/utils/modelconverter/ExtractSinks.ql
ql/csharp/ql/src/utils/modelconverter/ExtractSources.ql
ql/csharp/ql/src/utils/modelconverter/ExtractSummaries.ql
ql/csharp/ql/src/utils/modeleditor/ApplicationModeEndpoints.ql
ql/csharp/ql/src/utils/modeleditor/FrameworkModeEndpoints.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureContentSummaryModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureMixedNeutralModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureMixedSummaryModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureNeutralModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureSinkModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureSourceModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureSummaryModels.ql
ql/csharp/ql/src/utils/modelgenerator/CaptureTypeBasedSummaryModels.ql
ql/csharp/ql/src/utils/modelgenerator/debug/CaptureSummaryModelsPartialPath.ql
ql/csharp/ql/src/utils/modelgenerator/debug/CaptureSummaryModelsPath.ql

View File

@@ -0,0 +1,14 @@
import runs_on
import pytest
from query_suites import *
well_known_query_suites = ['csharp-code-quality.qls', 'csharp-security-and-quality.qls', 'csharp-security-extended.qls', 'csharp-code-scanning.qls']
@runs_on.posix
@pytest.mark.parametrize("query_suite", well_known_query_suites)
def test(codeql, csharp, check_query_suite, query_suite):
check_query_suite(query_suite)
@runs_on.posix
def test_not_included_queries(codeql, csharp, check_queries_not_included):
check_queries_not_included('csharp', well_known_query_suites)

View File

@@ -97,7 +97,8 @@ private class ParamsConstructedCollectionTypes extends ParamsCollectionTypeImpl
unboundbase instanceof SystemCollectionsGenericIReadOnlyListTInterface or
unboundbase instanceof SystemSpanStruct or
unboundbase instanceof SystemReadOnlySpanStruct
)
) and
not this instanceof SystemStringClass
}
override Type getElementType() { result = base.getTypeArgument(0) }

View File

@@ -408,7 +408,8 @@ Declaration interpretBaseDeclaration(string namespace, string type, string name,
)
}
pragma[inline]
bindingset[d, ext]
pragma[inline_late]
private Declaration interpretExt(Declaration d, ExtPath ext) {
ext = "" and result = d
or

View File

@@ -8,69 +8,122 @@ private import semmle.code.csharp.frameworks.System
private import semmle.code.csharp.frameworks.system.Text
/** A method that formats a string, for example `string.Format()`. */
class FormatMethod extends Method {
FormatMethod() {
exists(Class declType | declType = this.getDeclaringType() |
this.getParameter(0).getType() instanceof SystemIFormatProviderInterface and
this.getParameter(1).getType() instanceof StringType and
(
this = any(SystemStringClass c).getFormatMethod()
or
this = any(SystemTextStringBuilderClass c).getAppendFormatMethod()
)
or
this.getParameter(0).getType() instanceof StringType and
(
this = any(SystemStringClass c).getFormatMethod()
or
this = any(SystemTextStringBuilderClass c).getAppendFormatMethod()
or
(this.hasName("Write") or this.hasName("WriteLine")) and
(
declType.hasFullyQualifiedName("System", "Console")
or
declType.hasFullyQualifiedName("System.IO", "TextWriter")
or
declType.hasFullyQualifiedName("System.Diagnostics", "Debug") and
this.getParameter(1).getType() instanceof ArrayType
)
or
declType.hasFullyQualifiedName("System.Diagnostics", "Trace") and
(
this.hasName("TraceError") or
this.hasName("TraceInformation") or
this.hasName("TraceWarning")
)
or
this.hasName("TraceInformation") and
declType.hasFullyQualifiedName("System.Diagnostics", "TraceSource")
or
this.hasName("Print") and
declType.hasFullyQualifiedName("System.Diagnostics", "Debug")
)
or
this.hasName("Assert") and
declType.hasFullyQualifiedName("System.Diagnostics", "Debug") and
this.getNumberOfParameters() = 4
)
}
abstract private class FormatMethodImpl extends Method {
/**
* Gets the argument containing the format string. For example, the argument of
* `string.Format(IFormatProvider, String, Object)` is `1`.
*/
int getFormatArgument() {
abstract int getFormatArgument();
/**
* Gets the argument number of the first supplied insert.
*/
int getFirstArgument() { result = this.getFormatArgument() + 1 }
}
final class FormatMethod = FormatMethodImpl;
/** A class of types used for formatting. */
private class FormatType extends Type {
FormatType() {
this instanceof StringType or
this instanceof SystemTextCompositeFormatClass
}
}
private class StringAndStringBuilderFormatMethods extends FormatMethodImpl {
StringAndStringBuilderFormatMethods() {
(
this.getParameter(0).getType() instanceof SystemIFormatProviderInterface and
this.getParameter(1).getType() instanceof FormatType
or
this.getParameter(0).getType() instanceof StringType
) and
(
this = any(SystemStringClass c).getFormatMethod()
or
this = any(SystemTextStringBuilderClass c).getAppendFormatMethod()
)
}
override int getFormatArgument() {
if this.getParameter(0).getType() instanceof SystemIFormatProviderInterface
then result = 1
else
if
this.hasName("Assert") and
this.getDeclaringType().hasFullyQualifiedName("System.Diagnostics", "Debug")
then result = 2
else result = 0
else result = 0
}
}
private class SystemMemoryExtensionsFormatMethods extends FormatMethodImpl {
SystemMemoryExtensionsFormatMethods() {
this = any(SystemMemoryExtensionsClass c).getTryWriteMethod() and
this.getParameter(1).getType() instanceof SystemIFormatProviderInterface and
this.getParameter(2).getType() instanceof SystemTextCompositeFormatClass
}
override int getFormatArgument() { result = 2 }
override int getFirstArgument() { result = this.getFormatArgument() + 2 }
}
private class SystemConsoleAndSystemIoTextWriterFormatMethods extends FormatMethodImpl {
SystemConsoleAndSystemIoTextWriterFormatMethods() {
this.getParameter(0).getType() instanceof StringType and
this.getNumberOfParameters() > 1 and
exists(Class declType | declType = this.getDeclaringType() |
this.hasName(["Write", "WriteLine"]) and
(
declType.hasFullyQualifiedName("System", "Console")
or
declType.hasFullyQualifiedName("System.IO", "TextWriter")
)
)
}
override int getFormatArgument() { result = 0 }
}
private class SystemDiagnosticsDebugAssert extends FormatMethodImpl {
SystemDiagnosticsDebugAssert() {
this.hasName("Assert") and
this.getDeclaringType().hasFullyQualifiedName("System.Diagnostics", "Debug") and
this.getNumberOfParameters() = 4
}
override int getFormatArgument() { result = 2 }
}
private class SystemDiagnosticsFormatMethods extends FormatMethodImpl {
SystemDiagnosticsFormatMethods() {
this.getParameter(0).getType() instanceof StringType and
this.getNumberOfParameters() > 1 and
exists(Class declType |
declType = this.getDeclaringType() and
declType.getNamespace().getFullName() = "System.Diagnostics"
|
declType.hasName("Trace") and
(
this.hasName("TraceError")
or
this.hasName("TraceInformation")
or
this.hasName("TraceWarning")
)
or
declType.hasName("TraceSource") and this.hasName("TraceInformation")
or
declType.hasName("Debug") and
(
this.hasName("Print")
or
this.hasName(["Write", "WriteLine"]) and
this.getParameter(1).getType() instanceof ArrayType
)
)
}
override int getFormatArgument() { result = 0 }
}
pragma[nomagic]
private predicate parameterReadPostDominatesEntry(ParameterRead pr) {
pr.getAControlFlowNode().postDominates(pr.getEnclosingCallable().getEntryPoint()) and
@@ -194,24 +247,36 @@ class FormatCall extends MethodCall {
int getFormatArgument() { result = this.getTarget().(FormatMethod).getFormatArgument() }
/** Gets the argument number of the first supplied insert. */
int getFirstArgument() { result = this.getFormatArgument() + 1 }
int getFirstArgument() { result = this.getTarget().(FormatMethod).getFirstArgument() }
/** Holds if this call has one or more insertions. */
predicate hasInsertions() { exists(this.getArgument(this.getFirstArgument())) }
/** Holds if the arguments are supplied in an array, not individually. */
predicate hasArrayExpr() {
/**
* DEPRECATED: use `hasCollectionExpr` instead.
*
* Holds if the arguments are supplied in an array, not individually.
*/
deprecated predicate hasArrayExpr() {
this.getNumberOfArguments() = this.getFirstArgument() + 1 and
this.getArgument(this.getFirstArgument()).getType() instanceof ArrayType
}
/**
* Holds if the arguments are supplied in a collection, not individually.
*/
predicate hasCollectionExpr() {
this.getNumberOfArguments() = this.getFirstArgument() + 1 and
this.getArgument(this.getFirstArgument()).getType() instanceof ParamsCollectionType
}
/**
* Gets the number of supplied arguments (excluding the format string and format
* provider). Does not return a value if the arguments are supplied in an array,
* in which case we generally can't assess the size of the array.
*/
int getSuppliedArguments() {
not this.hasArrayExpr() and
not this.hasCollectionExpr() and
result = this.getNumberOfArguments() - this.getFirstArgument()
}

View File

@@ -365,7 +365,7 @@ class SystemStringClass extends StringType {
/** Gets a `Format(...)` method. */
Method getFormatMethod() {
result.getDeclaringType() = this and
result.hasName("Format") and
result.getName().regexpMatch("Format(<.*>)?") and
result.getNumberOfParameters() in [2 .. 5] and
result.getReturnType() instanceof StringType
}
@@ -751,6 +751,18 @@ class SystemNotImplementedExceptionClass extends SystemClass {
SystemNotImplementedExceptionClass() { this.hasName("NotImplementedException") }
}
/** The `System.MemoryExtensions` class. */
class SystemMemoryExtensionsClass extends SystemClass {
SystemMemoryExtensionsClass() { this.hasName("MemoryExtensions") }
/** Gets a `TryWrite` method. */
Method getTryWriteMethod() {
result.getDeclaringType() = this and
result.getName().regexpMatch("TryWrite(<.*>)?") and
result.getParameter(0).getType().getUnboundDeclaration() instanceof SystemSpanStruct
}
}
/** The `System.DateTime` struct. */
class SystemDateTimeStruct extends SystemStruct {
SystemDateTimeStruct() { this.hasName("DateTime") }

View File

@@ -22,7 +22,12 @@ class SystemTextStringBuilderClass extends SystemTextClass {
SystemTextStringBuilderClass() { this.hasName("StringBuilder") }
/** Gets the `AppendFormat` method. */
Method getAppendFormatMethod() { result = this.getAMethod("AppendFormat") }
Method getAppendFormatMethod() {
exists(string name |
name.regexpMatch("AppendFormat(<.*>)?") and
result = this.getAMethod(name)
)
}
}
/** The `System.Text.Encoding` class. */
@@ -38,3 +43,11 @@ class SystemTextEncodingClass extends SystemTextClass {
/** Gets the `GetChars` method. */
Method getGetCharsMethod() { result = this.getAMethod("GetChars") }
}
/** The `System.Text.CompositeFormat` class */
class SystemTextCompositeFormatClass extends SystemTextClass {
SystemTextCompositeFormatClass() { this.hasName("CompositeFormat") }
/** Gets the `Parse` method. */
Method getParseMethod() { result = this.getAMethod("Parse") }
}

View File

@@ -11,37 +11,75 @@
*/
import csharp
import semmle.code.csharp.frameworks.system.Text
import semmle.code.csharp.frameworks.Format
import FormatInvalid::PathGraph
import FormatFlow::PathGraph
abstract class FormatStringParseCall extends MethodCall {
abstract Expr getFormatExpr();
}
class OrdinaryFormatCall extends FormatStringParseCall instanceof FormatCall {
override Expr getFormatExpr() { result = FormatCall.super.getFormatExpr() }
}
class ParseFormatStringCall extends FormatStringParseCall {
ParseFormatStringCall() {
this.getTarget() = any(SystemTextCompositeFormatClass x).getParseMethod()
}
override Expr getFormatExpr() { result = this.getArgument(0) }
}
module FormatInvalidConfig implements DataFlow::ConfigSig {
predicate isSource(DataFlow::Node n) { n.asExpr() instanceof StringLiteral }
predicate isSink(DataFlow::Node n) { exists(FormatCall c | n.asExpr() = c.getFormatExpr()) }
predicate isSink(DataFlow::Node n) {
exists(FormatStringParseCall c | n.asExpr() = c.getFormatExpr())
}
}
module FormatInvalid = DataFlow::Global<FormatInvalidConfig>;
module FormatLiteralConfig implements DataFlow::ConfigSig {
predicate isSource(DataFlow::Node n) { n.asExpr() instanceof StringLiteral }
predicate isAdditionalFlowStep(DataFlow::Node pred, DataFlow::Node succ) {
// Add flow via `System.Text.CompositeFormat.Parse`.
exists(ParseFormatStringCall call |
pred.asExpr() = call.getFormatExpr() and
succ.asExpr() = call
)
}
predicate isSink(DataFlow::Node n) { exists(FormatCall c | n.asExpr() = c.getFormatExpr()) }
}
module FormatLiteral = DataFlow::Global<FormatLiteralConfig>;
module FormatFlow =
DataFlow::MergePathGraph<FormatInvalid::PathNode, FormatLiteral::PathNode,
FormatInvalid::PathGraph, FormatLiteral::PathGraph>;
private predicate invalidFormatString(
InvalidFormatString src, FormatInvalid::PathNode source, FormatInvalid::PathNode sink, string msg,
FormatCall call, string callString
FormatStringParseCall call, string callString
) {
source.getNode().asExpr() = src and
sink.getNode().asExpr() = call.getFormatExpr() and
FormatInvalid::flowPath(source, sink) and
call.hasInsertions() and
msg = "Invalid format string used in $@ formatting call." and
callString = "this"
}
private predicate unusedArgument(
FormatCall call, FormatInvalid::PathNode source, FormatInvalid::PathNode sink, string msg,
FormatCall call, FormatLiteral::PathNode source, FormatLiteral::PathNode sink, string msg,
ValidFormatString src, string srcString, Expr unusedExpr, string unusedString
) {
exists(int unused |
source.getNode().asExpr() = src and
sink.getNode().asExpr() = call.getFormatExpr() and
FormatInvalid::flowPath(source, sink) and
FormatLiteral::flowPath(source, sink) and
unused = call.getASuppliedArgument() and
not unused = src.getAnInsert() and
not src.getValue() = "" and
@@ -53,13 +91,13 @@ private predicate unusedArgument(
}
private predicate missingArgument(
FormatCall call, FormatInvalid::PathNode source, FormatInvalid::PathNode sink, string msg,
FormatCall call, FormatLiteral::PathNode source, FormatLiteral::PathNode sink, string msg,
ValidFormatString src, string srcString
) {
exists(int used, int supplied |
source.getNode().asExpr() = src and
sink.getNode().asExpr() = call.getFormatExpr() and
FormatInvalid::flowPath(source, sink) and
FormatLiteral::flowPath(source, sink) and
used = src.getAnInsert() and
supplied = call.getSuppliedArguments() and
used >= supplied and
@@ -69,16 +107,17 @@ private predicate missingArgument(
}
from
Element alert, FormatInvalid::PathNode source, FormatInvalid::PathNode sink, string msg,
Element extra1, string extra1String, Element extra2, string extra2String
Element alert, FormatFlow::PathNode source, FormatFlow::PathNode sink, string msg, Element extra1,
string extra1String, Element extra2, string extra2String
where
invalidFormatString(alert, source, sink, msg, extra1, extra1String) and
invalidFormatString(alert, source.asPathNode1(), sink.asPathNode1(), msg, extra1, extra1String) and
extra2 = extra1 and
extra2String = extra1String
or
unusedArgument(alert, source, sink, msg, extra1, extra1String, extra2, extra2String)
unusedArgument(alert, source.asPathNode2(), sink.asPathNode2(), msg, extra1, extra1String, extra2,
extra2String)
or
missingArgument(alert, source, sink, msg, extra1, extra1String) and
missingArgument(alert, source.asPathNode2(), sink.asPathNode2(), msg, extra1, extra1String) and
extra2 = extra1 and
extra2String = extra1String
select alert, source, sink, msg, extra1, extra1String, extra2, extra2String

View File

@@ -0,0 +1,4 @@
---
category: minorAnalysis
---
* The precision of the query `cs/invalid-string-formatting` has been improved. More methods and more overloads of existing format like methods are taken into account by the query.

View File

@@ -13,3 +13,4 @@
- cs/useless-gethashcode-call
- cs/non-short-circuit
- cs/useless-assignment-to-local
- cs/invalid-string-formatting

View File

@@ -17,6 +17,12 @@
| Debug | Assert(bool, string, string, params Object[]) | args |
| Debug | Print(string, params Object[]) | args |
| Debug | WriteLine(string, params Object[]) | args |
| MemoryExtensions | TryWrite(Span<char>, IFormatProvider, CompositeFormat, out int, params Object[]) | args |
| MemoryExtensions | TryWrite(Span<char>, IFormatProvider, CompositeFormat, out int, params Object[]) | charsWritten |
| MemoryExtensions | TryWrite(Span<char>, IFormatProvider, CompositeFormat, out int, params ReadOnlySpan<object>) | args |
| MemoryExtensions | TryWrite(Span<char>, IFormatProvider, CompositeFormat, out int, params ReadOnlySpan<object>) | charsWritten |
| StringBuilder | AppendFormat(IFormatProvider, CompositeFormat, params Object[]) | args |
| StringBuilder | AppendFormat(IFormatProvider, CompositeFormat, params ReadOnlySpan<object>) | args |
| StringBuilder | AppendFormat(IFormatProvider, string, object) | arg0 |
| StringBuilder | AppendFormat(IFormatProvider, string, object, object) | arg0 |
| StringBuilder | AppendFormat(IFormatProvider, string, object, object) | arg1 |
@@ -51,6 +57,8 @@
| TextWriter | WriteLine(string, object, object, object) | arg2 |
| TextWriter | WriteLine(string, params Object[]) | arg |
| TextWriter | WriteLine(string, params ReadOnlySpan<object>) | arg |
| string | Format(IFormatProvider, CompositeFormat, params Object[]) | args |
| string | Format(IFormatProvider, CompositeFormat, params ReadOnlySpan<object>) | args |
| string | Format(IFormatProvider, string, object) | arg0 |
| string | Format(IFormatProvider, string, object, object) | arg0 |
| string | Format(IFormatProvider, string, object, object) | arg1 |

View File

@@ -1,4 +1,5 @@
using System;
using System.Globalization;
using System.Text;
class FormatInvalid
@@ -24,38 +25,38 @@ class FormatInvalid
String.Format("{0, -10 :0.000}", 1);
// BAD: Invalid format string
String.Format("{ 0}", 1);
String.Format("{ 0}", 1); // $ Alert
// BAD: Invalid format string
String.Format("{0,--1}", 1);
String.Format("{0,--1}", 1); // $ Alert
// BAD: Invalid format string
String.Format("{0:{}}", 1);
String.Format("{0:{}}", 1); // $ Alert
// BAD: Invalid format string
String.Format("%d", 1);
String.Format("%d", 1); // $ Alert
// BAD: } { in the middle.
String.Format("{{0}-{1}}", 0, 1);
String.Format("{{0}-{1}}", 0, 1); // $ Alert
// BAD: This is invalid
String.Format("{0}}", 0, 1);
String.Format("{0}}", 0, 1); // $ Alert
// BAD: Invalid
string.Format("{foo{0}}", 0);
string.Format("{foo{0}}", 0); // $ Alert
// GOOD: {{ is output as {
String.Format("{{sdc}}", 0);
String.Format("{{sdc}}{0}", 0);
// BAD: Invalid: Stray }
String.Format("}", 0);
String.Format("}{0}", 0); // $ Alert
// GOOD: {{ output as {
String.Format("new {0} ({1} => {{", 0);
String.Format("new {0} ({1} => {{", 0, 1);
// GOOD: Literal {{ and }}
String.Format("{{", "");
String.Format("{{{{}}", "");
String.Format("{0}{{", 0);
String.Format("{0}{{{{}}", 0);
}
IFormatProvider fp;
@@ -72,51 +73,88 @@ class FormatInvalid
Format("}", 0);
// BAD: All of these are format methods with an invalid string.
String.Format("}", 0);
String.Format("}", ps);
String.Format(fp, "}", ps);
String.Format("}", 0, 1);
String.Format("}", 0, 1, 2);
String.Format("}", 0, 1, 2, 3);
String.Format("}"); // $ Alert
String.Format("}", 0); // $ Alert
String.Format("}", ps); // $ Alert
String.Format(fp, "}", ps); // $ Alert
String.Format("}", 0, 1); // $ Alert
String.Format("}", 0, 1, 2); // $ Alert
String.Format("}", 0, 1, 2, 3); // $ Alert
sb.AppendFormat("}", 0);
sb.AppendFormat("}", ps);
sb.AppendFormat(fp, "}", ps);
sb.AppendFormat("}", 0, 1);
sb.AppendFormat("}", 0, 1, 2);
sb.AppendFormat("}", 0, 1, 2, 3);
sb.AppendFormat("}"); // $ Alert
sb.AppendFormat("}", 0); // $ Alert
sb.AppendFormat("}", ps); // $ Alert
sb.AppendFormat(fp, "}", ps); // $ Alert
sb.AppendFormat("}", 0, 1); // $ Alert
sb.AppendFormat("}", 0, 1, 2); // $ Alert
sb.AppendFormat("}", 0, 1, 2, 3); // $ Alert
Console.WriteLine("}", 0);
Console.WriteLine("}", ps);
Console.WriteLine("}", 0, 1);
Console.WriteLine("}", 0, 1, 2);
Console.WriteLine("}", 0, 1, 2, 3);
Console.WriteLine("}", 0); // $ Alert
Console.WriteLine("}", ps); // $ Alert
Console.WriteLine("}", 0, 1); // $ Alert
Console.WriteLine("}", 0, 1, 2); // $ Alert
Console.WriteLine("}", 0, 1, 2, 3); // $ Alert
tw.WriteLine("}", 0);
tw.WriteLine("}", ps);
tw.WriteLine("}", 0, 1);
tw.WriteLine("}", 0, 1, 2);
tw.WriteLine("}", 0, 1, 2, 3);
tw.WriteLine("}", 0); // $ Alert
tw.WriteLine("}", ps); // $ Alert
tw.WriteLine("}", 0, 1); // $ Alert
tw.WriteLine("}", 0, 1, 2); // $ Alert
tw.WriteLine("}", 0, 1, 2, 3); // $ Alert
System.Diagnostics.Debug.WriteLine("}", ps);
System.Diagnostics.Trace.TraceError("}", 0);
System.Diagnostics.Trace.TraceInformation("}", 0);
System.Diagnostics.Trace.TraceWarning("}", 0);
ts.TraceInformation("}", 0);
System.Diagnostics.Debug.WriteLine("}", ps); // $ Alert
System.Diagnostics.Trace.TraceError("}", 0); // $ Alert
System.Diagnostics.Trace.TraceInformation("}", 0); // $ Alert
System.Diagnostics.Trace.TraceWarning("}", 0); // $ Alert
ts.TraceInformation("}", 0); // $ Alert
Console.Write("}", 0);
Console.Write("}", 0, 1);
Console.Write("}", 0, 1, 2);
Console.Write("}", 0, 1, 2, 3);
Console.Write("}", 0); // $ Alert
Console.Write("}", 0, 1); // $ Alert
Console.Write("}", 0, 1, 2); // $ Alert
Console.Write("}", 0, 1, 2, 3); // $ Alert
System.Diagnostics.Debug.WriteLine("}", ""); // GOOD
System.Diagnostics.Debug.Write("}", ""); // GOOD
System.Diagnostics.Debug.Assert(true, "Error", "}", ps);
sw.Write("}", 0);
System.Diagnostics.Debug.Print("}", ps);
System.Diagnostics.Debug.Assert(true, "Error", "}", ps); // $ Alert
sw.Write("}", 0); // $ Alert
System.Diagnostics.Debug.Print("}", ps); // $ Alert
Console.WriteLine("}"); // GOOD
// The Following methods are not recognised as format methods.
Console.WriteLine("{0}"); // GOOD
Console.Write("{0}"); // GOOD
tw.WriteLine("{0}"); // GOOD
tw.Write("{0}"); // GOOD
System.Diagnostics.Debug.Print("{0}"); // GOOD
System.Diagnostics.Debug.WriteLine("{0}"); // GOOD
System.Diagnostics.Debug.Write("{0}"); // GOOD
System.Diagnostics.Trace.TraceError("{0}"); // GOOD
System.Diagnostics.Trace.TraceInformation("{0}"); // GOOD
System.Diagnostics.Trace.TraceWarning("{0}"); // GOOD
ts.TraceInformation("{0}"); // GOOD
}
void CompositeFormatMethods()
{
var format = CompositeFormat.Parse("}"); // $ Alert
// GOOD: Format is invalid and this flagged during parsing.
String.Format<string>(null, format, "");
String.Format<string, string>(null, format, "", "");
String.Format<string, string, string>(null, format, "", "", "");
sb.AppendFormat(null, format, "");
sb.AppendFormat<string>(null, format, "");
sb.AppendFormat<string, string>(null, format, "", "");
sb.AppendFormat<string, string, string>(null, format, "", "", "");
var span = new Span<char>();
span.TryWrite(null, format, out _);
span.TryWrite<object>(null, format, out _, new object());
span.TryWrite<object, object>(null, format, out _, new object(), new object());
span.TryWrite<object, object, object>(null, format, out _, "", "", "");
}
System.IO.StringWriter sw;

View File

@@ -1,160 +1,401 @@
edges
| FormatMissingArgument.cs:22:16:22:20 | "{1}" : String | FormatMissingArgument.cs:28:24:28:29 | format : String | provenance | |
| FormatMissingArgument.cs:28:24:28:29 | format : String | FormatMissingArgument.cs:31:23:31:28 | access to parameter format | provenance | |
nodes
| FormatInvalid.cs:9:23:9:27 | "{0}" | semmle.label | "{0}" |
| FormatInvalid.cs:12:23:12:29 | "{0,1}" | semmle.label | "{0,1}" |
| FormatInvalid.cs:15:23:15:31 | "{0, 1}" | semmle.label | "{0, 1}" |
| FormatInvalid.cs:18:23:18:30 | "{0,-1}" | semmle.label | "{0,-1}" |
| FormatInvalid.cs:21:23:21:33 | "{0:0.000}" | semmle.label | "{0:0.000}" |
| FormatInvalid.cs:24:23:24:39 | "{0, -10 :0.000}" | semmle.label | "{0, -10 :0.000}" |
| FormatInvalid.cs:27:23:27:28 | "{ 0}" | semmle.label | "{ 0}" |
| FormatInvalid.cs:30:23:30:31 | "{0,--1}" | semmle.label | "{0,--1}" |
| FormatInvalid.cs:33:23:33:30 | "{0:{}}" | semmle.label | "{0:{}}" |
| FormatInvalid.cs:36:23:36:26 | "%d" | semmle.label | "%d" |
| FormatInvalid.cs:39:23:39:33 | "{{0}-{1}}" | semmle.label | "{{0}-{1}}" |
| FormatInvalid.cs:42:23:42:28 | "{0}}" | semmle.label | "{0}}" |
| FormatInvalid.cs:45:23:45:32 | "{foo{0}}" | semmle.label | "{foo{0}}" |
| FormatInvalid.cs:48:23:48:31 | "{{sdc}}" | semmle.label | "{{sdc}}" |
| FormatInvalid.cs:51:23:51:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:54:23:54:42 | "new {0} ({1} => {{" | semmle.label | "new {0} ({1} => {{" |
| FormatInvalid.cs:57:23:57:26 | "{{" | semmle.label | "{{" |
| FormatInvalid.cs:58:23:58:30 | "{{{{}}" | semmle.label | "{{{{}}" |
| FormatInvalid.cs:75:23:75:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:76:23:76:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:77:27:77:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:78:23:78:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:79:23:79:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:80:23:80:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:82:25:82:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:83:25:83:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:84:29:84:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:85:25:85:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:86:25:86:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:87:25:87:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:89:27:89:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:90:27:90:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:91:27:91:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:92:27:92:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:93:27:93:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:95:22:95:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:96:22:96:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:97:22:97:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:98:22:98:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:99:22:99:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:101:44:101:46 | "}" | semmle.label | "}" |
| FormatInvalid.cs:102:45:102:47 | "}" | semmle.label | "}" |
| FormatInvalid.cs:103:51:103:53 | "}" | semmle.label | "}" |
| FormatInvalid.cs:104:47:104:49 | "}" | semmle.label | "}" |
| FormatInvalid.cs:105:29:105:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:107:23:107:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:108:23:108:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:109:23:109:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:110:23:110:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:115:56:115:58 | [assertion success] "}" | semmle.label | [assertion success] "}" |
| FormatInvalid.cs:116:18:116:20 | "}" | semmle.label | "}" |
| FormatInvalid.cs:117:40:117:42 | "}" | semmle.label | "}" |
| FormatInvalid.cs:119:27:119:29 | "}" | semmle.label | "}" |
| FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | semmle.label | "class {0} { }" |
| FormatInvalidGood.cs:7:30:7:46 | "class {0} {{ }}" | semmle.label | "class {0} {{ }}" |
| FormatMissingArgument.cs:8:23:8:27 | "{0}" | semmle.label | "{0}" |
| FormatMissingArgument.cs:11:23:11:27 | "{1}" | semmle.label | "{1}" |
| FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | semmle.label | "{2} {3}" |
| FormatMissingArgument.cs:17:23:17:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatMissingArgument.cs:20:23:20:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatMissingArgument.cs:22:16:22:20 | "{1}" : String | semmle.label | "{1}" : String |
| FormatMissingArgument.cs:25:27:25:31 | "{0}" | semmle.label | "{0}" |
| FormatMissingArgument.cs:28:24:28:29 | format : String | semmle.label | format : String |
| FormatMissingArgument.cs:31:23:31:28 | access to parameter format | semmle.label | access to parameter format |
| FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | semmle.label | "Hello {1} {2}" |
| FormatMissingArgumentGood.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatUnusedArgument.cs:8:23:8:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:11:23:11:25 | "X" | semmle.label | "X" |
| FormatUnusedArgument.cs:14:23:14:27 | "{0}" | semmle.label | "{0}" |
| FormatUnusedArgument.cs:17:23:17:31 | "{0} {0}" | semmle.label | "{0} {0}" |
| FormatUnusedArgument.cs:20:23:20:31 | "{1} {1}" | semmle.label | "{1} {1}" |
| FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | semmle.label | "abcdefg" |
| FormatUnusedArgument.cs:26:23:26:31 | "{{sdc}}" | semmle.label | "{{sdc}}" |
| FormatUnusedArgument.cs:29:23:29:33 | "{{{0:D}}}" | semmle.label | "{{{0:D}}}" |
| FormatUnusedArgument.cs:32:23:32:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatUnusedArgument.cs:35:23:35:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:38:23:38:29 | "{{0}}" | semmle.label | "{{0}}" |
| FormatUnusedArgument.cs:42:23:42:24 | "" | semmle.label | "" |
| FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | semmle.label | "Error processing file: {0}" |
| FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | semmle.label | "Error processing file: {1} ({1})" |
| FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | semmle.label | "Error processing file: %s (%d)" |
subpaths
#select
| FormatInvalid.cs:27:23:27:28 | "{ 0}" | FormatInvalid.cs:27:23:27:28 | "{ 0}" | FormatInvalid.cs:27:23:27:28 | "{ 0}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:27:9:27:32 | call to method Format | this | FormatInvalid.cs:27:9:27:32 | call to method Format | this |
| FormatInvalid.cs:30:23:30:31 | "{0,--1}" | FormatInvalid.cs:30:23:30:31 | "{0,--1}" | FormatInvalid.cs:30:23:30:31 | "{0,--1}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:30:9:30:35 | call to method Format | this | FormatInvalid.cs:30:9:30:35 | call to method Format | this |
| FormatInvalid.cs:33:23:33:30 | "{0:{}}" | FormatInvalid.cs:33:23:33:30 | "{0:{}}" | FormatInvalid.cs:33:23:33:30 | "{0:{}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:33:9:33:34 | call to method Format | this | FormatInvalid.cs:33:9:33:34 | call to method Format | this |
| FormatInvalid.cs:36:9:36:30 | call to method Format | FormatInvalid.cs:36:23:36:26 | "%d" | FormatInvalid.cs:36:23:36:26 | "%d" | The $@ ignores $@. | FormatInvalid.cs:36:23:36:26 | "%d" | format string | FormatInvalid.cs:36:29:36:29 | (...) ... | this supplied value |
| FormatInvalid.cs:39:23:39:33 | "{{0}-{1}}" | FormatInvalid.cs:39:23:39:33 | "{{0}-{1}}" | FormatInvalid.cs:39:23:39:33 | "{{0}-{1}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:39:9:39:40 | call to method Format | this | FormatInvalid.cs:39:9:39:40 | call to method Format | this |
| FormatInvalid.cs:42:23:42:28 | "{0}}" | FormatInvalid.cs:42:23:42:28 | "{0}}" | FormatInvalid.cs:42:23:42:28 | "{0}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:42:9:42:35 | call to method Format | this | FormatInvalid.cs:42:9:42:35 | call to method Format | this |
| FormatInvalid.cs:45:23:45:32 | "{foo{0}}" | FormatInvalid.cs:45:23:45:32 | "{foo{0}}" | FormatInvalid.cs:45:23:45:32 | "{foo{0}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:45:9:45:36 | call to method Format | this | FormatInvalid.cs:45:9:45:36 | call to method Format | this |
| FormatInvalid.cs:48:9:48:35 | call to method Format | FormatInvalid.cs:48:23:48:31 | "{{sdc}}" | FormatInvalid.cs:48:23:48:31 | "{{sdc}}" | The $@ ignores $@. | FormatInvalid.cs:48:23:48:31 | "{{sdc}}" | format string | FormatInvalid.cs:48:34:48:34 | (...) ... | this supplied value |
| FormatInvalid.cs:51:23:51:25 | "}" | FormatInvalid.cs:51:23:51:25 | "}" | FormatInvalid.cs:51:23:51:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:51:9:51:29 | call to method Format | this | FormatInvalid.cs:51:9:51:29 | call to method Format | this |
| FormatInvalid.cs:54:9:54:46 | call to method Format | FormatInvalid.cs:54:23:54:42 | "new {0} ({1} => {{" | FormatInvalid.cs:54:23:54:42 | "new {0} ({1} => {{" | Argument '{1}' has not been supplied to $@ format string. | FormatInvalid.cs:54:23:54:42 | "new {0} ({1} => {{" | this | FormatInvalid.cs:54:23:54:42 | "new {0} ({1} => {{" | this |
| FormatInvalid.cs:57:9:57:31 | call to method Format | FormatInvalid.cs:57:23:57:26 | "{{" | FormatInvalid.cs:57:23:57:26 | "{{" | The $@ ignores $@. | FormatInvalid.cs:57:23:57:26 | "{{" | format string | FormatInvalid.cs:57:29:57:30 | "" | this supplied value |
| FormatInvalid.cs:58:9:58:35 | call to method Format | FormatInvalid.cs:58:23:58:30 | "{{{{}}" | FormatInvalid.cs:58:23:58:30 | "{{{{}}" | The $@ ignores $@. | FormatInvalid.cs:58:23:58:30 | "{{{{}}" | format string | FormatInvalid.cs:58:33:58:34 | "" | this supplied value |
| FormatInvalid.cs:75:23:75:25 | "}" | FormatInvalid.cs:75:23:75:25 | "}" | FormatInvalid.cs:75:23:75:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:75:9:75:29 | call to method Format | this | FormatInvalid.cs:75:9:75:29 | call to method Format | this |
| FormatInvalid.cs:76:23:76:25 | "}" | FormatInvalid.cs:76:23:76:25 | "}" | FormatInvalid.cs:76:23:76:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:76:9:76:30 | call to method Format | this | FormatInvalid.cs:76:9:76:30 | call to method Format | this |
| FormatInvalid.cs:77:27:77:29 | "}" | FormatInvalid.cs:77:27:77:29 | "}" | FormatInvalid.cs:77:27:77:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:77:9:77:34 | call to method Format | this | FormatInvalid.cs:77:9:77:34 | call to method Format | this |
| FormatInvalid.cs:78:23:78:25 | "}" | FormatInvalid.cs:78:23:78:25 | "}" | FormatInvalid.cs:78:23:78:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:78:9:78:32 | call to method Format | this | FormatInvalid.cs:78:9:78:32 | call to method Format | this |
| FormatInvalid.cs:79:23:79:25 | "}" | FormatInvalid.cs:79:23:79:25 | "}" | FormatInvalid.cs:79:23:79:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:79:9:79:35 | call to method Format | this | FormatInvalid.cs:79:9:79:35 | call to method Format | this |
| FormatInvalid.cs:80:23:80:25 | "}" | FormatInvalid.cs:80:23:80:25 | "}" | FormatInvalid.cs:80:23:80:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:80:9:80:38 | call to method Format | this | FormatInvalid.cs:80:9:80:38 | call to method Format | this |
| FormatInvalid.cs:82:25:82:27 | "}" | FormatInvalid.cs:82:25:82:27 | "}" | FormatInvalid.cs:82:25:82:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:82:9:82:31 | call to method AppendFormat | this | FormatInvalid.cs:82:9:82:31 | call to method AppendFormat | this |
| FormatInvalid.cs:83:25:83:27 | "}" | FormatInvalid.cs:83:25:83:27 | "}" | FormatInvalid.cs:83:25:83:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:83:9:83:32 | call to method AppendFormat | this | FormatInvalid.cs:83:9:83:32 | call to method AppendFormat | this |
| FormatInvalid.cs:84:29:84:31 | "}" | FormatInvalid.cs:84:29:84:31 | "}" | FormatInvalid.cs:84:29:84:31 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:84:9:84:36 | call to method AppendFormat | this | FormatInvalid.cs:84:9:84:36 | call to method AppendFormat | this |
| FormatInvalid.cs:85:25:85:27 | "}" | FormatInvalid.cs:85:25:85:27 | "}" | FormatInvalid.cs:85:25:85:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:85:9:85:34 | call to method AppendFormat | this | FormatInvalid.cs:85:9:85:34 | call to method AppendFormat | this |
| FormatInvalid.cs:86:25:86:27 | "}" | FormatInvalid.cs:86:25:86:27 | "}" | FormatInvalid.cs:86:25:86:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:86:9:86:37 | call to method AppendFormat | this | FormatInvalid.cs:86:9:86:37 | call to method AppendFormat | this |
| FormatInvalid.cs:87:25:87:27 | "}" | FormatInvalid.cs:87:25:87:27 | "}" | FormatInvalid.cs:87:25:87:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:87:9:87:40 | call to method AppendFormat | this | FormatInvalid.cs:87:9:87:40 | call to method AppendFormat | this |
| FormatInvalid.cs:89:27:89:29 | "}" | FormatInvalid.cs:89:27:89:29 | "}" | FormatInvalid.cs:89:27:89:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:89:9:89:33 | call to method WriteLine | this | FormatInvalid.cs:89:9:89:33 | call to method WriteLine | this |
| FormatInvalid.cs:90:27:90:29 | "}" | FormatInvalid.cs:90:27:90:29 | "}" | FormatInvalid.cs:90:27:90:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:90:9:90:34 | call to method WriteLine | this | FormatInvalid.cs:90:9:90:34 | call to method WriteLine | this |
| FormatInvalid.cs:91:27:91:29 | "}" | FormatInvalid.cs:91:27:91:29 | "}" | FormatInvalid.cs:91:27:91:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:91:9:91:36 | call to method WriteLine | this | FormatInvalid.cs:91:9:91:36 | call to method WriteLine | this |
| FormatInvalid.cs:92:27:92:29 | "}" | FormatInvalid.cs:92:27:92:29 | "}" | FormatInvalid.cs:92:27:92:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:92:9:92:39 | call to method WriteLine | this | FormatInvalid.cs:92:9:92:39 | call to method WriteLine | this |
| FormatInvalid.cs:93:27:93:29 | "}" | FormatInvalid.cs:93:27:93:29 | "}" | FormatInvalid.cs:93:27:93:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:93:9:93:42 | call to method WriteLine | this | FormatInvalid.cs:93:9:93:42 | call to method WriteLine | this |
| FormatInvalid.cs:95:22:95:24 | "}" | FormatInvalid.cs:95:22:95:24 | "}" | FormatInvalid.cs:95:22:95:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:95:9:95:28 | call to method WriteLine | this | FormatInvalid.cs:95:9:95:28 | call to method WriteLine | this |
| FormatInvalid.cs:96:22:96:24 | "}" | FormatInvalid.cs:96:22:96:24 | "}" | FormatInvalid.cs:96:22:96:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:96:9:96:29 | call to method WriteLine | this | FormatInvalid.cs:96:9:96:29 | call to method WriteLine | this |
| FormatInvalid.cs:97:22:97:24 | "}" | FormatInvalid.cs:97:22:97:24 | "}" | FormatInvalid.cs:97:22:97:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:97:9:97:31 | call to method WriteLine | this | FormatInvalid.cs:97:9:97:31 | call to method WriteLine | this |
| FormatInvalid.cs:98:22:98:24 | "}" | FormatInvalid.cs:98:22:98:24 | "}" | FormatInvalid.cs:98:22:98:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:98:9:98:34 | call to method WriteLine | this | FormatInvalid.cs:98:9:98:34 | call to method WriteLine | this |
| FormatInvalid.cs:99:22:99:24 | "}" | FormatInvalid.cs:99:22:99:24 | "}" | FormatInvalid.cs:99:22:99:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:99:9:99:37 | call to method WriteLine | this | FormatInvalid.cs:99:9:99:37 | call to method WriteLine | this |
| FormatInvalid.cs:101:44:101:46 | "}" | FormatInvalid.cs:101:44:101:46 | "}" | FormatInvalid.cs:101:44:101:46 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:101:9:101:51 | call to method WriteLine | this | FormatInvalid.cs:101:9:101:51 | call to method WriteLine | this |
| FormatInvalid.cs:102:45:102:47 | "}" | FormatInvalid.cs:102:45:102:47 | "}" | FormatInvalid.cs:102:45:102:47 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:102:9:102:51 | call to method TraceError | this | FormatInvalid.cs:102:9:102:51 | call to method TraceError | this |
| FormatInvalid.cs:103:51:103:53 | "}" | FormatInvalid.cs:103:51:103:53 | "}" | FormatInvalid.cs:103:51:103:53 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:103:9:103:57 | call to method TraceInformation | this | FormatInvalid.cs:103:9:103:57 | call to method TraceInformation | this |
| FormatInvalid.cs:104:47:104:49 | "}" | FormatInvalid.cs:104:47:104:49 | "}" | FormatInvalid.cs:104:47:104:49 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:104:9:104:53 | call to method TraceWarning | this | FormatInvalid.cs:104:9:104:53 | call to method TraceWarning | this |
| FormatInvalid.cs:105:29:105:31 | "}" | FormatInvalid.cs:105:29:105:31 | "}" | FormatInvalid.cs:105:29:105:31 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:105:9:105:35 | call to method TraceInformation | this | FormatInvalid.cs:105:9:105:35 | call to method TraceInformation | this |
| FormatInvalid.cs:107:23:107:25 | "}" | FormatInvalid.cs:107:23:107:25 | "}" | FormatInvalid.cs:107:23:107:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:107:9:107:29 | call to method Write | this | FormatInvalid.cs:107:9:107:29 | call to method Write | this |
| FormatInvalid.cs:108:23:108:25 | "}" | FormatInvalid.cs:108:23:108:25 | "}" | FormatInvalid.cs:108:23:108:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:108:9:108:32 | call to method Write | this | FormatInvalid.cs:108:9:108:32 | call to method Write | this |
| FormatInvalid.cs:109:23:109:25 | "}" | FormatInvalid.cs:109:23:109:25 | "}" | FormatInvalid.cs:109:23:109:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:109:9:109:35 | call to method Write | this | FormatInvalid.cs:109:9:109:35 | call to method Write | this |
| FormatInvalid.cs:110:23:110:25 | "}" | FormatInvalid.cs:110:23:110:25 | "}" | FormatInvalid.cs:110:23:110:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:110:9:110:38 | call to method Write | this | FormatInvalid.cs:110:9:110:38 | call to method Write | this |
| FormatInvalid.cs:115:56:115:58 | "}" | FormatInvalid.cs:115:56:115:58 | [assertion success] "}" | FormatInvalid.cs:115:56:115:58 | [assertion success] "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:115:9:115:63 | call to method Assert | this | FormatInvalid.cs:115:9:115:63 | call to method Assert | this |
| FormatInvalid.cs:116:18:116:20 | "}" | FormatInvalid.cs:116:18:116:20 | "}" | FormatInvalid.cs:116:18:116:20 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:116:9:116:24 | call to method Write | this | FormatInvalid.cs:116:9:116:24 | call to method Write | this |
| FormatInvalid.cs:117:40:117:42 | "}" | FormatInvalid.cs:117:40:117:42 | "}" | FormatInvalid.cs:117:40:117:42 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:117:9:117:47 | call to method Print | this | FormatInvalid.cs:117:9:117:47 | call to method Print | this |
| FormatInvalid.cs:28:23:28:28 | "{ 0}" | FormatInvalid.cs:28:23:28:28 | "{ 0}" | FormatInvalid.cs:28:23:28:28 | "{ 0}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:28:9:28:32 | call to method Format | this | FormatInvalid.cs:28:9:28:32 | call to method Format | this |
| FormatInvalid.cs:31:23:31:31 | "{0,--1}" | FormatInvalid.cs:31:23:31:31 | "{0,--1}" | FormatInvalid.cs:31:23:31:31 | "{0,--1}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:31:9:31:35 | call to method Format | this | FormatInvalid.cs:31:9:31:35 | call to method Format | this |
| FormatInvalid.cs:34:23:34:30 | "{0:{}}" | FormatInvalid.cs:34:23:34:30 | "{0:{}}" | FormatInvalid.cs:34:23:34:30 | "{0:{}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:34:9:34:34 | call to method Format | this | FormatInvalid.cs:34:9:34:34 | call to method Format | this |
| FormatInvalid.cs:37:9:37:30 | call to method Format | FormatInvalid.cs:37:23:37:26 | "%d" | FormatInvalid.cs:37:23:37:26 | "%d" | The $@ ignores $@. | FormatInvalid.cs:37:23:37:26 | "%d" | format string | FormatInvalid.cs:37:29:37:29 | (...) ... | this supplied value |
| FormatInvalid.cs:40:23:40:33 | "{{0}-{1}}" | FormatInvalid.cs:40:23:40:33 | "{{0}-{1}}" | FormatInvalid.cs:40:23:40:33 | "{{0}-{1}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:40:9:40:40 | call to method Format | this | FormatInvalid.cs:40:9:40:40 | call to method Format | this |
| FormatInvalid.cs:43:23:43:28 | "{0}}" | FormatInvalid.cs:43:23:43:28 | "{0}}" | FormatInvalid.cs:43:23:43:28 | "{0}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:43:9:43:35 | call to method Format | this | FormatInvalid.cs:43:9:43:35 | call to method Format | this |
| FormatInvalid.cs:46:23:46:32 | "{foo{0}}" | FormatInvalid.cs:46:23:46:32 | "{foo{0}}" | FormatInvalid.cs:46:23:46:32 | "{foo{0}}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:46:9:46:36 | call to method Format | this | FormatInvalid.cs:46:9:46:36 | call to method Format | this |
| FormatInvalid.cs:52:23:52:28 | "}{0}" | FormatInvalid.cs:52:23:52:28 | "}{0}" | FormatInvalid.cs:52:23:52:28 | "}{0}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:52:9:52:32 | call to method Format | this | FormatInvalid.cs:52:9:52:32 | call to method Format | this |
| FormatInvalid.cs:76:23:76:25 | "}" | FormatInvalid.cs:76:23:76:25 | "}" | FormatInvalid.cs:76:23:76:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:76:9:76:26 | call to method Format | this | FormatInvalid.cs:76:9:76:26 | call to method Format | this |
| FormatInvalid.cs:77:23:77:25 | "}" | FormatInvalid.cs:77:23:77:25 | "}" | FormatInvalid.cs:77:23:77:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:77:9:77:29 | call to method Format | this | FormatInvalid.cs:77:9:77:29 | call to method Format | this |
| FormatInvalid.cs:78:23:78:25 | "}" | FormatInvalid.cs:78:23:78:25 | "}" | FormatInvalid.cs:78:23:78:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:78:9:78:30 | call to method Format | this | FormatInvalid.cs:78:9:78:30 | call to method Format | this |
| FormatInvalid.cs:79:27:79:29 | "}" | FormatInvalid.cs:79:27:79:29 | "}" | FormatInvalid.cs:79:27:79:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:79:9:79:34 | call to method Format | this | FormatInvalid.cs:79:9:79:34 | call to method Format | this |
| FormatInvalid.cs:80:23:80:25 | "}" | FormatInvalid.cs:80:23:80:25 | "}" | FormatInvalid.cs:80:23:80:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:80:9:80:32 | call to method Format | this | FormatInvalid.cs:80:9:80:32 | call to method Format | this |
| FormatInvalid.cs:81:23:81:25 | "}" | FormatInvalid.cs:81:23:81:25 | "}" | FormatInvalid.cs:81:23:81:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:81:9:81:35 | call to method Format | this | FormatInvalid.cs:81:9:81:35 | call to method Format | this |
| FormatInvalid.cs:82:23:82:25 | "}" | FormatInvalid.cs:82:23:82:25 | "}" | FormatInvalid.cs:82:23:82:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:82:9:82:38 | call to method Format | this | FormatInvalid.cs:82:9:82:38 | call to method Format | this |
| FormatInvalid.cs:84:25:84:27 | "}" | FormatInvalid.cs:84:25:84:27 | "}" | FormatInvalid.cs:84:25:84:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:84:9:84:28 | call to method AppendFormat | this | FormatInvalid.cs:84:9:84:28 | call to method AppendFormat | this |
| FormatInvalid.cs:85:25:85:27 | "}" | FormatInvalid.cs:85:25:85:27 | "}" | FormatInvalid.cs:85:25:85:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:85:9:85:31 | call to method AppendFormat | this | FormatInvalid.cs:85:9:85:31 | call to method AppendFormat | this |
| FormatInvalid.cs:86:25:86:27 | "}" | FormatInvalid.cs:86:25:86:27 | "}" | FormatInvalid.cs:86:25:86:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:86:9:86:32 | call to method AppendFormat | this | FormatInvalid.cs:86:9:86:32 | call to method AppendFormat | this |
| FormatInvalid.cs:87:29:87:31 | "}" | FormatInvalid.cs:87:29:87:31 | "}" | FormatInvalid.cs:87:29:87:31 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:87:9:87:36 | call to method AppendFormat | this | FormatInvalid.cs:87:9:87:36 | call to method AppendFormat | this |
| FormatInvalid.cs:88:25:88:27 | "}" | FormatInvalid.cs:88:25:88:27 | "}" | FormatInvalid.cs:88:25:88:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:88:9:88:34 | call to method AppendFormat | this | FormatInvalid.cs:88:9:88:34 | call to method AppendFormat | this |
| FormatInvalid.cs:89:25:89:27 | "}" | FormatInvalid.cs:89:25:89:27 | "}" | FormatInvalid.cs:89:25:89:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:89:9:89:37 | call to method AppendFormat | this | FormatInvalid.cs:89:9:89:37 | call to method AppendFormat | this |
| FormatInvalid.cs:90:25:90:27 | "}" | FormatInvalid.cs:90:25:90:27 | "}" | FormatInvalid.cs:90:25:90:27 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:90:9:90:40 | call to method AppendFormat | this | FormatInvalid.cs:90:9:90:40 | call to method AppendFormat | this |
| FormatInvalid.cs:92:27:92:29 | "}" | FormatInvalid.cs:92:27:92:29 | "}" | FormatInvalid.cs:92:27:92:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:92:9:92:33 | call to method WriteLine | this | FormatInvalid.cs:92:9:92:33 | call to method WriteLine | this |
| FormatInvalid.cs:93:27:93:29 | "}" | FormatInvalid.cs:93:27:93:29 | "}" | FormatInvalid.cs:93:27:93:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:93:9:93:34 | call to method WriteLine | this | FormatInvalid.cs:93:9:93:34 | call to method WriteLine | this |
| FormatInvalid.cs:94:27:94:29 | "}" | FormatInvalid.cs:94:27:94:29 | "}" | FormatInvalid.cs:94:27:94:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:94:9:94:36 | call to method WriteLine | this | FormatInvalid.cs:94:9:94:36 | call to method WriteLine | this |
| FormatInvalid.cs:95:27:95:29 | "}" | FormatInvalid.cs:95:27:95:29 | "}" | FormatInvalid.cs:95:27:95:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:95:9:95:39 | call to method WriteLine | this | FormatInvalid.cs:95:9:95:39 | call to method WriteLine | this |
| FormatInvalid.cs:96:27:96:29 | "}" | FormatInvalid.cs:96:27:96:29 | "}" | FormatInvalid.cs:96:27:96:29 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:96:9:96:42 | call to method WriteLine | this | FormatInvalid.cs:96:9:96:42 | call to method WriteLine | this |
| FormatInvalid.cs:98:22:98:24 | "}" | FormatInvalid.cs:98:22:98:24 | "}" | FormatInvalid.cs:98:22:98:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:98:9:98:28 | call to method WriteLine | this | FormatInvalid.cs:98:9:98:28 | call to method WriteLine | this |
| FormatInvalid.cs:99:22:99:24 | "}" | FormatInvalid.cs:99:22:99:24 | "}" | FormatInvalid.cs:99:22:99:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:99:9:99:29 | call to method WriteLine | this | FormatInvalid.cs:99:9:99:29 | call to method WriteLine | this |
| FormatInvalid.cs:100:22:100:24 | "}" | FormatInvalid.cs:100:22:100:24 | "}" | FormatInvalid.cs:100:22:100:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:100:9:100:31 | call to method WriteLine | this | FormatInvalid.cs:100:9:100:31 | call to method WriteLine | this |
| FormatInvalid.cs:101:22:101:24 | "}" | FormatInvalid.cs:101:22:101:24 | "}" | FormatInvalid.cs:101:22:101:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:101:9:101:34 | call to method WriteLine | this | FormatInvalid.cs:101:9:101:34 | call to method WriteLine | this |
| FormatInvalid.cs:102:22:102:24 | "}" | FormatInvalid.cs:102:22:102:24 | "}" | FormatInvalid.cs:102:22:102:24 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:102:9:102:37 | call to method WriteLine | this | FormatInvalid.cs:102:9:102:37 | call to method WriteLine | this |
| FormatInvalid.cs:104:44:104:46 | "}" | FormatInvalid.cs:104:44:104:46 | "}" | FormatInvalid.cs:104:44:104:46 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:104:9:104:51 | call to method WriteLine | this | FormatInvalid.cs:104:9:104:51 | call to method WriteLine | this |
| FormatInvalid.cs:105:45:105:47 | "}" | FormatInvalid.cs:105:45:105:47 | "}" | FormatInvalid.cs:105:45:105:47 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:105:9:105:51 | call to method TraceError | this | FormatInvalid.cs:105:9:105:51 | call to method TraceError | this |
| FormatInvalid.cs:106:51:106:53 | "}" | FormatInvalid.cs:106:51:106:53 | "}" | FormatInvalid.cs:106:51:106:53 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:106:9:106:57 | call to method TraceInformation | this | FormatInvalid.cs:106:9:106:57 | call to method TraceInformation | this |
| FormatInvalid.cs:107:47:107:49 | "}" | FormatInvalid.cs:107:47:107:49 | "}" | FormatInvalid.cs:107:47:107:49 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:107:9:107:53 | call to method TraceWarning | this | FormatInvalid.cs:107:9:107:53 | call to method TraceWarning | this |
| FormatInvalid.cs:108:29:108:31 | "}" | FormatInvalid.cs:108:29:108:31 | "}" | FormatInvalid.cs:108:29:108:31 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:108:9:108:35 | call to method TraceInformation | this | FormatInvalid.cs:108:9:108:35 | call to method TraceInformation | this |
| FormatInvalid.cs:110:23:110:25 | "}" | FormatInvalid.cs:110:23:110:25 | "}" | FormatInvalid.cs:110:23:110:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:110:9:110:29 | call to method Write | this | FormatInvalid.cs:110:9:110:29 | call to method Write | this |
| FormatInvalid.cs:111:23:111:25 | "}" | FormatInvalid.cs:111:23:111:25 | "}" | FormatInvalid.cs:111:23:111:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:111:9:111:32 | call to method Write | this | FormatInvalid.cs:111:9:111:32 | call to method Write | this |
| FormatInvalid.cs:112:23:112:25 | "}" | FormatInvalid.cs:112:23:112:25 | "}" | FormatInvalid.cs:112:23:112:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:112:9:112:35 | call to method Write | this | FormatInvalid.cs:112:9:112:35 | call to method Write | this |
| FormatInvalid.cs:113:23:113:25 | "}" | FormatInvalid.cs:113:23:113:25 | "}" | FormatInvalid.cs:113:23:113:25 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:113:9:113:38 | call to method Write | this | FormatInvalid.cs:113:9:113:38 | call to method Write | this |
| FormatInvalid.cs:118:56:118:58 | "}" | FormatInvalid.cs:118:56:118:58 | [assertion success] "}" | FormatInvalid.cs:118:56:118:58 | [assertion success] "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:118:9:118:63 | call to method Assert | this | FormatInvalid.cs:118:9:118:63 | call to method Assert | this |
| FormatInvalid.cs:119:18:119:20 | "}" | FormatInvalid.cs:119:18:119:20 | "}" | FormatInvalid.cs:119:18:119:20 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:119:9:119:24 | call to method Write | this | FormatInvalid.cs:119:9:119:24 | call to method Write | this |
| FormatInvalid.cs:120:40:120:42 | "}" | FormatInvalid.cs:120:40:120:42 | "}" | FormatInvalid.cs:120:40:120:42 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:120:9:120:47 | call to method Print | this | FormatInvalid.cs:120:9:120:47 | call to method Print | this |
| FormatInvalid.cs:140:44:140:46 | "}" | FormatInvalid.cs:140:44:140:46 | "}" | FormatInvalid.cs:140:44:140:46 | "}" | Invalid format string used in $@ formatting call. | FormatInvalid.cs:140:22:140:47 | call to method Parse | this | FormatInvalid.cs:140:22:140:47 | call to method Parse | this |
| FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | Invalid format string used in $@ formatting call. | FormatInvalidBad.cs:7:16:7:50 | call to method Format | this | FormatInvalidBad.cs:7:16:7:50 | call to method Format | this |
| FormatMissingArgument.cs:11:9:11:31 | call to method Format | FormatMissingArgument.cs:11:23:11:27 | "{1}" | FormatMissingArgument.cs:11:23:11:27 | "{1}" | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:11:23:11:27 | "{1}" | this | FormatMissingArgument.cs:11:23:11:27 | "{1}" | this |
| FormatMissingArgument.cs:11:9:11:31 | call to method Format | FormatMissingArgument.cs:11:23:11:27 | "{1}" | FormatMissingArgument.cs:11:23:11:27 | "{1}" | The $@ ignores $@. | FormatMissingArgument.cs:11:23:11:27 | "{1}" | format string | FormatMissingArgument.cs:11:30:11:30 | (...) ... | this supplied value |
| FormatMissingArgument.cs:14:9:14:38 | call to method Format | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | this | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | this |
| FormatMissingArgument.cs:14:9:14:38 | call to method Format | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | Argument '{3}' has not been supplied to $@ format string. | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | this | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | this |
| FormatMissingArgument.cs:14:9:14:38 | call to method Format | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | The $@ ignores $@. | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | format string | FormatMissingArgument.cs:14:34:14:34 | (...) ... | this supplied value |
| FormatMissingArgument.cs:14:9:14:38 | call to method Format | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | The $@ ignores $@. | FormatMissingArgument.cs:14:23:14:31 | "{2} {3}" | format string | FormatMissingArgument.cs:14:37:14:37 | (...) ... | this supplied value |
| FormatMissingArgument.cs:25:9:25:32 | call to method WriteLine | FormatMissingArgument.cs:25:27:25:31 | "{0}" | FormatMissingArgument.cs:25:27:25:31 | "{0}" | Argument '{0}' has not been supplied to $@ format string. | FormatMissingArgument.cs:25:27:25:31 | "{0}" | this | FormatMissingArgument.cs:25:27:25:31 | "{0}" | this |
| FormatMissingArgument.cs:31:9:31:32 | call to method Format | FormatMissingArgument.cs:22:16:22:20 | "{1}" : String | FormatMissingArgument.cs:31:23:31:28 | access to parameter format | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:22:16:22:20 | "{1}" | this | FormatMissingArgument.cs:22:16:22:20 | "{1}" | this |
| FormatMissingArgument.cs:31:9:31:32 | call to method Format | FormatMissingArgument.cs:22:16:22:20 | "{1}" : String | FormatMissingArgument.cs:31:23:31:28 | access to parameter format | The $@ ignores $@. | FormatMissingArgument.cs:22:16:22:20 | "{1}" | format string | FormatMissingArgument.cs:31:31:31:31 | (...) ... | this supplied value |
| FormatMissingArgument.cs:12:9:12:31 | call to method Format | FormatMissingArgument.cs:12:23:12:27 | "{1}" | FormatMissingArgument.cs:12:23:12:27 | "{1}" | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:12:23:12:27 | "{1}" | this | FormatMissingArgument.cs:12:23:12:27 | "{1}" | this |
| FormatMissingArgument.cs:12:9:12:31 | call to method Format | FormatMissingArgument.cs:12:23:12:27 | "{1}" | FormatMissingArgument.cs:12:23:12:27 | "{1}" | The $@ ignores $@. | FormatMissingArgument.cs:12:23:12:27 | "{1}" | format string | FormatMissingArgument.cs:12:30:12:30 | (...) ... | this supplied value |
| FormatMissingArgument.cs:15:9:15:38 | call to method Format | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | this | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | this |
| FormatMissingArgument.cs:15:9:15:38 | call to method Format | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | Argument '{3}' has not been supplied to $@ format string. | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | this | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | this |
| FormatMissingArgument.cs:15:9:15:38 | call to method Format | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | The $@ ignores $@. | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | format string | FormatMissingArgument.cs:15:34:15:34 | (...) ... | this supplied value |
| FormatMissingArgument.cs:15:9:15:38 | call to method Format | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | The $@ ignores $@. | FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | format string | FormatMissingArgument.cs:15:37:15:37 | (...) ... | this supplied value |
| FormatMissingArgument.cs:32:9:32:32 | call to method Format | FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | FormatMissingArgument.cs:32:23:32:28 | access to parameter format | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:26:16:26:20 | "{1}" | this | FormatMissingArgument.cs:26:16:26:20 | "{1}" | this |
| FormatMissingArgument.cs:32:9:32:32 | call to method Format | FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | FormatMissingArgument.cs:32:23:32:28 | access to parameter format | The $@ ignores $@. | FormatMissingArgument.cs:26:16:26:20 | "{1}" | format string | FormatMissingArgument.cs:32:31:32:31 | (...) ... | this supplied value |
| FormatMissingArgument.cs:46:9:46:48 | call to method Format<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:46:37:46:43 | access to local variable format1 | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this |
| FormatMissingArgument.cs:46:9:46:48 | call to method Format<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:46:37:46:43 | access to local variable format1 | The $@ ignores $@. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | format string | FormatMissingArgument.cs:46:46:46:47 | "" | this supplied value |
| FormatMissingArgument.cs:52:9:52:61 | call to method Format<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:52:9:52:61 | call to method Format<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | Argument '{3}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:52:9:52:61 | call to method Format<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:52:55:52:56 | "" | this supplied value |
| FormatMissingArgument.cs:52:9:52:61 | call to method Format<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:52:59:52:60 | "" | this supplied value |
| FormatMissingArgument.cs:60:9:60:42 | call to method AppendFormat<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:60:31:60:37 | access to local variable format1 | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this |
| FormatMissingArgument.cs:60:9:60:42 | call to method AppendFormat<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:60:31:60:37 | access to local variable format1 | The $@ ignores $@. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | format string | FormatMissingArgument.cs:60:40:60:41 | "" | this supplied value |
| FormatMissingArgument.cs:61:9:61:50 | call to method AppendFormat<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:61:39:61:45 | access to local variable format1 | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this |
| FormatMissingArgument.cs:61:9:61:50 | call to method AppendFormat<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:61:39:61:45 | access to local variable format1 | The $@ ignores $@. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | format string | FormatMissingArgument.cs:61:48:61:49 | "" | this supplied value |
| FormatMissingArgument.cs:67:9:67:63 | call to method AppendFormat<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:67:9:67:63 | call to method AppendFormat<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | Argument '{3}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:67:9:67:63 | call to method AppendFormat<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:67:57:67:58 | "" | this supplied value |
| FormatMissingArgument.cs:67:9:67:63 | call to method AppendFormat<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:67:61:67:62 | "" | this supplied value |
| FormatMissingArgument.cs:77:9:77:47 | call to method TryWrite<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:77:29:77:35 | access to local variable format1 | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this |
| FormatMissingArgument.cs:77:9:77:47 | call to method TryWrite<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:77:29:77:35 | access to local variable format1 | The $@ ignores $@. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | format string | FormatMissingArgument.cs:77:45:77:46 | "" | this supplied value |
| FormatMissingArgument.cs:78:9:78:55 | call to method TryWrite<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:78:37:78:43 | access to local variable format1 | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this | FormatMissingArgument.cs:38:45:38:49 | "{1}" | this |
| FormatMissingArgument.cs:78:9:78:55 | call to method TryWrite<String> | FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:78:37:78:43 | access to local variable format1 | The $@ ignores $@. | FormatMissingArgument.cs:38:45:38:49 | "{1}" | format string | FormatMissingArgument.cs:78:53:78:54 | "" | this supplied value |
| FormatMissingArgument.cs:84:9:84:68 | call to method TryWrite<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:84:9:84:68 | call to method TryWrite<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | Argument '{3}' has not been supplied to $@ format string. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | this |
| FormatMissingArgument.cs:84:9:84:68 | call to method TryWrite<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:84:62:84:63 | "" | this supplied value |
| FormatMissingArgument.cs:84:9:84:68 | call to method TryWrite<String,String> | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | The $@ ignores $@. | FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | format string | FormatMissingArgument.cs:84:66:84:67 | "" | this supplied value |
| FormatMissingArgumentBad.cs:7:9:7:49 | call to method WriteLine | FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | Argument '{1}' has not been supplied to $@ format string. | FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | this | FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | this |
| FormatMissingArgumentBad.cs:8:9:8:55 | call to method WriteLine | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | Argument '{2}' has not been supplied to $@ format string. | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | this | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | this |
| FormatMissingArgumentBad.cs:8:9:8:55 | call to method WriteLine | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | The $@ ignores $@. | FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | format string | FormatMissingArgumentBad.cs:8:44:8:48 | access to parameter first | this supplied value |
| FormatUnusedArgument.cs:11:9:11:29 | call to method Format | FormatUnusedArgument.cs:11:23:11:25 | "X" | FormatUnusedArgument.cs:11:23:11:25 | "X" | The $@ ignores $@. | FormatUnusedArgument.cs:11:23:11:25 | "X" | format string | FormatUnusedArgument.cs:11:28:11:28 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:14:9:14:34 | call to method Format | FormatUnusedArgument.cs:14:23:14:27 | "{0}" | FormatUnusedArgument.cs:14:23:14:27 | "{0}" | The $@ ignores $@. | FormatUnusedArgument.cs:14:23:14:27 | "{0}" | format string | FormatUnusedArgument.cs:14:33:14:33 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:17:9:17:38 | call to method Format | FormatUnusedArgument.cs:17:23:17:31 | "{0} {0}" | FormatUnusedArgument.cs:17:23:17:31 | "{0} {0}" | The $@ ignores $@. | FormatUnusedArgument.cs:17:23:17:31 | "{0} {0}" | format string | FormatUnusedArgument.cs:17:37:17:37 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:20:9:20:38 | call to method Format | FormatUnusedArgument.cs:20:23:20:31 | "{1} {1}" | FormatUnusedArgument.cs:20:23:20:31 | "{1} {1}" | The $@ ignores $@. | FormatUnusedArgument.cs:20:23:20:31 | "{1} {1}" | format string | FormatUnusedArgument.cs:20:34:20:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:23:9:23:41 | call to method Format | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | format string | FormatUnusedArgument.cs:23:34:23:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:23:9:23:41 | call to method Format | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | format string | FormatUnusedArgument.cs:23:37:23:37 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:23:9:23:41 | call to method Format | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:23:23:23:31 | "abcdefg" | format string | FormatUnusedArgument.cs:23:40:23:40 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:26:9:26:35 | call to method Format | FormatUnusedArgument.cs:26:23:26:31 | "{{sdc}}" | FormatUnusedArgument.cs:26:23:26:31 | "{{sdc}}" | The $@ ignores $@. | FormatUnusedArgument.cs:26:23:26:31 | "{{sdc}}" | format string | FormatUnusedArgument.cs:26:34:26:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:38:9:38:33 | call to method Format | FormatUnusedArgument.cs:38:23:38:29 | "{{0}}" | FormatUnusedArgument.cs:38:23:38:29 | "{{0}}" | The $@ ignores $@. | FormatUnusedArgument.cs:38:23:38:29 | "{{0}}" | format string | FormatUnusedArgument.cs:38:32:38:32 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:12:9:12:29 | call to method Format | FormatUnusedArgument.cs:12:23:12:25 | "X" | FormatUnusedArgument.cs:12:23:12:25 | "X" | The $@ ignores $@. | FormatUnusedArgument.cs:12:23:12:25 | "X" | format string | FormatUnusedArgument.cs:12:28:12:28 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:15:9:15:34 | call to method Format | FormatUnusedArgument.cs:15:23:15:27 | "{0}" | FormatUnusedArgument.cs:15:23:15:27 | "{0}" | The $@ ignores $@. | FormatUnusedArgument.cs:15:23:15:27 | "{0}" | format string | FormatUnusedArgument.cs:15:33:15:33 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:18:9:18:38 | call to method Format | FormatUnusedArgument.cs:18:23:18:31 | "{0} {0}" | FormatUnusedArgument.cs:18:23:18:31 | "{0} {0}" | The $@ ignores $@. | FormatUnusedArgument.cs:18:23:18:31 | "{0} {0}" | format string | FormatUnusedArgument.cs:18:37:18:37 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:21:9:21:38 | call to method Format | FormatUnusedArgument.cs:21:23:21:31 | "{1} {1}" | FormatUnusedArgument.cs:21:23:21:31 | "{1} {1}" | The $@ ignores $@. | FormatUnusedArgument.cs:21:23:21:31 | "{1} {1}" | format string | FormatUnusedArgument.cs:21:34:21:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:24:9:24:41 | call to method Format | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | format string | FormatUnusedArgument.cs:24:34:24:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:24:9:24:41 | call to method Format | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | format string | FormatUnusedArgument.cs:24:37:24:37 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:24:9:24:41 | call to method Format | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | The $@ ignores $@. | FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | format string | FormatUnusedArgument.cs:24:40:24:40 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:27:9:27:35 | call to method Format | FormatUnusedArgument.cs:27:23:27:31 | "{{sdc}}" | FormatUnusedArgument.cs:27:23:27:31 | "{{sdc}}" | The $@ ignores $@. | FormatUnusedArgument.cs:27:23:27:31 | "{{sdc}}" | format string | FormatUnusedArgument.cs:27:34:27:34 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:39:9:39:33 | call to method Format | FormatUnusedArgument.cs:39:23:39:29 | "{{0}}" | FormatUnusedArgument.cs:39:23:39:29 | "{{0}}" | The $@ ignores $@. | FormatUnusedArgument.cs:39:23:39:29 | "{{0}}" | format string | FormatUnusedArgument.cs:39:32:39:32 | (...) ... | this supplied value |
| FormatUnusedArgument.cs:53:9:53:47 | call to method Format<String> | FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:53:37:53:42 | access to local variable format | The $@ ignores $@. | FormatUnusedArgument.cs:48:44:48:46 | "X" | format string | FormatUnusedArgument.cs:53:45:53:46 | "" | this supplied value |
| FormatUnusedArgument.cs:56:9:56:61 | call to method Format<String,String> | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" : String | FormatUnusedArgument.cs:56:45:56:52 | access to local variable format00 | The $@ ignores $@. | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" | format string | FormatUnusedArgument.cs:56:59:56:60 | "" | this supplied value |
| FormatUnusedArgument.cs:59:9:59:61 | call to method Format<String,String> | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" : String | FormatUnusedArgument.cs:59:45:59:52 | access to local variable format11 | The $@ ignores $@. | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" | format string | FormatUnusedArgument.cs:59:55:59:56 | "" | this supplied value |
| FormatUnusedArgument.cs:62:9:62:41 | call to method AppendFormat<String> | FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:62:31:62:36 | access to local variable format | The $@ ignores $@. | FormatUnusedArgument.cs:48:44:48:46 | "X" | format string | FormatUnusedArgument.cs:62:39:62:40 | "" | this supplied value |
| FormatUnusedArgument.cs:63:9:63:49 | call to method AppendFormat<String> | FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:63:39:63:44 | access to local variable format | The $@ ignores $@. | FormatUnusedArgument.cs:48:44:48:46 | "X" | format string | FormatUnusedArgument.cs:63:47:63:48 | "" | this supplied value |
| FormatUnusedArgument.cs:66:9:66:63 | call to method AppendFormat<String,String> | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" : String | FormatUnusedArgument.cs:66:47:66:54 | access to local variable format00 | The $@ ignores $@. | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" | format string | FormatUnusedArgument.cs:66:61:66:62 | "" | this supplied value |
| FormatUnusedArgument.cs:69:9:69:63 | call to method AppendFormat<String,String> | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" : String | FormatUnusedArgument.cs:69:47:69:54 | access to local variable format11 | The $@ ignores $@. | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" | format string | FormatUnusedArgument.cs:69:57:69:58 | "" | this supplied value |
| FormatUnusedArgument.cs:74:9:74:46 | call to method TryWrite<String> | FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:74:29:74:34 | access to local variable format | The $@ ignores $@. | FormatUnusedArgument.cs:48:44:48:46 | "X" | format string | FormatUnusedArgument.cs:74:44:74:45 | "" | this supplied value |
| FormatUnusedArgument.cs:75:9:75:54 | call to method TryWrite<String> | FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:75:37:75:42 | access to local variable format | The $@ ignores $@. | FormatUnusedArgument.cs:48:44:48:46 | "X" | format string | FormatUnusedArgument.cs:75:52:75:53 | "" | this supplied value |
| FormatUnusedArgument.cs:78:9:78:68 | call to method TryWrite<String,String> | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" : String | FormatUnusedArgument.cs:78:45:78:52 | access to local variable format00 | The $@ ignores $@. | FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" | format string | FormatUnusedArgument.cs:78:66:78:67 | "" | this supplied value |
| FormatUnusedArgument.cs:81:9:81:68 | call to method TryWrite<String,String> | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" : String | FormatUnusedArgument.cs:81:45:81:52 | access to local variable format11 | The $@ ignores $@. | FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" | format string | FormatUnusedArgument.cs:81:62:81:63 | "" | this supplied value |
| FormatUnusedArgumentBad.cs:7:9:7:71 | call to method WriteLine | FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | The $@ ignores $@. | FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | format string | FormatUnusedArgumentBad.cs:7:61:7:70 | (...) ... | this supplied value |
| FormatUnusedArgumentBad.cs:8:9:8:77 | call to method WriteLine | FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | The $@ ignores $@. | FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | format string | FormatUnusedArgumentBad.cs:8:63:8:64 | access to parameter ex | this supplied value |
| FormatUnusedArgumentBad.cs:9:9:9:75 | call to method WriteLine | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | The $@ ignores $@. | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | format string | FormatUnusedArgumentBad.cs:9:61:9:62 | access to parameter ex | this supplied value |
| FormatUnusedArgumentBad.cs:9:9:9:75 | call to method WriteLine | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | The $@ ignores $@. | FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | format string | FormatUnusedArgumentBad.cs:9:65:9:74 | (...) ... | this supplied value |
edges
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:143:37:143:42 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:144:45:144:50 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:145:53:145:58 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:147:31:147:36 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:148:39:148:44 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:149:47:149:52 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:150:55:150:60 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:154:29:154:34 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:155:37:155:42 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:156:45:156:50 | access to local variable format | provenance | |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | FormatInvalid.cs:157:53:157:58 | access to local variable format | provenance | |
| FormatInvalid.cs:140:22:140:47 | call to method Parse : CompositeFormat | FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | provenance | |
| FormatInvalid.cs:140:44:140:46 | "}" : String | FormatInvalid.cs:140:22:140:47 | call to method Parse : CompositeFormat | provenance | Config |
| FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | FormatMissingArgument.cs:29:24:29:29 | format : String | provenance | |
| FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | FormatMissingArgument.cs:29:24:29:29 | format : String | provenance | |
| FormatMissingArgument.cs:29:24:29:29 | format : String | FormatMissingArgument.cs:32:23:32:28 | access to parameter format | provenance | |
| FormatMissingArgument.cs:29:24:29:29 | format : String | FormatMissingArgument.cs:32:23:32:28 | access to parameter format | provenance | |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | FormatMissingArgument.cs:43:37:43:43 | access to local variable format0 | provenance | |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | FormatMissingArgument.cs:56:31:56:37 | access to local variable format0 | provenance | |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | FormatMissingArgument.cs:57:39:57:45 | access to local variable format0 | provenance | |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | FormatMissingArgument.cs:73:29:73:35 | access to local variable format0 | provenance | |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | FormatMissingArgument.cs:74:37:74:43 | access to local variable format0 | provenance | |
| FormatMissingArgument.cs:37:23:37:50 | call to method Parse : CompositeFormat | FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | provenance | |
| FormatMissingArgument.cs:37:45:37:49 | "{0}" : String | FormatMissingArgument.cs:37:23:37:50 | call to method Parse : CompositeFormat | provenance | Config |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | FormatMissingArgument.cs:46:37:46:43 | access to local variable format1 | provenance | |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | FormatMissingArgument.cs:60:31:60:37 | access to local variable format1 | provenance | |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | FormatMissingArgument.cs:61:39:61:45 | access to local variable format1 | provenance | |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | FormatMissingArgument.cs:77:29:77:35 | access to local variable format1 | provenance | |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | FormatMissingArgument.cs:78:37:78:43 | access to local variable format1 | provenance | |
| FormatMissingArgument.cs:38:23:38:50 | call to method Parse : CompositeFormat | FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | provenance | |
| FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | FormatMissingArgument.cs:38:23:38:50 | call to method Parse : CompositeFormat | provenance | Config |
| FormatMissingArgument.cs:39:13:39:20 | access to local variable format01 : CompositeFormat | FormatMissingArgument.cs:49:45:49:52 | access to local variable format01 | provenance | |
| FormatMissingArgument.cs:39:13:39:20 | access to local variable format01 : CompositeFormat | FormatMissingArgument.cs:64:47:64:54 | access to local variable format01 | provenance | |
| FormatMissingArgument.cs:39:13:39:20 | access to local variable format01 : CompositeFormat | FormatMissingArgument.cs:81:45:81:52 | access to local variable format01 | provenance | |
| FormatMissingArgument.cs:39:24:39:54 | call to method Parse : CompositeFormat | FormatMissingArgument.cs:39:13:39:20 | access to local variable format01 : CompositeFormat | provenance | |
| FormatMissingArgument.cs:39:46:39:53 | "{0}{1}" : String | FormatMissingArgument.cs:39:24:39:54 | call to method Parse : CompositeFormat | provenance | Config |
| FormatMissingArgument.cs:40:13:40:20 | access to local variable format23 : CompositeFormat | FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | provenance | |
| FormatMissingArgument.cs:40:13:40:20 | access to local variable format23 : CompositeFormat | FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | provenance | |
| FormatMissingArgument.cs:40:13:40:20 | access to local variable format23 : CompositeFormat | FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | provenance | |
| FormatMissingArgument.cs:40:24:40:54 | call to method Parse : CompositeFormat | FormatMissingArgument.cs:40:13:40:20 | access to local variable format23 : CompositeFormat | provenance | |
| FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | FormatMissingArgument.cs:40:24:40:54 | call to method Parse : CompositeFormat | provenance | Config |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | FormatUnusedArgument.cs:53:37:53:42 | access to local variable format | provenance | |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | FormatUnusedArgument.cs:62:31:62:36 | access to local variable format | provenance | |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | FormatUnusedArgument.cs:63:39:63:44 | access to local variable format | provenance | |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | FormatUnusedArgument.cs:74:29:74:34 | access to local variable format | provenance | |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | FormatUnusedArgument.cs:75:37:75:42 | access to local variable format | provenance | |
| FormatUnusedArgument.cs:48:22:48:47 | call to method Parse : CompositeFormat | FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | provenance | |
| FormatUnusedArgument.cs:48:44:48:46 | "X" : String | FormatUnusedArgument.cs:48:22:48:47 | call to method Parse : CompositeFormat | provenance | Config |
| FormatUnusedArgument.cs:49:13:49:20 | access to local variable format00 : CompositeFormat | FormatUnusedArgument.cs:56:45:56:52 | access to local variable format00 | provenance | |
| FormatUnusedArgument.cs:49:13:49:20 | access to local variable format00 : CompositeFormat | FormatUnusedArgument.cs:66:47:66:54 | access to local variable format00 | provenance | |
| FormatUnusedArgument.cs:49:13:49:20 | access to local variable format00 : CompositeFormat | FormatUnusedArgument.cs:78:45:78:52 | access to local variable format00 | provenance | |
| FormatUnusedArgument.cs:49:24:49:54 | call to method Parse : CompositeFormat | FormatUnusedArgument.cs:49:13:49:20 | access to local variable format00 : CompositeFormat | provenance | |
| FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" : String | FormatUnusedArgument.cs:49:24:49:54 | call to method Parse : CompositeFormat | provenance | Config |
| FormatUnusedArgument.cs:50:13:50:20 | access to local variable format11 : CompositeFormat | FormatUnusedArgument.cs:59:45:59:52 | access to local variable format11 | provenance | |
| FormatUnusedArgument.cs:50:13:50:20 | access to local variable format11 : CompositeFormat | FormatUnusedArgument.cs:69:47:69:54 | access to local variable format11 | provenance | |
| FormatUnusedArgument.cs:50:13:50:20 | access to local variable format11 : CompositeFormat | FormatUnusedArgument.cs:81:45:81:52 | access to local variable format11 | provenance | |
| FormatUnusedArgument.cs:50:24:50:54 | call to method Parse : CompositeFormat | FormatUnusedArgument.cs:50:13:50:20 | access to local variable format11 : CompositeFormat | provenance | |
| FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" : String | FormatUnusedArgument.cs:50:24:50:54 | call to method Parse : CompositeFormat | provenance | Config |
nodes
| FormatInvalid.cs:10:23:10:27 | "{0}" | semmle.label | "{0}" |
| FormatInvalid.cs:10:23:10:27 | "{0}" | semmle.label | "{0}" |
| FormatInvalid.cs:13:23:13:29 | "{0,1}" | semmle.label | "{0,1}" |
| FormatInvalid.cs:13:23:13:29 | "{0,1}" | semmle.label | "{0,1}" |
| FormatInvalid.cs:16:23:16:31 | "{0, 1}" | semmle.label | "{0, 1}" |
| FormatInvalid.cs:16:23:16:31 | "{0, 1}" | semmle.label | "{0, 1}" |
| FormatInvalid.cs:19:23:19:30 | "{0,-1}" | semmle.label | "{0,-1}" |
| FormatInvalid.cs:19:23:19:30 | "{0,-1}" | semmle.label | "{0,-1}" |
| FormatInvalid.cs:22:23:22:33 | "{0:0.000}" | semmle.label | "{0:0.000}" |
| FormatInvalid.cs:22:23:22:33 | "{0:0.000}" | semmle.label | "{0:0.000}" |
| FormatInvalid.cs:25:23:25:39 | "{0, -10 :0.000}" | semmle.label | "{0, -10 :0.000}" |
| FormatInvalid.cs:25:23:25:39 | "{0, -10 :0.000}" | semmle.label | "{0, -10 :0.000}" |
| FormatInvalid.cs:28:23:28:28 | "{ 0}" | semmle.label | "{ 0}" |
| FormatInvalid.cs:28:23:28:28 | "{ 0}" | semmle.label | "{ 0}" |
| FormatInvalid.cs:31:23:31:31 | "{0,--1}" | semmle.label | "{0,--1}" |
| FormatInvalid.cs:31:23:31:31 | "{0,--1}" | semmle.label | "{0,--1}" |
| FormatInvalid.cs:34:23:34:30 | "{0:{}}" | semmle.label | "{0:{}}" |
| FormatInvalid.cs:34:23:34:30 | "{0:{}}" | semmle.label | "{0:{}}" |
| FormatInvalid.cs:37:23:37:26 | "%d" | semmle.label | "%d" |
| FormatInvalid.cs:37:23:37:26 | "%d" | semmle.label | "%d" |
| FormatInvalid.cs:40:23:40:33 | "{{0}-{1}}" | semmle.label | "{{0}-{1}}" |
| FormatInvalid.cs:40:23:40:33 | "{{0}-{1}}" | semmle.label | "{{0}-{1}}" |
| FormatInvalid.cs:43:23:43:28 | "{0}}" | semmle.label | "{0}}" |
| FormatInvalid.cs:43:23:43:28 | "{0}}" | semmle.label | "{0}}" |
| FormatInvalid.cs:46:23:46:32 | "{foo{0}}" | semmle.label | "{foo{0}}" |
| FormatInvalid.cs:46:23:46:32 | "{foo{0}}" | semmle.label | "{foo{0}}" |
| FormatInvalid.cs:49:23:49:34 | "{{sdc}}{0}" | semmle.label | "{{sdc}}{0}" |
| FormatInvalid.cs:49:23:49:34 | "{{sdc}}{0}" | semmle.label | "{{sdc}}{0}" |
| FormatInvalid.cs:52:23:52:28 | "}{0}" | semmle.label | "}{0}" |
| FormatInvalid.cs:52:23:52:28 | "}{0}" | semmle.label | "}{0}" |
| FormatInvalid.cs:55:23:55:42 | "new {0} ({1} => {{" | semmle.label | "new {0} ({1} => {{" |
| FormatInvalid.cs:55:23:55:42 | "new {0} ({1} => {{" | semmle.label | "new {0} ({1} => {{" |
| FormatInvalid.cs:58:23:58:29 | "{0}{{" | semmle.label | "{0}{{" |
| FormatInvalid.cs:58:23:58:29 | "{0}{{" | semmle.label | "{0}{{" |
| FormatInvalid.cs:59:23:59:33 | "{0}{{{{}}" | semmle.label | "{0}{{{{}}" |
| FormatInvalid.cs:59:23:59:33 | "{0}{{{{}}" | semmle.label | "{0}{{{{}}" |
| FormatInvalid.cs:76:23:76:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:76:23:76:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:77:23:77:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:77:23:77:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:78:23:78:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:78:23:78:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:79:27:79:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:79:27:79:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:80:23:80:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:80:23:80:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:81:23:81:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:81:23:81:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:82:23:82:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:82:23:82:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:84:25:84:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:84:25:84:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:85:25:85:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:85:25:85:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:86:25:86:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:86:25:86:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:87:29:87:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:87:29:87:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:88:25:88:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:88:25:88:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:89:25:89:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:89:25:89:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:90:25:90:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:90:25:90:27 | "}" | semmle.label | "}" |
| FormatInvalid.cs:92:27:92:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:92:27:92:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:93:27:93:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:93:27:93:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:94:27:94:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:94:27:94:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:95:27:95:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:95:27:95:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:96:27:96:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:96:27:96:29 | "}" | semmle.label | "}" |
| FormatInvalid.cs:98:22:98:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:98:22:98:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:99:22:99:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:99:22:99:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:100:22:100:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:100:22:100:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:101:22:101:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:101:22:101:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:102:22:102:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:102:22:102:24 | "}" | semmle.label | "}" |
| FormatInvalid.cs:104:44:104:46 | "}" | semmle.label | "}" |
| FormatInvalid.cs:104:44:104:46 | "}" | semmle.label | "}" |
| FormatInvalid.cs:105:45:105:47 | "}" | semmle.label | "}" |
| FormatInvalid.cs:105:45:105:47 | "}" | semmle.label | "}" |
| FormatInvalid.cs:106:51:106:53 | "}" | semmle.label | "}" |
| FormatInvalid.cs:106:51:106:53 | "}" | semmle.label | "}" |
| FormatInvalid.cs:107:47:107:49 | "}" | semmle.label | "}" |
| FormatInvalid.cs:107:47:107:49 | "}" | semmle.label | "}" |
| FormatInvalid.cs:108:29:108:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:108:29:108:31 | "}" | semmle.label | "}" |
| FormatInvalid.cs:110:23:110:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:110:23:110:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:111:23:111:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:111:23:111:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:112:23:112:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:112:23:112:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:113:23:113:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:113:23:113:25 | "}" | semmle.label | "}" |
| FormatInvalid.cs:118:56:118:58 | [assertion success] "}" | semmle.label | [assertion success] "}" |
| FormatInvalid.cs:118:56:118:58 | [assertion success] "}" | semmle.label | [assertion success] "}" |
| FormatInvalid.cs:119:18:119:20 | "}" | semmle.label | "}" |
| FormatInvalid.cs:119:18:119:20 | "}" | semmle.label | "}" |
| FormatInvalid.cs:120:40:120:42 | "}" | semmle.label | "}" |
| FormatInvalid.cs:120:40:120:42 | "}" | semmle.label | "}" |
| FormatInvalid.cs:140:13:140:18 | access to local variable format : CompositeFormat | semmle.label | access to local variable format : CompositeFormat |
| FormatInvalid.cs:140:22:140:47 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatInvalid.cs:140:44:140:46 | "}" | semmle.label | "}" |
| FormatInvalid.cs:140:44:140:46 | "}" : String | semmle.label | "}" : String |
| FormatInvalid.cs:143:37:143:42 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:144:45:144:50 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:145:53:145:58 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:147:31:147:36 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:148:39:148:44 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:149:47:149:52 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:150:55:150:60 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:154:29:154:34 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:155:37:155:42 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:156:45:156:50 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalid.cs:157:53:157:58 | access to local variable format | semmle.label | access to local variable format |
| FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | semmle.label | "class {0} { }" |
| FormatInvalidBad.cs:7:30:7:44 | "class {0} { }" | semmle.label | "class {0} { }" |
| FormatInvalidGood.cs:7:30:7:46 | "class {0} {{ }}" | semmle.label | "class {0} {{ }}" |
| FormatInvalidGood.cs:7:30:7:46 | "class {0} {{ }}" | semmle.label | "class {0} {{ }}" |
| FormatMissingArgument.cs:9:23:9:27 | "{0}" | semmle.label | "{0}" |
| FormatMissingArgument.cs:9:23:9:27 | "{0}" | semmle.label | "{0}" |
| FormatMissingArgument.cs:12:23:12:27 | "{1}" | semmle.label | "{1}" |
| FormatMissingArgument.cs:12:23:12:27 | "{1}" | semmle.label | "{1}" |
| FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | semmle.label | "{2} {3}" |
| FormatMissingArgument.cs:15:23:15:31 | "{2} {3}" | semmle.label | "{2} {3}" |
| FormatMissingArgument.cs:18:23:18:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatMissingArgument.cs:18:23:18:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatMissingArgument.cs:21:23:21:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatMissingArgument.cs:21:23:21:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatMissingArgument.cs:24:23:24:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatMissingArgument.cs:24:23:24:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | semmle.label | "{1}" : String |
| FormatMissingArgument.cs:26:16:26:20 | "{1}" : String | semmle.label | "{1}" : String |
| FormatMissingArgument.cs:29:24:29:29 | format : String | semmle.label | format : String |
| FormatMissingArgument.cs:29:24:29:29 | format : String | semmle.label | format : String |
| FormatMissingArgument.cs:32:23:32:28 | access to parameter format | semmle.label | access to parameter format |
| FormatMissingArgument.cs:32:23:32:28 | access to parameter format | semmle.label | access to parameter format |
| FormatMissingArgument.cs:37:13:37:19 | access to local variable format0 : CompositeFormat | semmle.label | access to local variable format0 : CompositeFormat |
| FormatMissingArgument.cs:37:23:37:50 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatMissingArgument.cs:37:45:37:49 | "{0}" | semmle.label | "{0}" |
| FormatMissingArgument.cs:37:45:37:49 | "{0}" : String | semmle.label | "{0}" : String |
| FormatMissingArgument.cs:38:13:38:19 | access to local variable format1 : CompositeFormat | semmle.label | access to local variable format1 : CompositeFormat |
| FormatMissingArgument.cs:38:23:38:50 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatMissingArgument.cs:38:45:38:49 | "{1}" | semmle.label | "{1}" |
| FormatMissingArgument.cs:38:45:38:49 | "{1}" : String | semmle.label | "{1}" : String |
| FormatMissingArgument.cs:39:13:39:20 | access to local variable format01 : CompositeFormat | semmle.label | access to local variable format01 : CompositeFormat |
| FormatMissingArgument.cs:39:24:39:54 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatMissingArgument.cs:39:46:39:53 | "{0}{1}" | semmle.label | "{0}{1}" |
| FormatMissingArgument.cs:39:46:39:53 | "{0}{1}" : String | semmle.label | "{0}{1}" : String |
| FormatMissingArgument.cs:40:13:40:20 | access to local variable format23 : CompositeFormat | semmle.label | access to local variable format23 : CompositeFormat |
| FormatMissingArgument.cs:40:24:40:54 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" | semmle.label | "{2}{3}" |
| FormatMissingArgument.cs:40:46:40:53 | "{2}{3}" : String | semmle.label | "{2}{3}" : String |
| FormatMissingArgument.cs:43:37:43:43 | access to local variable format0 | semmle.label | access to local variable format0 |
| FormatMissingArgument.cs:46:37:46:43 | access to local variable format1 | semmle.label | access to local variable format1 |
| FormatMissingArgument.cs:49:45:49:52 | access to local variable format01 | semmle.label | access to local variable format01 |
| FormatMissingArgument.cs:52:45:52:52 | access to local variable format23 | semmle.label | access to local variable format23 |
| FormatMissingArgument.cs:56:31:56:37 | access to local variable format0 | semmle.label | access to local variable format0 |
| FormatMissingArgument.cs:57:39:57:45 | access to local variable format0 | semmle.label | access to local variable format0 |
| FormatMissingArgument.cs:60:31:60:37 | access to local variable format1 | semmle.label | access to local variable format1 |
| FormatMissingArgument.cs:61:39:61:45 | access to local variable format1 | semmle.label | access to local variable format1 |
| FormatMissingArgument.cs:64:47:64:54 | access to local variable format01 | semmle.label | access to local variable format01 |
| FormatMissingArgument.cs:67:47:67:54 | access to local variable format23 | semmle.label | access to local variable format23 |
| FormatMissingArgument.cs:73:29:73:35 | access to local variable format0 | semmle.label | access to local variable format0 |
| FormatMissingArgument.cs:74:37:74:43 | access to local variable format0 | semmle.label | access to local variable format0 |
| FormatMissingArgument.cs:77:29:77:35 | access to local variable format1 | semmle.label | access to local variable format1 |
| FormatMissingArgument.cs:78:37:78:43 | access to local variable format1 | semmle.label | access to local variable format1 |
| FormatMissingArgument.cs:81:45:81:52 | access to local variable format01 | semmle.label | access to local variable format01 |
| FormatMissingArgument.cs:84:45:84:52 | access to local variable format23 | semmle.label | access to local variable format23 |
| FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatMissingArgumentBad.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | semmle.label | "Hello {1} {2}" |
| FormatMissingArgumentBad.cs:8:27:8:41 | "Hello {1} {2}" | semmle.label | "Hello {1} {2}" |
| FormatMissingArgumentGood.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatMissingArgumentGood.cs:7:27:7:41 | "Hello {0} {1}" | semmle.label | "Hello {0} {1}" |
| FormatUnusedArgument.cs:9:23:9:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:9:23:9:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:12:23:12:25 | "X" | semmle.label | "X" |
| FormatUnusedArgument.cs:12:23:12:25 | "X" | semmle.label | "X" |
| FormatUnusedArgument.cs:15:23:15:27 | "{0}" | semmle.label | "{0}" |
| FormatUnusedArgument.cs:15:23:15:27 | "{0}" | semmle.label | "{0}" |
| FormatUnusedArgument.cs:18:23:18:31 | "{0} {0}" | semmle.label | "{0} {0}" |
| FormatUnusedArgument.cs:18:23:18:31 | "{0} {0}" | semmle.label | "{0} {0}" |
| FormatUnusedArgument.cs:21:23:21:31 | "{1} {1}" | semmle.label | "{1} {1}" |
| FormatUnusedArgument.cs:21:23:21:31 | "{1} {1}" | semmle.label | "{1} {1}" |
| FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | semmle.label | "abcdefg" |
| FormatUnusedArgument.cs:24:23:24:31 | "abcdefg" | semmle.label | "abcdefg" |
| FormatUnusedArgument.cs:27:23:27:31 | "{{sdc}}" | semmle.label | "{{sdc}}" |
| FormatUnusedArgument.cs:27:23:27:31 | "{{sdc}}" | semmle.label | "{{sdc}}" |
| FormatUnusedArgument.cs:30:23:30:33 | "{{{0:D}}}" | semmle.label | "{{{0:D}}}" |
| FormatUnusedArgument.cs:30:23:30:33 | "{{{0:D}}}" | semmle.label | "{{{0:D}}}" |
| FormatUnusedArgument.cs:33:23:33:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatUnusedArgument.cs:33:23:33:39 | "{0} {1} {2} {3}" | semmle.label | "{0} {1} {2} {3}" |
| FormatUnusedArgument.cs:36:23:36:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:36:23:36:35 | "{0} {1} {2}" | semmle.label | "{0} {1} {2}" |
| FormatUnusedArgument.cs:39:23:39:29 | "{{0}}" | semmle.label | "{{0}}" |
| FormatUnusedArgument.cs:39:23:39:29 | "{{0}}" | semmle.label | "{{0}}" |
| FormatUnusedArgument.cs:43:23:43:24 | "" | semmle.label | "" |
| FormatUnusedArgument.cs:43:23:43:24 | "" | semmle.label | "" |
| FormatUnusedArgument.cs:48:13:48:18 | access to local variable format : CompositeFormat | semmle.label | access to local variable format : CompositeFormat |
| FormatUnusedArgument.cs:48:22:48:47 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatUnusedArgument.cs:48:44:48:46 | "X" | semmle.label | "X" |
| FormatUnusedArgument.cs:48:44:48:46 | "X" : String | semmle.label | "X" : String |
| FormatUnusedArgument.cs:49:13:49:20 | access to local variable format00 : CompositeFormat | semmle.label | access to local variable format00 : CompositeFormat |
| FormatUnusedArgument.cs:49:24:49:54 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" | semmle.label | "{0}{0}" |
| FormatUnusedArgument.cs:49:46:49:53 | "{0}{0}" : String | semmle.label | "{0}{0}" : String |
| FormatUnusedArgument.cs:50:13:50:20 | access to local variable format11 : CompositeFormat | semmle.label | access to local variable format11 : CompositeFormat |
| FormatUnusedArgument.cs:50:24:50:54 | call to method Parse : CompositeFormat | semmle.label | call to method Parse : CompositeFormat |
| FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" | semmle.label | "{1}{1}" |
| FormatUnusedArgument.cs:50:46:50:53 | "{1}{1}" : String | semmle.label | "{1}{1}" : String |
| FormatUnusedArgument.cs:53:37:53:42 | access to local variable format | semmle.label | access to local variable format |
| FormatUnusedArgument.cs:56:45:56:52 | access to local variable format00 | semmle.label | access to local variable format00 |
| FormatUnusedArgument.cs:59:45:59:52 | access to local variable format11 | semmle.label | access to local variable format11 |
| FormatUnusedArgument.cs:62:31:62:36 | access to local variable format | semmle.label | access to local variable format |
| FormatUnusedArgument.cs:63:39:63:44 | access to local variable format | semmle.label | access to local variable format |
| FormatUnusedArgument.cs:66:47:66:54 | access to local variable format00 | semmle.label | access to local variable format00 |
| FormatUnusedArgument.cs:69:47:69:54 | access to local variable format11 | semmle.label | access to local variable format11 |
| FormatUnusedArgument.cs:74:29:74:34 | access to local variable format | semmle.label | access to local variable format |
| FormatUnusedArgument.cs:75:37:75:42 | access to local variable format | semmle.label | access to local variable format |
| FormatUnusedArgument.cs:78:45:78:52 | access to local variable format00 | semmle.label | access to local variable format00 |
| FormatUnusedArgument.cs:81:45:81:52 | access to local variable format11 | semmle.label | access to local variable format11 |
| FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | semmle.label | "Error processing file: {0}" |
| FormatUnusedArgumentBad.cs:7:27:7:54 | "Error processing file: {0}" | semmle.label | "Error processing file: {0}" |
| FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | semmle.label | "Error processing file: {1} ({1})" |
| FormatUnusedArgumentBad.cs:8:27:8:60 | "Error processing file: {1} ({1})" | semmle.label | "Error processing file: {1} ({1})" |
| FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | semmle.label | "Error processing file: %s (%d)" |
| FormatUnusedArgumentBad.cs:9:27:9:58 | "Error processing file: %s (%d)" | semmle.label | "Error processing file: %s (%d)" |
subpaths

View File

@@ -1 +1,2 @@
API Abuse/FormatInvalid.ql
query: API Abuse/FormatInvalid.ql
postprocess: utils/test/InlineExpectationsTestQuery.ql

View File

@@ -4,6 +4,6 @@ class Bad1
{
string GenerateEmptyClass(string c)
{
return string.Format("class {0} { }", "C");
return string.Format("class {0} { }", "C"); // $ Alert
}
}

View File

@@ -1,4 +1,5 @@
using System;
using System.Text;
class Class1
{
@@ -8,28 +9,82 @@ class Class1
String.Format("{0}", 0);
// BAD: Missing {1}
String.Format("{1}", 0);
String.Format("{1}", 0); // $ Alert
// BAD: Missing {2} and {3}
String.Format("{2} {3}", 0, 1);
String.Format("{2} {3}", 0, 1); // $ Alert
// GOOD: An array has been supplied.
String.Format("{0} {1} {2}", args);
// GOOD: A collection has been supplied.
String.Format("{0} {1} {2}", [0, 1, 2]);
// GOOD: All arguments supplied to params
String.Format("{0} {1} {2} {3}", 0, 1, 2, 3);
helper("{1}");
// BAD: Missing {0}
Console.WriteLine("{0}");
helper("{1}"); // $ Source=source1
}
void helper(string format)
{
// BAD: Missing {1}
String.Format(format, 0);
String.Format(format, 0); // $ Alert=source1
}
void TestCompositeFormatMissingArgument()
{
var format0 = CompositeFormat.Parse("{0}");
var format1 = CompositeFormat.Parse("{1}"); // $ Source=source2
var format01 = CompositeFormat.Parse("{0}{1}");
var format23 = CompositeFormat.Parse("{2}{3}"); // $ Source=source3
// GOOD: All args supplied
String.Format<string>(null, format0, "");
// BAD: Missing {1}
String.Format<string>(null, format1, ""); // $ Alert=source2
// GOOD: All args supplied
String.Format<string, string>(null, format01, "", "");
// BAD: Missing {2} and {3}
String.Format<string, string>(null, format23, "", ""); // $ Alert=source3
// GOOD: All arguments supplied
sb.AppendFormat(null, format0, "");
sb.AppendFormat<string>(null, format0, "");
// BAD: Missing {1}
sb.AppendFormat(null, format1, ""); // $ Alert=source2
sb.AppendFormat<string>(null, format1, ""); // $ Alert=source2
// GOOD: All args supplied
sb.AppendFormat<string, string>(null, format01, "", "");
// BAD: Missing {2} and {3}
sb.AppendFormat<string, string>(null, format23, "", ""); // $ Alert=source3
var span = new Span<char>();
// GOOD: All args supplied
span.TryWrite(null, format0, out _, "");
span.TryWrite<string>(null, format0, out _, "");
// BAD: Missing {1}
span.TryWrite(null, format1, out _, ""); // $ Alert=source2
span.TryWrite<string>(null, format1, out _, ""); // $ Alert=source2
// GOOD: All args supplied
span.TryWrite<string, string>(null, format01, out _, "", "");
// BAD: Missing {2} and {3}
span.TryWrite<string, string>(null, format23, out _, "", ""); // $ Alert=source3
}
object[] args;
StringBuilder sb;
}

View File

@@ -4,7 +4,7 @@ class Bad3
{
void Hello(string first, string last)
{
Console.WriteLine("Hello {0} {1}", first);
Console.WriteLine("Hello {1} {2}", first, last);
Console.WriteLine("Hello {0} {1}", first); // $ Alert
Console.WriteLine("Hello {1} {2}", first, last); // $ Alert
}
}

View File

@@ -1,4 +1,5 @@
using System;
using System.Text;
class C
{
@@ -8,22 +9,22 @@ class C
String.Format("{0} {1} {2}", 0, 1, 2);
// BAD: Missing arg {0}
String.Format("X", 1);
String.Format("X", 1); // $ Alert
// BAD: Missing {1}
String.Format("{0}", 1, 2);
String.Format("{0}", 1, 2); // $ Alert
// BAD: Missing {1}
String.Format("{0} {0}", 1, 2);
String.Format("{0} {0}", 1, 2); // $ Alert
// BAD: Missing {0}
String.Format("{1} {1}", 1, 2);
String.Format("{1} {1}", 1, 2); // $ Alert
// BAD: Missing {0}, {1} and {2}
String.Format("abcdefg", 0, 1, 2);
String.Format("abcdefg", 0, 1, 2); // $ Alert
// BAD: {0} is unused
String.Format("{{sdc}}", 0);
String.Format("{{sdc}}", 0); // $ Alert
// GOOD: {0} is used
String.Format("{{{0:D}}}", 0);
@@ -35,12 +36,52 @@ class C
String.Format("{0} {1} {2}", ps);
// BAD: Would display "{0}"
String.Format("{{0}}", 1);
String.Format("{{0}}", 1); // $ Alert
// GOOD: Ignore the empty string as it's often used as the default value
// of GetResource().
String.Format("", 1);
}
void CompositeFormatTests()
{
var format = CompositeFormat.Parse("X"); // $ Source=source4
var format00 = CompositeFormat.Parse("{0}{0}"); // $ Source=source5
var format11 = CompositeFormat.Parse("{1}{1}"); // $ Source=source6
// BAD: Unused arg {0}
String.Format<string>(null, format, ""); // $ Alert=source4
// BAD: Unused arg {1}
String.Format<string, string>(null, format00, "", ""); // $ Alert=source5
// BAD: Unused arg {0}
String.Format<string, string>(null, format11, "", ""); // $ Alert=source6
// BAD: Unused arg {0}
sb.AppendFormat(null, format, ""); // $ Alert=source4
sb.AppendFormat<string>(null, format, ""); // $ Alert=source4
// BAD: Unused arg {1}
sb.AppendFormat<string, string>(null, format00, "", ""); // $ Alert=source5
// BAD: Unused arg {0}
sb.AppendFormat<string, string>(null, format11, "", ""); // $ Alert=source6
var span = new Span<char>();
// BAD: Unused arg {0}
span.TryWrite(null, format, out _, ""); // $ Alert=source4
span.TryWrite<string>(null, format, out _, ""); // $ Alert=source4
// BAD: Unused arg {1}
span.TryWrite<string, string>(null, format00, out _, "", ""); // $ Alert=source5
// BAD: Unused arg {0}
span.TryWrite<string, string>(null, format11, out _, "", ""); // $ Alert=source6
}
object[] ps;
StringBuilder sb;
}

View File

@@ -4,8 +4,8 @@ class Bad2
{
void M(Exception ex)
{
Console.WriteLine("Error processing file: {0}", ex, ex.HResult);
Console.WriteLine("Error processing file: {1} ({1})", ex, ex.HResult);
Console.WriteLine("Error processing file: %s (%d)", ex, ex.HResult);
Console.WriteLine("Error processing file: {0}", ex, ex.HResult); // $ Alert
Console.WriteLine("Error processing file: {1} ({1})", ex, ex.HResult); // $ Alert
Console.WriteLine("Error processing file: %s (%d)", ex, ex.HResult); // $ Alert
}
}

View File

@@ -4,17 +4,17 @@
:stub-columns: 1
Operating system,Supported versions,Supported CPU architectures
Linux,"Ubuntu 20.04
Linux,"Ubuntu 22.04
Ubuntu 21.04
Ubuntu 22.04","x86-64"
Ubuntu 24.04","x86-64"
Windows,"Windows 10 / Windows Server 2019
Windows 11 / Windows Server 2022","x86-64"
macOS,"macOS 13 Ventura
macOS 14 Sonoma","x86-64, arm64 (Apple Silicon) [1]_"
macOS 14 Sonoma
macOS 15 Sequoia","x86-64, arm64 (Apple Silicon) [1]_"
.. container:: footnote-group

View File

@@ -4,13 +4,13 @@
:stub-columns: 1
Language,Variants,Compilers,Extensions
C/C++,"C89, C99, C11, C17, C++98, C++03, C++11, C++14, C++17, C++20 [1]_ [2]_","Clang (including clang-cl [3]_ and armclang) extensions (up to Clang 17.0),
C/C++,"C89, C99, C11, C17, C23, C++98, C++03, C++11, C++14, C++17, C++20, C++23 [1]_ [2]_ [3]_","Clang (including clang-cl [4]_ and armclang) extensions (up to Clang 17.0),
GNU extensions (up to GCC 13.2),
Microsoft extensions (up to VS 2022),
Arm Compiler 5 [4]_","``.cpp``, ``.c++``, ``.cxx``, ``.hpp``, ``.hh``, ``.h++``, ``.hxx``, ``.c``, ``.cc``, ``.h``"
Arm Compiler 5 [5]_","``.cpp``, ``.c++``, ``.cxx``, ``.hpp``, ``.hh``, ``.h++``, ``.hxx``, ``.c``, ``.cc``, ``.h``"
C#,C# up to 13,"Microsoft Visual Studio up to 2019 with .NET up to 4.8,
.NET Core up to 3.1
@@ -18,26 +18,27 @@
.NET 5, .NET 6, .NET 7, .NET 8, .NET 9","``.sln``, ``.csproj``, ``.cs``, ``.cshtml``, ``.xaml``"
GitHub Actions,"Not applicable",Not applicable,"``.github/workflows/*.yml``, ``.github/workflows/*.yaml``, ``**/action.yml``, ``**/action.yaml``"
Go (aka Golang), "Go up to 1.24", "Go 1.11 or more recent", ``.go``
Java,"Java 7 to 24 [5]_","javac (OpenJDK and Oracle JDK),
Java,"Java 7 to 24 [6]_","javac (OpenJDK and Oracle JDK),
Eclipse compiler for Java (ECJ) [6]_",``.java``
Eclipse compiler for Java (ECJ) [7]_",``.java``
Kotlin,"Kotlin 1.5.0 to 2.1.2\ *x*","kotlinc",``.kt``
JavaScript,ECMAScript 2022 or lower,Not applicable,"``.js``, ``.jsx``, ``.mjs``, ``.es``, ``.es6``, ``.htm``, ``.html``, ``.xhtm``, ``.xhtml``, ``.vue``, ``.hbs``, ``.ejs``, ``.njk``, ``.json``, ``.yaml``, ``.yml``, ``.raml``, ``.xml`` [7]_"
Python [8]_,"2.7, 3.5, 3.6, 3.7, 3.8, 3.9, 3.10, 3.11, 3.12, 3.13",Not applicable,``.py``
Ruby [9]_,"up to 3.3",Not applicable,"``.rb``, ``.erb``, ``.gemspec``, ``Gemfile``"
Swift [10]_,"Swift 5.4-6.0","Swift compiler","``.swift``"
TypeScript [11]_,"2.6-5.8",Standard TypeScript compiler,"``.ts``, ``.tsx``, ``.mts``, ``.cts``"
JavaScript,ECMAScript 2022 or lower,Not applicable,"``.js``, ``.jsx``, ``.mjs``, ``.es``, ``.es6``, ``.htm``, ``.html``, ``.xhtm``, ``.xhtml``, ``.vue``, ``.hbs``, ``.ejs``, ``.njk``, ``.json``, ``.yaml``, ``.yml``, ``.raml``, ``.xml`` [8]_"
Python [9]_,"2.7, 3.5, 3.6, 3.7, 3.8, 3.9, 3.10, 3.11, 3.12, 3.13",Not applicable,``.py``
Ruby [10]_,"up to 3.3",Not applicable,"``.rb``, ``.erb``, ``.gemspec``, ``Gemfile``"
Swift [11]_,"Swift 5.4-6.0","Swift compiler","``.swift``"
TypeScript [12]_,"2.6-5.8",Standard TypeScript compiler,"``.ts``, ``.tsx``, ``.mts``, ``.cts``"
.. container:: footnote-group
.. [1] C++20 modules are *not* supported.
.. [2] Objective-C, Objective-C++, C++/CLI, and C++/CX are not supported.
.. [3] Support for the clang-cl compiler is preliminary.
.. [4] Support for the Arm Compiler (armcc) is preliminary.
.. [5] Builds that execute on Java 7 to 24 can be analyzed. The analysis understands standard language features in Java 8 to 24; "preview" and "incubator" features are not supported. Source code using Java language versions older than Java 8 are analyzed as Java 8 code.
.. [6] ECJ is supported when the build invokes it via the Maven Compiler plugin or the Takari Lifecycle plugin.
.. [7] JSX and Flow code, YAML, JSON, HTML, and XML files may also be analyzed with JavaScript files.
.. [8] The extractor requires Python 3 to run. To analyze Python 2.7 you should install both versions of Python.
.. [9] Requires glibc 2.17.
.. [10] Support for the analysis of Swift requires macOS.
.. [11] TypeScript analysis is performed by running the JavaScript extractor with TypeScript enabled. This is the default.
.. [2] C23 and C++23 support is currently in beta.
.. [3] Objective-C, Objective-C++, C++/CLI, and C++/CX are not supported.
.. [4] Support for the clang-cl compiler is preliminary.
.. [5] Support for the Arm Compiler (armcc) is preliminary.
.. [6] Builds that execute on Java 7 to 24 can be analyzed. The analysis understands standard language features in Java 8 to 24; "preview" and "incubator" features are not supported. Source code using Java language versions older than Java 8 are analyzed as Java 8 code.
.. [7] ECJ is supported when the build invokes it via the Maven Compiler plugin or the Takari Lifecycle plugin.
.. [8] JSX and Flow code, YAML, JSON, HTML, and XML files may also be analyzed with JavaScript files.
.. [9] The extractor requires Python 3 to run. To analyze Python 2.7 you should install both versions of Python.
.. [10] Requires glibc 2.17.
.. [11] Support for the analysis of Swift requires macOS.
.. [12] TypeScript analysis is performed by running the JavaScript extractor with TypeScript enabled. This is the default.

View File

@@ -5,6 +5,8 @@
# and that we actually get are too big, the build fails on CI.
BAZEL := $(shell bash -c "which bazel")
rtjo ?= none
all: gen extractor
EXTRACTOR_PACK_OUT = extractor-pack

View File

@@ -425,7 +425,7 @@ func installDependencies(workspace project.GoWorkspace) {
} else {
if workspace.Modules == nil {
project.InitGoModForLegacyProject(workspace.BaseDir)
workspace.Modules = project.LoadGoModules(true, []string{filepath.Join(workspace.BaseDir, "go.mod")})
workspace.Modules = project.LoadGoModules([]string{filepath.Join(workspace.BaseDir, "go.mod")})
}
// get dependencies for all modules

View File

@@ -508,18 +508,3 @@ func EmitExtractionFailedForProjects(path []string) {
noLocation,
)
}
func EmitInvalidToolchainVersion(goModPath string, version string) {
emitDiagnostic(
"go/autobuilder/invalid-go-toolchain-version",
"Invalid Go toolchain version",
strings.Join([]string{
"As of Go 1.21, toolchain versions [must use the 1.N.P syntax](https://go.dev/doc/toolchain#version).",
fmt.Sprintf("`%s` in `%s` does not match this syntax and there is no additional `toolchain` directive, which may cause some `go` commands to fail.", version, goModPath),
},
"\n\n"),
severityWarning,
fullVisibility,
&locationStruct{File: goModPath},
)
}

View File

@@ -192,20 +192,10 @@ func findGoModFiles(root string) []string {
return util.FindAllFilesWithName(root, "go.mod", util.SkipVendorChecks...)
}
// A regular expression for the Go toolchain version syntax.
var toolchainVersionRe *regexp.Regexp = regexp.MustCompile(`(?m)^([0-9]+\.[0-9]+(\.[0-9]+|rc[0-9]+))$`)
// Returns true if the `go.mod` file specifies a Go language version, that version is `1.21` or greater, and
// there is no `toolchain` directive, and the Go language version is not a valid toolchain version.
func hasInvalidToolchainVersion(modFile *modfile.File) bool {
return modFile.Toolchain == nil && modFile.Go != nil &&
!toolchainVersionRe.Match([]byte(modFile.Go.Version)) && util.NewSemVer(modFile.Go.Version).IsAtLeast(toolchain.V1_21)
}
// Given a list of `go.mod` file paths, try to parse them all. The resulting array of `GoModule` objects
// will be the same length as the input array and the objects will contain at least the `go.mod` path.
// If parsing the corresponding file is successful, then the parsed contents will also be available.
func LoadGoModules(emitDiagnostics bool, goModFilePaths []string) []*GoModule {
func LoadGoModules(goModFilePaths []string) []*GoModule {
results := make([]*GoModule, len(goModFilePaths))
for i, goModFilePath := range goModFilePaths {
@@ -227,14 +217,6 @@ func LoadGoModules(emitDiagnostics bool, goModFilePaths []string) []*GoModule {
}
results[i].Module = modFile
// If this `go.mod` file specifies a Go language version, that version is `1.21` or greater, and
// there is no `toolchain` directive, check that it is a valid Go toolchain version. Otherwise,
// `go` commands which try to download the right version of the Go toolchain will fail. We detect
// this situation and emit a diagnostic.
if hasInvalidToolchainVersion(modFile) {
diagnostics.EmitInvalidToolchainVersion(goModFilePath, modFile.Go.Version)
}
}
return results
@@ -243,7 +225,7 @@ func LoadGoModules(emitDiagnostics bool, goModFilePaths []string) []*GoModule {
// Given a path to a `go.work` file, this function attempts to parse the `go.work` file. If unsuccessful,
// we attempt to discover `go.mod` files within subdirectories of the directory containing the `go.work`
// file ourselves.
func discoverWorkspace(emitDiagnostics bool, workFilePath string) GoWorkspace {
func discoverWorkspace(workFilePath string) GoWorkspace {
log.Printf("Loading %s...\n", workFilePath)
baseDir := filepath.Dir(workFilePath)
workFileSrc, err := os.ReadFile(workFilePath)
@@ -257,7 +239,7 @@ func discoverWorkspace(emitDiagnostics bool, workFilePath string) GoWorkspace {
return GoWorkspace{
BaseDir: baseDir,
Modules: LoadGoModules(emitDiagnostics, goModFilePaths),
Modules: LoadGoModules(goModFilePaths),
DepMode: GoGetWithModules,
ModMode: getModMode(GoGetWithModules, baseDir),
}
@@ -274,7 +256,7 @@ func discoverWorkspace(emitDiagnostics bool, workFilePath string) GoWorkspace {
return GoWorkspace{
BaseDir: baseDir,
Modules: LoadGoModules(emitDiagnostics, goModFilePaths),
Modules: LoadGoModules(goModFilePaths),
DepMode: GoGetWithModules,
ModMode: getModMode(GoGetWithModules, baseDir),
}
@@ -297,7 +279,7 @@ func discoverWorkspace(emitDiagnostics bool, workFilePath string) GoWorkspace {
return GoWorkspace{
BaseDir: baseDir,
WorkspaceFile: workFile,
Modules: LoadGoModules(emitDiagnostics, goModFilePaths),
Modules: LoadGoModules(goModFilePaths),
DepMode: GoGetWithModules,
ModMode: ModReadonly, // Workspaces only support "readonly"
}
@@ -325,7 +307,7 @@ func discoverWorkspaces(emitDiagnostics bool) []GoWorkspace {
for i, goModFile := range goModFiles {
results[i] = GoWorkspace{
BaseDir: filepath.Dir(goModFile),
Modules: LoadGoModules(emitDiagnostics, []string{goModFile}),
Modules: LoadGoModules([]string{goModFile}),
DepMode: GoGetWithModules,
ModMode: getModMode(GoGetWithModules, filepath.Dir(goModFile)),
}
@@ -342,7 +324,7 @@ func discoverWorkspaces(emitDiagnostics bool) []GoWorkspace {
results := make([]GoWorkspace, len(goWorkFiles))
for i, workFilePath := range goWorkFiles {
results[i] = discoverWorkspace(emitDiagnostics, workFilePath)
results[i] = discoverWorkspace(workFilePath)
}
// Add all stray `go.mod` files (i.e. those not referenced by `go.work` files)
@@ -374,7 +356,7 @@ func discoverWorkspaces(emitDiagnostics bool) []GoWorkspace {
log.Printf("Module %s is not referenced by any go.work file; adding it separately.\n", goModFile)
results = append(results, GoWorkspace{
BaseDir: filepath.Dir(goModFile),
Modules: LoadGoModules(emitDiagnostics, []string{goModFile}),
Modules: LoadGoModules([]string{goModFile}),
DepMode: GoGetWithModules,
ModMode: getModMode(GoGetWithModules, filepath.Dir(goModFile)),
})

View File

@@ -39,35 +39,6 @@ func parseModFile(t *testing.T, contents string) *modfile.File {
return modFile
}
func testHasInvalidToolchainVersion(t *testing.T, contents string) bool {
return hasInvalidToolchainVersion(parseModFile(t, contents))
}
func TestHasInvalidToolchainVersion(t *testing.T) {
invalid := []string{
"go 1.21\n",
"go 1.22\n",
}
for _, v := range invalid {
if !testHasInvalidToolchainVersion(t, v) {
t.Errorf("Expected testHasInvalidToolchainVersion(\"%s\") to be true, but got false", v)
}
}
valid := []string{
"go 1.20\n",
"go 1.21.1\n",
"go 1.22\n\ntoolchain go1.22.0\n",
}
for _, v := range valid {
if testHasInvalidToolchainVersion(t, v) {
t.Errorf("Expected testHasInvalidToolchainVersion(\"%s\") to be false, but got true", v)
}
}
}
func parseWorkFile(t *testing.T, contents string) *modfile.WorkFile {
workFile, err := modfile.ParseWork("go.work", []byte(contents), nil)

View File

@@ -1,5 +0,0 @@
{
"configuration" : {
"go" : { }
}
}

View File

@@ -1,31 +0,0 @@
{
"location": {
"file": "go.mod"
},
"markdownMessage": "As of Go 1.21, toolchain versions [must use the 1.N.P syntax](https://go.dev/doc/toolchain#version).\n\n`1.21` in `go.mod` does not match this syntax and there is no additional `toolchain` directive, which may cause some `go` commands to fail.",
"severity": "warning",
"source": {
"extractorName": "go",
"id": "go/autobuilder/invalid-go-toolchain-version",
"name": "Invalid Go toolchain version"
},
"visibility": {
"cliSummaryTable": true,
"statusPage": true,
"telemetry": true
}
}
{
"markdownMessage": "A single `go.mod` file was found.\n\n`go.mod`",
"severity": "note",
"source": {
"extractorName": "go",
"id": "go/autobuilder/single-root-go-mod-found",
"name": "A single `go.mod` file was found in the root"
},
"visibility": {
"cliSummaryTable": false,
"statusPage": false,
"telemetry": true
}
}

View File

@@ -1,3 +0,0 @@
go 1.21
module example

View File

@@ -1,5 +0,0 @@
package main
func main() {
}

View File

@@ -1,6 +0,0 @@
import os
def test(codeql, go):
os.environ["LGTM_INDEX_IMPORT_PATH"] = "test"
codeql.database.create(source_root="src")

View File

@@ -1,20 +1,3 @@
{
"location": {
"file": "go.mod"
},
"markdownMessage": "As of Go 1.21, toolchain versions [must use the 1.N.P syntax](https://go.dev/doc/toolchain#version).\n\n`1.21` in `go.mod` does not match this syntax and there is no additional `toolchain` directive, which may cause some `go` commands to fail.",
"severity": "warning",
"source": {
"extractorName": "go",
"id": "go/autobuilder/invalid-go-toolchain-version",
"name": "Invalid Go toolchain version"
},
"visibility": {
"cliSummaryTable": true,
"statusPage": true,
"telemetry": true
}
}
{
"markdownMessage": "A single `go.mod` file was found.\n\n`go.mod`",
"severity": "note",

View File

@@ -0,0 +1,6 @@
ql/go/ql/src/InconsistentCode/LengthComparisonOffByOne.ql
ql/go/ql/src/InconsistentCode/MissingErrorCheck.ql
ql/go/ql/src/InconsistentCode/UnhandledCloseWritableHandle.ql
ql/go/ql/src/InconsistentCode/WrappedErrorAlwaysNil.ql
ql/go/ql/src/RedundantCode/NegativeLengthCheck.ql
ql/go/ql/src/RedundantCode/RedundantRecover.ql

View File

@@ -0,0 +1,31 @@
ql/go/ql/src/Diagnostics/ExtractionErrors.ql
ql/go/ql/src/Diagnostics/SuccessfullyExtractedFiles.ql
ql/go/ql/src/Security/CWE-020/IncompleteHostnameRegexp.ql
ql/go/ql/src/Security/CWE-020/IncompleteUrlSchemeCheck.ql
ql/go/ql/src/Security/CWE-020/MissingRegexpAnchor.ql
ql/go/ql/src/Security/CWE-020/SuspiciousCharacterInRegexp.ql
ql/go/ql/src/Security/CWE-022/TaintedPath.ql
ql/go/ql/src/Security/CWE-022/UnsafeUnzipSymlink.ql
ql/go/ql/src/Security/CWE-022/ZipSlip.ql
ql/go/ql/src/Security/CWE-078/CommandInjection.ql
ql/go/ql/src/Security/CWE-079/ReflectedXss.ql
ql/go/ql/src/Security/CWE-089/SqlInjection.ql
ql/go/ql/src/Security/CWE-089/StringBreak.ql
ql/go/ql/src/Security/CWE-190/AllocationSizeOverflow.ql
ql/go/ql/src/Security/CWE-209/StackTraceExposure.ql
ql/go/ql/src/Security/CWE-295/DisabledCertificateCheck.ql
ql/go/ql/src/Security/CWE-312/CleartextLogging.ql
ql/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql
ql/go/ql/src/Security/CWE-326/InsufficientKeySize.ql
ql/go/ql/src/Security/CWE-327/InsecureTLS.ql
ql/go/ql/src/Security/CWE-338/InsecureRandomness.ql
ql/go/ql/src/Security/CWE-347/MissingJwtSignatureCheck.ql
ql/go/ql/src/Security/CWE-352/ConstantOauth2State.ql
ql/go/ql/src/Security/CWE-601/BadRedirectCheck.ql
ql/go/ql/src/Security/CWE-601/OpenUrlRedirect.ql
ql/go/ql/src/Security/CWE-640/EmailInjection.ql
ql/go/ql/src/Security/CWE-643/XPathInjection.ql
ql/go/ql/src/Security/CWE-681/IncorrectIntegerConversionQuery.ql
ql/go/ql/src/Security/CWE-770/UncontrolledAllocationSize.ql
ql/go/ql/src/Security/CWE-918/RequestForgery.ql
ql/go/ql/src/Summary/LinesOfCode.ql

View File

@@ -0,0 +1,55 @@
ql/go/ql/src/Diagnostics/ExtractionErrors.ql
ql/go/ql/src/Diagnostics/SuccessfullyExtractedFiles.ql
ql/go/ql/src/InconsistentCode/ConstantLengthComparison.ql
ql/go/ql/src/InconsistentCode/InconsistentLoopOrientation.ql
ql/go/ql/src/InconsistentCode/LengthComparisonOffByOne.ql
ql/go/ql/src/InconsistentCode/MissingErrorCheck.ql
ql/go/ql/src/InconsistentCode/MistypedExponentiation.ql
ql/go/ql/src/InconsistentCode/UnhandledCloseWritableHandle.ql
ql/go/ql/src/InconsistentCode/WhitespaceContradictsPrecedence.ql
ql/go/ql/src/InconsistentCode/WrappedErrorAlwaysNil.ql
ql/go/ql/src/RedundantCode/CompareIdenticalValues.ql
ql/go/ql/src/RedundantCode/DeadStoreOfField.ql
ql/go/ql/src/RedundantCode/DeadStoreOfLocal.ql
ql/go/ql/src/RedundantCode/DuplicateBranches.ql
ql/go/ql/src/RedundantCode/DuplicateCondition.ql
ql/go/ql/src/RedundantCode/DuplicateSwitchCase.ql
ql/go/ql/src/RedundantCode/ExprHasNoEffect.ql
ql/go/ql/src/RedundantCode/ImpossibleInterfaceNilCheck.ql
ql/go/ql/src/RedundantCode/NegativeLengthCheck.ql
ql/go/ql/src/RedundantCode/RedundantExpr.ql
ql/go/ql/src/RedundantCode/RedundantRecover.ql
ql/go/ql/src/RedundantCode/SelfAssignment.ql
ql/go/ql/src/RedundantCode/ShiftOutOfRange.ql
ql/go/ql/src/RedundantCode/UnreachableStatement.ql
ql/go/ql/src/Security/CWE-020/IncompleteHostnameRegexp.ql
ql/go/ql/src/Security/CWE-020/IncompleteUrlSchemeCheck.ql
ql/go/ql/src/Security/CWE-020/MissingRegexpAnchor.ql
ql/go/ql/src/Security/CWE-020/SuspiciousCharacterInRegexp.ql
ql/go/ql/src/Security/CWE-022/TaintedPath.ql
ql/go/ql/src/Security/CWE-022/UnsafeUnzipSymlink.ql
ql/go/ql/src/Security/CWE-022/ZipSlip.ql
ql/go/ql/src/Security/CWE-078/CommandInjection.ql
ql/go/ql/src/Security/CWE-079/ReflectedXss.ql
ql/go/ql/src/Security/CWE-089/SqlInjection.ql
ql/go/ql/src/Security/CWE-089/StringBreak.ql
ql/go/ql/src/Security/CWE-117/LogInjection.ql
ql/go/ql/src/Security/CWE-190/AllocationSizeOverflow.ql
ql/go/ql/src/Security/CWE-209/StackTraceExposure.ql
ql/go/ql/src/Security/CWE-295/DisabledCertificateCheck.ql
ql/go/ql/src/Security/CWE-312/CleartextLogging.ql
ql/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql
ql/go/ql/src/Security/CWE-326/InsufficientKeySize.ql
ql/go/ql/src/Security/CWE-327/InsecureTLS.ql
ql/go/ql/src/Security/CWE-338/InsecureRandomness.ql
ql/go/ql/src/Security/CWE-347/MissingJwtSignatureCheck.ql
ql/go/ql/src/Security/CWE-352/ConstantOauth2State.ql
ql/go/ql/src/Security/CWE-601/BadRedirectCheck.ql
ql/go/ql/src/Security/CWE-601/OpenUrlRedirect.ql
ql/go/ql/src/Security/CWE-640/EmailInjection.ql
ql/go/ql/src/Security/CWE-643/XPathInjection.ql
ql/go/ql/src/Security/CWE-681/IncorrectIntegerConversionQuery.ql
ql/go/ql/src/Security/CWE-770/UncontrolledAllocationSize.ql
ql/go/ql/src/Security/CWE-798/HardcodedCredentials.ql
ql/go/ql/src/Security/CWE-918/RequestForgery.ql
ql/go/ql/src/Summary/LinesOfCode.ql

View File

@@ -0,0 +1,33 @@
ql/go/ql/src/Diagnostics/ExtractionErrors.ql
ql/go/ql/src/Diagnostics/SuccessfullyExtractedFiles.ql
ql/go/ql/src/Security/CWE-020/IncompleteHostnameRegexp.ql
ql/go/ql/src/Security/CWE-020/IncompleteUrlSchemeCheck.ql
ql/go/ql/src/Security/CWE-020/MissingRegexpAnchor.ql
ql/go/ql/src/Security/CWE-020/SuspiciousCharacterInRegexp.ql
ql/go/ql/src/Security/CWE-022/TaintedPath.ql
ql/go/ql/src/Security/CWE-022/UnsafeUnzipSymlink.ql
ql/go/ql/src/Security/CWE-022/ZipSlip.ql
ql/go/ql/src/Security/CWE-078/CommandInjection.ql
ql/go/ql/src/Security/CWE-079/ReflectedXss.ql
ql/go/ql/src/Security/CWE-089/SqlInjection.ql
ql/go/ql/src/Security/CWE-089/StringBreak.ql
ql/go/ql/src/Security/CWE-117/LogInjection.ql
ql/go/ql/src/Security/CWE-190/AllocationSizeOverflow.ql
ql/go/ql/src/Security/CWE-209/StackTraceExposure.ql
ql/go/ql/src/Security/CWE-295/DisabledCertificateCheck.ql
ql/go/ql/src/Security/CWE-312/CleartextLogging.ql
ql/go/ql/src/Security/CWE-322/InsecureHostKeyCallback.ql
ql/go/ql/src/Security/CWE-326/InsufficientKeySize.ql
ql/go/ql/src/Security/CWE-327/InsecureTLS.ql
ql/go/ql/src/Security/CWE-338/InsecureRandomness.ql
ql/go/ql/src/Security/CWE-347/MissingJwtSignatureCheck.ql
ql/go/ql/src/Security/CWE-352/ConstantOauth2State.ql
ql/go/ql/src/Security/CWE-601/BadRedirectCheck.ql
ql/go/ql/src/Security/CWE-601/OpenUrlRedirect.ql
ql/go/ql/src/Security/CWE-640/EmailInjection.ql
ql/go/ql/src/Security/CWE-643/XPathInjection.ql
ql/go/ql/src/Security/CWE-681/IncorrectIntegerConversionQuery.ql
ql/go/ql/src/Security/CWE-770/UncontrolledAllocationSize.ql
ql/go/ql/src/Security/CWE-798/HardcodedCredentials.ql
ql/go/ql/src/Security/CWE-918/RequestForgery.ql
ql/go/ql/src/Summary/LinesOfCode.ql

View File

@@ -0,0 +1,33 @@
ql/go/ql/src/AlertSuppression.ql
ql/go/ql/src/Metrics/FLinesOfCode.ql
ql/go/ql/src/Metrics/FLinesOfComment.ql
ql/go/ql/src/Security/CWE-020/ExternalAPIsUsedWithUntrustedData.ql
ql/go/ql/src/Security/CWE-020/UntrustedDataToExternalAPI.ql
ql/go/ql/src/Security/CWE-020/UntrustedDataToUnknownExternalAPI.ql
ql/go/ql/src/Security/CWE-078/StoredCommand.ql
ql/go/ql/src/Security/CWE-079/StoredXss.ql
ql/go/ql/src/definitions.ql
ql/go/ql/src/experimental/CWE-090/LDAPInjection.ql
ql/go/ql/src/experimental/CWE-1004/CookieWithoutHttpOnly.ql
ql/go/ql/src/experimental/CWE-203/Timing.ql
ql/go/ql/src/experimental/CWE-285/PamAuthBypass.ql
ql/go/ql/src/experimental/CWE-287/ImproperLdapAuth.ql
ql/go/ql/src/experimental/CWE-321-V2/HardCodedKeys.ql
ql/go/ql/src/experimental/CWE-327/WeakCryptoAlgorithm.ql
ql/go/ql/src/experimental/CWE-369/DivideByZero.ql
ql/go/ql/src/experimental/CWE-400/DatabaseCallInLoop.ql
ql/go/ql/src/experimental/CWE-522-DecompressionBombs/DecompressionBombs.ql
ql/go/ql/src/experimental/CWE-525/WebCacheDeception.ql
ql/go/ql/src/experimental/CWE-74/DsnInjection.ql
ql/go/ql/src/experimental/CWE-74/DsnInjectionLocal.ql
ql/go/ql/src/experimental/CWE-79/HTMLTemplateEscapingPassthrough.ql
ql/go/ql/src/experimental/CWE-807/SensitiveConditionBypass.ql
ql/go/ql/src/experimental/CWE-840/ConditionalBypass.ql
ql/go/ql/src/experimental/CWE-918/SSRF.ql
ql/go/ql/src/experimental/CWE-942/CorsMisconfiguration.ql
ql/go/ql/src/experimental/InconsistentCode/DeferInLoop.ql
ql/go/ql/src/experimental/InconsistentCode/GORMErrorNotChecked.ql
ql/go/ql/src/experimental/IntegerOverflow/IntegerOverflow.ql
ql/go/ql/src/experimental/Unsafe/WrongUsageOfUnsafe.ql
ql/go/ql/src/filters/ClassifyFiles.ql
ql/go/ql/src/meta/frameworks/Coverage.ql

View File

@@ -0,0 +1,14 @@
import runs_on
import pytest
from query_suites import *
well_known_query_suites = ['go-code-quality.qls', 'go-security-and-quality.qls', 'go-security-extended.qls', 'go-code-scanning.qls']
@runs_on.posix
@pytest.mark.parametrize("query_suite", well_known_query_suites)
def test(codeql, go, check_query_suite, query_suite):
check_query_suite(query_suite)
@runs_on.posix
def test_not_included_queries(codeql, go, check_queries_not_included):
check_queries_not_included('go', well_known_query_suites)

View File

@@ -1,20 +1,3 @@
{
"location": {
"file": "go.mod"
},
"markdownMessage": "As of Go 1.21, toolchain versions [must use the 1.N.P syntax](https://go.dev/doc/toolchain#version).\n\n`1.22` in `go.mod` does not match this syntax and there is no additional `toolchain` directive, which may cause some `go` commands to fail.",
"severity": "warning",
"source": {
"extractorName": "go",
"id": "go/autobuilder/invalid-go-toolchain-version",
"name": "Invalid Go toolchain version"
},
"visibility": {
"cliSummaryTable": true,
"statusPage": true,
"telemetry": true
}
}
{
"markdownMessage": "A single `go.mod` file was found.\n\n`go.mod`",
"severity": "note",

Some files were not shown because too many files have changed in this diff Show More