diff --git a/CODEOWNERS b/CODEOWNERS
index b2eb53f0bb0..738605d6032 100644
--- a/CODEOWNERS
+++ b/CODEOWNERS
@@ -8,6 +8,8 @@
/swift/ @github/codeql-swift
/misc/codegen/ @github/codeql-swift
/java/kotlin-extractor/ @github/codeql-kotlin
+/java/ql/test-kotlin1/ @github/codeql-kotlin
+/java/ql/test-kotlin2/ @github/codeql-kotlin
# ML-powered queries
/javascript/ql/experimental/adaptivethreatmodeling/ @github/codeql-ml-powered-queries-reviewers
diff --git a/codeql-workspace.yml b/codeql-workspace.yml
index 31c94676962..5d8b300c8f4 100644
--- a/codeql-workspace.yml
+++ b/codeql-workspace.yml
@@ -1,7 +1,7 @@
provide:
- "*/ql/src/qlpack.yml"
- "*/ql/lib/qlpack.yml"
- - "*/ql/test/qlpack.yml"
+ - "*/ql/test*/qlpack.yml"
- "*/ql/examples/qlpack.yml"
- "*/ql/consistency-queries/qlpack.yml"
- "*/ql/automodel/src/qlpack.yml"
diff --git a/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/old.dbscheme b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/old.dbscheme
new file mode 100644
index 00000000000..0a9eb01d365
--- /dev/null
+++ b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/old.dbscheme
@@ -0,0 +1,2233 @@
+
+/**
+ * An invocation of the compiler. Note that more than one file may be
+ * compiled per invocation. For example, this command compiles three
+ * source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * The `id` simply identifies the invocation, while `cwd` is the working
+ * directory from which the compiler was invoked.
+ */
+compilations(
+ /**
+ * An invocation of the compiler. Note that more than one file may
+ * be compiled per invocation. For example, this command compiles
+ * three source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ */
+ unique int id : @compilation,
+ string cwd : string ref
+);
+
+/**
+ * The arguments that were passed to the extractor for a compiler
+ * invocation. If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then typically there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | *path to extractor*
+ * 1 | `--mimic`
+ * 2 | `/usr/bin/gcc`
+ * 3 | `-c`
+ * 4 | f1.c
+ * 5 | f2.c
+ * 6 | f3.c
+ */
+#keyset[id, num]
+compilation_args(
+ int id : @compilation ref,
+ int num : int ref,
+ string arg : string ref
+);
+
+/**
+ * The source files that are compiled by a compiler invocation.
+ * If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | f1.c
+ * 1 | f2.c
+ * 2 | f3.c
+ *
+ * Note that even if those files `#include` headers, those headers
+ * do not appear as rows.
+ */
+#keyset[id, num]
+compilation_compiling_files(
+ int id : @compilation ref,
+ int num : int ref,
+ int file : @file ref
+);
+
+/**
+ * The time taken by the extractor for a compiler invocation.
+ *
+ * For each file `num`, there will be rows for
+ *
+ * kind | seconds
+ * ---- | ---
+ * 1 | CPU seconds used by the extractor frontend
+ * 2 | Elapsed seconds during the extractor frontend
+ * 3 | CPU seconds used by the extractor backend
+ * 4 | Elapsed seconds during the extractor backend
+ */
+#keyset[id, num, kind]
+compilation_time(
+ int id : @compilation ref,
+ int num : int ref,
+ /* kind:
+ 1 = frontend_cpu_seconds
+ 2 = frontend_elapsed_seconds
+ 3 = extractor_cpu_seconds
+ 4 = extractor_elapsed_seconds
+ */
+ int kind : int ref,
+ float seconds : float ref
+);
+
+/**
+ * An error or warning generated by the extractor.
+ * The diagnostic message `diagnostic` was generated during compiler
+ * invocation `compilation`, and is the `file_number_diagnostic_number`th
+ * message generated while extracting the `file_number`th file of that
+ * invocation.
+ */
+#keyset[compilation, file_number, file_number_diagnostic_number]
+diagnostic_for(
+ int diagnostic : @diagnostic ref,
+ int compilation : @compilation ref,
+ int file_number : int ref,
+ int file_number_diagnostic_number : int ref
+);
+
+/**
+ * If extraction was successful, then `cpu_seconds` and
+ * `elapsed_seconds` are the CPU time and elapsed time (respectively)
+ * that extraction took for compiler invocation `id`.
+ */
+compilation_finished(
+ unique int id : @compilation ref,
+ float cpu_seconds : float ref,
+ float elapsed_seconds : float ref
+);
+
+
+/**
+ * External data, loaded from CSV files during snapshot creation. See
+ * [Tutorial: Incorporating external data](https://help.semmle.com/wiki/display/SD/Tutorial%3A+Incorporating+external+data)
+ * for more information.
+ */
+externalData(
+ int id : @externalDataElement,
+ string path : string ref,
+ int column: int ref,
+ string value : string ref
+);
+
+/**
+ * The source location of the snapshot.
+ */
+sourceLocationPrefix(string prefix : string ref);
+
+/**
+ * Information about packages that provide code used during compilation.
+ * The `id` is just a unique identifier.
+ * The `namespace` is typically the name of the package manager that
+ * provided the package (e.g. "dpkg" or "yum").
+ * The `package_name` is the name of the package, and `version` is its
+ * version (as a string).
+ */
+external_packages(
+ unique int id: @external_package,
+ string namespace : string ref,
+ string package_name : string ref,
+ string version : string ref
+);
+
+/**
+ * Holds if File `fileid` was provided by package `package`.
+ */
+header_to_external_package(
+ int fileid : @file ref,
+ int package : @external_package ref
+);
+
+/*
+ * Version history
+ */
+
+svnentries(
+ unique int id : @svnentry,
+ string revision : string ref,
+ string author : string ref,
+ date revisionDate : date ref,
+ int changeSize : int ref
+)
+
+svnaffectedfiles(
+ int id : @svnentry ref,
+ int file : @file ref,
+ string action : string ref
+)
+
+svnentrymsg(
+ unique int id : @svnentry ref,
+ string message : string ref
+)
+
+svnchurn(
+ int commit : @svnentry ref,
+ int file : @file ref,
+ int addedLines : int ref,
+ int deletedLines : int ref
+)
+
+/*
+ * C++ dbscheme
+ */
+
+extractor_version(
+ string codeql_version: string ref,
+ string frontend_version: string ref
+)
+
+@location = @location_stmt | @location_expr | @location_default ;
+
+/**
+ * The location of an element that is not an expression or a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_default(
+ /** The location of an element that is not an expression or a statement. */
+ unique int id: @location_default,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_stmt(
+ /** The location of a statement. */
+ unique int id: @location_stmt,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of an expression.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_expr(
+ /** The location of an expression. */
+ unique int id: @location_expr,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/** An element for which line-count information is available. */
+@sourceline = @file | @function | @variable | @enumconstant | @xmllocatable;
+
+numlines(
+ int element_id: @sourceline ref,
+ int num_lines: int ref,
+ int num_code: int ref,
+ int num_comment: int ref
+);
+
+diagnostics(
+ unique int id: @diagnostic,
+ int severity: int ref,
+ string error_tag: string ref,
+ string error_message: string ref,
+ string full_error_message: string ref,
+ int location: @location_default ref
+);
+
+files(
+ unique int id: @file,
+ string name: string ref
+);
+
+folders(
+ unique int id: @folder,
+ string name: string ref
+);
+
+@container = @folder | @file
+
+containerparent(
+ int parent: @container ref,
+ unique int child: @container ref
+);
+
+fileannotations(
+ int id: @file ref,
+ int kind: int ref,
+ string name: string ref,
+ string value: string ref
+);
+
+inmacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+affectedbymacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+case @macroinvocation.kind of
+ 1 = @macro_expansion
+| 2 = @other_macro_reference
+;
+
+macroinvocations(
+ unique int id: @macroinvocation,
+ int macro_id: @ppd_define ref,
+ int location: @location_default ref,
+ int kind: int ref
+);
+
+macroparent(
+ unique int id: @macroinvocation ref,
+ int parent_id: @macroinvocation ref
+);
+
+// a macroinvocation may be part of another location
+// the way to find a constant expression that uses a macro
+// is thus to find a constant expression that has a location
+// to which a macro invocation is bound
+macrolocationbind(
+ int id: @macroinvocation ref,
+ int location: @location ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_unexpanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_expanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+/*
+case @function.kind of
+ 1 = @normal_function
+| 2 = @constructor
+| 3 = @destructor
+| 4 = @conversion_function
+| 5 = @operator
+| 6 = @builtin_function // GCC built-in functions, e.g. __builtin___memcpy_chk
+;
+*/
+
+functions(
+ unique int id: @function,
+ string name: string ref,
+ int kind: int ref
+);
+
+function_entry_point(
+ int id: @function ref,
+ unique int entry_point: @stmt ref
+);
+
+function_return_type(
+ int id: @function ref,
+ int return_type: @type ref
+);
+
+/**
+ * If `function` is a coroutine, then this gives the `std::experimental::resumable_traits`
+ * instance associated with it, and the variables representing the `handle` and `promise`
+ * for it.
+ */
+coroutine(
+ unique int function: @function ref,
+ int traits: @type ref,
+ int handle: @variable ref,
+ int promise: @variable ref
+);
+
+/** The `new` function used for allocating the coroutine state, if any. */
+coroutine_new(
+ unique int function: @function ref,
+ int new: @function ref
+);
+
+/** The `delete` function used for deallocating the coroutine state, if any. */
+coroutine_delete(
+ unique int function: @function ref,
+ int delete: @function ref
+);
+
+purefunctions(unique int id: @function ref);
+
+function_deleted(unique int id: @function ref);
+
+function_defaulted(unique int id: @function ref);
+
+function_prototyped(unique int id: @function ref)
+
+member_function_this_type(
+ unique int id: @function ref,
+ int this_type: @type ref
+);
+
+#keyset[id, type_id]
+fun_decls(
+ int id: @fun_decl,
+ int function: @function ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+fun_def(unique int id: @fun_decl ref);
+fun_specialized(unique int id: @fun_decl ref);
+fun_implicit(unique int id: @fun_decl ref);
+fun_decl_specifiers(
+ int id: @fun_decl ref,
+ string name: string ref
+)
+#keyset[fun_decl, index]
+fun_decl_throws(
+ int fun_decl: @fun_decl ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+/* an empty throw specification is different from none */
+fun_decl_empty_throws(unique int fun_decl: @fun_decl ref);
+fun_decl_noexcept(
+ int fun_decl: @fun_decl ref,
+ int constant: @expr ref
+);
+fun_decl_empty_noexcept(int fun_decl: @fun_decl ref);
+fun_decl_typedef_type(
+ unique int fun_decl: @fun_decl ref,
+ int typedeftype_id: @usertype ref
+);
+
+param_decl_bind(
+ unique int id: @var_decl ref,
+ int index: int ref,
+ int fun_decl: @fun_decl ref
+);
+
+#keyset[id, type_id]
+var_decls(
+ int id: @var_decl,
+ int variable: @variable ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+var_def(unique int id: @var_decl ref);
+var_decl_specifiers(
+ int id: @var_decl ref,
+ string name: string ref
+)
+is_structured_binding(unique int id: @variable ref);
+
+type_decls(
+ unique int id: @type_decl,
+ int type_id: @type ref,
+ int location: @location_default ref
+);
+type_def(unique int id: @type_decl ref);
+type_decl_top(
+ unique int type_decl: @type_decl ref
+);
+
+namespace_decls(
+ unique int id: @namespace_decl,
+ int namespace_id: @namespace ref,
+ int location: @location_default ref,
+ int bodylocation: @location_default ref
+);
+
+usings(
+ unique int id: @using,
+ int element_id: @element ref,
+ int location: @location_default ref
+);
+
+/** The element which contains the `using` declaration. */
+using_container(
+ int parent: @element ref,
+ int child: @using ref
+);
+
+static_asserts(
+ unique int id: @static_assert,
+ int condition : @expr ref,
+ string message : string ref,
+ int location: @location_default ref,
+ int enclosing : @element ref
+);
+
+// each function has an ordered list of parameters
+#keyset[id, type_id]
+#keyset[function, index, type_id]
+params(
+ int id: @parameter,
+ int function: @functionorblock ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+overrides(
+ int new: @function ref,
+ int old: @function ref
+);
+
+#keyset[id, type_id]
+membervariables(
+ int id: @membervariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+globalvariables(
+ int id: @globalvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+localvariables(
+ int id: @localvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+autoderivation(
+ unique int var: @variable ref,
+ int derivation_type: @type ref
+);
+
+orphaned_variables(
+ int var: @localvariable ref,
+ int function: @function ref
+)
+
+enumconstants(
+ unique int id: @enumconstant,
+ int parent: @usertype ref,
+ int index: int ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+
+@variable = @localscopevariable | @globalvariable | @membervariable;
+
+@localscopevariable = @localvariable | @parameter;
+
+/**
+ * Built-in types are the fundamental types, e.g., integral, floating, and void.
+ */
+case @builtintype.kind of
+ 1 = @errortype
+| 2 = @unknowntype
+| 3 = @void
+| 4 = @boolean
+| 5 = @char
+| 6 = @unsigned_char
+| 7 = @signed_char
+| 8 = @short
+| 9 = @unsigned_short
+| 10 = @signed_short
+| 11 = @int
+| 12 = @unsigned_int
+| 13 = @signed_int
+| 14 = @long
+| 15 = @unsigned_long
+| 16 = @signed_long
+| 17 = @long_long
+| 18 = @unsigned_long_long
+| 19 = @signed_long_long
+// ... 20 Microsoft-specific __int8
+// ... 21 Microsoft-specific __int16
+// ... 22 Microsoft-specific __int32
+// ... 23 Microsoft-specific __int64
+| 24 = @float
+| 25 = @double
+| 26 = @long_double
+| 27 = @complex_float // C99-specific _Complex float
+| 28 = @complex_double // C99-specific _Complex double
+| 29 = @complex_long_double // C99-specific _Complex long double
+| 30 = @imaginary_float // C99-specific _Imaginary float
+| 31 = @imaginary_double // C99-specific _Imaginary double
+| 32 = @imaginary_long_double // C99-specific _Imaginary long double
+| 33 = @wchar_t // Microsoft-specific
+| 34 = @decltype_nullptr // C++11
+| 35 = @int128 // __int128
+| 36 = @unsigned_int128 // unsigned __int128
+| 37 = @signed_int128 // signed __int128
+| 38 = @float128 // __float128
+| 39 = @complex_float128 // _Complex __float128
+| 40 = @decimal32 // _Decimal32
+| 41 = @decimal64 // _Decimal64
+| 42 = @decimal128 // _Decimal128
+| 43 = @char16_t
+| 44 = @char32_t
+| 45 = @std_float32 // _Float32
+| 46 = @float32x // _Float32x
+| 47 = @std_float64 // _Float64
+| 48 = @float64x // _Float64x
+| 49 = @std_float128 // _Float128
+// ... 50 _Float128x
+| 51 = @char8_t
+| 52 = @float16 // _Float16
+| 53 = @complex_float16 // _Complex _Float16
+| 54 = @fp16 // __fp16
+| 55 = @std_bfloat16 // __bf16
+| 56 = @std_float16 // std::float16_t
+| 57 = @complex_std_float32 // _Complex _Float32
+| 58 = @complex_float32x // _Complex _Float32x
+| 59 = @complex_std_float64 // _Complex _Float64
+| 60 = @complex_float64x // _Complex _Float64x
+| 61 = @complex_std_float128 // _Complex _Float128
+;
+
+builtintypes(
+ unique int id: @builtintype,
+ string name: string ref,
+ int kind: int ref,
+ int size: int ref,
+ int sign: int ref,
+ int alignment: int ref
+);
+
+/**
+ * Derived types are types that are directly derived from existing types and
+ * point to, refer to, transform type data to return a new type.
+ */
+case @derivedtype.kind of
+ 1 = @pointer
+| 2 = @reference
+| 3 = @type_with_specifiers
+| 4 = @array
+| 5 = @gnu_vector
+| 6 = @routineptr
+| 7 = @routinereference
+| 8 = @rvalue_reference // C++11
+// ... 9 type_conforming_to_protocols deprecated
+| 10 = @block
+;
+
+derivedtypes(
+ unique int id: @derivedtype,
+ string name: string ref,
+ int kind: int ref,
+ int type_id: @type ref
+);
+
+pointerishsize(unique int id: @derivedtype ref,
+ int size: int ref,
+ int alignment: int ref);
+
+arraysizes(
+ unique int id: @derivedtype ref,
+ int num_elements: int ref,
+ int bytesize: int ref,
+ int alignment: int ref
+);
+
+typedefbase(
+ unique int id: @usertype ref,
+ int type_id: @type ref
+);
+
+/**
+ * An instance of the C++11 `decltype` operator. For example:
+ * ```
+ * int a;
+ * decltype(1+a) b;
+ * ```
+ * Here `expr` is `1+a`.
+ *
+ * Sometimes an additional pair of parentheses around the expression
+ * would change the semantics of this decltype, e.g.
+ * ```
+ * struct A { double x; };
+ * const A* a = new A();
+ * decltype( a->x ); // type is double
+ * decltype((a->x)); // type is const double&
+ * ```
+ * (Please consult the C++11 standard for more details).
+ * `parentheses_would_change_meaning` is `true` iff that is the case.
+ */
+#keyset[id, expr]
+decltypes(
+ int id: @decltype,
+ int expr: @expr ref,
+ int base_type: @type ref,
+ boolean parentheses_would_change_meaning: boolean ref
+);
+
+/*
+case @usertype.kind of
+ 1 = @struct
+| 2 = @class
+| 3 = @union
+| 4 = @enum
+| 5 = @typedef // classic C: typedef typedef type name
+| 6 = @template
+| 7 = @template_parameter
+| 8 = @template_template_parameter
+| 9 = @proxy_class // a proxy class associated with a template parameter
+// ... 10 objc_class deprecated
+// ... 11 objc_protocol deprecated
+// ... 12 objc_category deprecated
+| 13 = @scoped_enum
+| 14 = @using_alias // a using name = type style typedef
+;
+*/
+
+usertypes(
+ unique int id: @usertype,
+ string name: string ref,
+ int kind: int ref
+);
+
+usertypesize(
+ unique int id: @usertype ref,
+ int size: int ref,
+ int alignment: int ref
+);
+
+usertype_final(unique int id: @usertype ref);
+
+usertype_uuid(
+ unique int id: @usertype ref,
+ string uuid: string ref
+);
+
+mangled_name(
+ unique int id: @declaration ref,
+ int mangled_name : @mangledname
+);
+
+is_pod_class(unique int id: @usertype ref);
+is_standard_layout_class(unique int id: @usertype ref);
+
+is_complete(unique int id: @usertype ref);
+
+is_class_template(unique int id: @usertype ref);
+class_instantiation(
+ int to: @usertype ref,
+ int from: @usertype ref
+);
+class_template_argument(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+class_template_argument_value(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_proxy_class_for(
+ unique int id: @usertype ref,
+ unique int templ_param_id: @usertype ref
+);
+
+type_mentions(
+ unique int id: @type_mention,
+ int type_id: @type ref,
+ int location: @location ref,
+ // a_symbol_reference_kind from the frontend.
+ int kind: int ref
+);
+
+is_function_template(unique int id: @function ref);
+function_instantiation(
+ unique int to: @function ref,
+ int from: @function ref
+);
+function_template_argument(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+function_template_argument_value(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_variable_template(unique int id: @variable ref);
+variable_instantiation(
+ unique int to: @variable ref,
+ int from: @variable ref
+);
+variable_template_argument(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+variable_template_argument_value(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+/*
+ Fixed point types
+ precision(1) = short, precision(2) = default, precision(3) = long
+ is_unsigned(1) = unsigned is_unsigned(2) = signed
+ is_fract_type(1) = declared with _Fract
+ saturating(1) = declared with _Sat
+*/
+/* TODO
+fixedpointtypes(
+ unique int id: @fixedpointtype,
+ int precision: int ref,
+ int is_unsigned: int ref,
+ int is_fract_type: int ref,
+ int saturating: int ref);
+*/
+
+routinetypes(
+ unique int id: @routinetype,
+ int return_type: @type ref
+);
+
+routinetypeargs(
+ int routine: @routinetype ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+ptrtomembers(
+ unique int id: @ptrtomember,
+ int type_id: @type ref,
+ int class_id: @type ref
+);
+
+/*
+ specifiers for types, functions, and variables
+
+ "public",
+ "protected",
+ "private",
+
+ "const",
+ "volatile",
+ "static",
+
+ "pure",
+ "virtual",
+ "sealed", // Microsoft
+ "__interface", // Microsoft
+ "inline",
+ "explicit",
+
+ "near", // near far extension
+ "far", // near far extension
+ "__ptr32", // Microsoft
+ "__ptr64", // Microsoft
+ "__sptr", // Microsoft
+ "__uptr", // Microsoft
+ "dllimport", // Microsoft
+ "dllexport", // Microsoft
+ "thread", // Microsoft
+ "naked", // Microsoft
+ "microsoft_inline", // Microsoft
+ "forceinline", // Microsoft
+ "selectany", // Microsoft
+ "nothrow", // Microsoft
+ "novtable", // Microsoft
+ "noreturn", // Microsoft
+ "noinline", // Microsoft
+ "noalias", // Microsoft
+ "restrict", // Microsoft
+*/
+
+specifiers(
+ unique int id: @specifier,
+ unique string str: string ref
+);
+
+typespecifiers(
+ int type_id: @type ref,
+ int spec_id: @specifier ref
+);
+
+funspecifiers(
+ int func_id: @function ref,
+ int spec_id: @specifier ref
+);
+
+varspecifiers(
+ int var_id: @accessible ref,
+ int spec_id: @specifier ref
+);
+
+attributes(
+ unique int id: @attribute,
+ int kind: int ref,
+ string name: string ref,
+ string name_space: string ref,
+ int location: @location_default ref
+);
+
+case @attribute.kind of
+ 0 = @gnuattribute
+| 1 = @stdattribute
+| 2 = @declspec
+| 3 = @msattribute
+| 4 = @alignas
+// ... 5 @objc_propertyattribute deprecated
+;
+
+attribute_args(
+ unique int id: @attribute_arg,
+ int kind: int ref,
+ int attribute: @attribute ref,
+ int index: int ref,
+ int location: @location_default ref
+);
+
+case @attribute_arg.kind of
+ 0 = @attribute_arg_empty
+| 1 = @attribute_arg_token
+| 2 = @attribute_arg_constant
+| 3 = @attribute_arg_type
+| 4 = @attribute_arg_constant_expr
+;
+
+attribute_arg_value(
+ unique int arg: @attribute_arg ref,
+ string value: string ref
+);
+attribute_arg_type(
+ unique int arg: @attribute_arg ref,
+ int type_id: @type ref
+);
+attribute_arg_constant(
+ unique int arg: @attribute_arg ref,
+ int constant: @expr ref
+)
+attribute_arg_name(
+ unique int arg: @attribute_arg ref,
+ string name: string ref
+);
+
+typeattributes(
+ int type_id: @type ref,
+ int spec_id: @attribute ref
+);
+
+funcattributes(
+ int func_id: @function ref,
+ int spec_id: @attribute ref
+);
+
+varattributes(
+ int var_id: @accessible ref,
+ int spec_id: @attribute ref
+);
+
+stmtattributes(
+ int stmt_id: @stmt ref,
+ int spec_id: @attribute ref
+);
+
+@type = @builtintype
+ | @derivedtype
+ | @usertype
+ /* TODO | @fixedpointtype */
+ | @routinetype
+ | @ptrtomember
+ | @decltype;
+
+unspecifiedtype(
+ unique int type_id: @type ref,
+ int unspecified_type_id: @type ref
+);
+
+member(
+ int parent: @type ref,
+ int index: int ref,
+ int child: @member ref
+);
+
+@enclosingfunction_child = @usertype | @variable | @namespace
+
+enclosingfunction(
+ unique int child: @enclosingfunction_child ref,
+ int parent: @function ref
+);
+
+derivations(
+ unique int derivation: @derivation,
+ int sub: @type ref,
+ int index: int ref,
+ int super: @type ref,
+ int location: @location_default ref
+);
+
+derspecifiers(
+ int der_id: @derivation ref,
+ int spec_id: @specifier ref
+);
+
+/**
+ * Contains the byte offset of the base class subobject within the derived
+ * class. Only holds for non-virtual base classes, but see table
+ * `virtual_base_offsets` for offsets of virtual base class subobjects.
+ */
+direct_base_offsets(
+ unique int der_id: @derivation ref,
+ int offset: int ref
+);
+
+/**
+ * Contains the byte offset of the virtual base class subobject for class
+ * `super` within a most-derived object of class `sub`. `super` can be either a
+ * direct or indirect base class.
+ */
+#keyset[sub, super]
+virtual_base_offsets(
+ int sub: @usertype ref,
+ int super: @usertype ref,
+ int offset: int ref
+);
+
+frienddecls(
+ unique int id: @frienddecl,
+ int type_id: @type ref,
+ int decl_id: @declaration ref,
+ int location: @location_default ref
+);
+
+@declaredtype = @usertype ;
+
+@declaration = @function
+ | @declaredtype
+ | @variable
+ | @enumconstant
+ | @frienddecl;
+
+@member = @membervariable
+ | @function
+ | @declaredtype
+ | @enumconstant;
+
+@locatable = @diagnostic
+ | @declaration
+ | @ppd_include
+ | @ppd_define
+ | @macroinvocation
+ /*| @funcall*/
+ | @xmllocatable
+ | @attribute
+ | @attribute_arg;
+
+@namedscope = @namespace | @usertype;
+
+@element = @locatable
+ | @file
+ | @folder
+ | @specifier
+ | @type
+ | @expr
+ | @namespace
+ | @initialiser
+ | @stmt
+ | @derivation
+ | @comment
+ | @preprocdirect
+ | @fun_decl
+ | @var_decl
+ | @type_decl
+ | @namespace_decl
+ | @using
+ | @namequalifier
+ | @specialnamequalifyingelement
+ | @static_assert
+ | @type_mention
+ | @lambdacapture;
+
+@exprparent = @element;
+
+comments(
+ unique int id: @comment,
+ string contents: string ref,
+ int location: @location_default ref
+);
+
+commentbinding(
+ int id: @comment ref,
+ int element: @element ref
+);
+
+exprconv(
+ int converted: @expr ref,
+ unique int conversion: @expr ref
+);
+
+compgenerated(unique int id: @element ref);
+
+/**
+ * `destructor_call` destructs the `i`'th entity that should be
+ * destructed following `element`. Note that entities should be
+ * destructed in reverse construction order, so for a given `element`
+ * these should be called from highest to lowest `i`.
+ */
+#keyset[element, destructor_call]
+#keyset[element, i]
+synthetic_destructor_call(
+ int element: @element ref,
+ int i: int ref,
+ int destructor_call: @routineexpr ref
+);
+
+namespaces(
+ unique int id: @namespace,
+ string name: string ref
+);
+
+namespace_inline(
+ unique int id: @namespace ref
+);
+
+namespacembrs(
+ int parentid: @namespace ref,
+ unique int memberid: @namespacembr ref
+);
+
+@namespacembr = @declaration | @namespace;
+
+exprparents(
+ int expr_id: @expr ref,
+ int child_index: int ref,
+ int parent_id: @exprparent ref
+);
+
+expr_isload(unique int expr_id: @expr ref);
+
+@cast = @c_style_cast
+ | @const_cast
+ | @dynamic_cast
+ | @reinterpret_cast
+ | @static_cast
+ ;
+
+/*
+case @conversion.kind of
+ 0 = @simple_conversion // a numeric conversion, qualification conversion, or a reinterpret_cast
+| 1 = @bool_conversion // conversion to 'bool'
+| 2 = @base_class_conversion // a derived-to-base conversion
+| 3 = @derived_class_conversion // a base-to-derived conversion
+| 4 = @pm_base_class_conversion // a derived-to-base conversion of a pointer to member
+| 5 = @pm_derived_class_conversion // a base-to-derived conversion of a pointer to member
+| 6 = @glvalue_adjust // an adjustment of the type of a glvalue
+| 7 = @prvalue_adjust // an adjustment of the type of a prvalue
+;
+*/
+/**
+ * Describes the semantics represented by a cast expression. This is largely
+ * independent of the source syntax of the cast, so it is separate from the
+ * regular expression kind.
+ */
+conversionkinds(
+ unique int expr_id: @cast ref,
+ int kind: int ref
+);
+
+@conversion = @cast
+ | @array_to_pointer
+ | @parexpr
+ | @reference_to
+ | @ref_indirect
+ | @temp_init
+ ;
+
+/*
+case @funbindexpr.kind of
+ 0 = @normal_call // a normal call
+| 1 = @virtual_call // a virtual call
+| 2 = @adl_call // a call whose target is only found by ADL
+;
+*/
+iscall(
+ unique int caller: @funbindexpr ref,
+ int kind: int ref
+);
+
+numtemplatearguments(
+ unique int expr_id: @expr ref,
+ int num: int ref
+);
+
+specialnamequalifyingelements(
+ unique int id: @specialnamequalifyingelement,
+ unique string name: string ref
+);
+
+@namequalifiableelement = @expr | @namequalifier;
+@namequalifyingelement = @namespace
+ | @specialnamequalifyingelement
+ | @usertype;
+
+namequalifiers(
+ unique int id: @namequalifier,
+ unique int qualifiableelement: @namequalifiableelement ref,
+ int qualifyingelement: @namequalifyingelement ref,
+ int location: @location_default ref
+);
+
+varbind(
+ int expr: @varbindexpr ref,
+ int var: @accessible ref
+);
+
+funbind(
+ int expr: @funbindexpr ref,
+ int fun: @function ref
+);
+
+@any_new_expr = @new_expr
+ | @new_array_expr;
+
+@new_or_delete_expr = @any_new_expr
+ | @delete_expr
+ | @delete_array_expr;
+
+@prefix_crement_expr = @preincrexpr | @predecrexpr;
+
+@postfix_crement_expr = @postincrexpr | @postdecrexpr;
+
+@increment_expr = @preincrexpr | @postincrexpr;
+
+@decrement_expr = @predecrexpr | @postdecrexpr;
+
+@crement_expr = @increment_expr | @decrement_expr;
+
+@un_arith_op_expr = @arithnegexpr
+ | @unaryplusexpr
+ | @conjugation
+ | @realpartexpr
+ | @imagpartexpr
+ | @crement_expr
+ ;
+
+@un_bitwise_op_expr = @complementexpr;
+
+@un_log_op_expr = @notexpr;
+
+@un_op_expr = @address_of
+ | @indirect
+ | @un_arith_op_expr
+ | @un_bitwise_op_expr
+ | @builtinaddressof
+ | @vec_fill
+ | @un_log_op_expr
+ | @co_await
+ | @co_yield
+ ;
+
+@bin_log_op_expr = @andlogicalexpr | @orlogicalexpr;
+
+@cmp_op_expr = @eq_op_expr | @rel_op_expr;
+
+@eq_op_expr = @eqexpr | @neexpr;
+
+@rel_op_expr = @gtexpr
+ | @ltexpr
+ | @geexpr
+ | @leexpr
+ | @spaceshipexpr
+ ;
+
+@bin_bitwise_op_expr = @lshiftexpr
+ | @rshiftexpr
+ | @andexpr
+ | @orexpr
+ | @xorexpr
+ ;
+
+@p_arith_op_expr = @paddexpr
+ | @psubexpr
+ | @pdiffexpr
+ ;
+
+@bin_arith_op_expr = @addexpr
+ | @subexpr
+ | @mulexpr
+ | @divexpr
+ | @remexpr
+ | @jmulexpr
+ | @jdivexpr
+ | @fjaddexpr
+ | @jfaddexpr
+ | @fjsubexpr
+ | @jfsubexpr
+ | @minexpr
+ | @maxexpr
+ | @p_arith_op_expr
+ ;
+
+@bin_op_expr = @bin_arith_op_expr
+ | @bin_bitwise_op_expr
+ | @cmp_op_expr
+ | @bin_log_op_expr
+ ;
+
+@op_expr = @un_op_expr
+ | @bin_op_expr
+ | @assign_expr
+ | @conditionalexpr
+ ;
+
+@assign_arith_expr = @assignaddexpr
+ | @assignsubexpr
+ | @assignmulexpr
+ | @assigndivexpr
+ | @assignremexpr
+ ;
+
+@assign_bitwise_expr = @assignandexpr
+ | @assignorexpr
+ | @assignxorexpr
+ | @assignlshiftexpr
+ | @assignrshiftexpr
+ ;
+
+@assign_pointer_expr = @assignpaddexpr
+ | @assignpsubexpr
+ ;
+
+@assign_op_expr = @assign_arith_expr
+ | @assign_bitwise_expr
+ | @assign_pointer_expr
+ ;
+
+@assign_expr = @assignexpr | @assign_op_expr | @blockassignexpr
+
+/*
+ case @allocator.form of
+ 0 = plain
+ | 1 = alignment
+ ;
+*/
+
+/**
+ * The allocator function associated with a `new` or `new[]` expression.
+ * The `form` column specified whether the allocation call contains an alignment
+ * argument.
+ */
+expr_allocator(
+ unique int expr: @any_new_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/*
+ case @deallocator.form of
+ 0 = plain
+ | 1 = size
+ | 2 = alignment
+ | 3 = size_and_alignment
+ ;
+*/
+
+/**
+ * The deallocator function associated with a `delete`, `delete[]`, `new`, or
+ * `new[]` expression. For a `new` or `new[]` expression, the deallocator is the
+ * one used to free memory if the initialization throws an exception.
+ * The `form` column specifies whether the deallocation call contains a size
+ * argument, and alignment argument, or both.
+ */
+expr_deallocator(
+ unique int expr: @new_or_delete_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/**
+ * Holds if the `@conditionalexpr` is of the two operand form
+ * `guard ? : false`.
+ */
+expr_cond_two_operand(
+ unique int cond: @conditionalexpr ref
+);
+
+/**
+ * The guard of `@conditionalexpr` `guard ? true : false`
+ */
+expr_cond_guard(
+ unique int cond: @conditionalexpr ref,
+ int guard: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` holds. For the two operand form
+ * `guard ?: false` consider using `expr_cond_guard` instead.
+ */
+expr_cond_true(
+ unique int cond: @conditionalexpr ref,
+ int true: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` does not hold.
+ */
+expr_cond_false(
+ unique int cond: @conditionalexpr ref,
+ int false: @expr ref
+);
+
+/** A string representation of the value. */
+values(
+ unique int id: @value,
+ string str: string ref
+);
+
+/** The actual text in the source code for the value, if any. */
+valuetext(
+ unique int id: @value ref,
+ string text: string ref
+);
+
+valuebind(
+ int val: @value ref,
+ unique int expr: @expr ref
+);
+
+fieldoffsets(
+ unique int id: @variable ref,
+ int byteoffset: int ref,
+ int bitoffset: int ref
+);
+
+bitfield(
+ unique int id: @variable ref,
+ int bits: int ref,
+ int declared_bits: int ref
+);
+
+/* TODO
+memberprefix(
+ int member: @expr ref,
+ int prefix: @expr ref
+);
+*/
+
+/*
+ kind(1) = mbrcallexpr
+ kind(2) = mbrptrcallexpr
+ kind(3) = mbrptrmbrcallexpr
+ kind(4) = ptrmbrptrmbrcallexpr
+ kind(5) = mbrreadexpr // x.y
+ kind(6) = mbrptrreadexpr // p->y
+ kind(7) = mbrptrmbrreadexpr // x.*pm
+ kind(8) = mbrptrmbrptrreadexpr // x->*pm
+ kind(9) = staticmbrreadexpr // static x.y
+ kind(10) = staticmbrptrreadexpr // static p->y
+*/
+/* TODO
+memberaccess(
+ int member: @expr ref,
+ int kind: int ref
+);
+*/
+
+initialisers(
+ unique int init: @initialiser,
+ int var: @accessible ref,
+ unique int expr: @expr ref,
+ int location: @location_expr ref
+);
+
+braced_initialisers(
+ int init: @initialiser ref
+);
+
+/**
+ * An ancestor for the expression, for cases in which we cannot
+ * otherwise find the expression's parent.
+ */
+expr_ancestor(
+ int exp: @expr ref,
+ int ancestor: @element ref
+);
+
+exprs(
+ unique int id: @expr,
+ int kind: int ref,
+ int location: @location_expr ref
+);
+
+/*
+ case @value.category of
+ 1 = prval
+ | 2 = xval
+ | 3 = lval
+ ;
+*/
+expr_types(
+ int id: @expr ref,
+ int typeid: @type ref,
+ int value_category: int ref
+);
+
+case @expr.kind of
+ 1 = @errorexpr
+| 2 = @address_of // & AddressOfExpr
+| 3 = @reference_to // ReferenceToExpr (implicit?)
+| 4 = @indirect // * PointerDereferenceExpr
+| 5 = @ref_indirect // ReferenceDereferenceExpr (implicit?)
+// ...
+| 8 = @array_to_pointer // (???)
+| 9 = @vacuous_destructor_call // VacuousDestructorCall
+// ...
+| 11 = @assume // Microsoft
+| 12 = @parexpr
+| 13 = @arithnegexpr
+| 14 = @unaryplusexpr
+| 15 = @complementexpr
+| 16 = @notexpr
+| 17 = @conjugation // GNU ~ operator
+| 18 = @realpartexpr // GNU __real
+| 19 = @imagpartexpr // GNU __imag
+| 20 = @postincrexpr
+| 21 = @postdecrexpr
+| 22 = @preincrexpr
+| 23 = @predecrexpr
+| 24 = @conditionalexpr
+| 25 = @addexpr
+| 26 = @subexpr
+| 27 = @mulexpr
+| 28 = @divexpr
+| 29 = @remexpr
+| 30 = @jmulexpr // C99 mul imaginary
+| 31 = @jdivexpr // C99 div imaginary
+| 32 = @fjaddexpr // C99 add real + imaginary
+| 33 = @jfaddexpr // C99 add imaginary + real
+| 34 = @fjsubexpr // C99 sub real - imaginary
+| 35 = @jfsubexpr // C99 sub imaginary - real
+| 36 = @paddexpr // pointer add (pointer + int or int + pointer)
+| 37 = @psubexpr // pointer sub (pointer - integer)
+| 38 = @pdiffexpr // difference between two pointers
+| 39 = @lshiftexpr
+| 40 = @rshiftexpr
+| 41 = @andexpr
+| 42 = @orexpr
+| 43 = @xorexpr
+| 44 = @eqexpr
+| 45 = @neexpr
+| 46 = @gtexpr
+| 47 = @ltexpr
+| 48 = @geexpr
+| 49 = @leexpr
+| 50 = @minexpr // GNU minimum
+| 51 = @maxexpr // GNU maximum
+| 52 = @assignexpr
+| 53 = @assignaddexpr
+| 54 = @assignsubexpr
+| 55 = @assignmulexpr
+| 56 = @assigndivexpr
+| 57 = @assignremexpr
+| 58 = @assignlshiftexpr
+| 59 = @assignrshiftexpr
+| 60 = @assignandexpr
+| 61 = @assignorexpr
+| 62 = @assignxorexpr
+| 63 = @assignpaddexpr // assign pointer add
+| 64 = @assignpsubexpr // assign pointer sub
+| 65 = @andlogicalexpr
+| 66 = @orlogicalexpr
+| 67 = @commaexpr
+| 68 = @subscriptexpr // access to member of an array, e.g., a[5]
+// ... 69 @objc_subscriptexpr deprecated
+// ... 70 @cmdaccess deprecated
+// ...
+| 73 = @virtfunptrexpr
+| 74 = @callexpr
+// ... 75 @msgexpr_normal deprecated
+// ... 76 @msgexpr_super deprecated
+// ... 77 @atselectorexpr deprecated
+// ... 78 @atprotocolexpr deprecated
+| 79 = @vastartexpr
+| 80 = @vaargexpr
+| 81 = @vaendexpr
+| 82 = @vacopyexpr
+// ... 83 @atencodeexpr deprecated
+| 84 = @varaccess
+| 85 = @thisaccess
+// ... 86 @objc_box_expr deprecated
+| 87 = @new_expr
+| 88 = @delete_expr
+| 89 = @throw_expr
+| 90 = @condition_decl // a variable declared in a condition, e.g., if(int x = y > 2)
+| 91 = @braced_init_list
+| 92 = @type_id
+| 93 = @runtime_sizeof
+| 94 = @runtime_alignof
+| 95 = @sizeof_pack
+| 96 = @expr_stmt // GNU extension
+| 97 = @routineexpr
+| 98 = @type_operand // used to access a type in certain contexts (haven't found any examples yet....)
+| 99 = @offsetofexpr // offsetof ::= type and field
+| 100 = @hasassignexpr // __has_assign ::= type
+| 101 = @hascopyexpr // __has_copy ::= type
+| 102 = @hasnothrowassign // __has_nothrow_assign ::= type
+| 103 = @hasnothrowconstr // __has_nothrow_constructor ::= type
+| 104 = @hasnothrowcopy // __has_nothrow_copy ::= type
+| 105 = @hastrivialassign // __has_trivial_assign ::= type
+| 106 = @hastrivialconstr // __has_trivial_constructor ::= type
+| 107 = @hastrivialcopy // __has_trivial_copy ::= type
+| 108 = @hasuserdestr // __has_user_destructor ::= type
+| 109 = @hasvirtualdestr // __has_virtual_destructor ::= type
+| 110 = @isabstractexpr // __is_abstract ::= type
+| 111 = @isbaseofexpr // __is_base_of ::= type type
+| 112 = @isclassexpr // __is_class ::= type
+| 113 = @isconvtoexpr // __is_convertible_to ::= type type
+| 114 = @isemptyexpr // __is_empty ::= type
+| 115 = @isenumexpr // __is_enum ::= type
+| 116 = @ispodexpr // __is_pod ::= type
+| 117 = @ispolyexpr // __is_polymorphic ::= type
+| 118 = @isunionexpr // __is_union ::= type
+| 119 = @typescompexpr // GNU __builtin_types_compatible ::= type type
+| 120 = @intaddrexpr // frontend internal builtin, used to implement offsetof
+// ...
+| 122 = @hastrivialdestructor // __has_trivial_destructor ::= type
+| 123 = @literal
+| 124 = @uuidof
+| 127 = @aggregateliteral
+| 128 = @delete_array_expr
+| 129 = @new_array_expr
+// ... 130 @objc_array_literal deprecated
+// ... 131 @objc_dictionary_literal deprecated
+| 132 = @foldexpr
+// ...
+| 200 = @ctordirectinit
+| 201 = @ctorvirtualinit
+| 202 = @ctorfieldinit
+| 203 = @ctordelegatinginit
+| 204 = @dtordirectdestruct
+| 205 = @dtorvirtualdestruct
+| 206 = @dtorfielddestruct
+// ...
+| 210 = @static_cast
+| 211 = @reinterpret_cast
+| 212 = @const_cast
+| 213 = @dynamic_cast
+| 214 = @c_style_cast
+| 215 = @lambdaexpr
+| 216 = @param_ref
+| 217 = @noopexpr
+// ...
+| 294 = @istriviallyconstructibleexpr
+| 295 = @isdestructibleexpr
+| 296 = @isnothrowdestructibleexpr
+| 297 = @istriviallydestructibleexpr
+| 298 = @istriviallyassignableexpr
+| 299 = @isnothrowassignableexpr
+| 300 = @istrivialexpr
+| 301 = @isstandardlayoutexpr
+| 302 = @istriviallycopyableexpr
+| 303 = @isliteraltypeexpr
+| 304 = @hastrivialmoveconstructorexpr
+| 305 = @hastrivialmoveassignexpr
+| 306 = @hasnothrowmoveassignexpr
+| 307 = @isconstructibleexpr
+| 308 = @isnothrowconstructibleexpr
+| 309 = @hasfinalizerexpr
+| 310 = @isdelegateexpr
+| 311 = @isinterfaceclassexpr
+| 312 = @isrefarrayexpr
+| 313 = @isrefclassexpr
+| 314 = @issealedexpr
+| 315 = @issimplevalueclassexpr
+| 316 = @isvalueclassexpr
+| 317 = @isfinalexpr
+| 319 = @noexceptexpr
+| 320 = @builtinshufflevector
+| 321 = @builtinchooseexpr
+| 322 = @builtinaddressof
+| 323 = @vec_fill
+| 324 = @builtinconvertvector
+| 325 = @builtincomplex
+| 326 = @spaceshipexpr
+| 327 = @co_await
+| 328 = @co_yield
+| 329 = @temp_init
+| 330 = @isassignable
+| 331 = @isaggregate
+| 332 = @hasuniqueobjectrepresentations
+| 333 = @builtinbitcast
+| 334 = @builtinshuffle
+| 335 = @blockassignexpr
+| 336 = @issame
+| 337 = @isfunction
+| 338 = @islayoutcompatible
+| 339 = @ispointerinterconvertiblebaseof
+| 340 = @isarray
+| 341 = @arrayrank
+| 342 = @arrayextent
+| 343 = @isarithmetic
+| 344 = @iscompletetype
+| 345 = @iscompound
+| 346 = @isconst
+| 347 = @isfloatingpoint
+| 348 = @isfundamental
+| 349 = @isintegral
+| 350 = @islvaluereference
+| 351 = @ismemberfunctionpointer
+| 352 = @ismemberobjectpointer
+| 353 = @ismemberpointer
+| 354 = @isobject
+| 355 = @ispointer
+| 356 = @isreference
+| 357 = @isrvaluereference
+| 358 = @isscalar
+| 359 = @issigned
+| 360 = @isunsigned
+| 361 = @isvoid
+| 362 = @isvolatile
+;
+
+@var_args_expr = @vastartexpr
+ | @vaendexpr
+ | @vaargexpr
+ | @vacopyexpr
+ ;
+
+@builtin_op = @var_args_expr
+ | @noopexpr
+ | @offsetofexpr
+ | @intaddrexpr
+ | @hasassignexpr
+ | @hascopyexpr
+ | @hasnothrowassign
+ | @hasnothrowconstr
+ | @hasnothrowcopy
+ | @hastrivialassign
+ | @hastrivialconstr
+ | @hastrivialcopy
+ | @hastrivialdestructor
+ | @hasuserdestr
+ | @hasvirtualdestr
+ | @isabstractexpr
+ | @isbaseofexpr
+ | @isclassexpr
+ | @isconvtoexpr
+ | @isemptyexpr
+ | @isenumexpr
+ | @ispodexpr
+ | @ispolyexpr
+ | @isunionexpr
+ | @typescompexpr
+ | @builtinshufflevector
+ | @builtinconvertvector
+ | @builtinaddressof
+ | @istriviallyconstructibleexpr
+ | @isdestructibleexpr
+ | @isnothrowdestructibleexpr
+ | @istriviallydestructibleexpr
+ | @istriviallyassignableexpr
+ | @isnothrowassignableexpr
+ | @istrivialexpr
+ | @isstandardlayoutexpr
+ | @istriviallycopyableexpr
+ | @isliteraltypeexpr
+ | @hastrivialmoveconstructorexpr
+ | @hastrivialmoveassignexpr
+ | @hasnothrowmoveassignexpr
+ | @isconstructibleexpr
+ | @isnothrowconstructibleexpr
+ | @hasfinalizerexpr
+ | @isdelegateexpr
+ | @isinterfaceclassexpr
+ | @isrefarrayexpr
+ | @isrefclassexpr
+ | @issealedexpr
+ | @issimplevalueclassexpr
+ | @isvalueclassexpr
+ | @isfinalexpr
+ | @builtinchooseexpr
+ | @builtincomplex
+ | @isassignable
+ | @isaggregate
+ | @hasuniqueobjectrepresentations
+ | @builtinbitcast
+ | @builtinshuffle
+ | @issame
+ | @isfunction
+ | @islayoutcompatible
+ | @ispointerinterconvertiblebaseof
+ | @isarray
+ | @arrayrank
+ | @arrayextent
+ | @isarithmetic
+ | @iscompletetype
+ | @iscompound
+ | @isconst
+ | @isfloatingpoint
+ | @isfundamental
+ | @isintegral
+ | @islvaluereference
+ | @ismemberfunctionpointer
+ | @ismemberobjectpointer
+ | @ismemberpointer
+ | @isobject
+ | @ispointer
+ | @isreference
+ | @isrvaluereference
+ | @isscalar
+ | @issigned
+ | @isunsigned
+ | @isvoid
+ | @isvolatile
+ ;
+
+new_allocated_type(
+ unique int expr: @new_expr ref,
+ int type_id: @type ref
+);
+
+new_array_allocated_type(
+ unique int expr: @new_array_expr ref,
+ int type_id: @type ref
+);
+
+/**
+ * The field being initialized by an initializer expression within an aggregate
+ * initializer for a class/struct/union. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_field_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int field: @membervariable ref,
+ int position: int ref
+);
+
+/**
+ * The index of the element being initialized by an initializer expression
+ * within an aggregate initializer for an array. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_array_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int element_index: int ref,
+ int position: int ref
+);
+
+@ctorinit = @ctordirectinit
+ | @ctorvirtualinit
+ | @ctorfieldinit
+ | @ctordelegatinginit;
+@dtordestruct = @dtordirectdestruct
+ | @dtorvirtualdestruct
+ | @dtorfielddestruct;
+
+
+condition_decl_bind(
+ unique int expr: @condition_decl ref,
+ unique int decl: @declaration ref
+);
+
+typeid_bind(
+ unique int expr: @type_id ref,
+ int type_id: @type ref
+);
+
+uuidof_bind(
+ unique int expr: @uuidof ref,
+ int type_id: @type ref
+);
+
+@runtime_sizeof_or_alignof = @runtime_sizeof | @runtime_alignof;
+
+sizeof_bind(
+ unique int expr: @runtime_sizeof_or_alignof ref,
+ int type_id: @type ref
+);
+
+code_block(
+ unique int block: @literal ref,
+ unique int routine: @function ref
+);
+
+lambdas(
+ unique int expr: @lambdaexpr ref,
+ string default_capture: string ref,
+ boolean has_explicit_return_type: boolean ref
+);
+
+lambda_capture(
+ unique int id: @lambdacapture,
+ int lambda: @lambdaexpr ref,
+ int index: int ref,
+ int field: @membervariable ref,
+ boolean captured_by_reference: boolean ref,
+ boolean is_implicit: boolean ref,
+ int location: @location_default ref
+);
+
+@funbindexpr = @routineexpr
+ | @new_expr
+ | @delete_expr
+ | @delete_array_expr
+ | @ctordirectinit
+ | @ctorvirtualinit
+ | @ctordelegatinginit
+ | @dtordirectdestruct
+ | @dtorvirtualdestruct;
+
+@varbindexpr = @varaccess | @ctorfieldinit | @dtorfielddestruct;
+@addressable = @function | @variable ;
+@accessible = @addressable | @enumconstant ;
+
+@access = @varaccess | @routineexpr ;
+
+fold(
+ int expr: @foldexpr ref,
+ string operator: string ref,
+ boolean is_left_fold: boolean ref
+);
+
+stmts(
+ unique int id: @stmt,
+ int kind: int ref,
+ int location: @location_stmt ref
+);
+
+case @stmt.kind of
+ 1 = @stmt_expr
+| 2 = @stmt_if
+| 3 = @stmt_while
+| 4 = @stmt_goto
+| 5 = @stmt_label
+| 6 = @stmt_return
+| 7 = @stmt_block
+| 8 = @stmt_end_test_while // do { ... } while ( ... )
+| 9 = @stmt_for
+| 10 = @stmt_switch_case
+| 11 = @stmt_switch
+| 13 = @stmt_asm // "asm" statement or the body of an asm function
+| 15 = @stmt_try_block
+| 16 = @stmt_microsoft_try // Microsoft
+| 17 = @stmt_decl
+| 18 = @stmt_set_vla_size // C99
+| 19 = @stmt_vla_decl // C99
+| 25 = @stmt_assigned_goto // GNU
+| 26 = @stmt_empty
+| 27 = @stmt_continue
+| 28 = @stmt_break
+| 29 = @stmt_range_based_for // C++11
+// ... 30 @stmt_at_autoreleasepool_block deprecated
+// ... 31 @stmt_objc_for_in deprecated
+// ... 32 @stmt_at_synchronized deprecated
+| 33 = @stmt_handler
+// ... 34 @stmt_finally_end deprecated
+| 35 = @stmt_constexpr_if
+| 37 = @stmt_co_return
+;
+
+type_vla(
+ int type_id: @type ref,
+ int decl: @stmt_vla_decl ref
+);
+
+variable_vla(
+ int var: @variable ref,
+ int decl: @stmt_vla_decl ref
+);
+
+if_initialization(
+ unique int if_stmt: @stmt_if ref,
+ int init_id: @stmt ref
+);
+
+if_then(
+ unique int if_stmt: @stmt_if ref,
+ int then_id: @stmt ref
+);
+
+if_else(
+ unique int if_stmt: @stmt_if ref,
+ int else_id: @stmt ref
+);
+
+constexpr_if_initialization(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int init_id: @stmt ref
+);
+
+constexpr_if_then(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int then_id: @stmt ref
+);
+
+constexpr_if_else(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int else_id: @stmt ref
+);
+
+while_body(
+ unique int while_stmt: @stmt_while ref,
+ int body_id: @stmt ref
+);
+
+do_body(
+ unique int do_stmt: @stmt_end_test_while ref,
+ int body_id: @stmt ref
+);
+
+switch_initialization(
+ unique int switch_stmt: @stmt_switch ref,
+ int init_id: @stmt ref
+);
+
+#keyset[switch_stmt, index]
+switch_case(
+ int switch_stmt: @stmt_switch ref,
+ int index: int ref,
+ int case_id: @stmt_switch_case ref
+);
+
+switch_body(
+ unique int switch_stmt: @stmt_switch ref,
+ int body_id: @stmt ref
+);
+
+for_initialization(
+ unique int for_stmt: @stmt_for ref,
+ int init_id: @stmt ref
+);
+
+for_condition(
+ unique int for_stmt: @stmt_for ref,
+ int condition_id: @expr ref
+);
+
+for_update(
+ unique int for_stmt: @stmt_for ref,
+ int update_id: @expr ref
+);
+
+for_body(
+ unique int for_stmt: @stmt_for ref,
+ int body_id: @stmt ref
+);
+
+@stmtparent = @stmt | @expr_stmt ;
+stmtparents(
+ unique int id: @stmt ref,
+ int index: int ref,
+ int parent: @stmtparent ref
+);
+
+ishandler(unique int block: @stmt_block ref);
+
+@cfgnode = @stmt | @expr | @function | @initialiser ;
+
+stmt_decl_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl: @declaration ref
+);
+
+stmt_decl_entry_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl_entry: @element ref
+);
+
+@functionorblock = @function | @stmt_block;
+
+blockscope(
+ unique int block: @stmt_block ref,
+ int enclosing: @functionorblock ref
+);
+
+@jump = @stmt_goto | @stmt_break | @stmt_continue;
+
+@jumporlabel = @jump | @stmt_label | @literal;
+
+jumpinfo(
+ unique int id: @jumporlabel ref,
+ string str: string ref,
+ int target: @stmt ref
+);
+
+preprocdirects(
+ unique int id: @preprocdirect,
+ int kind: int ref,
+ int location: @location_default ref
+);
+case @preprocdirect.kind of
+ 0 = @ppd_if
+| 1 = @ppd_ifdef
+| 2 = @ppd_ifndef
+| 3 = @ppd_elif
+| 4 = @ppd_else
+| 5 = @ppd_endif
+| 6 = @ppd_plain_include
+| 7 = @ppd_define
+| 8 = @ppd_undef
+| 9 = @ppd_line
+| 10 = @ppd_error
+| 11 = @ppd_pragma
+| 12 = @ppd_objc_import
+| 13 = @ppd_include_next
+| 18 = @ppd_warning
+;
+
+@ppd_include = @ppd_plain_include | @ppd_objc_import | @ppd_include_next;
+
+@ppd_branch = @ppd_if | @ppd_ifdef | @ppd_ifndef | @ppd_elif;
+
+preprocpair(
+ int begin : @ppd_branch ref,
+ int elseelifend : @preprocdirect ref
+);
+
+preproctrue(int branch : @ppd_branch ref);
+preprocfalse(int branch : @ppd_branch ref);
+
+preproctext(
+ unique int id: @preprocdirect ref,
+ string head: string ref,
+ string body: string ref
+);
+
+includes(
+ unique int id: @ppd_include ref,
+ int included: @file ref
+);
+
+link_targets(
+ unique int id: @link_target,
+ int binary: @file ref
+);
+
+link_parent(
+ int element : @element ref,
+ int link_target : @link_target ref
+);
+
+/* XML Files */
+
+xmlEncoding(unique int id: @file ref, string encoding: string ref);
+
+xmlDTDs(
+ unique int id: @xmldtd,
+ string root: string ref,
+ string publicId: string ref,
+ string systemId: string ref,
+ int fileid: @file ref
+);
+
+xmlElements(
+ unique int id: @xmlelement,
+ string name: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlAttrs(
+ unique int id: @xmlattribute,
+ int elementid: @xmlelement ref,
+ string name: string ref,
+ string value: string ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlNs(
+ int id: @xmlnamespace,
+ string prefixName: string ref,
+ string URI: string ref,
+ int fileid: @file ref
+);
+
+xmlHasNs(
+ int elementId: @xmlnamespaceable ref,
+ int nsId: @xmlnamespace ref,
+ int fileid: @file ref
+);
+
+xmlComments(
+ unique int id: @xmlcomment,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int fileid: @file ref
+);
+
+xmlChars(
+ unique int id: @xmlcharacters,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int isCDATA: int ref,
+ int fileid: @file ref
+);
+
+@xmlparent = @file | @xmlelement;
+@xmlnamespaceable = @xmlelement | @xmlattribute;
+
+xmllocations(
+ int xmlElement: @xmllocatable ref,
+ int location: @location_default ref
+);
+
+@xmllocatable = @xmlcharacters
+ | @xmlelement
+ | @xmlcomment
+ | @xmlattribute
+ | @xmldtd
+ | @file
+ | @xmlnamespace;
diff --git a/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/semmlecode.cpp.dbscheme b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/semmlecode.cpp.dbscheme
new file mode 100644
index 00000000000..8cba93a4418
--- /dev/null
+++ b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/semmlecode.cpp.dbscheme
@@ -0,0 +1,2231 @@
+
+/**
+ * An invocation of the compiler. Note that more than one file may be
+ * compiled per invocation. For example, this command compiles three
+ * source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * The `id` simply identifies the invocation, while `cwd` is the working
+ * directory from which the compiler was invoked.
+ */
+compilations(
+ /**
+ * An invocation of the compiler. Note that more than one file may
+ * be compiled per invocation. For example, this command compiles
+ * three source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ */
+ unique int id : @compilation,
+ string cwd : string ref
+);
+
+/**
+ * The arguments that were passed to the extractor for a compiler
+ * invocation. If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then typically there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | *path to extractor*
+ * 1 | `--mimic`
+ * 2 | `/usr/bin/gcc`
+ * 3 | `-c`
+ * 4 | f1.c
+ * 5 | f2.c
+ * 6 | f3.c
+ */
+#keyset[id, num]
+compilation_args(
+ int id : @compilation ref,
+ int num : int ref,
+ string arg : string ref
+);
+
+/**
+ * The source files that are compiled by a compiler invocation.
+ * If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | f1.c
+ * 1 | f2.c
+ * 2 | f3.c
+ *
+ * Note that even if those files `#include` headers, those headers
+ * do not appear as rows.
+ */
+#keyset[id, num]
+compilation_compiling_files(
+ int id : @compilation ref,
+ int num : int ref,
+ int file : @file ref
+);
+
+/**
+ * The time taken by the extractor for a compiler invocation.
+ *
+ * For each file `num`, there will be rows for
+ *
+ * kind | seconds
+ * ---- | ---
+ * 1 | CPU seconds used by the extractor frontend
+ * 2 | Elapsed seconds during the extractor frontend
+ * 3 | CPU seconds used by the extractor backend
+ * 4 | Elapsed seconds during the extractor backend
+ */
+#keyset[id, num, kind]
+compilation_time(
+ int id : @compilation ref,
+ int num : int ref,
+ /* kind:
+ 1 = frontend_cpu_seconds
+ 2 = frontend_elapsed_seconds
+ 3 = extractor_cpu_seconds
+ 4 = extractor_elapsed_seconds
+ */
+ int kind : int ref,
+ float seconds : float ref
+);
+
+/**
+ * An error or warning generated by the extractor.
+ * The diagnostic message `diagnostic` was generated during compiler
+ * invocation `compilation`, and is the `file_number_diagnostic_number`th
+ * message generated while extracting the `file_number`th file of that
+ * invocation.
+ */
+#keyset[compilation, file_number, file_number_diagnostic_number]
+diagnostic_for(
+ int diagnostic : @diagnostic ref,
+ int compilation : @compilation ref,
+ int file_number : int ref,
+ int file_number_diagnostic_number : int ref
+);
+
+/**
+ * If extraction was successful, then `cpu_seconds` and
+ * `elapsed_seconds` are the CPU time and elapsed time (respectively)
+ * that extraction took for compiler invocation `id`.
+ */
+compilation_finished(
+ unique int id : @compilation ref,
+ float cpu_seconds : float ref,
+ float elapsed_seconds : float ref
+);
+
+
+/**
+ * External data, loaded from CSV files during snapshot creation. See
+ * [Tutorial: Incorporating external data](https://help.semmle.com/wiki/display/SD/Tutorial%3A+Incorporating+external+data)
+ * for more information.
+ */
+externalData(
+ int id : @externalDataElement,
+ string path : string ref,
+ int column: int ref,
+ string value : string ref
+);
+
+/**
+ * The source location of the snapshot.
+ */
+sourceLocationPrefix(string prefix : string ref);
+
+/**
+ * Information about packages that provide code used during compilation.
+ * The `id` is just a unique identifier.
+ * The `namespace` is typically the name of the package manager that
+ * provided the package (e.g. "dpkg" or "yum").
+ * The `package_name` is the name of the package, and `version` is its
+ * version (as a string).
+ */
+external_packages(
+ unique int id: @external_package,
+ string namespace : string ref,
+ string package_name : string ref,
+ string version : string ref
+);
+
+/**
+ * Holds if File `fileid` was provided by package `package`.
+ */
+header_to_external_package(
+ int fileid : @file ref,
+ int package : @external_package ref
+);
+
+/*
+ * Version history
+ */
+
+svnentries(
+ unique int id : @svnentry,
+ string revision : string ref,
+ string author : string ref,
+ date revisionDate : date ref,
+ int changeSize : int ref
+)
+
+svnaffectedfiles(
+ int id : @svnentry ref,
+ int file : @file ref,
+ string action : string ref
+)
+
+svnentrymsg(
+ unique int id : @svnentry ref,
+ string message : string ref
+)
+
+svnchurn(
+ int commit : @svnentry ref,
+ int file : @file ref,
+ int addedLines : int ref,
+ int deletedLines : int ref
+)
+
+/*
+ * C++ dbscheme
+ */
+
+extractor_version(
+ string codeql_version: string ref,
+ string frontend_version: string ref
+)
+
+@location = @location_stmt | @location_expr | @location_default ;
+
+/**
+ * The location of an element that is not an expression or a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_default(
+ /** The location of an element that is not an expression or a statement. */
+ unique int id: @location_default,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_stmt(
+ /** The location of a statement. */
+ unique int id: @location_stmt,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of an expression.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_expr(
+ /** The location of an expression. */
+ unique int id: @location_expr,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/** An element for which line-count information is available. */
+@sourceline = @file | @function | @variable | @enumconstant | @xmllocatable;
+
+numlines(
+ int element_id: @sourceline ref,
+ int num_lines: int ref,
+ int num_code: int ref,
+ int num_comment: int ref
+);
+
+diagnostics(
+ unique int id: @diagnostic,
+ int severity: int ref,
+ string error_tag: string ref,
+ string error_message: string ref,
+ string full_error_message: string ref,
+ int location: @location_default ref
+);
+
+files(
+ unique int id: @file,
+ string name: string ref
+);
+
+folders(
+ unique int id: @folder,
+ string name: string ref
+);
+
+@container = @folder | @file
+
+containerparent(
+ int parent: @container ref,
+ unique int child: @container ref
+);
+
+fileannotations(
+ int id: @file ref,
+ int kind: int ref,
+ string name: string ref,
+ string value: string ref
+);
+
+inmacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+affectedbymacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+case @macroinvocation.kind of
+ 1 = @macro_expansion
+| 2 = @other_macro_reference
+;
+
+macroinvocations(
+ unique int id: @macroinvocation,
+ int macro_id: @ppd_define ref,
+ int location: @location_default ref,
+ int kind: int ref
+);
+
+macroparent(
+ unique int id: @macroinvocation ref,
+ int parent_id: @macroinvocation ref
+);
+
+// a macroinvocation may be part of another location
+// the way to find a constant expression that uses a macro
+// is thus to find a constant expression that has a location
+// to which a macro invocation is bound
+macrolocationbind(
+ int id: @macroinvocation ref,
+ int location: @location ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_unexpanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_expanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+/*
+case @function.kind of
+ 1 = @normal_function
+| 2 = @constructor
+| 3 = @destructor
+| 4 = @conversion_function
+| 5 = @operator
+| 6 = @builtin_function // GCC built-in functions, e.g. __builtin___memcpy_chk
+;
+*/
+
+functions(
+ unique int id: @function,
+ string name: string ref,
+ int kind: int ref
+);
+
+function_entry_point(
+ int id: @function ref,
+ unique int entry_point: @stmt ref
+);
+
+function_return_type(
+ int id: @function ref,
+ int return_type: @type ref
+);
+
+/**
+ * If `function` is a coroutine, then this gives the `std::experimental::resumable_traits`
+ * instance associated with it, and the variables representing the `handle` and `promise`
+ * for it.
+ */
+coroutine(
+ unique int function: @function ref,
+ int traits: @type ref,
+ int handle: @variable ref,
+ int promise: @variable ref
+);
+
+/** The `new` function used for allocating the coroutine state, if any. */
+coroutine_new(
+ unique int function: @function ref,
+ int new: @function ref
+);
+
+/** The `delete` function used for deallocating the coroutine state, if any. */
+coroutine_delete(
+ unique int function: @function ref,
+ int delete: @function ref
+);
+
+purefunctions(unique int id: @function ref);
+
+function_deleted(unique int id: @function ref);
+
+function_defaulted(unique int id: @function ref);
+
+member_function_this_type(
+ unique int id: @function ref,
+ int this_type: @type ref
+);
+
+#keyset[id, type_id]
+fun_decls(
+ int id: @fun_decl,
+ int function: @function ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+fun_def(unique int id: @fun_decl ref);
+fun_specialized(unique int id: @fun_decl ref);
+fun_implicit(unique int id: @fun_decl ref);
+fun_decl_specifiers(
+ int id: @fun_decl ref,
+ string name: string ref
+)
+#keyset[fun_decl, index]
+fun_decl_throws(
+ int fun_decl: @fun_decl ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+/* an empty throw specification is different from none */
+fun_decl_empty_throws(unique int fun_decl: @fun_decl ref);
+fun_decl_noexcept(
+ int fun_decl: @fun_decl ref,
+ int constant: @expr ref
+);
+fun_decl_empty_noexcept(int fun_decl: @fun_decl ref);
+fun_decl_typedef_type(
+ unique int fun_decl: @fun_decl ref,
+ int typedeftype_id: @usertype ref
+);
+
+param_decl_bind(
+ unique int id: @var_decl ref,
+ int index: int ref,
+ int fun_decl: @fun_decl ref
+);
+
+#keyset[id, type_id]
+var_decls(
+ int id: @var_decl,
+ int variable: @variable ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+var_def(unique int id: @var_decl ref);
+var_decl_specifiers(
+ int id: @var_decl ref,
+ string name: string ref
+)
+is_structured_binding(unique int id: @variable ref);
+
+type_decls(
+ unique int id: @type_decl,
+ int type_id: @type ref,
+ int location: @location_default ref
+);
+type_def(unique int id: @type_decl ref);
+type_decl_top(
+ unique int type_decl: @type_decl ref
+);
+
+namespace_decls(
+ unique int id: @namespace_decl,
+ int namespace_id: @namespace ref,
+ int location: @location_default ref,
+ int bodylocation: @location_default ref
+);
+
+usings(
+ unique int id: @using,
+ int element_id: @element ref,
+ int location: @location_default ref
+);
+
+/** The element which contains the `using` declaration. */
+using_container(
+ int parent: @element ref,
+ int child: @using ref
+);
+
+static_asserts(
+ unique int id: @static_assert,
+ int condition : @expr ref,
+ string message : string ref,
+ int location: @location_default ref,
+ int enclosing : @element ref
+);
+
+// each function has an ordered list of parameters
+#keyset[id, type_id]
+#keyset[function, index, type_id]
+params(
+ int id: @parameter,
+ int function: @functionorblock ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+overrides(
+ int new: @function ref,
+ int old: @function ref
+);
+
+#keyset[id, type_id]
+membervariables(
+ int id: @membervariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+globalvariables(
+ int id: @globalvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+localvariables(
+ int id: @localvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+autoderivation(
+ unique int var: @variable ref,
+ int derivation_type: @type ref
+);
+
+orphaned_variables(
+ int var: @localvariable ref,
+ int function: @function ref
+)
+
+enumconstants(
+ unique int id: @enumconstant,
+ int parent: @usertype ref,
+ int index: int ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+
+@variable = @localscopevariable | @globalvariable | @membervariable;
+
+@localscopevariable = @localvariable | @parameter;
+
+/**
+ * Built-in types are the fundamental types, e.g., integral, floating, and void.
+ */
+case @builtintype.kind of
+ 1 = @errortype
+| 2 = @unknowntype
+| 3 = @void
+| 4 = @boolean
+| 5 = @char
+| 6 = @unsigned_char
+| 7 = @signed_char
+| 8 = @short
+| 9 = @unsigned_short
+| 10 = @signed_short
+| 11 = @int
+| 12 = @unsigned_int
+| 13 = @signed_int
+| 14 = @long
+| 15 = @unsigned_long
+| 16 = @signed_long
+| 17 = @long_long
+| 18 = @unsigned_long_long
+| 19 = @signed_long_long
+// ... 20 Microsoft-specific __int8
+// ... 21 Microsoft-specific __int16
+// ... 22 Microsoft-specific __int32
+// ... 23 Microsoft-specific __int64
+| 24 = @float
+| 25 = @double
+| 26 = @long_double
+| 27 = @complex_float // C99-specific _Complex float
+| 28 = @complex_double // C99-specific _Complex double
+| 29 = @complex_long_double // C99-specific _Complex long double
+| 30 = @imaginary_float // C99-specific _Imaginary float
+| 31 = @imaginary_double // C99-specific _Imaginary double
+| 32 = @imaginary_long_double // C99-specific _Imaginary long double
+| 33 = @wchar_t // Microsoft-specific
+| 34 = @decltype_nullptr // C++11
+| 35 = @int128 // __int128
+| 36 = @unsigned_int128 // unsigned __int128
+| 37 = @signed_int128 // signed __int128
+| 38 = @float128 // __float128
+| 39 = @complex_float128 // _Complex __float128
+| 40 = @decimal32 // _Decimal32
+| 41 = @decimal64 // _Decimal64
+| 42 = @decimal128 // _Decimal128
+| 43 = @char16_t
+| 44 = @char32_t
+| 45 = @std_float32 // _Float32
+| 46 = @float32x // _Float32x
+| 47 = @std_float64 // _Float64
+| 48 = @float64x // _Float64x
+| 49 = @std_float128 // _Float128
+// ... 50 _Float128x
+| 51 = @char8_t
+| 52 = @float16 // _Float16
+| 53 = @complex_float16 // _Complex _Float16
+| 54 = @fp16 // __fp16
+| 55 = @std_bfloat16 // __bf16
+| 56 = @std_float16 // std::float16_t
+| 57 = @complex_std_float32 // _Complex _Float32
+| 58 = @complex_float32x // _Complex _Float32x
+| 59 = @complex_std_float64 // _Complex _Float64
+| 60 = @complex_float64x // _Complex _Float64x
+| 61 = @complex_std_float128 // _Complex _Float128
+;
+
+builtintypes(
+ unique int id: @builtintype,
+ string name: string ref,
+ int kind: int ref,
+ int size: int ref,
+ int sign: int ref,
+ int alignment: int ref
+);
+
+/**
+ * Derived types are types that are directly derived from existing types and
+ * point to, refer to, transform type data to return a new type.
+ */
+case @derivedtype.kind of
+ 1 = @pointer
+| 2 = @reference
+| 3 = @type_with_specifiers
+| 4 = @array
+| 5 = @gnu_vector
+| 6 = @routineptr
+| 7 = @routinereference
+| 8 = @rvalue_reference // C++11
+// ... 9 type_conforming_to_protocols deprecated
+| 10 = @block
+;
+
+derivedtypes(
+ unique int id: @derivedtype,
+ string name: string ref,
+ int kind: int ref,
+ int type_id: @type ref
+);
+
+pointerishsize(unique int id: @derivedtype ref,
+ int size: int ref,
+ int alignment: int ref);
+
+arraysizes(
+ unique int id: @derivedtype ref,
+ int num_elements: int ref,
+ int bytesize: int ref,
+ int alignment: int ref
+);
+
+typedefbase(
+ unique int id: @usertype ref,
+ int type_id: @type ref
+);
+
+/**
+ * An instance of the C++11 `decltype` operator. For example:
+ * ```
+ * int a;
+ * decltype(1+a) b;
+ * ```
+ * Here `expr` is `1+a`.
+ *
+ * Sometimes an additional pair of parentheses around the expression
+ * would change the semantics of this decltype, e.g.
+ * ```
+ * struct A { double x; };
+ * const A* a = new A();
+ * decltype( a->x ); // type is double
+ * decltype((a->x)); // type is const double&
+ * ```
+ * (Please consult the C++11 standard for more details).
+ * `parentheses_would_change_meaning` is `true` iff that is the case.
+ */
+#keyset[id, expr]
+decltypes(
+ int id: @decltype,
+ int expr: @expr ref,
+ int base_type: @type ref,
+ boolean parentheses_would_change_meaning: boolean ref
+);
+
+/*
+case @usertype.kind of
+ 1 = @struct
+| 2 = @class
+| 3 = @union
+| 4 = @enum
+| 5 = @typedef // classic C: typedef typedef type name
+| 6 = @template
+| 7 = @template_parameter
+| 8 = @template_template_parameter
+| 9 = @proxy_class // a proxy class associated with a template parameter
+// ... 10 objc_class deprecated
+// ... 11 objc_protocol deprecated
+// ... 12 objc_category deprecated
+| 13 = @scoped_enum
+| 14 = @using_alias // a using name = type style typedef
+;
+*/
+
+usertypes(
+ unique int id: @usertype,
+ string name: string ref,
+ int kind: int ref
+);
+
+usertypesize(
+ unique int id: @usertype ref,
+ int size: int ref,
+ int alignment: int ref
+);
+
+usertype_final(unique int id: @usertype ref);
+
+usertype_uuid(
+ unique int id: @usertype ref,
+ string uuid: string ref
+);
+
+mangled_name(
+ unique int id: @declaration ref,
+ int mangled_name : @mangledname
+);
+
+is_pod_class(unique int id: @usertype ref);
+is_standard_layout_class(unique int id: @usertype ref);
+
+is_complete(unique int id: @usertype ref);
+
+is_class_template(unique int id: @usertype ref);
+class_instantiation(
+ int to: @usertype ref,
+ int from: @usertype ref
+);
+class_template_argument(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+class_template_argument_value(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_proxy_class_for(
+ unique int id: @usertype ref,
+ unique int templ_param_id: @usertype ref
+);
+
+type_mentions(
+ unique int id: @type_mention,
+ int type_id: @type ref,
+ int location: @location ref,
+ // a_symbol_reference_kind from the frontend.
+ int kind: int ref
+);
+
+is_function_template(unique int id: @function ref);
+function_instantiation(
+ unique int to: @function ref,
+ int from: @function ref
+);
+function_template_argument(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+function_template_argument_value(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_variable_template(unique int id: @variable ref);
+variable_instantiation(
+ unique int to: @variable ref,
+ int from: @variable ref
+);
+variable_template_argument(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+variable_template_argument_value(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+/*
+ Fixed point types
+ precision(1) = short, precision(2) = default, precision(3) = long
+ is_unsigned(1) = unsigned is_unsigned(2) = signed
+ is_fract_type(1) = declared with _Fract
+ saturating(1) = declared with _Sat
+*/
+/* TODO
+fixedpointtypes(
+ unique int id: @fixedpointtype,
+ int precision: int ref,
+ int is_unsigned: int ref,
+ int is_fract_type: int ref,
+ int saturating: int ref);
+*/
+
+routinetypes(
+ unique int id: @routinetype,
+ int return_type: @type ref
+);
+
+routinetypeargs(
+ int routine: @routinetype ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+ptrtomembers(
+ unique int id: @ptrtomember,
+ int type_id: @type ref,
+ int class_id: @type ref
+);
+
+/*
+ specifiers for types, functions, and variables
+
+ "public",
+ "protected",
+ "private",
+
+ "const",
+ "volatile",
+ "static",
+
+ "pure",
+ "virtual",
+ "sealed", // Microsoft
+ "__interface", // Microsoft
+ "inline",
+ "explicit",
+
+ "near", // near far extension
+ "far", // near far extension
+ "__ptr32", // Microsoft
+ "__ptr64", // Microsoft
+ "__sptr", // Microsoft
+ "__uptr", // Microsoft
+ "dllimport", // Microsoft
+ "dllexport", // Microsoft
+ "thread", // Microsoft
+ "naked", // Microsoft
+ "microsoft_inline", // Microsoft
+ "forceinline", // Microsoft
+ "selectany", // Microsoft
+ "nothrow", // Microsoft
+ "novtable", // Microsoft
+ "noreturn", // Microsoft
+ "noinline", // Microsoft
+ "noalias", // Microsoft
+ "restrict", // Microsoft
+*/
+
+specifiers(
+ unique int id: @specifier,
+ unique string str: string ref
+);
+
+typespecifiers(
+ int type_id: @type ref,
+ int spec_id: @specifier ref
+);
+
+funspecifiers(
+ int func_id: @function ref,
+ int spec_id: @specifier ref
+);
+
+varspecifiers(
+ int var_id: @accessible ref,
+ int spec_id: @specifier ref
+);
+
+attributes(
+ unique int id: @attribute,
+ int kind: int ref,
+ string name: string ref,
+ string name_space: string ref,
+ int location: @location_default ref
+);
+
+case @attribute.kind of
+ 0 = @gnuattribute
+| 1 = @stdattribute
+| 2 = @declspec
+| 3 = @msattribute
+| 4 = @alignas
+// ... 5 @objc_propertyattribute deprecated
+;
+
+attribute_args(
+ unique int id: @attribute_arg,
+ int kind: int ref,
+ int attribute: @attribute ref,
+ int index: int ref,
+ int location: @location_default ref
+);
+
+case @attribute_arg.kind of
+ 0 = @attribute_arg_empty
+| 1 = @attribute_arg_token
+| 2 = @attribute_arg_constant
+| 3 = @attribute_arg_type
+| 4 = @attribute_arg_constant_expr
+;
+
+attribute_arg_value(
+ unique int arg: @attribute_arg ref,
+ string value: string ref
+);
+attribute_arg_type(
+ unique int arg: @attribute_arg ref,
+ int type_id: @type ref
+);
+attribute_arg_constant(
+ unique int arg: @attribute_arg ref,
+ int constant: @expr ref
+)
+attribute_arg_name(
+ unique int arg: @attribute_arg ref,
+ string name: string ref
+);
+
+typeattributes(
+ int type_id: @type ref,
+ int spec_id: @attribute ref
+);
+
+funcattributes(
+ int func_id: @function ref,
+ int spec_id: @attribute ref
+);
+
+varattributes(
+ int var_id: @accessible ref,
+ int spec_id: @attribute ref
+);
+
+stmtattributes(
+ int stmt_id: @stmt ref,
+ int spec_id: @attribute ref
+);
+
+@type = @builtintype
+ | @derivedtype
+ | @usertype
+ /* TODO | @fixedpointtype */
+ | @routinetype
+ | @ptrtomember
+ | @decltype;
+
+unspecifiedtype(
+ unique int type_id: @type ref,
+ int unspecified_type_id: @type ref
+);
+
+member(
+ int parent: @type ref,
+ int index: int ref,
+ int child: @member ref
+);
+
+@enclosingfunction_child = @usertype | @variable | @namespace
+
+enclosingfunction(
+ unique int child: @enclosingfunction_child ref,
+ int parent: @function ref
+);
+
+derivations(
+ unique int derivation: @derivation,
+ int sub: @type ref,
+ int index: int ref,
+ int super: @type ref,
+ int location: @location_default ref
+);
+
+derspecifiers(
+ int der_id: @derivation ref,
+ int spec_id: @specifier ref
+);
+
+/**
+ * Contains the byte offset of the base class subobject within the derived
+ * class. Only holds for non-virtual base classes, but see table
+ * `virtual_base_offsets` for offsets of virtual base class subobjects.
+ */
+direct_base_offsets(
+ unique int der_id: @derivation ref,
+ int offset: int ref
+);
+
+/**
+ * Contains the byte offset of the virtual base class subobject for class
+ * `super` within a most-derived object of class `sub`. `super` can be either a
+ * direct or indirect base class.
+ */
+#keyset[sub, super]
+virtual_base_offsets(
+ int sub: @usertype ref,
+ int super: @usertype ref,
+ int offset: int ref
+);
+
+frienddecls(
+ unique int id: @frienddecl,
+ int type_id: @type ref,
+ int decl_id: @declaration ref,
+ int location: @location_default ref
+);
+
+@declaredtype = @usertype ;
+
+@declaration = @function
+ | @declaredtype
+ | @variable
+ | @enumconstant
+ | @frienddecl;
+
+@member = @membervariable
+ | @function
+ | @declaredtype
+ | @enumconstant;
+
+@locatable = @diagnostic
+ | @declaration
+ | @ppd_include
+ | @ppd_define
+ | @macroinvocation
+ /*| @funcall*/
+ | @xmllocatable
+ | @attribute
+ | @attribute_arg;
+
+@namedscope = @namespace | @usertype;
+
+@element = @locatable
+ | @file
+ | @folder
+ | @specifier
+ | @type
+ | @expr
+ | @namespace
+ | @initialiser
+ | @stmt
+ | @derivation
+ | @comment
+ | @preprocdirect
+ | @fun_decl
+ | @var_decl
+ | @type_decl
+ | @namespace_decl
+ | @using
+ | @namequalifier
+ | @specialnamequalifyingelement
+ | @static_assert
+ | @type_mention
+ | @lambdacapture;
+
+@exprparent = @element;
+
+comments(
+ unique int id: @comment,
+ string contents: string ref,
+ int location: @location_default ref
+);
+
+commentbinding(
+ int id: @comment ref,
+ int element: @element ref
+);
+
+exprconv(
+ int converted: @expr ref,
+ unique int conversion: @expr ref
+);
+
+compgenerated(unique int id: @element ref);
+
+/**
+ * `destructor_call` destructs the `i`'th entity that should be
+ * destructed following `element`. Note that entities should be
+ * destructed in reverse construction order, so for a given `element`
+ * these should be called from highest to lowest `i`.
+ */
+#keyset[element, destructor_call]
+#keyset[element, i]
+synthetic_destructor_call(
+ int element: @element ref,
+ int i: int ref,
+ int destructor_call: @routineexpr ref
+);
+
+namespaces(
+ unique int id: @namespace,
+ string name: string ref
+);
+
+namespace_inline(
+ unique int id: @namespace ref
+);
+
+namespacembrs(
+ int parentid: @namespace ref,
+ unique int memberid: @namespacembr ref
+);
+
+@namespacembr = @declaration | @namespace;
+
+exprparents(
+ int expr_id: @expr ref,
+ int child_index: int ref,
+ int parent_id: @exprparent ref
+);
+
+expr_isload(unique int expr_id: @expr ref);
+
+@cast = @c_style_cast
+ | @const_cast
+ | @dynamic_cast
+ | @reinterpret_cast
+ | @static_cast
+ ;
+
+/*
+case @conversion.kind of
+ 0 = @simple_conversion // a numeric conversion, qualification conversion, or a reinterpret_cast
+| 1 = @bool_conversion // conversion to 'bool'
+| 2 = @base_class_conversion // a derived-to-base conversion
+| 3 = @derived_class_conversion // a base-to-derived conversion
+| 4 = @pm_base_class_conversion // a derived-to-base conversion of a pointer to member
+| 5 = @pm_derived_class_conversion // a base-to-derived conversion of a pointer to member
+| 6 = @glvalue_adjust // an adjustment of the type of a glvalue
+| 7 = @prvalue_adjust // an adjustment of the type of a prvalue
+;
+*/
+/**
+ * Describes the semantics represented by a cast expression. This is largely
+ * independent of the source syntax of the cast, so it is separate from the
+ * regular expression kind.
+ */
+conversionkinds(
+ unique int expr_id: @cast ref,
+ int kind: int ref
+);
+
+@conversion = @cast
+ | @array_to_pointer
+ | @parexpr
+ | @reference_to
+ | @ref_indirect
+ | @temp_init
+ ;
+
+/*
+case @funbindexpr.kind of
+ 0 = @normal_call // a normal call
+| 1 = @virtual_call // a virtual call
+| 2 = @adl_call // a call whose target is only found by ADL
+;
+*/
+iscall(
+ unique int caller: @funbindexpr ref,
+ int kind: int ref
+);
+
+numtemplatearguments(
+ unique int expr_id: @expr ref,
+ int num: int ref
+);
+
+specialnamequalifyingelements(
+ unique int id: @specialnamequalifyingelement,
+ unique string name: string ref
+);
+
+@namequalifiableelement = @expr | @namequalifier;
+@namequalifyingelement = @namespace
+ | @specialnamequalifyingelement
+ | @usertype;
+
+namequalifiers(
+ unique int id: @namequalifier,
+ unique int qualifiableelement: @namequalifiableelement ref,
+ int qualifyingelement: @namequalifyingelement ref,
+ int location: @location_default ref
+);
+
+varbind(
+ int expr: @varbindexpr ref,
+ int var: @accessible ref
+);
+
+funbind(
+ int expr: @funbindexpr ref,
+ int fun: @function ref
+);
+
+@any_new_expr = @new_expr
+ | @new_array_expr;
+
+@new_or_delete_expr = @any_new_expr
+ | @delete_expr
+ | @delete_array_expr;
+
+@prefix_crement_expr = @preincrexpr | @predecrexpr;
+
+@postfix_crement_expr = @postincrexpr | @postdecrexpr;
+
+@increment_expr = @preincrexpr | @postincrexpr;
+
+@decrement_expr = @predecrexpr | @postdecrexpr;
+
+@crement_expr = @increment_expr | @decrement_expr;
+
+@un_arith_op_expr = @arithnegexpr
+ | @unaryplusexpr
+ | @conjugation
+ | @realpartexpr
+ | @imagpartexpr
+ | @crement_expr
+ ;
+
+@un_bitwise_op_expr = @complementexpr;
+
+@un_log_op_expr = @notexpr;
+
+@un_op_expr = @address_of
+ | @indirect
+ | @un_arith_op_expr
+ | @un_bitwise_op_expr
+ | @builtinaddressof
+ | @vec_fill
+ | @un_log_op_expr
+ | @co_await
+ | @co_yield
+ ;
+
+@bin_log_op_expr = @andlogicalexpr | @orlogicalexpr;
+
+@cmp_op_expr = @eq_op_expr | @rel_op_expr;
+
+@eq_op_expr = @eqexpr | @neexpr;
+
+@rel_op_expr = @gtexpr
+ | @ltexpr
+ | @geexpr
+ | @leexpr
+ | @spaceshipexpr
+ ;
+
+@bin_bitwise_op_expr = @lshiftexpr
+ | @rshiftexpr
+ | @andexpr
+ | @orexpr
+ | @xorexpr
+ ;
+
+@p_arith_op_expr = @paddexpr
+ | @psubexpr
+ | @pdiffexpr
+ ;
+
+@bin_arith_op_expr = @addexpr
+ | @subexpr
+ | @mulexpr
+ | @divexpr
+ | @remexpr
+ | @jmulexpr
+ | @jdivexpr
+ | @fjaddexpr
+ | @jfaddexpr
+ | @fjsubexpr
+ | @jfsubexpr
+ | @minexpr
+ | @maxexpr
+ | @p_arith_op_expr
+ ;
+
+@bin_op_expr = @bin_arith_op_expr
+ | @bin_bitwise_op_expr
+ | @cmp_op_expr
+ | @bin_log_op_expr
+ ;
+
+@op_expr = @un_op_expr
+ | @bin_op_expr
+ | @assign_expr
+ | @conditionalexpr
+ ;
+
+@assign_arith_expr = @assignaddexpr
+ | @assignsubexpr
+ | @assignmulexpr
+ | @assigndivexpr
+ | @assignremexpr
+ ;
+
+@assign_bitwise_expr = @assignandexpr
+ | @assignorexpr
+ | @assignxorexpr
+ | @assignlshiftexpr
+ | @assignrshiftexpr
+ ;
+
+@assign_pointer_expr = @assignpaddexpr
+ | @assignpsubexpr
+ ;
+
+@assign_op_expr = @assign_arith_expr
+ | @assign_bitwise_expr
+ | @assign_pointer_expr
+ ;
+
+@assign_expr = @assignexpr | @assign_op_expr | @blockassignexpr
+
+/*
+ case @allocator.form of
+ 0 = plain
+ | 1 = alignment
+ ;
+*/
+
+/**
+ * The allocator function associated with a `new` or `new[]` expression.
+ * The `form` column specified whether the allocation call contains an alignment
+ * argument.
+ */
+expr_allocator(
+ unique int expr: @any_new_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/*
+ case @deallocator.form of
+ 0 = plain
+ | 1 = size
+ | 2 = alignment
+ | 3 = size_and_alignment
+ ;
+*/
+
+/**
+ * The deallocator function associated with a `delete`, `delete[]`, `new`, or
+ * `new[]` expression. For a `new` or `new[]` expression, the deallocator is the
+ * one used to free memory if the initialization throws an exception.
+ * The `form` column specifies whether the deallocation call contains a size
+ * argument, and alignment argument, or both.
+ */
+expr_deallocator(
+ unique int expr: @new_or_delete_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/**
+ * Holds if the `@conditionalexpr` is of the two operand form
+ * `guard ? : false`.
+ */
+expr_cond_two_operand(
+ unique int cond: @conditionalexpr ref
+);
+
+/**
+ * The guard of `@conditionalexpr` `guard ? true : false`
+ */
+expr_cond_guard(
+ unique int cond: @conditionalexpr ref,
+ int guard: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` holds. For the two operand form
+ * `guard ?: false` consider using `expr_cond_guard` instead.
+ */
+expr_cond_true(
+ unique int cond: @conditionalexpr ref,
+ int true: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` does not hold.
+ */
+expr_cond_false(
+ unique int cond: @conditionalexpr ref,
+ int false: @expr ref
+);
+
+/** A string representation of the value. */
+values(
+ unique int id: @value,
+ string str: string ref
+);
+
+/** The actual text in the source code for the value, if any. */
+valuetext(
+ unique int id: @value ref,
+ string text: string ref
+);
+
+valuebind(
+ int val: @value ref,
+ unique int expr: @expr ref
+);
+
+fieldoffsets(
+ unique int id: @variable ref,
+ int byteoffset: int ref,
+ int bitoffset: int ref
+);
+
+bitfield(
+ unique int id: @variable ref,
+ int bits: int ref,
+ int declared_bits: int ref
+);
+
+/* TODO
+memberprefix(
+ int member: @expr ref,
+ int prefix: @expr ref
+);
+*/
+
+/*
+ kind(1) = mbrcallexpr
+ kind(2) = mbrptrcallexpr
+ kind(3) = mbrptrmbrcallexpr
+ kind(4) = ptrmbrptrmbrcallexpr
+ kind(5) = mbrreadexpr // x.y
+ kind(6) = mbrptrreadexpr // p->y
+ kind(7) = mbrptrmbrreadexpr // x.*pm
+ kind(8) = mbrptrmbrptrreadexpr // x->*pm
+ kind(9) = staticmbrreadexpr // static x.y
+ kind(10) = staticmbrptrreadexpr // static p->y
+*/
+/* TODO
+memberaccess(
+ int member: @expr ref,
+ int kind: int ref
+);
+*/
+
+initialisers(
+ unique int init: @initialiser,
+ int var: @accessible ref,
+ unique int expr: @expr ref,
+ int location: @location_expr ref
+);
+
+braced_initialisers(
+ int init: @initialiser ref
+);
+
+/**
+ * An ancestor for the expression, for cases in which we cannot
+ * otherwise find the expression's parent.
+ */
+expr_ancestor(
+ int exp: @expr ref,
+ int ancestor: @element ref
+);
+
+exprs(
+ unique int id: @expr,
+ int kind: int ref,
+ int location: @location_expr ref
+);
+
+/*
+ case @value.category of
+ 1 = prval
+ | 2 = xval
+ | 3 = lval
+ ;
+*/
+expr_types(
+ int id: @expr ref,
+ int typeid: @type ref,
+ int value_category: int ref
+);
+
+case @expr.kind of
+ 1 = @errorexpr
+| 2 = @address_of // & AddressOfExpr
+| 3 = @reference_to // ReferenceToExpr (implicit?)
+| 4 = @indirect // * PointerDereferenceExpr
+| 5 = @ref_indirect // ReferenceDereferenceExpr (implicit?)
+// ...
+| 8 = @array_to_pointer // (???)
+| 9 = @vacuous_destructor_call // VacuousDestructorCall
+// ...
+| 11 = @assume // Microsoft
+| 12 = @parexpr
+| 13 = @arithnegexpr
+| 14 = @unaryplusexpr
+| 15 = @complementexpr
+| 16 = @notexpr
+| 17 = @conjugation // GNU ~ operator
+| 18 = @realpartexpr // GNU __real
+| 19 = @imagpartexpr // GNU __imag
+| 20 = @postincrexpr
+| 21 = @postdecrexpr
+| 22 = @preincrexpr
+| 23 = @predecrexpr
+| 24 = @conditionalexpr
+| 25 = @addexpr
+| 26 = @subexpr
+| 27 = @mulexpr
+| 28 = @divexpr
+| 29 = @remexpr
+| 30 = @jmulexpr // C99 mul imaginary
+| 31 = @jdivexpr // C99 div imaginary
+| 32 = @fjaddexpr // C99 add real + imaginary
+| 33 = @jfaddexpr // C99 add imaginary + real
+| 34 = @fjsubexpr // C99 sub real - imaginary
+| 35 = @jfsubexpr // C99 sub imaginary - real
+| 36 = @paddexpr // pointer add (pointer + int or int + pointer)
+| 37 = @psubexpr // pointer sub (pointer - integer)
+| 38 = @pdiffexpr // difference between two pointers
+| 39 = @lshiftexpr
+| 40 = @rshiftexpr
+| 41 = @andexpr
+| 42 = @orexpr
+| 43 = @xorexpr
+| 44 = @eqexpr
+| 45 = @neexpr
+| 46 = @gtexpr
+| 47 = @ltexpr
+| 48 = @geexpr
+| 49 = @leexpr
+| 50 = @minexpr // GNU minimum
+| 51 = @maxexpr // GNU maximum
+| 52 = @assignexpr
+| 53 = @assignaddexpr
+| 54 = @assignsubexpr
+| 55 = @assignmulexpr
+| 56 = @assigndivexpr
+| 57 = @assignremexpr
+| 58 = @assignlshiftexpr
+| 59 = @assignrshiftexpr
+| 60 = @assignandexpr
+| 61 = @assignorexpr
+| 62 = @assignxorexpr
+| 63 = @assignpaddexpr // assign pointer add
+| 64 = @assignpsubexpr // assign pointer sub
+| 65 = @andlogicalexpr
+| 66 = @orlogicalexpr
+| 67 = @commaexpr
+| 68 = @subscriptexpr // access to member of an array, e.g., a[5]
+// ... 69 @objc_subscriptexpr deprecated
+// ... 70 @cmdaccess deprecated
+// ...
+| 73 = @virtfunptrexpr
+| 74 = @callexpr
+// ... 75 @msgexpr_normal deprecated
+// ... 76 @msgexpr_super deprecated
+// ... 77 @atselectorexpr deprecated
+// ... 78 @atprotocolexpr deprecated
+| 79 = @vastartexpr
+| 80 = @vaargexpr
+| 81 = @vaendexpr
+| 82 = @vacopyexpr
+// ... 83 @atencodeexpr deprecated
+| 84 = @varaccess
+| 85 = @thisaccess
+// ... 86 @objc_box_expr deprecated
+| 87 = @new_expr
+| 88 = @delete_expr
+| 89 = @throw_expr
+| 90 = @condition_decl // a variable declared in a condition, e.g., if(int x = y > 2)
+| 91 = @braced_init_list
+| 92 = @type_id
+| 93 = @runtime_sizeof
+| 94 = @runtime_alignof
+| 95 = @sizeof_pack
+| 96 = @expr_stmt // GNU extension
+| 97 = @routineexpr
+| 98 = @type_operand // used to access a type in certain contexts (haven't found any examples yet....)
+| 99 = @offsetofexpr // offsetof ::= type and field
+| 100 = @hasassignexpr // __has_assign ::= type
+| 101 = @hascopyexpr // __has_copy ::= type
+| 102 = @hasnothrowassign // __has_nothrow_assign ::= type
+| 103 = @hasnothrowconstr // __has_nothrow_constructor ::= type
+| 104 = @hasnothrowcopy // __has_nothrow_copy ::= type
+| 105 = @hastrivialassign // __has_trivial_assign ::= type
+| 106 = @hastrivialconstr // __has_trivial_constructor ::= type
+| 107 = @hastrivialcopy // __has_trivial_copy ::= type
+| 108 = @hasuserdestr // __has_user_destructor ::= type
+| 109 = @hasvirtualdestr // __has_virtual_destructor ::= type
+| 110 = @isabstractexpr // __is_abstract ::= type
+| 111 = @isbaseofexpr // __is_base_of ::= type type
+| 112 = @isclassexpr // __is_class ::= type
+| 113 = @isconvtoexpr // __is_convertible_to ::= type type
+| 114 = @isemptyexpr // __is_empty ::= type
+| 115 = @isenumexpr // __is_enum ::= type
+| 116 = @ispodexpr // __is_pod ::= type
+| 117 = @ispolyexpr // __is_polymorphic ::= type
+| 118 = @isunionexpr // __is_union ::= type
+| 119 = @typescompexpr // GNU __builtin_types_compatible ::= type type
+| 120 = @intaddrexpr // frontend internal builtin, used to implement offsetof
+// ...
+| 122 = @hastrivialdestructor // __has_trivial_destructor ::= type
+| 123 = @literal
+| 124 = @uuidof
+| 127 = @aggregateliteral
+| 128 = @delete_array_expr
+| 129 = @new_array_expr
+// ... 130 @objc_array_literal deprecated
+// ... 131 @objc_dictionary_literal deprecated
+| 132 = @foldexpr
+// ...
+| 200 = @ctordirectinit
+| 201 = @ctorvirtualinit
+| 202 = @ctorfieldinit
+| 203 = @ctordelegatinginit
+| 204 = @dtordirectdestruct
+| 205 = @dtorvirtualdestruct
+| 206 = @dtorfielddestruct
+// ...
+| 210 = @static_cast
+| 211 = @reinterpret_cast
+| 212 = @const_cast
+| 213 = @dynamic_cast
+| 214 = @c_style_cast
+| 215 = @lambdaexpr
+| 216 = @param_ref
+| 217 = @noopexpr
+// ...
+| 294 = @istriviallyconstructibleexpr
+| 295 = @isdestructibleexpr
+| 296 = @isnothrowdestructibleexpr
+| 297 = @istriviallydestructibleexpr
+| 298 = @istriviallyassignableexpr
+| 299 = @isnothrowassignableexpr
+| 300 = @istrivialexpr
+| 301 = @isstandardlayoutexpr
+| 302 = @istriviallycopyableexpr
+| 303 = @isliteraltypeexpr
+| 304 = @hastrivialmoveconstructorexpr
+| 305 = @hastrivialmoveassignexpr
+| 306 = @hasnothrowmoveassignexpr
+| 307 = @isconstructibleexpr
+| 308 = @isnothrowconstructibleexpr
+| 309 = @hasfinalizerexpr
+| 310 = @isdelegateexpr
+| 311 = @isinterfaceclassexpr
+| 312 = @isrefarrayexpr
+| 313 = @isrefclassexpr
+| 314 = @issealedexpr
+| 315 = @issimplevalueclassexpr
+| 316 = @isvalueclassexpr
+| 317 = @isfinalexpr
+| 319 = @noexceptexpr
+| 320 = @builtinshufflevector
+| 321 = @builtinchooseexpr
+| 322 = @builtinaddressof
+| 323 = @vec_fill
+| 324 = @builtinconvertvector
+| 325 = @builtincomplex
+| 326 = @spaceshipexpr
+| 327 = @co_await
+| 328 = @co_yield
+| 329 = @temp_init
+| 330 = @isassignable
+| 331 = @isaggregate
+| 332 = @hasuniqueobjectrepresentations
+| 333 = @builtinbitcast
+| 334 = @builtinshuffle
+| 335 = @blockassignexpr
+| 336 = @issame
+| 337 = @isfunction
+| 338 = @islayoutcompatible
+| 339 = @ispointerinterconvertiblebaseof
+| 340 = @isarray
+| 341 = @arrayrank
+| 342 = @arrayextent
+| 343 = @isarithmetic
+| 344 = @iscompletetype
+| 345 = @iscompound
+| 346 = @isconst
+| 347 = @isfloatingpoint
+| 348 = @isfundamental
+| 349 = @isintegral
+| 350 = @islvaluereference
+| 351 = @ismemberfunctionpointer
+| 352 = @ismemberobjectpointer
+| 353 = @ismemberpointer
+| 354 = @isobject
+| 355 = @ispointer
+| 356 = @isreference
+| 357 = @isrvaluereference
+| 358 = @isscalar
+| 359 = @issigned
+| 360 = @isunsigned
+| 361 = @isvoid
+| 362 = @isvolatile
+;
+
+@var_args_expr = @vastartexpr
+ | @vaendexpr
+ | @vaargexpr
+ | @vacopyexpr
+ ;
+
+@builtin_op = @var_args_expr
+ | @noopexpr
+ | @offsetofexpr
+ | @intaddrexpr
+ | @hasassignexpr
+ | @hascopyexpr
+ | @hasnothrowassign
+ | @hasnothrowconstr
+ | @hasnothrowcopy
+ | @hastrivialassign
+ | @hastrivialconstr
+ | @hastrivialcopy
+ | @hastrivialdestructor
+ | @hasuserdestr
+ | @hasvirtualdestr
+ | @isabstractexpr
+ | @isbaseofexpr
+ | @isclassexpr
+ | @isconvtoexpr
+ | @isemptyexpr
+ | @isenumexpr
+ | @ispodexpr
+ | @ispolyexpr
+ | @isunionexpr
+ | @typescompexpr
+ | @builtinshufflevector
+ | @builtinconvertvector
+ | @builtinaddressof
+ | @istriviallyconstructibleexpr
+ | @isdestructibleexpr
+ | @isnothrowdestructibleexpr
+ | @istriviallydestructibleexpr
+ | @istriviallyassignableexpr
+ | @isnothrowassignableexpr
+ | @istrivialexpr
+ | @isstandardlayoutexpr
+ | @istriviallycopyableexpr
+ | @isliteraltypeexpr
+ | @hastrivialmoveconstructorexpr
+ | @hastrivialmoveassignexpr
+ | @hasnothrowmoveassignexpr
+ | @isconstructibleexpr
+ | @isnothrowconstructibleexpr
+ | @hasfinalizerexpr
+ | @isdelegateexpr
+ | @isinterfaceclassexpr
+ | @isrefarrayexpr
+ | @isrefclassexpr
+ | @issealedexpr
+ | @issimplevalueclassexpr
+ | @isvalueclassexpr
+ | @isfinalexpr
+ | @builtinchooseexpr
+ | @builtincomplex
+ | @isassignable
+ | @isaggregate
+ | @hasuniqueobjectrepresentations
+ | @builtinbitcast
+ | @builtinshuffle
+ | @issame
+ | @isfunction
+ | @islayoutcompatible
+ | @ispointerinterconvertiblebaseof
+ | @isarray
+ | @arrayrank
+ | @arrayextent
+ | @isarithmetic
+ | @iscompletetype
+ | @iscompound
+ | @isconst
+ | @isfloatingpoint
+ | @isfundamental
+ | @isintegral
+ | @islvaluereference
+ | @ismemberfunctionpointer
+ | @ismemberobjectpointer
+ | @ismemberpointer
+ | @isobject
+ | @ispointer
+ | @isreference
+ | @isrvaluereference
+ | @isscalar
+ | @issigned
+ | @isunsigned
+ | @isvoid
+ | @isvolatile
+ ;
+
+new_allocated_type(
+ unique int expr: @new_expr ref,
+ int type_id: @type ref
+);
+
+new_array_allocated_type(
+ unique int expr: @new_array_expr ref,
+ int type_id: @type ref
+);
+
+/**
+ * The field being initialized by an initializer expression within an aggregate
+ * initializer for a class/struct/union. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_field_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int field: @membervariable ref,
+ int position: int ref
+);
+
+/**
+ * The index of the element being initialized by an initializer expression
+ * within an aggregate initializer for an array. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_array_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int element_index: int ref,
+ int position: int ref
+);
+
+@ctorinit = @ctordirectinit
+ | @ctorvirtualinit
+ | @ctorfieldinit
+ | @ctordelegatinginit;
+@dtordestruct = @dtordirectdestruct
+ | @dtorvirtualdestruct
+ | @dtorfielddestruct;
+
+
+condition_decl_bind(
+ unique int expr: @condition_decl ref,
+ unique int decl: @declaration ref
+);
+
+typeid_bind(
+ unique int expr: @type_id ref,
+ int type_id: @type ref
+);
+
+uuidof_bind(
+ unique int expr: @uuidof ref,
+ int type_id: @type ref
+);
+
+@runtime_sizeof_or_alignof = @runtime_sizeof | @runtime_alignof;
+
+sizeof_bind(
+ unique int expr: @runtime_sizeof_or_alignof ref,
+ int type_id: @type ref
+);
+
+code_block(
+ unique int block: @literal ref,
+ unique int routine: @function ref
+);
+
+lambdas(
+ unique int expr: @lambdaexpr ref,
+ string default_capture: string ref,
+ boolean has_explicit_return_type: boolean ref
+);
+
+lambda_capture(
+ unique int id: @lambdacapture,
+ int lambda: @lambdaexpr ref,
+ int index: int ref,
+ int field: @membervariable ref,
+ boolean captured_by_reference: boolean ref,
+ boolean is_implicit: boolean ref,
+ int location: @location_default ref
+);
+
+@funbindexpr = @routineexpr
+ | @new_expr
+ | @delete_expr
+ | @delete_array_expr
+ | @ctordirectinit
+ | @ctorvirtualinit
+ | @ctordelegatinginit
+ | @dtordirectdestruct
+ | @dtorvirtualdestruct;
+
+@varbindexpr = @varaccess | @ctorfieldinit | @dtorfielddestruct;
+@addressable = @function | @variable ;
+@accessible = @addressable | @enumconstant ;
+
+@access = @varaccess | @routineexpr ;
+
+fold(
+ int expr: @foldexpr ref,
+ string operator: string ref,
+ boolean is_left_fold: boolean ref
+);
+
+stmts(
+ unique int id: @stmt,
+ int kind: int ref,
+ int location: @location_stmt ref
+);
+
+case @stmt.kind of
+ 1 = @stmt_expr
+| 2 = @stmt_if
+| 3 = @stmt_while
+| 4 = @stmt_goto
+| 5 = @stmt_label
+| 6 = @stmt_return
+| 7 = @stmt_block
+| 8 = @stmt_end_test_while // do { ... } while ( ... )
+| 9 = @stmt_for
+| 10 = @stmt_switch_case
+| 11 = @stmt_switch
+| 13 = @stmt_asm // "asm" statement or the body of an asm function
+| 15 = @stmt_try_block
+| 16 = @stmt_microsoft_try // Microsoft
+| 17 = @stmt_decl
+| 18 = @stmt_set_vla_size // C99
+| 19 = @stmt_vla_decl // C99
+| 25 = @stmt_assigned_goto // GNU
+| 26 = @stmt_empty
+| 27 = @stmt_continue
+| 28 = @stmt_break
+| 29 = @stmt_range_based_for // C++11
+// ... 30 @stmt_at_autoreleasepool_block deprecated
+// ... 31 @stmt_objc_for_in deprecated
+// ... 32 @stmt_at_synchronized deprecated
+| 33 = @stmt_handler
+// ... 34 @stmt_finally_end deprecated
+| 35 = @stmt_constexpr_if
+| 37 = @stmt_co_return
+;
+
+type_vla(
+ int type_id: @type ref,
+ int decl: @stmt_vla_decl ref
+);
+
+variable_vla(
+ int var: @variable ref,
+ int decl: @stmt_vla_decl ref
+);
+
+if_initialization(
+ unique int if_stmt: @stmt_if ref,
+ int init_id: @stmt ref
+);
+
+if_then(
+ unique int if_stmt: @stmt_if ref,
+ int then_id: @stmt ref
+);
+
+if_else(
+ unique int if_stmt: @stmt_if ref,
+ int else_id: @stmt ref
+);
+
+constexpr_if_initialization(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int init_id: @stmt ref
+);
+
+constexpr_if_then(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int then_id: @stmt ref
+);
+
+constexpr_if_else(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int else_id: @stmt ref
+);
+
+while_body(
+ unique int while_stmt: @stmt_while ref,
+ int body_id: @stmt ref
+);
+
+do_body(
+ unique int do_stmt: @stmt_end_test_while ref,
+ int body_id: @stmt ref
+);
+
+switch_initialization(
+ unique int switch_stmt: @stmt_switch ref,
+ int init_id: @stmt ref
+);
+
+#keyset[switch_stmt, index]
+switch_case(
+ int switch_stmt: @stmt_switch ref,
+ int index: int ref,
+ int case_id: @stmt_switch_case ref
+);
+
+switch_body(
+ unique int switch_stmt: @stmt_switch ref,
+ int body_id: @stmt ref
+);
+
+for_initialization(
+ unique int for_stmt: @stmt_for ref,
+ int init_id: @stmt ref
+);
+
+for_condition(
+ unique int for_stmt: @stmt_for ref,
+ int condition_id: @expr ref
+);
+
+for_update(
+ unique int for_stmt: @stmt_for ref,
+ int update_id: @expr ref
+);
+
+for_body(
+ unique int for_stmt: @stmt_for ref,
+ int body_id: @stmt ref
+);
+
+@stmtparent = @stmt | @expr_stmt ;
+stmtparents(
+ unique int id: @stmt ref,
+ int index: int ref,
+ int parent: @stmtparent ref
+);
+
+ishandler(unique int block: @stmt_block ref);
+
+@cfgnode = @stmt | @expr | @function | @initialiser ;
+
+stmt_decl_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl: @declaration ref
+);
+
+stmt_decl_entry_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl_entry: @element ref
+);
+
+@functionorblock = @function | @stmt_block;
+
+blockscope(
+ unique int block: @stmt_block ref,
+ int enclosing: @functionorblock ref
+);
+
+@jump = @stmt_goto | @stmt_break | @stmt_continue;
+
+@jumporlabel = @jump | @stmt_label | @literal;
+
+jumpinfo(
+ unique int id: @jumporlabel ref,
+ string str: string ref,
+ int target: @stmt ref
+);
+
+preprocdirects(
+ unique int id: @preprocdirect,
+ int kind: int ref,
+ int location: @location_default ref
+);
+case @preprocdirect.kind of
+ 0 = @ppd_if
+| 1 = @ppd_ifdef
+| 2 = @ppd_ifndef
+| 3 = @ppd_elif
+| 4 = @ppd_else
+| 5 = @ppd_endif
+| 6 = @ppd_plain_include
+| 7 = @ppd_define
+| 8 = @ppd_undef
+| 9 = @ppd_line
+| 10 = @ppd_error
+| 11 = @ppd_pragma
+| 12 = @ppd_objc_import
+| 13 = @ppd_include_next
+| 18 = @ppd_warning
+;
+
+@ppd_include = @ppd_plain_include | @ppd_objc_import | @ppd_include_next;
+
+@ppd_branch = @ppd_if | @ppd_ifdef | @ppd_ifndef | @ppd_elif;
+
+preprocpair(
+ int begin : @ppd_branch ref,
+ int elseelifend : @preprocdirect ref
+);
+
+preproctrue(int branch : @ppd_branch ref);
+preprocfalse(int branch : @ppd_branch ref);
+
+preproctext(
+ unique int id: @preprocdirect ref,
+ string head: string ref,
+ string body: string ref
+);
+
+includes(
+ unique int id: @ppd_include ref,
+ int included: @file ref
+);
+
+link_targets(
+ unique int id: @link_target,
+ int binary: @file ref
+);
+
+link_parent(
+ int element : @element ref,
+ int link_target : @link_target ref
+);
+
+/* XML Files */
+
+xmlEncoding(unique int id: @file ref, string encoding: string ref);
+
+xmlDTDs(
+ unique int id: @xmldtd,
+ string root: string ref,
+ string publicId: string ref,
+ string systemId: string ref,
+ int fileid: @file ref
+);
+
+xmlElements(
+ unique int id: @xmlelement,
+ string name: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlAttrs(
+ unique int id: @xmlattribute,
+ int elementid: @xmlelement ref,
+ string name: string ref,
+ string value: string ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlNs(
+ int id: @xmlnamespace,
+ string prefixName: string ref,
+ string URI: string ref,
+ int fileid: @file ref
+);
+
+xmlHasNs(
+ int elementId: @xmlnamespaceable ref,
+ int nsId: @xmlnamespace ref,
+ int fileid: @file ref
+);
+
+xmlComments(
+ unique int id: @xmlcomment,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int fileid: @file ref
+);
+
+xmlChars(
+ unique int id: @xmlcharacters,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int isCDATA: int ref,
+ int fileid: @file ref
+);
+
+@xmlparent = @file | @xmlelement;
+@xmlnamespaceable = @xmlelement | @xmlattribute;
+
+xmllocations(
+ int xmlElement: @xmllocatable ref,
+ int location: @location_default ref
+);
+
+@xmllocatable = @xmlcharacters
+ | @xmlelement
+ | @xmlcomment
+ | @xmlattribute
+ | @xmldtd
+ | @file
+ | @xmlnamespace;
diff --git a/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/upgrade.properties b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/upgrade.properties
new file mode 100644
index 00000000000..a9622850f04
--- /dev/null
+++ b/cpp/downgrades/0a9eb01d3650642e013eb86be45d952289537f91/upgrade.properties
@@ -0,0 +1,3 @@
+description: Expose whether a function was prototyped or not
+compatibility: backwards
+function_prototyped.rel: delete
diff --git a/cpp/ql/lib/CHANGELOG.md b/cpp/ql/lib/CHANGELOG.md
index cf81a85004d..39e7da98714 100644
--- a/cpp/ql/lib/CHANGELOG.md
+++ b/cpp/ql/lib/CHANGELOG.md
@@ -1,3 +1,9 @@
+## 0.12.1
+
+### New Features
+
+* Added an `isPrototyped` predicate to `Function` that holds when the function has a prototype.
+
## 0.12.0
### Breaking Changes
diff --git a/cpp/ql/lib/change-notes/released/0.12.1.md b/cpp/ql/lib/change-notes/released/0.12.1.md
new file mode 100644
index 00000000000..c3d7c8ccfdf
--- /dev/null
+++ b/cpp/ql/lib/change-notes/released/0.12.1.md
@@ -0,0 +1,5 @@
+## 0.12.1
+
+### New Features
+
+* Added an `isPrototyped` predicate to `Function` that holds when the function has a prototype.
diff --git a/cpp/ql/lib/codeql-pack.release.yml b/cpp/ql/lib/codeql-pack.release.yml
index 5e2fb32b059..58783ccb26c 100644
--- a/cpp/ql/lib/codeql-pack.release.yml
+++ b/cpp/ql/lib/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 0.12.0
+lastReleaseVersion: 0.12.1
diff --git a/cpp/ql/lib/qlpack.yml b/cpp/ql/lib/qlpack.yml
index d25b31da94a..0b45bd870c4 100644
--- a/cpp/ql/lib/qlpack.yml
+++ b/cpp/ql/lib/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/cpp-all
-version: 0.12.0
+version: 0.12.1
groups: cpp
dbscheme: semmlecode.cpp.dbscheme
extractor: cpp
diff --git a/cpp/ql/lib/semmle/code/cpp/Function.qll b/cpp/ql/lib/semmle/code/cpp/Function.qll
index eec7a433774..234b2d05283 100644
--- a/cpp/ql/lib/semmle/code/cpp/Function.qll
+++ b/cpp/ql/lib/semmle/code/cpp/Function.qll
@@ -112,6 +112,16 @@ class Function extends Declaration, ControlFlowNode, AccessHolder, @function {
*/
predicate isDeleted() { function_deleted(underlyingElement(this)) }
+ /**
+ * Holds if this function has a prototyped interface.
+ *
+ * Functions generally have a prototyped interface, unless they are
+ * K&R-style functions either without any forward function declaration,
+ * or with all the forward declarations omitting the parameters of the
+ * function.
+ */
+ predicate isPrototyped() { function_prototyped(underlyingElement(this)) }
+
/**
* Holds if this function is explicitly defaulted with the `= default`
* specifier.
diff --git a/cpp/ql/lib/semmle/code/cpp/controlflow/IRGuards.qll b/cpp/ql/lib/semmle/code/cpp/controlflow/IRGuards.qll
index 5a0c561dc3f..702032182e0 100644
--- a/cpp/ql/lib/semmle/code/cpp/controlflow/IRGuards.qll
+++ b/cpp/ql/lib/semmle/code/cpp/controlflow/IRGuards.qll
@@ -30,11 +30,6 @@ class GuardCondition extends Expr {
or
// no binary operators in the IR
this.(BinaryLogicalOperation).getAnOperand() instanceof GuardCondition
- or
- // the IR short-circuits if(!x)
- // don't produce a guard condition for `y = !x` and other non-short-circuited cases
- not exists(Instruction inst | this.getFullyConverted() = inst.getAst()) and
- exists(IRGuardCondition ir | this.(NotExpr).getOperand() = ir.getAst())
}
/**
@@ -140,39 +135,6 @@ private class GuardConditionFromBinaryLogicalOperator extends GuardCondition {
}
}
-/**
- * A `!` operator in the AST that guards one or more basic blocks, and does not have a corresponding
- * IR instruction.
- */
-private class GuardConditionFromShortCircuitNot extends GuardCondition, NotExpr {
- GuardConditionFromShortCircuitNot() {
- not exists(Instruction inst | this.getFullyConverted() = inst.getAst()) and
- exists(IRGuardCondition ir | this.getOperand() = ir.getAst())
- }
-
- override predicate controls(BasicBlock controlled, boolean testIsTrue) {
- this.getOperand().(GuardCondition).controls(controlled, testIsTrue.booleanNot())
- }
-
- override predicate comparesLt(Expr left, Expr right, int k, boolean isLessThan, boolean testIsTrue) {
- this.getOperand()
- .(GuardCondition)
- .comparesLt(left, right, k, isLessThan, testIsTrue.booleanNot())
- }
-
- override predicate ensuresLt(Expr left, Expr right, int k, BasicBlock block, boolean isLessThan) {
- this.getOperand().(GuardCondition).ensuresLt(left, right, k, block, isLessThan.booleanNot())
- }
-
- override predicate comparesEq(Expr left, Expr right, int k, boolean areEqual, boolean testIsTrue) {
- this.getOperand().(GuardCondition).comparesEq(left, right, k, areEqual, testIsTrue.booleanNot())
- }
-
- override predicate ensuresEq(Expr left, Expr right, int k, BasicBlock block, boolean areEqual) {
- this.getOperand().(GuardCondition).ensuresEq(left, right, k, block, areEqual.booleanNot())
- }
-}
-
/**
* A Boolean condition in the AST that guards one or more basic blocks and has a corresponding IR
* instruction.
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowPrivate.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowPrivate.qll
index 9548ff68074..7b1a9ca3123 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowPrivate.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowPrivate.qll
@@ -645,6 +645,24 @@ class GlobalLikeVariable extends Variable {
}
}
+/**
+ * Returns the smallest indirection for the type `t`.
+ *
+ * For most types this is `1`, but for `ArrayType`s (which are allocated on
+ * the stack) this is `0`
+ */
+int getMinIndirectionsForType(Type t) {
+ if t.getUnspecifiedType() instanceof Cpp::ArrayType then result = 0 else result = 1
+}
+
+private int getMinIndirectionForGlobalUse(Ssa::GlobalUse use) {
+ result = getMinIndirectionsForType(use.getUnspecifiedType())
+}
+
+private int getMinIndirectionForGlobalDef(Ssa::GlobalDef def) {
+ result = getMinIndirectionsForType(def.getUnspecifiedType())
+}
+
/**
* Holds if data can flow from `node1` to `node2` in a way that loses the
* calling context. For example, this would happen with flow through a
@@ -656,7 +674,7 @@ predicate jumpStep(Node n1, Node n2) {
v = globalUse.getVariable() and
n1.(FinalGlobalValue).getGlobalUse() = globalUse
|
- globalUse.getIndirection() = 1 and
+ globalUse.getIndirection() = getMinIndirectionForGlobalUse(globalUse) and
v = n2.asVariable()
or
v = n2.asIndirectVariable(globalUse.getIndirection())
@@ -666,7 +684,7 @@ predicate jumpStep(Node n1, Node n2) {
v = globalDef.getVariable() and
n2.(InitialGlobalValue).getGlobalDef() = globalDef
|
- globalDef.getIndirection() = 1 and
+ globalDef.getIndirection() = getMinIndirectionForGlobalDef(globalDef) and
v = n1.asVariable()
or
v = n1.asIndirectVariable(globalDef.getIndirection())
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowUtil.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowUtil.qll
index 50b374c5b04..07015db1c08 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowUtil.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/DataFlowUtil.qll
@@ -34,7 +34,8 @@ cached
private newtype TIRDataFlowNode =
TNode0(Node0Impl node) { DataFlowImplCommon::forceCachingInSameStage() } or
TVariableNode(Variable var, int indirectionIndex) {
- indirectionIndex = [1 .. Ssa::getMaxIndirectionsForType(var.getUnspecifiedType())]
+ indirectionIndex =
+ [getMinIndirectionsForType(var.getUnspecifiedType()) .. Ssa::getMaxIndirectionsForType(var.getUnspecifiedType())]
} or
TPostFieldUpdateNode(FieldAddress operand, int indirectionIndex) {
indirectionIndex =
@@ -346,7 +347,9 @@ class Node extends TIRDataFlowNode {
* Gets the variable corresponding to this node, if any. This can be used for
* modeling flow in and out of global variables.
*/
- Variable asVariable() { this = TVariableNode(result, 1) }
+ Variable asVariable() {
+ this = TVariableNode(result, getMinIndirectionsForType(result.getUnspecifiedType()))
+ }
/**
* Gets the `indirectionIndex`'th indirection of this node's underlying variable, if any.
@@ -354,7 +357,7 @@ class Node extends TIRDataFlowNode {
* This can be used for modeling flow in and out of global variables.
*/
Variable asIndirectVariable(int indirectionIndex) {
- indirectionIndex > 1 and
+ indirectionIndex > getMinIndirectionsForType(result.getUnspecifiedType()) and
this = TVariableNode(result, indirectionIndex)
}
@@ -1273,31 +1276,90 @@ abstract private class IndirectExprNodeBase extends Node {
}
}
-private class IndirectOperandIndirectExprNode extends IndirectExprNodeBase instanceof IndirectOperand
-{
- IndirectOperandIndirectExprNode() {
- exists(Expr e, int n, int indirectionIndex |
- indirectExprNodeShouldBeIndirectOperand(this, e, n, indirectionIndex) and
- not indirectExprNodeShouldBeIndirectOperand(_, e, n + 1, indirectionIndex)
- )
+/** A signature for converting an indirect node to an expression. */
+private signature module IndirectNodeToIndirectExprSig {
+ /** The indirect node class to be converted to an expression */
+ class IndirectNode;
+
+ /**
+ * Holds if the indirect expression at indirection index `indirectionIndex`
+ * of `node` is `e`. The integer `n` specifies how many conversions has been
+ * applied to `node`.
+ */
+ predicate indirectNodeHasIndirectExpr(IndirectNode node, Expr e, int n, int indirectionIndex);
+}
+
+/**
+ * A module that implements the logic for deciding whether an indirect node
+ * should be an `IndirectExprNode`.
+ */
+private module IndirectNodeToIndirectExpr {
+ import Sig
+
+ /**
+ * This predicate shifts the indirection index by one when `conv` is a
+ * `ReferenceDereferenceExpr`.
+ *
+ * This is necessary because `ReferenceDereferenceExpr` is a conversion
+ * in the AST, but appears as a `LoadInstruction` in the IR.
+ */
+ bindingset[e, indirectionIndex]
+ private predicate adjustForReference(
+ Expr e, int indirectionIndex, Expr conv, int adjustedIndirectionIndex
+ ) {
+ conv.(ReferenceDereferenceExpr).getExpr() = e and
+ adjustedIndirectionIndex = indirectionIndex - 1
+ or
+ not conv instanceof ReferenceDereferenceExpr and
+ conv = e and
+ adjustedIndirectionIndex = indirectionIndex
}
- final override Expr getConvertedExpr(int n, int index) {
- indirectExprNodeShouldBeIndirectOperand(this, result, n, index)
+ /** Holds if `node` should be an `IndirectExprNode`. */
+ predicate charpred(IndirectNode node) {
+ exists(Expr e, int n, int indirectionIndex |
+ indirectNodeHasIndirectExpr(node, e, n, indirectionIndex) and
+ not exists(Expr conv, int adjustedIndirectionIndex |
+ adjustForReference(e, indirectionIndex, conv, adjustedIndirectionIndex) and
+ indirectNodeHasIndirectExpr(_, conv, n + 1, adjustedIndirectionIndex)
+ )
+ )
}
}
-private class IndirectInstructionIndirectExprNode extends IndirectExprNodeBase instanceof IndirectInstruction
+private module IndirectOperandIndirectExprNodeImpl implements IndirectNodeToIndirectExprSig {
+ class IndirectNode = IndirectOperand;
+
+ predicate indirectNodeHasIndirectExpr = indirectExprNodeShouldBeIndirectOperand/4;
+}
+
+module IndirectOperandToIndirectExpr =
+ IndirectNodeToIndirectExpr;
+
+private class IndirectOperandIndirectExprNode extends IndirectExprNodeBase instanceof IndirectOperand
{
- IndirectInstructionIndirectExprNode() {
- exists(Expr e, int n, int indirectionIndex |
- indirectExprNodeShouldBeIndirectInstruction(this, e, n, indirectionIndex) and
- not indirectExprNodeShouldBeIndirectInstruction(_, e, n + 1, indirectionIndex)
- )
- }
+ IndirectOperandIndirectExprNode() { IndirectOperandToIndirectExpr::charpred(this) }
final override Expr getConvertedExpr(int n, int index) {
- indirectExprNodeShouldBeIndirectInstruction(this, result, n, index)
+ IndirectOperandToIndirectExpr::indirectNodeHasIndirectExpr(this, result, n, index)
+ }
+}
+
+private module IndirectInstructionIndirectExprNodeImpl implements IndirectNodeToIndirectExprSig {
+ class IndirectNode = IndirectInstruction;
+
+ predicate indirectNodeHasIndirectExpr = indirectExprNodeShouldBeIndirectInstruction/4;
+}
+
+module IndirectInstructionToIndirectExpr =
+ IndirectNodeToIndirectExpr;
+
+private class IndirectInstructionIndirectExprNode extends IndirectExprNodeBase instanceof IndirectInstruction
+{
+ IndirectInstructionIndirectExprNode() { IndirectInstructionToIndirectExpr::charpred(this) }
+
+ final override Expr getConvertedExpr(int n, int index) {
+ IndirectInstructionToIndirectExpr::indirectNodeHasIndirectExpr(this, result, n, index)
}
}
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternals.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternals.qll
index 76741dfc5cc..5c0174be32d 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternals.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternals.qll
@@ -59,6 +59,9 @@ private module SourceVariables {
then result = base.getType()
else result = getTypeImpl(base.getType(), ind - 1)
}
+
+ /** Gets the location of this variable. */
+ Location getLocation() { result = this.getBaseVariable().getLocation() }
}
}
@@ -869,7 +872,7 @@ private predicate sourceVariableIsGlobal(
)
}
-private module SsaInput implements SsaImplCommon::InputSig {
+private module SsaInput implements SsaImplCommon::InputSig {
import InputSigCommon
import SourceVariables
@@ -1092,7 +1095,7 @@ class Def extends DefOrUse {
predicate isCertain() { defOrUse.isCertain() }
}
-private module SsaImpl = SsaImplCommon::Make;
+private module SsaImpl = SsaImplCommon::Make;
class PhiNode extends SsaImpl::DefinitionExt {
PhiNode() {
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternalsCommon.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternalsCommon.qll
index fc718693dbd..0ea5c45df4f 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternalsCommon.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/SsaInternalsCommon.qll
@@ -377,6 +377,9 @@ abstract private class AbstractBaseSourceVariable extends TBaseSourceVariable {
/** Gets a textual representation of this element. */
abstract string toString();
+ /** Gets the location of this variable. */
+ abstract Location getLocation();
+
/** Gets the type of this base source variable. */
final DataFlowType getType() { this.getLanguageType().hasUnspecifiedType(result, _) }
@@ -395,6 +398,8 @@ class BaseIRVariable extends AbstractBaseSourceVariable, TBaseIRVariable {
override string toString() { result = var.toString() }
+ override Location getLocation() { result = var.getLocation() }
+
override CppType getLanguageType() { result = var.getLanguageType() }
}
@@ -407,6 +412,8 @@ class BaseCallVariable extends AbstractBaseSourceVariable, TBaseCallVariable {
override string toString() { result = call.toString() }
+ override Location getLocation() { result = call.getLocation() }
+
override CppType getLanguageType() { result = getResultLanguageType(call) }
}
@@ -872,7 +879,7 @@ private module Cached {
upper = countIndirectionsForCppType(type) and
ind = ind0 + [lower .. upper] and
indirectionIndex = ind - (ind0 + lower) and
- (if type.hasType(any(Cpp::ArrayType arrayType), true) then lower = 0 else lower = 1)
+ lower = getMinIndirectionsForType(any(Type t | type.hasUnspecifiedType(t, _)))
)
}
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/TaintTrackingUtil.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/TaintTrackingUtil.qll
index fd4169edd7d..51b893ddb23 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/TaintTrackingUtil.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/TaintTrackingUtil.qll
@@ -72,6 +72,16 @@ private predicate operandToInstructionTaintStep(Operand opFrom, Instruction inst
or
instrTo.(FieldAddressInstruction).getField().getDeclaringType() instanceof Union
)
+ or
+ // Taint from int to boolean casts. This ensures that we have flow to `!x` in:
+ // ```cpp
+ // x = integer_source();
+ // if(!x) { ... }
+ // ```
+ exists(Operand zero |
+ zero.getDef().(ConstantValueInstruction).getValue() = "0" and
+ instrTo.(CompareNEInstruction).hasOperands(opFrom, zero)
+ )
}
/**
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/ssa0/SsaInternals.qll b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/ssa0/SsaInternals.qll
index fd27a4e354f..ce53005470d 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/ssa0/SsaInternals.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/dataflow/internal/ssa0/SsaInternals.qll
@@ -229,7 +229,7 @@ private class FinalParameterUse extends UseImpl, TFinalParameterUse {
override predicate isCertain() { any() }
}
-private module SsaInput implements SsaImplCommon::InputSig {
+private module SsaInput implements SsaImplCommon::InputSig {
import InputSigCommon
import SourceVariables
@@ -335,7 +335,7 @@ class Def extends DefOrUse {
predicate isIteratorDef() { defOrUse instanceof IteratorDef }
}
-private module SsaImpl = SsaImplCommon::Make;
+private module SsaImpl = SsaImplCommon::Make;
class PhiNode extends SsaImpl::DefinitionExt {
PhiNode() {
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/aliased_ssa/constant/ConstantAnalysis.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/aliased_ssa/constant/ConstantAnalysis.qll
index 76f52f8334a..47b744b3f7c 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/aliased_ssa/constant/ConstantAnalysis.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/aliased_ssa/constant/ConstantAnalysis.qll
@@ -12,6 +12,9 @@ int getConstantValue(Instruction instr) {
or
result = getConstantValue(instr.(CopyInstruction).getSourceValue())
or
+ getConstantValue(instr.(LogicalNotInstruction).getUnary()) != 0 and
+ result = 0
+ or
exists(PhiInstruction phi |
phi = instr and
result = unique(Operand op | op = phi.getAnInputOperand() | getConstantValue(op.getDef()))
@@ -26,28 +29,25 @@ private predicate binaryInstructionOperands(BinaryInstruction instr, int left, i
pragma[noinline]
private int getBinaryInstructionValue(BinaryInstruction instr) {
- exists(int left, int right |
- binaryInstructionOperands(instr, left, right) and
- (
- instr instanceof AddInstruction and result = add(left, right)
- or
- instr instanceof SubInstruction and result = sub(left, right)
- or
- instr instanceof MulInstruction and result = mul(left, right)
- or
- instr instanceof DivInstruction and result = div(left, right)
- or
- instr instanceof CompareEQInstruction and result = compareEQ(left, right)
- or
- instr instanceof CompareNEInstruction and result = compareNE(left, right)
- or
- instr instanceof CompareLTInstruction and result = compareLT(left, right)
- or
- instr instanceof CompareGTInstruction and result = compareGT(left, right)
- or
- instr instanceof CompareLEInstruction and result = compareLE(left, right)
- or
- instr instanceof CompareGEInstruction and result = compareGE(left, right)
- )
+ exists(int left, int right | binaryInstructionOperands(instr, left, right) |
+ instr instanceof AddInstruction and result = add(left, right)
+ or
+ instr instanceof SubInstruction and result = sub(left, right)
+ or
+ instr instanceof MulInstruction and result = mul(left, right)
+ or
+ instr instanceof DivInstruction and result = div(left, right)
+ or
+ instr instanceof CompareEQInstruction and result = compareEQ(left, right)
+ or
+ instr instanceof CompareNEInstruction and result = compareNE(left, right)
+ or
+ instr instanceof CompareLTInstruction and result = compareLT(left, right)
+ or
+ instr instanceof CompareGTInstruction and result = compareGT(left, right)
+ or
+ instr instanceof CompareLEInstruction and result = compareLE(left, right)
+ or
+ instr instanceof CompareGEInstruction and result = compareGE(left, right)
)
}
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/internal/TOperand.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/internal/TOperand.qll
index 8a330114fe9..048beec5424 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/internal/TOperand.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/internal/TOperand.qll
@@ -23,9 +23,8 @@ private module Internal {
newtype TOperand =
// RAW
TRegisterOperand(TRawInstruction useInstr, RegisterOperandTag tag, TRawInstruction defInstr) {
- defInstr = RawConstruction::getRegisterOperandDefinition(useInstr, tag) and
- not RawConstruction::isInCycle(useInstr) and
- strictcount(RawConstruction::getRegisterOperandDefinition(useInstr, tag)) = 1
+ defInstr = unique( | | RawConstruction::getRegisterOperandDefinition(useInstr, tag)) and
+ not RawConstruction::isInCycle(useInstr)
} or
// Placeholder for Phi and Chi operands in stages that don't have the corresponding instructions
TNoOperand() { none() } or
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/constant/ConstantAnalysis.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/constant/ConstantAnalysis.qll
index 76f52f8334a..47b744b3f7c 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/constant/ConstantAnalysis.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/constant/ConstantAnalysis.qll
@@ -12,6 +12,9 @@ int getConstantValue(Instruction instr) {
or
result = getConstantValue(instr.(CopyInstruction).getSourceValue())
or
+ getConstantValue(instr.(LogicalNotInstruction).getUnary()) != 0 and
+ result = 0
+ or
exists(PhiInstruction phi |
phi = instr and
result = unique(Operand op | op = phi.getAnInputOperand() | getConstantValue(op.getDef()))
@@ -26,28 +29,25 @@ private predicate binaryInstructionOperands(BinaryInstruction instr, int left, i
pragma[noinline]
private int getBinaryInstructionValue(BinaryInstruction instr) {
- exists(int left, int right |
- binaryInstructionOperands(instr, left, right) and
- (
- instr instanceof AddInstruction and result = add(left, right)
- or
- instr instanceof SubInstruction and result = sub(left, right)
- or
- instr instanceof MulInstruction and result = mul(left, right)
- or
- instr instanceof DivInstruction and result = div(left, right)
- or
- instr instanceof CompareEQInstruction and result = compareEQ(left, right)
- or
- instr instanceof CompareNEInstruction and result = compareNE(left, right)
- or
- instr instanceof CompareLTInstruction and result = compareLT(left, right)
- or
- instr instanceof CompareGTInstruction and result = compareGT(left, right)
- or
- instr instanceof CompareLEInstruction and result = compareLE(left, right)
- or
- instr instanceof CompareGEInstruction and result = compareGE(left, right)
- )
+ exists(int left, int right | binaryInstructionOperands(instr, left, right) |
+ instr instanceof AddInstruction and result = add(left, right)
+ or
+ instr instanceof SubInstruction and result = sub(left, right)
+ or
+ instr instanceof MulInstruction and result = mul(left, right)
+ or
+ instr instanceof DivInstruction and result = div(left, right)
+ or
+ instr instanceof CompareEQInstruction and result = compareEQ(left, right)
+ or
+ instr instanceof CompareNEInstruction and result = compareNE(left, right)
+ or
+ instr instanceof CompareLTInstruction and result = compareLT(left, right)
+ or
+ instr instanceof CompareGTInstruction and result = compareGT(left, right)
+ or
+ instr instanceof CompareLEInstruction and result = compareLE(left, right)
+ or
+ instr instanceof CompareGEInstruction and result = compareGE(left, right)
)
}
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedCondition.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedCondition.qll
index 30755f0f000..fd88e3f87cf 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedCondition.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedCondition.qll
@@ -77,24 +77,6 @@ class TranslatedParenthesisCondition extends TranslatedFlexibleCondition {
}
}
-class TranslatedNotCondition extends TranslatedFlexibleCondition {
- override NotExpr expr;
-
- override Instruction getChildTrueSuccessor(TranslatedCondition child) {
- child = this.getOperand() and
- result = this.getConditionContext().getChildFalseSuccessor(this)
- }
-
- override Instruction getChildFalseSuccessor(TranslatedCondition child) {
- child = this.getOperand() and
- result = this.getConditionContext().getChildTrueSuccessor(this)
- }
-
- override TranslatedCondition getOperand() {
- result = getTranslatedCondition(expr.getOperand().getFullyConverted())
- }
-}
-
abstract class TranslatedNativeCondition extends TranslatedCondition, TTranslatedNativeCondition {
TranslatedNativeCondition() { this = TTranslatedNativeCondition(expr) }
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedElement.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedElement.qll
index a0967ed9a77..8047e7886d1 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedElement.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/raw/internal/TranslatedElement.qll
@@ -190,10 +190,7 @@ private predicate isNativeCondition(Expr expr) {
* depending on context.
*/
private predicate isFlexibleCondition(Expr expr) {
- (
- expr instanceof ParenthesisExpr or
- expr instanceof NotExpr
- ) and
+ expr instanceof ParenthesisExpr and
usedAsCondition(expr) and
not isIRConstant(expr)
}
@@ -218,11 +215,6 @@ private predicate usedAsCondition(Expr expr) {
condExpr.getCondition().getFullyConverted() = expr and not condExpr.isTwoOperand()
)
or
- exists(NotExpr notExpr |
- notExpr.getOperand().getFullyConverted() = expr and
- usedAsCondition(notExpr)
- )
- or
exists(ParenthesisExpr paren |
paren.getExpr() = expr and
usedAsCondition(paren)
diff --git a/cpp/ql/lib/semmle/code/cpp/ir/implementation/unaliased_ssa/constant/ConstantAnalysis.qll b/cpp/ql/lib/semmle/code/cpp/ir/implementation/unaliased_ssa/constant/ConstantAnalysis.qll
index 76f52f8334a..47b744b3f7c 100644
--- a/cpp/ql/lib/semmle/code/cpp/ir/implementation/unaliased_ssa/constant/ConstantAnalysis.qll
+++ b/cpp/ql/lib/semmle/code/cpp/ir/implementation/unaliased_ssa/constant/ConstantAnalysis.qll
@@ -12,6 +12,9 @@ int getConstantValue(Instruction instr) {
or
result = getConstantValue(instr.(CopyInstruction).getSourceValue())
or
+ getConstantValue(instr.(LogicalNotInstruction).getUnary()) != 0 and
+ result = 0
+ or
exists(PhiInstruction phi |
phi = instr and
result = unique(Operand op | op = phi.getAnInputOperand() | getConstantValue(op.getDef()))
@@ -26,28 +29,25 @@ private predicate binaryInstructionOperands(BinaryInstruction instr, int left, i
pragma[noinline]
private int getBinaryInstructionValue(BinaryInstruction instr) {
- exists(int left, int right |
- binaryInstructionOperands(instr, left, right) and
- (
- instr instanceof AddInstruction and result = add(left, right)
- or
- instr instanceof SubInstruction and result = sub(left, right)
- or
- instr instanceof MulInstruction and result = mul(left, right)
- or
- instr instanceof DivInstruction and result = div(left, right)
- or
- instr instanceof CompareEQInstruction and result = compareEQ(left, right)
- or
- instr instanceof CompareNEInstruction and result = compareNE(left, right)
- or
- instr instanceof CompareLTInstruction and result = compareLT(left, right)
- or
- instr instanceof CompareGTInstruction and result = compareGT(left, right)
- or
- instr instanceof CompareLEInstruction and result = compareLE(left, right)
- or
- instr instanceof CompareGEInstruction and result = compareGE(left, right)
- )
+ exists(int left, int right | binaryInstructionOperands(instr, left, right) |
+ instr instanceof AddInstruction and result = add(left, right)
+ or
+ instr instanceof SubInstruction and result = sub(left, right)
+ or
+ instr instanceof MulInstruction and result = mul(left, right)
+ or
+ instr instanceof DivInstruction and result = div(left, right)
+ or
+ instr instanceof CompareEQInstruction and result = compareEQ(left, right)
+ or
+ instr instanceof CompareNEInstruction and result = compareNE(left, right)
+ or
+ instr instanceof CompareLTInstruction and result = compareLT(left, right)
+ or
+ instr instanceof CompareGTInstruction and result = compareGT(left, right)
+ or
+ instr instanceof CompareLEInstruction and result = compareLE(left, right)
+ or
+ instr instanceof CompareGEInstruction and result = compareGE(left, right)
)
}
diff --git a/cpp/ql/lib/semmle/code/cpp/models/implementations/Getenv.qll b/cpp/ql/lib/semmle/code/cpp/models/implementations/Getenv.qll
index 256b1a86ed5..c9299de368b 100644
--- a/cpp/ql/lib/semmle/code/cpp/models/implementations/Getenv.qll
+++ b/cpp/ql/lib/semmle/code/cpp/models/implementations/Getenv.qll
@@ -16,10 +16,7 @@ class Getenv extends LocalFlowSourceFunction {
}
override predicate hasLocalFlowSource(FunctionOutput output, string description) {
- (
- output.isReturnValueDeref() or
- output.isReturnValue()
- ) and
+ output.isReturnValueDeref() and
description = "an environment variable"
}
}
diff --git a/cpp/ql/lib/semmle/code/cpp/models/implementations/Gets.qll b/cpp/ql/lib/semmle/code/cpp/models/implementations/Gets.qll
index b2437ed8b1c..1c227684e4f 100644
--- a/cpp/ql/lib/semmle/code/cpp/models/implementations/Gets.qll
+++ b/cpp/ql/lib/semmle/code/cpp/models/implementations/Gets.qll
@@ -51,7 +51,6 @@ private class FgetsFunction extends DataFlowFunction, TaintFunction, ArrayFuncti
override predicate hasRemoteFlowSource(FunctionOutput output, string description) {
(
output.isParameterDeref(0) or
- output.isReturnValue() or
output.isReturnValueDeref()
) and
description = "string read by " + this.getName()
@@ -102,7 +101,6 @@ private class GetsFunction extends DataFlowFunction, ArrayFunction, AliasFunctio
override predicate hasLocalFlowSource(FunctionOutput output, string description) {
(
output.isParameterDeref(0) or
- output.isReturnValue() or
output.isReturnValueDeref()
) and
description = "string read by " + this.getName()
diff --git a/cpp/ql/lib/semmle/code/cpp/models/implementations/StdContainer.qll b/cpp/ql/lib/semmle/code/cpp/models/implementations/StdContainer.qll
index 9d74f4ac051..1fb42010caf 100644
--- a/cpp/ql/lib/semmle/code/cpp/models/implementations/StdContainer.qll
+++ b/cpp/ql/lib/semmle/code/cpp/models/implementations/StdContainer.qll
@@ -123,7 +123,7 @@ private class StdSequenceContainerData extends TaintFunction {
/**
* The standard container functions `push_back` and `push_front`.
*/
-private class StdSequenceContainerPush extends TaintFunction {
+class StdSequenceContainerPush extends MemberFunction {
StdSequenceContainerPush() {
this.getClassAndName("push_back") instanceof Vector or
this.getClassAndName(["push_back", "push_front"]) instanceof Deque or
@@ -131,6 +131,17 @@ private class StdSequenceContainerPush extends TaintFunction {
this.getClassAndName(["push_back", "push_front"]) instanceof List
}
+ /**
+ * Gets the index of a parameter to this function that is a reference to the
+ * value type of the container.
+ */
+ int getAValueTypeParameterIndex() {
+ this.getParameter(result).getUnspecifiedType().(ReferenceType).getBaseType() =
+ this.getDeclaringType().getTemplateArgument(0).(Type).getUnspecifiedType() // i.e. the `T` of this `std::vector`
+ }
+}
+
+private class StdSequenceContainerPushModel extends StdSequenceContainerPush, TaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from parameter to qualifier
input.isParameterDeref(0) and
@@ -160,7 +171,7 @@ private class StdSequenceContainerFrontBack extends TaintFunction {
/**
* The standard container functions `insert` and `insert_after`.
*/
-private class StdSequenceContainerInsert extends TaintFunction {
+class StdSequenceContainerInsert extends MemberFunction {
StdSequenceContainerInsert() {
this.getClassAndName("insert") instanceof Deque or
this.getClassAndName("insert") instanceof List or
@@ -181,7 +192,9 @@ private class StdSequenceContainerInsert extends TaintFunction {
* Gets the index of a parameter to this function that is an iterator.
*/
int getAnIteratorParameterIndex() { this.getParameter(result).getType() instanceof Iterator }
+}
+private class StdSequenceContainerInsertModel extends StdSequenceContainerInsert, TaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from parameter to container itself (qualifier) and return value
(
@@ -253,11 +266,28 @@ private class StdSequenceContainerAt extends TaintFunction {
}
/**
- * The standard vector `emplace` function.
+ * The standard `emplace` function.
*/
-class StdVectorEmplace extends TaintFunction {
- StdVectorEmplace() { this.getClassAndName("emplace") instanceof Vector }
+class StdSequenceEmplace extends MemberFunction {
+ StdSequenceEmplace() {
+ this.getClassAndName("emplace") instanceof Vector
+ or
+ this.getClassAndName("emplace") instanceof List
+ or
+ this.getClassAndName("emplace") instanceof Deque
+ }
+ /**
+ * Gets the index of a parameter to this function that is a reference to the
+ * value type of the container.
+ */
+ int getAValueTypeParameterIndex() {
+ this.getParameter(result).getUnspecifiedType().(ReferenceType).getBaseType() =
+ this.getDeclaringType().getTemplateArgument(0).(Type).getUnspecifiedType() // i.e. the `T` of this `std::vector`
+ }
+}
+
+private class StdSequenceEmplaceModel extends StdSequenceEmplace, TaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from any parameter except the position iterator to qualifier and return value
// (here we assume taint flow from any constructor parameter to the constructed object)
@@ -269,12 +299,36 @@ class StdVectorEmplace extends TaintFunction {
}
}
+/**
+ * The standard vector `emplace` function.
+ */
+class StdVectorEmplace extends StdSequenceEmplace {
+ StdVectorEmplace() { this.getDeclaringType() instanceof Vector }
+}
+
/**
* The standard vector `emplace_back` function.
*/
-class StdVectorEmplaceBack extends TaintFunction {
- StdVectorEmplaceBack() { this.getClassAndName("emplace_back") instanceof Vector }
+class StdSequenceEmplaceBack extends MemberFunction {
+ StdSequenceEmplaceBack() {
+ this.getClassAndName("emplace_back") instanceof Vector
+ or
+ this.getClassAndName("emplace_back") instanceof List
+ or
+ this.getClassAndName("emplace_back") instanceof Deque
+ }
+ /**
+ * Gets the index of a parameter to this function that is a reference to the
+ * value type of the container.
+ */
+ int getAValueTypeParameterIndex() {
+ this.getParameter(result).getUnspecifiedType().(ReferenceType).getBaseType() =
+ this.getDeclaringType().getTemplateArgument(0).(Type).getUnspecifiedType() // i.e. the `T` of this `std::vector`
+ }
+}
+
+private class StdSequenceEmplaceBackModel extends StdSequenceEmplaceBack, TaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from any parameter to qualifier
// (here we assume taint flow from any constructor parameter to the constructed object)
@@ -282,3 +336,10 @@ class StdVectorEmplaceBack extends TaintFunction {
output.isQualifierObject()
}
}
+
+/**
+ * The standard vector `emplace_back` function.
+ */
+class StdVectorEmplaceBack extends StdSequenceEmplaceBack {
+ StdVectorEmplaceBack() { this.getDeclaringType() instanceof Vector }
+}
diff --git a/cpp/ql/lib/semmle/code/cpp/models/implementations/StdString.qll b/cpp/ql/lib/semmle/code/cpp/models/implementations/StdString.qll
index 225422b9a46..9ddf87085df 100644
--- a/cpp/ql/lib/semmle/code/cpp/models/implementations/StdString.qll
+++ b/cpp/ql/lib/semmle/code/cpp/models/implementations/StdString.qll
@@ -99,9 +99,11 @@ private class StdStringConstructor extends Constructor, StdStringTaintFunction {
/**
* The `std::string` function `c_str`.
*/
-private class StdStringCStr extends StdStringTaintFunction {
+class StdStringCStr extends MemberFunction {
StdStringCStr() { this.getClassAndName("c_str") instanceof StdBasicString }
+}
+private class StdStringCStrModel extends StdStringCStr, StdStringTaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from string itself (qualifier) to return value
input.isQualifierObject() and
@@ -112,9 +114,11 @@ private class StdStringCStr extends StdStringTaintFunction {
/**
* The `std::string` function `data`.
*/
-private class StdStringData extends StdStringTaintFunction {
+class StdStringData extends MemberFunction {
StdStringData() { this.getClassAndName("data") instanceof StdBasicString }
+}
+private class StdStringDataModel extends StdStringData, StdStringTaintFunction {
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
// flow from string itself (qualifier) to return value
input.isQualifierObject() and
diff --git a/cpp/ql/lib/semmlecode.cpp.dbscheme b/cpp/ql/lib/semmlecode.cpp.dbscheme
index 8cba93a4418..0a9eb01d365 100644
--- a/cpp/ql/lib/semmlecode.cpp.dbscheme
+++ b/cpp/ql/lib/semmlecode.cpp.dbscheme
@@ -405,6 +405,8 @@ function_deleted(unique int id: @function ref);
function_defaulted(unique int id: @function ref);
+function_prototyped(unique int id: @function ref)
+
member_function_this_type(
unique int id: @function ref,
int this_type: @type ref
diff --git a/cpp/ql/lib/semmlecode.cpp.dbscheme.stats b/cpp/ql/lib/semmlecode.cpp.dbscheme.stats
index bd755b1cba1..35ffe97c708 100644
--- a/cpp/ql/lib/semmlecode.cpp.dbscheme.stats
+++ b/cpp/ql/lib/semmlecode.cpp.dbscheme.stats
@@ -24,14 +24,14 @@
@location_stmt
3814079
-
- @diagnostic
- 5200
-
@location_expr
13167909
+
+ @diagnostic
+ 5200
+
@file
122996
@@ -66,7 +66,7 @@
@namespace_decl
- 308602
+ 308610
@using
@@ -74,7 +74,7 @@
@static_assert
- 133390
+ 133393
@parameter
@@ -82,7 +82,7 @@
@membervariable
- 1077872
+ 1053094
@globalvariable
@@ -90,11 +90,11 @@
@localvariable
- 581158
+ 581156
@enumconstant
- 248647
+ 241303
@errortype
@@ -370,7 +370,7 @@
@type_mention
- 4060812
+ 4023013
@routinetype
@@ -390,11 +390,11 @@
@stdattribute
- 491264
+ 491320
@declspec
- 244509
+ 243362
@msattribute
@@ -434,7 +434,7 @@
@comment
- 8760472
+ 8761469
@namespace
@@ -454,12 +454,112 @@
@initialiser
- 1698613
+ 1698635
@lambdacapture
27953
+
+ @stmt_expr
+ 1483766
+
+
+ @stmt_if
+ 724811
+
+
+ @stmt_while
+ 29372
+
+
+ @stmt_goto
+ 110523
+
+
+ @stmt_label
+ 53061
+
+
+ @stmt_return
+ 1283543
+
+
+ @stmt_block
+ 1422380
+
+
+ @stmt_end_test_while
+ 148648
+
+
+ @stmt_for
+ 61463
+
+
+ @stmt_switch_case
+ 209381
+
+
+ @stmt_switch
+ 20755
+
+
+ @stmt_asm
+ 109816
+
+
+ @stmt_decl
+ 592150
+
+
+ @stmt_empty
+ 193307
+
+
+ @stmt_continue
+ 22528
+
+
+ @stmt_break
+ 102247
+
+
+ @stmt_try_block
+ 46863
+
+
+ @stmt_microsoft_try
+ 163
+
+
+ @stmt_set_vla_size
+ 26
+
+
+ @stmt_vla_decl
+ 22
+
+
+ @stmt_assigned_goto
+ 9061
+
+
+ @stmt_range_based_for
+ 8386
+
+
+ @stmt_handler
+ 65232
+
+
+ @stmt_constexpr_if
+ 52432
+
+
+ @stmt_co_return
+ 2
+
@address_of
438815
@@ -542,7 +642,7 @@
@pdiffexpr
- 35403
+ 35407
@lshiftexpr
@@ -582,7 +682,7 @@
@geexpr
- 59287
+ 59159
@leexpr
@@ -650,11 +750,11 @@
@commaexpr
- 123860
+ 123874
@subscriptexpr
- 367573
+ 367572
@callexpr
@@ -794,7 +894,7 @@
@thisaccess
- 1126135
+ 1126162
@new_expr
@@ -958,11 +1058,11 @@
@reinterpret_cast
- 30704
+ 30707
@const_cast
- 35194
+ 35198
@dynamic_cast
@@ -1038,7 +1138,7 @@
@isnothrowconstructibleexpr
- 14412
+ 14413
@hasfinalizerexpr
@@ -1248,106 +1348,6 @@
@isvolatile
2
-
- @stmt_expr
- 1483766
-
-
- @stmt_if
- 724811
-
-
- @stmt_while
- 29372
-
-
- @stmt_goto
- 110523
-
-
- @stmt_label
- 53061
-
-
- @stmt_return
- 1283543
-
-
- @stmt_block
- 1422380
-
-
- @stmt_end_test_while
- 148648
-
-
- @stmt_for
- 61463
-
-
- @stmt_switch_case
- 209381
-
-
- @stmt_switch
- 20755
-
-
- @stmt_asm
- 109816
-
-
- @stmt_decl
- 592150
-
-
- @stmt_empty
- 193308
-
-
- @stmt_continue
- 22528
-
-
- @stmt_break
- 102257
-
-
- @stmt_try_block
- 46863
-
-
- @stmt_microsoft_try
- 163
-
-
- @stmt_set_vla_size
- 26
-
-
- @stmt_vla_decl
- 22
-
-
- @stmt_assigned_goto
- 9061
-
-
- @stmt_range_based_for
- 8386
-
-
- @stmt_handler
- 65232
-
-
- @stmt_constexpr_if
- 52426
-
-
- @stmt_co_return
- 2
-
@ppd_if
665765
@@ -1378,7 +1378,7 @@
@ppd_define
- 2429484
+ 2429760
@ppd_undef
@@ -1398,7 +1398,7 @@
@ppd_pragma
- 311531
+ 311566
@ppd_objc_import
@@ -2036,7 +2036,7 @@
seconds
- 12884
+ 14600
@@ -2117,16 +2117,16 @@
3
4
- 398
+ 279
4
5
- 598
+ 718
6
- 8
+ 9
159
@@ -2137,31 +2137,26 @@
10
11
- 119
+ 159
11
- 12
- 119
-
-
- 13
- 17
+ 15
159
- 17
- 18
- 79
+ 16
+ 19
+ 159
20
- 27
+ 26
159
- 44
- 118
+ 45
+ 134
119
@@ -2230,12 +2225,12 @@
3
4
- 718
+ 638
4
5
- 1037
+ 1116
5
@@ -2245,32 +2240,32 @@
6
7
- 398
+ 319
7
8
- 159
+ 239
8
9
- 159
+ 79
9
- 12
+ 10
279
- 13
- 42
+ 11
+ 27
279
- 44
- 96
- 119
+ 29
+ 100
+ 199
@@ -2316,8 +2311,8 @@
12
- 3
- 4
+ 4
+ 5
39
@@ -2326,13 +2321,13 @@
39
- 160
- 161
+ 177
+ 178
39
- 165
- 166
+ 190
+ 191
39
@@ -2349,7 +2344,7 @@
1
2
- 8018
+ 10012
2
@@ -2359,12 +2354,12 @@
3
4
- 1116
+ 1037
4
- 46
- 678
+ 44
+ 478
@@ -2380,22 +2375,22 @@
1
2
- 6901
+ 9414
2
3
- 3390
+ 3071
3
4
- 1755
+ 1316
4
75
- 837
+ 797
@@ -2411,7 +2406,7 @@
1
2
- 12525
+ 14241
2
@@ -2760,7 +2755,7 @@
cpu_seconds
- 6938
+ 7140
elapsed_seconds
@@ -2810,22 +2805,17 @@
1
2
- 5465
+ 5667
2
3
- 933
+ 1023
3
- 10
- 528
-
-
- 16
- 17
- 11
+ 14
+ 449
@@ -2841,12 +2831,12 @@
1
2
- 6286
+ 6522
2
3
- 652
+ 618
@@ -2862,56 +2852,51 @@
1
2
- 22
+ 11
2
3
+ 33
+
+
+ 7
+ 8
11
- 3
- 4
+ 11
+ 12
11
- 8
- 9
+ 12
+ 13
11
- 9
- 10
+ 21
+ 22
11
- 10
- 11
+ 120
+ 121
11
- 33
- 34
+ 180
+ 181
11
- 101
- 102
+ 243
+ 244
11
- 185
- 186
- 11
-
-
- 249
- 250
- 11
-
-
- 261
- 262
+ 262
+ 263
11
@@ -2928,56 +2913,51 @@
1
2
- 22
+ 11
2
3
+ 33
+
+
+ 7
+ 8
11
- 3
- 4
+ 11
+ 12
11
- 8
- 9
+ 12
+ 13
11
- 9
- 10
+ 21
+ 22
11
- 10
- 11
+ 114
+ 115
11
- 32
- 33
+ 133
+ 134
11
- 92
- 93
+ 167
+ 168
11
- 135
- 136
- 11
-
-
- 160
- 161
- 11
-
-
- 222
- 223
+ 218
+ 219
11
@@ -12327,7 +12307,7 @@
2
3
- 543317
+ 543324
3
@@ -12362,7 +12342,7 @@
11
337
- 224529
+ 224522
339
@@ -14098,11 +14078,11 @@
purefunctions
- 99968
+ 99971
id
- 99968
+ 99971
@@ -14129,6 +14109,17 @@
+
+ function_prototyped
+ 4549008
+
+
+ id
+ 4549008
+
+
+
+
member_function_this_type
552359
@@ -14980,15 +14971,15 @@
fun_decl_noexcept
- 61094
+ 61101
fun_decl
- 61094
+ 61101
constant
- 60990
+ 60997
@@ -15002,7 +14993,7 @@
1
2
- 61094
+ 61101
@@ -15018,7 +15009,7 @@
1
2
- 60885
+ 60892
2
@@ -16234,11 +16225,11 @@
namespace_decls
- 308602
+ 308610
id
- 308602
+ 308610
namespace_id
@@ -16246,11 +16237,11 @@
location
- 308602
+ 308610
bodylocation
- 308602
+ 308610
@@ -16264,7 +16255,7 @@
1
2
- 308602
+ 308610
@@ -16280,7 +16271,7 @@
1
2
- 308602
+ 308610
@@ -16296,7 +16287,7 @@
1
2
- 308602
+ 308610
@@ -16510,7 +16501,7 @@
1
2
- 308602
+ 308610
@@ -16526,7 +16517,7 @@
1
2
- 308602
+ 308610
@@ -16542,7 +16533,7 @@
1
2
- 308602
+ 308610
@@ -16558,7 +16549,7 @@
1
2
- 308602
+ 308610
@@ -16574,7 +16565,7 @@
1
2
- 308602
+ 308610
@@ -16590,7 +16581,7 @@
1
2
- 308602
+ 308610
@@ -16869,19 +16860,19 @@
static_asserts
- 133390
+ 133393
id
- 133390
+ 133393
condition
- 133390
+ 133393
message
- 29937
+ 29938
location
@@ -16889,7 +16880,7 @@
enclosing
- 4602
+ 4603
@@ -16903,7 +16894,7 @@
1
2
- 133390
+ 133393
@@ -16919,7 +16910,7 @@
1
2
- 133390
+ 133393
@@ -16935,7 +16926,7 @@
1
2
- 133390
+ 133393
@@ -16951,7 +16942,7 @@
1
2
- 133390
+ 133393
@@ -16967,7 +16958,7 @@
1
2
- 133390
+ 133393
@@ -16983,7 +16974,7 @@
1
2
- 133390
+ 133393
@@ -16999,7 +16990,7 @@
1
2
- 133390
+ 133393
@@ -17015,7 +17006,7 @@
1
2
- 133390
+ 133393
@@ -17149,7 +17140,7 @@
4
12
- 1439
+ 1440
12
@@ -17323,12 +17314,12 @@
1
2
- 3860
+ 3861
2
3
- 6218
+ 6219
3
@@ -17436,7 +17427,7 @@
2
3
- 370
+ 371
3
@@ -17973,15 +17964,15 @@
overrides
- 159844
+ 159848
new
- 125039
+ 125042
old
- 15097
+ 15098
@@ -17995,12 +17986,12 @@
1
2
- 90240
+ 90243
2
3
- 34792
+ 34793
3
@@ -18061,19 +18052,19 @@
membervariables
- 1079662
+ 1054889
id
- 1077872
+ 1053094
type_id
- 331092
+ 327229
name
- 462559
+ 450932
@@ -18087,12 +18078,12 @@
1
2
- 1076161
+ 1051379
2
4
- 1710
+ 1715
@@ -18108,7 +18099,7 @@
1
2
- 1077872
+ 1053094
@@ -18124,22 +18115,22 @@
1
2
- 245663
+ 242659
2
3
- 52443
+ 51818
3
10
- 25664
+ 25490
10
- 4335
- 7321
+ 4152
+ 7260
@@ -18155,22 +18146,22 @@
1
2
- 258157
+ 254866
2
3
- 46832
+ 46393
3
- 46
- 24908
+ 40
+ 24573
- 48
- 2128
- 1193
+ 41
+ 2031
+ 1396
@@ -18186,22 +18177,22 @@
1
2
- 303956
+ 294877
2
3
- 87657
+ 86404
3
5
- 41739
+ 41128
5
- 653
- 29205
+ 646
+ 28522
@@ -18217,17 +18208,17 @@
1
2
- 377607
+ 367280
2
3
- 52483
+ 51659
3
- 657
- 32468
+ 650
+ 31992
@@ -18408,11 +18399,11 @@
localvariables
- 581158
+ 581156
id
- 581158
+ 581156
type_id
@@ -18420,7 +18411,7 @@
name
- 91319
+ 91318
@@ -18434,7 +18425,7 @@
1
2
- 581158
+ 581156
@@ -18450,7 +18441,7 @@
1
2
- 581158
+ 581156
@@ -18466,7 +18457,7 @@
1
2
- 21188
+ 21187
2
@@ -18507,7 +18498,7 @@
1
2
- 26970
+ 26969
2
@@ -18599,11 +18590,11 @@
autoderivation
- 149133
+ 149150
var
- 149133
+ 149150
derivation_type
@@ -18621,7 +18612,7 @@
1
2
- 149133
+ 149150
@@ -18720,19 +18711,19 @@
enumconstants
- 248647
+ 241303
id
- 248647
+ 241303
parent
- 29683
+ 28482
index
- 10186
+ 10212
type_id
@@ -18740,11 +18731,11 @@
name
- 248369
+ 241024
location
- 228633
+ 221237
@@ -18758,7 +18749,7 @@
1
2
- 248647
+ 241303
@@ -18774,7 +18765,7 @@
1
2
- 248647
+ 241303
@@ -18790,7 +18781,7 @@
1
2
- 248647
+ 241303
@@ -18806,7 +18797,7 @@
1
2
- 248647
+ 241303
@@ -18822,7 +18813,7 @@
1
2
- 248647
+ 241303
@@ -18838,57 +18829,57 @@
1
2
- 1114
+ 997
2
3
- 4177
+ 4029
3
4
- 6087
+ 5784
4
5
- 4058
+ 3909
5
6
- 3262
+ 3071
6
7
- 1870
+ 1835
7
8
- 1432
+ 1475
8
- 10
- 2148
+ 11
+ 2592
- 10
- 15
- 2387
+ 11
+ 17
+ 2353
- 15
- 34
- 2307
+ 17
+ 84
+ 2154
- 35
+ 94
257
- 835
+ 279
@@ -18904,57 +18895,57 @@
1
2
- 1114
+ 997
2
3
- 4177
+ 4029
3
4
- 6087
+ 5784
4
5
- 4058
+ 3909
5
6
- 3262
+ 3071
6
7
- 1870
+ 1835
7
8
- 1432
+ 1475
8
- 10
- 2148
+ 11
+ 2592
- 10
- 15
- 2387
+ 11
+ 17
+ 2353
- 15
- 34
- 2307
+ 17
+ 84
+ 2154
- 35
+ 94
257
- 835
+ 279
@@ -18970,7 +18961,7 @@
1
2
- 29683
+ 28482
@@ -18986,57 +18977,57 @@
1
2
- 1114
+ 997
2
3
- 4177
+ 4029
3
4
- 6087
+ 5784
4
5
- 4058
+ 3909
5
6
- 3262
+ 3071
6
7
- 1870
+ 1835
7
8
- 1432
+ 1475
8
- 10
- 2148
+ 11
+ 2592
- 10
- 15
- 2387
+ 11
+ 17
+ 2353
- 15
- 34
- 2307
+ 17
+ 84
+ 2154
- 35
+ 94
257
- 835
+ 279
@@ -19052,52 +19043,52 @@
1
2
- 1551
+ 1436
2
3
- 4337
+ 4188
3
4
- 6127
+ 5824
4
5
- 4018
+ 3869
5
6
- 3262
+ 3071
6
7
- 1830
+ 1795
7
8
- 1352
+ 1396
8
11
- 2705
+ 2513
11
- 18
- 2268
+ 17
+ 2233
- 18
+ 17
257
- 2228
+ 2154
@@ -19113,47 +19104,47 @@
1
2
- 2029
+ 2034
2
3
- 1631
+ 1635
3
4
- 1750
+ 1755
4
5
- 835
+ 877
5
9
- 795
+ 797
9
12
- 875
+ 837
12
20
- 835
+ 877
20
- 66
- 795
+ 69
+ 797
- 70
- 747
- 636
+ 77
+ 715
+ 598
@@ -19169,47 +19160,47 @@
1
2
- 2029
+ 2034
2
3
- 1631
+ 1635
3
4
- 1750
+ 1755
4
5
- 835
+ 877
5
9
- 795
+ 797
9
12
- 875
+ 837
12
20
- 835
+ 877
20
- 66
- 795
+ 69
+ 797
- 70
- 747
- 636
+ 77
+ 715
+ 598
@@ -19225,7 +19216,7 @@
1
2
- 10186
+ 10212
@@ -19241,47 +19232,47 @@
1
2
- 2029
+ 2034
2
3
- 1631
+ 1635
3
4
- 1750
+ 1755
4
5
- 835
+ 877
5
9
- 795
+ 797
9
12
- 875
+ 837
12
20
- 835
+ 877
20
- 66
- 795
+ 69
+ 797
- 70
- 744
- 636
+ 77
+ 712
+ 598
@@ -19297,47 +19288,47 @@
1
2
- 2029
+ 2034
2
3
- 1631
+ 1635
3
4
- 1750
+ 1755
4
5
- 835
+ 877
5
9
- 795
+ 797
9
12
- 875
+ 837
12
20
- 835
+ 877
20
- 66
- 795
+ 69
+ 797
- 70
- 747
- 636
+ 77
+ 715
+ 598
@@ -19351,8 +19342,8 @@
12
- 6249
- 6250
+ 6049
+ 6050
39
@@ -19367,8 +19358,8 @@
12
- 746
- 747
+ 714
+ 715
39
@@ -19399,8 +19390,8 @@
12
- 6242
- 6243
+ 6042
+ 6043
39
@@ -19415,8 +19406,8 @@
12
- 5746
- 5747
+ 5546
+ 5547
39
@@ -19433,12 +19424,12 @@
1
2
- 248090
+ 240744
2
3
- 278
+ 279
@@ -19454,12 +19445,12 @@
1
2
- 248090
+ 240744
2
3
- 278
+ 279
@@ -19475,7 +19466,7 @@
1
2
- 248369
+ 241024
@@ -19491,7 +19482,7 @@
1
2
- 248369
+ 241024
@@ -19507,12 +19498,12 @@
1
2
- 248090
+ 240744
2
3
- 278
+ 279
@@ -19528,12 +19519,12 @@
1
2
- 227877
+ 220480
2
205
- 756
+ 757
@@ -19549,7 +19540,7 @@
1
2
- 228633
+ 221237
@@ -19565,12 +19556,12 @@
1
2
- 227877
+ 220480
2
205
- 756
+ 757
@@ -19586,7 +19577,7 @@
1
2
- 228633
+ 221237
@@ -19602,12 +19593,12 @@
1
2
- 227877
+ 220480
2
205
- 756
+ 757
@@ -21938,11 +21929,11 @@
usertype_final
- 9503
+ 9504
id
- 9503
+ 9504
@@ -21992,7 +21983,7 @@
2
3
- 370
+ 371
@@ -22647,19 +22638,19 @@
type_mentions
- 4060812
+ 4023013
id
- 4060812
+ 4023013
type_id
- 200223
+ 197901
location
- 4027428
+ 3989544
kind
@@ -22677,7 +22668,7 @@
1
2
- 4060812
+ 4023013
@@ -22693,7 +22684,7 @@
1
2
- 4060812
+ 4023013
@@ -22709,7 +22700,7 @@
1
2
- 4060812
+ 4023013
@@ -22725,42 +22716,42 @@
1
2
- 98918
+ 97454
2
3
- 22322
+ 21700
3
4
- 8196
+ 8217
4
5
- 10663
+ 10770
5
7
- 14642
+ 14360
7
12
- 15876
+ 15836
12
27
- 15160
+ 15158
27
- 8808
- 14443
+ 8555
+ 14400
@@ -22776,42 +22767,42 @@
1
2
- 98918
+ 97454
2
3
- 22322
+ 21700
3
4
- 8196
+ 8217
4
5
- 10663
+ 10770
5
7
- 14642
+ 14360
7
12
- 15876
+ 15836
12
27
- 15160
+ 15158
27
- 8808
- 14443
+ 8555
+ 14400
@@ -22827,7 +22818,7 @@
1
2
- 200223
+ 197901
@@ -22843,12 +22834,12 @@
1
2
- 3994044
+ 3956075
2
3
- 33383
+ 33468
@@ -22864,12 +22855,12 @@
1
2
- 3994044
+ 3956075
2
3
- 33383
+ 33468
@@ -22885,7 +22876,7 @@
1
2
- 4027428
+ 3989544
@@ -22899,8 +22890,8 @@
12
- 102056
- 102057
+ 100849
+ 100850
39
@@ -22915,8 +22906,8 @@
12
- 5032
- 5033
+ 4961
+ 4962
39
@@ -22931,8 +22922,8 @@
12
- 101217
- 101218
+ 100010
+ 100011
39
@@ -23529,26 +23520,26 @@
is_variable_template
- 47204
+ 47210
id
- 47204
+ 47210
variable_instantiation
- 172631
+ 172651
to
- 172631
+ 172651
from
- 25900
+ 25902
@@ -23562,7 +23553,7 @@
1
2
- 172631
+ 172651
@@ -23578,12 +23569,12 @@
1
2
- 13889
+ 13891
2
3
- 2610
+ 2611
3
@@ -23593,7 +23584,7 @@
4
6
- 1879
+ 1880
6
@@ -23623,11 +23614,11 @@
variable_template_argument
- 310904
+ 310940
variable_id
- 163441
+ 163460
index
@@ -23635,7 +23626,7 @@
arg_type
- 171274
+ 171293
@@ -23649,22 +23640,22 @@
1
2
- 83652
+ 83662
2
3
- 50860
+ 50865
3
4
- 18798
+ 18800
4
17
- 10130
+ 10131
@@ -23680,22 +23671,22 @@
1
2
- 88352
+ 88362
2
3
- 52113
+ 52119
3
4
- 13681
+ 13682
4
17
- 9294
+ 9295
@@ -23828,17 +23819,17 @@
1
2
- 137750
+ 137766
2
3
- 19529
+ 19531
3
23
- 12845
+ 12847
23
@@ -23859,12 +23850,12 @@
1
2
- 154251
+ 154268
2
3
- 14934
+ 14935
3
@@ -23879,11 +23870,11 @@
variable_template_argument_value
- 11905
+ 11907
variable_id
- 7832
+ 7833
index
@@ -23891,7 +23882,7 @@
arg_value
- 11905
+ 11907
@@ -23905,7 +23896,7 @@
1
2
- 7414
+ 7415
2
@@ -24014,7 +24005,7 @@
1
2
- 11905
+ 11907
@@ -24030,7 +24021,7 @@
1
2
- 11905
+ 11907
@@ -24927,11 +24918,11 @@
attributes
- 735121
+ 735205
id
- 735121
+ 735205
kind
@@ -24939,7 +24930,7 @@
name
- 1670
+ 1671
name_space
@@ -24947,7 +24938,7 @@
location
- 482701
+ 482756
@@ -24961,7 +24952,7 @@
1
2
- 735121
+ 735205
@@ -24977,7 +24968,7 @@
1
2
- 735121
+ 735205
@@ -24993,7 +24984,7 @@
1
2
- 735121
+ 735205
@@ -25009,7 +25000,7 @@
1
2
- 735121
+ 735205
@@ -25226,7 +25217,7 @@
1
2
- 1670
+ 1671
@@ -25402,17 +25393,17 @@
1
2
- 425157
+ 425205
2
3
- 36865
+ 36869
3
201
- 20678
+ 20680
@@ -25428,7 +25419,7 @@
1
2
- 482701
+ 482756
@@ -25444,12 +25435,12 @@
1
2
- 478419
+ 478473
2
3
- 4281
+ 4282
@@ -25465,7 +25456,7 @@
1
2
- 482701
+ 482756
@@ -26165,15 +26156,15 @@
typeattributes
- 84801
+ 84811
type_id
- 61930
+ 61937
spec_id
- 84801
+ 84811
@@ -26187,17 +26178,17 @@
1
2
- 55977
+ 55983
2
4
- 4281
+ 4282
12
13
- 1670
+ 1671
@@ -26213,7 +26204,7 @@
1
2
- 84801
+ 84811
@@ -28135,19 +28126,19 @@
comments
- 8760472
+ 8761469
id
- 8760472
+ 8761469
contents
- 3335045
+ 3335424
location
- 8760472
+ 8761469
@@ -28161,7 +28152,7 @@
1
2
- 8760472
+ 8761469
@@ -28177,7 +28168,7 @@
1
2
- 8760472
+ 8761469
@@ -28193,17 +28184,17 @@
1
2
- 3050980
+ 3051327
2
7
- 250540
+ 250569
7
32784
- 33523
+ 33527
@@ -28219,17 +28210,17 @@
1
2
- 3050980
+ 3051327
2
7
- 250540
+ 250569
7
32784
- 33523
+ 33527
@@ -28245,7 +28236,7 @@
1
2
- 8760472
+ 8761469
@@ -28261,7 +28252,7 @@
1
2
- 8760472
+ 8761469
@@ -29017,11 +29008,11 @@
expr_isload
- 5206008
+ 5206600
expr_id
- 5206008
+ 5206600
@@ -30393,19 +30384,19 @@
fieldoffsets
- 1077872
+ 1053094
id
- 1077872
+ 1053094
byteoffset
- 22879
+ 22658
bitoffset
- 318
+ 319
@@ -30419,7 +30410,7 @@
1
2
- 1077872
+ 1053094
@@ -30435,7 +30426,7 @@
1
2
- 1077872
+ 1053094
@@ -30451,37 +30442,37 @@
1
2
- 12891
+ 13004
2
3
- 1790
+ 1715
3
5
- 1949
+ 1795
5
12
- 1949
+ 1914
12
35
- 1750
+ 1715
35
- 209
- 1750
+ 205
+ 1715
- 248
- 5836
- 795
+ 244
+ 5638
+ 797
@@ -30497,12 +30488,12 @@
1
2
- 22202
+ 21980
2
9
- 676
+ 678
@@ -30516,18 +30507,28 @@
12
- 31
- 32
+ 29
+ 30
39
- 32
- 33
+ 30
+ 31
39
- 37
- 38
+ 33
+ 34
+ 39
+
+
+ 36
+ 37
+ 39
+
+
+ 42
+ 43
39
@@ -30536,23 +30537,13 @@
39
- 46
- 47
+ 55
+ 56
39
- 53
- 54
- 39
-
-
- 68
- 69
- 39
-
-
- 26779
- 26780
+ 26131
+ 26132
39
@@ -30569,7 +30560,7 @@
11
12
- 119
+ 159
12
@@ -30579,11 +30570,11 @@
13
14
- 79
+ 39
- 575
- 576
+ 568
+ 569
39
@@ -30594,19 +30585,19 @@
bitfield
- 20887
+ 20889
id
- 20887
+ 20889
bits
- 2610
+ 2611
declared_bits
- 2610
+ 2611
@@ -30620,7 +30611,7 @@
1
2
- 20887
+ 20889
@@ -30636,7 +30627,7 @@
1
2
- 20887
+ 20889
@@ -30703,7 +30694,7 @@
1
2
- 2610
+ 2611
@@ -30770,7 +30761,7 @@
1
2
- 2610
+ 2611
@@ -30780,23 +30771,23 @@
initialisers
- 1698613
+ 1698635
init
- 1698613
+ 1698635
var
- 722110
+ 722109
expr
- 1698613
+ 1698635
location
- 390813
+ 390823
@@ -30810,7 +30801,7 @@
1
2
- 1698613
+ 1698635
@@ -30826,7 +30817,7 @@
1
2
- 1698613
+ 1698635
@@ -30842,7 +30833,7 @@
1
2
- 1698613
+ 1698635
@@ -30858,17 +30849,17 @@
1
2
- 633988
+ 633984
2
16
- 31465
+ 31466
16
25
- 56656
+ 56657
@@ -30884,17 +30875,17 @@
1
2
- 633988
+ 633984
2
16
- 31465
+ 31466
16
25
- 56656
+ 56657
@@ -30910,7 +30901,7 @@
1
2
- 722104
+ 722102
2
@@ -30931,7 +30922,7 @@
1
2
- 1698613
+ 1698635
@@ -30947,7 +30938,7 @@
1
2
- 1698613
+ 1698635
@@ -30963,7 +30954,7 @@
1
2
- 1698613
+ 1698635
@@ -30979,17 +30970,17 @@
1
2
- 318443
+ 318451
2
3
- 23850
+ 23851
3
15
- 30679
+ 30680
15
@@ -31010,12 +31001,12 @@
1
2
- 341112
+ 341120
2
4
- 35641
+ 35642
4
@@ -31036,17 +31027,17 @@
1
2
- 318443
+ 318451
2
3
- 23850
+ 23851
3
15
- 30679
+ 30680
15
@@ -32874,7 +32865,7 @@
1
2
- 19744
+ 19745
2
@@ -34015,11 +34006,11 @@
stmts
- 4646337
+ 4646866
id
- 4646337
+ 4646866
kind
@@ -34027,7 +34018,7 @@
location
- 2281499
+ 2281758
@@ -34041,7 +34032,7 @@
1
2
- 4646337
+ 4646866
@@ -34057,7 +34048,7 @@
1
2
- 4646337
+ 4646866
@@ -34285,22 +34276,22 @@
1
2
- 1887672
+ 1887887
2
4
- 175556
+ 175576
4
12
- 175765
+ 175785
12
687
- 42505
+ 42510
@@ -34316,12 +34307,12 @@
1
2
- 2224372
+ 2224626
2
8
- 57126
+ 57132
@@ -34619,15 +34610,15 @@
constexpr_if_then
- 52426
+ 52432
constexpr_if_stmt
- 52426
+ 52432
then_id
- 52426
+ 52432
@@ -34641,7 +34632,7 @@
1
2
- 52426
+ 52432
@@ -34657,7 +34648,7 @@
1
2
- 52426
+ 52432
@@ -34667,15 +34658,15 @@
constexpr_if_else
- 30808
+ 30811
constexpr_if_stmt
- 30808
+ 30811
else_id
- 30808
+ 30811
@@ -34689,7 +34680,7 @@
1
2
- 30808
+ 30811
@@ -34705,7 +34696,7 @@
1
2
- 30808
+ 30811
@@ -35365,11 +35356,11 @@
stmtparents
- 4053248
+ 4053171
id
- 4053248
+ 4053171
index
@@ -35377,7 +35368,7 @@
parent
- 1719942
+ 1719896
@@ -35391,7 +35382,7 @@
1
2
- 4053248
+ 4053171
@@ -35407,7 +35398,7 @@
1
2
- 4053248
+ 4053171
@@ -35467,7 +35458,7 @@
77
- 196973
+ 196965
697
@@ -35528,7 +35519,7 @@
77
- 196973
+ 196965
697
@@ -35545,27 +35536,27 @@
1
2
- 987639
+ 987613
2
3
- 373043
+ 373033
3
4
- 105766
+ 105762
4
6
- 111262
+ 111258
6
17
- 129868
+ 129865
17
@@ -35586,27 +35577,27 @@
1
2
- 987639
+ 987613
2
3
- 373043
+ 373033
3
4
- 105766
+ 105762
4
6
- 111262
+ 111258
6
17
- 129868
+ 129865
17
@@ -35632,11 +35623,11 @@
stmt_decl_bind
- 585089
+ 585087
stmt
- 544976
+ 544974
num
@@ -35644,7 +35635,7 @@
decl
- 584984
+ 584982
@@ -35658,7 +35649,7 @@
1
2
- 524115
+ 524114
2
@@ -35679,7 +35670,7 @@
1
2
- 524115
+ 524114
2
@@ -35882,7 +35873,7 @@
1
2
- 584946
+ 584944
2
@@ -35903,7 +35894,7 @@
1
2
- 584984
+ 584982
@@ -35913,11 +35904,11 @@
stmt_decl_entry_bind
- 527550
+ 527548
stmt
- 487740
+ 487738
num
@@ -35925,7 +35916,7 @@
decl_entry
- 527491
+ 527490
@@ -35939,7 +35930,7 @@
1
2
- 467144
+ 467142
2
@@ -35960,7 +35951,7 @@
1
2
- 467144
+ 467142
2
@@ -36163,7 +36154,7 @@
1
2
- 527470
+ 527469
3
@@ -36184,7 +36175,7 @@
1
2
- 527491
+ 527490
@@ -36433,11 +36424,11 @@
preprocdirects
- 4420757
+ 4421260
id
- 4420757
+ 4421260
kind
@@ -36445,7 +36436,7 @@
location
- 4418250
+ 4418753
@@ -36459,7 +36450,7 @@
1
2
- 4420757
+ 4421260
@@ -36475,7 +36466,7 @@
1
2
- 4420757
+ 4421260
@@ -36613,7 +36604,7 @@
1
2
- 4418146
+ 4418648
25
@@ -36634,7 +36625,7 @@
1
2
- 4418250
+ 4418753
@@ -36724,19 +36715,19 @@
preproctext
- 3564176
+ 3564582
id
- 3564176
+ 3564582
head
- 2585406
+ 2585700
body
- 1512226
+ 1512398
@@ -36750,7 +36741,7 @@
1
2
- 3564176
+ 3564582
@@ -36766,7 +36757,7 @@
1
2
- 3564176
+ 3564582
@@ -36782,12 +36773,12 @@
1
2
- 2438674
+ 2438952
2
740
- 146731
+ 146748
@@ -36803,12 +36794,12 @@
1
2
- 2523371
+ 2523659
2
5
- 62034
+ 62041
@@ -36824,17 +36815,17 @@
1
2
- 1368941
+ 1369097
2
6
- 113417
+ 113429
6
11572
- 29868
+ 29871
@@ -36850,17 +36841,17 @@
1
2
- 1371969
+ 1372126
2
7
- 113730
+ 113743
7
2959
- 26526
+ 26529
diff --git a/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/old.dbscheme b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/old.dbscheme
new file mode 100644
index 00000000000..8cba93a4418
--- /dev/null
+++ b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/old.dbscheme
@@ -0,0 +1,2231 @@
+
+/**
+ * An invocation of the compiler. Note that more than one file may be
+ * compiled per invocation. For example, this command compiles three
+ * source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * The `id` simply identifies the invocation, while `cwd` is the working
+ * directory from which the compiler was invoked.
+ */
+compilations(
+ /**
+ * An invocation of the compiler. Note that more than one file may
+ * be compiled per invocation. For example, this command compiles
+ * three source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ */
+ unique int id : @compilation,
+ string cwd : string ref
+);
+
+/**
+ * The arguments that were passed to the extractor for a compiler
+ * invocation. If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then typically there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | *path to extractor*
+ * 1 | `--mimic`
+ * 2 | `/usr/bin/gcc`
+ * 3 | `-c`
+ * 4 | f1.c
+ * 5 | f2.c
+ * 6 | f3.c
+ */
+#keyset[id, num]
+compilation_args(
+ int id : @compilation ref,
+ int num : int ref,
+ string arg : string ref
+);
+
+/**
+ * The source files that are compiled by a compiler invocation.
+ * If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | f1.c
+ * 1 | f2.c
+ * 2 | f3.c
+ *
+ * Note that even if those files `#include` headers, those headers
+ * do not appear as rows.
+ */
+#keyset[id, num]
+compilation_compiling_files(
+ int id : @compilation ref,
+ int num : int ref,
+ int file : @file ref
+);
+
+/**
+ * The time taken by the extractor for a compiler invocation.
+ *
+ * For each file `num`, there will be rows for
+ *
+ * kind | seconds
+ * ---- | ---
+ * 1 | CPU seconds used by the extractor frontend
+ * 2 | Elapsed seconds during the extractor frontend
+ * 3 | CPU seconds used by the extractor backend
+ * 4 | Elapsed seconds during the extractor backend
+ */
+#keyset[id, num, kind]
+compilation_time(
+ int id : @compilation ref,
+ int num : int ref,
+ /* kind:
+ 1 = frontend_cpu_seconds
+ 2 = frontend_elapsed_seconds
+ 3 = extractor_cpu_seconds
+ 4 = extractor_elapsed_seconds
+ */
+ int kind : int ref,
+ float seconds : float ref
+);
+
+/**
+ * An error or warning generated by the extractor.
+ * The diagnostic message `diagnostic` was generated during compiler
+ * invocation `compilation`, and is the `file_number_diagnostic_number`th
+ * message generated while extracting the `file_number`th file of that
+ * invocation.
+ */
+#keyset[compilation, file_number, file_number_diagnostic_number]
+diagnostic_for(
+ int diagnostic : @diagnostic ref,
+ int compilation : @compilation ref,
+ int file_number : int ref,
+ int file_number_diagnostic_number : int ref
+);
+
+/**
+ * If extraction was successful, then `cpu_seconds` and
+ * `elapsed_seconds` are the CPU time and elapsed time (respectively)
+ * that extraction took for compiler invocation `id`.
+ */
+compilation_finished(
+ unique int id : @compilation ref,
+ float cpu_seconds : float ref,
+ float elapsed_seconds : float ref
+);
+
+
+/**
+ * External data, loaded from CSV files during snapshot creation. See
+ * [Tutorial: Incorporating external data](https://help.semmle.com/wiki/display/SD/Tutorial%3A+Incorporating+external+data)
+ * for more information.
+ */
+externalData(
+ int id : @externalDataElement,
+ string path : string ref,
+ int column: int ref,
+ string value : string ref
+);
+
+/**
+ * The source location of the snapshot.
+ */
+sourceLocationPrefix(string prefix : string ref);
+
+/**
+ * Information about packages that provide code used during compilation.
+ * The `id` is just a unique identifier.
+ * The `namespace` is typically the name of the package manager that
+ * provided the package (e.g. "dpkg" or "yum").
+ * The `package_name` is the name of the package, and `version` is its
+ * version (as a string).
+ */
+external_packages(
+ unique int id: @external_package,
+ string namespace : string ref,
+ string package_name : string ref,
+ string version : string ref
+);
+
+/**
+ * Holds if File `fileid` was provided by package `package`.
+ */
+header_to_external_package(
+ int fileid : @file ref,
+ int package : @external_package ref
+);
+
+/*
+ * Version history
+ */
+
+svnentries(
+ unique int id : @svnentry,
+ string revision : string ref,
+ string author : string ref,
+ date revisionDate : date ref,
+ int changeSize : int ref
+)
+
+svnaffectedfiles(
+ int id : @svnentry ref,
+ int file : @file ref,
+ string action : string ref
+)
+
+svnentrymsg(
+ unique int id : @svnentry ref,
+ string message : string ref
+)
+
+svnchurn(
+ int commit : @svnentry ref,
+ int file : @file ref,
+ int addedLines : int ref,
+ int deletedLines : int ref
+)
+
+/*
+ * C++ dbscheme
+ */
+
+extractor_version(
+ string codeql_version: string ref,
+ string frontend_version: string ref
+)
+
+@location = @location_stmt | @location_expr | @location_default ;
+
+/**
+ * The location of an element that is not an expression or a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_default(
+ /** The location of an element that is not an expression or a statement. */
+ unique int id: @location_default,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_stmt(
+ /** The location of a statement. */
+ unique int id: @location_stmt,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of an expression.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_expr(
+ /** The location of an expression. */
+ unique int id: @location_expr,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/** An element for which line-count information is available. */
+@sourceline = @file | @function | @variable | @enumconstant | @xmllocatable;
+
+numlines(
+ int element_id: @sourceline ref,
+ int num_lines: int ref,
+ int num_code: int ref,
+ int num_comment: int ref
+);
+
+diagnostics(
+ unique int id: @diagnostic,
+ int severity: int ref,
+ string error_tag: string ref,
+ string error_message: string ref,
+ string full_error_message: string ref,
+ int location: @location_default ref
+);
+
+files(
+ unique int id: @file,
+ string name: string ref
+);
+
+folders(
+ unique int id: @folder,
+ string name: string ref
+);
+
+@container = @folder | @file
+
+containerparent(
+ int parent: @container ref,
+ unique int child: @container ref
+);
+
+fileannotations(
+ int id: @file ref,
+ int kind: int ref,
+ string name: string ref,
+ string value: string ref
+);
+
+inmacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+affectedbymacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+case @macroinvocation.kind of
+ 1 = @macro_expansion
+| 2 = @other_macro_reference
+;
+
+macroinvocations(
+ unique int id: @macroinvocation,
+ int macro_id: @ppd_define ref,
+ int location: @location_default ref,
+ int kind: int ref
+);
+
+macroparent(
+ unique int id: @macroinvocation ref,
+ int parent_id: @macroinvocation ref
+);
+
+// a macroinvocation may be part of another location
+// the way to find a constant expression that uses a macro
+// is thus to find a constant expression that has a location
+// to which a macro invocation is bound
+macrolocationbind(
+ int id: @macroinvocation ref,
+ int location: @location ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_unexpanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_expanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+/*
+case @function.kind of
+ 1 = @normal_function
+| 2 = @constructor
+| 3 = @destructor
+| 4 = @conversion_function
+| 5 = @operator
+| 6 = @builtin_function // GCC built-in functions, e.g. __builtin___memcpy_chk
+;
+*/
+
+functions(
+ unique int id: @function,
+ string name: string ref,
+ int kind: int ref
+);
+
+function_entry_point(
+ int id: @function ref,
+ unique int entry_point: @stmt ref
+);
+
+function_return_type(
+ int id: @function ref,
+ int return_type: @type ref
+);
+
+/**
+ * If `function` is a coroutine, then this gives the `std::experimental::resumable_traits`
+ * instance associated with it, and the variables representing the `handle` and `promise`
+ * for it.
+ */
+coroutine(
+ unique int function: @function ref,
+ int traits: @type ref,
+ int handle: @variable ref,
+ int promise: @variable ref
+);
+
+/** The `new` function used for allocating the coroutine state, if any. */
+coroutine_new(
+ unique int function: @function ref,
+ int new: @function ref
+);
+
+/** The `delete` function used for deallocating the coroutine state, if any. */
+coroutine_delete(
+ unique int function: @function ref,
+ int delete: @function ref
+);
+
+purefunctions(unique int id: @function ref);
+
+function_deleted(unique int id: @function ref);
+
+function_defaulted(unique int id: @function ref);
+
+member_function_this_type(
+ unique int id: @function ref,
+ int this_type: @type ref
+);
+
+#keyset[id, type_id]
+fun_decls(
+ int id: @fun_decl,
+ int function: @function ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+fun_def(unique int id: @fun_decl ref);
+fun_specialized(unique int id: @fun_decl ref);
+fun_implicit(unique int id: @fun_decl ref);
+fun_decl_specifiers(
+ int id: @fun_decl ref,
+ string name: string ref
+)
+#keyset[fun_decl, index]
+fun_decl_throws(
+ int fun_decl: @fun_decl ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+/* an empty throw specification is different from none */
+fun_decl_empty_throws(unique int fun_decl: @fun_decl ref);
+fun_decl_noexcept(
+ int fun_decl: @fun_decl ref,
+ int constant: @expr ref
+);
+fun_decl_empty_noexcept(int fun_decl: @fun_decl ref);
+fun_decl_typedef_type(
+ unique int fun_decl: @fun_decl ref,
+ int typedeftype_id: @usertype ref
+);
+
+param_decl_bind(
+ unique int id: @var_decl ref,
+ int index: int ref,
+ int fun_decl: @fun_decl ref
+);
+
+#keyset[id, type_id]
+var_decls(
+ int id: @var_decl,
+ int variable: @variable ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+var_def(unique int id: @var_decl ref);
+var_decl_specifiers(
+ int id: @var_decl ref,
+ string name: string ref
+)
+is_structured_binding(unique int id: @variable ref);
+
+type_decls(
+ unique int id: @type_decl,
+ int type_id: @type ref,
+ int location: @location_default ref
+);
+type_def(unique int id: @type_decl ref);
+type_decl_top(
+ unique int type_decl: @type_decl ref
+);
+
+namespace_decls(
+ unique int id: @namespace_decl,
+ int namespace_id: @namespace ref,
+ int location: @location_default ref,
+ int bodylocation: @location_default ref
+);
+
+usings(
+ unique int id: @using,
+ int element_id: @element ref,
+ int location: @location_default ref
+);
+
+/** The element which contains the `using` declaration. */
+using_container(
+ int parent: @element ref,
+ int child: @using ref
+);
+
+static_asserts(
+ unique int id: @static_assert,
+ int condition : @expr ref,
+ string message : string ref,
+ int location: @location_default ref,
+ int enclosing : @element ref
+);
+
+// each function has an ordered list of parameters
+#keyset[id, type_id]
+#keyset[function, index, type_id]
+params(
+ int id: @parameter,
+ int function: @functionorblock ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+overrides(
+ int new: @function ref,
+ int old: @function ref
+);
+
+#keyset[id, type_id]
+membervariables(
+ int id: @membervariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+globalvariables(
+ int id: @globalvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+localvariables(
+ int id: @localvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+autoderivation(
+ unique int var: @variable ref,
+ int derivation_type: @type ref
+);
+
+orphaned_variables(
+ int var: @localvariable ref,
+ int function: @function ref
+)
+
+enumconstants(
+ unique int id: @enumconstant,
+ int parent: @usertype ref,
+ int index: int ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+
+@variable = @localscopevariable | @globalvariable | @membervariable;
+
+@localscopevariable = @localvariable | @parameter;
+
+/**
+ * Built-in types are the fundamental types, e.g., integral, floating, and void.
+ */
+case @builtintype.kind of
+ 1 = @errortype
+| 2 = @unknowntype
+| 3 = @void
+| 4 = @boolean
+| 5 = @char
+| 6 = @unsigned_char
+| 7 = @signed_char
+| 8 = @short
+| 9 = @unsigned_short
+| 10 = @signed_short
+| 11 = @int
+| 12 = @unsigned_int
+| 13 = @signed_int
+| 14 = @long
+| 15 = @unsigned_long
+| 16 = @signed_long
+| 17 = @long_long
+| 18 = @unsigned_long_long
+| 19 = @signed_long_long
+// ... 20 Microsoft-specific __int8
+// ... 21 Microsoft-specific __int16
+// ... 22 Microsoft-specific __int32
+// ... 23 Microsoft-specific __int64
+| 24 = @float
+| 25 = @double
+| 26 = @long_double
+| 27 = @complex_float // C99-specific _Complex float
+| 28 = @complex_double // C99-specific _Complex double
+| 29 = @complex_long_double // C99-specific _Complex long double
+| 30 = @imaginary_float // C99-specific _Imaginary float
+| 31 = @imaginary_double // C99-specific _Imaginary double
+| 32 = @imaginary_long_double // C99-specific _Imaginary long double
+| 33 = @wchar_t // Microsoft-specific
+| 34 = @decltype_nullptr // C++11
+| 35 = @int128 // __int128
+| 36 = @unsigned_int128 // unsigned __int128
+| 37 = @signed_int128 // signed __int128
+| 38 = @float128 // __float128
+| 39 = @complex_float128 // _Complex __float128
+| 40 = @decimal32 // _Decimal32
+| 41 = @decimal64 // _Decimal64
+| 42 = @decimal128 // _Decimal128
+| 43 = @char16_t
+| 44 = @char32_t
+| 45 = @std_float32 // _Float32
+| 46 = @float32x // _Float32x
+| 47 = @std_float64 // _Float64
+| 48 = @float64x // _Float64x
+| 49 = @std_float128 // _Float128
+// ... 50 _Float128x
+| 51 = @char8_t
+| 52 = @float16 // _Float16
+| 53 = @complex_float16 // _Complex _Float16
+| 54 = @fp16 // __fp16
+| 55 = @std_bfloat16 // __bf16
+| 56 = @std_float16 // std::float16_t
+| 57 = @complex_std_float32 // _Complex _Float32
+| 58 = @complex_float32x // _Complex _Float32x
+| 59 = @complex_std_float64 // _Complex _Float64
+| 60 = @complex_float64x // _Complex _Float64x
+| 61 = @complex_std_float128 // _Complex _Float128
+;
+
+builtintypes(
+ unique int id: @builtintype,
+ string name: string ref,
+ int kind: int ref,
+ int size: int ref,
+ int sign: int ref,
+ int alignment: int ref
+);
+
+/**
+ * Derived types are types that are directly derived from existing types and
+ * point to, refer to, transform type data to return a new type.
+ */
+case @derivedtype.kind of
+ 1 = @pointer
+| 2 = @reference
+| 3 = @type_with_specifiers
+| 4 = @array
+| 5 = @gnu_vector
+| 6 = @routineptr
+| 7 = @routinereference
+| 8 = @rvalue_reference // C++11
+// ... 9 type_conforming_to_protocols deprecated
+| 10 = @block
+;
+
+derivedtypes(
+ unique int id: @derivedtype,
+ string name: string ref,
+ int kind: int ref,
+ int type_id: @type ref
+);
+
+pointerishsize(unique int id: @derivedtype ref,
+ int size: int ref,
+ int alignment: int ref);
+
+arraysizes(
+ unique int id: @derivedtype ref,
+ int num_elements: int ref,
+ int bytesize: int ref,
+ int alignment: int ref
+);
+
+typedefbase(
+ unique int id: @usertype ref,
+ int type_id: @type ref
+);
+
+/**
+ * An instance of the C++11 `decltype` operator. For example:
+ * ```
+ * int a;
+ * decltype(1+a) b;
+ * ```
+ * Here `expr` is `1+a`.
+ *
+ * Sometimes an additional pair of parentheses around the expression
+ * would change the semantics of this decltype, e.g.
+ * ```
+ * struct A { double x; };
+ * const A* a = new A();
+ * decltype( a->x ); // type is double
+ * decltype((a->x)); // type is const double&
+ * ```
+ * (Please consult the C++11 standard for more details).
+ * `parentheses_would_change_meaning` is `true` iff that is the case.
+ */
+#keyset[id, expr]
+decltypes(
+ int id: @decltype,
+ int expr: @expr ref,
+ int base_type: @type ref,
+ boolean parentheses_would_change_meaning: boolean ref
+);
+
+/*
+case @usertype.kind of
+ 1 = @struct
+| 2 = @class
+| 3 = @union
+| 4 = @enum
+| 5 = @typedef // classic C: typedef typedef type name
+| 6 = @template
+| 7 = @template_parameter
+| 8 = @template_template_parameter
+| 9 = @proxy_class // a proxy class associated with a template parameter
+// ... 10 objc_class deprecated
+// ... 11 objc_protocol deprecated
+// ... 12 objc_category deprecated
+| 13 = @scoped_enum
+| 14 = @using_alias // a using name = type style typedef
+;
+*/
+
+usertypes(
+ unique int id: @usertype,
+ string name: string ref,
+ int kind: int ref
+);
+
+usertypesize(
+ unique int id: @usertype ref,
+ int size: int ref,
+ int alignment: int ref
+);
+
+usertype_final(unique int id: @usertype ref);
+
+usertype_uuid(
+ unique int id: @usertype ref,
+ string uuid: string ref
+);
+
+mangled_name(
+ unique int id: @declaration ref,
+ int mangled_name : @mangledname
+);
+
+is_pod_class(unique int id: @usertype ref);
+is_standard_layout_class(unique int id: @usertype ref);
+
+is_complete(unique int id: @usertype ref);
+
+is_class_template(unique int id: @usertype ref);
+class_instantiation(
+ int to: @usertype ref,
+ int from: @usertype ref
+);
+class_template_argument(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+class_template_argument_value(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_proxy_class_for(
+ unique int id: @usertype ref,
+ unique int templ_param_id: @usertype ref
+);
+
+type_mentions(
+ unique int id: @type_mention,
+ int type_id: @type ref,
+ int location: @location ref,
+ // a_symbol_reference_kind from the frontend.
+ int kind: int ref
+);
+
+is_function_template(unique int id: @function ref);
+function_instantiation(
+ unique int to: @function ref,
+ int from: @function ref
+);
+function_template_argument(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+function_template_argument_value(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_variable_template(unique int id: @variable ref);
+variable_instantiation(
+ unique int to: @variable ref,
+ int from: @variable ref
+);
+variable_template_argument(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+variable_template_argument_value(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+/*
+ Fixed point types
+ precision(1) = short, precision(2) = default, precision(3) = long
+ is_unsigned(1) = unsigned is_unsigned(2) = signed
+ is_fract_type(1) = declared with _Fract
+ saturating(1) = declared with _Sat
+*/
+/* TODO
+fixedpointtypes(
+ unique int id: @fixedpointtype,
+ int precision: int ref,
+ int is_unsigned: int ref,
+ int is_fract_type: int ref,
+ int saturating: int ref);
+*/
+
+routinetypes(
+ unique int id: @routinetype,
+ int return_type: @type ref
+);
+
+routinetypeargs(
+ int routine: @routinetype ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+ptrtomembers(
+ unique int id: @ptrtomember,
+ int type_id: @type ref,
+ int class_id: @type ref
+);
+
+/*
+ specifiers for types, functions, and variables
+
+ "public",
+ "protected",
+ "private",
+
+ "const",
+ "volatile",
+ "static",
+
+ "pure",
+ "virtual",
+ "sealed", // Microsoft
+ "__interface", // Microsoft
+ "inline",
+ "explicit",
+
+ "near", // near far extension
+ "far", // near far extension
+ "__ptr32", // Microsoft
+ "__ptr64", // Microsoft
+ "__sptr", // Microsoft
+ "__uptr", // Microsoft
+ "dllimport", // Microsoft
+ "dllexport", // Microsoft
+ "thread", // Microsoft
+ "naked", // Microsoft
+ "microsoft_inline", // Microsoft
+ "forceinline", // Microsoft
+ "selectany", // Microsoft
+ "nothrow", // Microsoft
+ "novtable", // Microsoft
+ "noreturn", // Microsoft
+ "noinline", // Microsoft
+ "noalias", // Microsoft
+ "restrict", // Microsoft
+*/
+
+specifiers(
+ unique int id: @specifier,
+ unique string str: string ref
+);
+
+typespecifiers(
+ int type_id: @type ref,
+ int spec_id: @specifier ref
+);
+
+funspecifiers(
+ int func_id: @function ref,
+ int spec_id: @specifier ref
+);
+
+varspecifiers(
+ int var_id: @accessible ref,
+ int spec_id: @specifier ref
+);
+
+attributes(
+ unique int id: @attribute,
+ int kind: int ref,
+ string name: string ref,
+ string name_space: string ref,
+ int location: @location_default ref
+);
+
+case @attribute.kind of
+ 0 = @gnuattribute
+| 1 = @stdattribute
+| 2 = @declspec
+| 3 = @msattribute
+| 4 = @alignas
+// ... 5 @objc_propertyattribute deprecated
+;
+
+attribute_args(
+ unique int id: @attribute_arg,
+ int kind: int ref,
+ int attribute: @attribute ref,
+ int index: int ref,
+ int location: @location_default ref
+);
+
+case @attribute_arg.kind of
+ 0 = @attribute_arg_empty
+| 1 = @attribute_arg_token
+| 2 = @attribute_arg_constant
+| 3 = @attribute_arg_type
+| 4 = @attribute_arg_constant_expr
+;
+
+attribute_arg_value(
+ unique int arg: @attribute_arg ref,
+ string value: string ref
+);
+attribute_arg_type(
+ unique int arg: @attribute_arg ref,
+ int type_id: @type ref
+);
+attribute_arg_constant(
+ unique int arg: @attribute_arg ref,
+ int constant: @expr ref
+)
+attribute_arg_name(
+ unique int arg: @attribute_arg ref,
+ string name: string ref
+);
+
+typeattributes(
+ int type_id: @type ref,
+ int spec_id: @attribute ref
+);
+
+funcattributes(
+ int func_id: @function ref,
+ int spec_id: @attribute ref
+);
+
+varattributes(
+ int var_id: @accessible ref,
+ int spec_id: @attribute ref
+);
+
+stmtattributes(
+ int stmt_id: @stmt ref,
+ int spec_id: @attribute ref
+);
+
+@type = @builtintype
+ | @derivedtype
+ | @usertype
+ /* TODO | @fixedpointtype */
+ | @routinetype
+ | @ptrtomember
+ | @decltype;
+
+unspecifiedtype(
+ unique int type_id: @type ref,
+ int unspecified_type_id: @type ref
+);
+
+member(
+ int parent: @type ref,
+ int index: int ref,
+ int child: @member ref
+);
+
+@enclosingfunction_child = @usertype | @variable | @namespace
+
+enclosingfunction(
+ unique int child: @enclosingfunction_child ref,
+ int parent: @function ref
+);
+
+derivations(
+ unique int derivation: @derivation,
+ int sub: @type ref,
+ int index: int ref,
+ int super: @type ref,
+ int location: @location_default ref
+);
+
+derspecifiers(
+ int der_id: @derivation ref,
+ int spec_id: @specifier ref
+);
+
+/**
+ * Contains the byte offset of the base class subobject within the derived
+ * class. Only holds for non-virtual base classes, but see table
+ * `virtual_base_offsets` for offsets of virtual base class subobjects.
+ */
+direct_base_offsets(
+ unique int der_id: @derivation ref,
+ int offset: int ref
+);
+
+/**
+ * Contains the byte offset of the virtual base class subobject for class
+ * `super` within a most-derived object of class `sub`. `super` can be either a
+ * direct or indirect base class.
+ */
+#keyset[sub, super]
+virtual_base_offsets(
+ int sub: @usertype ref,
+ int super: @usertype ref,
+ int offset: int ref
+);
+
+frienddecls(
+ unique int id: @frienddecl,
+ int type_id: @type ref,
+ int decl_id: @declaration ref,
+ int location: @location_default ref
+);
+
+@declaredtype = @usertype ;
+
+@declaration = @function
+ | @declaredtype
+ | @variable
+ | @enumconstant
+ | @frienddecl;
+
+@member = @membervariable
+ | @function
+ | @declaredtype
+ | @enumconstant;
+
+@locatable = @diagnostic
+ | @declaration
+ | @ppd_include
+ | @ppd_define
+ | @macroinvocation
+ /*| @funcall*/
+ | @xmllocatable
+ | @attribute
+ | @attribute_arg;
+
+@namedscope = @namespace | @usertype;
+
+@element = @locatable
+ | @file
+ | @folder
+ | @specifier
+ | @type
+ | @expr
+ | @namespace
+ | @initialiser
+ | @stmt
+ | @derivation
+ | @comment
+ | @preprocdirect
+ | @fun_decl
+ | @var_decl
+ | @type_decl
+ | @namespace_decl
+ | @using
+ | @namequalifier
+ | @specialnamequalifyingelement
+ | @static_assert
+ | @type_mention
+ | @lambdacapture;
+
+@exprparent = @element;
+
+comments(
+ unique int id: @comment,
+ string contents: string ref,
+ int location: @location_default ref
+);
+
+commentbinding(
+ int id: @comment ref,
+ int element: @element ref
+);
+
+exprconv(
+ int converted: @expr ref,
+ unique int conversion: @expr ref
+);
+
+compgenerated(unique int id: @element ref);
+
+/**
+ * `destructor_call` destructs the `i`'th entity that should be
+ * destructed following `element`. Note that entities should be
+ * destructed in reverse construction order, so for a given `element`
+ * these should be called from highest to lowest `i`.
+ */
+#keyset[element, destructor_call]
+#keyset[element, i]
+synthetic_destructor_call(
+ int element: @element ref,
+ int i: int ref,
+ int destructor_call: @routineexpr ref
+);
+
+namespaces(
+ unique int id: @namespace,
+ string name: string ref
+);
+
+namespace_inline(
+ unique int id: @namespace ref
+);
+
+namespacembrs(
+ int parentid: @namespace ref,
+ unique int memberid: @namespacembr ref
+);
+
+@namespacembr = @declaration | @namespace;
+
+exprparents(
+ int expr_id: @expr ref,
+ int child_index: int ref,
+ int parent_id: @exprparent ref
+);
+
+expr_isload(unique int expr_id: @expr ref);
+
+@cast = @c_style_cast
+ | @const_cast
+ | @dynamic_cast
+ | @reinterpret_cast
+ | @static_cast
+ ;
+
+/*
+case @conversion.kind of
+ 0 = @simple_conversion // a numeric conversion, qualification conversion, or a reinterpret_cast
+| 1 = @bool_conversion // conversion to 'bool'
+| 2 = @base_class_conversion // a derived-to-base conversion
+| 3 = @derived_class_conversion // a base-to-derived conversion
+| 4 = @pm_base_class_conversion // a derived-to-base conversion of a pointer to member
+| 5 = @pm_derived_class_conversion // a base-to-derived conversion of a pointer to member
+| 6 = @glvalue_adjust // an adjustment of the type of a glvalue
+| 7 = @prvalue_adjust // an adjustment of the type of a prvalue
+;
+*/
+/**
+ * Describes the semantics represented by a cast expression. This is largely
+ * independent of the source syntax of the cast, so it is separate from the
+ * regular expression kind.
+ */
+conversionkinds(
+ unique int expr_id: @cast ref,
+ int kind: int ref
+);
+
+@conversion = @cast
+ | @array_to_pointer
+ | @parexpr
+ | @reference_to
+ | @ref_indirect
+ | @temp_init
+ ;
+
+/*
+case @funbindexpr.kind of
+ 0 = @normal_call // a normal call
+| 1 = @virtual_call // a virtual call
+| 2 = @adl_call // a call whose target is only found by ADL
+;
+*/
+iscall(
+ unique int caller: @funbindexpr ref,
+ int kind: int ref
+);
+
+numtemplatearguments(
+ unique int expr_id: @expr ref,
+ int num: int ref
+);
+
+specialnamequalifyingelements(
+ unique int id: @specialnamequalifyingelement,
+ unique string name: string ref
+);
+
+@namequalifiableelement = @expr | @namequalifier;
+@namequalifyingelement = @namespace
+ | @specialnamequalifyingelement
+ | @usertype;
+
+namequalifiers(
+ unique int id: @namequalifier,
+ unique int qualifiableelement: @namequalifiableelement ref,
+ int qualifyingelement: @namequalifyingelement ref,
+ int location: @location_default ref
+);
+
+varbind(
+ int expr: @varbindexpr ref,
+ int var: @accessible ref
+);
+
+funbind(
+ int expr: @funbindexpr ref,
+ int fun: @function ref
+);
+
+@any_new_expr = @new_expr
+ | @new_array_expr;
+
+@new_or_delete_expr = @any_new_expr
+ | @delete_expr
+ | @delete_array_expr;
+
+@prefix_crement_expr = @preincrexpr | @predecrexpr;
+
+@postfix_crement_expr = @postincrexpr | @postdecrexpr;
+
+@increment_expr = @preincrexpr | @postincrexpr;
+
+@decrement_expr = @predecrexpr | @postdecrexpr;
+
+@crement_expr = @increment_expr | @decrement_expr;
+
+@un_arith_op_expr = @arithnegexpr
+ | @unaryplusexpr
+ | @conjugation
+ | @realpartexpr
+ | @imagpartexpr
+ | @crement_expr
+ ;
+
+@un_bitwise_op_expr = @complementexpr;
+
+@un_log_op_expr = @notexpr;
+
+@un_op_expr = @address_of
+ | @indirect
+ | @un_arith_op_expr
+ | @un_bitwise_op_expr
+ | @builtinaddressof
+ | @vec_fill
+ | @un_log_op_expr
+ | @co_await
+ | @co_yield
+ ;
+
+@bin_log_op_expr = @andlogicalexpr | @orlogicalexpr;
+
+@cmp_op_expr = @eq_op_expr | @rel_op_expr;
+
+@eq_op_expr = @eqexpr | @neexpr;
+
+@rel_op_expr = @gtexpr
+ | @ltexpr
+ | @geexpr
+ | @leexpr
+ | @spaceshipexpr
+ ;
+
+@bin_bitwise_op_expr = @lshiftexpr
+ | @rshiftexpr
+ | @andexpr
+ | @orexpr
+ | @xorexpr
+ ;
+
+@p_arith_op_expr = @paddexpr
+ | @psubexpr
+ | @pdiffexpr
+ ;
+
+@bin_arith_op_expr = @addexpr
+ | @subexpr
+ | @mulexpr
+ | @divexpr
+ | @remexpr
+ | @jmulexpr
+ | @jdivexpr
+ | @fjaddexpr
+ | @jfaddexpr
+ | @fjsubexpr
+ | @jfsubexpr
+ | @minexpr
+ | @maxexpr
+ | @p_arith_op_expr
+ ;
+
+@bin_op_expr = @bin_arith_op_expr
+ | @bin_bitwise_op_expr
+ | @cmp_op_expr
+ | @bin_log_op_expr
+ ;
+
+@op_expr = @un_op_expr
+ | @bin_op_expr
+ | @assign_expr
+ | @conditionalexpr
+ ;
+
+@assign_arith_expr = @assignaddexpr
+ | @assignsubexpr
+ | @assignmulexpr
+ | @assigndivexpr
+ | @assignremexpr
+ ;
+
+@assign_bitwise_expr = @assignandexpr
+ | @assignorexpr
+ | @assignxorexpr
+ | @assignlshiftexpr
+ | @assignrshiftexpr
+ ;
+
+@assign_pointer_expr = @assignpaddexpr
+ | @assignpsubexpr
+ ;
+
+@assign_op_expr = @assign_arith_expr
+ | @assign_bitwise_expr
+ | @assign_pointer_expr
+ ;
+
+@assign_expr = @assignexpr | @assign_op_expr | @blockassignexpr
+
+/*
+ case @allocator.form of
+ 0 = plain
+ | 1 = alignment
+ ;
+*/
+
+/**
+ * The allocator function associated with a `new` or `new[]` expression.
+ * The `form` column specified whether the allocation call contains an alignment
+ * argument.
+ */
+expr_allocator(
+ unique int expr: @any_new_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/*
+ case @deallocator.form of
+ 0 = plain
+ | 1 = size
+ | 2 = alignment
+ | 3 = size_and_alignment
+ ;
+*/
+
+/**
+ * The deallocator function associated with a `delete`, `delete[]`, `new`, or
+ * `new[]` expression. For a `new` or `new[]` expression, the deallocator is the
+ * one used to free memory if the initialization throws an exception.
+ * The `form` column specifies whether the deallocation call contains a size
+ * argument, and alignment argument, or both.
+ */
+expr_deallocator(
+ unique int expr: @new_or_delete_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/**
+ * Holds if the `@conditionalexpr` is of the two operand form
+ * `guard ? : false`.
+ */
+expr_cond_two_operand(
+ unique int cond: @conditionalexpr ref
+);
+
+/**
+ * The guard of `@conditionalexpr` `guard ? true : false`
+ */
+expr_cond_guard(
+ unique int cond: @conditionalexpr ref,
+ int guard: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` holds. For the two operand form
+ * `guard ?: false` consider using `expr_cond_guard` instead.
+ */
+expr_cond_true(
+ unique int cond: @conditionalexpr ref,
+ int true: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` does not hold.
+ */
+expr_cond_false(
+ unique int cond: @conditionalexpr ref,
+ int false: @expr ref
+);
+
+/** A string representation of the value. */
+values(
+ unique int id: @value,
+ string str: string ref
+);
+
+/** The actual text in the source code for the value, if any. */
+valuetext(
+ unique int id: @value ref,
+ string text: string ref
+);
+
+valuebind(
+ int val: @value ref,
+ unique int expr: @expr ref
+);
+
+fieldoffsets(
+ unique int id: @variable ref,
+ int byteoffset: int ref,
+ int bitoffset: int ref
+);
+
+bitfield(
+ unique int id: @variable ref,
+ int bits: int ref,
+ int declared_bits: int ref
+);
+
+/* TODO
+memberprefix(
+ int member: @expr ref,
+ int prefix: @expr ref
+);
+*/
+
+/*
+ kind(1) = mbrcallexpr
+ kind(2) = mbrptrcallexpr
+ kind(3) = mbrptrmbrcallexpr
+ kind(4) = ptrmbrptrmbrcallexpr
+ kind(5) = mbrreadexpr // x.y
+ kind(6) = mbrptrreadexpr // p->y
+ kind(7) = mbrptrmbrreadexpr // x.*pm
+ kind(8) = mbrptrmbrptrreadexpr // x->*pm
+ kind(9) = staticmbrreadexpr // static x.y
+ kind(10) = staticmbrptrreadexpr // static p->y
+*/
+/* TODO
+memberaccess(
+ int member: @expr ref,
+ int kind: int ref
+);
+*/
+
+initialisers(
+ unique int init: @initialiser,
+ int var: @accessible ref,
+ unique int expr: @expr ref,
+ int location: @location_expr ref
+);
+
+braced_initialisers(
+ int init: @initialiser ref
+);
+
+/**
+ * An ancestor for the expression, for cases in which we cannot
+ * otherwise find the expression's parent.
+ */
+expr_ancestor(
+ int exp: @expr ref,
+ int ancestor: @element ref
+);
+
+exprs(
+ unique int id: @expr,
+ int kind: int ref,
+ int location: @location_expr ref
+);
+
+/*
+ case @value.category of
+ 1 = prval
+ | 2 = xval
+ | 3 = lval
+ ;
+*/
+expr_types(
+ int id: @expr ref,
+ int typeid: @type ref,
+ int value_category: int ref
+);
+
+case @expr.kind of
+ 1 = @errorexpr
+| 2 = @address_of // & AddressOfExpr
+| 3 = @reference_to // ReferenceToExpr (implicit?)
+| 4 = @indirect // * PointerDereferenceExpr
+| 5 = @ref_indirect // ReferenceDereferenceExpr (implicit?)
+// ...
+| 8 = @array_to_pointer // (???)
+| 9 = @vacuous_destructor_call // VacuousDestructorCall
+// ...
+| 11 = @assume // Microsoft
+| 12 = @parexpr
+| 13 = @arithnegexpr
+| 14 = @unaryplusexpr
+| 15 = @complementexpr
+| 16 = @notexpr
+| 17 = @conjugation // GNU ~ operator
+| 18 = @realpartexpr // GNU __real
+| 19 = @imagpartexpr // GNU __imag
+| 20 = @postincrexpr
+| 21 = @postdecrexpr
+| 22 = @preincrexpr
+| 23 = @predecrexpr
+| 24 = @conditionalexpr
+| 25 = @addexpr
+| 26 = @subexpr
+| 27 = @mulexpr
+| 28 = @divexpr
+| 29 = @remexpr
+| 30 = @jmulexpr // C99 mul imaginary
+| 31 = @jdivexpr // C99 div imaginary
+| 32 = @fjaddexpr // C99 add real + imaginary
+| 33 = @jfaddexpr // C99 add imaginary + real
+| 34 = @fjsubexpr // C99 sub real - imaginary
+| 35 = @jfsubexpr // C99 sub imaginary - real
+| 36 = @paddexpr // pointer add (pointer + int or int + pointer)
+| 37 = @psubexpr // pointer sub (pointer - integer)
+| 38 = @pdiffexpr // difference between two pointers
+| 39 = @lshiftexpr
+| 40 = @rshiftexpr
+| 41 = @andexpr
+| 42 = @orexpr
+| 43 = @xorexpr
+| 44 = @eqexpr
+| 45 = @neexpr
+| 46 = @gtexpr
+| 47 = @ltexpr
+| 48 = @geexpr
+| 49 = @leexpr
+| 50 = @minexpr // GNU minimum
+| 51 = @maxexpr // GNU maximum
+| 52 = @assignexpr
+| 53 = @assignaddexpr
+| 54 = @assignsubexpr
+| 55 = @assignmulexpr
+| 56 = @assigndivexpr
+| 57 = @assignremexpr
+| 58 = @assignlshiftexpr
+| 59 = @assignrshiftexpr
+| 60 = @assignandexpr
+| 61 = @assignorexpr
+| 62 = @assignxorexpr
+| 63 = @assignpaddexpr // assign pointer add
+| 64 = @assignpsubexpr // assign pointer sub
+| 65 = @andlogicalexpr
+| 66 = @orlogicalexpr
+| 67 = @commaexpr
+| 68 = @subscriptexpr // access to member of an array, e.g., a[5]
+// ... 69 @objc_subscriptexpr deprecated
+// ... 70 @cmdaccess deprecated
+// ...
+| 73 = @virtfunptrexpr
+| 74 = @callexpr
+// ... 75 @msgexpr_normal deprecated
+// ... 76 @msgexpr_super deprecated
+// ... 77 @atselectorexpr deprecated
+// ... 78 @atprotocolexpr deprecated
+| 79 = @vastartexpr
+| 80 = @vaargexpr
+| 81 = @vaendexpr
+| 82 = @vacopyexpr
+// ... 83 @atencodeexpr deprecated
+| 84 = @varaccess
+| 85 = @thisaccess
+// ... 86 @objc_box_expr deprecated
+| 87 = @new_expr
+| 88 = @delete_expr
+| 89 = @throw_expr
+| 90 = @condition_decl // a variable declared in a condition, e.g., if(int x = y > 2)
+| 91 = @braced_init_list
+| 92 = @type_id
+| 93 = @runtime_sizeof
+| 94 = @runtime_alignof
+| 95 = @sizeof_pack
+| 96 = @expr_stmt // GNU extension
+| 97 = @routineexpr
+| 98 = @type_operand // used to access a type in certain contexts (haven't found any examples yet....)
+| 99 = @offsetofexpr // offsetof ::= type and field
+| 100 = @hasassignexpr // __has_assign ::= type
+| 101 = @hascopyexpr // __has_copy ::= type
+| 102 = @hasnothrowassign // __has_nothrow_assign ::= type
+| 103 = @hasnothrowconstr // __has_nothrow_constructor ::= type
+| 104 = @hasnothrowcopy // __has_nothrow_copy ::= type
+| 105 = @hastrivialassign // __has_trivial_assign ::= type
+| 106 = @hastrivialconstr // __has_trivial_constructor ::= type
+| 107 = @hastrivialcopy // __has_trivial_copy ::= type
+| 108 = @hasuserdestr // __has_user_destructor ::= type
+| 109 = @hasvirtualdestr // __has_virtual_destructor ::= type
+| 110 = @isabstractexpr // __is_abstract ::= type
+| 111 = @isbaseofexpr // __is_base_of ::= type type
+| 112 = @isclassexpr // __is_class ::= type
+| 113 = @isconvtoexpr // __is_convertible_to ::= type type
+| 114 = @isemptyexpr // __is_empty ::= type
+| 115 = @isenumexpr // __is_enum ::= type
+| 116 = @ispodexpr // __is_pod ::= type
+| 117 = @ispolyexpr // __is_polymorphic ::= type
+| 118 = @isunionexpr // __is_union ::= type
+| 119 = @typescompexpr // GNU __builtin_types_compatible ::= type type
+| 120 = @intaddrexpr // frontend internal builtin, used to implement offsetof
+// ...
+| 122 = @hastrivialdestructor // __has_trivial_destructor ::= type
+| 123 = @literal
+| 124 = @uuidof
+| 127 = @aggregateliteral
+| 128 = @delete_array_expr
+| 129 = @new_array_expr
+// ... 130 @objc_array_literal deprecated
+// ... 131 @objc_dictionary_literal deprecated
+| 132 = @foldexpr
+// ...
+| 200 = @ctordirectinit
+| 201 = @ctorvirtualinit
+| 202 = @ctorfieldinit
+| 203 = @ctordelegatinginit
+| 204 = @dtordirectdestruct
+| 205 = @dtorvirtualdestruct
+| 206 = @dtorfielddestruct
+// ...
+| 210 = @static_cast
+| 211 = @reinterpret_cast
+| 212 = @const_cast
+| 213 = @dynamic_cast
+| 214 = @c_style_cast
+| 215 = @lambdaexpr
+| 216 = @param_ref
+| 217 = @noopexpr
+// ...
+| 294 = @istriviallyconstructibleexpr
+| 295 = @isdestructibleexpr
+| 296 = @isnothrowdestructibleexpr
+| 297 = @istriviallydestructibleexpr
+| 298 = @istriviallyassignableexpr
+| 299 = @isnothrowassignableexpr
+| 300 = @istrivialexpr
+| 301 = @isstandardlayoutexpr
+| 302 = @istriviallycopyableexpr
+| 303 = @isliteraltypeexpr
+| 304 = @hastrivialmoveconstructorexpr
+| 305 = @hastrivialmoveassignexpr
+| 306 = @hasnothrowmoveassignexpr
+| 307 = @isconstructibleexpr
+| 308 = @isnothrowconstructibleexpr
+| 309 = @hasfinalizerexpr
+| 310 = @isdelegateexpr
+| 311 = @isinterfaceclassexpr
+| 312 = @isrefarrayexpr
+| 313 = @isrefclassexpr
+| 314 = @issealedexpr
+| 315 = @issimplevalueclassexpr
+| 316 = @isvalueclassexpr
+| 317 = @isfinalexpr
+| 319 = @noexceptexpr
+| 320 = @builtinshufflevector
+| 321 = @builtinchooseexpr
+| 322 = @builtinaddressof
+| 323 = @vec_fill
+| 324 = @builtinconvertvector
+| 325 = @builtincomplex
+| 326 = @spaceshipexpr
+| 327 = @co_await
+| 328 = @co_yield
+| 329 = @temp_init
+| 330 = @isassignable
+| 331 = @isaggregate
+| 332 = @hasuniqueobjectrepresentations
+| 333 = @builtinbitcast
+| 334 = @builtinshuffle
+| 335 = @blockassignexpr
+| 336 = @issame
+| 337 = @isfunction
+| 338 = @islayoutcompatible
+| 339 = @ispointerinterconvertiblebaseof
+| 340 = @isarray
+| 341 = @arrayrank
+| 342 = @arrayextent
+| 343 = @isarithmetic
+| 344 = @iscompletetype
+| 345 = @iscompound
+| 346 = @isconst
+| 347 = @isfloatingpoint
+| 348 = @isfundamental
+| 349 = @isintegral
+| 350 = @islvaluereference
+| 351 = @ismemberfunctionpointer
+| 352 = @ismemberobjectpointer
+| 353 = @ismemberpointer
+| 354 = @isobject
+| 355 = @ispointer
+| 356 = @isreference
+| 357 = @isrvaluereference
+| 358 = @isscalar
+| 359 = @issigned
+| 360 = @isunsigned
+| 361 = @isvoid
+| 362 = @isvolatile
+;
+
+@var_args_expr = @vastartexpr
+ | @vaendexpr
+ | @vaargexpr
+ | @vacopyexpr
+ ;
+
+@builtin_op = @var_args_expr
+ | @noopexpr
+ | @offsetofexpr
+ | @intaddrexpr
+ | @hasassignexpr
+ | @hascopyexpr
+ | @hasnothrowassign
+ | @hasnothrowconstr
+ | @hasnothrowcopy
+ | @hastrivialassign
+ | @hastrivialconstr
+ | @hastrivialcopy
+ | @hastrivialdestructor
+ | @hasuserdestr
+ | @hasvirtualdestr
+ | @isabstractexpr
+ | @isbaseofexpr
+ | @isclassexpr
+ | @isconvtoexpr
+ | @isemptyexpr
+ | @isenumexpr
+ | @ispodexpr
+ | @ispolyexpr
+ | @isunionexpr
+ | @typescompexpr
+ | @builtinshufflevector
+ | @builtinconvertvector
+ | @builtinaddressof
+ | @istriviallyconstructibleexpr
+ | @isdestructibleexpr
+ | @isnothrowdestructibleexpr
+ | @istriviallydestructibleexpr
+ | @istriviallyassignableexpr
+ | @isnothrowassignableexpr
+ | @istrivialexpr
+ | @isstandardlayoutexpr
+ | @istriviallycopyableexpr
+ | @isliteraltypeexpr
+ | @hastrivialmoveconstructorexpr
+ | @hastrivialmoveassignexpr
+ | @hasnothrowmoveassignexpr
+ | @isconstructibleexpr
+ | @isnothrowconstructibleexpr
+ | @hasfinalizerexpr
+ | @isdelegateexpr
+ | @isinterfaceclassexpr
+ | @isrefarrayexpr
+ | @isrefclassexpr
+ | @issealedexpr
+ | @issimplevalueclassexpr
+ | @isvalueclassexpr
+ | @isfinalexpr
+ | @builtinchooseexpr
+ | @builtincomplex
+ | @isassignable
+ | @isaggregate
+ | @hasuniqueobjectrepresentations
+ | @builtinbitcast
+ | @builtinshuffle
+ | @issame
+ | @isfunction
+ | @islayoutcompatible
+ | @ispointerinterconvertiblebaseof
+ | @isarray
+ | @arrayrank
+ | @arrayextent
+ | @isarithmetic
+ | @iscompletetype
+ | @iscompound
+ | @isconst
+ | @isfloatingpoint
+ | @isfundamental
+ | @isintegral
+ | @islvaluereference
+ | @ismemberfunctionpointer
+ | @ismemberobjectpointer
+ | @ismemberpointer
+ | @isobject
+ | @ispointer
+ | @isreference
+ | @isrvaluereference
+ | @isscalar
+ | @issigned
+ | @isunsigned
+ | @isvoid
+ | @isvolatile
+ ;
+
+new_allocated_type(
+ unique int expr: @new_expr ref,
+ int type_id: @type ref
+);
+
+new_array_allocated_type(
+ unique int expr: @new_array_expr ref,
+ int type_id: @type ref
+);
+
+/**
+ * The field being initialized by an initializer expression within an aggregate
+ * initializer for a class/struct/union. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_field_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int field: @membervariable ref,
+ int position: int ref
+);
+
+/**
+ * The index of the element being initialized by an initializer expression
+ * within an aggregate initializer for an array. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_array_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int element_index: int ref,
+ int position: int ref
+);
+
+@ctorinit = @ctordirectinit
+ | @ctorvirtualinit
+ | @ctorfieldinit
+ | @ctordelegatinginit;
+@dtordestruct = @dtordirectdestruct
+ | @dtorvirtualdestruct
+ | @dtorfielddestruct;
+
+
+condition_decl_bind(
+ unique int expr: @condition_decl ref,
+ unique int decl: @declaration ref
+);
+
+typeid_bind(
+ unique int expr: @type_id ref,
+ int type_id: @type ref
+);
+
+uuidof_bind(
+ unique int expr: @uuidof ref,
+ int type_id: @type ref
+);
+
+@runtime_sizeof_or_alignof = @runtime_sizeof | @runtime_alignof;
+
+sizeof_bind(
+ unique int expr: @runtime_sizeof_or_alignof ref,
+ int type_id: @type ref
+);
+
+code_block(
+ unique int block: @literal ref,
+ unique int routine: @function ref
+);
+
+lambdas(
+ unique int expr: @lambdaexpr ref,
+ string default_capture: string ref,
+ boolean has_explicit_return_type: boolean ref
+);
+
+lambda_capture(
+ unique int id: @lambdacapture,
+ int lambda: @lambdaexpr ref,
+ int index: int ref,
+ int field: @membervariable ref,
+ boolean captured_by_reference: boolean ref,
+ boolean is_implicit: boolean ref,
+ int location: @location_default ref
+);
+
+@funbindexpr = @routineexpr
+ | @new_expr
+ | @delete_expr
+ | @delete_array_expr
+ | @ctordirectinit
+ | @ctorvirtualinit
+ | @ctordelegatinginit
+ | @dtordirectdestruct
+ | @dtorvirtualdestruct;
+
+@varbindexpr = @varaccess | @ctorfieldinit | @dtorfielddestruct;
+@addressable = @function | @variable ;
+@accessible = @addressable | @enumconstant ;
+
+@access = @varaccess | @routineexpr ;
+
+fold(
+ int expr: @foldexpr ref,
+ string operator: string ref,
+ boolean is_left_fold: boolean ref
+);
+
+stmts(
+ unique int id: @stmt,
+ int kind: int ref,
+ int location: @location_stmt ref
+);
+
+case @stmt.kind of
+ 1 = @stmt_expr
+| 2 = @stmt_if
+| 3 = @stmt_while
+| 4 = @stmt_goto
+| 5 = @stmt_label
+| 6 = @stmt_return
+| 7 = @stmt_block
+| 8 = @stmt_end_test_while // do { ... } while ( ... )
+| 9 = @stmt_for
+| 10 = @stmt_switch_case
+| 11 = @stmt_switch
+| 13 = @stmt_asm // "asm" statement or the body of an asm function
+| 15 = @stmt_try_block
+| 16 = @stmt_microsoft_try // Microsoft
+| 17 = @stmt_decl
+| 18 = @stmt_set_vla_size // C99
+| 19 = @stmt_vla_decl // C99
+| 25 = @stmt_assigned_goto // GNU
+| 26 = @stmt_empty
+| 27 = @stmt_continue
+| 28 = @stmt_break
+| 29 = @stmt_range_based_for // C++11
+// ... 30 @stmt_at_autoreleasepool_block deprecated
+// ... 31 @stmt_objc_for_in deprecated
+// ... 32 @stmt_at_synchronized deprecated
+| 33 = @stmt_handler
+// ... 34 @stmt_finally_end deprecated
+| 35 = @stmt_constexpr_if
+| 37 = @stmt_co_return
+;
+
+type_vla(
+ int type_id: @type ref,
+ int decl: @stmt_vla_decl ref
+);
+
+variable_vla(
+ int var: @variable ref,
+ int decl: @stmt_vla_decl ref
+);
+
+if_initialization(
+ unique int if_stmt: @stmt_if ref,
+ int init_id: @stmt ref
+);
+
+if_then(
+ unique int if_stmt: @stmt_if ref,
+ int then_id: @stmt ref
+);
+
+if_else(
+ unique int if_stmt: @stmt_if ref,
+ int else_id: @stmt ref
+);
+
+constexpr_if_initialization(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int init_id: @stmt ref
+);
+
+constexpr_if_then(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int then_id: @stmt ref
+);
+
+constexpr_if_else(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int else_id: @stmt ref
+);
+
+while_body(
+ unique int while_stmt: @stmt_while ref,
+ int body_id: @stmt ref
+);
+
+do_body(
+ unique int do_stmt: @stmt_end_test_while ref,
+ int body_id: @stmt ref
+);
+
+switch_initialization(
+ unique int switch_stmt: @stmt_switch ref,
+ int init_id: @stmt ref
+);
+
+#keyset[switch_stmt, index]
+switch_case(
+ int switch_stmt: @stmt_switch ref,
+ int index: int ref,
+ int case_id: @stmt_switch_case ref
+);
+
+switch_body(
+ unique int switch_stmt: @stmt_switch ref,
+ int body_id: @stmt ref
+);
+
+for_initialization(
+ unique int for_stmt: @stmt_for ref,
+ int init_id: @stmt ref
+);
+
+for_condition(
+ unique int for_stmt: @stmt_for ref,
+ int condition_id: @expr ref
+);
+
+for_update(
+ unique int for_stmt: @stmt_for ref,
+ int update_id: @expr ref
+);
+
+for_body(
+ unique int for_stmt: @stmt_for ref,
+ int body_id: @stmt ref
+);
+
+@stmtparent = @stmt | @expr_stmt ;
+stmtparents(
+ unique int id: @stmt ref,
+ int index: int ref,
+ int parent: @stmtparent ref
+);
+
+ishandler(unique int block: @stmt_block ref);
+
+@cfgnode = @stmt | @expr | @function | @initialiser ;
+
+stmt_decl_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl: @declaration ref
+);
+
+stmt_decl_entry_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl_entry: @element ref
+);
+
+@functionorblock = @function | @stmt_block;
+
+blockscope(
+ unique int block: @stmt_block ref,
+ int enclosing: @functionorblock ref
+);
+
+@jump = @stmt_goto | @stmt_break | @stmt_continue;
+
+@jumporlabel = @jump | @stmt_label | @literal;
+
+jumpinfo(
+ unique int id: @jumporlabel ref,
+ string str: string ref,
+ int target: @stmt ref
+);
+
+preprocdirects(
+ unique int id: @preprocdirect,
+ int kind: int ref,
+ int location: @location_default ref
+);
+case @preprocdirect.kind of
+ 0 = @ppd_if
+| 1 = @ppd_ifdef
+| 2 = @ppd_ifndef
+| 3 = @ppd_elif
+| 4 = @ppd_else
+| 5 = @ppd_endif
+| 6 = @ppd_plain_include
+| 7 = @ppd_define
+| 8 = @ppd_undef
+| 9 = @ppd_line
+| 10 = @ppd_error
+| 11 = @ppd_pragma
+| 12 = @ppd_objc_import
+| 13 = @ppd_include_next
+| 18 = @ppd_warning
+;
+
+@ppd_include = @ppd_plain_include | @ppd_objc_import | @ppd_include_next;
+
+@ppd_branch = @ppd_if | @ppd_ifdef | @ppd_ifndef | @ppd_elif;
+
+preprocpair(
+ int begin : @ppd_branch ref,
+ int elseelifend : @preprocdirect ref
+);
+
+preproctrue(int branch : @ppd_branch ref);
+preprocfalse(int branch : @ppd_branch ref);
+
+preproctext(
+ unique int id: @preprocdirect ref,
+ string head: string ref,
+ string body: string ref
+);
+
+includes(
+ unique int id: @ppd_include ref,
+ int included: @file ref
+);
+
+link_targets(
+ unique int id: @link_target,
+ int binary: @file ref
+);
+
+link_parent(
+ int element : @element ref,
+ int link_target : @link_target ref
+);
+
+/* XML Files */
+
+xmlEncoding(unique int id: @file ref, string encoding: string ref);
+
+xmlDTDs(
+ unique int id: @xmldtd,
+ string root: string ref,
+ string publicId: string ref,
+ string systemId: string ref,
+ int fileid: @file ref
+);
+
+xmlElements(
+ unique int id: @xmlelement,
+ string name: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlAttrs(
+ unique int id: @xmlattribute,
+ int elementid: @xmlelement ref,
+ string name: string ref,
+ string value: string ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlNs(
+ int id: @xmlnamespace,
+ string prefixName: string ref,
+ string URI: string ref,
+ int fileid: @file ref
+);
+
+xmlHasNs(
+ int elementId: @xmlnamespaceable ref,
+ int nsId: @xmlnamespace ref,
+ int fileid: @file ref
+);
+
+xmlComments(
+ unique int id: @xmlcomment,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int fileid: @file ref
+);
+
+xmlChars(
+ unique int id: @xmlcharacters,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int isCDATA: int ref,
+ int fileid: @file ref
+);
+
+@xmlparent = @file | @xmlelement;
+@xmlnamespaceable = @xmlelement | @xmlattribute;
+
+xmllocations(
+ int xmlElement: @xmllocatable ref,
+ int location: @location_default ref
+);
+
+@xmllocatable = @xmlcharacters
+ | @xmlelement
+ | @xmlcomment
+ | @xmlattribute
+ | @xmldtd
+ | @file
+ | @xmlnamespace;
diff --git a/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/semmlecode.cpp.dbscheme b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/semmlecode.cpp.dbscheme
new file mode 100644
index 00000000000..0a9eb01d365
--- /dev/null
+++ b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/semmlecode.cpp.dbscheme
@@ -0,0 +1,2233 @@
+
+/**
+ * An invocation of the compiler. Note that more than one file may be
+ * compiled per invocation. For example, this command compiles three
+ * source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * The `id` simply identifies the invocation, while `cwd` is the working
+ * directory from which the compiler was invoked.
+ */
+compilations(
+ /**
+ * An invocation of the compiler. Note that more than one file may
+ * be compiled per invocation. For example, this command compiles
+ * three source files:
+ *
+ * gcc -c f1.c f2.c f3.c
+ */
+ unique int id : @compilation,
+ string cwd : string ref
+);
+
+/**
+ * The arguments that were passed to the extractor for a compiler
+ * invocation. If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then typically there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | *path to extractor*
+ * 1 | `--mimic`
+ * 2 | `/usr/bin/gcc`
+ * 3 | `-c`
+ * 4 | f1.c
+ * 5 | f2.c
+ * 6 | f3.c
+ */
+#keyset[id, num]
+compilation_args(
+ int id : @compilation ref,
+ int num : int ref,
+ string arg : string ref
+);
+
+/**
+ * The source files that are compiled by a compiler invocation.
+ * If `id` is for the compiler invocation
+ *
+ * gcc -c f1.c f2.c f3.c
+ *
+ * then there will be rows for
+ *
+ * num | arg
+ * --- | ---
+ * 0 | f1.c
+ * 1 | f2.c
+ * 2 | f3.c
+ *
+ * Note that even if those files `#include` headers, those headers
+ * do not appear as rows.
+ */
+#keyset[id, num]
+compilation_compiling_files(
+ int id : @compilation ref,
+ int num : int ref,
+ int file : @file ref
+);
+
+/**
+ * The time taken by the extractor for a compiler invocation.
+ *
+ * For each file `num`, there will be rows for
+ *
+ * kind | seconds
+ * ---- | ---
+ * 1 | CPU seconds used by the extractor frontend
+ * 2 | Elapsed seconds during the extractor frontend
+ * 3 | CPU seconds used by the extractor backend
+ * 4 | Elapsed seconds during the extractor backend
+ */
+#keyset[id, num, kind]
+compilation_time(
+ int id : @compilation ref,
+ int num : int ref,
+ /* kind:
+ 1 = frontend_cpu_seconds
+ 2 = frontend_elapsed_seconds
+ 3 = extractor_cpu_seconds
+ 4 = extractor_elapsed_seconds
+ */
+ int kind : int ref,
+ float seconds : float ref
+);
+
+/**
+ * An error or warning generated by the extractor.
+ * The diagnostic message `diagnostic` was generated during compiler
+ * invocation `compilation`, and is the `file_number_diagnostic_number`th
+ * message generated while extracting the `file_number`th file of that
+ * invocation.
+ */
+#keyset[compilation, file_number, file_number_diagnostic_number]
+diagnostic_for(
+ int diagnostic : @diagnostic ref,
+ int compilation : @compilation ref,
+ int file_number : int ref,
+ int file_number_diagnostic_number : int ref
+);
+
+/**
+ * If extraction was successful, then `cpu_seconds` and
+ * `elapsed_seconds` are the CPU time and elapsed time (respectively)
+ * that extraction took for compiler invocation `id`.
+ */
+compilation_finished(
+ unique int id : @compilation ref,
+ float cpu_seconds : float ref,
+ float elapsed_seconds : float ref
+);
+
+
+/**
+ * External data, loaded from CSV files during snapshot creation. See
+ * [Tutorial: Incorporating external data](https://help.semmle.com/wiki/display/SD/Tutorial%3A+Incorporating+external+data)
+ * for more information.
+ */
+externalData(
+ int id : @externalDataElement,
+ string path : string ref,
+ int column: int ref,
+ string value : string ref
+);
+
+/**
+ * The source location of the snapshot.
+ */
+sourceLocationPrefix(string prefix : string ref);
+
+/**
+ * Information about packages that provide code used during compilation.
+ * The `id` is just a unique identifier.
+ * The `namespace` is typically the name of the package manager that
+ * provided the package (e.g. "dpkg" or "yum").
+ * The `package_name` is the name of the package, and `version` is its
+ * version (as a string).
+ */
+external_packages(
+ unique int id: @external_package,
+ string namespace : string ref,
+ string package_name : string ref,
+ string version : string ref
+);
+
+/**
+ * Holds if File `fileid` was provided by package `package`.
+ */
+header_to_external_package(
+ int fileid : @file ref,
+ int package : @external_package ref
+);
+
+/*
+ * Version history
+ */
+
+svnentries(
+ unique int id : @svnentry,
+ string revision : string ref,
+ string author : string ref,
+ date revisionDate : date ref,
+ int changeSize : int ref
+)
+
+svnaffectedfiles(
+ int id : @svnentry ref,
+ int file : @file ref,
+ string action : string ref
+)
+
+svnentrymsg(
+ unique int id : @svnentry ref,
+ string message : string ref
+)
+
+svnchurn(
+ int commit : @svnentry ref,
+ int file : @file ref,
+ int addedLines : int ref,
+ int deletedLines : int ref
+)
+
+/*
+ * C++ dbscheme
+ */
+
+extractor_version(
+ string codeql_version: string ref,
+ string frontend_version: string ref
+)
+
+@location = @location_stmt | @location_expr | @location_default ;
+
+/**
+ * The location of an element that is not an expression or a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_default(
+ /** The location of an element that is not an expression or a statement. */
+ unique int id: @location_default,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of a statement.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_stmt(
+ /** The location of a statement. */
+ unique int id: @location_stmt,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/**
+ * The location of an expression.
+ * The location spans column `startcolumn` of line `startline` to
+ * column `endcolumn` of line `endline` in file `file`.
+ * For more information, see
+ * [Locations](https://codeql.github.com/docs/writing-codeql-queries/providing-locations-in-codeql-queries/).
+ */
+locations_expr(
+ /** The location of an expression. */
+ unique int id: @location_expr,
+ int container: @container ref,
+ int startLine: int ref,
+ int startColumn: int ref,
+ int endLine: int ref,
+ int endColumn: int ref
+);
+
+/** An element for which line-count information is available. */
+@sourceline = @file | @function | @variable | @enumconstant | @xmllocatable;
+
+numlines(
+ int element_id: @sourceline ref,
+ int num_lines: int ref,
+ int num_code: int ref,
+ int num_comment: int ref
+);
+
+diagnostics(
+ unique int id: @diagnostic,
+ int severity: int ref,
+ string error_tag: string ref,
+ string error_message: string ref,
+ string full_error_message: string ref,
+ int location: @location_default ref
+);
+
+files(
+ unique int id: @file,
+ string name: string ref
+);
+
+folders(
+ unique int id: @folder,
+ string name: string ref
+);
+
+@container = @folder | @file
+
+containerparent(
+ int parent: @container ref,
+ unique int child: @container ref
+);
+
+fileannotations(
+ int id: @file ref,
+ int kind: int ref,
+ string name: string ref,
+ string value: string ref
+);
+
+inmacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+affectedbymacroexpansion(
+ int id: @element ref,
+ int inv: @macroinvocation ref
+);
+
+case @macroinvocation.kind of
+ 1 = @macro_expansion
+| 2 = @other_macro_reference
+;
+
+macroinvocations(
+ unique int id: @macroinvocation,
+ int macro_id: @ppd_define ref,
+ int location: @location_default ref,
+ int kind: int ref
+);
+
+macroparent(
+ unique int id: @macroinvocation ref,
+ int parent_id: @macroinvocation ref
+);
+
+// a macroinvocation may be part of another location
+// the way to find a constant expression that uses a macro
+// is thus to find a constant expression that has a location
+// to which a macro invocation is bound
+macrolocationbind(
+ int id: @macroinvocation ref,
+ int location: @location ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_unexpanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+#keyset[invocation, argument_index]
+macro_argument_expanded(
+ int invocation: @macroinvocation ref,
+ int argument_index: int ref,
+ string text: string ref
+);
+
+/*
+case @function.kind of
+ 1 = @normal_function
+| 2 = @constructor
+| 3 = @destructor
+| 4 = @conversion_function
+| 5 = @operator
+| 6 = @builtin_function // GCC built-in functions, e.g. __builtin___memcpy_chk
+;
+*/
+
+functions(
+ unique int id: @function,
+ string name: string ref,
+ int kind: int ref
+);
+
+function_entry_point(
+ int id: @function ref,
+ unique int entry_point: @stmt ref
+);
+
+function_return_type(
+ int id: @function ref,
+ int return_type: @type ref
+);
+
+/**
+ * If `function` is a coroutine, then this gives the `std::experimental::resumable_traits`
+ * instance associated with it, and the variables representing the `handle` and `promise`
+ * for it.
+ */
+coroutine(
+ unique int function: @function ref,
+ int traits: @type ref,
+ int handle: @variable ref,
+ int promise: @variable ref
+);
+
+/** The `new` function used for allocating the coroutine state, if any. */
+coroutine_new(
+ unique int function: @function ref,
+ int new: @function ref
+);
+
+/** The `delete` function used for deallocating the coroutine state, if any. */
+coroutine_delete(
+ unique int function: @function ref,
+ int delete: @function ref
+);
+
+purefunctions(unique int id: @function ref);
+
+function_deleted(unique int id: @function ref);
+
+function_defaulted(unique int id: @function ref);
+
+function_prototyped(unique int id: @function ref)
+
+member_function_this_type(
+ unique int id: @function ref,
+ int this_type: @type ref
+);
+
+#keyset[id, type_id]
+fun_decls(
+ int id: @fun_decl,
+ int function: @function ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+fun_def(unique int id: @fun_decl ref);
+fun_specialized(unique int id: @fun_decl ref);
+fun_implicit(unique int id: @fun_decl ref);
+fun_decl_specifiers(
+ int id: @fun_decl ref,
+ string name: string ref
+)
+#keyset[fun_decl, index]
+fun_decl_throws(
+ int fun_decl: @fun_decl ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+/* an empty throw specification is different from none */
+fun_decl_empty_throws(unique int fun_decl: @fun_decl ref);
+fun_decl_noexcept(
+ int fun_decl: @fun_decl ref,
+ int constant: @expr ref
+);
+fun_decl_empty_noexcept(int fun_decl: @fun_decl ref);
+fun_decl_typedef_type(
+ unique int fun_decl: @fun_decl ref,
+ int typedeftype_id: @usertype ref
+);
+
+param_decl_bind(
+ unique int id: @var_decl ref,
+ int index: int ref,
+ int fun_decl: @fun_decl ref
+);
+
+#keyset[id, type_id]
+var_decls(
+ int id: @var_decl,
+ int variable: @variable ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+var_def(unique int id: @var_decl ref);
+var_decl_specifiers(
+ int id: @var_decl ref,
+ string name: string ref
+)
+is_structured_binding(unique int id: @variable ref);
+
+type_decls(
+ unique int id: @type_decl,
+ int type_id: @type ref,
+ int location: @location_default ref
+);
+type_def(unique int id: @type_decl ref);
+type_decl_top(
+ unique int type_decl: @type_decl ref
+);
+
+namespace_decls(
+ unique int id: @namespace_decl,
+ int namespace_id: @namespace ref,
+ int location: @location_default ref,
+ int bodylocation: @location_default ref
+);
+
+usings(
+ unique int id: @using,
+ int element_id: @element ref,
+ int location: @location_default ref
+);
+
+/** The element which contains the `using` declaration. */
+using_container(
+ int parent: @element ref,
+ int child: @using ref
+);
+
+static_asserts(
+ unique int id: @static_assert,
+ int condition : @expr ref,
+ string message : string ref,
+ int location: @location_default ref,
+ int enclosing : @element ref
+);
+
+// each function has an ordered list of parameters
+#keyset[id, type_id]
+#keyset[function, index, type_id]
+params(
+ int id: @parameter,
+ int function: @functionorblock ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+overrides(
+ int new: @function ref,
+ int old: @function ref
+);
+
+#keyset[id, type_id]
+membervariables(
+ int id: @membervariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+globalvariables(
+ int id: @globalvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+#keyset[id, type_id]
+localvariables(
+ int id: @localvariable,
+ int type_id: @type ref,
+ string name: string ref
+);
+
+autoderivation(
+ unique int var: @variable ref,
+ int derivation_type: @type ref
+);
+
+orphaned_variables(
+ int var: @localvariable ref,
+ int function: @function ref
+)
+
+enumconstants(
+ unique int id: @enumconstant,
+ int parent: @usertype ref,
+ int index: int ref,
+ int type_id: @type ref,
+ string name: string ref,
+ int location: @location_default ref
+);
+
+@variable = @localscopevariable | @globalvariable | @membervariable;
+
+@localscopevariable = @localvariable | @parameter;
+
+/**
+ * Built-in types are the fundamental types, e.g., integral, floating, and void.
+ */
+case @builtintype.kind of
+ 1 = @errortype
+| 2 = @unknowntype
+| 3 = @void
+| 4 = @boolean
+| 5 = @char
+| 6 = @unsigned_char
+| 7 = @signed_char
+| 8 = @short
+| 9 = @unsigned_short
+| 10 = @signed_short
+| 11 = @int
+| 12 = @unsigned_int
+| 13 = @signed_int
+| 14 = @long
+| 15 = @unsigned_long
+| 16 = @signed_long
+| 17 = @long_long
+| 18 = @unsigned_long_long
+| 19 = @signed_long_long
+// ... 20 Microsoft-specific __int8
+// ... 21 Microsoft-specific __int16
+// ... 22 Microsoft-specific __int32
+// ... 23 Microsoft-specific __int64
+| 24 = @float
+| 25 = @double
+| 26 = @long_double
+| 27 = @complex_float // C99-specific _Complex float
+| 28 = @complex_double // C99-specific _Complex double
+| 29 = @complex_long_double // C99-specific _Complex long double
+| 30 = @imaginary_float // C99-specific _Imaginary float
+| 31 = @imaginary_double // C99-specific _Imaginary double
+| 32 = @imaginary_long_double // C99-specific _Imaginary long double
+| 33 = @wchar_t // Microsoft-specific
+| 34 = @decltype_nullptr // C++11
+| 35 = @int128 // __int128
+| 36 = @unsigned_int128 // unsigned __int128
+| 37 = @signed_int128 // signed __int128
+| 38 = @float128 // __float128
+| 39 = @complex_float128 // _Complex __float128
+| 40 = @decimal32 // _Decimal32
+| 41 = @decimal64 // _Decimal64
+| 42 = @decimal128 // _Decimal128
+| 43 = @char16_t
+| 44 = @char32_t
+| 45 = @std_float32 // _Float32
+| 46 = @float32x // _Float32x
+| 47 = @std_float64 // _Float64
+| 48 = @float64x // _Float64x
+| 49 = @std_float128 // _Float128
+// ... 50 _Float128x
+| 51 = @char8_t
+| 52 = @float16 // _Float16
+| 53 = @complex_float16 // _Complex _Float16
+| 54 = @fp16 // __fp16
+| 55 = @std_bfloat16 // __bf16
+| 56 = @std_float16 // std::float16_t
+| 57 = @complex_std_float32 // _Complex _Float32
+| 58 = @complex_float32x // _Complex _Float32x
+| 59 = @complex_std_float64 // _Complex _Float64
+| 60 = @complex_float64x // _Complex _Float64x
+| 61 = @complex_std_float128 // _Complex _Float128
+;
+
+builtintypes(
+ unique int id: @builtintype,
+ string name: string ref,
+ int kind: int ref,
+ int size: int ref,
+ int sign: int ref,
+ int alignment: int ref
+);
+
+/**
+ * Derived types are types that are directly derived from existing types and
+ * point to, refer to, transform type data to return a new type.
+ */
+case @derivedtype.kind of
+ 1 = @pointer
+| 2 = @reference
+| 3 = @type_with_specifiers
+| 4 = @array
+| 5 = @gnu_vector
+| 6 = @routineptr
+| 7 = @routinereference
+| 8 = @rvalue_reference // C++11
+// ... 9 type_conforming_to_protocols deprecated
+| 10 = @block
+;
+
+derivedtypes(
+ unique int id: @derivedtype,
+ string name: string ref,
+ int kind: int ref,
+ int type_id: @type ref
+);
+
+pointerishsize(unique int id: @derivedtype ref,
+ int size: int ref,
+ int alignment: int ref);
+
+arraysizes(
+ unique int id: @derivedtype ref,
+ int num_elements: int ref,
+ int bytesize: int ref,
+ int alignment: int ref
+);
+
+typedefbase(
+ unique int id: @usertype ref,
+ int type_id: @type ref
+);
+
+/**
+ * An instance of the C++11 `decltype` operator. For example:
+ * ```
+ * int a;
+ * decltype(1+a) b;
+ * ```
+ * Here `expr` is `1+a`.
+ *
+ * Sometimes an additional pair of parentheses around the expression
+ * would change the semantics of this decltype, e.g.
+ * ```
+ * struct A { double x; };
+ * const A* a = new A();
+ * decltype( a->x ); // type is double
+ * decltype((a->x)); // type is const double&
+ * ```
+ * (Please consult the C++11 standard for more details).
+ * `parentheses_would_change_meaning` is `true` iff that is the case.
+ */
+#keyset[id, expr]
+decltypes(
+ int id: @decltype,
+ int expr: @expr ref,
+ int base_type: @type ref,
+ boolean parentheses_would_change_meaning: boolean ref
+);
+
+/*
+case @usertype.kind of
+ 1 = @struct
+| 2 = @class
+| 3 = @union
+| 4 = @enum
+| 5 = @typedef // classic C: typedef typedef type name
+| 6 = @template
+| 7 = @template_parameter
+| 8 = @template_template_parameter
+| 9 = @proxy_class // a proxy class associated with a template parameter
+// ... 10 objc_class deprecated
+// ... 11 objc_protocol deprecated
+// ... 12 objc_category deprecated
+| 13 = @scoped_enum
+| 14 = @using_alias // a using name = type style typedef
+;
+*/
+
+usertypes(
+ unique int id: @usertype,
+ string name: string ref,
+ int kind: int ref
+);
+
+usertypesize(
+ unique int id: @usertype ref,
+ int size: int ref,
+ int alignment: int ref
+);
+
+usertype_final(unique int id: @usertype ref);
+
+usertype_uuid(
+ unique int id: @usertype ref,
+ string uuid: string ref
+);
+
+mangled_name(
+ unique int id: @declaration ref,
+ int mangled_name : @mangledname
+);
+
+is_pod_class(unique int id: @usertype ref);
+is_standard_layout_class(unique int id: @usertype ref);
+
+is_complete(unique int id: @usertype ref);
+
+is_class_template(unique int id: @usertype ref);
+class_instantiation(
+ int to: @usertype ref,
+ int from: @usertype ref
+);
+class_template_argument(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+class_template_argument_value(
+ int type_id: @usertype ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_proxy_class_for(
+ unique int id: @usertype ref,
+ unique int templ_param_id: @usertype ref
+);
+
+type_mentions(
+ unique int id: @type_mention,
+ int type_id: @type ref,
+ int location: @location ref,
+ // a_symbol_reference_kind from the frontend.
+ int kind: int ref
+);
+
+is_function_template(unique int id: @function ref);
+function_instantiation(
+ unique int to: @function ref,
+ int from: @function ref
+);
+function_template_argument(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+function_template_argument_value(
+ int function_id: @function ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+is_variable_template(unique int id: @variable ref);
+variable_instantiation(
+ unique int to: @variable ref,
+ int from: @variable ref
+);
+variable_template_argument(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_type: @type ref
+);
+variable_template_argument_value(
+ int variable_id: @variable ref,
+ int index: int ref,
+ int arg_value: @expr ref
+);
+
+/*
+ Fixed point types
+ precision(1) = short, precision(2) = default, precision(3) = long
+ is_unsigned(1) = unsigned is_unsigned(2) = signed
+ is_fract_type(1) = declared with _Fract
+ saturating(1) = declared with _Sat
+*/
+/* TODO
+fixedpointtypes(
+ unique int id: @fixedpointtype,
+ int precision: int ref,
+ int is_unsigned: int ref,
+ int is_fract_type: int ref,
+ int saturating: int ref);
+*/
+
+routinetypes(
+ unique int id: @routinetype,
+ int return_type: @type ref
+);
+
+routinetypeargs(
+ int routine: @routinetype ref,
+ int index: int ref,
+ int type_id: @type ref
+);
+
+ptrtomembers(
+ unique int id: @ptrtomember,
+ int type_id: @type ref,
+ int class_id: @type ref
+);
+
+/*
+ specifiers for types, functions, and variables
+
+ "public",
+ "protected",
+ "private",
+
+ "const",
+ "volatile",
+ "static",
+
+ "pure",
+ "virtual",
+ "sealed", // Microsoft
+ "__interface", // Microsoft
+ "inline",
+ "explicit",
+
+ "near", // near far extension
+ "far", // near far extension
+ "__ptr32", // Microsoft
+ "__ptr64", // Microsoft
+ "__sptr", // Microsoft
+ "__uptr", // Microsoft
+ "dllimport", // Microsoft
+ "dllexport", // Microsoft
+ "thread", // Microsoft
+ "naked", // Microsoft
+ "microsoft_inline", // Microsoft
+ "forceinline", // Microsoft
+ "selectany", // Microsoft
+ "nothrow", // Microsoft
+ "novtable", // Microsoft
+ "noreturn", // Microsoft
+ "noinline", // Microsoft
+ "noalias", // Microsoft
+ "restrict", // Microsoft
+*/
+
+specifiers(
+ unique int id: @specifier,
+ unique string str: string ref
+);
+
+typespecifiers(
+ int type_id: @type ref,
+ int spec_id: @specifier ref
+);
+
+funspecifiers(
+ int func_id: @function ref,
+ int spec_id: @specifier ref
+);
+
+varspecifiers(
+ int var_id: @accessible ref,
+ int spec_id: @specifier ref
+);
+
+attributes(
+ unique int id: @attribute,
+ int kind: int ref,
+ string name: string ref,
+ string name_space: string ref,
+ int location: @location_default ref
+);
+
+case @attribute.kind of
+ 0 = @gnuattribute
+| 1 = @stdattribute
+| 2 = @declspec
+| 3 = @msattribute
+| 4 = @alignas
+// ... 5 @objc_propertyattribute deprecated
+;
+
+attribute_args(
+ unique int id: @attribute_arg,
+ int kind: int ref,
+ int attribute: @attribute ref,
+ int index: int ref,
+ int location: @location_default ref
+);
+
+case @attribute_arg.kind of
+ 0 = @attribute_arg_empty
+| 1 = @attribute_arg_token
+| 2 = @attribute_arg_constant
+| 3 = @attribute_arg_type
+| 4 = @attribute_arg_constant_expr
+;
+
+attribute_arg_value(
+ unique int arg: @attribute_arg ref,
+ string value: string ref
+);
+attribute_arg_type(
+ unique int arg: @attribute_arg ref,
+ int type_id: @type ref
+);
+attribute_arg_constant(
+ unique int arg: @attribute_arg ref,
+ int constant: @expr ref
+)
+attribute_arg_name(
+ unique int arg: @attribute_arg ref,
+ string name: string ref
+);
+
+typeattributes(
+ int type_id: @type ref,
+ int spec_id: @attribute ref
+);
+
+funcattributes(
+ int func_id: @function ref,
+ int spec_id: @attribute ref
+);
+
+varattributes(
+ int var_id: @accessible ref,
+ int spec_id: @attribute ref
+);
+
+stmtattributes(
+ int stmt_id: @stmt ref,
+ int spec_id: @attribute ref
+);
+
+@type = @builtintype
+ | @derivedtype
+ | @usertype
+ /* TODO | @fixedpointtype */
+ | @routinetype
+ | @ptrtomember
+ | @decltype;
+
+unspecifiedtype(
+ unique int type_id: @type ref,
+ int unspecified_type_id: @type ref
+);
+
+member(
+ int parent: @type ref,
+ int index: int ref,
+ int child: @member ref
+);
+
+@enclosingfunction_child = @usertype | @variable | @namespace
+
+enclosingfunction(
+ unique int child: @enclosingfunction_child ref,
+ int parent: @function ref
+);
+
+derivations(
+ unique int derivation: @derivation,
+ int sub: @type ref,
+ int index: int ref,
+ int super: @type ref,
+ int location: @location_default ref
+);
+
+derspecifiers(
+ int der_id: @derivation ref,
+ int spec_id: @specifier ref
+);
+
+/**
+ * Contains the byte offset of the base class subobject within the derived
+ * class. Only holds for non-virtual base classes, but see table
+ * `virtual_base_offsets` for offsets of virtual base class subobjects.
+ */
+direct_base_offsets(
+ unique int der_id: @derivation ref,
+ int offset: int ref
+);
+
+/**
+ * Contains the byte offset of the virtual base class subobject for class
+ * `super` within a most-derived object of class `sub`. `super` can be either a
+ * direct or indirect base class.
+ */
+#keyset[sub, super]
+virtual_base_offsets(
+ int sub: @usertype ref,
+ int super: @usertype ref,
+ int offset: int ref
+);
+
+frienddecls(
+ unique int id: @frienddecl,
+ int type_id: @type ref,
+ int decl_id: @declaration ref,
+ int location: @location_default ref
+);
+
+@declaredtype = @usertype ;
+
+@declaration = @function
+ | @declaredtype
+ | @variable
+ | @enumconstant
+ | @frienddecl;
+
+@member = @membervariable
+ | @function
+ | @declaredtype
+ | @enumconstant;
+
+@locatable = @diagnostic
+ | @declaration
+ | @ppd_include
+ | @ppd_define
+ | @macroinvocation
+ /*| @funcall*/
+ | @xmllocatable
+ | @attribute
+ | @attribute_arg;
+
+@namedscope = @namespace | @usertype;
+
+@element = @locatable
+ | @file
+ | @folder
+ | @specifier
+ | @type
+ | @expr
+ | @namespace
+ | @initialiser
+ | @stmt
+ | @derivation
+ | @comment
+ | @preprocdirect
+ | @fun_decl
+ | @var_decl
+ | @type_decl
+ | @namespace_decl
+ | @using
+ | @namequalifier
+ | @specialnamequalifyingelement
+ | @static_assert
+ | @type_mention
+ | @lambdacapture;
+
+@exprparent = @element;
+
+comments(
+ unique int id: @comment,
+ string contents: string ref,
+ int location: @location_default ref
+);
+
+commentbinding(
+ int id: @comment ref,
+ int element: @element ref
+);
+
+exprconv(
+ int converted: @expr ref,
+ unique int conversion: @expr ref
+);
+
+compgenerated(unique int id: @element ref);
+
+/**
+ * `destructor_call` destructs the `i`'th entity that should be
+ * destructed following `element`. Note that entities should be
+ * destructed in reverse construction order, so for a given `element`
+ * these should be called from highest to lowest `i`.
+ */
+#keyset[element, destructor_call]
+#keyset[element, i]
+synthetic_destructor_call(
+ int element: @element ref,
+ int i: int ref,
+ int destructor_call: @routineexpr ref
+);
+
+namespaces(
+ unique int id: @namespace,
+ string name: string ref
+);
+
+namespace_inline(
+ unique int id: @namespace ref
+);
+
+namespacembrs(
+ int parentid: @namespace ref,
+ unique int memberid: @namespacembr ref
+);
+
+@namespacembr = @declaration | @namespace;
+
+exprparents(
+ int expr_id: @expr ref,
+ int child_index: int ref,
+ int parent_id: @exprparent ref
+);
+
+expr_isload(unique int expr_id: @expr ref);
+
+@cast = @c_style_cast
+ | @const_cast
+ | @dynamic_cast
+ | @reinterpret_cast
+ | @static_cast
+ ;
+
+/*
+case @conversion.kind of
+ 0 = @simple_conversion // a numeric conversion, qualification conversion, or a reinterpret_cast
+| 1 = @bool_conversion // conversion to 'bool'
+| 2 = @base_class_conversion // a derived-to-base conversion
+| 3 = @derived_class_conversion // a base-to-derived conversion
+| 4 = @pm_base_class_conversion // a derived-to-base conversion of a pointer to member
+| 5 = @pm_derived_class_conversion // a base-to-derived conversion of a pointer to member
+| 6 = @glvalue_adjust // an adjustment of the type of a glvalue
+| 7 = @prvalue_adjust // an adjustment of the type of a prvalue
+;
+*/
+/**
+ * Describes the semantics represented by a cast expression. This is largely
+ * independent of the source syntax of the cast, so it is separate from the
+ * regular expression kind.
+ */
+conversionkinds(
+ unique int expr_id: @cast ref,
+ int kind: int ref
+);
+
+@conversion = @cast
+ | @array_to_pointer
+ | @parexpr
+ | @reference_to
+ | @ref_indirect
+ | @temp_init
+ ;
+
+/*
+case @funbindexpr.kind of
+ 0 = @normal_call // a normal call
+| 1 = @virtual_call // a virtual call
+| 2 = @adl_call // a call whose target is only found by ADL
+;
+*/
+iscall(
+ unique int caller: @funbindexpr ref,
+ int kind: int ref
+);
+
+numtemplatearguments(
+ unique int expr_id: @expr ref,
+ int num: int ref
+);
+
+specialnamequalifyingelements(
+ unique int id: @specialnamequalifyingelement,
+ unique string name: string ref
+);
+
+@namequalifiableelement = @expr | @namequalifier;
+@namequalifyingelement = @namespace
+ | @specialnamequalifyingelement
+ | @usertype;
+
+namequalifiers(
+ unique int id: @namequalifier,
+ unique int qualifiableelement: @namequalifiableelement ref,
+ int qualifyingelement: @namequalifyingelement ref,
+ int location: @location_default ref
+);
+
+varbind(
+ int expr: @varbindexpr ref,
+ int var: @accessible ref
+);
+
+funbind(
+ int expr: @funbindexpr ref,
+ int fun: @function ref
+);
+
+@any_new_expr = @new_expr
+ | @new_array_expr;
+
+@new_or_delete_expr = @any_new_expr
+ | @delete_expr
+ | @delete_array_expr;
+
+@prefix_crement_expr = @preincrexpr | @predecrexpr;
+
+@postfix_crement_expr = @postincrexpr | @postdecrexpr;
+
+@increment_expr = @preincrexpr | @postincrexpr;
+
+@decrement_expr = @predecrexpr | @postdecrexpr;
+
+@crement_expr = @increment_expr | @decrement_expr;
+
+@un_arith_op_expr = @arithnegexpr
+ | @unaryplusexpr
+ | @conjugation
+ | @realpartexpr
+ | @imagpartexpr
+ | @crement_expr
+ ;
+
+@un_bitwise_op_expr = @complementexpr;
+
+@un_log_op_expr = @notexpr;
+
+@un_op_expr = @address_of
+ | @indirect
+ | @un_arith_op_expr
+ | @un_bitwise_op_expr
+ | @builtinaddressof
+ | @vec_fill
+ | @un_log_op_expr
+ | @co_await
+ | @co_yield
+ ;
+
+@bin_log_op_expr = @andlogicalexpr | @orlogicalexpr;
+
+@cmp_op_expr = @eq_op_expr | @rel_op_expr;
+
+@eq_op_expr = @eqexpr | @neexpr;
+
+@rel_op_expr = @gtexpr
+ | @ltexpr
+ | @geexpr
+ | @leexpr
+ | @spaceshipexpr
+ ;
+
+@bin_bitwise_op_expr = @lshiftexpr
+ | @rshiftexpr
+ | @andexpr
+ | @orexpr
+ | @xorexpr
+ ;
+
+@p_arith_op_expr = @paddexpr
+ | @psubexpr
+ | @pdiffexpr
+ ;
+
+@bin_arith_op_expr = @addexpr
+ | @subexpr
+ | @mulexpr
+ | @divexpr
+ | @remexpr
+ | @jmulexpr
+ | @jdivexpr
+ | @fjaddexpr
+ | @jfaddexpr
+ | @fjsubexpr
+ | @jfsubexpr
+ | @minexpr
+ | @maxexpr
+ | @p_arith_op_expr
+ ;
+
+@bin_op_expr = @bin_arith_op_expr
+ | @bin_bitwise_op_expr
+ | @cmp_op_expr
+ | @bin_log_op_expr
+ ;
+
+@op_expr = @un_op_expr
+ | @bin_op_expr
+ | @assign_expr
+ | @conditionalexpr
+ ;
+
+@assign_arith_expr = @assignaddexpr
+ | @assignsubexpr
+ | @assignmulexpr
+ | @assigndivexpr
+ | @assignremexpr
+ ;
+
+@assign_bitwise_expr = @assignandexpr
+ | @assignorexpr
+ | @assignxorexpr
+ | @assignlshiftexpr
+ | @assignrshiftexpr
+ ;
+
+@assign_pointer_expr = @assignpaddexpr
+ | @assignpsubexpr
+ ;
+
+@assign_op_expr = @assign_arith_expr
+ | @assign_bitwise_expr
+ | @assign_pointer_expr
+ ;
+
+@assign_expr = @assignexpr | @assign_op_expr | @blockassignexpr
+
+/*
+ case @allocator.form of
+ 0 = plain
+ | 1 = alignment
+ ;
+*/
+
+/**
+ * The allocator function associated with a `new` or `new[]` expression.
+ * The `form` column specified whether the allocation call contains an alignment
+ * argument.
+ */
+expr_allocator(
+ unique int expr: @any_new_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/*
+ case @deallocator.form of
+ 0 = plain
+ | 1 = size
+ | 2 = alignment
+ | 3 = size_and_alignment
+ ;
+*/
+
+/**
+ * The deallocator function associated with a `delete`, `delete[]`, `new`, or
+ * `new[]` expression. For a `new` or `new[]` expression, the deallocator is the
+ * one used to free memory if the initialization throws an exception.
+ * The `form` column specifies whether the deallocation call contains a size
+ * argument, and alignment argument, or both.
+ */
+expr_deallocator(
+ unique int expr: @new_or_delete_expr ref,
+ int func: @function ref,
+ int form: int ref
+);
+
+/**
+ * Holds if the `@conditionalexpr` is of the two operand form
+ * `guard ? : false`.
+ */
+expr_cond_two_operand(
+ unique int cond: @conditionalexpr ref
+);
+
+/**
+ * The guard of `@conditionalexpr` `guard ? true : false`
+ */
+expr_cond_guard(
+ unique int cond: @conditionalexpr ref,
+ int guard: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` holds. For the two operand form
+ * `guard ?: false` consider using `expr_cond_guard` instead.
+ */
+expr_cond_true(
+ unique int cond: @conditionalexpr ref,
+ int true: @expr ref
+);
+
+/**
+ * The expression used when the guard of `@conditionalexpr`
+ * `guard ? true : false` does not hold.
+ */
+expr_cond_false(
+ unique int cond: @conditionalexpr ref,
+ int false: @expr ref
+);
+
+/** A string representation of the value. */
+values(
+ unique int id: @value,
+ string str: string ref
+);
+
+/** The actual text in the source code for the value, if any. */
+valuetext(
+ unique int id: @value ref,
+ string text: string ref
+);
+
+valuebind(
+ int val: @value ref,
+ unique int expr: @expr ref
+);
+
+fieldoffsets(
+ unique int id: @variable ref,
+ int byteoffset: int ref,
+ int bitoffset: int ref
+);
+
+bitfield(
+ unique int id: @variable ref,
+ int bits: int ref,
+ int declared_bits: int ref
+);
+
+/* TODO
+memberprefix(
+ int member: @expr ref,
+ int prefix: @expr ref
+);
+*/
+
+/*
+ kind(1) = mbrcallexpr
+ kind(2) = mbrptrcallexpr
+ kind(3) = mbrptrmbrcallexpr
+ kind(4) = ptrmbrptrmbrcallexpr
+ kind(5) = mbrreadexpr // x.y
+ kind(6) = mbrptrreadexpr // p->y
+ kind(7) = mbrptrmbrreadexpr // x.*pm
+ kind(8) = mbrptrmbrptrreadexpr // x->*pm
+ kind(9) = staticmbrreadexpr // static x.y
+ kind(10) = staticmbrptrreadexpr // static p->y
+*/
+/* TODO
+memberaccess(
+ int member: @expr ref,
+ int kind: int ref
+);
+*/
+
+initialisers(
+ unique int init: @initialiser,
+ int var: @accessible ref,
+ unique int expr: @expr ref,
+ int location: @location_expr ref
+);
+
+braced_initialisers(
+ int init: @initialiser ref
+);
+
+/**
+ * An ancestor for the expression, for cases in which we cannot
+ * otherwise find the expression's parent.
+ */
+expr_ancestor(
+ int exp: @expr ref,
+ int ancestor: @element ref
+);
+
+exprs(
+ unique int id: @expr,
+ int kind: int ref,
+ int location: @location_expr ref
+);
+
+/*
+ case @value.category of
+ 1 = prval
+ | 2 = xval
+ | 3 = lval
+ ;
+*/
+expr_types(
+ int id: @expr ref,
+ int typeid: @type ref,
+ int value_category: int ref
+);
+
+case @expr.kind of
+ 1 = @errorexpr
+| 2 = @address_of // & AddressOfExpr
+| 3 = @reference_to // ReferenceToExpr (implicit?)
+| 4 = @indirect // * PointerDereferenceExpr
+| 5 = @ref_indirect // ReferenceDereferenceExpr (implicit?)
+// ...
+| 8 = @array_to_pointer // (???)
+| 9 = @vacuous_destructor_call // VacuousDestructorCall
+// ...
+| 11 = @assume // Microsoft
+| 12 = @parexpr
+| 13 = @arithnegexpr
+| 14 = @unaryplusexpr
+| 15 = @complementexpr
+| 16 = @notexpr
+| 17 = @conjugation // GNU ~ operator
+| 18 = @realpartexpr // GNU __real
+| 19 = @imagpartexpr // GNU __imag
+| 20 = @postincrexpr
+| 21 = @postdecrexpr
+| 22 = @preincrexpr
+| 23 = @predecrexpr
+| 24 = @conditionalexpr
+| 25 = @addexpr
+| 26 = @subexpr
+| 27 = @mulexpr
+| 28 = @divexpr
+| 29 = @remexpr
+| 30 = @jmulexpr // C99 mul imaginary
+| 31 = @jdivexpr // C99 div imaginary
+| 32 = @fjaddexpr // C99 add real + imaginary
+| 33 = @jfaddexpr // C99 add imaginary + real
+| 34 = @fjsubexpr // C99 sub real - imaginary
+| 35 = @jfsubexpr // C99 sub imaginary - real
+| 36 = @paddexpr // pointer add (pointer + int or int + pointer)
+| 37 = @psubexpr // pointer sub (pointer - integer)
+| 38 = @pdiffexpr // difference between two pointers
+| 39 = @lshiftexpr
+| 40 = @rshiftexpr
+| 41 = @andexpr
+| 42 = @orexpr
+| 43 = @xorexpr
+| 44 = @eqexpr
+| 45 = @neexpr
+| 46 = @gtexpr
+| 47 = @ltexpr
+| 48 = @geexpr
+| 49 = @leexpr
+| 50 = @minexpr // GNU minimum
+| 51 = @maxexpr // GNU maximum
+| 52 = @assignexpr
+| 53 = @assignaddexpr
+| 54 = @assignsubexpr
+| 55 = @assignmulexpr
+| 56 = @assigndivexpr
+| 57 = @assignremexpr
+| 58 = @assignlshiftexpr
+| 59 = @assignrshiftexpr
+| 60 = @assignandexpr
+| 61 = @assignorexpr
+| 62 = @assignxorexpr
+| 63 = @assignpaddexpr // assign pointer add
+| 64 = @assignpsubexpr // assign pointer sub
+| 65 = @andlogicalexpr
+| 66 = @orlogicalexpr
+| 67 = @commaexpr
+| 68 = @subscriptexpr // access to member of an array, e.g., a[5]
+// ... 69 @objc_subscriptexpr deprecated
+// ... 70 @cmdaccess deprecated
+// ...
+| 73 = @virtfunptrexpr
+| 74 = @callexpr
+// ... 75 @msgexpr_normal deprecated
+// ... 76 @msgexpr_super deprecated
+// ... 77 @atselectorexpr deprecated
+// ... 78 @atprotocolexpr deprecated
+| 79 = @vastartexpr
+| 80 = @vaargexpr
+| 81 = @vaendexpr
+| 82 = @vacopyexpr
+// ... 83 @atencodeexpr deprecated
+| 84 = @varaccess
+| 85 = @thisaccess
+// ... 86 @objc_box_expr deprecated
+| 87 = @new_expr
+| 88 = @delete_expr
+| 89 = @throw_expr
+| 90 = @condition_decl // a variable declared in a condition, e.g., if(int x = y > 2)
+| 91 = @braced_init_list
+| 92 = @type_id
+| 93 = @runtime_sizeof
+| 94 = @runtime_alignof
+| 95 = @sizeof_pack
+| 96 = @expr_stmt // GNU extension
+| 97 = @routineexpr
+| 98 = @type_operand // used to access a type in certain contexts (haven't found any examples yet....)
+| 99 = @offsetofexpr // offsetof ::= type and field
+| 100 = @hasassignexpr // __has_assign ::= type
+| 101 = @hascopyexpr // __has_copy ::= type
+| 102 = @hasnothrowassign // __has_nothrow_assign ::= type
+| 103 = @hasnothrowconstr // __has_nothrow_constructor ::= type
+| 104 = @hasnothrowcopy // __has_nothrow_copy ::= type
+| 105 = @hastrivialassign // __has_trivial_assign ::= type
+| 106 = @hastrivialconstr // __has_trivial_constructor ::= type
+| 107 = @hastrivialcopy // __has_trivial_copy ::= type
+| 108 = @hasuserdestr // __has_user_destructor ::= type
+| 109 = @hasvirtualdestr // __has_virtual_destructor ::= type
+| 110 = @isabstractexpr // __is_abstract ::= type
+| 111 = @isbaseofexpr // __is_base_of ::= type type
+| 112 = @isclassexpr // __is_class ::= type
+| 113 = @isconvtoexpr // __is_convertible_to ::= type type
+| 114 = @isemptyexpr // __is_empty ::= type
+| 115 = @isenumexpr // __is_enum ::= type
+| 116 = @ispodexpr // __is_pod ::= type
+| 117 = @ispolyexpr // __is_polymorphic ::= type
+| 118 = @isunionexpr // __is_union ::= type
+| 119 = @typescompexpr // GNU __builtin_types_compatible ::= type type
+| 120 = @intaddrexpr // frontend internal builtin, used to implement offsetof
+// ...
+| 122 = @hastrivialdestructor // __has_trivial_destructor ::= type
+| 123 = @literal
+| 124 = @uuidof
+| 127 = @aggregateliteral
+| 128 = @delete_array_expr
+| 129 = @new_array_expr
+// ... 130 @objc_array_literal deprecated
+// ... 131 @objc_dictionary_literal deprecated
+| 132 = @foldexpr
+// ...
+| 200 = @ctordirectinit
+| 201 = @ctorvirtualinit
+| 202 = @ctorfieldinit
+| 203 = @ctordelegatinginit
+| 204 = @dtordirectdestruct
+| 205 = @dtorvirtualdestruct
+| 206 = @dtorfielddestruct
+// ...
+| 210 = @static_cast
+| 211 = @reinterpret_cast
+| 212 = @const_cast
+| 213 = @dynamic_cast
+| 214 = @c_style_cast
+| 215 = @lambdaexpr
+| 216 = @param_ref
+| 217 = @noopexpr
+// ...
+| 294 = @istriviallyconstructibleexpr
+| 295 = @isdestructibleexpr
+| 296 = @isnothrowdestructibleexpr
+| 297 = @istriviallydestructibleexpr
+| 298 = @istriviallyassignableexpr
+| 299 = @isnothrowassignableexpr
+| 300 = @istrivialexpr
+| 301 = @isstandardlayoutexpr
+| 302 = @istriviallycopyableexpr
+| 303 = @isliteraltypeexpr
+| 304 = @hastrivialmoveconstructorexpr
+| 305 = @hastrivialmoveassignexpr
+| 306 = @hasnothrowmoveassignexpr
+| 307 = @isconstructibleexpr
+| 308 = @isnothrowconstructibleexpr
+| 309 = @hasfinalizerexpr
+| 310 = @isdelegateexpr
+| 311 = @isinterfaceclassexpr
+| 312 = @isrefarrayexpr
+| 313 = @isrefclassexpr
+| 314 = @issealedexpr
+| 315 = @issimplevalueclassexpr
+| 316 = @isvalueclassexpr
+| 317 = @isfinalexpr
+| 319 = @noexceptexpr
+| 320 = @builtinshufflevector
+| 321 = @builtinchooseexpr
+| 322 = @builtinaddressof
+| 323 = @vec_fill
+| 324 = @builtinconvertvector
+| 325 = @builtincomplex
+| 326 = @spaceshipexpr
+| 327 = @co_await
+| 328 = @co_yield
+| 329 = @temp_init
+| 330 = @isassignable
+| 331 = @isaggregate
+| 332 = @hasuniqueobjectrepresentations
+| 333 = @builtinbitcast
+| 334 = @builtinshuffle
+| 335 = @blockassignexpr
+| 336 = @issame
+| 337 = @isfunction
+| 338 = @islayoutcompatible
+| 339 = @ispointerinterconvertiblebaseof
+| 340 = @isarray
+| 341 = @arrayrank
+| 342 = @arrayextent
+| 343 = @isarithmetic
+| 344 = @iscompletetype
+| 345 = @iscompound
+| 346 = @isconst
+| 347 = @isfloatingpoint
+| 348 = @isfundamental
+| 349 = @isintegral
+| 350 = @islvaluereference
+| 351 = @ismemberfunctionpointer
+| 352 = @ismemberobjectpointer
+| 353 = @ismemberpointer
+| 354 = @isobject
+| 355 = @ispointer
+| 356 = @isreference
+| 357 = @isrvaluereference
+| 358 = @isscalar
+| 359 = @issigned
+| 360 = @isunsigned
+| 361 = @isvoid
+| 362 = @isvolatile
+;
+
+@var_args_expr = @vastartexpr
+ | @vaendexpr
+ | @vaargexpr
+ | @vacopyexpr
+ ;
+
+@builtin_op = @var_args_expr
+ | @noopexpr
+ | @offsetofexpr
+ | @intaddrexpr
+ | @hasassignexpr
+ | @hascopyexpr
+ | @hasnothrowassign
+ | @hasnothrowconstr
+ | @hasnothrowcopy
+ | @hastrivialassign
+ | @hastrivialconstr
+ | @hastrivialcopy
+ | @hastrivialdestructor
+ | @hasuserdestr
+ | @hasvirtualdestr
+ | @isabstractexpr
+ | @isbaseofexpr
+ | @isclassexpr
+ | @isconvtoexpr
+ | @isemptyexpr
+ | @isenumexpr
+ | @ispodexpr
+ | @ispolyexpr
+ | @isunionexpr
+ | @typescompexpr
+ | @builtinshufflevector
+ | @builtinconvertvector
+ | @builtinaddressof
+ | @istriviallyconstructibleexpr
+ | @isdestructibleexpr
+ | @isnothrowdestructibleexpr
+ | @istriviallydestructibleexpr
+ | @istriviallyassignableexpr
+ | @isnothrowassignableexpr
+ | @istrivialexpr
+ | @isstandardlayoutexpr
+ | @istriviallycopyableexpr
+ | @isliteraltypeexpr
+ | @hastrivialmoveconstructorexpr
+ | @hastrivialmoveassignexpr
+ | @hasnothrowmoveassignexpr
+ | @isconstructibleexpr
+ | @isnothrowconstructibleexpr
+ | @hasfinalizerexpr
+ | @isdelegateexpr
+ | @isinterfaceclassexpr
+ | @isrefarrayexpr
+ | @isrefclassexpr
+ | @issealedexpr
+ | @issimplevalueclassexpr
+ | @isvalueclassexpr
+ | @isfinalexpr
+ | @builtinchooseexpr
+ | @builtincomplex
+ | @isassignable
+ | @isaggregate
+ | @hasuniqueobjectrepresentations
+ | @builtinbitcast
+ | @builtinshuffle
+ | @issame
+ | @isfunction
+ | @islayoutcompatible
+ | @ispointerinterconvertiblebaseof
+ | @isarray
+ | @arrayrank
+ | @arrayextent
+ | @isarithmetic
+ | @iscompletetype
+ | @iscompound
+ | @isconst
+ | @isfloatingpoint
+ | @isfundamental
+ | @isintegral
+ | @islvaluereference
+ | @ismemberfunctionpointer
+ | @ismemberobjectpointer
+ | @ismemberpointer
+ | @isobject
+ | @ispointer
+ | @isreference
+ | @isrvaluereference
+ | @isscalar
+ | @issigned
+ | @isunsigned
+ | @isvoid
+ | @isvolatile
+ ;
+
+new_allocated_type(
+ unique int expr: @new_expr ref,
+ int type_id: @type ref
+);
+
+new_array_allocated_type(
+ unique int expr: @new_array_expr ref,
+ int type_id: @type ref
+);
+
+/**
+ * The field being initialized by an initializer expression within an aggregate
+ * initializer for a class/struct/union. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_field_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int field: @membervariable ref,
+ int position: int ref
+);
+
+/**
+ * The index of the element being initialized by an initializer expression
+ * within an aggregate initializer for an array. Position is used to sort repeated initializers.
+ */
+#keyset[aggregate, position]
+aggregate_array_init(
+ int aggregate: @aggregateliteral ref,
+ int initializer: @expr ref,
+ int element_index: int ref,
+ int position: int ref
+);
+
+@ctorinit = @ctordirectinit
+ | @ctorvirtualinit
+ | @ctorfieldinit
+ | @ctordelegatinginit;
+@dtordestruct = @dtordirectdestruct
+ | @dtorvirtualdestruct
+ | @dtorfielddestruct;
+
+
+condition_decl_bind(
+ unique int expr: @condition_decl ref,
+ unique int decl: @declaration ref
+);
+
+typeid_bind(
+ unique int expr: @type_id ref,
+ int type_id: @type ref
+);
+
+uuidof_bind(
+ unique int expr: @uuidof ref,
+ int type_id: @type ref
+);
+
+@runtime_sizeof_or_alignof = @runtime_sizeof | @runtime_alignof;
+
+sizeof_bind(
+ unique int expr: @runtime_sizeof_or_alignof ref,
+ int type_id: @type ref
+);
+
+code_block(
+ unique int block: @literal ref,
+ unique int routine: @function ref
+);
+
+lambdas(
+ unique int expr: @lambdaexpr ref,
+ string default_capture: string ref,
+ boolean has_explicit_return_type: boolean ref
+);
+
+lambda_capture(
+ unique int id: @lambdacapture,
+ int lambda: @lambdaexpr ref,
+ int index: int ref,
+ int field: @membervariable ref,
+ boolean captured_by_reference: boolean ref,
+ boolean is_implicit: boolean ref,
+ int location: @location_default ref
+);
+
+@funbindexpr = @routineexpr
+ | @new_expr
+ | @delete_expr
+ | @delete_array_expr
+ | @ctordirectinit
+ | @ctorvirtualinit
+ | @ctordelegatinginit
+ | @dtordirectdestruct
+ | @dtorvirtualdestruct;
+
+@varbindexpr = @varaccess | @ctorfieldinit | @dtorfielddestruct;
+@addressable = @function | @variable ;
+@accessible = @addressable | @enumconstant ;
+
+@access = @varaccess | @routineexpr ;
+
+fold(
+ int expr: @foldexpr ref,
+ string operator: string ref,
+ boolean is_left_fold: boolean ref
+);
+
+stmts(
+ unique int id: @stmt,
+ int kind: int ref,
+ int location: @location_stmt ref
+);
+
+case @stmt.kind of
+ 1 = @stmt_expr
+| 2 = @stmt_if
+| 3 = @stmt_while
+| 4 = @stmt_goto
+| 5 = @stmt_label
+| 6 = @stmt_return
+| 7 = @stmt_block
+| 8 = @stmt_end_test_while // do { ... } while ( ... )
+| 9 = @stmt_for
+| 10 = @stmt_switch_case
+| 11 = @stmt_switch
+| 13 = @stmt_asm // "asm" statement or the body of an asm function
+| 15 = @stmt_try_block
+| 16 = @stmt_microsoft_try // Microsoft
+| 17 = @stmt_decl
+| 18 = @stmt_set_vla_size // C99
+| 19 = @stmt_vla_decl // C99
+| 25 = @stmt_assigned_goto // GNU
+| 26 = @stmt_empty
+| 27 = @stmt_continue
+| 28 = @stmt_break
+| 29 = @stmt_range_based_for // C++11
+// ... 30 @stmt_at_autoreleasepool_block deprecated
+// ... 31 @stmt_objc_for_in deprecated
+// ... 32 @stmt_at_synchronized deprecated
+| 33 = @stmt_handler
+// ... 34 @stmt_finally_end deprecated
+| 35 = @stmt_constexpr_if
+| 37 = @stmt_co_return
+;
+
+type_vla(
+ int type_id: @type ref,
+ int decl: @stmt_vla_decl ref
+);
+
+variable_vla(
+ int var: @variable ref,
+ int decl: @stmt_vla_decl ref
+);
+
+if_initialization(
+ unique int if_stmt: @stmt_if ref,
+ int init_id: @stmt ref
+);
+
+if_then(
+ unique int if_stmt: @stmt_if ref,
+ int then_id: @stmt ref
+);
+
+if_else(
+ unique int if_stmt: @stmt_if ref,
+ int else_id: @stmt ref
+);
+
+constexpr_if_initialization(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int init_id: @stmt ref
+);
+
+constexpr_if_then(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int then_id: @stmt ref
+);
+
+constexpr_if_else(
+ unique int constexpr_if_stmt: @stmt_constexpr_if ref,
+ int else_id: @stmt ref
+);
+
+while_body(
+ unique int while_stmt: @stmt_while ref,
+ int body_id: @stmt ref
+);
+
+do_body(
+ unique int do_stmt: @stmt_end_test_while ref,
+ int body_id: @stmt ref
+);
+
+switch_initialization(
+ unique int switch_stmt: @stmt_switch ref,
+ int init_id: @stmt ref
+);
+
+#keyset[switch_stmt, index]
+switch_case(
+ int switch_stmt: @stmt_switch ref,
+ int index: int ref,
+ int case_id: @stmt_switch_case ref
+);
+
+switch_body(
+ unique int switch_stmt: @stmt_switch ref,
+ int body_id: @stmt ref
+);
+
+for_initialization(
+ unique int for_stmt: @stmt_for ref,
+ int init_id: @stmt ref
+);
+
+for_condition(
+ unique int for_stmt: @stmt_for ref,
+ int condition_id: @expr ref
+);
+
+for_update(
+ unique int for_stmt: @stmt_for ref,
+ int update_id: @expr ref
+);
+
+for_body(
+ unique int for_stmt: @stmt_for ref,
+ int body_id: @stmt ref
+);
+
+@stmtparent = @stmt | @expr_stmt ;
+stmtparents(
+ unique int id: @stmt ref,
+ int index: int ref,
+ int parent: @stmtparent ref
+);
+
+ishandler(unique int block: @stmt_block ref);
+
+@cfgnode = @stmt | @expr | @function | @initialiser ;
+
+stmt_decl_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl: @declaration ref
+);
+
+stmt_decl_entry_bind(
+ int stmt: @stmt_decl ref,
+ int num: int ref,
+ int decl_entry: @element ref
+);
+
+@functionorblock = @function | @stmt_block;
+
+blockscope(
+ unique int block: @stmt_block ref,
+ int enclosing: @functionorblock ref
+);
+
+@jump = @stmt_goto | @stmt_break | @stmt_continue;
+
+@jumporlabel = @jump | @stmt_label | @literal;
+
+jumpinfo(
+ unique int id: @jumporlabel ref,
+ string str: string ref,
+ int target: @stmt ref
+);
+
+preprocdirects(
+ unique int id: @preprocdirect,
+ int kind: int ref,
+ int location: @location_default ref
+);
+case @preprocdirect.kind of
+ 0 = @ppd_if
+| 1 = @ppd_ifdef
+| 2 = @ppd_ifndef
+| 3 = @ppd_elif
+| 4 = @ppd_else
+| 5 = @ppd_endif
+| 6 = @ppd_plain_include
+| 7 = @ppd_define
+| 8 = @ppd_undef
+| 9 = @ppd_line
+| 10 = @ppd_error
+| 11 = @ppd_pragma
+| 12 = @ppd_objc_import
+| 13 = @ppd_include_next
+| 18 = @ppd_warning
+;
+
+@ppd_include = @ppd_plain_include | @ppd_objc_import | @ppd_include_next;
+
+@ppd_branch = @ppd_if | @ppd_ifdef | @ppd_ifndef | @ppd_elif;
+
+preprocpair(
+ int begin : @ppd_branch ref,
+ int elseelifend : @preprocdirect ref
+);
+
+preproctrue(int branch : @ppd_branch ref);
+preprocfalse(int branch : @ppd_branch ref);
+
+preproctext(
+ unique int id: @preprocdirect ref,
+ string head: string ref,
+ string body: string ref
+);
+
+includes(
+ unique int id: @ppd_include ref,
+ int included: @file ref
+);
+
+link_targets(
+ unique int id: @link_target,
+ int binary: @file ref
+);
+
+link_parent(
+ int element : @element ref,
+ int link_target : @link_target ref
+);
+
+/* XML Files */
+
+xmlEncoding(unique int id: @file ref, string encoding: string ref);
+
+xmlDTDs(
+ unique int id: @xmldtd,
+ string root: string ref,
+ string publicId: string ref,
+ string systemId: string ref,
+ int fileid: @file ref
+);
+
+xmlElements(
+ unique int id: @xmlelement,
+ string name: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlAttrs(
+ unique int id: @xmlattribute,
+ int elementid: @xmlelement ref,
+ string name: string ref,
+ string value: string ref,
+ int idx: int ref,
+ int fileid: @file ref
+);
+
+xmlNs(
+ int id: @xmlnamespace,
+ string prefixName: string ref,
+ string URI: string ref,
+ int fileid: @file ref
+);
+
+xmlHasNs(
+ int elementId: @xmlnamespaceable ref,
+ int nsId: @xmlnamespace ref,
+ int fileid: @file ref
+);
+
+xmlComments(
+ unique int id: @xmlcomment,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int fileid: @file ref
+);
+
+xmlChars(
+ unique int id: @xmlcharacters,
+ string text: string ref,
+ int parentid: @xmlparent ref,
+ int idx: int ref,
+ int isCDATA: int ref,
+ int fileid: @file ref
+);
+
+@xmlparent = @file | @xmlelement;
+@xmlnamespaceable = @xmlelement | @xmlattribute;
+
+xmllocations(
+ int xmlElement: @xmllocatable ref,
+ int location: @location_default ref
+);
+
+@xmllocatable = @xmlcharacters
+ | @xmlelement
+ | @xmlcomment
+ | @xmlattribute
+ | @xmldtd
+ | @file
+ | @xmlnamespace;
diff --git a/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/upgrade.properties b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/upgrade.properties
new file mode 100644
index 00000000000..5ad1a2fd4c3
--- /dev/null
+++ b/cpp/ql/lib/upgrades/8cba93a44180e0d50a80a660950800d822b981fc/upgrade.properties
@@ -0,0 +1,2 @@
+description: Expose whether a function was prototyped or not
+compatibility: partial
diff --git a/cpp/ql/src/CHANGELOG.md b/cpp/ql/src/CHANGELOG.md
index 4d374ad0ccf..c771f8bd03e 100644
--- a/cpp/ql/src/CHANGELOG.md
+++ b/cpp/ql/src/CHANGELOG.md
@@ -1,3 +1,13 @@
+## 0.9.0
+
+### Breaking Changes
+
+* The `cpp/tainted-format-string-through-global` query has been deleted. This does not lead to a loss of relevant alerts, as the query duplicated a subset of the alerts from `cpp/tainted-format-string`.
+
+### New Queries
+
+* Added a new query, `cpp/use-of-string-after-lifetime-ends`, to detect calls to `c_str` on strings that will be destroyed immediately.
+
## 0.8.3
### Minor Analysis Improvements
diff --git a/cpp/ql/src/Security/CWE/CWE-114/UncontrolledProcessOperation.ql b/cpp/ql/src/Security/CWE/CWE-114/UncontrolledProcessOperation.ql
index 3e1c62b02c2..9672a830ce0 100644
--- a/cpp/ql/src/Security/CWE/CWE-114/UncontrolledProcessOperation.ql
+++ b/cpp/ql/src/Security/CWE/CWE-114/UncontrolledProcessOperation.ql
@@ -27,10 +27,7 @@ predicate isProcessOperationExplanation(DataFlow::Node arg, string processOperat
)
}
-predicate isSource(FlowSource source, string sourceType) {
- not source instanceof DataFlow::ExprNode and
- sourceType = source.getSourceType()
-}
+predicate isSource(FlowSource source, string sourceType) { sourceType = source.getSourceType() }
module Config implements DataFlow::ConfigSig {
predicate isSource(DataFlow::Node node) { isSource(node, _) }
diff --git a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatString.ql b/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatString.ql
index 3a5cb7931b2..f4a716765b8 100644
--- a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatString.ql
+++ b/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatString.ql
@@ -16,22 +16,47 @@
import cpp
import semmle.code.cpp.security.Security
import semmle.code.cpp.security.FunctionWithWrappers
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
-import TaintedWithPath
+import semmle.code.cpp.security.FlowSources
+import semmle.code.cpp.ir.dataflow.TaintTracking
+import semmle.code.cpp.ir.IR
+import Flow::PathGraph
-class Configuration extends TaintTrackingConfiguration {
- override predicate isSink(Element tainted) {
- exists(PrintfLikeFunction printf | printf.outermostWrapperFunctionCall(tainted, _))
+predicate isSource(FlowSource source, string sourceType) { sourceType = source.getSourceType() }
+
+module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node node) { isSource(node, _) }
+
+ predicate isSink(DataFlow::Node node) {
+ exists(PrintfLikeFunction printf |
+ printf.outermostWrapperFunctionCall([node.asExpr(), node.asIndirectExpr()], _)
+ )
+ }
+
+ private predicate isArithmeticNonCharType(ArithmeticType type) {
+ not type instanceof CharType and
+ not type instanceof Char8Type and
+ not type instanceof Char16Type and
+ not type instanceof Char32Type
+ }
+
+ predicate isBarrier(DataFlow::Node node) {
+ isSink(node) and isArithmeticNonCharType(node.asExpr().getUnspecifiedType())
+ or
+ isArithmeticNonCharType(node.asInstruction().(StoreInstruction).getResultType())
}
}
+module Flow = TaintTracking::Global;
+
from
- PrintfLikeFunction printf, Expr arg, PathNode sourceNode, PathNode sinkNode,
- string printfFunction, Expr userValue, string cause
+ PrintfLikeFunction printf, string printfFunction, string sourceType, DataFlow::Node source,
+ DataFlow::Node sink, Flow::PathNode sourceNode, Flow::PathNode sinkNode
where
- printf.outermostWrapperFunctionCall(arg, printfFunction) and
- taintedWithPath(userValue, arg, sourceNode, sinkNode) and
- isUserInput(userValue, cause)
-select arg, sourceNode, sinkNode,
+ source = sourceNode.getNode() and
+ sink = sinkNode.getNode() and
+ isSource(source, sourceType) and
+ printf.outermostWrapperFunctionCall([sink.asExpr(), sink.asIndirectExpr()], printfFunction) and
+ Flow::flowPath(sourceNode, sinkNode)
+select sink, sourceNode, sinkNode,
"The value of this argument may come from $@ and is being used as a formatting argument to " +
- printfFunction + ".", userValue, cause
+ printfFunction + ".", source, sourceType
diff --git a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.c b/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.c
deleted file mode 100644
index 2700109a586..00000000000
--- a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.c
+++ /dev/null
@@ -1,24 +0,0 @@
-#include
-
-char *copy;
-
-void copyArgv(char **argv) {
- copy = argv[1];
-}
-
-void printWrapper(char *str) {
- printf(str);
-}
-
-int main(int argc, char **argv) {
- copyArgv(argv);
-
- // This should be avoided
- printf(copy);
-
- // This should be avoided too, because it has the same effect
- printWrapper(copy);
-
- // This is fine
- printf("%s", copy);
-}
diff --git a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.qhelp b/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.qhelp
deleted file mode 100644
index 80b84580a57..00000000000
--- a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.qhelp
+++ /dev/null
@@ -1,36 +0,0 @@
-
-
-
-The program uses input from the user, propagated via a global variable, as a format string for printf style functions.
-This can lead to buffer overflows or data representation problems. An attacker can exploit this weakness to crash the program,
-disclose information or even execute arbitrary code.
-
-This rule only identifies inputs from the user that are transferred through global variables before being used in printf style functions.
-Analyzing the flow of data through global variables is more prone to errors and so this rule may identify some examples of code where
-the input is not really from the user. For example, when a global variable is set in two places, one that comes from the user and one that does not.
-In this case we would mark all usages of the global variable as input from the user, but the input from the user may always came after the call to the
-printf style functions.
-
-The results of this rule should be considered alongside the related rule "Uncontrolled format string" which tracks the flow of the
-values input by a user, excluding global variables, until the values are used as the format argument for a printf like function call.
-
-
-
-Use constant expressions as the format strings. If you need to print a value from the user, use printf("%s", value_from_user).
-
-
-
-
-
-
-
-
-CERT C Coding
-Standard: FIO30-C. Exclude
-user input from format strings.
-
-
-
-
diff --git a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.ql b/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.ql
deleted file mode 100644
index b37e34c296c..00000000000
--- a/cpp/ql/src/Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.ql
+++ /dev/null
@@ -1,40 +0,0 @@
-/**
- * @name Uncontrolled format string (through global variable)
- * @description Using externally-controlled format strings in
- * printf-style functions can lead to buffer overflows
- * or data representation problems.
- * @kind path-problem
- * @problem.severity warning
- * @security-severity 9.3
- * @precision high
- * @id cpp/tainted-format-string-through-global
- * @tags reliability
- * security
- * external/cwe/cwe-134
- */
-
-import cpp
-import semmle.code.cpp.security.FunctionWithWrappers
-import semmle.code.cpp.security.Security
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
-import TaintedWithPath
-
-class Configuration extends TaintTrackingConfiguration {
- override predicate isSink(Element tainted) {
- exists(PrintfLikeFunction printf | printf.outermostWrapperFunctionCall(tainted, _))
- }
-
- override predicate taintThroughGlobals() { any() }
-}
-
-from
- PrintfLikeFunction printf, Expr arg, PathNode sourceNode, PathNode sinkNode,
- string printfFunction, Expr userValue, string cause
-where
- printf.outermostWrapperFunctionCall(arg, printfFunction) and
- not taintedWithoutGlobals(arg) and
- taintedWithPath(userValue, arg, sourceNode, sinkNode) and
- isUserInput(userValue, cause)
-select arg, sourceNode, sinkNode,
- "The value of this argument may come from $@ and is being used as a formatting argument to " +
- printfFunction + ".", userValue, cause
diff --git a/cpp/ql/src/Security/CWE/CWE-170/ImproperNullTerminationTainted.ql b/cpp/ql/src/Security/CWE/CWE-170/ImproperNullTerminationTainted.ql
index ff2e7e924df..e1e459c259f 100644
--- a/cpp/ql/src/Security/CWE/CWE-170/ImproperNullTerminationTainted.ql
+++ b/cpp/ql/src/Security/CWE/CWE-170/ImproperNullTerminationTainted.ql
@@ -12,79 +12,44 @@
import cpp
import semmle.code.cpp.commons.NullTermination
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
+import semmle.code.cpp.security.FlowSources as FS
+import semmle.code.cpp.dataflow.new.TaintTracking
+import semmle.code.cpp.ir.IR
-/** A user-controlled expression that may not be null terminated. */
-class TaintSource extends VariableAccess {
- TaintSource() {
- exists(SecurityOptions x, string cause |
- this.getTarget() instanceof SemanticStackVariable and
- x.isUserInput(this, cause)
- |
- cause = ["read", "fread", "recv", "recvfrom", "recvmsg"]
- )
- }
-
- /**
- * Holds if `sink` is a tainted variable access that must be null
- * terminated.
- */
- private predicate isSink(VariableAccess sink) {
- tainted(this, sink) and
- variableMustBeNullTerminated(sink)
- }
-
- /**
- * Holds if this source can reach `va`, possibly using intermediate
- * reassignments.
- */
- private predicate sourceReaches(VariableAccess va) {
- definitionUsePair(_, this, va)
- or
- exists(VariableAccess mid, Expr def |
- this.sourceReaches(mid) and
- exprDefinition(_, def, mid) and
- definitionUsePair(_, def, va)
- )
- }
-
- /**
- * Holds if the sink `sink` is reachable both from this source and
- * from `va`, possibly using intermediate reassignments.
- */
- private predicate reachesSink(VariableAccess va, VariableAccess sink) {
- this.isSink(sink) and
- va = sink
- or
- exists(VariableAccess mid, Expr def |
- this.reachesSink(mid, sink) and
- exprDefinition(_, def, va) and
- definitionUsePair(_, def, mid)
- )
- }
-
- /**
- * Holds if `sink` is a tainted variable access that must be null
- * terminated, and no access which null terminates its contents can
- * either reach the sink or be reached from the source. (Ideally,
- * we should instead look for such accesses only on the path from
- * this source to `sink` found via `tainted(source, sink)`.)
- */
- predicate reaches(VariableAccess sink) {
- this.isSink(sink) and
- not exists(VariableAccess va |
- va != this and
- va != sink and
- mayAddNullTerminator(_, va)
- |
- this.sourceReaches(va)
- or
- this.reachesSink(va, sink)
- )
- }
+predicate isSource(FS::FlowSource source, string sourceType) {
+ sourceType = source.getSourceType() and
+ exists(VariableAccess va, Call call |
+ va = source.asDefiningArgument() and
+ call.getAnArgument() = va and
+ va.getTarget() instanceof SemanticStackVariable and
+ call.getTarget().hasGlobalName(["read", "fread", "recv", "recvfrom", "recvmsg"])
+ )
}
-from TaintSource source, VariableAccess sink
-where source.reaches(sink)
-select sink, "String operation depends on a $@ that may not be null terminated.", source,
- "user-provided value"
+predicate isSink(DataFlow::Node sink, VariableAccess va) {
+ va = [sink.asExpr(), sink.asIndirectExpr()] and
+ variableMustBeNullTerminated(va)
+}
+
+private module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) { isSource(source, _) }
+
+ predicate isBarrier(DataFlow::Node node) {
+ isSink(node) and node.asExpr().getUnspecifiedType() instanceof ArithmeticType
+ or
+ node.asInstruction().(StoreInstruction).getResultType() instanceof ArithmeticType
+ or
+ mayAddNullTerminator(_, node.asIndirectExpr())
+ }
+
+ predicate isSink(DataFlow::Node sink) { isSink(sink, _) }
+}
+
+module Flow = TaintTracking::Global;
+
+from DataFlow::Node source, DataFlow::Node sink, VariableAccess va, string sourceType
+where
+ Flow::flow(source, sink) and
+ isSource(source, sourceType) and
+ isSink(sink, va)
+select va, "String operation depends on $@ that may not be null terminated.", source, sourceType
diff --git a/cpp/ql/src/Security/CWE/CWE-190/ArithmeticWithExtremeValues.ql b/cpp/ql/src/Security/CWE/CWE-190/ArithmeticWithExtremeValues.ql
index 6034b4f5ffd..15fd2cbca15 100644
--- a/cpp/ql/src/Security/CWE/CWE-190/ArithmeticWithExtremeValues.ql
+++ b/cpp/ql/src/Security/CWE/CWE-190/ArithmeticWithExtremeValues.ql
@@ -16,45 +16,30 @@
import cpp
import semmle.code.cpp.security.Overflow
-import semmle.code.cpp.security.Security
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
+import semmle.code.cpp.dataflow.new.TaintTracking
+import semmle.code.cpp.ir.IR
+import semmle.code.cpp.controlflow.IRGuards as IRGuards
predicate isMaxValue(Expr mie) {
exists(MacroInvocation mi |
mi.getExpr() = mie and
- (
- mi.getMacroName() = "CHAR_MAX" or
- mi.getMacroName() = "LLONG_MAX" or
- mi.getMacroName() = "INT_MAX" or
- mi.getMacroName() = "SHRT_MAX" or
- mi.getMacroName() = "UINT_MAX"
- )
+ mi.getMacroName() = ["CHAR_MAX", "LLONG_MAX", "INT_MAX", "SHRT_MAX", "UINT_MAX"]
)
}
predicate isMinValue(Expr mie) {
exists(MacroInvocation mi |
mi.getExpr() = mie and
- (
- mi.getMacroName() = "CHAR_MIN" or
- mi.getMacroName() = "LLONG_MIN" or
- mi.getMacroName() = "INT_MIN" or
- mi.getMacroName() = "SHRT_MIN"
- )
+ mi.getMacroName() = ["CHAR_MIN", "LLONG_MIN", "INT_MIN", "SHRT_MIN"]
)
}
-class SecurityOptionsArith extends SecurityOptions {
- override predicate isUserInput(Expr expr, string cause) {
+predicate isSource(DataFlow::Node source, string cause) {
+ exists(Expr expr | expr = source.asExpr() |
isMaxValue(expr) and cause = "max value"
or
isMinValue(expr) and cause = "min value"
- }
-}
-
-predicate taintedVarAccess(Expr origin, VariableAccess va, string cause) {
- isUserInput(origin, cause) and
- tainted(origin, va)
+ )
}
predicate causeEffectCorrespond(string cause, string effect) {
@@ -65,16 +50,79 @@ predicate causeEffectCorrespond(string cause, string effect) {
effect = "underflow"
}
-from Expr origin, Operation op, VariableAccess va, string cause, string effect
-where
- taintedVarAccess(origin, va, cause) and
- op.getAnOperand() = va and
- (
+predicate isSink(DataFlow::Node sink, VariableAccess va, string effect) {
+ exists(Operation op |
+ sink.asExpr() = va and
+ op.getAnOperand() = va
+ |
missingGuardAgainstUnderflow(op, va) and effect = "underflow"
or
missingGuardAgainstOverflow(op, va) and effect = "overflow"
- ) and
- causeEffectCorrespond(cause, effect)
+ )
+}
+
+predicate hasUpperBoundsCheck(Variable var) {
+ exists(RelationalOperation oper, VariableAccess access |
+ oper.getAnOperand() = access and
+ access.getTarget() = var and
+ // Comparing to 0 is not an upper bound check
+ not oper.getAnOperand().getValue() = "0"
+ )
+}
+
+predicate constantInstruction(Instruction instr) {
+ instr instanceof ConstantInstruction or
+ constantInstruction(instr.(UnaryInstruction).getUnary())
+}
+
+predicate readsVariable(LoadInstruction load, Variable var) {
+ load.getSourceAddress().(VariableAddressInstruction).getAstVariable() = var
+}
+
+predicate nodeIsBarrierEqualityCandidate(DataFlow::Node node, Operand access, Variable checkedVar) {
+ exists(Instruction instr | instr = node.asInstruction() |
+ readsVariable(instr, checkedVar) and
+ any(IRGuards::IRGuardCondition guard).ensuresEq(access, _, _, instr.getBlock(), true)
+ )
+}
+
+module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) { isSource(source, _) }
+
+ predicate isSink(DataFlow::Node sink) { isSink(sink, _, _) }
+
+ predicate isBarrier(DataFlow::Node node) {
+ // Block flow if there's an upper bound check of the variable anywhere in the program
+ exists(Variable checkedVar, Instruction instr | instr = node.asInstruction() |
+ readsVariable(instr, checkedVar) and
+ hasUpperBoundsCheck(checkedVar)
+ )
+ or
+ // Block flow if the node is guarded by an equality check
+ exists(Variable checkedVar, Operand access |
+ nodeIsBarrierEqualityCandidate(node, access, checkedVar) and
+ readsVariable(access.getDef(), checkedVar)
+ )
+ or
+ // Block flow to any binary instruction whose operands are both non-constants.
+ exists(BinaryInstruction iTo |
+ iTo = node.asInstruction() and
+ not constantInstruction(iTo.getLeft()) and
+ not constantInstruction(iTo.getRight()) and
+ // propagate taint from either the pointer or the offset, regardless of constantness
+ not iTo instanceof PointerArithmeticInstruction
+ )
+ }
+}
+
+module Flow = TaintTracking::Global;
+
+from DataFlow::Node source, DataFlow::Node sink, VariableAccess va, string cause, string effect
+where
+ Flow::flow(source, sink) and
+ isSource(source, cause) and
+ causeEffectCorrespond(cause, effect) and
+ isSink(sink, va, effect)
select va,
"$@ flows to an operand of an arithmetic expression, potentially causing an " + effect + ".",
- origin, "Extreme value"
+ source, "Extreme value"
diff --git a/cpp/ql/src/Security/CWE/CWE-190/IntegerOverflowTainted.ql b/cpp/ql/src/Security/CWE/CWE-190/IntegerOverflowTainted.ql
index 19fe7df4c44..98c53828d2a 100644
--- a/cpp/ql/src/Security/CWE/CWE-190/IntegerOverflowTainted.ql
+++ b/cpp/ql/src/Security/CWE/CWE-190/IntegerOverflowTainted.ql
@@ -15,7 +15,11 @@
import cpp
import semmle.code.cpp.rangeanalysis.SimpleRangeAnalysis
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
+import semmle.code.cpp.dataflow.new.DataFlow
+import semmle.code.cpp.security.FlowSources as FS
+import semmle.code.cpp.dataflow.new.TaintTracking
+import semmle.code.cpp.ir.IR
+import semmle.code.cpp.controlflow.IRGuards as IRGuards
/** Holds if `expr` might overflow. */
predicate outOfBoundsExpr(Expr expr, string kind) {
@@ -27,13 +31,76 @@ predicate outOfBoundsExpr(Expr expr, string kind) {
else none()
}
-from Expr use, Expr origin, string kind
+predicate isSource(FS::FlowSource source, string sourceType) { sourceType = source.getSourceType() }
+
+predicate isSink(DataFlow::Node sink, string kind) {
+ exists(Expr use |
+ use = sink.asExpr() and
+ not use.getUnspecifiedType() instanceof PointerType and
+ outOfBoundsExpr(use, kind) and
+ not inSystemMacroExpansion(use)
+ )
+}
+
+predicate hasUpperBoundsCheck(Variable var) {
+ exists(RelationalOperation oper, VariableAccess access |
+ oper.getAnOperand() = access and
+ access.getTarget() = var and
+ // Comparing to 0 is not an upper bound check
+ not oper.getAnOperand().getValue() = "0"
+ )
+}
+
+predicate constantInstruction(Instruction instr) {
+ instr instanceof ConstantInstruction or
+ constantInstruction(instr.(UnaryInstruction).getUnary())
+}
+
+predicate readsVariable(LoadInstruction load, Variable var) {
+ load.getSourceAddress().(VariableAddressInstruction).getAstVariable() = var
+}
+
+predicate nodeIsBarrierEqualityCandidate(DataFlow::Node node, Operand access, Variable checkedVar) {
+ exists(Instruction instr | instr = node.asInstruction() |
+ readsVariable(instr, checkedVar) and
+ any(IRGuards::IRGuardCondition guard).ensuresEq(access, _, _, instr.getBlock(), true)
+ )
+}
+
+module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) { isSource(source, _) }
+
+ predicate isSink(DataFlow::Node sink) { isSink(sink, _) }
+
+ predicate isBarrier(DataFlow::Node node) {
+ // Block flow if there's an upper bound check of the variable anywhere in the program
+ exists(Variable checkedVar, Instruction instr | instr = node.asInstruction() |
+ readsVariable(instr, checkedVar) and
+ hasUpperBoundsCheck(checkedVar)
+ )
+ or
+ // Block flow if the node is guarded by an equality check
+ exists(Variable checkedVar, Operand access |
+ nodeIsBarrierEqualityCandidate(node, access, checkedVar) and
+ readsVariable(access.getDef(), checkedVar)
+ )
+ or
+ // Block flow to any binary instruction whose operands are both non-constants.
+ exists(BinaryInstruction iTo |
+ iTo = node.asInstruction() and
+ not constantInstruction(iTo.getLeft()) and
+ not constantInstruction(iTo.getRight()) and
+ // propagate taint from either the pointer or the offset, regardless of constantness
+ not iTo instanceof PointerArithmeticInstruction
+ )
+ }
+}
+
+module Flow = TaintTracking::Global;
+
+from DataFlow::Node source, DataFlow::Node sink, string kind, string sourceType
where
- not use.getUnspecifiedType() instanceof PointerType and
- outOfBoundsExpr(use, kind) and
- tainted(origin, use) and
- origin != use and
- not inSystemMacroExpansion(use) and
- // Avoid double-counting: don't include all the conversions of `use`.
- not use instanceof Conversion
-select use, "$@ flows an expression which might " + kind + ".", origin, "User-provided value"
+ Flow::flow(source, sink) and
+ isSource(source, sourceType) and
+ isSink(sink, kind)
+select sink, "$@ flows an expression which might " + kind + ".", source, sourceType
diff --git a/cpp/ql/src/Security/CWE/CWE-290/AuthenticationBypass.ql b/cpp/ql/src/Security/CWE/CWE-290/AuthenticationBypass.ql
index 1c163eade27..ada0180668e 100644
--- a/cpp/ql/src/Security/CWE/CWE-290/AuthenticationBypass.ql
+++ b/cpp/ql/src/Security/CWE/CWE-290/AuthenticationBypass.ql
@@ -12,8 +12,10 @@
* external/cwe/cwe-290
*/
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
-import TaintedWithPath
+import cpp
+import semmle.code.cpp.dataflow.new.TaintTracking
+import semmle.code.cpp.security.FlowSources as FS
+import Flow::PathGraph
string getATopLevelDomain() {
result =
@@ -60,13 +62,26 @@ predicate hardCodedAddressInCondition(Expr subexpression, Expr condition) {
condition = any(IfStmt ifStmt).getCondition()
}
-class Configuration extends TaintTrackingConfiguration {
- override predicate isSink(Element sink) { hardCodedAddressInCondition(sink, _) }
+predicate isSource(FS::FlowSource source, string sourceType) { source.getSourceType() = sourceType }
+
+predicate isSink(DataFlow::Node sink, Expr condition) {
+ hardCodedAddressInCondition([sink.asExpr(), sink.asIndirectExpr()], condition)
}
-from Expr subexpression, Expr source, Expr condition, PathNode sourceNode, PathNode sinkNode
+module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) { isSource(source, _) }
+
+ predicate isSink(DataFlow::Node sink) { isSink(sink, _) }
+}
+
+module Flow = TaintTracking::Global;
+
+from
+ Expr subexpression, Expr condition, Flow::PathNode source, Flow::PathNode sink, string sourceType
where
hardCodedAddressInCondition(subexpression, condition) and
- taintedWithPath(source, subexpression, sourceNode, sinkNode)
-select condition, sourceNode, sinkNode,
- "Untrusted input $@ might be vulnerable to a spoofing attack.", source, source.toString()
+ isSource(source.getNode(), sourceType) and
+ Flow::flowPath(source, sink) and
+ isSink(sink.getNode(), condition)
+select condition, source, sink, "Untrusted input $@ might be vulnerable to a spoofing attack.",
+ source, sourceType
diff --git a/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.qhelp b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.qhelp
new file mode 100644
index 00000000000..e0678c0beff
--- /dev/null
+++ b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.qhelp
@@ -0,0 +1,44 @@
+
+
+
+
+Calling c_str on a std::string object returns a pointer to the underlying character array.
+When the std::string object is destroyed, the pointer returned by c_str is no
+longer valid. If the pointer is used after the std::string object is destroyed, then the behavior is undefined.
+
+
+
+
+
+Ensure that the pointer returned by c_str does not outlive the underlying std::string object.
+
+
+
+
+
+The following example concatenates two std::string objects, and then converts the resulting string to a
+C string using c_str so that it can be passed to the work function.
+
+However, the underlying std::string object that represents the concatenated string is destroyed as soon as the call
+to c_str returns. This means that work is given a pointer to invalid memory.
+
+
+
+
+
+The following example fixes the above code by ensuring that the pointer returned by the call to c_str does
+not outlive the underlying std::string objects. This ensures that the pointer passed to work
+points to valid memory.
+
+
+
+
+
+
+
+MEM50-CPP. Do not access freed memory.
+
+
+
diff --git a/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.ql b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.ql
new file mode 100644
index 00000000000..5fd75150167
--- /dev/null
+++ b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.ql
@@ -0,0 +1,100 @@
+/**
+ * @name Use of string after lifetime ends
+ * @description If the value of a call to 'c_str' outlives the underlying object it may lead to unexpected behavior.
+ * @kind problem
+ * @precision high
+ * @id cpp/use-of-string-after-lifetime-ends
+ * @problem.severity warning
+ * @security-severity 8.8
+ * @tags reliability
+ * security
+ * external/cwe/cwe-416
+ * external/cwe/cwe-664
+ */
+
+import cpp
+import semmle.code.cpp.models.implementations.StdString
+import semmle.code.cpp.models.implementations.StdContainer
+
+/**
+ * Holds if `e` will be consumed by its parent as a glvalue and does not have
+ * an lvalue-to-rvalue conversion. This means that it will be materialized into
+ * a temporary object.
+ */
+predicate isTemporary(Expr e) {
+ e instanceof TemporaryObjectExpr
+ or
+ e.isPRValueCategory() and
+ e.getUnspecifiedType() instanceof Class and
+ not e.hasLValueToRValueConversion()
+}
+
+/** Holds if `e` is written to a container. */
+predicate isStoredInContainer(Expr e) {
+ exists(StdSequenceContainerInsert insert, Call call, int index |
+ call = insert.getACallToThisFunction() and
+ index = insert.getAValueTypeParameterIndex() and
+ call.getArgument(index) = e
+ )
+ or
+ exists(StdSequenceContainerPush push, Call call, int index |
+ call = push.getACallToThisFunction() and
+ index = push.getAValueTypeParameterIndex() and
+ call.getArgument(index) = e
+ )
+ or
+ exists(StdSequenceEmplace emplace, Call call, int index |
+ call = emplace.getACallToThisFunction() and
+ index = emplace.getAValueTypeParameterIndex() and
+ call.getArgument(index) = e
+ )
+ or
+ exists(StdSequenceEmplaceBack emplaceBack, Call call, int index |
+ call = emplaceBack.getACallToThisFunction() and
+ index = emplaceBack.getAValueTypeParameterIndex() and
+ call.getArgument(index) = e
+ )
+}
+
+/**
+ * Holds if the value of `e` outlives the enclosing full expression. For
+ * example, because the value is stored in a local variable.
+ */
+predicate outlivesFullExpr(Expr e) {
+ any(Assignment assign).getRValue() = e
+ or
+ any(Variable v).getInitializer().getExpr() = e
+ or
+ any(ReturnStmt ret).getExpr() = e
+ or
+ exists(ConditionalExpr cond |
+ outlivesFullExpr(cond) and
+ [cond.getThen(), cond.getElse()] = e
+ )
+ or
+ exists(BinaryOperation bin |
+ outlivesFullExpr(bin) and
+ bin.getAnOperand() = e
+ )
+ or
+ exists(ClassAggregateLiteral aggr |
+ outlivesFullExpr(aggr) and
+ aggr.getAFieldExpr(_) = e
+ )
+ or
+ exists(ArrayAggregateLiteral aggr |
+ outlivesFullExpr(aggr) and
+ aggr.getAnElementExpr(_) = e
+ )
+ or
+ isStoredInContainer(e)
+}
+
+from Call c
+where
+ outlivesFullExpr(c) and
+ not c.isFromUninstantiatedTemplate(_) and
+ (c.getTarget() instanceof StdStringCStr or c.getTarget() instanceof StdStringData) and
+ isTemporary(c.getQualifier().getFullyConverted())
+select c,
+ "The underlying string object is destroyed after the call to '" + c.getTarget() + "' returns."
diff --git a/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsBad.cpp b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsBad.cpp
new file mode 100644
index 00000000000..77fa30d5e48
--- /dev/null
+++ b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsBad.cpp
@@ -0,0 +1,9 @@
+#include
+void work(const char*);
+
+// BAD: the concatenated string is deallocated when `c_str` returns. So `work`
+// is given a pointer to invalid memory.
+void work_with_combined_string_bad(std::string s1, std::string s2) {
+ const char* combined_string = (s1 + s2).c_str();
+ work(combined_string);
+}
\ No newline at end of file
diff --git a/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsGood.cpp b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsGood.cpp
new file mode 100644
index 00000000000..abd2e06f18d
--- /dev/null
+++ b/cpp/ql/src/Security/CWE/CWE-416/UseOfStringAfterLifetimeEndsGood.cpp
@@ -0,0 +1,9 @@
+#include
+void work(const char*);
+
+// GOOD: the concatenated string outlives the call to `work`. So the pointer
+// obtainted from `c_str` is valid.
+void work_with_combined_string_good(std::string s1, std::string s2) {
+ auto combined_string = s1 + s2;
+ work(combined_string.c_str());
+}
\ No newline at end of file
diff --git a/cpp/ql/src/Security/CWE/CWE-807/TaintedCondition.ql b/cpp/ql/src/Security/CWE/CWE-807/TaintedCondition.ql
index c5d7f2cbb61..7eaa5df849d 100644
--- a/cpp/ql/src/Security/CWE/CWE-807/TaintedCondition.ql
+++ b/cpp/ql/src/Security/CWE/CWE-807/TaintedCondition.ql
@@ -12,8 +12,12 @@
* external/cwe/cwe-807
*/
-import semmle.code.cpp.ir.dataflow.internal.DefaultTaintTrackingImpl
-import TaintedWithPath
+import cpp
+import semmle.code.cpp.security.Security
+import semmle.code.cpp.security.FlowSources
+import semmle.code.cpp.ir.dataflow.TaintTracking
+import semmle.code.cpp.ir.IR
+import Flow::PathGraph
predicate sensitiveCondition(Expr condition, Expr raise) {
raisesPrivilege(raise) and
@@ -23,19 +27,62 @@ predicate sensitiveCondition(Expr condition, Expr raise) {
)
}
-class Configuration extends TaintTrackingConfiguration {
- override predicate isSink(Element tainted) { sensitiveCondition(tainted, _) }
+private predicate constantInstruction(Instruction instr) {
+ instr instanceof ConstantInstruction
+ or
+ instr instanceof StringConstantInstruction
+ or
+ constantInstruction(instr.(UnaryInstruction).getUnary())
}
+predicate isSource(FlowSource source, string sourceType) { sourceType = source.getSourceType() }
+
+module Config implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node node) { isSource(node, _) }
+
+ predicate isSink(DataFlow::Node node) {
+ sensitiveCondition([node.asExpr(), node.asIndirectExpr()], _)
+ }
+
+ predicate isBarrier(DataFlow::Node node) {
+ // Block flow into binary instructions if both operands are non-constant
+ exists(BinaryInstruction iTo |
+ iTo = node.asInstruction() and
+ not constantInstruction(iTo.getLeft()) and
+ not constantInstruction(iTo.getRight()) and
+ // propagate taint from either the pointer or the offset, regardless of constant-ness
+ not iTo instanceof PointerArithmeticInstruction
+ )
+ or
+ // Block flow through calls to pure functions if two or more operands are non-constant
+ exists(Instruction iFrom1, Instruction iFrom2, CallInstruction iTo |
+ iTo = node.asInstruction() and
+ isPureFunction(iTo.getStaticCallTarget().getName()) and
+ iFrom1 = iTo.getAnArgument() and
+ iFrom2 = iTo.getAnArgument() and
+ not constantInstruction(iFrom1) and
+ not constantInstruction(iFrom2) and
+ iFrom1 != iFrom2
+ )
+ }
+}
+
+module Flow = TaintTracking::Global;
+
/*
* Produce an alert if there is an 'if' statement whose condition `condition`
* is influenced by tainted data `source`, and the body contains
* `raise` which escalates privilege.
*/
-from Expr source, Expr condition, Expr raise, PathNode sourceNode, PathNode sinkNode
+from
+ Expr raise, string sourceType, DataFlow::Node source, DataFlow::Node sink,
+ Flow::PathNode sourceNode, Flow::PathNode sinkNode
where
- taintedWithPath(source, condition, sourceNode, sinkNode) and
- sensitiveCondition(condition, raise)
-select condition, sourceNode, sinkNode, "Reliance on untrusted input $@ to raise privilege at $@.",
- source, source.toString(), raise, raise.toString()
+ source = sourceNode.getNode() and
+ sink = sinkNode.getNode() and
+ isSource(source, sourceType) and
+ sensitiveCondition([sink.asExpr(), sink.asIndirectExpr()], raise) and
+ Flow::flowPath(sourceNode, sinkNode)
+select sink, sourceNode, sinkNode, "Reliance on $@ to raise privilege at $@.", source, sourceType,
+ raise, raise.toString()
diff --git a/cpp/ql/src/change-notes/released/0.9.0.md b/cpp/ql/src/change-notes/released/0.9.0.md
new file mode 100644
index 00000000000..b6f5efca81c
--- /dev/null
+++ b/cpp/ql/src/change-notes/released/0.9.0.md
@@ -0,0 +1,9 @@
+## 0.9.0
+
+### Breaking Changes
+
+* The `cpp/tainted-format-string-through-global` query has been deleted. This does not lead to a loss of relevant alerts, as the query duplicated a subset of the alerts from `cpp/tainted-format-string`.
+
+### New Queries
+
+* Added a new query, `cpp/use-of-string-after-lifetime-ends`, to detect calls to `c_str` on strings that will be destroyed immediately.
diff --git a/cpp/ql/src/codeql-pack.release.yml b/cpp/ql/src/codeql-pack.release.yml
index b6e46394f37..8b9fc185202 100644
--- a/cpp/ql/src/codeql-pack.release.yml
+++ b/cpp/ql/src/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 0.8.3
+lastReleaseVersion: 0.9.0
diff --git a/cpp/ql/src/experimental/Security/CWE/CWE-416/UseAfterExpiredLifetime.ql b/cpp/ql/src/experimental/Security/CWE/CWE-416/UseAfterExpiredLifetime.ql
index e42e73dd92b..ffcac802b6d 100644
--- a/cpp/ql/src/experimental/Security/CWE/CWE-416/UseAfterExpiredLifetime.ql
+++ b/cpp/ql/src/experimental/Security/CWE/CWE-416/UseAfterExpiredLifetime.ql
@@ -12,7 +12,6 @@
*/
import cpp
-import semmle.code.cpp.dataflow.DataFlow
import semmle.code.cpp.controlflow.Nullness
class StarOperator extends Operator {
diff --git a/cpp/ql/src/experimental/cryptography/example_alerts/WeakHashes.ql b/cpp/ql/src/experimental/cryptography/example_alerts/WeakHashes.ql
index 8b6835d9b26..906069fa410 100644
--- a/cpp/ql/src/experimental/cryptography/example_alerts/WeakHashes.ql
+++ b/cpp/ql/src/experimental/cryptography/example_alerts/WeakHashes.ql
@@ -9,7 +9,6 @@
*/
import cpp
-import semmle.code.cpp.dataflow.DataFlow as ASTDataFlow
import experimental.cryptography.Concepts
from HashAlgorithm alg, Expr confSink, string msg
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/AllAsymmetricAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/AllAsymmetricAlgorithms.ql
index 138664b7665..275049d8aea 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/AllAsymmetricAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/AllAsymmetricAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/all-asymmetric-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/AllCryptoAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/AllCryptoAlgorithms.ql
index 1fe71b00a58..41c3d625a70 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/AllCryptoAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/AllCryptoAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/all-cryptographic-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/AsymmetricEncryptionAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/AsymmetricEncryptionAlgorithms.ql
index 29e429af95f..4edafed9499 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/AsymmetricEncryptionAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/AsymmetricEncryptionAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/all-asymmetric-encryption-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/AuthenticatedEncryptionAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/AuthenticatedEncryptionAlgorithms.ql
index d855e50ea88..cbf62036359 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/AuthenticatedEncryptionAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/AuthenticatedEncryptionAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/authenticated-encryption-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeAlgorithms.ql
index 36b5d52a7c1..33cb44742d2 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/block-cipher-mode
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeKnownIVsOrNonces.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeKnownIVsOrNonces.ql
index 6b91e84edba..9bfafee3696 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeKnownIVsOrNonces.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeKnownIVsOrNonces.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/iv-sources
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeUnknownIVsOrNonces.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeUnknownIVsOrNonces.ql
index 6acf3bb598f..4d54d6acce5 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeUnknownIVsOrNonces.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/BlockModeUnknownIVsOrNonces.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/unkown-iv-sources
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithmSize.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithmSize.ql
index ad9206b5ba4..4fbe4cc881a 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithmSize.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithmSize.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/elliptic-curve-key-length
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithms.ql
index 06aa44cd1bb..79d4ab7750a 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/EllipticCurveAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/elliptic-curve-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/HashingAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/HashingAlgorithms.ql
index 175ba39e138..17541f45177 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/HashingAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/HashingAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/hash-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/KeyExchangeAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/KeyExchangeAlgorithms.ql
index 7f7ceb17c39..193a895f30e 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/KeyExchangeAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/KeyExchangeAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/key-exchange
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/KnownAsymmetricKeyGeneration.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/KnownAsymmetricKeyGeneration.ql
index 34fca159fdb..240c6e6c8ca 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/KnownAsymmetricKeyGeneration.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/KnownAsymmetricKeyGeneration.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/asymmetric-key-generation
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/SigningAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/SigningAlgorithms.ql
index b052e48a664..fa79d6635d9 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/SigningAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/SigningAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/signing-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/SymmetricEncryptionAlgorithms.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/SymmetricEncryptionAlgorithms.ql
index 2a4c3f1056a..4d518d09058 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/SymmetricEncryptionAlgorithms.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/SymmetricEncryptionAlgorithms.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/symmetric-encryption-algorithms
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/experimental/cryptography/inventory/new_models/UnknownAsymmetricKeyGeneration.ql b/cpp/ql/src/experimental/cryptography/inventory/new_models/UnknownAsymmetricKeyGeneration.ql
index 63ab3fdcffb..6c1018ecc2a 100644
--- a/cpp/ql/src/experimental/cryptography/inventory/new_models/UnknownAsymmetricKeyGeneration.ql
+++ b/cpp/ql/src/experimental/cryptography/inventory/new_models/UnknownAsymmetricKeyGeneration.ql
@@ -4,7 +4,6 @@
* @kind problem
* @id cpp/quantum-readiness/cbom/unkwon-asymmetric-key-generation
* @problem.severity error
- * @precision high
* @tags cbom
* cryptography
*/
diff --git a/cpp/ql/src/qlpack.yml b/cpp/ql/src/qlpack.yml
index bb8073a4eab..14ead38877a 100644
--- a/cpp/ql/src/qlpack.yml
+++ b/cpp/ql/src/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/cpp-queries
-version: 0.8.3
+version: 0.9.0
groups:
- cpp
- queries
diff --git a/cpp/ql/test/library-tests/controlflow/guards-ir/tests.expected b/cpp/ql/test/library-tests/controlflow/guards-ir/tests.expected
index 01b46187b69..0a50d6fdcab 100644
--- a/cpp/ql/test/library-tests/controlflow/guards-ir/tests.expected
+++ b/cpp/ql/test/library-tests/controlflow/guards-ir/tests.expected
@@ -450,6 +450,7 @@ irGuards
| test.c:126:12:126:26 | Call: call to test3_condition |
| test.c:131:7:131:7 | Load: b |
| test.c:137:7:137:7 | Constant: 0 |
+| test.c:146:7:146:8 | LogicalNot: ! ... |
| test.c:146:8:146:8 | Load: x |
| test.c:152:10:152:10 | Load: x |
| test.c:152:15:152:15 | Load: y |
@@ -640,6 +641,7 @@ irGuardsControl
| test.c:126:12:126:26 | Call: call to test3_condition | true | 127 | 127 |
| test.c:131:7:131:7 | Load: b | true | 132 | 132 |
| test.c:137:7:137:7 | Constant: 0 | false | 142 | 142 |
+| test.c:146:7:146:8 | LogicalNot: ! ... | true | 147 | 147 |
| test.c:146:8:146:8 | Load: x | false | 147 | 147 |
| test.c:152:10:152:10 | Load: x | true | 152 | 152 |
| test.c:152:15:152:15 | Load: y | true | 152 | 152 |
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/TestBase.qll b/cpp/ql/test/library-tests/dataflow/dataflow-tests/TestBase.qll
new file mode 100644
index 00000000000..528e7ca6ad3
--- /dev/null
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/TestBase.qll
@@ -0,0 +1,111 @@
+module AstTest {
+ import semmle.code.cpp.dataflow.DataFlow
+ private import semmle.code.cpp.controlflow.Guards
+
+ /**
+ * A `BarrierGuard` that stops flow to all occurrences of `x` within statement
+ * S in `if (guarded(x)) S`.
+ */
+ // This is tested in `BarrierGuard.cpp`.
+ predicate testBarrierGuard(GuardCondition g, Expr checked, boolean isTrue) {
+ g.(FunctionCall).getTarget().getName() = "guarded" and
+ checked = g.(FunctionCall).getArgument(0) and
+ isTrue = true
+ }
+
+ /** Common data flow configuration to be used by tests. */
+ module AstTestAllocationConfig implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) {
+ source.asExpr().(FunctionCall).getTarget().getName() = "source"
+ or
+ source.asParameter().getName().matches("source%")
+ or
+ source.asExpr().(FunctionCall).getTarget().getName() = "indirect_source"
+ or
+ source.(DataFlow::DefinitionByReferenceNode).getParameter().getName().matches("ref_source%")
+ or
+ // Track uninitialized variables
+ exists(source.asUninitialized())
+ }
+
+ predicate isSink(DataFlow::Node sink) {
+ exists(FunctionCall call |
+ call.getTarget().getName() = ["sink", "indirect_sink"] and
+ sink.asExpr() = call.getAnArgument()
+ )
+ }
+
+ predicate isBarrier(DataFlow::Node barrier) {
+ barrier.asExpr().(VariableAccess).getTarget().hasName("barrier") or
+ barrier = DataFlow::BarrierGuard::getABarrierNode()
+ }
+ }
+
+ module AstFlow = DataFlow::Global;
+}
+
+module IRTest {
+ private import cpp
+ import semmle.code.cpp.ir.dataflow.DataFlow
+ private import semmle.code.cpp.ir.IR
+ private import semmle.code.cpp.controlflow.IRGuards
+
+ /**
+ * A `BarrierGuard` that stops flow to all occurrences of `x` within statement
+ * S in `if (guarded(x)) S`.
+ */
+ // This is tested in `BarrierGuard.cpp`.
+ predicate testBarrierGuard(IRGuardCondition g, Expr checked, boolean isTrue) {
+ exists(Call call |
+ call = g.getUnconvertedResultExpression() and
+ call.getTarget().hasName("guarded") and
+ checked = call.getArgument(0) and
+ isTrue = true
+ )
+ }
+
+ /** Common data flow configuration to be used by tests. */
+ module IRTestAllocationConfig implements DataFlow::ConfigSig {
+ predicate isSource(DataFlow::Node source) {
+ source.asExpr().(FunctionCall).getTarget().getName() = "source"
+ or
+ source.asIndirectExpr(1).(FunctionCall).getTarget().getName() = "indirect_source"
+ or
+ source.asExpr().(StringLiteral).getValue() = "source"
+ or
+ // indirect_source(n) gives the dataflow node representing the indirect node after n dereferences.
+ exists(int n, string s |
+ n = s.regexpCapture("indirect_source\\((\\d)\\)", 1).toInt() and
+ source.asIndirectExpr(n).(StringLiteral).getValue() = s
+ )
+ or
+ source.asParameter().getName().matches("source%")
+ or
+ source.(DataFlow::DefinitionByReferenceNode).getParameter().getName().matches("ref_source%")
+ or
+ exists(source.asUninitialized())
+ }
+
+ predicate isSink(DataFlow::Node sink) {
+ exists(FunctionCall call, Expr e | e = call.getAnArgument() |
+ call.getTarget().getName() = "sink" and
+ sink.asExpr() = e
+ or
+ call.getTarget().getName() = "indirect_sink" and
+ sink.asIndirectExpr() = e
+ )
+ }
+
+ predicate isBarrier(DataFlow::Node barrier) {
+ exists(Expr barrierExpr | barrierExpr in [barrier.asExpr(), barrier.asIndirectExpr()] |
+ barrierExpr.(VariableAccess).getTarget().hasName("barrier")
+ )
+ or
+ barrier = DataFlow::BarrierGuard::getABarrierNode()
+ or
+ barrier = DataFlow::BarrierGuard::getAnIndirectBarrierNode()
+ }
+ }
+
+ module IRFlow = DataFlow::Global;
+}
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/dataflow-consistency.expected b/cpp/ql/test/library-tests/dataflow/dataflow-tests/dataflow-consistency.expected
index da59987d742..a98cfd7e22a 100644
--- a/cpp/ql/test/library-tests/dataflow/dataflow-tests/dataflow-consistency.expected
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/dataflow-consistency.expected
@@ -1,5 +1,11 @@
uniqueEnclosingCallable
+| test.cpp:864:44:864:58 | {...} | Node should have one enclosing callable but has 0. |
+| test.cpp:864:47:864:54 | call to source | Node should have one enclosing callable but has 0. |
+| test.cpp:872:46:872:51 | call to source | Node should have one enclosing callable but has 0. |
+| test.cpp:872:53:872:56 | 1 | Node should have one enclosing callable but has 0. |
uniqueCallEnclosingCallable
+| test.cpp:864:47:864:54 | call to source | Call should have one enclosing callable but has 0. |
+| test.cpp:872:46:872:51 | call to source | Call should have one enclosing callable but has 0. |
uniqueType
uniqueNodeLocation
missingLocation
@@ -24,6 +30,7 @@ argHasPostUpdate
| lambdas.cpp:45:2:45:2 | e | ArgumentNode is missing PostUpdateNode. |
| test.cpp:67:29:67:35 | source1 | ArgumentNode is missing PostUpdateNode. |
| test.cpp:813:19:813:35 | * ... | ArgumentNode is missing PostUpdateNode. |
+| test.cpp:848:23:848:25 | rpx | ArgumentNode is missing PostUpdateNode. |
postWithInFlow
| BarrierGuard.cpp:49:6:49:6 | x [post update] | PostUpdateNode should not be the target of local flow. |
| BarrierGuard.cpp:60:7:60:7 | x [post update] | PostUpdateNode should not be the target of local flow. |
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.expected b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.expected
new file mode 100644
index 00000000000..c98bc68c884
--- /dev/null
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.expected
@@ -0,0 +1,306 @@
+WARNING: Module DataFlow has been deprecated and may be removed in future (test-source-sink.ql:3,25-42)
+WARNING: Module DataFlow has been deprecated and may be removed in future (test-source-sink.ql:3,57-74)
+astFlow
+| BarrierGuard.cpp:5:19:5:24 | source | BarrierGuard.cpp:9:10:9:15 | source |
+| BarrierGuard.cpp:13:17:13:22 | source | BarrierGuard.cpp:15:10:15:15 | source |
+| BarrierGuard.cpp:21:17:21:22 | source | BarrierGuard.cpp:25:10:25:15 | source |
+| BarrierGuard.cpp:29:16:29:21 | source | BarrierGuard.cpp:31:10:31:15 | source |
+| BarrierGuard.cpp:29:16:29:21 | source | BarrierGuard.cpp:33:10:33:15 | source |
+| BarrierGuard.cpp:49:10:49:15 | call to source | BarrierGuard.cpp:51:13:51:13 | x |
+| BarrierGuard.cpp:49:10:49:15 | call to source | BarrierGuard.cpp:53:13:53:13 | x |
+| BarrierGuard.cpp:49:10:49:15 | call to source | BarrierGuard.cpp:55:13:55:13 | x |
+| BarrierGuard.cpp:60:11:60:16 | call to source | BarrierGuard.cpp:62:14:62:14 | x |
+| BarrierGuard.cpp:60:11:60:16 | call to source | BarrierGuard.cpp:64:14:64:14 | x |
+| BarrierGuard.cpp:60:11:60:16 | call to source | BarrierGuard.cpp:66:14:66:14 | x |
+| acrossLinkTargets.cpp:19:27:19:32 | call to source | acrossLinkTargets.cpp:12:8:12:8 | x |
+| clang.cpp:12:9:12:20 | sourceArray1 | clang.cpp:18:8:18:19 | sourceArray1 |
+| clang.cpp:12:9:12:20 | sourceArray1 | clang.cpp:22:8:22:20 | & ... |
+| clang.cpp:12:9:12:20 | sourceArray1 | clang.cpp:23:17:23:29 | & ... |
+| clang.cpp:29:27:29:32 | call to source | clang.cpp:30:27:30:28 | m1 |
+| clang.cpp:29:27:29:32 | call to source | clang.cpp:31:27:31:34 | call to getFirst |
+| clang.cpp:35:32:35:37 | call to source | clang.cpp:38:10:38:11 | m2 |
+| clang.cpp:44:35:44:40 | call to source | clang.cpp:46:17:46:18 | m2 |
+| clang.cpp:51:19:51:24 | call to source | clang.cpp:52:8:52:17 | stackArray |
+| clang.cpp:51:19:51:24 | call to source | clang.cpp:53:17:53:26 | stackArray |
+| dispatch.cpp:9:37:9:42 | call to source | dispatch.cpp:35:16:35:25 | call to notSource1 |
+| dispatch.cpp:9:37:9:42 | call to source | dispatch.cpp:43:15:43:24 | call to notSource1 |
+| dispatch.cpp:10:37:10:42 | call to source | dispatch.cpp:36:16:36:25 | call to notSource2 |
+| dispatch.cpp:10:37:10:42 | call to source | dispatch.cpp:44:15:44:24 | call to notSource2 |
+| dispatch.cpp:37:19:37:24 | call to source | dispatch.cpp:11:38:11:38 | x |
+| dispatch.cpp:45:18:45:23 | call to source | dispatch.cpp:11:38:11:38 | x |
+| globals.cpp:5:17:5:22 | call to source | globals.cpp:6:10:6:14 | local |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:14:3:14:6 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:18:8:18:8 | call to operator() |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:21:3:21:6 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:29:3:29:6 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:35:8:35:8 | a |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:41:8:41:8 | a |
+| lambdas.cpp:43:7:43:12 | call to source | lambdas.cpp:46:7:46:7 | w |
+| ref.cpp:29:11:29:16 | call to source | ref.cpp:62:10:62:11 | x3 |
+| ref.cpp:53:9:53:10 | x1 | ref.cpp:56:10:56:11 | x1 |
+| ref.cpp:53:13:53:14 | x2 | ref.cpp:59:10:59:11 | x2 |
+| ref.cpp:53:17:53:18 | x3 | ref.cpp:62:10:62:11 | x3 |
+| ref.cpp:53:21:53:22 | x4 | ref.cpp:65:10:65:11 | x4 |
+| ref.cpp:55:23:55:28 | call to source | ref.cpp:56:10:56:11 | x1 |
+| ref.cpp:94:15:94:20 | call to source | ref.cpp:129:13:129:15 | val |
+| ref.cpp:109:15:109:20 | call to source | ref.cpp:132:13:132:15 | val |
+| ref.cpp:122:23:122:28 | call to source | ref.cpp:123:13:123:15 | val |
+| ref.cpp:125:19:125:24 | call to source | ref.cpp:126:13:126:15 | val |
+| self-Iterator.cpp:19:23:19:28 | call to source | self-Iterator.cpp:20:10:20:10 | x |
+| test.cpp:6:12:6:17 | call to source | test.cpp:7:8:7:9 | t1 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:9:8:9:9 | t1 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:10:8:10:9 | t2 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:15:8:15:9 | t2 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:26:8:26:9 | t1 |
+| test.cpp:35:10:35:15 | call to source | test.cpp:30:8:30:8 | t |
+| test.cpp:36:13:36:18 | call to source | test.cpp:31:8:31:8 | c |
+| test.cpp:50:14:50:19 | call to source | test.cpp:58:10:58:10 | t |
+| test.cpp:66:30:66:36 | source1 | test.cpp:71:8:71:9 | x4 |
+| test.cpp:75:7:75:8 | u1 | test.cpp:76:8:76:9 | u1 |
+| test.cpp:83:7:83:8 | u2 | test.cpp:84:8:84:18 | ... ? ... : ... |
+| test.cpp:83:7:83:8 | u2 | test.cpp:86:8:86:9 | i1 |
+| test.cpp:89:28:89:34 | source1 | test.cpp:90:8:90:14 | source1 |
+| test.cpp:100:13:100:18 | call to source | test.cpp:103:10:103:12 | ref |
+| test.cpp:138:27:138:32 | call to source | test.cpp:140:8:140:8 | y |
+| test.cpp:151:33:151:38 | call to source | test.cpp:144:8:144:8 | s |
+| test.cpp:151:33:151:38 | call to source | test.cpp:152:8:152:8 | y |
+| test.cpp:164:34:164:39 | call to source | test.cpp:157:8:157:8 | x |
+| test.cpp:164:34:164:39 | call to source | test.cpp:165:8:165:8 | y |
+| test.cpp:171:11:171:16 | call to source | test.cpp:178:8:178:8 | y |
+| test.cpp:245:14:245:19 | call to source | test.cpp:260:12:260:12 | x |
+| test.cpp:265:22:265:27 | call to source | test.cpp:266:12:266:12 | x |
+| test.cpp:305:17:305:22 | call to source | test.cpp:289:14:289:14 | x |
+| test.cpp:314:4:314:9 | call to source | test.cpp:318:7:318:7 | x |
+| test.cpp:347:17:347:22 | call to source | test.cpp:349:10:349:18 | globalVar |
+| test.cpp:359:13:359:18 | call to source | test.cpp:365:10:365:14 | field |
+| test.cpp:373:13:373:18 | call to source | test.cpp:369:10:369:14 | field |
+| test.cpp:373:13:373:18 | call to source | test.cpp:375:10:375:14 | field |
+| test.cpp:382:48:382:54 | source1 | test.cpp:385:8:385:10 | tmp |
+| test.cpp:388:53:388:59 | source1 | test.cpp:392:8:392:10 | tmp |
+| test.cpp:388:53:388:59 | source1 | test.cpp:394:10:394:12 | tmp |
+| test.cpp:399:7:399:9 | tmp | test.cpp:401:8:401:10 | tmp |
+| test.cpp:405:7:405:9 | tmp | test.cpp:408:8:408:10 | tmp |
+| test.cpp:416:7:416:11 | local | test.cpp:418:8:418:12 | local |
+| test.cpp:417:16:417:20 | ref arg local | test.cpp:418:8:418:12 | local |
+| test.cpp:422:7:422:11 | local | test.cpp:424:8:424:12 | local |
+| test.cpp:423:20:423:25 | ref arg & ... | test.cpp:424:8:424:12 | local |
+| test.cpp:433:7:433:11 | local | test.cpp:435:8:435:12 | local |
+| test.cpp:433:7:433:11 | local | test.cpp:436:8:436:13 | * ... |
+| test.cpp:434:20:434:24 | ref arg local | test.cpp:435:8:435:12 | local |
+| test.cpp:434:20:434:24 | ref arg local | test.cpp:436:8:436:13 | * ... |
+| test.cpp:440:7:440:11 | local | test.cpp:442:8:442:12 | local |
+| test.cpp:441:18:441:23 | ref arg & ... | test.cpp:442:8:442:12 | local |
+| test.cpp:448:7:448:11 | local | test.cpp:450:8:450:12 | local |
+| test.cpp:448:7:448:11 | local | test.cpp:451:8:451:13 | * ... |
+| test.cpp:449:18:449:22 | ref arg local | test.cpp:450:8:450:12 | local |
+| test.cpp:449:18:449:22 | ref arg local | test.cpp:451:8:451:13 | * ... |
+| test.cpp:456:26:456:32 | source1 | test.cpp:457:9:457:22 | (statement expression) |
+| test.cpp:456:26:456:32 | source1 | test.cpp:468:8:468:12 | local |
+| test.cpp:472:8:472:13 | call to source | test.cpp:478:8:478:8 | x |
+| test.cpp:506:8:506:13 | call to source | test.cpp:513:8:513:8 | x |
+| test.cpp:517:7:517:16 | stackArray | test.cpp:521:8:521:20 | access to array |
+| test.cpp:519:19:519:24 | call to source | test.cpp:521:8:521:20 | access to array |
+| test.cpp:551:9:551:9 | y | test.cpp:541:10:541:10 | y |
+| test.cpp:583:11:583:16 | call to source | test.cpp:590:8:590:8 | x |
+| test.cpp:628:20:628:25 | ref arg buffer | test.cpp:629:17:629:22 | buffer |
+| test.cpp:633:18:633:23 | call to source | test.cpp:634:8:634:8 | x |
+| test.cpp:702:38:702:43 | source | test.cpp:695:8:695:10 | buf |
+| test.cpp:726:11:726:16 | call to source | test.cpp:735:8:735:8 | x |
+| test.cpp:733:7:733:7 | x | test.cpp:735:8:735:8 | x |
+| test.cpp:749:27:749:32 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:751:27:751:32 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:753:32:753:37 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:755:32:755:37 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:769:27:769:32 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:771:27:771:32 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:773:32:773:37 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:775:32:775:37 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:788:31:788:36 | call to source | test.cpp:782:12:782:12 | x |
+| test.cpp:790:31:790:36 | call to source | test.cpp:782:12:782:12 | x |
+| test.cpp:797:22:797:28 | ref arg content | test.cpp:798:19:798:25 | content |
+| test.cpp:842:11:842:16 | call to source | test.cpp:844:8:844:8 | y |
+| test.cpp:846:13:846:27 | call to indirect_source | test.cpp:848:23:848:25 | rpx |
+| test.cpp:860:54:860:59 | call to source | test.cpp:861:10:861:37 | static_local_pointer_dynamic |
+| true_upon_entry.cpp:17:11:17:16 | call to source | true_upon_entry.cpp:21:8:21:8 | x |
+| true_upon_entry.cpp:27:9:27:14 | call to source | true_upon_entry.cpp:29:8:29:8 | x |
+| true_upon_entry.cpp:33:11:33:16 | call to source | true_upon_entry.cpp:39:8:39:8 | x |
+| true_upon_entry.cpp:43:11:43:16 | call to source | true_upon_entry.cpp:49:8:49:8 | x |
+| true_upon_entry.cpp:54:11:54:16 | call to source | true_upon_entry.cpp:57:8:57:8 | x |
+| true_upon_entry.cpp:70:11:70:16 | call to source | true_upon_entry.cpp:78:8:78:8 | x |
+| true_upon_entry.cpp:83:11:83:16 | call to source | true_upon_entry.cpp:86:8:86:8 | x |
+irFlow
+| BarrierGuard.cpp:5:19:5:24 | source | BarrierGuard.cpp:9:10:9:15 | source |
+| BarrierGuard.cpp:13:17:13:22 | source | BarrierGuard.cpp:15:10:15:15 | source |
+| BarrierGuard.cpp:21:17:21:22 | source | BarrierGuard.cpp:25:10:25:15 | source |
+| BarrierGuard.cpp:29:16:29:21 | source | BarrierGuard.cpp:31:10:31:15 | source |
+| BarrierGuard.cpp:29:16:29:21 | source | BarrierGuard.cpp:33:10:33:15 | source |
+| BarrierGuard.cpp:49:10:49:15 | call to source | BarrierGuard.cpp:53:13:53:13 | x |
+| BarrierGuard.cpp:49:10:49:15 | call to source | BarrierGuard.cpp:55:13:55:13 | x |
+| BarrierGuard.cpp:60:11:60:16 | call to source | BarrierGuard.cpp:64:14:64:14 | x |
+| BarrierGuard.cpp:60:11:60:16 | call to source | BarrierGuard.cpp:66:14:66:14 | x |
+| acrossLinkTargets.cpp:19:27:19:32 | call to source | acrossLinkTargets.cpp:12:8:12:8 | x |
+| clang.cpp:12:9:12:20 | sourceArray1 | clang.cpp:18:8:18:19 | sourceArray1 |
+| clang.cpp:12:9:12:20 | sourceArray1 | clang.cpp:23:17:23:29 | & ... indirection |
+| clang.cpp:29:27:29:32 | call to source | clang.cpp:30:27:30:28 | m1 |
+| clang.cpp:29:27:29:32 | call to source | clang.cpp:31:27:31:34 | call to getFirst |
+| clang.cpp:35:32:35:37 | call to source | clang.cpp:38:10:38:11 | m2 |
+| clang.cpp:40:42:40:47 | call to source | clang.cpp:42:18:42:19 | m2 |
+| clang.cpp:44:35:44:40 | call to source | clang.cpp:46:17:46:18 | m2 |
+| clang.cpp:50:7:50:16 | definition of stackArray | clang.cpp:52:8:52:17 | stackArray |
+| clang.cpp:50:25:50:30 | call to source | clang.cpp:53:17:53:26 | stackArray indirection |
+| clang.cpp:50:35:50:40 | call to source | clang.cpp:53:17:53:26 | stackArray indirection |
+| clang.cpp:51:19:51:24 | call to source | clang.cpp:53:17:53:26 | stackArray indirection |
+| dispatch.cpp:9:37:9:42 | call to source | dispatch.cpp:35:16:35:25 | call to notSource1 |
+| dispatch.cpp:9:37:9:42 | call to source | dispatch.cpp:43:15:43:24 | call to notSource1 |
+| dispatch.cpp:10:37:10:42 | call to source | dispatch.cpp:36:16:36:25 | call to notSource2 |
+| dispatch.cpp:10:37:10:42 | call to source | dispatch.cpp:44:15:44:24 | call to notSource2 |
+| dispatch.cpp:16:37:16:42 | call to source | dispatch.cpp:32:16:32:24 | call to isSource2 |
+| dispatch.cpp:16:37:16:42 | call to source | dispatch.cpp:40:15:40:23 | call to isSource2 |
+| dispatch.cpp:22:37:22:42 | call to source | dispatch.cpp:31:16:31:24 | call to isSource1 |
+| dispatch.cpp:22:37:22:42 | call to source | dispatch.cpp:39:15:39:23 | call to isSource1 |
+| dispatch.cpp:22:37:22:42 | call to source | dispatch.cpp:55:22:55:30 | call to isSource1 |
+| dispatch.cpp:22:37:22:42 | call to source | dispatch.cpp:58:28:58:36 | call to isSource1 |
+| dispatch.cpp:33:18:33:23 | call to source | dispatch.cpp:23:38:23:38 | x |
+| dispatch.cpp:37:19:37:24 | call to source | dispatch.cpp:11:38:11:38 | x |
+| dispatch.cpp:41:17:41:22 | call to source | dispatch.cpp:23:38:23:38 | x |
+| dispatch.cpp:45:18:45:23 | call to source | dispatch.cpp:11:38:11:38 | x |
+| dispatch.cpp:69:15:69:20 | call to source | dispatch.cpp:23:38:23:38 | x |
+| dispatch.cpp:73:14:73:19 | call to source | dispatch.cpp:23:38:23:38 | x |
+| dispatch.cpp:81:13:81:18 | call to source | dispatch.cpp:23:38:23:38 | x |
+| dispatch.cpp:107:17:107:22 | call to source | dispatch.cpp:96:8:96:8 | x |
+| dispatch.cpp:140:8:140:13 | call to source | dispatch.cpp:96:8:96:8 | x |
+| dispatch.cpp:144:8:144:13 | call to source | dispatch.cpp:96:8:96:8 | x |
+| flowOut.cpp:5:16:5:21 | call to source | flowOut.cpp:19:9:19:9 | x |
+| globals.cpp:5:17:5:22 | call to source | globals.cpp:6:10:6:14 | local |
+| globals.cpp:13:23:13:28 | call to source | globals.cpp:12:10:12:24 | flowTestGlobal1 |
+| globals.cpp:23:23:23:28 | call to source | globals.cpp:19:10:19:24 | flowTestGlobal2 |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:14:8:14:8 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:18:8:18:8 | call to operator() |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:21:8:21:8 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:29:8:29:8 | t |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:35:8:35:8 | a |
+| lambdas.cpp:8:10:8:15 | call to source | lambdas.cpp:41:8:41:8 | a |
+| lambdas.cpp:43:7:43:12 | call to source | lambdas.cpp:46:7:46:7 | w |
+| ref.cpp:29:11:29:16 | call to source | ref.cpp:62:10:62:11 | x3 |
+| ref.cpp:53:9:53:10 | definition of x1 | ref.cpp:56:10:56:11 | x1 |
+| ref.cpp:53:13:53:14 | definition of x2 | ref.cpp:59:10:59:11 | x2 |
+| ref.cpp:53:17:53:18 | definition of x3 | ref.cpp:62:10:62:11 | x3 |
+| ref.cpp:53:21:53:22 | definition of x4 | ref.cpp:65:10:65:11 | x4 |
+| ref.cpp:55:23:55:28 | call to source | ref.cpp:56:10:56:11 | x1 |
+| ref.cpp:94:15:94:20 | call to source | ref.cpp:129:13:129:15 | val |
+| ref.cpp:109:15:109:20 | call to source | ref.cpp:132:13:132:15 | val |
+| ref.cpp:122:23:122:28 | call to source | ref.cpp:123:13:123:15 | val |
+| ref.cpp:125:19:125:24 | call to source | ref.cpp:126:13:126:15 | val |
+| self-Iterator.cpp:19:23:19:30 | call to source | self-Iterator.cpp:20:10:20:10 | x |
+| test.cpp:6:12:6:17 | call to source | test.cpp:7:8:7:9 | t1 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:9:8:9:9 | t1 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:10:8:10:9 | t2 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:15:8:15:9 | t2 |
+| test.cpp:6:12:6:17 | call to source | test.cpp:26:8:26:9 | t1 |
+| test.cpp:35:10:35:15 | call to source | test.cpp:30:8:30:8 | t |
+| test.cpp:36:13:36:18 | call to source | test.cpp:31:8:31:8 | c |
+| test.cpp:50:14:50:19 | call to source | test.cpp:58:10:58:10 | t |
+| test.cpp:66:30:66:36 | source1 | test.cpp:71:8:71:9 | x4 |
+| test.cpp:75:7:75:8 | definition of u1 | test.cpp:76:8:76:9 | u1 |
+| test.cpp:83:7:83:8 | definition of u2 | test.cpp:84:8:84:18 | ... ? ... : ... |
+| test.cpp:83:7:83:8 | definition of u2 | test.cpp:86:8:86:9 | i1 |
+| test.cpp:89:28:89:34 | source1 indirection | test.cpp:90:8:90:14 | source1 |
+| test.cpp:100:13:100:18 | call to source | test.cpp:103:10:103:12 | ref |
+| test.cpp:138:27:138:32 | call to source | test.cpp:140:8:140:8 | y |
+| test.cpp:151:33:151:38 | call to source | test.cpp:144:8:144:8 | s |
+| test.cpp:151:33:151:38 | call to source | test.cpp:152:8:152:8 | y |
+| test.cpp:164:34:164:39 | call to source | test.cpp:157:8:157:8 | x |
+| test.cpp:164:34:164:39 | call to source | test.cpp:165:8:165:8 | y |
+| test.cpp:171:11:171:16 | call to source | test.cpp:178:8:178:8 | y |
+| test.cpp:245:14:245:19 | call to source | test.cpp:260:12:260:12 | x |
+| test.cpp:265:22:265:27 | call to source | test.cpp:266:12:266:12 | x |
+| test.cpp:305:17:305:22 | call to source | test.cpp:289:14:289:14 | x |
+| test.cpp:314:4:314:9 | call to source | test.cpp:318:7:318:7 | x |
+| test.cpp:333:17:333:22 | call to source | test.cpp:337:10:337:18 | globalVar |
+| test.cpp:333:17:333:22 | call to source | test.cpp:339:10:339:18 | globalVar |
+| test.cpp:333:17:333:22 | call to source | test.cpp:343:10:343:18 | globalVar |
+| test.cpp:333:17:333:22 | call to source | test.cpp:349:10:349:18 | globalVar |
+| test.cpp:347:17:347:22 | call to source | test.cpp:337:10:337:18 | globalVar |
+| test.cpp:347:17:347:22 | call to source | test.cpp:339:10:339:18 | globalVar |
+| test.cpp:347:17:347:22 | call to source | test.cpp:343:10:343:18 | globalVar |
+| test.cpp:347:17:347:22 | call to source | test.cpp:349:10:349:18 | globalVar |
+| test.cpp:359:13:359:18 | call to source | test.cpp:365:10:365:14 | field |
+| test.cpp:373:13:373:18 | call to source | test.cpp:369:10:369:14 | field |
+| test.cpp:373:13:373:18 | call to source | test.cpp:375:10:375:14 | field |
+| test.cpp:382:48:382:54 | source1 | test.cpp:385:8:385:10 | tmp |
+| test.cpp:388:53:388:59 | source1 | test.cpp:392:8:392:10 | tmp |
+| test.cpp:388:53:388:59 | source1 | test.cpp:394:10:394:12 | tmp |
+| test.cpp:399:7:399:9 | definition of tmp | test.cpp:401:8:401:10 | tmp |
+| test.cpp:405:7:405:9 | definition of tmp | test.cpp:408:8:408:10 | tmp |
+| test.cpp:416:7:416:11 | definition of local | test.cpp:418:8:418:12 | local |
+| test.cpp:417:16:417:20 | intRefSource output argument | test.cpp:418:8:418:12 | local |
+| test.cpp:422:7:422:11 | definition of local | test.cpp:424:8:424:12 | local |
+| test.cpp:423:20:423:25 | intPointerSource output argument | test.cpp:424:8:424:12 | local |
+| test.cpp:433:7:433:11 | definition of local | test.cpp:435:8:435:12 | local |
+| test.cpp:434:20:434:24 | intPointerSource output argument | test.cpp:436:8:436:13 | * ... |
+| test.cpp:440:7:440:11 | definition of local | test.cpp:442:8:442:12 | local |
+| test.cpp:441:18:441:23 | intArraySource output argument | test.cpp:442:8:442:12 | local |
+| test.cpp:448:7:448:11 | definition of local | test.cpp:450:8:450:12 | local |
+| test.cpp:449:18:449:22 | intArraySource output argument | test.cpp:451:8:451:13 | * ... |
+| test.cpp:456:26:456:32 | source1 | test.cpp:457:9:457:22 | (statement expression) |
+| test.cpp:456:26:456:32 | source1 | test.cpp:468:8:468:12 | local |
+| test.cpp:472:8:472:13 | call to source | test.cpp:478:8:478:8 | x |
+| test.cpp:506:8:506:13 | call to source | test.cpp:513:8:513:8 | x |
+| test.cpp:519:19:519:24 | call to source | test.cpp:521:8:521:20 | access to array |
+| test.cpp:531:29:531:34 | call to source | test.cpp:532:8:532:9 | * ... |
+| test.cpp:547:9:547:9 | definition of x | test.cpp:536:10:536:11 | * ... |
+| test.cpp:551:9:551:9 | definition of y | test.cpp:541:10:541:10 | y |
+| test.cpp:562:17:562:31 | call to indirect_source indirection | test.cpp:566:10:566:19 | * ... |
+| test.cpp:562:17:562:31 | call to indirect_source indirection | test.cpp:568:10:568:19 | * ... |
+| test.cpp:562:17:562:31 | call to indirect_source indirection | test.cpp:572:10:572:19 | * ... |
+| test.cpp:562:17:562:31 | call to indirect_source indirection | test.cpp:578:10:578:19 | * ... |
+| test.cpp:576:17:576:31 | call to indirect_source indirection | test.cpp:566:10:566:19 | * ... |
+| test.cpp:576:17:576:31 | call to indirect_source indirection | test.cpp:568:10:568:19 | * ... |
+| test.cpp:576:17:576:31 | call to indirect_source indirection | test.cpp:572:10:572:19 | * ... |
+| test.cpp:576:17:576:31 | call to indirect_source indirection | test.cpp:578:10:578:19 | * ... |
+| test.cpp:594:12:594:26 | call to indirect_source indirection | test.cpp:597:8:597:13 | * ... |
+| test.cpp:601:20:601:20 | intPointerSource output argument | test.cpp:603:8:603:9 | * ... |
+| test.cpp:607:20:607:20 | intPointerSource output argument | test.cpp:609:8:609:9 | * ... |
+| test.cpp:614:20:614:20 | intPointerSource output argument | test.cpp:616:8:616:17 | * ... |
+| test.cpp:628:20:628:25 | intPointerSource output argument | test.cpp:629:17:629:22 | buffer indirection |
+| test.cpp:633:18:633:23 | call to source | test.cpp:634:8:634:8 | x |
+| test.cpp:646:7:646:12 | call to source | test.cpp:645:8:645:8 | x |
+| test.cpp:660:7:660:12 | call to source | test.cpp:658:8:658:8 | x |
+| test.cpp:664:18:664:23 | call to source | test.cpp:666:8:666:16 | * ... |
+| test.cpp:681:7:681:12 | call to source | test.cpp:679:8:679:16 | * ... |
+| test.cpp:733:7:733:7 | definition of x | test.cpp:735:8:735:8 | x |
+| test.cpp:751:27:751:32 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:753:32:753:37 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:755:32:755:37 | call to source | test.cpp:740:10:740:10 | x |
+| test.cpp:771:27:771:32 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:773:32:773:37 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:775:32:775:37 | call to source | test.cpp:760:10:760:10 | x |
+| test.cpp:788:31:788:36 | call to source | test.cpp:782:12:782:12 | x |
+| test.cpp:790:31:790:36 | call to source | test.cpp:782:12:782:12 | x |
+| test.cpp:797:22:797:28 | intPointerSource output argument | test.cpp:798:19:798:25 | content indirection |
+| test.cpp:808:25:808:39 | call to indirect_source indirection | test.cpp:813:19:813:35 | * ... indirection |
+| test.cpp:818:26:818:31 | call to source | test.cpp:823:10:823:27 | * ... |
+| test.cpp:832:21:832:26 | call to source | test.cpp:836:10:836:22 | global_direct |
+| test.cpp:842:11:842:16 | call to source | test.cpp:844:8:844:8 | y |
+| test.cpp:846:13:846:27 | call to indirect_source indirection | test.cpp:848:17:848:25 | rpx indirection |
+| test.cpp:853:55:853:62 | call to source | test.cpp:854:10:854:36 | * ... |
+| test.cpp:860:54:860:59 | call to source | test.cpp:861:10:861:37 | static_local_pointer_dynamic |
+| test.cpp:872:46:872:51 | call to source | test.cpp:875:10:875:31 | global_pointer_dynamic |
+| test.cpp:880:64:880:83 | indirect_source(1) indirection | test.cpp:883:10:883:45 | static_local_array_static_indirect_1 |
+| test.cpp:881:64:881:83 | indirect_source(2) indirection | test.cpp:886:19:886:54 | static_local_array_static_indirect_2 indirection |
+| test.cpp:890:54:890:61 | source | test.cpp:893:10:893:36 | static_local_pointer_static |
+| test.cpp:891:65:891:84 | indirect_source(1) indirection | test.cpp:895:19:895:56 | static_local_pointer_static_indirect_1 indirection |
+| test.cpp:901:56:901:75 | indirect_source(1) indirection | test.cpp:907:10:907:39 | global_array_static_indirect_1 |
+| test.cpp:902:56:902:75 | indirect_source(2) indirection | test.cpp:911:19:911:48 | global_array_static_indirect_2 indirection |
+| test.cpp:914:46:914:53 | source | test.cpp:919:10:919:30 | global_pointer_static |
+| test.cpp:915:57:915:76 | indirect_source(1) indirection | test.cpp:921:19:921:50 | global_pointer_static_indirect_1 indirection |
+| true_upon_entry.cpp:9:11:9:16 | call to source | true_upon_entry.cpp:13:8:13:8 | x |
+| true_upon_entry.cpp:17:11:17:16 | call to source | true_upon_entry.cpp:21:8:21:8 | x |
+| true_upon_entry.cpp:27:9:27:14 | call to source | true_upon_entry.cpp:29:8:29:8 | x |
+| true_upon_entry.cpp:33:11:33:16 | call to source | true_upon_entry.cpp:39:8:39:8 | x |
+| true_upon_entry.cpp:43:11:43:16 | call to source | true_upon_entry.cpp:49:8:49:8 | x |
+| true_upon_entry.cpp:54:11:54:16 | call to source | true_upon_entry.cpp:57:8:57:8 | x |
+| true_upon_entry.cpp:62:11:62:16 | call to source | true_upon_entry.cpp:66:8:66:8 | x |
+| true_upon_entry.cpp:70:11:70:16 | call to source | true_upon_entry.cpp:78:8:78:8 | x |
+| true_upon_entry.cpp:83:11:83:16 | call to source | true_upon_entry.cpp:86:8:86:8 | x |
+| true_upon_entry.cpp:98:11:98:16 | call to source | true_upon_entry.cpp:105:8:105:8 | x |
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.ql b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.ql
new file mode 100644
index 00000000000..4198e007d2e
--- /dev/null
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test-source-sink.ql
@@ -0,0 +1,9 @@
+import TestBase
+
+query predicate astFlow(AstTest::DataFlow::Node source, AstTest::DataFlow::Node sink) {
+ AstTest::AstFlow::flow(source, sink)
+}
+
+query predicate irFlow(IRTest::DataFlow::Node source, IRTest::DataFlow::Node sink) {
+ IRTest::IRFlow::flow(source, sink)
+}
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.cpp b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.cpp
index 73c9fd28b93..b5883963620 100644
--- a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.cpp
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.cpp
@@ -1,5 +1,5 @@
int source();
-void sink(int); void sink(const int *); void sink(int **); void indirect_sink(...);
+void sink(...); void indirect_sink(...);
void intraprocedural_with_local_flow() {
int t2;
@@ -836,4 +836,90 @@ namespace MoreGlobalTests {
sink(global_direct); // $ ir MISSING: ast
indirect_sink(global_direct); // clean
}
+}
+
+void test_references() {
+ int x = source();
+ int &y = x;
+ sink(y); // $ ast,ir
+
+ int* px = indirect_source();
+ int*& rpx = px;
+ indirect_sink((int*)rpx); // $ ast,ir
+}
+
+namespace GlobalArrays {
+ void test1() {
+ static const int static_local_array_dynamic[] = { ::source() };
+ sink(*static_local_array_dynamic); // $ ir MISSING: ast
+ }
+
+ const int* source(bool);
+
+ void test2() {
+ static const int* static_local_pointer_dynamic = source(true);
+ sink(static_local_pointer_dynamic); // $ ast,ir
+ }
+
+ static const int global_array_dynamic[] = { ::source() };
+
+ void test3() {
+ sink(*global_array_dynamic); // $ MISSING: ir,ast // Missing in IR because no 'IRFunction' for global_array is generated because the type of global_array_dynamic is "deeply const".
+ }
+
+ const int* source(bool);
+
+ static const int* global_pointer_dynamic = source(true);
+
+ void test4() {
+ sink(global_pointer_dynamic); // $ ir MISSING: ast
+ }
+
+ void test5() {
+ static const char static_local_array_static[] = "source";
+ static const char static_local_array_static_indirect_1[] = "indirect_source(1)";
+ static const char static_local_array_static_indirect_2[] = "indirect_source(2)";
+ sink(static_local_array_static); // clean
+ sink(static_local_array_static_indirect_1); // $ ir MISSING: ast
+ indirect_sink(static_local_array_static_indirect_1); // clean
+ sink(static_local_array_static_indirect_2); // clean
+ indirect_sink(static_local_array_static_indirect_2); // $ ir MISSING: ast
+ }
+
+ void test6() {
+ static const char* static_local_pointer_static = "source";
+ static const char* static_local_pointer_static_indirect_1 = "indirect_source(1)";
+ static const char* static_local_pointer_static_indirect_2 = "indirect_source(2)";
+ sink(static_local_pointer_static); // $ ir MISSING: ast
+ sink(static_local_pointer_static_indirect_1); // clean
+ indirect_sink(static_local_pointer_static_indirect_1); // $ ir MISSING: ast
+ sink(static_local_pointer_static_indirect_2); // clean: static_local_pointer_static_indirect_2 does not have 2 indirections
+ indirect_sink(static_local_pointer_static_indirect_2); // clean: static_local_pointer_static_indirect_2 does not have 2 indirections
+ }
+
+ static const char global_array_static[] = "source";
+ static const char global_array_static_indirect_1[] = "indirect_source(1)";
+ static const char global_array_static_indirect_2[] = "indirect_source(2)";
+
+ void test7() {
+ sink(global_array_static); // clean
+ sink(*global_array_static); // clean
+ sink(global_array_static_indirect_1); // $ ir MISSING: ast
+ sink(*global_array_static_indirect_1); // clean
+ indirect_sink(global_array_static); // clean
+ indirect_sink(global_array_static_indirect_1); // clean
+ indirect_sink(global_array_static_indirect_2); // $ ir MISSING: ast
+ }
+
+ static const char* global_pointer_static = "source";
+ static const char* global_pointer_static_indirect_1 = "indirect_source(1)";
+ static const char* global_pointer_static_indirect_2 = "indirect_source(2)";
+
+ void test8() {
+ sink(global_pointer_static); // $ ir MISSING: ast
+ sink(global_pointer_static_indirect_1); // clean
+ indirect_sink(global_pointer_static_indirect_1); // $ ir MISSING: ast
+ sink(global_pointer_static_indirect_2); // clean: global_pointer_static_indirect_2 does not have 2 indirections
+ indirect_sink(global_pointer_static_indirect_2); // clean: global_pointer_static_indirect_2 does not have 2 indirections
+ }
}
\ No newline at end of file
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.expected b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.expected
index d4756e8d808..8ec8033d086 100644
--- a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.expected
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.expected
@@ -1,9 +1,2 @@
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:19,45-53)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:20,24-32)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:27,15-23)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:33,22-30)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:40,25-33)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:42,17-25)
-WARNING: Module DataFlow has been deprecated and may be removed in future (test.ql:46,20-28)
testFailures
failures
diff --git a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.ql b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.ql
index ea27ec0d51d..05e1112d5f3 100644
--- a/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.ql
+++ b/cpp/ql/test/library-tests/dataflow/dataflow-tests/test.ql
@@ -1,107 +1,3 @@
+import TestBase
import TestUtilities.dataflow.FlowTestCommon
-
-module AstTest {
- private import semmle.code.cpp.dataflow.DataFlow
- private import semmle.code.cpp.controlflow.Guards
-
- /**
- * A `BarrierGuard` that stops flow to all occurrences of `x` within statement
- * S in `if (guarded(x)) S`.
- */
- // This is tested in `BarrierGuard.cpp`.
- predicate testBarrierGuard(GuardCondition g, Expr checked, boolean isTrue) {
- g.(FunctionCall).getTarget().getName() = "guarded" and
- checked = g.(FunctionCall).getArgument(0) and
- isTrue = true
- }
-
- /** Common data flow configuration to be used by tests. */
- module AstTestAllocationConfig implements DataFlow::ConfigSig {
- predicate isSource(DataFlow::Node source) {
- source.asExpr().(FunctionCall).getTarget().getName() = "source"
- or
- source.asParameter().getName().matches("source%")
- or
- source.asExpr().(FunctionCall).getTarget().getName() = "indirect_source"
- or
- source.(DataFlow::DefinitionByReferenceNode).getParameter().getName().matches("ref_source%")
- or
- // Track uninitialized variables
- exists(source.asUninitialized())
- }
-
- predicate isSink(DataFlow::Node sink) {
- exists(FunctionCall call |
- call.getTarget().getName() = ["sink", "indirect_sink"] and
- sink.asExpr() = call.getAnArgument()
- )
- }
-
- predicate isBarrier(DataFlow::Node barrier) {
- barrier.asExpr().(VariableAccess).getTarget().hasName("barrier") or
- barrier = DataFlow::BarrierGuard::getABarrierNode()
- }
- }
-
- module AstFlow = DataFlow::Global;
-}
-
-module IRTest {
- private import cpp
- private import semmle.code.cpp.ir.dataflow.DataFlow
- private import semmle.code.cpp.ir.IR
- private import semmle.code.cpp.controlflow.IRGuards
-
- /**
- * A `BarrierGuard` that stops flow to all occurrences of `x` within statement
- * S in `if (guarded(x)) S`.
- */
- // This is tested in `BarrierGuard.cpp`.
- predicate testBarrierGuard(IRGuardCondition g, Expr checked, boolean isTrue) {
- exists(Call call |
- call = g.getUnconvertedResultExpression() and
- call.getTarget().hasName("guarded") and
- checked = call.getArgument(0) and
- isTrue = true
- )
- }
-
- /** Common data flow configuration to be used by tests. */
- module IRTestAllocationConfig implements DataFlow::ConfigSig {
- predicate isSource(DataFlow::Node source) {
- source.asExpr().(FunctionCall).getTarget().getName() = "source"
- or
- source.asIndirectExpr(1).(FunctionCall).getTarget().getName() = "indirect_source"
- or
- source.asParameter().getName().matches("source%")
- or
- source.(DataFlow::DefinitionByReferenceNode).getParameter().getName().matches("ref_source%")
- or
- exists(source.asUninitialized())
- }
-
- predicate isSink(DataFlow::Node sink) {
- exists(FunctionCall call, Expr e | e = call.getAnArgument() |
- call.getTarget().getName() = "sink" and
- sink.asExpr() = e
- or
- call.getTarget().getName() = "indirect_sink" and
- sink.asIndirectExpr() = e
- )
- }
-
- predicate isBarrier(DataFlow::Node barrier) {
- exists(Expr barrierExpr | barrierExpr in [barrier.asExpr(), barrier.asIndirectExpr()] |
- barrierExpr.(VariableAccess).getTarget().hasName("barrier")
- )
- or
- barrier = DataFlow::BarrierGuard::getABarrierNode()
- or
- barrier = DataFlow::BarrierGuard::getAnIndirectBarrierNode()
- }
- }
-
- module IRFlow = DataFlow::Global;
-}
-
import MakeTest, IRFlowTest>>
diff --git a/cpp/ql/test/library-tests/ir/ir/aliased_ir.expected b/cpp/ql/test/library-tests/ir/ir/aliased_ir.expected
index d7e3c36d204..9d56ffda040 100644
--- a/cpp/ql/test/library-tests/ir/ir/aliased_ir.expected
+++ b/cpp/ql/test/library-tests/ir/ir/aliased_ir.expected
@@ -2770,43 +2770,65 @@ ir.cpp:
# 462| m462_2(int) = Uninitialized[x] : &:r462_1
# 463| r463_1(glval) = VariableAddress[a] :
# 463| r463_2(bool) = Load[a] : &:r463_1, m461_6
-# 463| v463_3(void) = ConditionalBranch : r463_2
-#-----| False -> Block 1
-#-----| True -> Block 2
+# 463| r463_3(bool) = LogicalNot : r463_2
+# 463| v463_4(void) = ConditionalBranch : r463_3
+#-----| False -> Block 5
+#-----| True -> Block 1
# 464| Block 1
# 464| r464_1(int) = Constant[1] :
# 464| r464_2(glval) = VariableAddress[x] :
# 464| m464_3(int) = Store[x] : &:r464_2, r464_1
-#-----| Goto -> Block 2
+#-----| Goto -> Block 5
# 467| Block 2
-# 467| r467_1(glval) = VariableAddress[a] :
-# 467| r467_2(bool) = Load[a] : &:r467_1, m461_6
-# 467| v467_3(void) = ConditionalBranch : r467_2
-#-----| False -> Block 4
-#-----| True -> Block 3
+# 467| r467_1(glval) = VariableAddress[#temp467:11] :
+# 467| r467_2(bool) = Constant[0] :
+# 467| m467_3(bool) = Store[#temp467:11] : &:r467_1, r467_2
+#-----| Goto -> Block 3
# 467| Block 3
-# 467| r467_4(glval) = VariableAddress[b] :
-# 467| r467_5(bool) = Load[b] : &:r467_4, m461_8
-# 467| v467_6(void) = ConditionalBranch : r467_5
-#-----| False -> Block 4
-#-----| True -> Block 5
+# 467| m467_4(bool) = Phi : from 2:m467_3, from 4:m467_11
+# 467| r467_5(glval) = VariableAddress[#temp467:11] :
+# 467| r467_6(bool) = Load[#temp467:11] : &:r467_5, m467_4
+# 467| r467_7(bool) = LogicalNot : r467_6
+# 467| v467_8(void) = ConditionalBranch : r467_7
+#-----| False -> Block 8
+#-----| True -> Block 7
-# 468| Block 4
+# 467| Block 4
+# 467| r467_9(glval) = VariableAddress[#temp467:11] :
+# 467| r467_10(bool) = Constant[1] :
+# 467| m467_11(bool) = Store[#temp467:11] : &:r467_9, r467_10
+#-----| Goto -> Block 3
+
+# 467| Block 5
+# 467| r467_12(glval) = VariableAddress[a] :
+# 467| r467_13(bool) = Load[a] : &:r467_12, m461_6
+# 467| v467_14(void) = ConditionalBranch : r467_13
+#-----| False -> Block 2
+#-----| True -> Block 6
+
+# 467| Block 6
+# 467| r467_15(glval) = VariableAddress[b] :
+# 467| r467_16(bool) = Load[b] : &:r467_15, m461_8
+# 467| v467_17(void) = ConditionalBranch : r467_16
+#-----| False -> Block 2
+#-----| True -> Block 4
+
+# 468| Block 7
# 468| r468_1(int) = Constant[2] :
# 468| r468_2(glval) = VariableAddress[x] :
# 468| m468_3(int) = Store[x] : &:r468_2, r468_1
-#-----| Goto -> Block 6
+#-----| Goto -> Block 9
-# 471| Block 5
+# 471| Block 8
# 471| r471_1(int) = Constant[3] :
# 471| r471_2(glval) = VariableAddress[x] :
# 471| m471_3(int) = Store[x] : &:r471_2, r471_1
-#-----| Goto -> Block 6
+#-----| Goto -> Block 9
-# 473| Block 6
+# 473| Block 9
# 473| v473_1(void) = NoOp :
# 461| v461_9(void) = ReturnVoid :
# 461| v461_10(void) = AliasedUse : m461_3
diff --git a/cpp/ql/test/library-tests/ir/ir/operand_locations.expected b/cpp/ql/test/library-tests/ir/ir/operand_locations.expected
index 39d238c1fae..c77c7f5e364 100644
--- a/cpp/ql/test/library-tests/ir/ir/operand_locations.expected
+++ b/cpp/ql/test/library-tests/ir/ir/operand_locations.expected
@@ -2398,16 +2398,27 @@
| ir.cpp:461:22:461:22 | Address | &:r461_5 |
| ir.cpp:461:30:461:30 | Address | &:r461_7 |
| ir.cpp:462:9:462:9 | Address | &:r462_1 |
+| ir.cpp:463:9:463:10 | Condition | r463_3 |
| ir.cpp:463:10:463:10 | Address | &:r463_1 |
-| ir.cpp:463:10:463:10 | Condition | r463_2 |
| ir.cpp:463:10:463:10 | Load | m461_6 |
+| ir.cpp:463:10:463:10 | Unary | r463_2 |
| ir.cpp:464:9:464:9 | Address | &:r464_2 |
| ir.cpp:464:13:464:13 | StoreValue | r464_1 |
-| ir.cpp:467:11:467:11 | Address | &:r467_1 |
-| ir.cpp:467:11:467:11 | Condition | r467_2 |
+| ir.cpp:467:9:467:17 | Condition | r467_7 |
+| ir.cpp:467:11:467:11 | Address | &:r467_12 |
+| ir.cpp:467:11:467:11 | Condition | r467_13 |
| ir.cpp:467:11:467:11 | Load | m461_6 |
-| ir.cpp:467:16:467:16 | Address | &:r467_4 |
-| ir.cpp:467:16:467:16 | Condition | r467_5 |
+| ir.cpp:467:11:467:16 | Address | &:r467_1 |
+| ir.cpp:467:11:467:16 | Address | &:r467_5 |
+| ir.cpp:467:11:467:16 | Address | &:r467_9 |
+| ir.cpp:467:11:467:16 | Load | m467_4 |
+| ir.cpp:467:11:467:16 | Phi | from 2:m467_3 |
+| ir.cpp:467:11:467:16 | Phi | from 4:m467_11 |
+| ir.cpp:467:11:467:16 | StoreValue | r467_2 |
+| ir.cpp:467:11:467:16 | StoreValue | r467_10 |
+| ir.cpp:467:11:467:16 | Unary | r467_6 |
+| ir.cpp:467:16:467:16 | Address | &:r467_15 |
+| ir.cpp:467:16:467:16 | Condition | r467_16 |
| ir.cpp:467:16:467:16 | Load | m461_8 |
| ir.cpp:468:9:468:9 | Address | &:r468_2 |
| ir.cpp:468:13:468:13 | StoreValue | r468_1 |
diff --git a/cpp/ql/test/library-tests/ir/ir/raw_ir.expected b/cpp/ql/test/library-tests/ir/ir/raw_ir.expected
index f43a105f70a..88b3f5dafd1 100644
--- a/cpp/ql/test/library-tests/ir/ir/raw_ir.expected
+++ b/cpp/ql/test/library-tests/ir/ir/raw_ir.expected
@@ -2725,43 +2725,64 @@ ir.cpp:
# 462| mu462_2(int) = Uninitialized[x] : &:r462_1
# 463| r463_1(glval) = VariableAddress[a] :
# 463| r463_2(bool) = Load[a] : &:r463_1, ~m?
-# 463| v463_3(void) = ConditionalBranch : r463_2
-#-----| False -> Block 1
-#-----| True -> Block 2
+# 463| r463_3(bool) = LogicalNot : r463_2
+# 463| v463_4(void) = ConditionalBranch : r463_3
+#-----| False -> Block 5
+#-----| True -> Block 1
# 464| Block 1
# 464| r464_1(int) = Constant[1] :
# 464| r464_2(glval) = VariableAddress[x] :
# 464| mu464_3(int) = Store[x] : &:r464_2, r464_1
-#-----| Goto -> Block 2
+#-----| Goto -> Block 5
# 467| Block 2
-# 467| r467_1(glval) = VariableAddress[a] :
-# 467| r467_2(bool) = Load[a] : &:r467_1, ~m?
-# 467| v467_3(void) = ConditionalBranch : r467_2
-#-----| False -> Block 4
-#-----| True -> Block 3
+# 467| r467_1(glval) = VariableAddress[#temp467:11] :
+# 467| r467_2(bool) = Constant[0] :
+# 467| mu467_3(bool) = Store[#temp467:11] : &:r467_1, r467_2
+#-----| Goto -> Block 3
# 467| Block 3
-# 467| r467_4(glval) = VariableAddress[b] :
-# 467| r467_5(bool) = Load[b] : &:r467_4, ~m?
-# 467| v467_6(void) = ConditionalBranch : r467_5
-#-----| False -> Block 4
-#-----| True -> Block 5
+# 467| r467_4(glval) = VariableAddress[#temp467:11] :
+# 467| r467_5(bool) = Load[#temp467:11] : &:r467_4, ~m?
+# 467| r467_6(bool) = LogicalNot : r467_5
+# 467| v467_7(void) = ConditionalBranch : r467_6
+#-----| False -> Block 8
+#-----| True -> Block 7
-# 468| Block 4
+# 467| Block 4
+# 467| r467_8(glval) = VariableAddress[#temp467:11] :
+# 467| r467_9(bool) = Constant[1] :
+# 467| mu467_10(bool) = Store[#temp467:11] : &:r467_8, r467_9
+#-----| Goto -> Block 3
+
+# 467| Block 5
+# 467| r467_11(glval) = VariableAddress[a] :
+# 467| r467_12(bool) = Load[a] : &:r467_11, ~m?
+# 467| v467_13(void) = ConditionalBranch : r467_12
+#-----| False -> Block 2
+#-----| True -> Block 6
+
+# 467| Block 6
+# 467| r467_14(glval) = VariableAddress[b] :
+# 467| r467_15(bool) = Load[b] : &:r467_14, ~m?
+# 467| v467_16(void) = ConditionalBranch : r467_15
+#-----| False -> Block 2
+#-----| True -> Block 4
+
+# 468| Block 7
# 468| r468_1(int) = Constant[2] :
# 468| r468_2(glval) = VariableAddress[x] :
# 468| mu468_3(int) = Store[x] : &:r468_2, r468_1
-#-----| Goto -> Block 6
+#-----| Goto -> Block 9
-# 471| Block 5
+# 471| Block 8
# 471| r471_1(int) = Constant[3] :
# 471| r471_2(glval) = VariableAddress[x] :
# 471| mu471_3(int) = Store[x] : &:r471_2, r471_1
-#-----| Goto -> Block 6
+#-----| Goto -> Block 9
-# 473| Block 6
+# 473| Block 9
# 473| v473_1(void) = NoOp :
# 461| v461_8(void) = ReturnVoid :
# 461| v461_9(void) = AliasedUse : ~m?
diff --git a/cpp/ql/test/query-tests/Likely Bugs/Memory Management/ImproperNullTermination/ImproperNullTerminationTainted.expected b/cpp/ql/test/query-tests/Likely Bugs/Memory Management/ImproperNullTermination/ImproperNullTerminationTainted.expected
index 34c3ad79520..247f134a179 100644
--- a/cpp/ql/test/query-tests/Likely Bugs/Memory Management/ImproperNullTermination/ImproperNullTerminationTainted.expected
+++ b/cpp/ql/test/query-tests/Likely Bugs/Memory Management/ImproperNullTermination/ImproperNullTerminationTainted.expected
@@ -1,2 +1,2 @@
-| test.cpp:466:10:466:15 | buffer | String operation depends on a $@ that may not be null terminated. | test.cpp:465:18:465:23 | buffer | user-provided value |
-| test.cpp:481:10:481:15 | buffer | String operation depends on a $@ that may not be null terminated. | test.cpp:480:9:480:14 | buffer | user-provided value |
+| test.cpp:466:10:466:15 | buffer | String operation depends on $@ that may not be null terminated. | test.cpp:465:18:465:23 | read output argument | buffer read by read |
+| test.cpp:481:10:481:15 | buffer | String operation depends on $@ that may not be null terminated. | test.cpp:480:9:480:14 | fread output argument | string read by fread |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-078/semmle/ExecTainted/ExecTainted.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-078/semmle/ExecTainted/ExecTainted.expected
index 094234a77be..e0d25038104 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-078/semmle/ExecTainted/ExecTainted.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-078/semmle/ExecTainted/ExecTainted.expected
@@ -14,18 +14,15 @@ edges
| test.cpp:91:9:91:16 | fread output argument | test.cpp:93:17:93:24 | filename indirection |
| test.cpp:93:11:93:14 | strncat output argument | test.cpp:94:45:94:48 | path indirection |
| test.cpp:93:17:93:24 | filename indirection | test.cpp:93:11:93:14 | strncat output argument |
-| test.cpp:106:20:106:38 | call to getenv | test.cpp:107:33:107:36 | path indirection |
| test.cpp:106:20:106:38 | call to getenv indirection | test.cpp:107:33:107:36 | path indirection |
| test.cpp:107:31:107:31 | call to operator+ | test.cpp:108:18:108:22 | call to c_str indirection |
| test.cpp:107:33:107:36 | path indirection | test.cpp:107:31:107:31 | call to operator+ |
-| test.cpp:113:20:113:38 | call to getenv | test.cpp:114:19:114:22 | path indirection |
| test.cpp:113:20:113:38 | call to getenv indirection | test.cpp:114:19:114:22 | path indirection |
| test.cpp:114:10:114:23 | call to operator+ | test.cpp:114:25:114:29 | call to c_str indirection |
| test.cpp:114:10:114:23 | call to operator+ | test.cpp:114:25:114:29 | call to c_str indirection |
| test.cpp:114:17:114:17 | call to operator+ | test.cpp:114:10:114:23 | call to operator+ |
| test.cpp:114:19:114:22 | path indirection | test.cpp:114:10:114:23 | call to operator+ |
| test.cpp:114:19:114:22 | path indirection | test.cpp:114:17:114:17 | call to operator+ |
-| test.cpp:119:20:119:38 | call to getenv | test.cpp:120:19:120:22 | path indirection |
| test.cpp:119:20:119:38 | call to getenv indirection | test.cpp:120:19:120:22 | path indirection |
| test.cpp:120:17:120:17 | call to operator+ | test.cpp:120:10:120:30 | call to data indirection |
| test.cpp:120:19:120:22 | path indirection | test.cpp:120:17:120:17 | call to operator+ |
@@ -89,12 +86,10 @@ nodes
| test.cpp:93:11:93:14 | strncat output argument | semmle.label | strncat output argument |
| test.cpp:93:17:93:24 | filename indirection | semmle.label | filename indirection |
| test.cpp:94:45:94:48 | path indirection | semmle.label | path indirection |
-| test.cpp:106:20:106:38 | call to getenv | semmle.label | call to getenv |
| test.cpp:106:20:106:38 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:107:31:107:31 | call to operator+ | semmle.label | call to operator+ |
| test.cpp:107:33:107:36 | path indirection | semmle.label | path indirection |
| test.cpp:108:18:108:22 | call to c_str indirection | semmle.label | call to c_str indirection |
-| test.cpp:113:20:113:38 | call to getenv | semmle.label | call to getenv |
| test.cpp:113:20:113:38 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:114:10:114:23 | call to operator+ | semmle.label | call to operator+ |
| test.cpp:114:10:114:23 | call to operator+ | semmle.label | call to operator+ |
@@ -102,7 +97,6 @@ nodes
| test.cpp:114:19:114:22 | path indirection | semmle.label | path indirection |
| test.cpp:114:25:114:29 | call to c_str indirection | semmle.label | call to c_str indirection |
| test.cpp:114:25:114:29 | call to c_str indirection | semmle.label | call to c_str indirection |
-| test.cpp:119:20:119:38 | call to getenv | semmle.label | call to getenv |
| test.cpp:119:20:119:38 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:120:10:120:30 | call to data indirection | semmle.label | call to data indirection |
| test.cpp:120:17:120:17 | call to operator+ | semmle.label | call to operator+ |
@@ -156,13 +150,9 @@ subpaths
| test.cpp:65:10:65:16 | command | test.cpp:62:9:62:16 | fread output argument | test.cpp:65:10:65:16 | command indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:62:9:62:16 | fread output argument | user input (string read by fread) | test.cpp:64:11:64:17 | strncat output argument | strncat output argument |
| test.cpp:85:32:85:38 | command | test.cpp:82:9:82:16 | fread output argument | test.cpp:85:32:85:38 | command indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to execl. | test.cpp:82:9:82:16 | fread output argument | user input (string read by fread) | test.cpp:84:11:84:17 | strncat output argument | strncat output argument |
| test.cpp:94:45:94:48 | path | test.cpp:91:9:91:16 | fread output argument | test.cpp:94:45:94:48 | path indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to execl. | test.cpp:91:9:91:16 | fread output argument | user input (string read by fread) | test.cpp:93:11:93:14 | strncat output argument | strncat output argument |
-| test.cpp:108:18:108:22 | call to c_str | test.cpp:106:20:106:38 | call to getenv | test.cpp:108:18:108:22 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:106:20:106:38 | call to getenv | user input (an environment variable) | test.cpp:107:31:107:31 | call to operator+ | call to operator+ |
| test.cpp:108:18:108:22 | call to c_str | test.cpp:106:20:106:38 | call to getenv indirection | test.cpp:108:18:108:22 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:106:20:106:38 | call to getenv indirection | user input (an environment variable) | test.cpp:107:31:107:31 | call to operator+ | call to operator+ |
-| test.cpp:114:25:114:29 | call to c_str | test.cpp:113:20:113:38 | call to getenv | test.cpp:114:25:114:29 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:113:20:113:38 | call to getenv | user input (an environment variable) | test.cpp:114:10:114:23 | call to operator+ | call to operator+ |
-| test.cpp:114:25:114:29 | call to c_str | test.cpp:113:20:113:38 | call to getenv | test.cpp:114:25:114:29 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:113:20:113:38 | call to getenv | user input (an environment variable) | test.cpp:114:17:114:17 | call to operator+ | call to operator+ |
| test.cpp:114:25:114:29 | call to c_str | test.cpp:113:20:113:38 | call to getenv indirection | test.cpp:114:25:114:29 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:113:20:113:38 | call to getenv indirection | user input (an environment variable) | test.cpp:114:10:114:23 | call to operator+ | call to operator+ |
| test.cpp:114:25:114:29 | call to c_str | test.cpp:113:20:113:38 | call to getenv indirection | test.cpp:114:25:114:29 | call to c_str indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:113:20:113:38 | call to getenv indirection | user input (an environment variable) | test.cpp:114:17:114:17 | call to operator+ | call to operator+ |
-| test.cpp:120:25:120:28 | call to data | test.cpp:119:20:119:38 | call to getenv | test.cpp:120:10:120:30 | call to data indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:119:20:119:38 | call to getenv | user input (an environment variable) | test.cpp:120:17:120:17 | call to operator+ | call to operator+ |
| test.cpp:120:25:120:28 | call to data | test.cpp:119:20:119:38 | call to getenv indirection | test.cpp:120:10:120:30 | call to data indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:119:20:119:38 | call to getenv indirection | user input (an environment variable) | test.cpp:120:17:120:17 | call to operator+ | call to operator+ |
| test.cpp:143:10:143:16 | command | test.cpp:140:9:140:11 | fread output argument | test.cpp:143:10:143:16 | command indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to system(string). | test.cpp:140:9:140:11 | fread output argument | user input (string read by fread) | test.cpp:142:11:142:17 | sprintf output argument | sprintf output argument |
| test.cpp:183:32:183:38 | command | test.cpp:174:9:174:16 | fread output argument | test.cpp:183:32:183:38 | command indirection | This argument to an OS command is derived from $@, dangerously concatenated into $@, and then passed to execl. | test.cpp:174:9:174:16 | fread output argument | user input (string read by fread) | test.cpp:177:13:177:17 | strncat output argument | strncat output argument |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-114/semmle/UncontrolledProcessOperation/UncontrolledProcessOperation.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-114/semmle/UncontrolledProcessOperation/UncontrolledProcessOperation.expected
index b30de4bceba..816c8f156e7 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-114/semmle/UncontrolledProcessOperation/UncontrolledProcessOperation.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-114/semmle/UncontrolledProcessOperation/UncontrolledProcessOperation.expected
@@ -5,7 +5,6 @@ edges
| test.cpp:43:18:43:34 | call to getenv indirection | test.cpp:29:30:29:36 | command indirection |
| test.cpp:56:12:56:17 | fgets output argument | test.cpp:62:10:62:15 | buffer indirection |
| test.cpp:56:12:56:17 | fgets output argument | test.cpp:63:10:63:13 | data indirection |
-| test.cpp:56:12:56:17 | fgets output argument | test.cpp:64:10:64:16 | (reference dereference) indirection |
| test.cpp:56:12:56:17 | fgets output argument | test.cpp:64:10:64:16 | dataref indirection |
| test.cpp:56:12:56:17 | fgets output argument | test.cpp:65:10:65:14 | data2 indirection |
| test.cpp:76:12:76:17 | fgets output argument | test.cpp:78:10:78:15 | buffer indirection |
@@ -22,7 +21,6 @@ nodes
| test.cpp:56:12:56:17 | fgets output argument | semmle.label | fgets output argument |
| test.cpp:62:10:62:15 | buffer indirection | semmle.label | buffer indirection |
| test.cpp:63:10:63:13 | data indirection | semmle.label | data indirection |
-| test.cpp:64:10:64:16 | (reference dereference) indirection | semmle.label | (reference dereference) indirection |
| test.cpp:64:10:64:16 | dataref indirection | semmle.label | dataref indirection |
| test.cpp:65:10:65:14 | data2 indirection | semmle.label | data2 indirection |
| test.cpp:76:12:76:17 | fgets output argument | semmle.label | fgets output argument |
@@ -39,7 +37,6 @@ subpaths
| test.cpp:31:10:31:16 | command indirection | test.cpp:43:18:43:34 | call to getenv indirection | test.cpp:31:10:31:16 | command indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:43:18:43:34 | call to getenv indirection | an environment variable |
| test.cpp:62:10:62:15 | buffer indirection | test.cpp:56:12:56:17 | fgets output argument | test.cpp:62:10:62:15 | buffer indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:56:12:56:17 | fgets output argument | string read by fgets |
| test.cpp:63:10:63:13 | data indirection | test.cpp:56:12:56:17 | fgets output argument | test.cpp:63:10:63:13 | data indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:56:12:56:17 | fgets output argument | string read by fgets |
-| test.cpp:64:10:64:16 | (reference dereference) indirection | test.cpp:56:12:56:17 | fgets output argument | test.cpp:64:10:64:16 | (reference dereference) indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:56:12:56:17 | fgets output argument | string read by fgets |
| test.cpp:64:10:64:16 | dataref indirection | test.cpp:56:12:56:17 | fgets output argument | test.cpp:64:10:64:16 | dataref indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:56:12:56:17 | fgets output argument | string read by fgets |
| test.cpp:65:10:65:14 | data2 indirection | test.cpp:56:12:56:17 | fgets output argument | test.cpp:65:10:65:14 | data2 indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:56:12:56:17 | fgets output argument | string read by fgets |
| test.cpp:78:10:78:15 | buffer indirection | test.cpp:76:12:76:17 | fgets output argument | test.cpp:78:10:78:15 | buffer indirection | The value of this argument may come from $@ and is being passed to system. | test.cpp:76:12:76:17 | fgets output argument | string read by fgets |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/SAMATE/UncontrolledFormatString.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/SAMATE/UncontrolledFormatString.expected
index ece5d00bdc9..f394382405d 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/SAMATE/UncontrolledFormatString.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/SAMATE/UncontrolledFormatString.expected
@@ -1,31 +1,16 @@
edges
-| char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data |
-| char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data |
-| char_connect_socket_w32_vsnprintf_01_bad.c:94:55:94:68 | ... + ... | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data |
-| char_connect_socket_w32_vsnprintf_01_bad.c:94:55:94:68 | ... + ... | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data |
-| char_console_fprintf_01_bad.c:30:23:30:35 | ... + ... | char_console_fprintf_01_bad.c:49:21:49:24 | data |
-| char_console_fprintf_01_bad.c:30:23:30:35 | ... + ... | char_console_fprintf_01_bad.c:49:21:49:24 | data |
-| char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | char_console_fprintf_01_bad.c:49:21:49:24 | data |
-| char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | char_console_fprintf_01_bad.c:49:21:49:24 | data |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | char_environment_fprintf_01_bad.c:36:21:36:24 | data |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | char_environment_fprintf_01_bad.c:36:21:36:24 | data |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | char_environment_fprintf_01_bad.c:36:21:36:24 | data |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | char_environment_fprintf_01_bad.c:36:21:36:24 | data |
-subpaths
+| char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data indirection |
+| char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | char_console_fprintf_01_bad.c:49:21:49:24 | data indirection |
+| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv indirection | char_environment_fprintf_01_bad.c:36:21:36:24 | data indirection |
nodes
| char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | semmle.label | recv output argument |
-| char_connect_socket_w32_vsnprintf_01_bad.c:94:55:94:68 | ... + ... | semmle.label | ... + ... |
-| char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data | semmle.label | data |
-| char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data | semmle.label | data |
-| char_console_fprintf_01_bad.c:30:23:30:35 | ... + ... | semmle.label | ... + ... |
+| char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data indirection | semmle.label | data indirection |
| char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | semmle.label | fgets output argument |
-| char_console_fprintf_01_bad.c:49:21:49:24 | data | semmle.label | data |
-| char_console_fprintf_01_bad.c:49:21:49:24 | data | semmle.label | data |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | semmle.label | call to getenv |
-| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | semmle.label | call to getenv |
-| char_environment_fprintf_01_bad.c:36:21:36:24 | data | semmle.label | data |
-| char_environment_fprintf_01_bad.c:36:21:36:24 | data | semmle.label | data |
+| char_console_fprintf_01_bad.c:49:21:49:24 | data indirection | semmle.label | data indirection |
+| char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv indirection | semmle.label | call to getenv indirection |
+| char_environment_fprintf_01_bad.c:36:21:36:24 | data indirection | semmle.label | data indirection |
+subpaths
#select
-| char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data | char_connect_socket_w32_vsnprintf_01_bad.c:94:55:94:68 | ... + ... | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data | The value of this argument may come from $@ and is being used as a formatting argument to badVaSink(data), which calls vsnprintf(format). | char_connect_socket_w32_vsnprintf_01_bad.c:94:55:94:68 | ... + ... | recv |
-| char_console_fprintf_01_bad.c:49:21:49:24 | data | char_console_fprintf_01_bad.c:30:23:30:35 | ... + ... | char_console_fprintf_01_bad.c:49:21:49:24 | data | The value of this argument may come from $@ and is being used as a formatting argument to fprintf(format). | char_console_fprintf_01_bad.c:30:23:30:35 | ... + ... | fgets |
-| char_environment_fprintf_01_bad.c:36:21:36:24 | data | char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | char_environment_fprintf_01_bad.c:36:21:36:24 | data | The value of this argument may come from $@ and is being used as a formatting argument to fprintf(format). | char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv | getenv |
+| char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data indirection | char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | char_connect_socket_w32_vsnprintf_01_bad.c:125:15:125:18 | data indirection | The value of this argument may come from $@ and is being used as a formatting argument to badVaSink(data), which calls vsnprintf(format). | char_connect_socket_w32_vsnprintf_01_bad.c:94:46:94:69 | recv output argument | buffer read by recv |
+| char_console_fprintf_01_bad.c:49:21:49:24 | data indirection | char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | char_console_fprintf_01_bad.c:49:21:49:24 | data indirection | The value of this argument may come from $@ and is being used as a formatting argument to fprintf(format). | char_console_fprintf_01_bad.c:30:23:30:35 | fgets output argument | string read by fgets |
+| char_environment_fprintf_01_bad.c:36:21:36:24 | data indirection | char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv indirection | char_environment_fprintf_01_bad.c:36:21:36:24 | data indirection | The value of this argument may come from $@ and is being used as a formatting argument to fprintf(format). | char_environment_fprintf_01_bad.c:27:30:27:35 | call to getenv indirection | an environment variable |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.c b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.c
index e60756e76bf..5649c0e19b1 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.c
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.c
@@ -164,7 +164,7 @@ int main(int argc, char **argv) {
printf(i91);
printWrapper(i91);
- // BAD: i10 value comes from argv
+ // BAD: i10 value comes from argv [NOT DETECTED]
int i10 = (int) argv[1];
printf((char *) i10);
printWrapper((char *) i10);
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.expected
index 2b27b7ff732..466d34aa1c2 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/argv/argvLocal.expected
@@ -1,211 +1,80 @@
edges
-| argvLocal.c:95:9:95:12 | argv | argvLocal.c:95:9:95:15 | access to array |
-| argvLocal.c:95:9:95:12 | argv | argvLocal.c:95:9:95:15 | access to array |
-| argvLocal.c:95:9:95:12 | argv | argvLocal.c:95:9:95:15 | access to array |
-| argvLocal.c:95:9:95:12 | argv | argvLocal.c:95:9:95:15 | access to array |
-| argvLocal.c:96:15:96:18 | argv | argvLocal.c:96:15:96:21 | access to array |
-| argvLocal.c:96:15:96:18 | argv | argvLocal.c:96:15:96:21 | access to array |
-| argvLocal.c:96:15:96:18 | argv | argvLocal.c:96:15:96:21 | access to array |
-| argvLocal.c:96:15:96:18 | argv | argvLocal.c:96:15:96:21 | access to array |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:101:9:101:10 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:101:9:101:10 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:101:9:101:10 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:101:9:101:10 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:102:15:102:16 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:102:15:102:16 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:102:15:102:16 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:102:15:102:16 | i1 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:144:9:144:10 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:144:9:144:10 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:144:9:144:10 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:144:9:144:10 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:145:15:145:16 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:145:15:145:16 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:145:15:145:16 | i7 |
-| argvLocal.c:100:7:100:10 | argv | argvLocal.c:145:15:145:16 | i7 |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:106:9:106:13 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:106:9:106:13 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:106:9:106:13 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:106:9:106:13 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:107:15:107:19 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:107:15:107:19 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:107:15:107:19 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:107:15:107:19 | access to array |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:110:9:110:11 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:110:9:110:11 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:110:9:110:11 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:110:9:110:11 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:111:15:111:17 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:111:15:111:17 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:111:15:111:17 | * ... |
-| argvLocal.c:105:14:105:17 | argv | argvLocal.c:111:15:111:17 | * ... |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:116:9:116:10 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:116:9:116:10 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:116:9:116:10 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:116:9:116:10 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:117:15:117:16 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:117:15:117:16 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:117:15:117:16 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:117:15:117:16 | i3 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:121:9:121:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:121:9:121:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:121:9:121:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:121:9:121:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:122:15:122:16 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:122:15:122:16 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:122:15:122:16 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:122:15:122:16 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:10 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:15:136:18 | -- ... |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:15:136:18 | -- ... |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:15:136:18 | -- ... |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:15:136:18 | -- ... |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:17:136:18 | i4 |
-| argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:17:136:18 | i4 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:127:9:127:10 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:127:9:127:10 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:127:9:127:10 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:127:9:127:10 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:128:15:128:16 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:128:15:128:16 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:128:15:128:16 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:128:15:128:16 | i5 |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:131:9:131:14 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:131:9:131:14 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:131:9:131:14 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:131:9:131:14 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:132:15:132:20 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:132:15:132:20 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:132:15:132:20 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:132:15:132:20 | ... + ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:139:9:139:26 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:139:9:139:26 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:139:9:139:26 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:139:9:139:26 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:140:15:140:32 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:140:15:140:32 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:140:15:140:32 | ... ? ... : ... |
-| argvLocal.c:126:10:126:13 | argv | argvLocal.c:140:15:140:32 | ... ? ... : ... |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:150:9:150:10 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:150:9:150:10 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:150:9:150:10 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:150:9:150:10 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:151:15:151:16 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:151:15:151:16 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:151:15:151:16 | i8 |
-| argvLocal.c:149:11:149:14 | argv | argvLocal.c:151:15:151:16 | i8 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:169:9:169:20 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:169:9:169:20 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:169:18:169:20 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:169:18:169:20 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:170:15:170:26 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:170:15:170:26 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:170:24:170:26 | i10 |
-| argvLocal.c:168:18:168:21 | argv | argvLocal.c:170:24:170:26 | i10 |
-subpaths
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:95:9:95:15 | access to array indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:96:15:96:21 | access to array indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:101:9:101:10 | i1 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:102:15:102:16 | i1 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:106:9:106:13 | access to array indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:107:15:107:19 | access to array indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:110:9:110:11 | * ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:111:15:111:17 | * ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:116:9:116:10 | i3 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:117:15:117:16 | i3 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:121:9:121:10 | i4 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:122:15:122:16 | i4 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:127:9:127:10 | i5 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:128:15:128:16 | i5 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:131:9:131:14 | ... + ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:132:15:132:20 | ... + ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:135:9:135:12 | ... ++ indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:135:9:135:12 | ... ++ indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:136:15:136:18 | -- ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:139:9:139:26 | ... ? ... : ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:140:15:140:32 | ... ? ... : ... indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:144:9:144:10 | i7 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:145:15:145:16 | i7 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:150:9:150:10 | i8 indirection |
+| argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:151:15:151:16 | i8 indirection |
nodes
-| argvLocal.c:95:9:95:12 | argv | semmle.label | argv |
-| argvLocal.c:95:9:95:12 | argv | semmle.label | argv |
-| argvLocal.c:95:9:95:15 | access to array | semmle.label | access to array |
-| argvLocal.c:95:9:95:15 | access to array | semmle.label | access to array |
-| argvLocal.c:96:15:96:18 | argv | semmle.label | argv |
-| argvLocal.c:96:15:96:18 | argv | semmle.label | argv |
-| argvLocal.c:96:15:96:21 | access to array | semmle.label | access to array |
-| argvLocal.c:96:15:96:21 | access to array | semmle.label | access to array |
-| argvLocal.c:100:7:100:10 | argv | semmle.label | argv |
-| argvLocal.c:100:7:100:10 | argv | semmle.label | argv |
-| argvLocal.c:101:9:101:10 | i1 | semmle.label | i1 |
-| argvLocal.c:101:9:101:10 | i1 | semmle.label | i1 |
-| argvLocal.c:102:15:102:16 | i1 | semmle.label | i1 |
-| argvLocal.c:102:15:102:16 | i1 | semmle.label | i1 |
-| argvLocal.c:105:14:105:17 | argv | semmle.label | argv |
-| argvLocal.c:105:14:105:17 | argv | semmle.label | argv |
-| argvLocal.c:106:9:106:13 | access to array | semmle.label | access to array |
-| argvLocal.c:106:9:106:13 | access to array | semmle.label | access to array |
-| argvLocal.c:107:15:107:19 | access to array | semmle.label | access to array |
-| argvLocal.c:107:15:107:19 | access to array | semmle.label | access to array |
-| argvLocal.c:110:9:110:11 | * ... | semmle.label | * ... |
-| argvLocal.c:110:9:110:11 | * ... | semmle.label | * ... |
-| argvLocal.c:111:15:111:17 | * ... | semmle.label | * ... |
-| argvLocal.c:111:15:111:17 | * ... | semmle.label | * ... |
-| argvLocal.c:115:13:115:16 | argv | semmle.label | argv |
-| argvLocal.c:115:13:115:16 | argv | semmle.label | argv |
-| argvLocal.c:116:9:116:10 | i3 | semmle.label | i3 |
-| argvLocal.c:116:9:116:10 | i3 | semmle.label | i3 |
-| argvLocal.c:117:15:117:16 | i3 | semmle.label | i3 |
-| argvLocal.c:117:15:117:16 | i3 | semmle.label | i3 |
-| argvLocal.c:121:9:121:10 | i4 | semmle.label | i4 |
-| argvLocal.c:121:9:121:10 | i4 | semmle.label | i4 |
-| argvLocal.c:122:15:122:16 | i4 | semmle.label | i4 |
-| argvLocal.c:122:15:122:16 | i4 | semmle.label | i4 |
-| argvLocal.c:126:10:126:13 | argv | semmle.label | argv |
-| argvLocal.c:126:10:126:13 | argv | semmle.label | argv |
-| argvLocal.c:127:9:127:10 | i5 | semmle.label | i5 |
-| argvLocal.c:127:9:127:10 | i5 | semmle.label | i5 |
-| argvLocal.c:128:15:128:16 | i5 | semmle.label | i5 |
-| argvLocal.c:128:15:128:16 | i5 | semmle.label | i5 |
-| argvLocal.c:131:9:131:14 | ... + ... | semmle.label | ... + ... |
-| argvLocal.c:131:9:131:14 | ... + ... | semmle.label | ... + ... |
-| argvLocal.c:132:15:132:20 | ... + ... | semmle.label | ... + ... |
-| argvLocal.c:132:15:132:20 | ... + ... | semmle.label | ... + ... |
-| argvLocal.c:135:9:135:10 | i4 | semmle.label | i4 |
-| argvLocal.c:135:9:135:12 | ... ++ | semmle.label | ... ++ |
-| argvLocal.c:135:9:135:12 | ... ++ | semmle.label | ... ++ |
-| argvLocal.c:135:9:135:12 | ... ++ | semmle.label | ... ++ |
-| argvLocal.c:136:15:136:18 | -- ... | semmle.label | -- ... |
-| argvLocal.c:136:15:136:18 | -- ... | semmle.label | -- ... |
-| argvLocal.c:136:17:136:18 | i4 | semmle.label | i4 |
-| argvLocal.c:139:9:139:26 | ... ? ... : ... | semmle.label | ... ? ... : ... |
-| argvLocal.c:139:9:139:26 | ... ? ... : ... | semmle.label | ... ? ... : ... |
-| argvLocal.c:140:15:140:32 | ... ? ... : ... | semmle.label | ... ? ... : ... |
-| argvLocal.c:140:15:140:32 | ... ? ... : ... | semmle.label | ... ? ... : ... |
-| argvLocal.c:144:9:144:10 | i7 | semmle.label | i7 |
-| argvLocal.c:144:9:144:10 | i7 | semmle.label | i7 |
-| argvLocal.c:145:15:145:16 | i7 | semmle.label | i7 |
-| argvLocal.c:145:15:145:16 | i7 | semmle.label | i7 |
-| argvLocal.c:149:11:149:14 | argv | semmle.label | argv |
-| argvLocal.c:149:11:149:14 | argv | semmle.label | argv |
-| argvLocal.c:150:9:150:10 | i8 | semmle.label | i8 |
-| argvLocal.c:150:9:150:10 | i8 | semmle.label | i8 |
-| argvLocal.c:151:15:151:16 | i8 | semmle.label | i8 |
-| argvLocal.c:151:15:151:16 | i8 | semmle.label | i8 |
-| argvLocal.c:168:18:168:21 | argv | semmle.label | argv |
-| argvLocal.c:168:18:168:21 | argv | semmle.label | argv |
-| argvLocal.c:169:9:169:20 | i10 | semmle.label | i10 |
-| argvLocal.c:169:18:169:20 | i10 | semmle.label | i10 |
-| argvLocal.c:170:15:170:26 | i10 | semmle.label | i10 |
-| argvLocal.c:170:24:170:26 | i10 | semmle.label | i10 |
+| argvLocal.c:13:27:13:30 | argv indirection | semmle.label | argv indirection |
+| argvLocal.c:95:9:95:15 | access to array indirection | semmle.label | access to array indirection |
+| argvLocal.c:96:15:96:21 | access to array indirection | semmle.label | access to array indirection |
+| argvLocal.c:101:9:101:10 | i1 indirection | semmle.label | i1 indirection |
+| argvLocal.c:102:15:102:16 | i1 indirection | semmle.label | i1 indirection |
+| argvLocal.c:106:9:106:13 | access to array indirection | semmle.label | access to array indirection |
+| argvLocal.c:107:15:107:19 | access to array indirection | semmle.label | access to array indirection |
+| argvLocal.c:110:9:110:11 | * ... indirection | semmle.label | * ... indirection |
+| argvLocal.c:111:15:111:17 | * ... indirection | semmle.label | * ... indirection |
+| argvLocal.c:116:9:116:10 | i3 indirection | semmle.label | i3 indirection |
+| argvLocal.c:117:15:117:16 | i3 indirection | semmle.label | i3 indirection |
+| argvLocal.c:121:9:121:10 | i4 indirection | semmle.label | i4 indirection |
+| argvLocal.c:122:15:122:16 | i4 indirection | semmle.label | i4 indirection |
+| argvLocal.c:127:9:127:10 | i5 indirection | semmle.label | i5 indirection |
+| argvLocal.c:128:15:128:16 | i5 indirection | semmle.label | i5 indirection |
+| argvLocal.c:131:9:131:14 | ... + ... indirection | semmle.label | ... + ... indirection |
+| argvLocal.c:132:15:132:20 | ... + ... indirection | semmle.label | ... + ... indirection |
+| argvLocal.c:135:9:135:12 | ... ++ indirection | semmle.label | ... ++ indirection |
+| argvLocal.c:135:9:135:12 | ... ++ indirection | semmle.label | ... ++ indirection |
+| argvLocal.c:136:15:136:18 | -- ... indirection | semmle.label | -- ... indirection |
+| argvLocal.c:139:9:139:26 | ... ? ... : ... indirection | semmle.label | ... ? ... : ... indirection |
+| argvLocal.c:140:15:140:32 | ... ? ... : ... indirection | semmle.label | ... ? ... : ... indirection |
+| argvLocal.c:144:9:144:10 | i7 indirection | semmle.label | i7 indirection |
+| argvLocal.c:145:15:145:16 | i7 indirection | semmle.label | i7 indirection |
+| argvLocal.c:150:9:150:10 | i8 indirection | semmle.label | i8 indirection |
+| argvLocal.c:151:15:151:16 | i8 indirection | semmle.label | i8 indirection |
+subpaths
#select
-| argvLocal.c:95:9:95:15 | access to array | argvLocal.c:95:9:95:12 | argv | argvLocal.c:95:9:95:15 | access to array | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:95:9:95:12 | argv | argv |
-| argvLocal.c:96:15:96:21 | access to array | argvLocal.c:96:15:96:18 | argv | argvLocal.c:96:15:96:21 | access to array | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:96:15:96:18 | argv | argv |
-| argvLocal.c:101:9:101:10 | i1 | argvLocal.c:100:7:100:10 | argv | argvLocal.c:101:9:101:10 | i1 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:100:7:100:10 | argv | argv |
-| argvLocal.c:102:15:102:16 | i1 | argvLocal.c:100:7:100:10 | argv | argvLocal.c:102:15:102:16 | i1 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:100:7:100:10 | argv | argv |
-| argvLocal.c:106:9:106:13 | access to array | argvLocal.c:105:14:105:17 | argv | argvLocal.c:106:9:106:13 | access to array | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:105:14:105:17 | argv | argv |
-| argvLocal.c:107:15:107:19 | access to array | argvLocal.c:105:14:105:17 | argv | argvLocal.c:107:15:107:19 | access to array | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:105:14:105:17 | argv | argv |
-| argvLocal.c:110:9:110:11 | * ... | argvLocal.c:105:14:105:17 | argv | argvLocal.c:110:9:110:11 | * ... | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:105:14:105:17 | argv | argv |
-| argvLocal.c:111:15:111:17 | * ... | argvLocal.c:105:14:105:17 | argv | argvLocal.c:111:15:111:17 | * ... | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:105:14:105:17 | argv | argv |
-| argvLocal.c:116:9:116:10 | i3 | argvLocal.c:115:13:115:16 | argv | argvLocal.c:116:9:116:10 | i3 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:117:15:117:16 | i3 | argvLocal.c:115:13:115:16 | argv | argvLocal.c:117:15:117:16 | i3 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:121:9:121:10 | i4 | argvLocal.c:115:13:115:16 | argv | argvLocal.c:121:9:121:10 | i4 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:122:15:122:16 | i4 | argvLocal.c:115:13:115:16 | argv | argvLocal.c:122:15:122:16 | i4 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:127:9:127:10 | i5 | argvLocal.c:126:10:126:13 | argv | argvLocal.c:127:9:127:10 | i5 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:128:15:128:16 | i5 | argvLocal.c:126:10:126:13 | argv | argvLocal.c:128:15:128:16 | i5 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:131:9:131:14 | ... + ... | argvLocal.c:126:10:126:13 | argv | argvLocal.c:131:9:131:14 | ... + ... | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:132:15:132:20 | ... + ... | argvLocal.c:126:10:126:13 | argv | argvLocal.c:132:15:132:20 | ... + ... | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:135:9:135:12 | ... ++ | argvLocal.c:115:13:115:16 | argv | argvLocal.c:135:9:135:12 | ... ++ | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:136:15:136:18 | -- ... | argvLocal.c:115:13:115:16 | argv | argvLocal.c:136:15:136:18 | -- ... | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:115:13:115:16 | argv | argv |
-| argvLocal.c:139:9:139:26 | ... ? ... : ... | argvLocal.c:126:10:126:13 | argv | argvLocal.c:139:9:139:26 | ... ? ... : ... | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:140:15:140:32 | ... ? ... : ... | argvLocal.c:126:10:126:13 | argv | argvLocal.c:140:15:140:32 | ... ? ... : ... | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:126:10:126:13 | argv | argv |
-| argvLocal.c:144:9:144:10 | i7 | argvLocal.c:100:7:100:10 | argv | argvLocal.c:144:9:144:10 | i7 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:100:7:100:10 | argv | argv |
-| argvLocal.c:145:15:145:16 | i7 | argvLocal.c:100:7:100:10 | argv | argvLocal.c:145:15:145:16 | i7 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:100:7:100:10 | argv | argv |
-| argvLocal.c:150:9:150:10 | i8 | argvLocal.c:149:11:149:14 | argv | argvLocal.c:150:9:150:10 | i8 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:149:11:149:14 | argv | argv |
-| argvLocal.c:151:15:151:16 | i8 | argvLocal.c:149:11:149:14 | argv | argvLocal.c:151:15:151:16 | i8 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:149:11:149:14 | argv | argv |
-| argvLocal.c:169:18:169:20 | i10 | argvLocal.c:168:18:168:21 | argv | argvLocal.c:169:18:169:20 | i10 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:168:18:168:21 | argv | argv |
-| argvLocal.c:170:24:170:26 | i10 | argvLocal.c:168:18:168:21 | argv | argvLocal.c:170:24:170:26 | i10 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:168:18:168:21 | argv | argv |
+| argvLocal.c:95:9:95:15 | access to array indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:95:9:95:15 | access to array indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:96:15:96:21 | access to array indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:96:15:96:21 | access to array indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:101:9:101:10 | i1 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:101:9:101:10 | i1 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:102:15:102:16 | i1 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:102:15:102:16 | i1 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:106:9:106:13 | access to array indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:106:9:106:13 | access to array indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:107:15:107:19 | access to array indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:107:15:107:19 | access to array indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:110:9:110:11 | * ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:110:9:110:11 | * ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:111:15:111:17 | * ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:111:15:111:17 | * ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:116:9:116:10 | i3 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:116:9:116:10 | i3 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:117:15:117:16 | i3 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:117:15:117:16 | i3 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:121:9:121:10 | i4 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:121:9:121:10 | i4 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:122:15:122:16 | i4 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:122:15:122:16 | i4 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:127:9:127:10 | i5 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:127:9:127:10 | i5 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:128:15:128:16 | i5 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:128:15:128:16 | i5 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:131:9:131:14 | ... + ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:131:9:131:14 | ... + ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:132:15:132:20 | ... + ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:132:15:132:20 | ... + ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:135:9:135:12 | ... ++ indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:135:9:135:12 | ... ++ indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:135:9:135:12 | ... ++ indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:135:9:135:12 | ... ++ indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:136:15:136:18 | -- ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:136:15:136:18 | -- ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:139:9:139:26 | ... ? ... : ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:139:9:139:26 | ... ? ... : ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:140:15:140:32 | ... ? ... : ... indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:140:15:140:32 | ... ? ... : ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:144:9:144:10 | i7 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:144:9:144:10 | i7 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:145:15:145:16 | i7 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:145:15:145:16 | i7 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:150:9:150:10 | i8 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:150:9:150:10 | i8 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
+| argvLocal.c:151:15:151:16 | i8 indirection | argvLocal.c:13:27:13:30 | argv indirection | argvLocal.c:151:15:151:16 | i8 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(correct), which calls printf(format). | argvLocal.c:13:27:13:30 | argv indirection | a command-line argument |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/funcs/funcsLocal.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/funcs/funcsLocal.expected
index 46da3c5f62d..061abbe9ab5 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/funcs/funcsLocal.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/funcs/funcsLocal.expected
@@ -1,88 +1,35 @@
edges
-| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:17:9:17:10 | i1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:58:9:58:10 | e1 |
-| funcsLocal.c:26:8:26:9 | fgets output argument | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:26:8:26:9 | fgets output argument | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:26:8:26:9 | i3 | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:26:8:26:9 | i3 | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:26:8:26:9 | i3 | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:26:8:26:9 | i3 | funcsLocal.c:27:9:27:10 | i3 |
-| funcsLocal.c:31:13:31:17 | call to fgets | funcsLocal.c:32:9:32:10 | i4 |
-| funcsLocal.c:31:13:31:17 | call to fgets | funcsLocal.c:32:9:32:10 | i4 |
-| funcsLocal.c:31:13:31:17 | call to fgets | funcsLocal.c:32:9:32:10 | i4 |
-| funcsLocal.c:31:13:31:17 | call to fgets | funcsLocal.c:32:9:32:10 | i4 |
-| funcsLocal.c:36:7:36:8 | gets output argument | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:36:7:36:8 | gets output argument | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:36:7:36:8 | i5 | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:36:7:36:8 | i5 | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:36:7:36:8 | i5 | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:36:7:36:8 | i5 | funcsLocal.c:37:9:37:10 | i5 |
-| funcsLocal.c:41:13:41:16 | call to gets | funcsLocal.c:42:9:42:10 | i6 |
-| funcsLocal.c:41:13:41:16 | call to gets | funcsLocal.c:42:9:42:10 | i6 |
-| funcsLocal.c:41:13:41:16 | call to gets | funcsLocal.c:42:9:42:10 | i6 |
-| funcsLocal.c:41:13:41:16 | call to gets | funcsLocal.c:42:9:42:10 | i6 |
-| funcsLocal.c:46:7:46:9 | * ... | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:46:7:46:9 | * ... | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:46:7:46:9 | * ... | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:46:7:46:9 | * ... | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:46:7:46:9 | gets output argument | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:46:7:46:9 | gets output argument | funcsLocal.c:47:9:47:11 | * ... |
-| funcsLocal.c:52:8:52:11 | call to gets | funcsLocal.c:53:9:53:11 | * ... |
-| funcsLocal.c:52:8:52:11 | call to gets | funcsLocal.c:53:9:53:11 | * ... |
-| funcsLocal.c:52:8:52:11 | call to gets | funcsLocal.c:53:9:53:11 | * ... |
-| funcsLocal.c:52:8:52:11 | call to gets | funcsLocal.c:53:9:53:11 | * ... |
-subpaths
+| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:17:9:17:10 | i1 indirection |
+| funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:58:9:58:10 | e1 indirection |
+| funcsLocal.c:26:8:26:9 | fgets output argument | funcsLocal.c:27:9:27:10 | i3 indirection |
+| funcsLocal.c:31:13:31:17 | call to fgets indirection | funcsLocal.c:32:9:32:10 | i4 indirection |
+| funcsLocal.c:36:7:36:8 | gets output argument | funcsLocal.c:37:9:37:10 | i5 indirection |
+| funcsLocal.c:41:13:41:16 | call to gets indirection | funcsLocal.c:42:9:42:10 | i6 indirection |
+| funcsLocal.c:46:7:46:9 | gets output argument | funcsLocal.c:47:9:47:11 | * ... indirection |
+| funcsLocal.c:52:8:52:11 | call to gets indirection | funcsLocal.c:53:9:53:11 | * ... indirection |
nodes
| funcsLocal.c:16:8:16:9 | fread output argument | semmle.label | fread output argument |
-| funcsLocal.c:16:8:16:9 | i1 | semmle.label | i1 |
-| funcsLocal.c:16:8:16:9 | i1 | semmle.label | i1 |
-| funcsLocal.c:17:9:17:10 | i1 | semmle.label | i1 |
-| funcsLocal.c:17:9:17:10 | i1 | semmle.label | i1 |
+| funcsLocal.c:17:9:17:10 | i1 indirection | semmle.label | i1 indirection |
| funcsLocal.c:26:8:26:9 | fgets output argument | semmle.label | fgets output argument |
-| funcsLocal.c:26:8:26:9 | i3 | semmle.label | i3 |
-| funcsLocal.c:26:8:26:9 | i3 | semmle.label | i3 |
-| funcsLocal.c:27:9:27:10 | i3 | semmle.label | i3 |
-| funcsLocal.c:27:9:27:10 | i3 | semmle.label | i3 |
-| funcsLocal.c:31:13:31:17 | call to fgets | semmle.label | call to fgets |
-| funcsLocal.c:31:13:31:17 | call to fgets | semmle.label | call to fgets |
-| funcsLocal.c:32:9:32:10 | i4 | semmle.label | i4 |
-| funcsLocal.c:32:9:32:10 | i4 | semmle.label | i4 |
+| funcsLocal.c:27:9:27:10 | i3 indirection | semmle.label | i3 indirection |
+| funcsLocal.c:31:13:31:17 | call to fgets indirection | semmle.label | call to fgets indirection |
+| funcsLocal.c:32:9:32:10 | i4 indirection | semmle.label | i4 indirection |
| funcsLocal.c:36:7:36:8 | gets output argument | semmle.label | gets output argument |
-| funcsLocal.c:36:7:36:8 | i5 | semmle.label | i5 |
-| funcsLocal.c:36:7:36:8 | i5 | semmle.label | i5 |
-| funcsLocal.c:37:9:37:10 | i5 | semmle.label | i5 |
-| funcsLocal.c:37:9:37:10 | i5 | semmle.label | i5 |
-| funcsLocal.c:41:13:41:16 | call to gets | semmle.label | call to gets |
-| funcsLocal.c:41:13:41:16 | call to gets | semmle.label | call to gets |
-| funcsLocal.c:42:9:42:10 | i6 | semmle.label | i6 |
-| funcsLocal.c:42:9:42:10 | i6 | semmle.label | i6 |
-| funcsLocal.c:46:7:46:9 | * ... | semmle.label | * ... |
-| funcsLocal.c:46:7:46:9 | * ... | semmle.label | * ... |
+| funcsLocal.c:37:9:37:10 | i5 indirection | semmle.label | i5 indirection |
+| funcsLocal.c:41:13:41:16 | call to gets indirection | semmle.label | call to gets indirection |
+| funcsLocal.c:42:9:42:10 | i6 indirection | semmle.label | i6 indirection |
| funcsLocal.c:46:7:46:9 | gets output argument | semmle.label | gets output argument |
-| funcsLocal.c:47:9:47:11 | * ... | semmle.label | * ... |
-| funcsLocal.c:47:9:47:11 | * ... | semmle.label | * ... |
-| funcsLocal.c:52:8:52:11 | call to gets | semmle.label | call to gets |
-| funcsLocal.c:52:8:52:11 | call to gets | semmle.label | call to gets |
-| funcsLocal.c:53:9:53:11 | * ... | semmle.label | * ... |
-| funcsLocal.c:53:9:53:11 | * ... | semmle.label | * ... |
-| funcsLocal.c:58:9:58:10 | e1 | semmle.label | e1 |
-| funcsLocal.c:58:9:58:10 | e1 | semmle.label | e1 |
+| funcsLocal.c:47:9:47:11 | * ... indirection | semmle.label | * ... indirection |
+| funcsLocal.c:52:8:52:11 | call to gets indirection | semmle.label | call to gets indirection |
+| funcsLocal.c:53:9:53:11 | * ... indirection | semmle.label | * ... indirection |
+| funcsLocal.c:58:9:58:10 | e1 indirection | semmle.label | e1 indirection |
+subpaths
#select
-| funcsLocal.c:17:9:17:10 | i1 | funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:17:9:17:10 | i1 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:16:8:16:9 | i1 | fread |
-| funcsLocal.c:27:9:27:10 | i3 | funcsLocal.c:26:8:26:9 | i3 | funcsLocal.c:27:9:27:10 | i3 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:26:8:26:9 | i3 | fgets |
-| funcsLocal.c:32:9:32:10 | i4 | funcsLocal.c:31:13:31:17 | call to fgets | funcsLocal.c:32:9:32:10 | i4 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:31:13:31:17 | call to fgets | fgets |
-| funcsLocal.c:37:9:37:10 | i5 | funcsLocal.c:36:7:36:8 | i5 | funcsLocal.c:37:9:37:10 | i5 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:36:7:36:8 | i5 | gets |
-| funcsLocal.c:42:9:42:10 | i6 | funcsLocal.c:41:13:41:16 | call to gets | funcsLocal.c:42:9:42:10 | i6 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:41:13:41:16 | call to gets | gets |
-| funcsLocal.c:47:9:47:11 | * ... | funcsLocal.c:46:7:46:9 | * ... | funcsLocal.c:47:9:47:11 | * ... | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:46:7:46:9 | * ... | gets |
-| funcsLocal.c:53:9:53:11 | * ... | funcsLocal.c:52:8:52:11 | call to gets | funcsLocal.c:53:9:53:11 | * ... | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:52:8:52:11 | call to gets | gets |
-| funcsLocal.c:58:9:58:10 | e1 | funcsLocal.c:16:8:16:9 | i1 | funcsLocal.c:58:9:58:10 | e1 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:16:8:16:9 | i1 | fread |
+| funcsLocal.c:17:9:17:10 | i1 indirection | funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:17:9:17:10 | i1 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:16:8:16:9 | fread output argument | string read by fread |
+| funcsLocal.c:27:9:27:10 | i3 indirection | funcsLocal.c:26:8:26:9 | fgets output argument | funcsLocal.c:27:9:27:10 | i3 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:26:8:26:9 | fgets output argument | string read by fgets |
+| funcsLocal.c:32:9:32:10 | i4 indirection | funcsLocal.c:31:13:31:17 | call to fgets indirection | funcsLocal.c:32:9:32:10 | i4 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:31:13:31:17 | call to fgets indirection | string read by fgets |
+| funcsLocal.c:37:9:37:10 | i5 indirection | funcsLocal.c:36:7:36:8 | gets output argument | funcsLocal.c:37:9:37:10 | i5 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:36:7:36:8 | gets output argument | string read by gets |
+| funcsLocal.c:42:9:42:10 | i6 indirection | funcsLocal.c:41:13:41:16 | call to gets indirection | funcsLocal.c:42:9:42:10 | i6 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:41:13:41:16 | call to gets indirection | string read by gets |
+| funcsLocal.c:47:9:47:11 | * ... indirection | funcsLocal.c:46:7:46:9 | gets output argument | funcsLocal.c:47:9:47:11 | * ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:46:7:46:9 | gets output argument | string read by gets |
+| funcsLocal.c:53:9:53:11 | * ... indirection | funcsLocal.c:52:8:52:11 | call to gets indirection | funcsLocal.c:53:9:53:11 | * ... indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:52:8:52:11 | call to gets indirection | string read by gets |
+| funcsLocal.c:58:9:58:10 | e1 indirection | funcsLocal.c:16:8:16:9 | fread output argument | funcsLocal.c:58:9:58:10 | e1 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | funcsLocal.c:16:8:16:9 | fread output argument | string read by fread |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatString.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatString.expected
index 49a4696c31f..79d78dab924 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatString.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatString.expected
@@ -1,42 +1,32 @@
edges
-| globalVars.c:8:7:8:10 | copy | globalVars.c:27:9:27:12 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:27:9:27:12 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:35:11:35:14 | copy |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:38:9:38:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:38:9:38:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:11:22:11:25 | argv | globalVars.c:8:7:8:10 | copy |
-| globalVars.c:15:21:15:23 | val | globalVars.c:9:7:9:11 | copy2 |
-| globalVars.c:24:11:24:14 | argv | globalVars.c:11:22:11:25 | argv |
-| globalVars.c:24:11:24:14 | argv | globalVars.c:11:22:11:25 | argv |
-| globalVars.c:35:11:35:14 | copy | globalVars.c:15:21:15:23 | val |
-subpaths
+| globalVars.c:8:7:8:10 | copy indirection | globalVars.c:27:9:27:12 | copy indirection |
+| globalVars.c:8:7:8:10 | copy indirection | globalVars.c:30:15:30:18 | copy indirection |
+| globalVars.c:8:7:8:10 | copy indirection | globalVars.c:35:11:35:14 | copy indirection |
+| globalVars.c:9:7:9:11 | copy2 indirection | globalVars.c:38:9:38:13 | copy2 indirection |
+| globalVars.c:9:7:9:11 | copy2 indirection | globalVars.c:41:15:41:19 | copy2 indirection |
+| globalVars.c:9:7:9:11 | copy2 indirection | globalVars.c:50:9:50:13 | copy2 indirection |
+| globalVars.c:11:22:11:25 | argv indirection | globalVars.c:8:7:8:10 | copy indirection |
+| globalVars.c:15:21:15:23 | val indirection | globalVars.c:9:7:9:11 | copy2 indirection |
+| globalVars.c:23:27:23:30 | argv indirection | globalVars.c:24:11:24:14 | argv indirection |
+| globalVars.c:24:11:24:14 | argv indirection | globalVars.c:11:22:11:25 | argv indirection |
+| globalVars.c:35:11:35:14 | copy indirection | globalVars.c:15:21:15:23 | val indirection |
nodes
-| globalVars.c:8:7:8:10 | copy | semmle.label | copy |
-| globalVars.c:9:7:9:11 | copy2 | semmle.label | copy2 |
-| globalVars.c:11:22:11:25 | argv | semmle.label | argv |
-| globalVars.c:15:21:15:23 | val | semmle.label | val |
-| globalVars.c:24:11:24:14 | argv | semmle.label | argv |
-| globalVars.c:24:11:24:14 | argv | semmle.label | argv |
-| globalVars.c:27:9:27:12 | copy | semmle.label | copy |
-| globalVars.c:27:9:27:12 | copy | semmle.label | copy |
-| globalVars.c:30:15:30:18 | copy | semmle.label | copy |
-| globalVars.c:30:15:30:18 | copy | semmle.label | copy |
-| globalVars.c:35:11:35:14 | copy | semmle.label | copy |
-| globalVars.c:38:9:38:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:38:9:38:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:50:9:50:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:50:9:50:13 | copy2 | semmle.label | copy2 |
+| globalVars.c:8:7:8:10 | copy indirection | semmle.label | copy indirection |
+| globalVars.c:9:7:9:11 | copy2 indirection | semmle.label | copy2 indirection |
+| globalVars.c:11:22:11:25 | argv indirection | semmle.label | argv indirection |
+| globalVars.c:15:21:15:23 | val indirection | semmle.label | val indirection |
+| globalVars.c:23:27:23:30 | argv indirection | semmle.label | argv indirection |
+| globalVars.c:24:11:24:14 | argv indirection | semmle.label | argv indirection |
+| globalVars.c:27:9:27:12 | copy indirection | semmle.label | copy indirection |
+| globalVars.c:30:15:30:18 | copy indirection | semmle.label | copy indirection |
+| globalVars.c:35:11:35:14 | copy indirection | semmle.label | copy indirection |
+| globalVars.c:38:9:38:13 | copy2 indirection | semmle.label | copy2 indirection |
+| globalVars.c:41:15:41:19 | copy2 indirection | semmle.label | copy2 indirection |
+| globalVars.c:50:9:50:13 | copy2 indirection | semmle.label | copy2 indirection |
+subpaths
#select
-| globalVars.c:27:9:27:12 | copy | globalVars.c:24:11:24:14 | argv | globalVars.c:27:9:27:12 | copy | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:24:11:24:14 | argv | globalVars.c:30:15:30:18 | copy | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:38:9:38:13 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:38:9:38:13 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:41:15:41:19 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:50:9:50:13 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:50:9:50:13 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
+| globalVars.c:27:9:27:12 | copy indirection | globalVars.c:23:27:23:30 | argv indirection | globalVars.c:27:9:27:12 | copy indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:23:27:23:30 | argv indirection | a command-line argument |
+| globalVars.c:30:15:30:18 | copy indirection | globalVars.c:23:27:23:30 | argv indirection | globalVars.c:30:15:30:18 | copy indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:23:27:23:30 | argv indirection | a command-line argument |
+| globalVars.c:38:9:38:13 | copy2 indirection | globalVars.c:23:27:23:30 | argv indirection | globalVars.c:38:9:38:13 | copy2 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:23:27:23:30 | argv indirection | a command-line argument |
+| globalVars.c:41:15:41:19 | copy2 indirection | globalVars.c:23:27:23:30 | argv indirection | globalVars.c:41:15:41:19 | copy2 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:23:27:23:30 | argv indirection | a command-line argument |
+| globalVars.c:50:9:50:13 | copy2 indirection | globalVars.c:23:27:23:30 | argv indirection | globalVars.c:50:9:50:13 | copy2 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:23:27:23:30 | argv indirection | a command-line argument |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.expected
deleted file mode 100644
index 6aca673fb4b..00000000000
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.expected
+++ /dev/null
@@ -1,69 +0,0 @@
-edges
-| globalVars.c:8:7:8:10 | copy | globalVars.c:27:9:27:12 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:27:9:27:12 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:33:15:33:18 | copy |
-| globalVars.c:8:7:8:10 | copy | globalVars.c:35:11:35:14 | copy |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:38:9:38:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:38:9:38:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:44:15:44:19 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:9:7:9:11 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:11:22:11:25 | argv | globalVars.c:8:7:8:10 | copy |
-| globalVars.c:11:22:11:25 | argv | globalVars.c:12:2:12:15 | ... = ... |
-| globalVars.c:12:2:12:15 | ... = ... | globalVars.c:8:7:8:10 | copy |
-| globalVars.c:15:21:15:23 | val | globalVars.c:9:7:9:11 | copy2 |
-| globalVars.c:15:21:15:23 | val | globalVars.c:16:2:16:12 | ... = ... |
-| globalVars.c:16:2:16:12 | ... = ... | globalVars.c:9:7:9:11 | copy2 |
-| globalVars.c:24:11:24:14 | argv | globalVars.c:11:22:11:25 | argv |
-| globalVars.c:24:11:24:14 | argv | globalVars.c:11:22:11:25 | argv |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:30:15:30:18 | copy |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:35:11:35:14 | copy |
-| globalVars.c:33:15:33:18 | copy | globalVars.c:35:11:35:14 | copy |
-| globalVars.c:35:11:35:14 | copy | globalVars.c:15:21:15:23 | val |
-| globalVars.c:35:11:35:14 | copy | globalVars.c:35:11:35:14 | copy |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:41:15:41:19 | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:44:15:44:19 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-| globalVars.c:44:15:44:19 | copy2 | globalVars.c:50:9:50:13 | copy2 |
-subpaths
-nodes
-| globalVars.c:8:7:8:10 | copy | semmle.label | copy |
-| globalVars.c:9:7:9:11 | copy2 | semmle.label | copy2 |
-| globalVars.c:11:22:11:25 | argv | semmle.label | argv |
-| globalVars.c:12:2:12:15 | ... = ... | semmle.label | ... = ... |
-| globalVars.c:15:21:15:23 | val | semmle.label | val |
-| globalVars.c:16:2:16:12 | ... = ... | semmle.label | ... = ... |
-| globalVars.c:24:11:24:14 | argv | semmle.label | argv |
-| globalVars.c:24:11:24:14 | argv | semmle.label | argv |
-| globalVars.c:27:9:27:12 | copy | semmle.label | copy |
-| globalVars.c:27:9:27:12 | copy | semmle.label | copy |
-| globalVars.c:30:15:30:18 | copy | semmle.label | copy |
-| globalVars.c:30:15:30:18 | copy | semmle.label | copy |
-| globalVars.c:30:15:30:18 | copy | semmle.label | copy |
-| globalVars.c:33:15:33:18 | copy | semmle.label | copy |
-| globalVars.c:35:11:35:14 | copy | semmle.label | copy |
-| globalVars.c:38:9:38:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:38:9:38:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:41:15:41:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:44:15:44:19 | copy2 | semmle.label | copy2 |
-| globalVars.c:50:9:50:13 | copy2 | semmle.label | copy2 |
-| globalVars.c:50:9:50:13 | copy2 | semmle.label | copy2 |
-#select
-| globalVars.c:27:9:27:12 | copy | globalVars.c:24:11:24:14 | argv | globalVars.c:27:9:27:12 | copy | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:30:15:30:18 | copy | globalVars.c:24:11:24:14 | argv | globalVars.c:30:15:30:18 | copy | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:38:9:38:13 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:38:9:38:13 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:41:15:41:19 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:41:15:41:19 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printWrapper(str), which calls printf(format). | globalVars.c:24:11:24:14 | argv | argv |
-| globalVars.c:50:9:50:13 | copy2 | globalVars.c:24:11:24:14 | argv | globalVars.c:50:9:50:13 | copy2 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | globalVars.c:24:11:24:14 | argv | argv |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.qlref b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.qlref
deleted file mode 100644
index eac059de2bb..00000000000
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/globalVars/UncontrolledFormatStringThroughGlobalVar.qlref
+++ /dev/null
@@ -1 +0,0 @@
-Security/CWE/CWE-134/UncontrolledFormatStringThroughGlobalVar.ql
\ No newline at end of file
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/ifs/ifs.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/ifs/ifs.expected
index 8b512068877..a71038f5713 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/ifs/ifs.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-134/semmle/ifs/ifs.expected
@@ -1,103 +1,38 @@
edges
-| ifs.c:61:8:61:11 | argv | ifs.c:62:9:62:10 | c7 |
-| ifs.c:61:8:61:11 | argv | ifs.c:62:9:62:10 | c7 |
-| ifs.c:61:8:61:11 | argv | ifs.c:62:9:62:10 | c7 |
-| ifs.c:61:8:61:11 | argv | ifs.c:62:9:62:10 | c7 |
-| ifs.c:68:8:68:11 | argv | ifs.c:69:9:69:10 | c8 |
-| ifs.c:68:8:68:11 | argv | ifs.c:69:9:69:10 | c8 |
-| ifs.c:68:8:68:11 | argv | ifs.c:69:9:69:10 | c8 |
-| ifs.c:68:8:68:11 | argv | ifs.c:69:9:69:10 | c8 |
-| ifs.c:74:8:74:11 | argv | ifs.c:75:9:75:10 | i1 |
-| ifs.c:74:8:74:11 | argv | ifs.c:75:9:75:10 | i1 |
-| ifs.c:74:8:74:11 | argv | ifs.c:75:9:75:10 | i1 |
-| ifs.c:74:8:74:11 | argv | ifs.c:75:9:75:10 | i1 |
-| ifs.c:80:8:80:11 | argv | ifs.c:81:9:81:10 | i2 |
-| ifs.c:80:8:80:11 | argv | ifs.c:81:9:81:10 | i2 |
-| ifs.c:80:8:80:11 | argv | ifs.c:81:9:81:10 | i2 |
-| ifs.c:80:8:80:11 | argv | ifs.c:81:9:81:10 | i2 |
-| ifs.c:86:8:86:11 | argv | ifs.c:87:9:87:10 | i3 |
-| ifs.c:86:8:86:11 | argv | ifs.c:87:9:87:10 | i3 |
-| ifs.c:86:8:86:11 | argv | ifs.c:87:9:87:10 | i3 |
-| ifs.c:86:8:86:11 | argv | ifs.c:87:9:87:10 | i3 |
-| ifs.c:92:8:92:11 | argv | ifs.c:93:9:93:10 | i4 |
-| ifs.c:92:8:92:11 | argv | ifs.c:93:9:93:10 | i4 |
-| ifs.c:92:8:92:11 | argv | ifs.c:93:9:93:10 | i4 |
-| ifs.c:92:8:92:11 | argv | ifs.c:93:9:93:10 | i4 |
-| ifs.c:98:8:98:11 | argv | ifs.c:99:9:99:10 | i5 |
-| ifs.c:98:8:98:11 | argv | ifs.c:99:9:99:10 | i5 |
-| ifs.c:98:8:98:11 | argv | ifs.c:99:9:99:10 | i5 |
-| ifs.c:98:8:98:11 | argv | ifs.c:99:9:99:10 | i5 |
-| ifs.c:105:8:105:11 | argv | ifs.c:106:9:106:10 | i6 |
-| ifs.c:105:8:105:11 | argv | ifs.c:106:9:106:10 | i6 |
-| ifs.c:105:8:105:11 | argv | ifs.c:106:9:106:10 | i6 |
-| ifs.c:105:8:105:11 | argv | ifs.c:106:9:106:10 | i6 |
-| ifs.c:111:8:111:11 | argv | ifs.c:112:9:112:10 | i7 |
-| ifs.c:111:8:111:11 | argv | ifs.c:112:9:112:10 | i7 |
-| ifs.c:111:8:111:11 | argv | ifs.c:112:9:112:10 | i7 |
-| ifs.c:111:8:111:11 | argv | ifs.c:112:9:112:10 | i7 |
-| ifs.c:117:8:117:11 | argv | ifs.c:118:9:118:10 | i8 |
-| ifs.c:117:8:117:11 | argv | ifs.c:118:9:118:10 | i8 |
-| ifs.c:117:8:117:11 | argv | ifs.c:118:9:118:10 | i8 |
-| ifs.c:117:8:117:11 | argv | ifs.c:118:9:118:10 | i8 |
-| ifs.c:123:8:123:11 | argv | ifs.c:124:9:124:10 | i9 |
-| ifs.c:123:8:123:11 | argv | ifs.c:124:9:124:10 | i9 |
-| ifs.c:123:8:123:11 | argv | ifs.c:124:9:124:10 | i9 |
-| ifs.c:123:8:123:11 | argv | ifs.c:124:9:124:10 | i9 |
-subpaths
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:62:9:62:10 | c7 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:69:9:69:10 | c8 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:75:9:75:10 | i1 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:81:9:81:10 | i2 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:87:9:87:10 | i3 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:93:9:93:10 | i4 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:99:9:99:10 | i5 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:106:9:106:10 | i6 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:112:9:112:10 | i7 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:118:9:118:10 | i8 indirection |
+| ifs.c:16:27:16:30 | argv indirection | ifs.c:124:9:124:10 | i9 indirection |
nodes
-| ifs.c:61:8:61:11 | argv | semmle.label | argv |
-| ifs.c:61:8:61:11 | argv | semmle.label | argv |
-| ifs.c:62:9:62:10 | c7 | semmle.label | c7 |
-| ifs.c:62:9:62:10 | c7 | semmle.label | c7 |
-| ifs.c:68:8:68:11 | argv | semmle.label | argv |
-| ifs.c:68:8:68:11 | argv | semmle.label | argv |
-| ifs.c:69:9:69:10 | c8 | semmle.label | c8 |
-| ifs.c:69:9:69:10 | c8 | semmle.label | c8 |
-| ifs.c:74:8:74:11 | argv | semmle.label | argv |
-| ifs.c:74:8:74:11 | argv | semmle.label | argv |
-| ifs.c:75:9:75:10 | i1 | semmle.label | i1 |
-| ifs.c:75:9:75:10 | i1 | semmle.label | i1 |
-| ifs.c:80:8:80:11 | argv | semmle.label | argv |
-| ifs.c:80:8:80:11 | argv | semmle.label | argv |
-| ifs.c:81:9:81:10 | i2 | semmle.label | i2 |
-| ifs.c:81:9:81:10 | i2 | semmle.label | i2 |
-| ifs.c:86:8:86:11 | argv | semmle.label | argv |
-| ifs.c:86:8:86:11 | argv | semmle.label | argv |
-| ifs.c:87:9:87:10 | i3 | semmle.label | i3 |
-| ifs.c:87:9:87:10 | i3 | semmle.label | i3 |
-| ifs.c:92:8:92:11 | argv | semmle.label | argv |
-| ifs.c:92:8:92:11 | argv | semmle.label | argv |
-| ifs.c:93:9:93:10 | i4 | semmle.label | i4 |
-| ifs.c:93:9:93:10 | i4 | semmle.label | i4 |
-| ifs.c:98:8:98:11 | argv | semmle.label | argv |
-| ifs.c:98:8:98:11 | argv | semmle.label | argv |
-| ifs.c:99:9:99:10 | i5 | semmle.label | i5 |
-| ifs.c:99:9:99:10 | i5 | semmle.label | i5 |
-| ifs.c:105:8:105:11 | argv | semmle.label | argv |
-| ifs.c:105:8:105:11 | argv | semmle.label | argv |
-| ifs.c:106:9:106:10 | i6 | semmle.label | i6 |
-| ifs.c:106:9:106:10 | i6 | semmle.label | i6 |
-| ifs.c:111:8:111:11 | argv | semmle.label | argv |
-| ifs.c:111:8:111:11 | argv | semmle.label | argv |
-| ifs.c:112:9:112:10 | i7 | semmle.label | i7 |
-| ifs.c:112:9:112:10 | i7 | semmle.label | i7 |
-| ifs.c:117:8:117:11 | argv | semmle.label | argv |
-| ifs.c:117:8:117:11 | argv | semmle.label | argv |
-| ifs.c:118:9:118:10 | i8 | semmle.label | i8 |
-| ifs.c:118:9:118:10 | i8 | semmle.label | i8 |
-| ifs.c:123:8:123:11 | argv | semmle.label | argv |
-| ifs.c:123:8:123:11 | argv | semmle.label | argv |
-| ifs.c:124:9:124:10 | i9 | semmle.label | i9 |
-| ifs.c:124:9:124:10 | i9 | semmle.label | i9 |
+| ifs.c:16:27:16:30 | argv indirection | semmle.label | argv indirection |
+| ifs.c:62:9:62:10 | c7 indirection | semmle.label | c7 indirection |
+| ifs.c:69:9:69:10 | c8 indirection | semmle.label | c8 indirection |
+| ifs.c:75:9:75:10 | i1 indirection | semmle.label | i1 indirection |
+| ifs.c:81:9:81:10 | i2 indirection | semmle.label | i2 indirection |
+| ifs.c:87:9:87:10 | i3 indirection | semmle.label | i3 indirection |
+| ifs.c:93:9:93:10 | i4 indirection | semmle.label | i4 indirection |
+| ifs.c:99:9:99:10 | i5 indirection | semmle.label | i5 indirection |
+| ifs.c:106:9:106:10 | i6 indirection | semmle.label | i6 indirection |
+| ifs.c:112:9:112:10 | i7 indirection | semmle.label | i7 indirection |
+| ifs.c:118:9:118:10 | i8 indirection | semmle.label | i8 indirection |
+| ifs.c:124:9:124:10 | i9 indirection | semmle.label | i9 indirection |
+subpaths
#select
-| ifs.c:62:9:62:10 | c7 | ifs.c:61:8:61:11 | argv | ifs.c:62:9:62:10 | c7 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:61:8:61:11 | argv | argv |
-| ifs.c:69:9:69:10 | c8 | ifs.c:68:8:68:11 | argv | ifs.c:69:9:69:10 | c8 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:68:8:68:11 | argv | argv |
-| ifs.c:75:9:75:10 | i1 | ifs.c:74:8:74:11 | argv | ifs.c:75:9:75:10 | i1 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:74:8:74:11 | argv | argv |
-| ifs.c:81:9:81:10 | i2 | ifs.c:80:8:80:11 | argv | ifs.c:81:9:81:10 | i2 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:80:8:80:11 | argv | argv |
-| ifs.c:87:9:87:10 | i3 | ifs.c:86:8:86:11 | argv | ifs.c:87:9:87:10 | i3 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:86:8:86:11 | argv | argv |
-| ifs.c:93:9:93:10 | i4 | ifs.c:92:8:92:11 | argv | ifs.c:93:9:93:10 | i4 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:92:8:92:11 | argv | argv |
-| ifs.c:99:9:99:10 | i5 | ifs.c:98:8:98:11 | argv | ifs.c:99:9:99:10 | i5 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:98:8:98:11 | argv | argv |
-| ifs.c:106:9:106:10 | i6 | ifs.c:105:8:105:11 | argv | ifs.c:106:9:106:10 | i6 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:105:8:105:11 | argv | argv |
-| ifs.c:112:9:112:10 | i7 | ifs.c:111:8:111:11 | argv | ifs.c:112:9:112:10 | i7 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:111:8:111:11 | argv | argv |
-| ifs.c:118:9:118:10 | i8 | ifs.c:117:8:117:11 | argv | ifs.c:118:9:118:10 | i8 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:117:8:117:11 | argv | argv |
-| ifs.c:124:9:124:10 | i9 | ifs.c:123:8:123:11 | argv | ifs.c:124:9:124:10 | i9 | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:123:8:123:11 | argv | argv |
+| ifs.c:62:9:62:10 | c7 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:62:9:62:10 | c7 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:69:9:69:10 | c8 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:69:9:69:10 | c8 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:75:9:75:10 | i1 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:75:9:75:10 | i1 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:81:9:81:10 | i2 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:81:9:81:10 | i2 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:87:9:87:10 | i3 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:87:9:87:10 | i3 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:93:9:93:10 | i4 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:93:9:93:10 | i4 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:99:9:99:10 | i5 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:99:9:99:10 | i5 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:106:9:106:10 | i6 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:106:9:106:10 | i6 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:112:9:112:10 | i7 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:112:9:112:10 | i7 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:118:9:118:10 | i8 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:118:9:118:10 | i8 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
+| ifs.c:124:9:124:10 | i9 indirection | ifs.c:16:27:16:30 | argv indirection | ifs.c:124:9:124:10 | i9 indirection | The value of this argument may come from $@ and is being used as a formatting argument to printf(format). | ifs.c:16:27:16:30 | argv indirection | a command-line argument |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-190/SAMATE/IntegerOverflowTainted.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-190/SAMATE/IntegerOverflowTainted.expected
index 81a97849431..bd2085e9863 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-190/SAMATE/IntegerOverflowTainted.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-190/SAMATE/IntegerOverflowTainted.expected
@@ -1 +1 @@
-| examples.cpp:66:9:66:14 | -- ... | $@ flows an expression which might overflow negatively. | examples.cpp:63:26:63:30 | & ... | User-provided value |
+| examples.cpp:66:9:66:14 | -- ... | $@ flows an expression which might overflow negatively. | examples.cpp:63:26:63:30 | fscanf output argument | value read by fscanf |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/TaintedAllocationSize/TaintedAllocationSize.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/TaintedAllocationSize/TaintedAllocationSize.expected
index 555fa923549..c8863502326 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/TaintedAllocationSize/TaintedAllocationSize.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/TaintedAllocationSize/TaintedAllocationSize.expected
@@ -5,33 +5,22 @@ edges
| test.cpp:39:27:39:30 | argv indirection | test.cpp:49:32:49:35 | size |
| test.cpp:39:27:39:30 | argv indirection | test.cpp:50:17:50:30 | size |
| test.cpp:39:27:39:30 | argv indirection | test.cpp:53:35:53:60 | ... * ... |
-| test.cpp:124:18:124:31 | call to getenv | test.cpp:128:24:128:41 | ... * ... |
| test.cpp:124:18:124:31 | call to getenv indirection | test.cpp:128:24:128:41 | ... * ... |
-| test.cpp:133:19:133:32 | call to getenv | test.cpp:135:10:135:27 | ... * ... |
| test.cpp:133:19:133:32 | call to getenv indirection | test.cpp:135:10:135:27 | ... * ... |
-| test.cpp:148:20:148:33 | call to getenv | test.cpp:152:11:152:28 | ... * ... |
| test.cpp:148:20:148:33 | call to getenv indirection | test.cpp:152:11:152:28 | ... * ... |
| test.cpp:209:8:209:23 | get_tainted_size indirection | test.cpp:241:9:241:24 | call to get_tainted_size |
-| test.cpp:211:14:211:27 | call to getenv | test.cpp:209:8:209:23 | get_tainted_size indirection |
| test.cpp:211:14:211:27 | call to getenv indirection | test.cpp:209:8:209:23 | get_tainted_size indirection |
| test.cpp:230:21:230:21 | s | test.cpp:231:21:231:21 | s |
-| test.cpp:237:24:237:37 | call to getenv | test.cpp:239:9:239:18 | local_size |
-| test.cpp:237:24:237:37 | call to getenv | test.cpp:245:11:245:20 | local_size |
-| test.cpp:237:24:237:37 | call to getenv | test.cpp:247:10:247:19 | local_size |
| test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:239:9:239:18 | local_size |
| test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:245:11:245:20 | local_size |
| test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:247:10:247:19 | local_size |
| test.cpp:247:10:247:19 | local_size | test.cpp:230:21:230:21 | s |
| test.cpp:250:20:250:27 | out_size | test.cpp:289:17:289:20 | get_size output argument |
| test.cpp:250:20:250:27 | out_size | test.cpp:305:18:305:21 | get_size output argument |
-| test.cpp:251:18:251:31 | call to getenv | test.cpp:250:20:250:27 | out_size |
| test.cpp:251:18:251:31 | call to getenv indirection | test.cpp:250:20:250:27 | out_size |
-| test.cpp:259:20:259:33 | call to getenv | test.cpp:263:11:263:29 | ... * ... |
| test.cpp:259:20:259:33 | call to getenv indirection | test.cpp:263:11:263:29 | ... * ... |
| test.cpp:289:17:289:20 | get_size output argument | test.cpp:291:11:291:28 | ... * ... |
| test.cpp:305:18:305:21 | get_size output argument | test.cpp:308:10:308:27 | ... * ... |
-| test.cpp:353:18:353:31 | call to getenv | test.cpp:355:35:355:38 | size |
-| test.cpp:353:18:353:31 | call to getenv | test.cpp:356:35:356:38 | size |
| test.cpp:353:18:353:31 | call to getenv indirection | test.cpp:355:35:355:38 | size |
| test.cpp:353:18:353:31 | call to getenv indirection | test.cpp:356:35:356:38 | size |
nodes
@@ -42,37 +31,29 @@ nodes
| test.cpp:49:32:49:35 | size | semmle.label | size |
| test.cpp:50:17:50:30 | size | semmle.label | size |
| test.cpp:53:35:53:60 | ... * ... | semmle.label | ... * ... |
-| test.cpp:124:18:124:31 | call to getenv | semmle.label | call to getenv |
| test.cpp:124:18:124:31 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:128:24:128:41 | ... * ... | semmle.label | ... * ... |
-| test.cpp:133:19:133:32 | call to getenv | semmle.label | call to getenv |
| test.cpp:133:19:133:32 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:135:10:135:27 | ... * ... | semmle.label | ... * ... |
-| test.cpp:148:20:148:33 | call to getenv | semmle.label | call to getenv |
| test.cpp:148:20:148:33 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:152:11:152:28 | ... * ... | semmle.label | ... * ... |
| test.cpp:209:8:209:23 | get_tainted_size indirection | semmle.label | get_tainted_size indirection |
-| test.cpp:211:14:211:27 | call to getenv | semmle.label | call to getenv |
| test.cpp:211:14:211:27 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:230:21:230:21 | s | semmle.label | s |
| test.cpp:231:21:231:21 | s | semmle.label | s |
-| test.cpp:237:24:237:37 | call to getenv | semmle.label | call to getenv |
| test.cpp:237:24:237:37 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:239:9:239:18 | local_size | semmle.label | local_size |
| test.cpp:241:9:241:24 | call to get_tainted_size | semmle.label | call to get_tainted_size |
| test.cpp:245:11:245:20 | local_size | semmle.label | local_size |
| test.cpp:247:10:247:19 | local_size | semmle.label | local_size |
| test.cpp:250:20:250:27 | out_size | semmle.label | out_size |
-| test.cpp:251:18:251:31 | call to getenv | semmle.label | call to getenv |
| test.cpp:251:18:251:31 | call to getenv indirection | semmle.label | call to getenv indirection |
-| test.cpp:259:20:259:33 | call to getenv | semmle.label | call to getenv |
| test.cpp:259:20:259:33 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:263:11:263:29 | ... * ... | semmle.label | ... * ... |
| test.cpp:289:17:289:20 | get_size output argument | semmle.label | get_size output argument |
| test.cpp:291:11:291:28 | ... * ... | semmle.label | ... * ... |
| test.cpp:305:18:305:21 | get_size output argument | semmle.label | get_size output argument |
| test.cpp:308:10:308:27 | ... * ... | semmle.label | ... * ... |
-| test.cpp:353:18:353:31 | call to getenv | semmle.label | call to getenv |
| test.cpp:353:18:353:31 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:355:35:355:38 | size | semmle.label | size |
| test.cpp:356:35:356:38 | size | semmle.label | size |
@@ -84,27 +65,15 @@ subpaths
| test.cpp:49:25:49:30 | call to malloc | test.cpp:39:27:39:30 | argv indirection | test.cpp:49:32:49:35 | size | This allocation size is derived from $@ and might overflow. | test.cpp:39:27:39:30 | argv indirection | user input (a command-line argument) |
| test.cpp:50:17:50:30 | new[] | test.cpp:39:27:39:30 | argv indirection | test.cpp:50:17:50:30 | size | This allocation size is derived from $@ and might overflow. | test.cpp:39:27:39:30 | argv indirection | user input (a command-line argument) |
| test.cpp:53:21:53:27 | call to realloc | test.cpp:39:27:39:30 | argv indirection | test.cpp:53:35:53:60 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:39:27:39:30 | argv indirection | user input (a command-line argument) |
-| test.cpp:128:17:128:22 | call to malloc | test.cpp:124:18:124:31 | call to getenv | test.cpp:128:24:128:41 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:124:18:124:31 | call to getenv | user input (an environment variable) |
| test.cpp:128:17:128:22 | call to malloc | test.cpp:124:18:124:31 | call to getenv indirection | test.cpp:128:24:128:41 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:124:18:124:31 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:135:3:135:8 | call to malloc | test.cpp:133:19:133:32 | call to getenv | test.cpp:135:10:135:27 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:133:19:133:32 | call to getenv | user input (an environment variable) |
| test.cpp:135:3:135:8 | call to malloc | test.cpp:133:19:133:32 | call to getenv indirection | test.cpp:135:10:135:27 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:133:19:133:32 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:152:4:152:9 | call to malloc | test.cpp:148:20:148:33 | call to getenv | test.cpp:152:11:152:28 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:148:20:148:33 | call to getenv | user input (an environment variable) |
| test.cpp:152:4:152:9 | call to malloc | test.cpp:148:20:148:33 | call to getenv indirection | test.cpp:152:11:152:28 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:148:20:148:33 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:231:14:231:19 | call to malloc | test.cpp:237:24:237:37 | call to getenv | test.cpp:231:21:231:21 | s | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv | user input (an environment variable) |
| test.cpp:231:14:231:19 | call to malloc | test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:231:21:231:21 | s | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:239:2:239:7 | call to malloc | test.cpp:237:24:237:37 | call to getenv | test.cpp:239:9:239:18 | local_size | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv | user input (an environment variable) |
| test.cpp:239:2:239:7 | call to malloc | test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:239:9:239:18 | local_size | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:241:2:241:7 | call to malloc | test.cpp:211:14:211:27 | call to getenv | test.cpp:241:9:241:24 | call to get_tainted_size | This allocation size is derived from $@ and might overflow. | test.cpp:211:14:211:27 | call to getenv | user input (an environment variable) |
| test.cpp:241:2:241:7 | call to malloc | test.cpp:211:14:211:27 | call to getenv indirection | test.cpp:241:9:241:24 | call to get_tainted_size | This allocation size is derived from $@ and might overflow. | test.cpp:211:14:211:27 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:245:2:245:9 | call to my_alloc | test.cpp:237:24:237:37 | call to getenv | test.cpp:245:11:245:20 | local_size | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv | user input (an environment variable) |
| test.cpp:245:2:245:9 | call to my_alloc | test.cpp:237:24:237:37 | call to getenv indirection | test.cpp:245:11:245:20 | local_size | This allocation size is derived from $@ and might overflow. | test.cpp:237:24:237:37 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:263:4:263:9 | call to malloc | test.cpp:259:20:259:33 | call to getenv | test.cpp:263:11:263:29 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:259:20:259:33 | call to getenv | user input (an environment variable) |
| test.cpp:263:4:263:9 | call to malloc | test.cpp:259:20:259:33 | call to getenv indirection | test.cpp:263:11:263:29 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:259:20:259:33 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:291:4:291:9 | call to malloc | test.cpp:251:18:251:31 | call to getenv | test.cpp:291:11:291:28 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:251:18:251:31 | call to getenv | user input (an environment variable) |
| test.cpp:291:4:291:9 | call to malloc | test.cpp:251:18:251:31 | call to getenv indirection | test.cpp:291:11:291:28 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:251:18:251:31 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:308:3:308:8 | call to malloc | test.cpp:251:18:251:31 | call to getenv | test.cpp:308:10:308:27 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:251:18:251:31 | call to getenv | user input (an environment variable) |
| test.cpp:308:3:308:8 | call to malloc | test.cpp:251:18:251:31 | call to getenv indirection | test.cpp:308:10:308:27 | ... * ... | This allocation size is derived from $@ and might overflow. | test.cpp:251:18:251:31 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:355:25:355:33 | call to MyMalloc1 | test.cpp:353:18:353:31 | call to getenv | test.cpp:355:35:355:38 | size | This allocation size is derived from $@ and might overflow. | test.cpp:353:18:353:31 | call to getenv | user input (an environment variable) |
| test.cpp:355:25:355:33 | call to MyMalloc1 | test.cpp:353:18:353:31 | call to getenv indirection | test.cpp:355:35:355:38 | size | This allocation size is derived from $@ and might overflow. | test.cpp:353:18:353:31 | call to getenv indirection | user input (an environment variable) |
-| test.cpp:356:25:356:33 | call to MyMalloc2 | test.cpp:353:18:353:31 | call to getenv | test.cpp:356:35:356:38 | size | This allocation size is derived from $@ and might overflow. | test.cpp:353:18:353:31 | call to getenv | user input (an environment variable) |
| test.cpp:356:25:356:33 | call to MyMalloc2 | test.cpp:353:18:353:31 | call to getenv indirection | test.cpp:356:35:356:38 | size | This allocation size is derived from $@ and might overflow. | test.cpp:353:18:353:31 | call to getenv indirection | user input (an environment variable) |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/tainted/IntegerOverflowTainted.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/tainted/IntegerOverflowTainted.expected
index 4b6f14663c0..2f01718f0f4 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/tainted/IntegerOverflowTainted.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-190/semmle/tainted/IntegerOverflowTainted.expected
@@ -1,18 +1,23 @@
-| test2.cpp:14:11:14:15 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | & ... | User-provided value |
-| test2.cpp:15:11:15:19 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | & ... | User-provided value |
-| test2.cpp:16:11:16:21 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | & ... | User-provided value |
-| test2.cpp:17:11:17:22 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | & ... | User-provided value |
-| test2.cpp:39:9:39:18 | ... + ... | $@ flows an expression which might overflow. | test2.cpp:36:9:36:14 | buffer | User-provided value |
-| test2.cpp:40:3:40:13 | ... += ... | $@ flows an expression which might overflow. | test2.cpp:36:9:36:14 | buffer | User-provided value |
-| test3.c:12:31:12:34 | * ... | $@ flows an expression which might overflow negatively. | test3.c:11:15:11:18 | argv | User-provided value |
-| test3.c:13:16:13:19 | * ... | $@ flows an expression which might overflow negatively. | test3.c:11:15:11:18 | argv | User-provided value |
-| test4.cpp:13:17:13:20 | access to array | $@ flows an expression which might overflow negatively. | test4.cpp:9:13:9:16 | argv | User-provided value |
-| test5.cpp:10:9:10:15 | call to strtoul | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | buf | User-provided value |
-| test5.cpp:17:6:17:27 | ... * ... | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | buf | User-provided value |
-| test5.cpp:19:6:19:13 | ... * ... | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | buf | User-provided value |
-| test6.cpp:11:15:11:15 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | & ... | User-provided value |
-| test6.cpp:16:15:16:15 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | & ... | User-provided value |
-| test6.cpp:30:16:30:16 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | & ... | User-provided value |
-| test.c:14:15:14:35 | ... * ... | $@ flows an expression which might overflow. | test.c:11:29:11:32 | argv | User-provided value |
-| test.c:44:7:44:12 | ... -- | $@ flows an expression which might overflow negatively. | test.c:41:17:41:20 | argv | User-provided value |
-| test.c:54:7:54:12 | ... -- | $@ flows an expression which might overflow negatively. | test.c:51:17:51:20 | argv | User-provided value |
+| test2.cpp:14:11:14:15 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | fscanf output argument | value read by fscanf |
+| test2.cpp:15:11:15:19 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | fscanf output argument | value read by fscanf |
+| test2.cpp:16:11:16:21 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | fscanf output argument | value read by fscanf |
+| test2.cpp:17:11:17:22 | ... * ... | $@ flows an expression which might overflow. | test2.cpp:25:22:25:23 | fscanf output argument | value read by fscanf |
+| test2.cpp:39:9:39:18 | ... + ... | $@ flows an expression which might overflow. | test2.cpp:36:9:36:14 | fgets output argument | string read by fgets |
+| test2.cpp:40:3:40:13 | ... += ... | $@ flows an expression which might overflow. | test2.cpp:36:9:36:14 | fgets output argument | string read by fgets |
+| test3.c:12:11:12:34 | * ... | $@ flows an expression which might overflow negatively. | test3.c:10:27:10:30 | argv indirection | a command-line argument |
+| test3.c:12:11:12:34 | * ... | $@ flows an expression which might overflow negatively. | test.c:10:27:10:30 | argv indirection | a command-line argument |
+| test3.c:13:11:13:20 | * ... | $@ flows an expression which might overflow negatively. | test3.c:10:27:10:30 | argv indirection | a command-line argument |
+| test3.c:13:11:13:20 | * ... | $@ flows an expression which might overflow negatively. | test.c:10:27:10:30 | argv indirection | a command-line argument |
+| test4.cpp:13:7:13:20 | access to array | $@ flows an expression which might overflow negatively. | test4.cpp:8:27:8:30 | argv indirection | a command-line argument |
+| test5.cpp:10:9:10:27 | call to strtoul | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | gets output argument | string read by gets |
+| test5.cpp:17:6:17:27 | ... * ... | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | gets output argument | string read by gets |
+| test5.cpp:19:6:19:13 | ... * ... | $@ flows an expression which might overflow. | test5.cpp:9:7:9:9 | gets output argument | string read by gets |
+| test6.cpp:11:10:11:15 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | fscanf output argument | value read by fscanf |
+| test6.cpp:16:10:16:15 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | fscanf output argument | value read by fscanf |
+| test6.cpp:30:11:30:16 | s | $@ flows an expression which might overflow. | test6.cpp:39:23:39:24 | fscanf output argument | value read by fscanf |
+| test.c:14:15:14:35 | ... * ... | $@ flows an expression which might overflow. | test3.c:10:27:10:30 | argv indirection | a command-line argument |
+| test.c:14:15:14:35 | ... * ... | $@ flows an expression which might overflow. | test.c:10:27:10:30 | argv indirection | a command-line argument |
+| test.c:44:7:44:12 | ... -- | $@ flows an expression which might overflow negatively. | test3.c:10:27:10:30 | argv indirection | a command-line argument |
+| test.c:44:7:44:12 | ... -- | $@ flows an expression which might overflow negatively. | test.c:10:27:10:30 | argv indirection | a command-line argument |
+| test.c:54:7:54:12 | ... -- | $@ flows an expression which might overflow negatively. | test3.c:10:27:10:30 | argv indirection | a command-line argument |
+| test.c:54:7:54:12 | ... -- | $@ flows an expression which might overflow negatively. | test.c:10:27:10:30 | argv indirection | a command-line argument |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-197/SAMATE/IntegerOverflowTainted/IntegerOverflowTainted.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-197/SAMATE/IntegerOverflowTainted/IntegerOverflowTainted.expected
index 9965c10070d..cb31529859e 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-197/SAMATE/IntegerOverflowTainted/IntegerOverflowTainted.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-197/SAMATE/IntegerOverflowTainted/IntegerOverflowTainted.expected
@@ -1 +1 @@
-| tests.cpp:38:31:38:34 | data | $@ flows an expression which might overflow. | tests.cpp:57:27:57:31 | & ... | User-provided value |
+| tests.cpp:38:25:38:34 | data | $@ flows an expression which might overflow. | tests.cpp:57:27:57:31 | fscanf output argument | value read by fscanf |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-290/semmle/AuthenticationBypass/AuthenticationBypass.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-290/semmle/AuthenticationBypass/AuthenticationBypass.expected
index 11db5c7acaa..afc2b610254 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-290/semmle/AuthenticationBypass/AuthenticationBypass.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-290/semmle/AuthenticationBypass/AuthenticationBypass.expected
@@ -1,54 +1,26 @@
edges
-| test.cpp:16:25:16:30 | call to getenv | test.cpp:20:14:20:20 | address |
-| test.cpp:16:25:16:30 | call to getenv | test.cpp:20:14:20:20 | address |
-| test.cpp:16:25:16:42 | call to getenv | test.cpp:20:14:20:20 | address |
-| test.cpp:16:25:16:42 | call to getenv | test.cpp:20:14:20:20 | address |
-| test.cpp:27:25:27:30 | call to getenv | test.cpp:31:14:31:20 | address |
-| test.cpp:27:25:27:30 | call to getenv | test.cpp:31:14:31:20 | address |
-| test.cpp:27:25:27:42 | call to getenv | test.cpp:31:14:31:20 | address |
-| test.cpp:27:25:27:42 | call to getenv | test.cpp:31:14:31:20 | address |
-| test.cpp:38:25:38:30 | call to getenv | test.cpp:42:14:42:20 | address |
-| test.cpp:38:25:38:30 | call to getenv | test.cpp:42:14:42:20 | address |
-| test.cpp:38:25:38:42 | call to getenv | test.cpp:42:14:42:20 | address |
-| test.cpp:38:25:38:42 | call to getenv | test.cpp:42:14:42:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:52:14:52:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:52:14:52:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:56:14:56:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:56:14:56:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:60:14:60:20 | address |
-| test.cpp:49:25:49:30 | call to getenv | test.cpp:60:14:60:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:52:14:52:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:52:14:52:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:56:14:56:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:56:14:56:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:60:14:60:20 | address |
-| test.cpp:49:25:49:42 | call to getenv | test.cpp:60:14:60:20 | address |
-subpaths
+| test.cpp:16:25:16:42 | call to getenv indirection | test.cpp:20:14:20:20 | address indirection |
+| test.cpp:27:25:27:42 | call to getenv indirection | test.cpp:31:14:31:20 | address indirection |
+| test.cpp:38:25:38:42 | call to getenv indirection | test.cpp:42:14:42:20 | address indirection |
+| test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:52:14:52:20 | address indirection |
+| test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:56:14:56:20 | address indirection |
+| test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:60:14:60:20 | address indirection |
nodes
-| test.cpp:16:25:16:30 | call to getenv | semmle.label | call to getenv |
-| test.cpp:16:25:16:42 | call to getenv | semmle.label | call to getenv |
-| test.cpp:20:14:20:20 | address | semmle.label | address |
-| test.cpp:20:14:20:20 | address | semmle.label | address |
-| test.cpp:27:25:27:30 | call to getenv | semmle.label | call to getenv |
-| test.cpp:27:25:27:42 | call to getenv | semmle.label | call to getenv |
-| test.cpp:31:14:31:20 | address | semmle.label | address |
-| test.cpp:31:14:31:20 | address | semmle.label | address |
-| test.cpp:38:25:38:30 | call to getenv | semmle.label | call to getenv |
-| test.cpp:38:25:38:42 | call to getenv | semmle.label | call to getenv |
-| test.cpp:42:14:42:20 | address | semmle.label | address |
-| test.cpp:42:14:42:20 | address | semmle.label | address |
-| test.cpp:49:25:49:30 | call to getenv | semmle.label | call to getenv |
-| test.cpp:49:25:49:42 | call to getenv | semmle.label | call to getenv |
-| test.cpp:52:14:52:20 | address | semmle.label | address |
-| test.cpp:52:14:52:20 | address | semmle.label | address |
-| test.cpp:56:14:56:20 | address | semmle.label | address |
-| test.cpp:56:14:56:20 | address | semmle.label | address |
-| test.cpp:60:14:60:20 | address | semmle.label | address |
-| test.cpp:60:14:60:20 | address | semmle.label | address |
+| test.cpp:16:25:16:42 | call to getenv indirection | semmle.label | call to getenv indirection |
+| test.cpp:20:14:20:20 | address indirection | semmle.label | address indirection |
+| test.cpp:27:25:27:42 | call to getenv indirection | semmle.label | call to getenv indirection |
+| test.cpp:31:14:31:20 | address indirection | semmle.label | address indirection |
+| test.cpp:38:25:38:42 | call to getenv indirection | semmle.label | call to getenv indirection |
+| test.cpp:42:14:42:20 | address indirection | semmle.label | address indirection |
+| test.cpp:49:25:49:42 | call to getenv indirection | semmle.label | call to getenv indirection |
+| test.cpp:52:14:52:20 | address indirection | semmle.label | address indirection |
+| test.cpp:56:14:56:20 | address indirection | semmle.label | address indirection |
+| test.cpp:60:14:60:20 | address indirection | semmle.label | address indirection |
+subpaths
#select
-| test.cpp:20:7:20:12 | call to strcmp | test.cpp:16:25:16:30 | call to getenv | test.cpp:20:14:20:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:16:25:16:30 | call to getenv | call to getenv |
-| test.cpp:31:7:31:12 | call to strcmp | test.cpp:27:25:27:30 | call to getenv | test.cpp:31:14:31:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:27:25:27:30 | call to getenv | call to getenv |
-| test.cpp:42:7:42:12 | call to strcmp | test.cpp:38:25:38:30 | call to getenv | test.cpp:42:14:42:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:38:25:38:30 | call to getenv | call to getenv |
-| test.cpp:52:7:52:12 | call to strcmp | test.cpp:49:25:49:30 | call to getenv | test.cpp:52:14:52:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:30 | call to getenv | call to getenv |
-| test.cpp:56:7:56:12 | call to strcmp | test.cpp:49:25:49:30 | call to getenv | test.cpp:56:14:56:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:30 | call to getenv | call to getenv |
-| test.cpp:60:7:60:12 | call to strcmp | test.cpp:49:25:49:30 | call to getenv | test.cpp:60:14:60:20 | address | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:30 | call to getenv | call to getenv |
+| test.cpp:20:7:20:12 | call to strcmp | test.cpp:16:25:16:42 | call to getenv indirection | test.cpp:20:14:20:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:16:25:16:42 | call to getenv indirection | an environment variable |
+| test.cpp:31:7:31:12 | call to strcmp | test.cpp:27:25:27:42 | call to getenv indirection | test.cpp:31:14:31:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:27:25:27:42 | call to getenv indirection | an environment variable |
+| test.cpp:42:7:42:12 | call to strcmp | test.cpp:38:25:38:42 | call to getenv indirection | test.cpp:42:14:42:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:38:25:38:42 | call to getenv indirection | an environment variable |
+| test.cpp:52:7:52:12 | call to strcmp | test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:52:14:52:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:42 | call to getenv indirection | an environment variable |
+| test.cpp:56:7:56:12 | call to strcmp | test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:56:14:56:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:42 | call to getenv indirection | an environment variable |
+| test.cpp:60:7:60:12 | call to strcmp | test.cpp:49:25:49:42 | call to getenv indirection | test.cpp:60:14:60:20 | address indirection | Untrusted input $@ might be vulnerable to a spoofing attack. | test.cpp:49:25:49:42 | call to getenv indirection | an environment variable |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/UseAfterFree.expected
similarity index 100%
rename from cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree.expected
rename to cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/UseAfterFree.expected
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree.qlref b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/UseAfterFree.qlref
similarity index 100%
rename from cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree.qlref
rename to cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/UseAfterFree.qlref
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/test.cpp b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/test.cpp
similarity index 100%
rename from cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/test.cpp
rename to cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseAfterFree/test.cpp
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.expected
new file mode 100644
index 00000000000..7e33c948d2e
--- /dev/null
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.expected
@@ -0,0 +1,12 @@
+| test.cpp:165:34:165:38 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:166:39:166:43 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:167:44:167:48 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:169:29:169:33 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:178:37:178:41 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:181:39:181:43 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:183:37:183:41 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
+| test.cpp:187:34:187:37 | call to data | The underlying string object is destroyed after the call to 'data' returns. |
+| test.cpp:188:39:188:42 | call to data | The underlying string object is destroyed after the call to 'data' returns. |
+| test.cpp:189:44:189:47 | call to data | The underlying string object is destroyed after the call to 'data' returns. |
+| test.cpp:191:29:191:32 | call to data | The underlying string object is destroyed after the call to 'data' returns. |
+| test.cpp:193:31:193:35 | call to c_str | The underlying string object is destroyed after the call to 'c_str' returns. |
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.qlref b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.qlref
new file mode 100644
index 00000000000..a69a1a7f4e5
--- /dev/null
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/UseOfStringAfterLifetimeEnds.qlref
@@ -0,0 +1,2 @@
+
+Security/CWE/CWE-416/UseOfStringAfterLifetimeEnds.ql
\ No newline at end of file
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/test.cpp b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/test.cpp
new file mode 100644
index 00000000000..51f85c91860
--- /dev/null
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-416/semmle/tests/UseOfStringAfterLifetimeEnds/test.cpp
@@ -0,0 +1,219 @@
+typedef unsigned long size_t;
+
+namespace std {
+ template struct remove_reference { typedef T type; };
+
+ template struct remove_reference { typedef T type; };
+
+ template struct remove_reference { typedef T type; };
+
+ template using remove_reference_t = typename remove_reference::type;
+
+ template< class T > std::remove_reference_t&& move( T&& t );
+}
+
+// --- iterator ---
+
+namespace std {
+ template struct remove_const { typedef T type; };
+
+ template struct remove_const { typedef T type; };
+
+ // `remove_const_t` removes any `const` specifier from `T`
+ template using remove_const_t = typename remove_const::type;
+
+ struct ptrdiff_t;
+
+ template struct iterator_traits;
+
+ template
+ struct iterator {
+ typedef Category iterator_category;
+
+ iterator();
+ iterator(iterator > const &other); // non-const -> const conversion constructor
+
+ iterator &operator++();
+ iterator operator++(int);
+ iterator &operator--();
+ iterator operator--(int);
+ bool operator==(iterator other) const;
+ bool operator!=(iterator other) const;
+ reference_type operator*() const;
+ pointer_type operator->() const;
+ iterator operator+(int);
+ iterator operator-(int);
+ iterator &operator+=(int);
+ iterator &operator-=(int);
+ int operator-(iterator);
+ reference_type operator[](int);
+ };
+
+ struct input_iterator_tag {};
+ struct forward_iterator_tag : public input_iterator_tag {};
+ struct bidirectional_iterator_tag : public forward_iterator_tag {};
+ struct random_access_iterator_tag : public bidirectional_iterator_tag {};
+}
+
+// --- string ---
+
+namespace std
+{
+ template struct char_traits;
+
+ typedef size_t streamsize;
+
+ template class allocator {
+ public:
+ allocator() throw();
+ typedef size_t size_type;
+ };
+
+ template, class Allocator = allocator >
+ class basic_string {
+ public:
+ using value_type = charT;
+ using reference = value_type&;
+ using const_reference = const value_type&;
+ typedef typename Allocator::size_type size_type;
+ static const size_type npos = -1;
+
+ explicit basic_string(const Allocator& a = Allocator());
+ basic_string(const charT* s, const Allocator& a = Allocator());
+ template basic_string(InputIterator begin, InputIterator end, const Allocator& a = Allocator());
+
+ const charT* c_str() const;
+ charT* data() noexcept;
+ size_t length() const;
+
+ typedef std::iterator iterator;
+ typedef std::iterator const_iterator;
+
+ iterator begin();
+ iterator end();
+ const_iterator begin() const;
+ const_iterator end() const;
+ const_iterator cbegin() const;
+ const_iterator cend() const;
+
+ const_reference operator[](size_type pos) const;
+ reference operator[](size_type pos);
+ const_reference at(size_type n) const;
+ reference at(size_type n);
+ basic_string& insert(size_type pos, const basic_string& str);
+ basic_string& insert(size_type pos, size_type n, charT c);
+ basic_string& insert(size_type pos, const charT* s);
+ iterator insert(const_iterator p, size_type n, charT c);
+ template iterator insert(const_iterator p, InputIterator first, InputIterator last);
+ basic_string& replace(size_type pos1, size_type n1, const basic_string& str);
+ basic_string& replace(size_type pos1, size_type n1, size_type n2, charT c);
+ };
+
+ template basic_string operator+(const basic_string& lhs, const basic_string& rhs);
+ template basic_string operator+(const basic_string& lhs, const charT* rhs);
+
+ typedef basic_string string;
+}
+
+// --- vector ---
+
+namespace std {
+ template>
+ class vector {
+ public:
+ using value_type = T;
+ using reference = value_type&;
+ using const_reference = const value_type&;
+ using size_type = unsigned int;
+ using iterator = std::iterator;
+ using const_iterator = std::iterator;
+
+ vector() noexcept(noexcept(Allocator()));
+ explicit vector(const Allocator&) noexcept;
+ explicit vector(size_type n, const Allocator& = Allocator());
+ vector(size_type n, const T& value, const Allocator& = Allocator());
+ template vector(InputIterator first, InputIterator last, const Allocator& = Allocator());
+ ~vector();
+
+ void push_back(const T& x);
+ void push_back(T&& x);
+
+ iterator insert(const_iterator position, const T& x);
+ iterator insert(const_iterator position, T&& x);
+ iterator insert(const_iterator position, size_type n, const T& x);
+ template iterator insert(const_iterator position, InputIterator first, InputIterator last);
+
+ template iterator emplace (const_iterator position, Args&&... args);
+ template void emplace_back (Args&&... args);
+ };
+}
+
+struct S {
+ const char* s;
+};
+
+void call_by_value(S);
+void call_by_cref(const S&);
+
+void call(const char*);
+
+const char* test1(bool b1, bool b2) {
+ auto s1 = std::string("hello").c_str(); // BAD
+ auto s2 = b1 ? std::string("hello").c_str() : ""; // BAD
+ auto s3 = b2 ? "" : std::string("hello").c_str(); // BAD
+ const char* s4;
+ s4 = std::string("hello").c_str(); // BAD
+
+ call(std::string("hello").c_str()); // GOOD
+ call(b1 ? std::string("hello").c_str() : ""); // GOOD
+ call(b1 ? (b2 ? "" : std::string("hello").c_str()) : ""); // GOOD
+ call_by_value({ std::string("hello").c_str() }); // GOOD
+ call_by_cref({ std::string("hello").c_str() }); // GOOD
+
+ std::vector v1;
+ v1.push_back(std::string("hello").c_str()); // BAD
+
+ std::vector v2;
+ v2.push_back({ std::string("hello").c_str() }); // BAD
+
+ S s5[] = { { std::string("hello").c_str() } }; // BAD
+
+ char c = std::string("hello").c_str()[0]; // GOOD
+
+ auto s6 = std::string("hello").data(); // BAD
+ auto s7 = b1 ? std::string("hello").data() : ""; // BAD
+ auto s8 = b2 ? "" : std::string("hello").data(); // BAD
+ char* s9;
+ s9 = std::string("hello").data(); // BAD
+
+ return std::string("hello").c_str(); // BAD
+}
+
+void test2(bool b1, bool b2) {
+ std::string s("hello");
+ auto s1 = s.c_str(); // GOOD
+ auto s2 = b1 ? s.c_str() : ""; // GOOD
+ auto s3 = b2 ? "" : s.c_str(); // GOOD
+ const char* s4;
+ s4 = s.c_str(); // GOOD
+
+ std::string& sRef = s;
+
+ auto s5 = sRef.c_str(); // GOOD
+ auto s6 = b1 ? sRef.c_str() : ""; // GOOD
+ auto s7 = b2 ? "" : sRef.c_str(); // GOOD
+ const char* s8;
+ s8 = sRef.c_str(); // GOOD
+
+ std::string&& sRefRef = std::string("hello");
+
+ auto s9 = sRefRef.c_str(); // GOOD
+ auto s10 = b1 ? sRefRef.c_str() : ""; // GOOD
+ auto s11 = b2 ? "" : sRefRef.c_str(); // GOOD
+ const char* s12;
+ s12 = sRefRef.c_str(); // GOOD
+}
\ No newline at end of file
diff --git a/cpp/ql/test/query-tests/Security/CWE/CWE-807/semmle/TaintedCondition/TaintedCondition.expected b/cpp/ql/test/query-tests/Security/CWE/CWE-807/semmle/TaintedCondition/TaintedCondition.expected
index c2bd2653994..626e8490708 100644
--- a/cpp/ql/test/query-tests/Security/CWE/CWE-807/semmle/TaintedCondition/TaintedCondition.expected
+++ b/cpp/ql/test/query-tests/Security/CWE/CWE-807/semmle/TaintedCondition/TaintedCondition.expected
@@ -1,13 +1,8 @@
edges
-| test.cpp:20:29:20:34 | call to getenv | test.cpp:24:10:24:35 | ! ... |
-| test.cpp:20:29:20:34 | call to getenv | test.cpp:24:11:24:16 | call to strcmp |
-| test.cpp:20:29:20:47 | call to getenv | test.cpp:24:10:24:35 | ! ... |
-| test.cpp:20:29:20:47 | call to getenv | test.cpp:24:11:24:16 | call to strcmp |
-subpaths
+| test.cpp:20:29:20:47 | call to getenv indirection | test.cpp:24:10:24:35 | ! ... |
nodes
-| test.cpp:20:29:20:34 | call to getenv | semmle.label | call to getenv |
-| test.cpp:20:29:20:47 | call to getenv | semmle.label | call to getenv |
+| test.cpp:20:29:20:47 | call to getenv indirection | semmle.label | call to getenv indirection |
| test.cpp:24:10:24:35 | ! ... | semmle.label | ! ... |
-| test.cpp:24:11:24:16 | call to strcmp | semmle.label | call to strcmp |
+subpaths
#select
-| test.cpp:24:10:24:35 | ! ... | test.cpp:20:29:20:34 | call to getenv | test.cpp:24:10:24:35 | ! ... | Reliance on untrusted input $@ to raise privilege at $@. | test.cpp:20:29:20:34 | call to getenv | call to getenv | test.cpp:25:9:25:27 | ... = ... | ... = ... |
+| test.cpp:24:10:24:35 | ! ... | test.cpp:20:29:20:47 | call to getenv indirection | test.cpp:24:10:24:35 | ! ... | Reliance on $@ to raise privilege at $@. | test.cpp:20:29:20:47 | call to getenv indirection | an environment variable | test.cpp:25:9:25:27 | ... = ... | ... = ... |
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCache.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCache.cs
index 7adceebc7eb..3a124d13e0e 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCache.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCache.cs
@@ -1,5 +1,4 @@
-using System;
-using System.Collections.Generic;
+using System.Collections.Generic;
using System.IO;
using System.Linq;
@@ -20,7 +19,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
/// assembly cache.
///
/// Callback for progress.
- public AssemblyCache(IEnumerable paths, ProgressMonitor progressMonitor)
+ public AssemblyCache(IEnumerable paths, IEnumerable frameworkPaths, ProgressMonitor progressMonitor)
{
foreach (var path in paths)
{
@@ -40,7 +39,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
progressMonitor.LogInfo("AssemblyCache: Path not found: " + path);
}
}
- IndexReferences();
+ IndexReferences(frameworkPaths);
}
///
@@ -57,13 +56,11 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
}
- private static readonly Version emptyVersion = new Version(0, 0, 0, 0);
-
///
/// Indexes all DLLs we have located.
/// Because this is a potentially time-consuming operation, it is put into a separate stage.
///
- private void IndexReferences()
+ private void IndexReferences(IEnumerable frameworkPaths)
{
// Read all of the files
foreach (var filename in pendingDllsToIndex)
@@ -71,13 +68,9 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
IndexReference(filename);
}
- // Index "assemblyInfo" by version string
- // The OrderBy is used to ensure that we by default select the highest version number.
foreach (var info in assemblyInfoByFileName.Values
.OrderBy(info => info.Name)
- .ThenBy(info => info.NetCoreVersion ?? emptyVersion)
- .ThenBy(info => info.Version ?? emptyVersion)
- .ThenBy(info => info.Filename))
+ .OrderAssemblyInfosByPreference(frameworkPaths))
{
foreach (var index in info.IndexStrings)
{
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCacheExtensions.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCacheExtensions.cs
new file mode 100644
index 00000000000..a4e7723266b
--- /dev/null
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/AssemblyCacheExtensions.cs
@@ -0,0 +1,29 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+
+namespace Semmle.Extraction.CSharp.DependencyFetching
+{
+ internal static class AssemblyCacheExtensions
+ {
+ private static readonly Version emptyVersion = new Version(0, 0, 0, 0);
+
+ ///
+ /// This method orders AssemblyInfos by version numbers (.net core version first, then assembly version). Finally, it orders by filename to make the order deterministic.
+ ///
+ public static IOrderedEnumerable OrderAssemblyInfosByPreference(this IEnumerable assemblies, IEnumerable frameworkPaths)
+ {
+ // prefer framework assemblies over others
+ int initialOrdering(AssemblyInfo info) => frameworkPaths.Any(framework => info.Filename.StartsWith(framework, StringComparison.OrdinalIgnoreCase)) ? 1 : 0;
+
+ var ordered = assemblies is IOrderedEnumerable o
+ ? o.ThenBy(initialOrdering)
+ : assemblies.OrderBy(initialOrdering);
+
+ return ordered
+ .ThenBy(info => info.NetCoreVersion ?? emptyVersion)
+ .ThenBy(info => info.Version ?? emptyVersion)
+ .ThenBy(info => info.Filename);
+ }
+ }
+}
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/Assets.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/Assets.cs
index 7558fd7970f..38db871d1b6 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/Assets.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/Assets.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
using System.IO;
using System.Linq;
using Newtonsoft.Json.Linq;
@@ -14,14 +15,6 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
{
private readonly ProgressMonitor progressMonitor;
- private static readonly string[] netFrameworks = new[] {
- "microsoft.aspnetcore.app.ref",
- "microsoft.netcore.app.ref",
- "microsoft.netframework.referenceassemblies",
- "microsoft.windowsdesktop.app.ref",
- "netstandard.library.ref"
- };
-
internal Assets(ProgressMonitor progressMonitor)
{
this.progressMonitor = progressMonitor;
@@ -68,19 +61,19 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
/// }
/// }
///
- /// Returns dependencies
- /// RequiredPaths = {
+ /// Adds the following dependencies
+ /// Paths: {
/// "castle.core/4.4.1/lib/netstandard1.5/Castle.Core.dll",
/// "json.net/1.0.33/lib/netstandard2.0/Json.Net.dll"
/// }
- /// UsedPackages = {
+ /// Packages: {
/// "castle.core",
/// "json.net"
/// }
///
- private DependencyContainer AddPackageDependencies(JObject json, DependencyContainer dependencies)
+ private void AddPackageDependencies(JObject json, DependencyContainer dependencies)
{
- // If there are more than one framework we need to pick just one.
+ // If there is more than one framework we need to pick just one.
// To ensure stability we pick one based on the lexicographic order of
// the framework names.
var references = json
@@ -93,7 +86,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
if (references is null)
{
progressMonitor.LogDebug("No references found in the targets section in the assets file.");
- return dependencies;
+ return;
}
// Find all the compile dependencies for each reference and
@@ -108,19 +101,83 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
return;
}
- // If this is a .NET framework reference then include everything.
- if (netFrameworks.Any(framework => name.StartsWith(framework)))
+ if (info.Compile is null || !info.Compile.Any())
{
- dependencies.Add(name);
- }
- else
- {
- info.Compile?
- .ForEach(r => dependencies.Add(name, r.Key));
+ // If this is a framework reference then include everything.
+ if (FrameworkPackageNames.AllFrameworks.Any(framework => name.StartsWith(framework)))
+ {
+ dependencies.AddFramework(name);
+ }
+ return;
}
+
+ info.Compile
+ .ForEach(r => dependencies.Add(name, r.Key));
});
- return dependencies;
+ return;
+ }
+
+ ///
+ /// Add the framework dependencies from the assets file to dependencies.
+ ///
+ /// Example:
+ /// "project": {
+ // "version": "1.0.0",
+ // "frameworks": {
+ // "net7.0": {
+ // "frameworkReferences": {
+ // "Microsoft.AspNetCore.App": {
+ // "privateAssets": "none"
+ // },
+ // "Microsoft.NETCore.App": {
+ // "privateAssets": "all"
+ // }
+ // }
+ // }
+ // }
+ // }
+ //
+ /// Adds the following dependencies
+ /// Paths: {
+ /// "microsoft.aspnetcore.app.ref",
+ /// "microsoft.netcore.app.ref"
+ /// }
+ /// Packages: {
+ /// "microsoft.aspnetcore.app.ref",
+ /// "microsoft.netcore.app.ref"
+ /// }
+ ///
+ private void AddFrameworkDependencies(JObject json, DependencyContainer dependencies)
+ {
+
+ var frameworks = json
+ .GetProperty("project")?
+ .GetProperty("frameworks");
+
+ if (frameworks is null)
+ {
+ progressMonitor.LogDebug("No framework section in assets.json.");
+ return;
+ }
+
+ // If there is more than one framework we need to pick just one.
+ // To ensure stability we pick one based on the lexicographic order of
+ // the framework names.
+ var references = frameworks
+ .Properties()?
+ .MaxBy(p => p.Name)?
+ .Value["frameworkReferences"] as JObject;
+
+ if (references is null)
+ {
+ progressMonitor.LogDebug("No framework references in assets.json.");
+ return;
+ }
+
+ references
+ .Properties()
+ .ForEach(f => dependencies.AddFramework($"{f.Name}.Ref".ToLowerInvariant()));
}
///
@@ -134,6 +191,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
{
var obj = JObject.Parse(json);
AddPackageDependencies(obj, dependencies);
+ AddFrameworkDependencies(obj, dependencies);
return true;
}
catch (Exception e)
@@ -143,14 +201,31 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
}
+ private static bool TryReadAllText(string path, ProgressMonitor progressMonitor, [NotNullWhen(returnValue: true)] out string? content)
+ {
+ try
+ {
+ content = File.ReadAllText(path);
+ return true;
+ }
+ catch (Exception e)
+ {
+ progressMonitor.LogInfo($"Failed to read assets file '{path}': {e.Message}");
+ content = null;
+ return false;
+ }
+ }
+
public static DependencyContainer GetCompilationDependencies(ProgressMonitor progressMonitor, IEnumerable assets)
{
var parser = new Assets(progressMonitor);
var dependencies = new DependencyContainer();
assets.ForEach(asset =>
{
- var json = File.ReadAllText(asset);
- parser.TryParse(json, dependencies);
+ if (TryReadAllText(asset, progressMonitor, out var json))
+ {
+ parser.TryParse(json, dependencies);
+ }
});
return dependencies;
}
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyContainer.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyContainer.cs
index 4c0586c7f83..d3858f17fe1 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyContainer.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyContainer.cs
@@ -9,14 +9,19 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
///
internal class DependencyContainer
{
- private readonly List requiredPaths = new();
- private readonly HashSet usedPackages = new();
+ ///
+ /// Paths to dependencies required for compilation.
+ ///
+ public List Paths { get; } = new();
///
- /// In most cases paths in asset files point to dll's or the empty _._ file, which
- /// is sometimes there to avoid the directory being empty.
- /// That is, if the path specifically adds a .dll we use that, otherwise we as a fallback
- /// add the entire directory (which should be fine in case of _._ as well).
+ /// Packages that are used as a part of the required dependencies.
+ ///
+ public HashSet Packages { get; } = new();
+
+ ///
+ /// If the path specifically adds a .dll we use that, otherwise we as a fallback
+ /// add the entire directory.
///
private static string ParseFilePath(string path)
{
@@ -32,16 +37,6 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
.Split(Path.DirectorySeparatorChar)
.First();
- ///
- /// Paths to dependencies required for compilation.
- ///
- public IEnumerable RequiredPaths => requiredPaths;
-
- ///
- /// Packages that are used as a part of the required dependencies.
- ///
- public HashSet UsedPackages => usedPackages;
-
///
/// Add a dependency inside a package.
///
@@ -50,20 +45,27 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
var p = package.Replace('/', Path.DirectorySeparatorChar);
var d = dependency.Replace('/', Path.DirectorySeparatorChar);
+ // In most cases paths in asset files point to dll's or the empty _._ file.
+ // That is, for _._ we don't need to add anything.
+ if (Path.GetFileName(d) == "_._")
+ {
+ return;
+ }
+
var path = Path.Combine(p, ParseFilePath(d));
- requiredPaths.Add(path);
- usedPackages.Add(GetPackageName(p));
+ Paths.Add(path);
+ Packages.Add(GetPackageName(p));
}
///
- /// Add a dependency to an entire package
+ /// Add a dependency to an entire framework package.
///
- public void Add(string package)
+ public void AddFramework(string framework)
{
- var p = package.Replace('/', Path.DirectorySeparatorChar);
+ var p = framework.Replace('/', Path.DirectorySeparatorChar);
- requiredPaths.Add(p);
- usedPackages.Add(GetPackageName(p));
+ Paths.Add(p);
+ Packages.Add(GetPackageName(p));
}
}
}
\ No newline at end of file
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyManager.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyManager.cs
index e315b194bd0..e2555ddcd6f 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyManager.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DependencyManager.cs
@@ -119,7 +119,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
var dependencies = Assets.GetCompilationDependencies(progressMonitor, assets1.Union(assets2));
var paths = dependencies
- .RequiredPaths
+ .Paths
.Select(d => Path.Combine(packageDirectory.DirInfo.FullName, d))
.ToList();
dllPaths.UnionWith(paths);
@@ -128,16 +128,18 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
DownloadMissingPackages(allNonBinaryFiles, dllPaths);
}
+ var frameworkLocations = new HashSet();
+
// Find DLLs in the .Net / Asp.Net Framework
// This block needs to come after the nuget restore, because the nuget restore might fetch the .NET Core/Framework reference assemblies.
if (options.ScanNetFrameworkDlls)
{
- AddNetFrameworkDlls(dllPaths);
- AddAspNetCoreFrameworkDlls(dllPaths);
- AddMicrosoftWindowsDesktopDlls(dllPaths);
+ AddNetFrameworkDlls(dllPaths, frameworkLocations);
+ AddAspNetCoreFrameworkDlls(dllPaths, frameworkLocations);
+ AddMicrosoftWindowsDesktopDlls(dllPaths, frameworkLocations);
}
- assemblyCache = new AssemblyCache(dllPaths, progressMonitor);
+ assemblyCache = new AssemblyCache(dllPaths, frameworkLocations, progressMonitor);
AnalyseSolutions(solutions);
foreach (var filename in assemblyCache.AllAssemblies.Select(a => a.Filename))
@@ -146,7 +148,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
RemoveNugetAnalyzerReferences();
- ResolveConflicts();
+ ResolveConflicts(frameworkLocations);
// Output the findings
foreach (var r in usedReferences.Keys.OrderBy(r => r))
@@ -228,17 +230,11 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
}
- private void AddNetFrameworkDlls(ISet dllPaths)
+ private void AddNetFrameworkDlls(ISet dllPaths, ISet frameworkLocations)
{
// Multiple dotnet framework packages could be present.
// The order of the packages is important, we're adding the first one that is present in the nuget cache.
- var packagesInPrioOrder = new string[]
- {
- "microsoft.netcore.app.ref", // net7.0, ... net5.0, netcoreapp3.1, netcoreapp3.0
- "microsoft.netframework.referenceassemblies.", // net48, ..., net20
- "netstandard.library.ref", // netstandard2.1
- "netstandard.library" // netstandard2.0
- };
+ var packagesInPrioOrder = FrameworkPackageNames.NetFrameworks;
var frameworkPath = packagesInPrioOrder
.Select((s, index) => (Index: index, Path: GetPackageDirectory(s)))
@@ -247,6 +243,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
if (frameworkPath.Path is not null)
{
dllPaths.Add(frameworkPath.Path);
+ frameworkLocations.Add(frameworkPath.Path);
progressMonitor.LogInfo($"Found .NET Core/Framework DLLs in NuGet packages at {frameworkPath.Path}. Not adding installation directory.");
for (var i = frameworkPath.Index + 1; i < packagesInPrioOrder.Length; i++)
@@ -276,6 +273,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
progressMonitor.LogInfo($".NET runtime location selected: {runtimeLocation}");
dllPaths.Add(runtimeLocation);
+ frameworkLocations.Add(runtimeLocation);
}
private void RemoveNugetPackageReference(string packagePrefix, ISet dllPaths)
@@ -300,7 +298,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
}
- private void AddAspNetCoreFrameworkDlls(ISet dllPaths)
+ private void AddAspNetCoreFrameworkDlls(ISet dllPaths, ISet frameworkLocations)
{
if (!fileContent.IsNewProjectStructureUsed || !fileContent.UseAspNetCoreDlls)
{
@@ -308,24 +306,29 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
// First try to find ASP.NET Core assemblies in the NuGet packages
- if (GetPackageDirectory("microsoft.aspnetcore.app.ref") is string aspNetCorePackage)
+ if (GetPackageDirectory(FrameworkPackageNames.AspNetCoreFramework) is string aspNetCorePackage)
{
progressMonitor.LogInfo($"Found ASP.NET Core in NuGet packages. Not adding installation directory.");
dllPaths.Add(aspNetCorePackage);
+ frameworkLocations.Add(aspNetCorePackage);
+ return;
}
- else if (Runtime.AspNetCoreRuntime is string aspNetCoreRuntime)
+
+ if (Runtime.AspNetCoreRuntime is string aspNetCoreRuntime)
{
progressMonitor.LogInfo($"ASP.NET runtime location selected: {aspNetCoreRuntime}");
dllPaths.Add(aspNetCoreRuntime);
+ frameworkLocations.Add(aspNetCoreRuntime);
}
}
- private void AddMicrosoftWindowsDesktopDlls(ISet dllPaths)
+ private void AddMicrosoftWindowsDesktopDlls(ISet dllPaths, ISet frameworkLocations)
{
- if (GetPackageDirectory("microsoft.windowsdesktop.app.ref") is string windowsDesktopApp)
+ if (GetPackageDirectory(FrameworkPackageNames.WindowsDesktopFramework) is string windowsDesktopApp)
{
progressMonitor.LogInfo($"Found Windows Desktop App in NuGet packages.");
dllPaths.Add(windowsDesktopApp);
+ frameworkLocations.Add(windowsDesktopApp);
}
}
@@ -351,12 +354,13 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
return new DirectoryInfo(packageDirectory.DirInfo.FullName)
.EnumerateDirectories("*", new EnumerationOptions { MatchCasing = MatchCasing.CaseInsensitive, RecurseSubdirectories = false })
- .Select(d => d.FullName);
+ .Select(d => d.Name);
}
private void LogAllUnusedPackages(DependencyContainer dependencies) =>
GetAllPackageDirectories()
- .Where(package => !dependencies.UsedPackages.Contains(package))
+ .Where(package => !dependencies.Packages.Contains(package))
+ .Order()
.ForEach(package => progressMonitor.LogInfo($"Unused package: {package}"));
private void GenerateSourceFileFromImplicitUsings()
@@ -478,7 +482,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
/// If the same assembly name is duplicated with different versions,
/// resolve to the higher version number.
///
- private void ResolveConflicts()
+ private void ResolveConflicts(IEnumerable frameworkPaths)
{
var sortedReferences = new List();
foreach (var usedReference in usedReferences)
@@ -494,11 +498,8 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
}
}
- var emptyVersion = new Version(0, 0);
sortedReferences = sortedReferences
- .OrderBy(r => r.NetCoreVersion ?? emptyVersion)
- .ThenBy(r => r.Version ?? emptyVersion)
- .ThenBy(r => r.Filename)
+ .OrderAssemblyInfosByPreference(frameworkPaths)
.ToList();
var finalAssemblyList = new Dictionary();
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DotNet.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DotNet.cs
index e8493a770db..a2af85a1c48 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DotNet.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/DotNet.cs
@@ -128,7 +128,7 @@ namespace Semmle.Extraction.CSharp.DependencyFetching
[GeneratedRegex("Restored\\s+(.+\\.csproj)", RegexOptions.Compiled)]
private static partial Regex RestoredProjectRegex();
- [GeneratedRegex("[Assets\\sfile\\shas\\snot\\schanged.\\sSkipping\\sassets\\sfile\\swriting.|Writing\\sassets\\sfile\\sto\\sdisk.]\\sPath:\\s(.*)", RegexOptions.Compiled)]
+ [GeneratedRegex("[Assets\\sfile\\shas\\snot\\schanged.\\sSkipping\\sassets\\sfile\\swriting.|Writing\\sassets\\sfile\\sto\\sdisk.]\\sPath:\\s(.+)", RegexOptions.Compiled)]
private static partial Regex AssetsFileRegex();
}
}
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/FrameworkPackageNames.cs b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/FrameworkPackageNames.cs
new file mode 100644
index 00000000000..7b4a076f99f
--- /dev/null
+++ b/csharp/extractor/Semmle.Extraction.CSharp.DependencyFetching/FrameworkPackageNames.cs
@@ -0,0 +1,25 @@
+using System.Collections.Generic;
+using System.Linq;
+
+namespace Semmle.Extraction.CSharp.DependencyFetching
+{
+ internal static class FrameworkPackageNames
+ {
+ public static string AspNetCoreFramework { get; } = "microsoft.aspnetcore.app.ref";
+
+ public static string WindowsDesktopFramework { get; } = "microsoft.windowsdesktop.app.ref";
+
+ // The order of the packages is important.
+ public static string[] NetFrameworks { get; } = new string[]
+ {
+ "microsoft.netcore.app.ref", // net7.0, ... net5.0, netcoreapp3.1, netcoreapp3.0
+ "microsoft.netframework.referenceassemblies.", // net48, ..., net20
+ "netstandard.library.ref", // netstandard2.1
+ "netstandard.library" // netstandard2.0
+ };
+
+ public static IEnumerable AllFrameworks { get; } =
+ NetFrameworks
+ .Union(new string[] { AspNetCoreFramework, WindowsDesktopFramework });
+ }
+}
diff --git a/csharp/extractor/Semmle.Extraction.CSharp.StubGenerator/StubVisitor.cs b/csharp/extractor/Semmle.Extraction.CSharp.StubGenerator/StubVisitor.cs
index e29cd532a5c..a9bd82d2617 100644
--- a/csharp/extractor/Semmle.Extraction.CSharp.StubGenerator/StubVisitor.cs
+++ b/csharp/extractor/Semmle.Extraction.CSharp.StubGenerator/StubVisitor.cs
@@ -41,6 +41,7 @@ internal sealed class StubVisitor : SymbolVisitor
(
t1 is INamedTypeSymbol named1 &&
t2 is INamedTypeSymbol named2 &&
+ (!SymbolEqualityComparer.Default.Equals(named1, named1.ConstructedFrom) || !SymbolEqualityComparer.Default.Equals(named2, named2.ConstructedFrom)) &&
EqualsModuloTupleElementNames(named1.ConstructedFrom, named2.ConstructedFrom) &&
named1.TypeArguments.Length == named2.TypeArguments.Length &&
named1.TypeArguments.Zip(named2.TypeArguments).All(p => EqualsModuloTupleElementNames(p.First, p.Second))
diff --git a/csharp/extractor/Semmle.Extraction.Tests/Assets.cs b/csharp/extractor/Semmle.Extraction.Tests/Assets.cs
index 1dbd6f9d41c..85e56b6de64 100644
--- a/csharp/extractor/Semmle.Extraction.Tests/Assets.cs
+++ b/csharp/extractor/Semmle.Extraction.Tests/Assets.cs
@@ -21,49 +21,26 @@ namespace Semmle.Extraction.Tests
// Verify
Assert.True(success);
- Assert.Equal(5, dependencies.RequiredPaths.Count());
- Assert.Equal(4, dependencies.UsedPackages.Count());
+ Assert.Equal(6, dependencies.Paths.Count());
+ Assert.Equal(5, dependencies.Packages.Count());
- var normalizedPaths = dependencies.RequiredPaths.Select(FixExpectedPathOnWindows);
- // Required references
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+ // Used references
Assert.Contains("castle.core/4.4.1/lib/netstandard1.5/Castle.Core.dll", normalizedPaths);
Assert.Contains("castle.core/4.4.1/lib/netstandard1.5/Castle.Core2.dll", normalizedPaths);
Assert.Contains("json.net/1.0.33/lib/netstandard2.0/Json.Net.dll", normalizedPaths);
Assert.Contains("microsoft.aspnetcore.cryptography.internal/6.0.8/lib/net6.0/Microsoft.AspNetCore.Cryptography.Internal.dll", normalizedPaths);
- Assert.Contains("humanizer.core/2.8.26/lib/netstandard2.0", normalizedPaths);
// Used packages
- Assert.Contains("castle.core", dependencies.UsedPackages);
- Assert.Contains("json.net", dependencies.UsedPackages);
- Assert.Contains("microsoft.aspnetcore.cryptography.internal", dependencies.UsedPackages);
- Assert.Contains("humanizer.core", dependencies.UsedPackages);
+ Assert.Contains("castle.core", dependencies.Packages);
+ Assert.Contains("json.net", dependencies.Packages);
+ Assert.Contains("microsoft.aspnetcore.cryptography.internal", dependencies.Packages);
+ // Used frameworks
+ Assert.Contains("microsoft.netcore.app.ref", dependencies.Packages);
+ Assert.Contains("microsoft.aspnetcore.app.ref", dependencies.Packages);
}
[Fact]
- public void TestAssets2()
- {
- // Setup
- var assets = new Assets(new ProgressMonitor(new LoggerStub()));
- var json = assetsJson2;
- var dependencies = new DependencyContainer();
-
- // Execute
- var success = assets.TryParse(json, dependencies);
-
- // Verify
- Assert.True(success);
- Assert.Equal(2, dependencies.RequiredPaths.Count());
-
- var normalizedPaths = dependencies.RequiredPaths.Select(FixExpectedPathOnWindows);
- // Required references
- Assert.Contains("microsoft.netframework.referenceassemblies/1.0.3", normalizedPaths);
- Assert.Contains("microsoft.netframework.referenceassemblies.net48/1.0.3", normalizedPaths);
- // Used packages
- Assert.Contains("microsoft.netframework.referenceassemblies", dependencies.UsedPackages);
- Assert.Contains("microsoft.netframework.referenceassemblies.net48", dependencies.UsedPackages);
- }
-
- [Fact]
- public void TestAssets3()
+ public void TestAssetsFailure()
{
// Setup
var assets = new Assets(new ProgressMonitor(new LoggerStub()));
@@ -75,9 +52,186 @@ namespace Semmle.Extraction.Tests
// Verify
Assert.False(success);
- Assert.Empty(dependencies.RequiredPaths);
+ Assert.Empty(dependencies.Paths);
}
+ [Fact]
+ public void TestAssetsNet70()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNet70;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+ Assert.Equal(4, dependencies.Paths.Count);
+ Assert.Equal(4, dependencies.Packages.Count);
+
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+ // Used paths
+ Assert.Contains("microsoft.netcore.app.ref", normalizedPaths);
+ Assert.Contains("microsoft.aspnetcore.app.ref", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/netstandard2.0/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/netstandard2.0/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("microsoft.netcore.app.ref", dependencies.Packages);
+ Assert.Contains("microsoft.aspnetcore.app.ref", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+
+ }
+
+ [Fact]
+ public void TestAssetsNet48()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNet48;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+ Assert.Equal(3, dependencies.Paths.Count);
+ Assert.Equal(3, dependencies.Packages.Count);
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+ // Used references
+ Assert.Contains("microsoft.netframework.referenceassemblies.net48/1.0.2", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/net45/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/net45/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("microsoft.netframework.referenceassemblies.net48", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+ }
+
+ [Fact]
+ public void TestAssetsNetstandard21()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNetstandard21;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+ Assert.Equal(3, dependencies.Paths.Count);
+ Assert.Equal(3, dependencies.Packages.Count);
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+
+ // Used references
+ Assert.Contains("netstandard.library.ref", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/netstandard2.0/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/netstandard2.0/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("netstandard.library.ref", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+ }
+
+ [Fact]
+ public void TestAssetsNetStandard16()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNetstandard16;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+ Assert.Equal(5, dependencies.Paths.Count);
+ Assert.Equal(5, dependencies.Packages.Count);
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+
+ // Used references
+ Assert.Contains("netstandard.library/1.6.1", normalizedPaths);
+ Assert.Contains("microsoft.csharp/4.3.0/ref/netstandard1.0/Microsoft.CSharp.dll", normalizedPaths);
+ Assert.Contains("microsoft.win32.primitives/4.3.0/ref/netstandard1.3/Microsoft.Win32.Primitives.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/netstandard1.3/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/netstandard1.3/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("netstandard.library", dependencies.Packages);
+ Assert.Contains("microsoft.csharp", dependencies.Packages);
+ Assert.Contains("microsoft.win32.primitives", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+ }
+
+ [Fact]
+ public void TestAssetsNetcoreapp20()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNetcoreapp20;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+ Assert.Equal(144, dependencies.Paths.Count);
+ Assert.Equal(3, dependencies.Packages.Count);
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+
+ // Used references (only some of them)
+ Assert.Contains("microsoft.netcore.app/2.0.0/ref/netcoreapp2.0/Microsoft.CSharp.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/netstandard2.0/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/netstandard2.0/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("microsoft.netcore.app", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+ }
+
+ [Fact]
+ public void TestAssetsNetcoreapp31()
+ {
+ // Setup
+ var assets = new Assets(new ProgressMonitor(new LoggerStub()));
+ var json = assetsNetcoreapp31;
+ var dependencies = new DependencyContainer();
+
+ // Execute
+ var success = assets.TryParse(json, dependencies);
+
+ // Verify
+ Assert.True(success);
+
+ var normalizedPaths = dependencies.Paths.Select(FixExpectedPathOnWindows);
+
+ // Used paths
+ Assert.Contains("microsoft.netcore.app.ref", normalizedPaths);
+ Assert.Contains("microsoft.aspnetcore.app.ref", normalizedPaths);
+ Assert.Contains("newtonsoft.json/12.0.1/lib/netstandard2.0/Newtonsoft.Json.dll", normalizedPaths);
+ Assert.Contains("newtonsoft.json.bson/1.0.2/lib/netstandard2.0/Newtonsoft.Json.Bson.dll", normalizedPaths);
+ // Used packages
+ Assert.Contains("microsoft.netcore.app.ref", dependencies.Packages);
+ Assert.Contains("microsoft.aspnetcore.app.ref", dependencies.Packages);
+ Assert.Contains("newtonsoft.json", dependencies.Packages);
+ Assert.Contains("newtonsoft.json.bson", dependencies.Packages);
+ }
+
+ ///
+ /// This is manually created JSON string with the same structure as the assets file.
+ ///
private readonly string assetsJson1 = """
{
"version": 3,
@@ -181,25 +335,1326 @@ namespace Semmle.Extraction.Tests
}
""";
- private readonly string assetsJson2 = """
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// net70
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNet70 = """
{
- "version": 3,
- "targets": {
- ".NETFramework,Version=v4.8": {
- "Microsoft.NETFramework.ReferenceAssemblies/1.0.3": {
- "type": "package",
- "dependencies": {
- "Microsoft.NETFramework.ReferenceAssemblies.net48": "1.0.3"
- }
- },
- "Microsoft.NETFramework.ReferenceAssemblies.net48/1.0.3": {
- "type": "package",
- "build": {
- "build/Microsoft.NETFramework.ReferenceAssemblies.net48.targets": {}
- }
- }
+ "version": 3,
+ "targets": {
+ "net7.0": {
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
}
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "net70"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "net7.0": {
+ "targetAlias": "net70",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "net7.0": {
+ "targetAlias": "net70",
+ "dependencies": {
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "imports": [
+ "net461",
+ "net462",
+ "net47",
+ "net471",
+ "net472",
+ "net48",
+ "net481"
+ ],
+ "assetTargetFallback": true,
+ "warn": true,
+ "downloadDependencies": [
+ {
+ "name": "Microsoft.AspNetCore.App.Ref",
+ "version": "[7.0.2, 7.0.2]"
+ },
+ {
+ "name": "Microsoft.NETCore.App.Host.osx-x64",
+ "version": "[7.0.2, 7.0.2]"
+ },
+ {
+ "name": "Microsoft.NETCore.App.Ref",
+ "version": "[7.0.2, 7.0.2]"
+ }
+ ],
+ "frameworkReferences": {
+ "Microsoft.AspNetCore.App": {
+ "privateAssets": "none"
+ },
+ "Microsoft.NETCore.App": {
+ "privateAssets": "all"
+ }
+ },
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
+}
+""";
+
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// net4.8
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNet48 = """
+{
+ "version": 3,
+ "targets": {
+ ".NETFramework,Version=v4.8": {
+ "Microsoft.NETFramework.ReferenceAssemblies/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETFramework.ReferenceAssemblies.net48": "1.0.2"
+ }
+ },
+ "Microsoft.NETFramework.ReferenceAssemblies.net48/1.0.2": {
+ "type": "package",
+ "build": {
+ "build/Microsoft.NETFramework.ReferenceAssemblies.net48.targets": {}
+ }
+ },
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "compile": {
+ "lib/net45/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/net45/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/net45/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/net45/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
+ }
+ },
+ "projectFileDependencyGroups": {
+ ".NETFramework,Version=v4.8": [
+ "Microsoft.NETFramework.ReferenceAssemblies >= 1.0.2",
+ "Newtonsoft.Json.Bson >= 1.0.2"
+ ]
+ },
+ "packageFolders": {
+ "/Users/michaelnebel/Work/playground/csharpwebapp/packages": {}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "net4.8"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "net48": {
+ "targetAlias": "net4.8",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "net48": {
+ "targetAlias": "net4.8",
+ "dependencies": {
+ "Microsoft.NETFramework.ReferenceAssemblies": {
+ "suppressParent": "All",
+ "target": "Package",
+ "version": "[1.0.2, )",
+ "autoReferenced": true
+ },
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
+}
+""";
+
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// netstandard2.1
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNetstandard21 = """
+{
+ "version": 3,
+ "targets": {
+ ".NETStandard,Version=v2.1": {
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
+ }
+ },
+ "projectFileDependencyGroups": {
+ ".NETStandard,Version=v2.1": [
+ "Newtonsoft.Json.Bson >= 1.0.2"
+ ]
+ },
+ "packageFolders": {
+ "/Users/michaelnebel/Work/playground/csharpwebapp/packages": {}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "netstandard2.1"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "netstandard2.1": {
+ "targetAlias": "netstandard2.1",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "netstandard2.1": {
+ "targetAlias": "netstandard2.1",
+ "dependencies": {
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "imports": [
+ "net461",
+ "net462",
+ "net47",
+ "net471",
+ "net472",
+ "net48",
+ "net481"
+ ],
+ "assetTargetFallback": true,
+ "warn": true,
+ "downloadDependencies": [
+ {
+ "name": "NETStandard.Library.Ref",
+ "version": "[2.1.0, 2.1.0]"
+ }
+ ],
+ "frameworkReferences": {
+ "NETStandard.Library": {
+ "privateAssets": "all"
+ }
+ },
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
+}
+""";
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// netstandard1.6
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNetstandard16 = """
+{
+ "version": 3,
+ "targets": {
+ ".NETStandard,Version=v1.6": {
+ "Microsoft.CSharp/4.3.0": {
+ "type": "package",
+ "dependencies": {
+ "System.Collections": "4.3.0",
+ "System.Diagnostics.Debug": "4.3.0",
+ "System.Dynamic.Runtime": "4.3.0",
+ "System.Globalization": "4.3.0",
+ "System.Linq": "4.3.0",
+ "System.Linq.Expressions": "4.3.0",
+ "System.ObjectModel": "4.3.0",
+ "System.Reflection": "4.3.0",
+ "System.Reflection.Extensions": "4.3.0",
+ "System.Reflection.Primitives": "4.3.0",
+ "System.Reflection.TypeExtensions": "4.3.0",
+ "System.Resources.ResourceManager": "4.3.0",
+ "System.Runtime": "4.3.0",
+ "System.Runtime.Extensions": "4.3.0",
+ "System.Runtime.InteropServices": "4.3.0",
+ "System.Threading": "4.3.0"
+ },
+ "compile": {
+ "ref/netstandard1.0/Microsoft.CSharp.dll": {
+ "related": ".xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard1.3/Microsoft.CSharp.dll": {}
+ }
+ },
+ "Microsoft.NETCore.Platforms/1.1.0": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard1.0/_._": {}
+ },
+ "runtime": {
+ "lib/netstandard1.0/_._": {}
+ }
+ },
+ "Microsoft.NETCore.Targets/1.1.0": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard1.0/_._": {}
+ },
+ "runtime": {
+ "lib/netstandard1.0/_._": {}
+ }
+ },
+ "Microsoft.Win32.Primitives/4.3.0": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.Platforms": "1.1.0",
+ "Microsoft.NETCore.Targets": "1.1.0",
+ "System.Runtime": "4.3.0"
+ },
+ "compile": {
+ "ref/netstandard1.3/Microsoft.Win32.Primitives.dll": {
+ "related": ".xml"
+ }
+ }
+ },
+ "NETStandard.Library/1.6.1": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.Platforms": "1.1.0",
+ "Microsoft.Win32.Primitives": "4.3.0",
+ "System.AppContext": "4.3.0",
+ "System.Collections": "4.3.0",
+ "System.Collections.Concurrent": "4.3.0",
+ "System.Console": "4.3.0",
+ "System.Diagnostics.Debug": "4.3.0",
+ "System.Diagnostics.Tools": "4.3.0",
+ "System.Diagnostics.Tracing": "4.3.0",
+ "System.Globalization": "4.3.0",
+ "System.Globalization.Calendars": "4.3.0",
+ "System.IO": "4.3.0",
+ "System.IO.Compression": "4.3.0",
+ "System.IO.Compression.ZipFile": "4.3.0",
+ "System.IO.FileSystem": "4.3.0",
+ "System.IO.FileSystem.Primitives": "4.3.0",
+ "System.Linq": "4.3.0",
+ "System.Linq.Expressions": "4.3.0",
+ "System.Net.Http": "4.3.0",
+ "System.Net.Primitives": "4.3.0",
+ "System.Net.Sockets": "4.3.0",
+ "System.ObjectModel": "4.3.0",
+ "System.Reflection": "4.3.0",
+ "System.Reflection.Extensions": "4.3.0",
+ "System.Reflection.Primitives": "4.3.0",
+ "System.Resources.ResourceManager": "4.3.0",
+ "System.Runtime": "4.3.0",
+ "System.Runtime.Extensions": "4.3.0",
+ "System.Runtime.Handles": "4.3.0",
+ "System.Runtime.InteropServices": "4.3.0",
+ "System.Runtime.InteropServices.RuntimeInformation": "4.3.0",
+ "System.Runtime.Numerics": "4.3.0",
+ "System.Security.Cryptography.Algorithms": "4.3.0",
+ "System.Security.Cryptography.Encoding": "4.3.0",
+ "System.Security.Cryptography.Primitives": "4.3.0",
+ "System.Security.Cryptography.X509Certificates": "4.3.0",
+ "System.Text.Encoding": "4.3.0",
+ "System.Text.Encoding.Extensions": "4.3.0",
+ "System.Text.RegularExpressions": "4.3.0",
+ "System.Threading": "4.3.0",
+ "System.Threading.Tasks": "4.3.0",
+ "System.Threading.Timer": "4.3.0",
+ "System.Xml.ReaderWriter": "4.3.0",
+ "System.Xml.XDocument": "4.3.0"
+ }
+ },
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.CSharp": "4.3.0",
+ "NETStandard.Library": "1.6.1",
+ "System.ComponentModel.TypeConverter": "4.3.0",
+ "System.Runtime.Serialization.Formatters": "4.3.0",
+ "System.Runtime.Serialization.Primitives": "4.3.0",
+ "System.Xml.XmlDocument": "4.3.0"
+ },
+ "compile": {
+ "lib/netstandard1.3/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard1.3/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "NETStandard.Library": "1.6.1",
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/netstandard1.3/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard1.3/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
+ }
+ },
+ "projectFileDependencyGroups": {
+ ".NETStandard,Version=v1.6": [
+ "NETStandard.Library >= 1.6.1",
+ "Newtonsoft.Json.Bson >= 1.0.2"
+ ]
+ },
+ "packageFolders": {
+ "/Users/michaelnebel/Work/playground/csharpwebapp/packages": {}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "netstandard1.6"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "netstandard1.6": {
+ "targetAlias": "netstandard1.6",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "netstandard1.6": {
+ "targetAlias": "netstandard1.6",
+ "dependencies": {
+ "NETStandard.Library": {
+ "target": "Package",
+ "version": "[1.6.1, )",
+ "autoReferenced": true
+ },
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
+}
+""";
+
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// netcoreapp2.0
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNetcoreapp20 = """
+{
+ "version": 3,
+ "targets": {
+ ".NETCoreApp,Version=v2.0": {
+ "Microsoft.NETCore.App/2.0.0": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.DotNetHostPolicy": "2.0.0",
+ "Microsoft.NETCore.Platforms": "2.0.0",
+ "NETStandard.Library": "2.0.0"
+ },
+ "compile": {
+ "ref/netcoreapp2.0/Microsoft.CSharp.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/Microsoft.VisualBasic.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/Microsoft.Win32.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.AppContext.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Buffers.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Collections.Concurrent.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Collections.Immutable.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Collections.NonGeneric.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Collections.Specialized.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Collections.dll": {
+ "related": ".Concurrent.xml;.Immutable.xml;.NonGeneric.xml;.Specialized.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.ComponentModel.Annotations.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.ComponentModel.Composition.dll": {},
+ "ref/netcoreapp2.0/System.ComponentModel.DataAnnotations.dll": {},
+ "ref/netcoreapp2.0/System.ComponentModel.EventBasedAsync.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.ComponentModel.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.ComponentModel.TypeConverter.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.ComponentModel.dll": {
+ "related": ".Annotations.xml;.EventBasedAsync.xml;.Primitives.xml;.TypeConverter.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Configuration.dll": {},
+ "ref/netcoreapp2.0/System.Console.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Core.dll": {},
+ "ref/netcoreapp2.0/System.Data.Common.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Data.dll": {
+ "related": ".Common.xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.Contracts.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.Debug.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.DiagnosticSource.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.FileVersionInfo.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.Process.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.StackTrace.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.TextWriterTraceListener.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.Tools.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.TraceSource.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Diagnostics.Tracing.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Drawing.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Drawing.dll": {
+ "related": ".Primitives.xml"
+ },
+ "ref/netcoreapp2.0/System.Dynamic.Runtime.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Globalization.Calendars.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Globalization.Extensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Globalization.dll": {
+ "related": ".Calendars.xml;.Extensions.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.IO.Compression.FileSystem.dll": {},
+ "ref/netcoreapp2.0/System.IO.Compression.ZipFile.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.Compression.dll": {
+ "related": ".xml;.ZipFile.xml"
+ },
+ "ref/netcoreapp2.0/System.IO.FileSystem.DriveInfo.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.FileSystem.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.FileSystem.Watcher.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.FileSystem.dll": {
+ "related": ".DriveInfo.xml;.Primitives.xml;.Watcher.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.IO.IsolatedStorage.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.MemoryMappedFiles.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.Pipes.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.UnmanagedMemoryStream.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.IO.dll": {
+ "related": ".Compression.xml;.Compression.ZipFile.xml;.FileSystem.DriveInfo.xml;.FileSystem.Primitives.xml;.FileSystem.Watcher.xml;.FileSystem.xml;.IsolatedStorage.xml;.MemoryMappedFiles.xml;.Pipes.xml;.UnmanagedMemoryStream.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Linq.Expressions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Linq.Parallel.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Linq.Queryable.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Linq.dll": {
+ "related": ".Expressions.xml;.Parallel.xml;.Queryable.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Http.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.HttpListener.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Mail.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.NameResolution.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.NetworkInformation.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Ping.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Requests.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Security.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.ServicePoint.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.Sockets.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.WebClient.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.WebHeaderCollection.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.WebProxy.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.WebSockets.Client.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Net.WebSockets.dll": {
+ "related": ".Client.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Net.dll": {
+ "related": ".Http.xml;.HttpListener.xml;.Mail.xml;.NameResolution.xml;.NetworkInformation.xml;.Ping.xml;.Primitives.xml;.Requests.xml;.Security.xml;.ServicePoint.xml;.Sockets.xml;.WebClient.xml;.WebHeaderCollection.xml;.WebProxy.xml;.WebSockets.Client.xml;.WebSockets.xml"
+ },
+ "ref/netcoreapp2.0/System.Numerics.Vectors.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Numerics.dll": {
+ "related": ".Vectors.xml"
+ },
+ "ref/netcoreapp2.0/System.ObjectModel.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.DispatchProxy.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Emit.ILGeneration.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Emit.Lightweight.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Emit.dll": {
+ "related": ".ILGeneration.xml;.Lightweight.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Extensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Metadata.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.TypeExtensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Reflection.dll": {
+ "related": ".DispatchProxy.xml;.Emit.ILGeneration.xml;.Emit.Lightweight.xml;.Emit.xml;.Extensions.xml;.Metadata.xml;.Primitives.xml;.TypeExtensions.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Resources.Reader.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Resources.ResourceManager.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Resources.Writer.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.CompilerServices.VisualC.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Extensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Handles.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.InteropServices.RuntimeInformation.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.InteropServices.WindowsRuntime.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.InteropServices.dll": {
+ "related": ".RuntimeInformation.xml;.WindowsRuntime.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Loader.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Numerics.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Serialization.Formatters.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Serialization.Json.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Serialization.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Serialization.Xml.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.Serialization.dll": {
+ "related": ".Formatters.xml;.Json.xml;.Primitives.xml;.Xml.xml"
+ },
+ "ref/netcoreapp2.0/System.Runtime.dll": {
+ "related": ".CompilerServices.VisualC.xml;.Extensions.xml;.Handles.xml;.InteropServices.RuntimeInformation.xml;.InteropServices.WindowsRuntime.xml;.InteropServices.xml;.Loader.xml;.Numerics.xml;.Serialization.Formatters.xml;.Serialization.Json.xml;.Serialization.Primitives.xml;.Serialization.Xml.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Claims.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Cryptography.Algorithms.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Cryptography.Csp.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Cryptography.Encoding.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Cryptography.Primitives.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Cryptography.X509Certificates.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.Principal.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.SecureString.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Security.dll": {
+ "related": ".Claims.xml;.Cryptography.Algorithms.xml;.Cryptography.Csp.xml;.Cryptography.Encoding.xml;.Cryptography.Primitives.xml;.Cryptography.X509Certificates.xml;.Principal.xml;.SecureString.xml"
+ },
+ "ref/netcoreapp2.0/System.ServiceModel.Web.dll": {},
+ "ref/netcoreapp2.0/System.ServiceProcess.dll": {},
+ "ref/netcoreapp2.0/System.Text.Encoding.Extensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Text.Encoding.dll": {
+ "related": ".Extensions.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Text.RegularExpressions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Overlapped.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Tasks.Dataflow.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Tasks.Extensions.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Tasks.Parallel.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Tasks.dll": {
+ "related": ".Dataflow.xml;.Extensions.xml;.Parallel.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Thread.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.ThreadPool.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.Timer.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Threading.dll": {
+ "related": ".Overlapped.xml;.Tasks.Dataflow.xml;.Tasks.Extensions.xml;.Tasks.Parallel.xml;.Tasks.xml;.Thread.xml;.ThreadPool.xml;.Timer.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Transactions.Local.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Transactions.dll": {
+ "related": ".Local.xml"
+ },
+ "ref/netcoreapp2.0/System.ValueTuple.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Web.HttpUtility.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Web.dll": {
+ "related": ".HttpUtility.xml"
+ },
+ "ref/netcoreapp2.0/System.Windows.dll": {},
+ "ref/netcoreapp2.0/System.Xml.Linq.dll": {},
+ "ref/netcoreapp2.0/System.Xml.ReaderWriter.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.Serialization.dll": {},
+ "ref/netcoreapp2.0/System.Xml.XDocument.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.XPath.XDocument.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.XPath.dll": {
+ "related": ".XDocument.xml;.xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.XmlDocument.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.XmlSerializer.dll": {
+ "related": ".xml"
+ },
+ "ref/netcoreapp2.0/System.Xml.dll": {
+ "related": ".ReaderWriter.xml;.XDocument.xml;.XmlDocument.xml;.XmlSerializer.xml;.XPath.XDocument.xml;.XPath.xml"
+ },
+ "ref/netcoreapp2.0/System.dll": {
+ "related": ".AppContext.xml;.Buffers.xml;.Collections.Concurrent.xml;.Collections.Immutable.xml;.Collections.NonGeneric.xml;.Collections.Specialized.xml;.Collections.xml;.ComponentModel.Annotations.xml;.ComponentModel.EventBasedAsync.xml;.ComponentModel.Primitives.xml;.ComponentModel.TypeConverter.xml;.ComponentModel.xml;.Console.xml;.Data.Common.xml;.Diagnostics.Contracts.xml;.Diagnostics.Debug.xml;.Diagnostics.DiagnosticSource.xml;.Diagnostics.FileVersionInfo.xml;.Diagnostics.Process.xml;.Diagnostics.StackTrace.xml;.Diagnostics.TextWriterTraceListener.xml;.Diagnostics.Tools.xml;.Diagnostics.TraceSource.xml;.Diagnostics.Tracing.xml;.Drawing.Primitives.xml;.Dynamic.Runtime.xml;.Globalization.Calendars.xml;.Globalization.Extensions.xml;.Globalization.xml;.IO.Compression.xml;.IO.Compression.ZipFile.xml;.IO.FileSystem.DriveInfo.xml;.IO.FileSystem.Primitives.xml;.IO.FileSystem.Watcher.xml;.IO.FileSystem.xml;.IO.IsolatedStorage.xml;.IO.MemoryMappedFiles.xml;.IO.Pipes.xml;.IO.UnmanagedMemoryStream.xml;.IO.xml;.Linq.Expressions.xml;.Linq.Parallel.xml;.Linq.Queryable.xml;.Linq.xml;.Net.Http.xml;.Net.HttpListener.xml;.Net.Mail.xml;.Net.NameResolution.xml;.Net.NetworkInformation.xml;.Net.Ping.xml;.Net.Primitives.xml;.Net.Requests.xml;.Net.Security.xml;.Net.ServicePoint.xml;.Net.Sockets.xml;.Net.WebClient.xml;.Net.WebHeaderCollection.xml;.Net.WebProxy.xml;.Net.WebSockets.Client.xml;.Net.WebSockets.xml;.Numerics.Vectors.xml;.ObjectModel.xml;.Reflection.DispatchProxy.xml;.Reflection.Emit.ILGeneration.xml;.Reflection.Emit.Lightweight.xml;.Reflection.Emit.xml;.Reflection.Extensions.xml;.Reflection.Metadata.xml;.Reflection.Primitives.xml;.Reflection.TypeExtensions.xml;.Reflection.xml;.Resources.Reader.xml;.Resources.ResourceManager.xml;.Resources.Writer.xml;.Runtime.CompilerServices.VisualC.xml;.Runtime.Extensions.xml;.Runtime.Handles.xml;.Runtime.InteropServices.RuntimeInformation.xml;.Runtime.InteropServices.WindowsRuntime.xml;.Runtime.InteropServices.xml;.Runtime.Loader.xml;.Runtime.Numerics.xml;.Runtime.Serialization.Formatters.xml;.Runtime.Serialization.Json.xml;.Runtime.Serialization.Primitives.xml;.Runtime.Serialization.Xml.xml;.Runtime.xml;.Security.Claims.xml;.Security.Cryptography.Algorithms.xml;.Security.Cryptography.Csp.xml;.Security.Cryptography.Encoding.xml;.Security.Cryptography.Primitives.xml;.Security.Cryptography.X509Certificates.xml;.Security.Principal.xml;.Security.SecureString.xml;.Text.Encoding.Extensions.xml;.Text.Encoding.xml;.Text.RegularExpressions.xml;.Threading.Overlapped.xml;.Threading.Tasks.Dataflow.xml;.Threading.Tasks.Extensions.xml;.Threading.Tasks.Parallel.xml;.Threading.Tasks.xml;.Threading.Thread.xml;.Threading.ThreadPool.xml;.Threading.Timer.xml;.Threading.xml;.Transactions.Local.xml;.ValueTuple.xml;.Web.HttpUtility.xml;.Xml.ReaderWriter.xml;.Xml.XDocument.xml;.Xml.XmlDocument.xml;.Xml.XmlSerializer.xml;.Xml.XPath.XDocument.xml;.Xml.XPath.xml"
+ },
+ "ref/netcoreapp2.0/WindowsBase.dll": {},
+ "ref/netcoreapp2.0/mscorlib.dll": {},
+ "ref/netcoreapp2.0/netstandard.dll": {}
+ },
+ "build": {
+ "build/netcoreapp2.0/Microsoft.NETCore.App.props": {},
+ "build/netcoreapp2.0/Microsoft.NETCore.App.targets": {}
+ }
+ },
+ "Microsoft.NETCore.DotNetAppHost/2.0.0": {
+ "type": "package"
+ },
+ "Microsoft.NETCore.DotNetHostPolicy/2.0.0": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.DotNetHostResolver": "2.0.0"
+ }
+ },
+ "Microsoft.NETCore.DotNetHostResolver/2.0.0": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.DotNetAppHost": "2.0.0"
+ }
+ },
+ "Microsoft.NETCore.Platforms/2.0.0": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard1.0/_._": {}
+ },
+ "runtime": {
+ "lib/netstandard1.0/_._": {}
+ }
+ },
+ "NETStandard.Library/2.0.0": {
+ "type": "package",
+ "dependencies": {
+ "Microsoft.NETCore.Platforms": "1.1.0"
+ },
+ "compile": {
+ "lib/netstandard1.0/_._": {}
+ },
+ "runtime": {
+ "lib/netstandard1.0/_._": {}
+ },
+ "build": {
+ "build/netstandard2.0/NETStandard.Library.targets": {}
+ }
+ },
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
+ }
+ },
+ "projectFileDependencyGroups": {
+ ".NETCoreApp,Version=v2.0": [
+ "Microsoft.NETCore.App >= 2.0.0",
+ "Newtonsoft.Json.Bson >= 1.0.2"
+ ]
+ },
+ "packageFolders": {
+ "/Users/michaelnebel/Work/playground/csharpwebapp/packages": {}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "netcoreapp2.0"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "netcoreapp2.0": {
+ "targetAlias": "netcoreapp2.0",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "netcoreapp2.0": {
+ "targetAlias": "netcoreapp2.0",
+ "dependencies": {
+ "Microsoft.NETCore.App": {
+ "suppressParent": "All",
+ "target": "Package",
+ "version": "[2.0.0, )",
+ "autoReferenced": true
+ },
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "imports": [
+ "net461",
+ "net462",
+ "net47",
+ "net471",
+ "net472",
+ "net48",
+ "net481"
+ ],
+ "assetTargetFallback": true,
+ "warn": true,
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
+}
+""";
+
+ ///
+ /// This is part of the content of the assets file that dotnet generates based on the
+ /// following project file content.
+ ///
+ ///
+ ///
+ /// netcoreapp3.1
+ /// enable
+ /// enable
+ ///
+ ///
+ ///
+ ///
+ ///
+ ///
+ private readonly string assetsNetcoreapp31 = """
+{
+ "version": 3,
+ "targets": {
+ ".NETCoreApp,Version=v3.1": {
+ "Newtonsoft.Json/12.0.1": {
+ "type": "package",
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ },
+ "Newtonsoft.Json.Bson/1.0.2": {
+ "type": "package",
+ "dependencies": {
+ "Newtonsoft.Json": "12.0.1"
+ },
+ "compile": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ },
+ "runtime": {
+ "lib/netstandard2.0/Newtonsoft.Json.Bson.dll": {
+ "related": ".pdb;.xml"
+ }
+ }
+ }
+ }
+ },
+ "projectFileDependencyGroups": {
+ ".NETCoreApp,Version=v3.1": [
+ "Newtonsoft.Json.Bson >= 1.0.2"
+ ]
+ },
+ "packageFolders": {
+ "/Users/michaelnebel/Work/playground/csharpwebapp/packages": {}
+ },
+ "project": {
+ "version": "1.0.0",
+ "restore": {
+ "projectUniqueName": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "projectName": "csharpwebapp",
+ "projectPath": "/Users/michaelnebel/Work/playground/csharpwebapp/csharpwebapp.csproj",
+ "packagesPath": "/Users/michaelnebel/Work/playground/csharpwebapp/packages",
+ "outputPath": "/Users/michaelnebel/Work/playground/csharpwebapp/obj/",
+ "projectStyle": "PackageReference",
+ "configFilePaths": [
+ "/Users/michaelnebel/.nuget/NuGet/NuGet.Config"
+ ],
+ "originalTargetFrameworks": [
+ "netcoreapp3.1"
+ ],
+ "sources": {
+ "https://api.nuget.org/v3/index.json": {}
+ },
+ "frameworks": {
+ "netcoreapp3.1": {
+ "targetAlias": "netcoreapp3.1",
+ "projectReferences": {}
+ }
+ },
+ "warningProperties": {
+ "warnAsError": [
+ "NU1605"
+ ]
+ }
+ },
+ "frameworks": {
+ "netcoreapp3.1": {
+ "targetAlias": "netcoreapp3.1",
+ "dependencies": {
+ "Newtonsoft.Json.Bson": {
+ "target": "Package",
+ "version": "[1.0.2, )"
+ }
+ },
+ "imports": [
+ "net461",
+ "net462",
+ "net47",
+ "net471",
+ "net472",
+ "net48",
+ "net481"
+ ],
+ "assetTargetFallback": true,
+ "warn": true,
+ "downloadDependencies": [
+ {
+ "name": "Microsoft.AspNetCore.App.Ref",
+ "version": "[3.1.10, 3.1.10]"
+ },
+ {
+ "name": "Microsoft.NETCore.App.Host.osx-x64",
+ "version": "[3.1.32, 3.1.32]"
+ },
+ {
+ "name": "Microsoft.NETCore.App.Ref",
+ "version": "[3.1.0, 3.1.0]"
+ }
+ ],
+ "frameworkReferences": {
+ "Microsoft.AspNetCore.App": {
+ "privateAssets": "none"
+ },
+ "Microsoft.NETCore.App": {
+ "privateAssets": "all"
+ }
+ },
+ "runtimeIdentifierGraphPath": "/Users/michaelnebel/.dotnet/sdk/7.0.102/RuntimeIdentifierGraph.json"
+ }
+ }
+ }
}
""";
}
diff --git a/csharp/ql/campaigns/Solorigate/lib/CHANGELOG.md b/csharp/ql/campaigns/Solorigate/lib/CHANGELOG.md
index e9d0229bf18..cebd2a51e84 100644
--- a/csharp/ql/campaigns/Solorigate/lib/CHANGELOG.md
+++ b/csharp/ql/campaigns/Solorigate/lib/CHANGELOG.md
@@ -1,3 +1,7 @@
+## 1.7.4
+
+No user-facing changes.
+
## 1.7.3
No user-facing changes.
diff --git a/csharp/ql/campaigns/Solorigate/lib/change-notes/released/1.7.4.md b/csharp/ql/campaigns/Solorigate/lib/change-notes/released/1.7.4.md
new file mode 100644
index 00000000000..801ed5f5e71
--- /dev/null
+++ b/csharp/ql/campaigns/Solorigate/lib/change-notes/released/1.7.4.md
@@ -0,0 +1,3 @@
+## 1.7.4
+
+No user-facing changes.
diff --git a/csharp/ql/campaigns/Solorigate/lib/codeql-pack.release.yml b/csharp/ql/campaigns/Solorigate/lib/codeql-pack.release.yml
index 9f9661b1e77..f4f3a4d5120 100644
--- a/csharp/ql/campaigns/Solorigate/lib/codeql-pack.release.yml
+++ b/csharp/ql/campaigns/Solorigate/lib/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 1.7.3
+lastReleaseVersion: 1.7.4
diff --git a/csharp/ql/campaigns/Solorigate/lib/qlpack.yml b/csharp/ql/campaigns/Solorigate/lib/qlpack.yml
index 16084717c85..c94dc8a2238 100644
--- a/csharp/ql/campaigns/Solorigate/lib/qlpack.yml
+++ b/csharp/ql/campaigns/Solorigate/lib/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/csharp-solorigate-all
-version: 1.7.3
+version: 1.7.4
groups:
- csharp
- solorigate
diff --git a/csharp/ql/campaigns/Solorigate/src/CHANGELOG.md b/csharp/ql/campaigns/Solorigate/src/CHANGELOG.md
index e9d0229bf18..cebd2a51e84 100644
--- a/csharp/ql/campaigns/Solorigate/src/CHANGELOG.md
+++ b/csharp/ql/campaigns/Solorigate/src/CHANGELOG.md
@@ -1,3 +1,7 @@
+## 1.7.4
+
+No user-facing changes.
+
## 1.7.3
No user-facing changes.
diff --git a/csharp/ql/campaigns/Solorigate/src/change-notes/released/1.7.4.md b/csharp/ql/campaigns/Solorigate/src/change-notes/released/1.7.4.md
new file mode 100644
index 00000000000..801ed5f5e71
--- /dev/null
+++ b/csharp/ql/campaigns/Solorigate/src/change-notes/released/1.7.4.md
@@ -0,0 +1,3 @@
+## 1.7.4
+
+No user-facing changes.
diff --git a/csharp/ql/campaigns/Solorigate/src/codeql-pack.release.yml b/csharp/ql/campaigns/Solorigate/src/codeql-pack.release.yml
index 9f9661b1e77..f4f3a4d5120 100644
--- a/csharp/ql/campaigns/Solorigate/src/codeql-pack.release.yml
+++ b/csharp/ql/campaigns/Solorigate/src/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 1.7.3
+lastReleaseVersion: 1.7.4
diff --git a/csharp/ql/campaigns/Solorigate/src/qlpack.yml b/csharp/ql/campaigns/Solorigate/src/qlpack.yml
index 594ce8224b3..3df278ff4b9 100644
--- a/csharp/ql/campaigns/Solorigate/src/qlpack.yml
+++ b/csharp/ql/campaigns/Solorigate/src/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/csharp-solorigate-queries
-version: 1.7.3
+version: 1.7.4
groups:
- csharp
- solorigate
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml/global.json b/csharp/ql/integration-tests/all-platforms/cshtml/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone/global.json b/csharp/ql/integration-tests/all-platforms/cshtml_standalone/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Controllers/TestController.cs b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Controllers/TestController.cs
new file mode 100644
index 00000000000..48d4b340fbf
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Controllers/TestController.cs
@@ -0,0 +1,16 @@
+namespace test;
+
+using System.Net;
+using Microsoft.AspNetCore.Mvc;
+using Microsoft.AspNetCore.Mvc.Razor;
+
+public class UserData
+{
+ public string Name { get; set; }
+}
+
+public class TestController : Controller {
+ public IActionResult Test(UserData tainted1) {
+ return View("Test", tainted1);
+ }
+}
\ No newline at end of file
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/Test/Test.cshtml b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/Test/Test.cshtml
new file mode 100644
index 00000000000..3489539fe87
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/Test/Test.cshtml
@@ -0,0 +1,8 @@
+@page
+
+@model UserData
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/_ViewImports.cshtml b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/_ViewImports.cshtml
new file mode 100644
index 00000000000..f4d0ca8def7
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/Views/_ViewImports.cshtml
@@ -0,0 +1,3 @@
+@using test
+
+@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.expected b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.expected
new file mode 100644
index 00000000000..c5e1e6db6d6
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.expected
@@ -0,0 +1 @@
+| Views/Test/Test.cshtml:7:27:7:36 | access to property Name | Controllers/TestController.cs:13:40:13:47 | tainted1 : UserData | Views/Test/Test.cshtml:7:27:7:36 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:13:40:13:47 | tainted1 : UserData | User-provided value |
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.ql b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.ql
new file mode 100644
index 00000000000..762d792b92f
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/XSS.ql
@@ -0,0 +1,21 @@
+/**
+ * @name Cross-site scripting
+ * @description Writing user input directly to a web page
+ * allows for a cross-site scripting vulnerability.
+ * @kind path-problem
+ * @problem.severity error
+ * @security-severity 6.1
+ * @precision high
+ * @id cs/web/xss
+ * @tags security
+ * external/cwe/cwe-079
+ * external/cwe/cwe-116
+ */
+
+import csharp
+import semmle.code.csharp.security.dataflow.XSSQuery
+
+// import PathGraph // exclude query predicates with output dependant on the absolute filepath the tests are run in
+from XssNode source, XssNode sink, string message
+where xssFlow(source, sink, message)
+select sink, source, sink, "$@ flows to here and " + message, source, "User-provided value"
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/cshtml.csproj b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/cshtml.csproj
new file mode 100644
index 00000000000..e580f24c65d
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/cshtml.csproj
@@ -0,0 +1,9 @@
+
+
+
+ net7.0
+ enable
+ enable
+
+
+
\ No newline at end of file
diff --git a/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/test.py b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/test.py
new file mode 100644
index 00000000000..5fa07537d4a
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/cshtml_standalone_flowsteps/test.py
@@ -0,0 +1,6 @@
+import os
+from create_database_utils import *
+
+
+os.environ['CODEQL_EXTRACTOR_CSHARP_STANDALONE_EXTRACT_WEB_VIEWS'] = 'true'
+run_codeql_database_create(lang="csharp", extra_args=["--extractor-option=buildless=true", "--extractor-option=cil=false"])
diff --git a/csharp/ql/integration-tests/all-platforms/diag_dotnet_incompatible/global.json b/csharp/ql/integration-tests/all-platforms/diag_dotnet_incompatible/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/diag_dotnet_incompatible/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/diag_missing_project_files/global.json b/csharp/ql/integration-tests/all-platforms/diag_missing_project_files/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/diag_missing_project_files/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/diag_missing_xamarin_sdk/global.json b/csharp/ql/integration-tests/all-platforms/diag_missing_xamarin_sdk/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/diag_missing_xamarin_sdk/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/diag_recursive_generics/global.json b/csharp/ql/integration-tests/all-platforms/diag_recursive_generics/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/diag_recursive_generics/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/dotnet_build/global.json b/csharp/ql/integration-tests/all-platforms/dotnet_build/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/dotnet_build/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/dotnet_no_args_inject/global.json b/csharp/ql/integration-tests/all-platforms/dotnet_no_args_inject/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/dotnet_no_args_inject/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/dotnet_pack/global.json b/csharp/ql/integration-tests/all-platforms/dotnet_pack/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/dotnet_pack/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/dotnet_publish/global.json b/csharp/ql/integration-tests/all-platforms/dotnet_publish/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/dotnet_publish/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/dotnet_run/global.json b/csharp/ql/integration-tests/all-platforms/dotnet_run/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/dotnet_run/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/all-platforms/standalone/global.json b/csharp/ql/integration-tests/all-platforms/standalone/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/all-platforms/standalone/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/posix-only/dotnet_test/global.json b/csharp/ql/integration-tests/posix-only/dotnet_test/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/posix-only/dotnet_test/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/posix-only/dotnet_test_mstest/global.json b/csharp/ql/integration-tests/posix-only/dotnet_test_mstest/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/posix-only/dotnet_test_mstest/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/posix-only/inherit-env-vars/global.json b/csharp/ql/integration-tests/posix-only/inherit-env-vars/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/posix-only/inherit-env-vars/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/posix-only/standalone_dependencies_nuget/global.json b/csharp/ql/integration-tests/posix-only/standalone_dependencies_nuget/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/posix-only/standalone_dependencies_nuget/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/integration-tests/posix-only/warn_as_error/global.json b/csharp/ql/integration-tests/posix-only/warn_as_error/global.json
new file mode 100644
index 00000000000..ed58992d1ff
--- /dev/null
+++ b/csharp/ql/integration-tests/posix-only/warn_as_error/global.json
@@ -0,0 +1,5 @@
+{
+ "sdk": {
+ "version": "7.0.102"
+ }
+}
diff --git a/csharp/ql/lib/CHANGELOG.md b/csharp/ql/lib/CHANGELOG.md
index 5109822d6b3..09826df60f4 100644
--- a/csharp/ql/lib/CHANGELOG.md
+++ b/csharp/ql/lib/CHANGELOG.md
@@ -1,3 +1,7 @@
+## 0.8.4
+
+No user-facing changes.
+
## 0.8.3
### Minor Analysis Improvements
diff --git a/csharp/ql/lib/change-notes/released/0.8.4.md b/csharp/ql/lib/change-notes/released/0.8.4.md
new file mode 100644
index 00000000000..145d3b468c8
--- /dev/null
+++ b/csharp/ql/lib/change-notes/released/0.8.4.md
@@ -0,0 +1,3 @@
+## 0.8.4
+
+No user-facing changes.
diff --git a/csharp/ql/lib/codeql-pack.release.yml b/csharp/ql/lib/codeql-pack.release.yml
index b6e46394f37..32eff3dc9f3 100644
--- a/csharp/ql/lib/codeql-pack.release.yml
+++ b/csharp/ql/lib/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 0.8.3
+lastReleaseVersion: 0.8.4
diff --git a/csharp/ql/lib/qlpack.yml b/csharp/ql/lib/qlpack.yml
index 40d0d3d81cd..1456166a62a 100644
--- a/csharp/ql/lib/qlpack.yml
+++ b/csharp/ql/lib/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/csharp-all
-version: 0.8.3
+version: 0.8.4
groups: csharp
dbscheme: semmlecode.csharp.dbscheme
extractor: csharp
diff --git a/csharp/ql/lib/semmle/code/cil/internal/SsaImpl.qll b/csharp/ql/lib/semmle/code/cil/internal/SsaImpl.qll
index 2f8fde205fd..3aafaa00baa 100644
--- a/csharp/ql/lib/semmle/code/cil/internal/SsaImpl.qll
+++ b/csharp/ql/lib/semmle/code/cil/internal/SsaImpl.qll
@@ -1,7 +1,7 @@
private import cil
private import codeql.ssa.Ssa as SsaImplCommon
-private module SsaInput implements SsaImplCommon::InputSig {
+private module SsaInput implements SsaImplCommon::InputSig {
class BasicBlock = CIL::BasicBlock;
BasicBlock getImmediateBasicBlockDominator(BasicBlock bb) { result = bb.getImmediateDominator() }
@@ -29,7 +29,7 @@ private module SsaInput implements SsaImplCommon::InputSig {
}
}
-import SsaImplCommon::Make
+import SsaImplCommon::Make
cached
private module Cached {
diff --git a/csharp/ql/lib/semmle/code/csharp/Callable.qll b/csharp/ql/lib/semmle/code/csharp/Callable.qll
index 20999215d0d..dd67d2667e3 100644
--- a/csharp/ql/lib/semmle/code/csharp/Callable.qll
+++ b/csharp/ql/lib/semmle/code/csharp/Callable.qll
@@ -105,7 +105,10 @@ class Callable extends DotNet::Callable, Parameterizable, ExprOrStmtParent, @cal
* then both `{ return 0; }` and `{ return 1; }` are statement bodies of
* `N.C.M()`.
*/
- final BlockStmt getStatementBody() { result = this.getAChildStmt() }
+ final BlockStmt getStatementBody() {
+ result = getStatementBody(this) and
+ not this.getFile().isStub()
+ }
/**
* DEPRECATED: Use `getStatementBody` instead.
@@ -143,8 +146,8 @@ class Callable extends DotNet::Callable, Parameterizable, ExprOrStmtParent, @cal
* then both `0` and `1` are expression bodies of `N.C.M()`.
*/
final Expr getExpressionBody() {
- result = this.getAChildExpr() and
- not result = this.(Constructor).getInitializer()
+ result = getExpressionBody(this) and
+ not this.getFile().isStub()
}
/** Holds if this callable has an expression body. */
diff --git a/csharp/ql/lib/semmle/code/csharp/ExprOrStmtParent.qll b/csharp/ql/lib/semmle/code/csharp/ExprOrStmtParent.qll
index 45ceeea060e..636f8061b2a 100644
--- a/csharp/ql/lib/semmle/code/csharp/ExprOrStmtParent.qll
+++ b/csharp/ql/lib/semmle/code/csharp/ExprOrStmtParent.qll
@@ -53,6 +53,20 @@ class TopLevelExprParent extends Element, @top_level_expr_parent {
private predicate hasNoSourceLocation(Element e) { not e.getALocation() instanceof SourceLocation }
+/** INTERNAL: Do not use. */
+Expr getExpressionBody(Callable c) {
+ result = c.getAChildExpr() and
+ not result = c.(Constructor).getInitializer()
+}
+
+/** INTERNAL: Do not use. */
+BlockStmt getStatementBody(Callable c) { result = c.getAChildStmt() }
+
+private ControlFlowElement getBody(Callable c) {
+ result = getExpressionBody(c) or
+ result = getStatementBody(c)
+}
+
cached
private module Cached {
cached
@@ -161,20 +175,20 @@ private module Cached {
private predicate parent(ControlFlowElement child, ExprOrStmtParent parent) {
child = getAChild(parent) and
- not child = any(Callable c).getBody()
+ not child = getBody(_)
}
/** Holds if the enclosing body of `cfe` is `body`. */
cached
predicate enclosingBody(ControlFlowElement cfe, ControlFlowElement body) {
- body = any(Callable c).getBody() and
+ body = getBody(_) and
parent*(enclosingStart(cfe), body)
}
/** Holds if the enclosing callable of `cfe` is `c`. */
cached
predicate enclosingCallable(ControlFlowElement cfe, Callable c) {
- enclosingBody(cfe, c.getBody())
+ enclosingBody(cfe, getBody(c))
or
parent*(enclosingStart(cfe), c.(Constructor).getInitializer())
}
diff --git a/csharp/ql/lib/semmle/code/csharp/File.qll b/csharp/ql/lib/semmle/code/csharp/File.qll
index 320d6e4c5d9..3e1a0ca477b 100644
--- a/csharp/ql/lib/semmle/code/csharp/File.qll
+++ b/csharp/ql/lib/semmle/code/csharp/File.qll
@@ -54,14 +54,14 @@ class File extends Container, Impl::File {
/** Holds if this file is a QL test stub file. */
pragma[noinline]
- private predicate isStub() {
+ predicate isStub() {
this.extractedQlTest() and
this.getAbsolutePath().matches("%resources/stubs/%")
}
/** Holds if this file contains source code. */
final predicate fromSource() {
- this.getExtension() = "cs" and
+ this.getExtension() = ["cs", "cshtml"] and
not this.isStub()
}
diff --git a/csharp/ql/lib/semmle/code/csharp/controlflow/internal/ControlFlowGraphImpl.qll b/csharp/ql/lib/semmle/code/csharp/controlflow/internal/ControlFlowGraphImpl.qll
index 3af8974b1d5..b6efc78e55c 100644
--- a/csharp/ql/lib/semmle/code/csharp/controlflow/internal/ControlFlowGraphImpl.qll
+++ b/csharp/ql/lib/semmle/code/csharp/controlflow/internal/ControlFlowGraphImpl.qll
@@ -13,11 +13,14 @@ private import semmle.code.csharp.commons.Compilation
/** An element that defines a new CFG scope. */
class CfgScope extends Element, @top_level_exprorstmt_parent {
CfgScope() {
- this instanceof Callable
- or
- // For now, static initializer values have their own scope. Eventually, they
- // should be treated like instance initializers.
- this.(Assignable).(Modifiable).isStatic()
+ this.getFile().fromSource() and
+ (
+ this instanceof Callable
+ or
+ // For now, static initializer values have their own scope. Eventually, they
+ // should be treated like instance initializers.
+ this.(Assignable).(Modifiable).isStatic()
+ )
}
}
diff --git a/csharp/ql/lib/semmle/code/csharp/controlflow/internal/PreSsa.qll b/csharp/ql/lib/semmle/code/csharp/controlflow/internal/PreSsa.qll
index 2c61592778a..42d9c21102a 100644
--- a/csharp/ql/lib/semmle/code/csharp/controlflow/internal/PreSsa.qll
+++ b/csharp/ql/lib/semmle/code/csharp/controlflow/internal/PreSsa.qll
@@ -36,7 +36,7 @@ module PreSsa {
scopeFirst(c, bb)
}
- module SsaInput implements SsaImplCommon::InputSig {
+ module SsaInput implements SsaImplCommon::InputSig {
class BasicBlock = PreBasicBlocks::PreBasicBlock;
BasicBlock getImmediateBasicBlockDominator(BasicBlock bb) { result.immediatelyDominates(bb) }
@@ -137,7 +137,7 @@ module PreSsa {
}
}
- private module SsaImpl = SsaImplCommon::Make;
+ private module SsaImpl = SsaImplCommon::Make;
class Definition extends SsaImpl::Definition {
final AssignableRead getARead() {
diff --git a/csharp/ql/lib/semmle/code/csharp/dataflow/FlowSummary.qll b/csharp/ql/lib/semmle/code/csharp/dataflow/FlowSummary.qll
index 92a09558946..70efa618c9a 100644
--- a/csharp/ql/lib/semmle/code/csharp/dataflow/FlowSummary.qll
+++ b/csharp/ql/lib/semmle/code/csharp/dataflow/FlowSummary.qll
@@ -168,7 +168,8 @@ private SummaryComponent delegateSelf() {
private predicate mayInvokeCallback(Callable c, int n) {
c.getParameter(n).getType() instanceof SystemLinqExpressions::DelegateExtType and
- not c.fromSource()
+ not c.hasBody() and
+ (if c instanceof Accessor then not c.fromSource() else any())
}
private class SummarizedCallableWithCallback extends SummarizedCallable {
diff --git a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/BaseSSA.qll b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/BaseSSA.qll
index cb737200a02..0933559347e 100644
--- a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/BaseSSA.qll
+++ b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/BaseSSA.qll
@@ -24,7 +24,7 @@ module BaseSsa {
)
}
- private module SsaInput implements SsaImplCommon::InputSig {
+ private module SsaInput implements SsaImplCommon::InputSig {
class BasicBlock = ControlFlow::BasicBlock;
BasicBlock getImmediateBasicBlockDominator(BasicBlock bb) {
@@ -60,7 +60,7 @@ module BaseSsa {
}
}
- private module SsaImpl = SsaImplCommon::Make;
+ private module SsaImpl = SsaImplCommon::Make;
class Definition extends SsaImpl::Definition {
final AssignableRead getARead() {
diff --git a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowDispatch.qll b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowDispatch.qll
index 0a5877d4897..a06f9a183c2 100644
--- a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowDispatch.qll
+++ b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowDispatch.qll
@@ -81,9 +81,9 @@ newtype TReturnKind =
*/
class DataFlowSummarizedCallable instanceof FlowSummary::SummarizedCallable {
DataFlowSummarizedCallable() {
- not this.fromSource()
+ not this.hasBody()
or
- this.fromSource() and not this.applyGeneratedModel()
+ this.hasBody() and not this.applyGeneratedModel()
}
string toString() { result = super.toString() }
diff --git a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowPrivate.qll b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowPrivate.qll
index fb9a0c6b13c..37b493e001f 100644
--- a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowPrivate.qll
+++ b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/DataFlowPrivate.qll
@@ -15,6 +15,7 @@ private import semmle.code.csharp.controlflow.Guards
private import semmle.code.csharp.dispatch.Dispatch
private import semmle.code.csharp.frameworks.EntityFramework
private import semmle.code.csharp.frameworks.NHibernate
+private import semmle.code.csharp.frameworks.Razor
private import semmle.code.csharp.frameworks.system.Collections
private import semmle.code.csharp.frameworks.system.threading.Tasks
private import semmle.code.cil.Ssa::Ssa as CilSsa
diff --git a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/SsaImpl.qll b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/SsaImpl.qll
index 596ddde0f55..8a1f2b5b296 100644
--- a/csharp/ql/lib/semmle/code/csharp/dataflow/internal/SsaImpl.qll
+++ b/csharp/ql/lib/semmle/code/csharp/dataflow/internal/SsaImpl.qll
@@ -6,7 +6,7 @@ import csharp
private import codeql.ssa.Ssa as SsaImplCommon
private import AssignableDefinitions
-private module SsaInput implements SsaImplCommon::InputSig {
+private module SsaInput implements SsaImplCommon::InputSig {
class BasicBlock = ControlFlow::BasicBlock;
BasicBlock getImmediateBasicBlockDominator(BasicBlock bb) { result = bb.getImmediateDominator() }
@@ -49,7 +49,7 @@ private module SsaInput implements SsaImplCommon::InputSig {
}
}
-private import SsaImplCommon::Make as Impl
+private import SsaImplCommon::Make as Impl
class Definition = Impl::Definition;
@@ -310,7 +310,12 @@ private module CallGraph {
c = any(DelegateCall dc | e = dc.getExpr()) and
libraryDelegateCall = false
or
- c.getTarget().fromLibrary() and
+ exists(Callable target |
+ target = c.getTarget() and
+ not target.hasBody()
+ |
+ if target instanceof Accessor then not target.fromSource() else any()
+ ) and
e = c.getAnArgument() and
e.getType() instanceof SystemLinqExpressions::DelegateExtType and
libraryDelegateCall = true
diff --git a/csharp/ql/lib/semmle/code/csharp/frameworks/Razor.qll b/csharp/ql/lib/semmle/code/csharp/frameworks/Razor.qll
new file mode 100644
index 00000000000..6bfa927e7c0
--- /dev/null
+++ b/csharp/ql/lib/semmle/code/csharp/frameworks/Razor.qll
@@ -0,0 +1,217 @@
+/** Provides definitions and flow steps related to Razor pages. */
+
+private import csharp
+private import codeql.util.Unit
+private import codeql.util.FilePath
+private import semmle.code.csharp.frameworks.microsoft.AspNetCore
+
+/** A call to the `View` method */
+private class ViewCall extends MethodCall {
+ ViewCall() {
+ this.getTarget().hasFullyQualifiedName("Microsoft.AspNetCore.Mvc", "Controller", "View")
+ }
+
+ /** Gets the `name` argument to this call, if any. */
+ string getNameArgument() {
+ exists(StringLiteral lit |
+ this.getTarget().getParameter(0).getType() instanceof StringType and
+ DataFlow::localExprFlow(lit, this.getArgument(0)) and
+ result = lit.getValue()
+ )
+ }
+
+ /** Gets the `model` argument to this call, if any. */
+ Expr getModelArgument() {
+ exists(int i | i in [0 .. 1] |
+ this.getTarget().getParameter(i).getType() instanceof ObjectType and
+ result = this.getArgument(i)
+ )
+ }
+
+ /** Gets the MVC action method that this call is made from, if any. */
+ Method getActionMethod() {
+ result = this.getEnclosingCallable() and
+ result = this.getController().getAnActionMethod()
+ }
+
+ /**
+ * Gets the action name that this call refers to, if any.
+ * This is either the name argument, or the name of the action method calling this if there is no name argument.
+ */
+ string getActionName() {
+ result = this.getNameArgument()
+ or
+ not exists(this.getNameArgument()) and
+ result = this.getActionMethod().getName()
+ }
+
+ /** Gets the MVC controller that this call is made from, if any. */
+ MicrosoftAspNetCoreMvcController getController() {
+ result = this.getEnclosingCallable().getDeclaringType()
+ }
+
+ /** Gets the name of the MVC controller that this call is made from, if any. */
+ string getControllerName() { result + "Controller" = this.getController().getName() }
+
+ /** Gets the name of the Area that the controller of this call belongs to, if any. */
+ string getAreaName() {
+ exists(Attribute attr |
+ attr = this.getController().getAnAttribute() and
+ attr.getType().hasFullyQualifiedName("Microsoft.AspNetCore.Mvc", "AreaAttribute") and
+ result = attr.getArgument(0).(StringLiteral).getValue()
+ )
+ }
+
+ /** `result` is `true` if this call is from a controller that is an Area, and `false` otherwise. */
+ boolean hasArea() { if exists(this.getAreaName()) then result = true else result = false }
+}
+
+/** A compiler-generated Razor page from a `.cshtml` file. */
+class RazorViewClass extends Class {
+ AssemblyAttribute attr;
+
+ RazorViewClass() {
+ exists(Class baseClass | baseClass = this.getBaseClass().getUnboundDeclaration() |
+ baseClass.hasFullyQualifiedName("Microsoft.AspNetCore.Mvc.Razor", "RazorPage`1")
+ or
+ baseClass.hasFullyQualifiedName("Microsoft.AspNetCore.Mvc.RazorPages", "Page")
+ ) and
+ attr.getFile() = this.getFile() and
+ attr.getType()
+ .hasFullyQualifiedName("Microsoft.AspNetCore.Razor.Hosting", "RazorCompiledItemAttribute")
+ }
+
+ /**
+ * Gets the filepath of the source file that this class was generated from.
+ *
+ * This is an absolute path if the database was extracted in standalone mode,
+ * and is relative to to application root (the directory containing the .csproj file) otherwise.
+ */
+ string getSourceFilepath() { result = attr.getArgument(2).(StringLiteral).getValue() }
+}
+
+/**
+ * Gets a possible prefix to be applied to view search paths to locate a Razor page.
+ * This may be empty (for the case that the generated Razor page files contain paths relative to the application root),
+ * or the absolute path of the directory containing the .csproj file (for the case that standalone extraction is used and the generated files contain absolute paths).
+ */
+private string getARazorPathPrefix() {
+ result = ""
+ or
+ exists(File csproj |
+ csproj.getExtension() = "csproj" and
+ // possibly prepend '/' to match Windows absolute paths starting with `C:/` with paths appearing in the Razor file in standalone mode starting with `/C:/`
+ result = ["/", ""] + csproj.getParentContainer().getAbsolutePath()
+ )
+}
+
+private class ViewCallJumpNode extends DataFlow::NonLocalJumpNode {
+ RazorViewClass rp;
+
+ ViewCallJumpNode() {
+ exists(ViewCall vc |
+ viewCallRefersToPage(vc, rp) and
+ this.asExpr() = vc.getModelArgument()
+ )
+ }
+
+ override DataFlow::Node getAJumpSuccessor(boolean preservesValue) {
+ preservesValue = true and
+ exists(PropertyAccess modelProp |
+ result.asExpr() = modelProp and
+ modelProp.getTarget().hasName("Model") and
+ modelProp.getEnclosingCallable().getDeclaringType() = rp
+ )
+ }
+}
+
+private predicate viewCallRefersToPage(ViewCall vc, RazorViewClass rp) {
+ viewCallRefersToPageAbsolute(vc, rp) or
+ viewCallRefersToPageRelative(vc, rp)
+}
+
+bindingset[path]
+private string stripTilde(string path) { result = path.regexpReplaceAll("^~/", "/") }
+
+private predicate viewCallRefersToPageAbsolute(ViewCall vc, RazorViewClass rp) {
+ getARazorPathPrefix() + ["/", ""] + stripTilde(vc.getNameArgument()) = rp.getSourceFilepath()
+}
+
+private predicate viewCallRefersToPageRelative(ViewCall vc, RazorViewClass rp) {
+ rp = min(int i, RazorViewClass rp2 | matchesViewCallWithIndex(vc, rp2, i) | rp2 order by i)
+}
+
+private predicate matchesViewCallWithIndex(ViewCall vc, RazorViewClass rp, int i) {
+ exists(RelativeViewCallFilepath fp |
+ fp.hasViewCallWithIndex(vc, i) and
+ getARazorPathPrefix() + fp.getNormalizedPath() = rp.getSourceFilepath()
+ )
+}
+
+/** Gets the `i`th template for view discovery. */
+private string getViewSearchTemplate(int i, boolean isArea) {
+ i = 0 and result = "/Areas/{2}/Views/{1}/{0}.cshtml" and isArea = true
+ or
+ i = 1 and result = "/Areas/{2}/Views/Shared/{0}.cshtml" and isArea = true
+ or
+ i = 2 and result = "/Views/{1}/{0}.cshtml" and isArea = false
+ or
+ i = 3 and result = "/Views/Shared/{0}.cshtml" and isArea = [true, false]
+ or
+ i = 4 and result = "/Pages/Shared/{0}.cshtml" and isArea = true
+ or
+ i = 5 and result = getAViewSearchTemplateInCode(isArea)
+}
+
+/** Gets an additional template used for view discovery defined in code. */
+private string getAViewSearchTemplateInCode(boolean isArea) {
+ exists(StringLiteral str, MethodCall addCall |
+ addCall.getTarget().hasName("Add") and
+ DataFlow::localExprFlow(str, addCall.getArgument(0)) and
+ addCall.getQualifier() = getAViewLocationList(isArea) and
+ result = str.getValue()
+ )
+}
+
+/** Gets a list expression containing view search locations */
+private Expr getAViewLocationList(boolean isArea) {
+ exists(string name |
+ result
+ .(PropertyRead)
+ .getProperty()
+ .hasFullyQualifiedName("Microsoft.AspNetCore.Mvc.Razor", "RazorViewEngineOptions", name)
+ |
+ name = "ViewLocationFormats" and isArea = false
+ or
+ name = "AreaViewLocationFormats" and isArea = true
+ // PageViewLocationFormats and AreaPageViewLocationFormats are used for calls within a page rather than a controller
+ )
+}
+
+/** A filepath that should be searched for a View call. */
+private class RelativeViewCallFilepath extends NormalizableFilepath {
+ ViewCall vc_;
+ int idx_;
+
+ RelativeViewCallFilepath() {
+ exists(string template, string sub2, string sub1, string sub0 |
+ template = getViewSearchTemplate(idx_, vc_.hasArea())
+ |
+ (
+ if template.matches("%{2}%")
+ then sub2 = template.replaceAll("{2}", vc_.getAreaName())
+ else sub2 = template
+ ) and
+ (
+ if template.matches("%{1}%")
+ then sub1 = sub2.replaceAll("{1}", vc_.getControllerName())
+ else sub1 = sub2
+ ) and
+ sub0 = sub1.replaceAll("{0}", vc_.getActionName()) and
+ this = stripTilde(sub0)
+ )
+ }
+
+ /** Holds if this string is the `idx`th path that will be searched for the `vc` call. */
+ predicate hasViewCallWithIndex(ViewCall vc, int idx) { vc = vc_ and idx = idx_ }
+}
diff --git a/csharp/ql/lib/semmle/code/csharp/security/dataflow/flowsinks/ExternalLocationSink.qll b/csharp/ql/lib/semmle/code/csharp/security/dataflow/flowsinks/ExternalLocationSink.qll
index 03f8bd42715..abd1ad92733 100644
--- a/csharp/ql/lib/semmle/code/csharp/security/dataflow/flowsinks/ExternalLocationSink.qll
+++ b/csharp/ql/lib/semmle/code/csharp/security/dataflow/flowsinks/ExternalLocationSink.qll
@@ -27,8 +27,9 @@ private class ExternalModelSink extends ExternalLocationSink {
*/
class LogMessageSink extends ExternalLocationSink {
LogMessageSink() {
- this.getExpr() = any(LoggerType i).getAMethod().getACall().getAnArgument()
- or
+ this.getExpr() = any(LoggerType i).getAMethod().getACall().getAnArgument() or
+ this.getExpr() =
+ any(MethodCall call | call.getQualifier().getType() instanceof LoggerType).getAnArgument() or
this.getExpr() =
any(ExtensionMethodCall call |
call.getTarget().(ExtensionMethod).getExtendedType() instanceof LoggerType
diff --git a/csharp/ql/src/CHANGELOG.md b/csharp/ql/src/CHANGELOG.md
index 6cc567b98de..06f83675355 100644
--- a/csharp/ql/src/CHANGELOG.md
+++ b/csharp/ql/src/CHANGELOG.md
@@ -1,3 +1,9 @@
+## 0.8.4
+
+### Minor Analysis Improvements
+
+* Modelled additional flow steps to track flow from a `View` call in an MVC controller to the corresponding Razor View (`.cshtml`) file, which may result in additional results for queries such as `cs/web/xss`.
+
## 0.8.3
### Minor Analysis Improvements
diff --git a/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql b/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql
index 06129ec88ec..006874d93bd 100644
--- a/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql
+++ b/csharp/ql/src/Security Features/CWE-639/InsecureDirectObjectReference.ql
@@ -8,7 +8,7 @@
* @precision medium
* @id cs/web/insecure-direct-object-reference
* @tags security
- * external/cwe-639
+ * external/cwe/cwe-639
*/
import csharp
diff --git a/csharp/ql/src/Security Features/InsecureRandomness.qhelp b/csharp/ql/src/Security Features/InsecureRandomness.qhelp
index b0fe5a5513e..6f9634643ec 100644
--- a/csharp/ql/src/Security Features/InsecureRandomness.qhelp
+++ b/csharp/ql/src/Security Features/InsecureRandomness.qhelp
@@ -29,11 +29,6 @@ number generator. Random is not cryptographically secure, and shoul
security contexts. For contexts which are not security sensitive, Random may be
preferable as it has a more convenient interface, and is likely to be faster.
-
-For the specific use-case of generating passwords, consider
-System.Web.Security.Membership.GeneratePassword, which provides a cryptographically
-secure method of generating random passwords.
-
@@ -54,10 +49,7 @@ purpose. In this case, it is much harder to predict the generated integers.
In the final example, the password is generated using the Membership.GeneratePassword
-library method, which uses a cryptographically secure random number generator to generate a random
-series of characters. This method should be preferred when generating passwords, if possible, as it
-avoids potential pitfalls when converting the output of a random number generator (usually an int or
-a byte) to a series of permitted characters.
+library method, which generates a password with a bias, therefore should be avoided.
diff --git a/csharp/ql/src/change-notes/released/0.8.4.md b/csharp/ql/src/change-notes/released/0.8.4.md
new file mode 100644
index 00000000000..56259c2d6bc
--- /dev/null
+++ b/csharp/ql/src/change-notes/released/0.8.4.md
@@ -0,0 +1,5 @@
+## 0.8.4
+
+### Minor Analysis Improvements
+
+* Modelled additional flow steps to track flow from a `View` call in an MVC controller to the corresponding Razor View (`.cshtml`) file, which may result in additional results for queries such as `cs/web/xss`.
diff --git a/csharp/ql/src/codeql-pack.release.yml b/csharp/ql/src/codeql-pack.release.yml
index b6e46394f37..32eff3dc9f3 100644
--- a/csharp/ql/src/codeql-pack.release.yml
+++ b/csharp/ql/src/codeql-pack.release.yml
@@ -1,2 +1,2 @@
---
-lastReleaseVersion: 0.8.3
+lastReleaseVersion: 0.8.4
diff --git a/csharp/ql/src/experimental/Security Features/CWE-759/HashWithoutSalt.ql b/csharp/ql/src/experimental/Security Features/CWE-759/HashWithoutSalt.ql
index b478699c2cf..f9c279e09bf 100644
--- a/csharp/ql/src/experimental/Security Features/CWE-759/HashWithoutSalt.ql
+++ b/csharp/ql/src/experimental/Security Features/CWE-759/HashWithoutSalt.ql
@@ -6,7 +6,7 @@
* @id cs/hash-without-salt
* @tags security
* experimental
- * external/cwe-759
+ * external/cwe/cwe-759
*/
import csharp
diff --git a/csharp/ql/src/qlpack.yml b/csharp/ql/src/qlpack.yml
index 21d66abf3cf..3ea01233aae 100644
--- a/csharp/ql/src/qlpack.yml
+++ b/csharp/ql/src/qlpack.yml
@@ -1,5 +1,5 @@
name: codeql/csharp-queries
-version: 0.8.3
+version: 0.8.4
groups:
- csharp
- queries
diff --git a/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.cs b/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.cs
index 7a0e896e54d..bc49805fc04 100644
--- a/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.cs
+++ b/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.cs
@@ -185,16 +185,16 @@ namespace My.Qltest
void M1()
{
var o = new object();
- Sink(GeneratedFlow(o));
+ Sink(GeneratedFlow(o)); // no flow because the modelled method exists in source code
}
void M2()
{
var o1 = new object();
- Sink(GeneratedFlowArgs(o1, null));
+ Sink(GeneratedFlowArgs(o1, null)); // no flow because the modelled method exists in source code
var o2 = new object();
- Sink(GeneratedFlowArgs(null, o2));
+ Sink(GeneratedFlowArgs(null, o2)); // no flow because the modelled method exists in source code
}
void M3()
diff --git a/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.expected b/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.expected
index c69a86a5cb3..34849ad7014 100644
--- a/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.expected
+++ b/csharp/ql/test/library-tests/dataflow/external-models/ExternalFlow.expected
@@ -61,12 +61,6 @@ edges
| ExternalFlow.cs:118:21:118:30 | call to method Reverse : null [element] : Object | ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object |
| ExternalFlow.cs:118:29:118:29 | access to local variable a : null [element] : Object | ExternalFlow.cs:118:21:118:30 | call to method Reverse : null [element] : Object |
| ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object | ExternalFlow.cs:120:18:120:21 | access to array element |
-| ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | ExternalFlow.cs:188:32:188:32 | access to local variable o : Object |
-| ExternalFlow.cs:188:32:188:32 | access to local variable o : Object | ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow |
-| ExternalFlow.cs:193:22:193:33 | object creation of type Object : Object | ExternalFlow.cs:194:36:194:37 | access to local variable o1 : Object |
-| ExternalFlow.cs:194:36:194:37 | access to local variable o1 : Object | ExternalFlow.cs:194:18:194:44 | call to method GeneratedFlowArgs |
-| ExternalFlow.cs:196:22:196:33 | object creation of type Object : Object | ExternalFlow.cs:197:42:197:43 | access to local variable o2 : Object |
-| ExternalFlow.cs:197:42:197:43 | access to local variable o2 : Object | ExternalFlow.cs:197:18:197:44 | call to method GeneratedFlowArgs |
| ExternalFlow.cs:205:22:205:33 | object creation of type Object : Object | ExternalFlow.cs:206:38:206:39 | access to local variable o2 : Object |
| ExternalFlow.cs:206:38:206:39 | access to local variable o2 : Object | ExternalFlow.cs:206:18:206:40 | call to method MixedFlowArgs |
| ExternalFlow.cs:231:21:231:28 | object creation of type HC : HC | ExternalFlow.cs:232:21:232:21 | access to local variable h : HC |
@@ -151,15 +145,6 @@ nodes
| ExternalFlow.cs:118:29:118:29 | access to local variable a : null [element] : Object | semmle.label | access to local variable a : null [element] : Object |
| ExternalFlow.cs:120:18:120:18 | access to local variable b : null [element] : Object | semmle.label | access to local variable b : null [element] : Object |
| ExternalFlow.cs:120:18:120:21 | access to array element | semmle.label | access to array element |
-| ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
-| ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow | semmle.label | call to method GeneratedFlow |
-| ExternalFlow.cs:188:32:188:32 | access to local variable o : Object | semmle.label | access to local variable o : Object |
-| ExternalFlow.cs:193:22:193:33 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
-| ExternalFlow.cs:194:18:194:44 | call to method GeneratedFlowArgs | semmle.label | call to method GeneratedFlowArgs |
-| ExternalFlow.cs:194:36:194:37 | access to local variable o1 : Object | semmle.label | access to local variable o1 : Object |
-| ExternalFlow.cs:196:22:196:33 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
-| ExternalFlow.cs:197:18:197:44 | call to method GeneratedFlowArgs | semmle.label | call to method GeneratedFlowArgs |
-| ExternalFlow.cs:197:42:197:43 | access to local variable o2 : Object | semmle.label | access to local variable o2 : Object |
| ExternalFlow.cs:205:22:205:33 | object creation of type Object : Object | semmle.label | object creation of type Object : Object |
| ExternalFlow.cs:206:18:206:40 | call to method MixedFlowArgs | semmle.label | call to method MixedFlowArgs |
| ExternalFlow.cs:206:38:206:39 | access to local variable o2 : Object | semmle.label | access to local variable o2 : Object |
@@ -189,8 +174,5 @@ subpaths
| ExternalFlow.cs:104:18:104:25 | access to field Field | ExternalFlow.cs:98:24:98:35 | object creation of type Object : Object | ExternalFlow.cs:104:18:104:25 | access to field Field | $@ | ExternalFlow.cs:98:24:98:35 | object creation of type Object : Object | object creation of type Object : Object |
| ExternalFlow.cs:112:18:112:25 | access to property MyProp | ExternalFlow.cs:111:24:111:35 | object creation of type Object : Object | ExternalFlow.cs:112:18:112:25 | access to property MyProp | $@ | ExternalFlow.cs:111:24:111:35 | object creation of type Object : Object | object creation of type Object : Object |
| ExternalFlow.cs:120:18:120:21 | access to array element | ExternalFlow.cs:117:36:117:47 | object creation of type Object : Object | ExternalFlow.cs:120:18:120:21 | access to array element | $@ | ExternalFlow.cs:117:36:117:47 | object creation of type Object : Object | object creation of type Object : Object |
-| ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow | ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | ExternalFlow.cs:188:18:188:33 | call to method GeneratedFlow | $@ | ExternalFlow.cs:187:21:187:32 | object creation of type Object : Object | object creation of type Object : Object |
-| ExternalFlow.cs:194:18:194:44 | call to method GeneratedFlowArgs | ExternalFlow.cs:193:22:193:33 | object creation of type Object : Object | ExternalFlow.cs:194:18:194:44 | call to method GeneratedFlowArgs | $@ | ExternalFlow.cs:193:22:193:33 | object creation of type Object : Object | object creation of type Object : Object |
-| ExternalFlow.cs:197:18:197:44 | call to method GeneratedFlowArgs | ExternalFlow.cs:196:22:196:33 | object creation of type Object : Object | ExternalFlow.cs:197:18:197:44 | call to method GeneratedFlowArgs | $@ | ExternalFlow.cs:196:22:196:33 | object creation of type Object : Object | object creation of type Object : Object |
| ExternalFlow.cs:206:18:206:40 | call to method MixedFlowArgs | ExternalFlow.cs:205:22:205:33 | object creation of type Object : Object | ExternalFlow.cs:206:18:206:40 | call to method MixedFlowArgs | $@ | ExternalFlow.cs:205:22:205:33 | object creation of type Object : Object | object creation of type Object : Object |
| ExternalFlow.cs:233:18:233:18 | access to local variable o | ExternalFlow.cs:231:21:231:28 | object creation of type HC : HC | ExternalFlow.cs:233:18:233:18 | access to local variable o | $@ | ExternalFlow.cs:231:21:231:28 | object creation of type HC : HC | object creation of type HC : HC |
diff --git a/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.expected b/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.expected
new file mode 100644
index 00000000000..8c4346f7832
--- /dev/null
+++ b/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.expected
@@ -0,0 +1,8 @@
+#select
+| standalone.cs:20:20:20:20 | access to parameter s | standalone.cs:20:20:20:20 | access to parameter s |
+| standalone.cs:25:28:25:32 | "abc" | standalone.cs:25:28:25:32 | "abc" |
+compilationErrors
+| standalone.cs:16:12:16:18 | CS0104: 'ILogger' is an ambiguous reference between 'A.ILogger' and 'B.ILogger' |
+methodCalls
+| standalone.cs:20:9:20:21 | call to method |
+| standalone.cs:25:9:25:33 | call to method |
diff --git a/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.ql b/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.ql
new file mode 100644
index 00000000000..3ffef6704dd
--- /dev/null
+++ b/csharp/ql/test/library-tests/standalone/externalLocationSink/externalLocationSink.ql
@@ -0,0 +1,10 @@
+import semmle.code.csharp.security.dataflow.flowsinks.ExternalLocationSink
+import semmle.code.csharp.commons.Diagnostics
+
+from ExternalLocationSink sink
+where sink.getLocation().getFile().fromSource()
+select sink, sink.getExpr()
+
+query predicate compilationErrors(CompilerError e) { any() }
+
+query predicate methodCalls(MethodCall m) { any() }
diff --git a/csharp/ql/test/library-tests/standalone/externalLocationSink/options b/csharp/ql/test/library-tests/standalone/externalLocationSink/options
new file mode 100644
index 00000000000..7ba3811b2af
--- /dev/null
+++ b/csharp/ql/test/library-tests/standalone/externalLocationSink/options
@@ -0,0 +1 @@
+semmle-extractor-options: --standalone
diff --git a/csharp/ql/test/library-tests/standalone/externalLocationSink/standalone.cs b/csharp/ql/test/library-tests/standalone/externalLocationSink/standalone.cs
new file mode 100644
index 00000000000..13d54e2c80a
--- /dev/null
+++ b/csharp/ql/test/library-tests/standalone/externalLocationSink/standalone.cs
@@ -0,0 +1,27 @@
+using A;
+using B;
+
+namespace A
+{
+ public interface ILogger { }
+}
+
+namespace B
+{
+ public interface ILogger { }
+}
+
+public class C
+{
+ public ILogger logger;
+
+ private void M(string s)
+ {
+ logger.Log(s);
+ }
+
+ private static void Main()
+ {
+ new C().logger.Log("abc");
+ }
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Shared/Test18.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Shared/Test18.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Shared/Test18.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Test4/Test17.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Test4/Test17.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Areas/TestArea/Views/Test4/Test17.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Controllers/TestController.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Controllers/TestController.cs
new file mode 100644
index 00000000000..001c83b9f34
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Controllers/TestController.cs
@@ -0,0 +1,155 @@
+namespace test;
+
+using System.Net;
+using Microsoft.AspNetCore.Mvc;
+using Microsoft.AspNetCore.Mvc.Razor;
+
+public class UserData
+{
+ public string Name { get; set; }
+}
+
+public class TestController : Controller {
+ public IActionResult test1(UserData tainted1) {
+ // Expected to find file /Views/Test/Test1.cshtml
+ return View("Test1", tainted1);
+ }
+
+ public IActionResult test2(UserData tainted2) {
+ // Expected to find file /Views/Shared/Test2.cshtml
+ return View("Test2", tainted2);
+ }
+
+ public IActionResult test3(UserData tainted3) {
+ // Expected to find file /Views/Test/Test3.cshtml and NOT /Views/Shared/Test3.cshtml
+ return View("Test3", tainted3);
+ }
+
+ public IActionResult test4(UserData tainted4) {
+ // Expected to find file /Views/Test/Test4.cshtml
+ return View("./Test4", tainted4);
+ }
+
+ public IActionResult test5(UserData tainted5) {
+ // Expected to find file /Views/Other/Test5.cshtml
+ return View("../Other/Test5", tainted5);
+ }
+
+ public IActionResult test6(UserData tainted6) {
+ // Expected to find file /Views/Other/Test6.cshtml
+ return View("../../Views/.////Shared/../Other//Test6", tainted6);
+ }
+
+ public IActionResult Test7(UserData tainted7) {
+ // Expected to find file /Views/Test/Test7.cshtml
+ return View(tainted7);
+ }
+
+ public IActionResult test8(UserData tainted8) {
+ // Expected to find file /Views/Other/Test8.cshtml
+ return View("/Views/Other/Test8.cshtml", tainted8);
+ }
+
+ public IActionResult test9(UserData tainted9) {
+ // Expected to find file /Views/Test/Test9.cshtml
+ return View("~/Views/Other/Test9.cshtml", tainted9);
+ }
+}
+
+public class Test2Controller : Controller {
+ public IActionResult test10(UserData tainted10) {
+ // Expected to find file /Views/Test2/Test10.cshtml
+ return View("Test10", tainted10);
+ }
+
+ public IActionResult test11(UserData tainted11) {
+ // Expected to find file /Views/Test2/Test10.cshtml
+ return helper(tainted11);
+ }
+
+ private IActionResult helper(UserData x) { return View("Test11", x); }
+
+ public IActionResult Test12(UserData tainted12) {
+ // Expected to find nothing.
+ return helper2(tainted12);
+ }
+
+ private IActionResult helper2(UserData x) {
+ return View(x);
+ }
+
+ public IActionResult test13(UserData tainted13) {
+ // Expected to find file /Views/Other/Test13.cshtml.
+ return Helper.helper3(this, tainted13);
+ }
+
+ public IActionResult test14(UserData tainted14) {
+ // Expected to find file /Views/Shared/Test14.cshtml and NOT /Views/Test2/Test14.cshtml
+ return Helper.helper4(this, tainted14);
+ }
+
+}
+
+class Helper {
+ public static IActionResult helper3(Controller c, UserData x) { return c.View("/Views/Other/Test13.cshtml", x); }
+
+ public static IActionResult helper4(Controller c, UserData x) { return c.View("Test14", x); }
+}
+
+public class Test3Controller : Controller {
+ public void Setup(RazorViewEngineOptions o) {
+ o.ViewLocationFormats.Add("/Views/Custom/{1}/{0}.cshtml");
+ o.ViewLocationFormats.Add("~/Views/Custom2/{0}.cshtml");
+ o.AreaViewLocationFormats.Add("/MyAreas/{2}/{1}/{0}.cshtml");
+ }
+
+ public IActionResult Test15(UserData tainted15) {
+ // Expected to find file /Views/Custom/Test3/Test15.cshtml
+ return View(tainted15);
+ }
+
+ public IActionResult test16(UserData tainted16) {
+ // Expected to find file /Views/Custom2/Test16.cshtml
+ return View("Test16", tainted16);
+ }
+}
+
+[Area("TestArea")]
+public class Test4Controller : Controller {
+ public IActionResult test17(UserData tainted17) {
+ // Expected to find file /Areas/TestArea/Views/Test4/Test17.cshtml
+ return View("Test17", tainted17);
+ }
+
+ public IActionResult test18(UserData tainted18) {
+ // Expected to find file /Areas/TestArea/Views/Shared/Test17.cshtml
+ return View("Test18", tainted18);
+ }
+
+ public IActionResult test19(UserData tainted19) {
+ // Expected to find file /Views/Shared/Test19.cshtml
+ return View("Test19", tainted19);
+ }
+
+ public IActionResult test20(UserData tainted20) {
+ // Expected to find nothing (and NOT /Views/Test4/Test20.cshtml).
+ return View("Test20", tainted20);
+ }
+
+ public IActionResult test21(UserData tainted21) {
+ // Expected to find file /Pages/Shared/Test21.cshtml
+ return View("Test21", tainted21);
+ }
+
+ public IActionResult test22(UserData tainted22) {
+ // Expected to find file /MyAreas/TestArea/Test4/Test22.cshtml
+ return View("Test22", tainted22);
+ }
+
+ public IActionResult test23(string tainted23) {
+ // Expected to find file /Views/Shared/Test23.cshtml
+ UserData x = new UserData();
+ x.Name = tainted23;
+ return View("Test23", x);
+ }
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Shared_Test18.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Shared_Test18.cshtml.g.cs
new file mode 100644
index 00000000000..eecb00361d6
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Shared_Test18.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Areas_TestArea_Views_Shared_Test18), @"mvc.1.0.view", @"/Areas/TestArea/Views/Shared/Test18.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Areas/TestArea/Views/Shared/Test18.cshtml")]
+ public class Areas_TestArea_Views_Shared_Test18 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Areas/TestArea/Views/Shared/Test18.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Areas/TestArea/Views/Shared/Test18.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Areas/TestArea/Views/Shared/Test18.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Test4_Test17.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Test4_Test17.cshtml.g.cs
new file mode 100644
index 00000000000..ee7ee811920
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Areas_TestArea_Views_Test4_Test17.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Areas_TestArea_Views_Test4_Test17), @"mvc.1.0.view", @"/Areas/TestArea/Views/Test4/Test17.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Areas/TestArea/Views/Test4/Test17.cshtml")]
+ public class Areas_TestArea_Views_Test4_Test17 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Areas/TestArea/Views/Test4/Test17.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Areas/TestArea/Views/Test4/Test17.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Areas/TestArea/Views/Test4/Test17.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/MyAreas_Test4_Test22.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/MyAreas_Test4_Test22.cshtml.g.cs
new file mode 100644
index 00000000000..f8b2ecde53a
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/MyAreas_Test4_Test22.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.MyAreas_Test4_Test22), @"mvc.1.0.view", @"/MyAreas/Test4/Test22.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/MyAreas/Test4/Test22.cshtml")]
+ public class MyAreas_Test4_Test22 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "MyAreas/Test4/Test22.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "MyAreas/Test4/Test22.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "MyAreas/Test4/Test22.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Pages_Shared_Test21.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Pages_Shared_Test21.cshtml.g.cs
new file mode 100644
index 00000000000..483df5af705
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Pages_Shared_Test21.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Pages_Shared_Test21), @"mvc.1.0.view", @"/Pages/Shared/Test21.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Pages/Shared/Test21.cshtml")]
+ public class Pages_Shared_Test21 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Pages/Shared/Test21.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Pages/Shared/Test21.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Pages/Shared/Test21.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Template.g b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Template.g
new file mode 100644
index 00000000000..1f283c9e3a0
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Template.g
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.$PATHUNDER), @"mvc.1.0.view", @"/$PATHSLASH")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/$PATHSLASH")]
+ public class $PATHUNDER : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "$PATHSLASH"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "$PATHSLASH"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "$PATHSLASH"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom2_Test16.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom2_Test16.cshtml.g.cs
new file mode 100644
index 00000000000..c6048503384
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom2_Test16.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Custom2_Test16), @"mvc.1.0.view", @"/Views/Custom2/Test16.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Custom2/Test16.cshtml")]
+ public class Views_Custom2_Test16 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Custom2/Test16.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Custom2/Test16.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Custom2/Test16.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom_Test3_Test15.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom_Test3_Test15.cshtml.g.cs
new file mode 100644
index 00000000000..00edb1f4b8c
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Custom_Test3_Test15.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Custom_Test3_Test15), @"mvc.1.0.view", @"/Views/Custom/Test3/Test15.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Custom/Test3/Test15.cshtml")]
+ public class Views_Custom_Test3_Test15 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Custom/Test3/Test15.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Custom/Test3/Test15.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Custom/Test3/Test15.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test13.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test13.cshtml.g.cs
new file mode 100644
index 00000000000..ad153243a9d
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test13.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Other_Test13), @"mvc.1.0.view", @"/Views/Other/Test13.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Other/Test13.cshtml")]
+ public class Views_Other_Test13 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Other/Test13.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Other/Test13.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Other/Test13.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test5.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test5.cshtml.g.cs
new file mode 100644
index 00000000000..8b6dcfa243b
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test5.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Other_Test5), @"mvc.1.0.view", @"/Views/Other/Test5.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Other/Test5.cshtml")]
+ public class Views_Other_Test5 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Other/Test5.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Other/Test5.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Other/Test5.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test6.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test6.cshtml.g.cs
new file mode 100644
index 00000000000..58aa308379b
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test6.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Other_Test6), @"mvc.1.0.view", @"/Views/Other/Test6.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Other/Test6.cshtml")]
+ public class Views_Other_Test6 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Other/Test6.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Other/Test6.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Other/Test6.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test8.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test8.cshtml.g.cs
new file mode 100644
index 00000000000..799e7a84768
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test8.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Other_Test8), @"mvc.1.0.view", @"/Views/Other/Test8.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Other/Test8.cshtml")]
+ public class Views_Other_Test8 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Other/Test8.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Other/Test8.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Other/Test8.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test9.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test9.cshtml.g.cs
new file mode 100644
index 00000000000..9c1199c2ee3
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Other_Test9.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Other_Test9), @"mvc.1.0.view", @"/Views/Other/Test9.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Other/Test9.cshtml")]
+ public class Views_Other_Test9 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Other/Test9.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Other/Test9.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Other/Test9.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test12.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test12.cshtml.g.cs
new file mode 100644
index 00000000000..6292047ecec
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test12.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test12), @"mvc.1.0.view", @"/Views/Shared/Test12.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test12.cshtml")]
+ public class Views_Shared_Test12 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test12.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test12.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test12.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test14.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test14.cshtml.g.cs
new file mode 100644
index 00000000000..93cb009780f
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test14.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test14), @"mvc.1.0.view", @"/Views/Shared/Test14.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test14.cshtml")]
+ public class Views_Shared_Test14 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test14.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test14.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test14.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test19.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test19.cshtml.g.cs
new file mode 100644
index 00000000000..daacf56a1f1
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test19.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test19), @"mvc.1.0.view", @"/Views/Shared/Test19.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test19.cshtml")]
+ public class Views_Shared_Test19 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test19.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test19.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test19.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test2.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test2.cshtml.g.cs
new file mode 100644
index 00000000000..c20f1456c06
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test2.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test2), @"mvc.1.0.view", @"/Views/Shared/Test2.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test2.cshtml")]
+ public class Views_Shared_Test2 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test2.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test2.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test2.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test23.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test23.cshtml.g.cs
new file mode 100644
index 00000000000..919c874680b
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test23.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test23), @"mvc.1.0.view", @"/Views/Shared/Test23.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test23.cshtml")]
+ public class Views_Shared_Test23 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test23.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test23.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test23.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test3.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test3.cshtml.g.cs
new file mode 100644
index 00000000000..7bd08d8665b
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Shared_Test3.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Shared_Test3), @"mvc.1.0.view", @"/Views/Shared/Test3.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Shared/Test3.cshtml")]
+ public class Views_Shared_Test3 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Shared/Test3.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Shared/Test3.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Shared/Test3.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test1.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test1.cshtml.g.cs
new file mode 100644
index 00000000000..a4dec53b632
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test1.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test1), @"mvc.1.0.view", @"/Views/Test2/Test1.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test1.cshtml")]
+ public class Views_Test2_Test1 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test1.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test1.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test1.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test10.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test10.cshtml.g.cs
new file mode 100644
index 00000000000..33a4d27e254
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test10.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test10), @"mvc.1.0.view", @"/Views/Test2/Test10.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test10.cshtml")]
+ public class Views_Test2_Test10 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test10.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test10.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test10.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test11.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test11.cshtml.g.cs
new file mode 100644
index 00000000000..da0b0a9c162
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test11.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test11), @"mvc.1.0.view", @"/Views/Test2/Test11.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test11.cshtml")]
+ public class Views_Test2_Test11 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test11.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test11.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test11.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test12.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test12.cshtml.g.cs
new file mode 100644
index 00000000000..023daa7b03e
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test12.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test12), @"mvc.1.0.view", @"/Views/Test2/Test12.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test12.cshtml")]
+ public class Views_Test2_Test12 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test12.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test12.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test12.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test14.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test14.cshtml.g.cs
new file mode 100644
index 00000000000..28b0ab8ee3f
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test14.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test14), @"mvc.1.0.view", @"/Views/Test2/Test14.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test14.cshtml")]
+ public class Views_Test2_Test14 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test14.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test14.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test14.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test2.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test2.cshtml.g.cs
new file mode 100644
index 00000000000..53c7e6eed47
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test2.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test2), @"mvc.1.0.view", @"/Views/Test2/Test2.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test2.cshtml")]
+ public class Views_Test2_Test2 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test2.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test2.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test2.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test3.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test3.cshtml.g.cs
new file mode 100644
index 00000000000..299f6f89a16
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test2_Test3.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test2_Test3), @"mvc.1.0.view", @"/Views/Test2/Test3.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test2/Test3.cshtml")]
+ public class Views_Test2_Test3 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test2/Test3.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test2/Test3.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test2/Test3.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test4_Test20.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test4_Test20.cshtml.g.cs
new file mode 100644
index 00000000000..814a81a5b5d
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test4_Test20.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test4_Test20), @"mvc.1.0.view", @"/Views/Test4/Test20.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test4/Test20.cshtml")]
+ public class Views_Test4_Test20 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test4/Test20.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test4/Test20.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test4/Test20.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test1.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test1.cshtml.g.cs
new file mode 100644
index 00000000000..2ad66b7a032
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test1.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test_Test1), @"mvc.1.0.view", @"/Views/Test/Test1.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test/Test1.cshtml")]
+ public class Views_Test_Test1 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test/Test1.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test/Test1.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test/Test1.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test3.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test3.cshtml.g.cs
new file mode 100644
index 00000000000..95ef158286b
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test3.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test_Test3), @"mvc.1.0.view", @"/Views/Test/Test3.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test/Test3.cshtml")]
+ public class Views_Test_Test3 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test/Test3.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test/Test3.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test/Test3.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test4.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test4.cshtml.g.cs
new file mode 100644
index 00000000000..7a8cea221f7
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test4.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test_Test4), @"mvc.1.0.view", @"/Views/Test/Test4.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test/Test4.cshtml")]
+ public class Views_Test_Test4 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test/Test4.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test/Test4.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test/Test4.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test7.cshtml.g.cs b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test7.cshtml.g.cs
new file mode 100644
index 00000000000..1eef0024c7a
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Generated/Views_Test_Test7.cshtml.g.cs
@@ -0,0 +1,74 @@
+// A test file that mimics the output of compiling a `.cshtml` file
+//
+#pragma warning disable 1591
+[assembly: global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemAttribute(typeof(test.Views.Views_Test_Test7), @"mvc.1.0.view", @"/Views/Test/Test7.cshtml")]
+namespace test.Views
+{
+ #line hidden
+ using System;
+ using System.Collections.Generic;
+ using System.Linq;
+ using System.Threading.Tasks;
+ using Microsoft.AspNetCore.Mvc;
+ using Microsoft.AspNetCore.Mvc.Rendering;
+ using Microsoft.AspNetCore.Mvc.ViewFeatures;
+#nullable restore
+using test;
+
+#line default
+#line hidden
+#nullable disable
+ [global::Microsoft.AspNetCore.Razor.Hosting.RazorCompiledItemMetadataAttribute("Identifier", "/Views/Test/Test7.cshtml")]
+ public class Views_Test_Test7 : global::Microsoft.AspNetCore.Mvc.Razor.RazorPage
+ {
+ #pragma warning disable 1998
+ public async override global::System.Threading.Tasks.Task ExecuteAsync()
+ {
+#line 6 "Views/Test/Test7.cshtml"
+ if (Model != null)
+{
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral(" Hello \"");
+#nullable restore
+#line 8 "Views/Test/Test7.cshtml"
+Write(Html.Raw(Model.Name));
+
+#line default
+#line hidden
+#nullable disable
+ WriteLiteral("\"
\n");
+#nullable restore
+#line 9 "Views/Test/Test7.cshtml"
+}
+
+#line default
+#line hidden
+#nullable disable
+ }
+ #pragma warning restore 1998
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.ViewFeatures.IModelExpressionProvider ModelExpressionProvider { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IUrlHelper Url { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.IViewComponentHelper Component { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IJsonHelper Json { get; private set; } = default!;
+ #nullable disable
+ #nullable restore
+ [global::Microsoft.AspNetCore.Mvc.Razor.Internal.RazorInjectAttribute]
+ public global::Microsoft.AspNetCore.Mvc.Rendering.IHtmlHelper Html { get; private set; } = default!;
+ #nullable disable
+ }
+}
+#pragma warning restore 1591
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/MyAreas/Test4/Test22.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/MyAreas/Test4/Test22.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/MyAreas/Test4/Test22.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Pages/Shared/Test21.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Pages/Shared/Test21.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Pages/Shared/Test21.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom/Test3/Test15.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom/Test3/Test15.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom/Test3/Test15.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom2/Test16.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom2/Test16.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Custom2/Test16.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test13.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test13.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test13.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test5.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test5.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test5.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test6.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test6.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test6.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test8.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test8.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test8.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test9.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test9.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Other/Test9.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test12.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test12.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test12.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test14.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test14.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test14.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test19.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test19.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test19.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test2.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test2.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test2.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test23.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test23.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test23.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test3.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test3.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Shared/Test3.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test1.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test1.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test1.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test3.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test3.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test3.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test4.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test4.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test4.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test7.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test7.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test/Test7.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test1.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test1.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test1.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test10.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test10.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test10.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test11.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test11.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test11.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test12.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test12.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test12.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test14.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test14.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test14.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test2.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test2.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test2.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test3.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test3.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test2/Test3.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test4/Test20.cshtml b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test4/Test20.cshtml
new file mode 100644
index 00000000000..74a8eab1c71
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/Views/Test4/Test20.cshtml
@@ -0,0 +1,9 @@
+@namespace test
+@model UserData
+@{
+}
+
+@if (Model != null)
+{
+ Hello "@Html.Raw(Model.Name)"
+}
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.expected b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.expected
new file mode 100644
index 00000000000..19413509bcb
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.expected
@@ -0,0 +1,180 @@
+edges
+| Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:20 | access to property Model : UserData | Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:25 | access to property Name |
+| Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:20 | access to property Model : UserData | Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:25 | access to property Name |
+| Controllers/TestController.cs:13:41:13:48 | tainted1 : UserData | Controllers/TestController.cs:15:30:15:37 | access to parameter tainted1 : UserData |
+| Controllers/TestController.cs:15:30:15:37 | access to parameter tainted1 : UserData | Views/Test/Test1.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:18:41:18:48 | tainted2 : UserData | Controllers/TestController.cs:20:30:20:37 | access to parameter tainted2 : UserData |
+| Controllers/TestController.cs:20:30:20:37 | access to parameter tainted2 : UserData | Views/Shared/Test2.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:23:41:23:48 | tainted3 : UserData | Controllers/TestController.cs:25:30:25:37 | access to parameter tainted3 : UserData |
+| Controllers/TestController.cs:25:30:25:37 | access to parameter tainted3 : UserData | Views/Test/Test3.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:28:41:28:48 | tainted4 : UserData | Controllers/TestController.cs:30:32:30:39 | access to parameter tainted4 : UserData |
+| Controllers/TestController.cs:30:32:30:39 | access to parameter tainted4 : UserData | Views/Test/Test4.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:33:41:33:48 | tainted5 : UserData | Controllers/TestController.cs:35:39:35:46 | access to parameter tainted5 : UserData |
+| Controllers/TestController.cs:35:39:35:46 | access to parameter tainted5 : UserData | Views/Other/Test5.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:38:41:38:48 | tainted6 : UserData | Controllers/TestController.cs:40:64:40:71 | access to parameter tainted6 : UserData |
+| Controllers/TestController.cs:40:64:40:71 | access to parameter tainted6 : UserData | Views/Other/Test6.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:43:41:43:48 | tainted7 : UserData | Controllers/TestController.cs:45:21:45:28 | access to parameter tainted7 : UserData |
+| Controllers/TestController.cs:45:21:45:28 | access to parameter tainted7 : UserData | Views/Test/Test7.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:48:41:48:48 | tainted8 : UserData | Controllers/TestController.cs:50:50:50:57 | access to parameter tainted8 : UserData |
+| Controllers/TestController.cs:50:50:50:57 | access to parameter tainted8 : UserData | Views/Other/Test8.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:53:41:53:48 | tainted9 : UserData | Controllers/TestController.cs:55:51:55:58 | access to parameter tainted9 : UserData |
+| Controllers/TestController.cs:55:51:55:58 | access to parameter tainted9 : UserData | Views/Other/Test9.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:60:42:60:50 | tainted10 : UserData | Controllers/TestController.cs:62:31:62:39 | access to parameter tainted10 : UserData |
+| Controllers/TestController.cs:62:31:62:39 | access to parameter tainted10 : UserData | Views/Test2/Test10.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:65:42:65:50 | tainted11 : UserData | Controllers/TestController.cs:67:23:67:31 | access to parameter tainted11 : UserData |
+| Controllers/TestController.cs:67:23:67:31 | access to parameter tainted11 : UserData | Controllers/TestController.cs:70:43:70:43 | x : UserData |
+| Controllers/TestController.cs:70:43:70:43 | x : UserData | Controllers/TestController.cs:70:70:70:70 | access to parameter x : UserData |
+| Controllers/TestController.cs:70:70:70:70 | access to parameter x : UserData | Views/Test2/Test11.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:81:42:81:50 | tainted13 : UserData | Controllers/TestController.cs:83:37:83:45 | access to parameter tainted13 : UserData |
+| Controllers/TestController.cs:83:37:83:45 | access to parameter tainted13 : UserData | Controllers/TestController.cs:94:64:94:64 | x : UserData |
+| Controllers/TestController.cs:86:42:86:50 | tainted14 : UserData | Controllers/TestController.cs:88:37:88:45 | access to parameter tainted14 : UserData |
+| Controllers/TestController.cs:88:37:88:45 | access to parameter tainted14 : UserData | Controllers/TestController.cs:96:64:96:64 | x : UserData |
+| Controllers/TestController.cs:94:64:94:64 | x : UserData | Controllers/TestController.cs:94:113:94:113 | access to parameter x : UserData |
+| Controllers/TestController.cs:94:113:94:113 | access to parameter x : UserData | Views/Other/Test13.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:96:64:96:64 | x : UserData | Controllers/TestController.cs:96:93:96:93 | access to parameter x : UserData |
+| Controllers/TestController.cs:96:93:96:93 | access to parameter x : UserData | Views/Shared/Test14.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:106:42:106:50 | tainted15 : UserData | Controllers/TestController.cs:108:21:108:29 | access to parameter tainted15 : UserData |
+| Controllers/TestController.cs:108:21:108:29 | access to parameter tainted15 : UserData | Views/Custom/Test3/Test15.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:111:42:111:50 | tainted16 : UserData | Controllers/TestController.cs:113:31:113:39 | access to parameter tainted16 : UserData |
+| Controllers/TestController.cs:113:31:113:39 | access to parameter tainted16 : UserData | Views/Custom2/Test16.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:119:42:119:50 | tainted17 : UserData | Controllers/TestController.cs:121:31:121:39 | access to parameter tainted17 : UserData |
+| Controllers/TestController.cs:121:31:121:39 | access to parameter tainted17 : UserData | Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:124:42:124:50 | tainted18 : UserData | Controllers/TestController.cs:126:31:126:39 | access to parameter tainted18 : UserData |
+| Controllers/TestController.cs:126:31:126:39 | access to parameter tainted18 : UserData | Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:129:42:129:50 | tainted19 : UserData | Controllers/TestController.cs:131:31:131:39 | access to parameter tainted19 : UserData |
+| Controllers/TestController.cs:131:31:131:39 | access to parameter tainted19 : UserData | Views/Shared/Test19.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:139:42:139:50 | tainted21 : UserData | Controllers/TestController.cs:141:31:141:39 | access to parameter tainted21 : UserData |
+| Controllers/TestController.cs:141:31:141:39 | access to parameter tainted21 : UserData | Pages/Shared/Test21.cshtml:8:16:8:20 | access to property Model : UserData |
+| Controllers/TestController.cs:149:40:149:48 | tainted23 : String | Controllers/TestController.cs:152:18:152:26 | access to parameter tainted23 : String |
+| Controllers/TestController.cs:152:9:152:9 | [post] access to local variable x : UserData [property Name] : String | Controllers/TestController.cs:153:31:153:31 | access to local variable x : UserData [property Name] : String |
+| Controllers/TestController.cs:152:18:152:26 | access to parameter tainted23 : String | Controllers/TestController.cs:152:9:152:9 | [post] access to local variable x : UserData [property Name] : String |
+| Controllers/TestController.cs:153:31:153:31 | access to local variable x : UserData [property Name] : String | Views/Shared/Test23.cshtml:8:16:8:20 | access to property Model : UserData [property Name] : String |
+| Pages/Shared/Test21.cshtml:8:16:8:20 | access to property Model : UserData | Pages/Shared/Test21.cshtml:8:16:8:25 | access to property Name |
+| Views/Custom2/Test16.cshtml:8:16:8:20 | access to property Model : UserData | Views/Custom2/Test16.cshtml:8:16:8:25 | access to property Name |
+| Views/Custom/Test3/Test15.cshtml:8:16:8:20 | access to property Model : UserData | Views/Custom/Test3/Test15.cshtml:8:16:8:25 | access to property Name |
+| Views/Other/Test5.cshtml:8:16:8:20 | access to property Model : UserData | Views/Other/Test5.cshtml:8:16:8:25 | access to property Name |
+| Views/Other/Test6.cshtml:8:16:8:20 | access to property Model : UserData | Views/Other/Test6.cshtml:8:16:8:25 | access to property Name |
+| Views/Other/Test8.cshtml:8:16:8:20 | access to property Model : UserData | Views/Other/Test8.cshtml:8:16:8:25 | access to property Name |
+| Views/Other/Test9.cshtml:8:16:8:20 | access to property Model : UserData | Views/Other/Test9.cshtml:8:16:8:25 | access to property Name |
+| Views/Other/Test13.cshtml:8:16:8:20 | access to property Model : UserData | Views/Other/Test13.cshtml:8:16:8:25 | access to property Name |
+| Views/Shared/Test2.cshtml:8:16:8:20 | access to property Model : UserData | Views/Shared/Test2.cshtml:8:16:8:25 | access to property Name |
+| Views/Shared/Test14.cshtml:8:16:8:20 | access to property Model : UserData | Views/Shared/Test14.cshtml:8:16:8:25 | access to property Name |
+| Views/Shared/Test19.cshtml:8:16:8:20 | access to property Model : UserData | Views/Shared/Test19.cshtml:8:16:8:25 | access to property Name |
+| Views/Shared/Test23.cshtml:8:16:8:20 | access to property Model : UserData [property Name] : String | Views/Shared/Test23.cshtml:8:16:8:25 | access to property Name |
+| Views/Test2/Test10.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test2/Test10.cshtml:8:16:8:25 | access to property Name |
+| Views/Test2/Test11.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test2/Test11.cshtml:8:16:8:25 | access to property Name |
+| Views/Test/Test1.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test/Test1.cshtml:8:16:8:25 | access to property Name |
+| Views/Test/Test3.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test/Test3.cshtml:8:16:8:25 | access to property Name |
+| Views/Test/Test4.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test/Test4.cshtml:8:16:8:25 | access to property Name |
+| Views/Test/Test7.cshtml:8:16:8:20 | access to property Model : UserData | Views/Test/Test7.cshtml:8:16:8:25 | access to property Name |
+nodes
+| Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Controllers/TestController.cs:13:41:13:48 | tainted1 : UserData | semmle.label | tainted1 : UserData |
+| Controllers/TestController.cs:15:30:15:37 | access to parameter tainted1 : UserData | semmle.label | access to parameter tainted1 : UserData |
+| Controllers/TestController.cs:18:41:18:48 | tainted2 : UserData | semmle.label | tainted2 : UserData |
+| Controllers/TestController.cs:20:30:20:37 | access to parameter tainted2 : UserData | semmle.label | access to parameter tainted2 : UserData |
+| Controllers/TestController.cs:23:41:23:48 | tainted3 : UserData | semmle.label | tainted3 : UserData |
+| Controllers/TestController.cs:25:30:25:37 | access to parameter tainted3 : UserData | semmle.label | access to parameter tainted3 : UserData |
+| Controllers/TestController.cs:28:41:28:48 | tainted4 : UserData | semmle.label | tainted4 : UserData |
+| Controllers/TestController.cs:30:32:30:39 | access to parameter tainted4 : UserData | semmle.label | access to parameter tainted4 : UserData |
+| Controllers/TestController.cs:33:41:33:48 | tainted5 : UserData | semmle.label | tainted5 : UserData |
+| Controllers/TestController.cs:35:39:35:46 | access to parameter tainted5 : UserData | semmle.label | access to parameter tainted5 : UserData |
+| Controllers/TestController.cs:38:41:38:48 | tainted6 : UserData | semmle.label | tainted6 : UserData |
+| Controllers/TestController.cs:40:64:40:71 | access to parameter tainted6 : UserData | semmle.label | access to parameter tainted6 : UserData |
+| Controllers/TestController.cs:43:41:43:48 | tainted7 : UserData | semmle.label | tainted7 : UserData |
+| Controllers/TestController.cs:45:21:45:28 | access to parameter tainted7 : UserData | semmle.label | access to parameter tainted7 : UserData |
+| Controllers/TestController.cs:48:41:48:48 | tainted8 : UserData | semmle.label | tainted8 : UserData |
+| Controllers/TestController.cs:50:50:50:57 | access to parameter tainted8 : UserData | semmle.label | access to parameter tainted8 : UserData |
+| Controllers/TestController.cs:53:41:53:48 | tainted9 : UserData | semmle.label | tainted9 : UserData |
+| Controllers/TestController.cs:55:51:55:58 | access to parameter tainted9 : UserData | semmle.label | access to parameter tainted9 : UserData |
+| Controllers/TestController.cs:60:42:60:50 | tainted10 : UserData | semmle.label | tainted10 : UserData |
+| Controllers/TestController.cs:62:31:62:39 | access to parameter tainted10 : UserData | semmle.label | access to parameter tainted10 : UserData |
+| Controllers/TestController.cs:65:42:65:50 | tainted11 : UserData | semmle.label | tainted11 : UserData |
+| Controllers/TestController.cs:67:23:67:31 | access to parameter tainted11 : UserData | semmle.label | access to parameter tainted11 : UserData |
+| Controllers/TestController.cs:70:43:70:43 | x : UserData | semmle.label | x : UserData |
+| Controllers/TestController.cs:70:70:70:70 | access to parameter x : UserData | semmle.label | access to parameter x : UserData |
+| Controllers/TestController.cs:81:42:81:50 | tainted13 : UserData | semmle.label | tainted13 : UserData |
+| Controllers/TestController.cs:83:37:83:45 | access to parameter tainted13 : UserData | semmle.label | access to parameter tainted13 : UserData |
+| Controllers/TestController.cs:86:42:86:50 | tainted14 : UserData | semmle.label | tainted14 : UserData |
+| Controllers/TestController.cs:88:37:88:45 | access to parameter tainted14 : UserData | semmle.label | access to parameter tainted14 : UserData |
+| Controllers/TestController.cs:94:64:94:64 | x : UserData | semmle.label | x : UserData |
+| Controllers/TestController.cs:94:113:94:113 | access to parameter x : UserData | semmle.label | access to parameter x : UserData |
+| Controllers/TestController.cs:96:64:96:64 | x : UserData | semmle.label | x : UserData |
+| Controllers/TestController.cs:96:93:96:93 | access to parameter x : UserData | semmle.label | access to parameter x : UserData |
+| Controllers/TestController.cs:106:42:106:50 | tainted15 : UserData | semmle.label | tainted15 : UserData |
+| Controllers/TestController.cs:108:21:108:29 | access to parameter tainted15 : UserData | semmle.label | access to parameter tainted15 : UserData |
+| Controllers/TestController.cs:111:42:111:50 | tainted16 : UserData | semmle.label | tainted16 : UserData |
+| Controllers/TestController.cs:113:31:113:39 | access to parameter tainted16 : UserData | semmle.label | access to parameter tainted16 : UserData |
+| Controllers/TestController.cs:119:42:119:50 | tainted17 : UserData | semmle.label | tainted17 : UserData |
+| Controllers/TestController.cs:121:31:121:39 | access to parameter tainted17 : UserData | semmle.label | access to parameter tainted17 : UserData |
+| Controllers/TestController.cs:124:42:124:50 | tainted18 : UserData | semmle.label | tainted18 : UserData |
+| Controllers/TestController.cs:126:31:126:39 | access to parameter tainted18 : UserData | semmle.label | access to parameter tainted18 : UserData |
+| Controllers/TestController.cs:129:42:129:50 | tainted19 : UserData | semmle.label | tainted19 : UserData |
+| Controllers/TestController.cs:131:31:131:39 | access to parameter tainted19 : UserData | semmle.label | access to parameter tainted19 : UserData |
+| Controllers/TestController.cs:139:42:139:50 | tainted21 : UserData | semmle.label | tainted21 : UserData |
+| Controllers/TestController.cs:141:31:141:39 | access to parameter tainted21 : UserData | semmle.label | access to parameter tainted21 : UserData |
+| Controllers/TestController.cs:149:40:149:48 | tainted23 : String | semmle.label | tainted23 : String |
+| Controllers/TestController.cs:152:9:152:9 | [post] access to local variable x : UserData [property Name] : String | semmle.label | [post] access to local variable x : UserData [property Name] : String |
+| Controllers/TestController.cs:152:18:152:26 | access to parameter tainted23 : String | semmle.label | access to parameter tainted23 : String |
+| Controllers/TestController.cs:153:31:153:31 | access to local variable x : UserData [property Name] : String | semmle.label | access to local variable x : UserData [property Name] : String |
+| Pages/Shared/Test21.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Pages/Shared/Test21.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Custom2/Test16.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Custom2/Test16.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Custom/Test3/Test15.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Custom/Test3/Test15.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Other/Test5.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Other/Test5.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Other/Test6.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Other/Test6.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Other/Test8.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Other/Test8.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Other/Test9.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Other/Test9.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Other/Test13.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Other/Test13.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Shared/Test2.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Shared/Test2.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Shared/Test14.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Shared/Test14.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Shared/Test19.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Shared/Test19.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Shared/Test23.cshtml:8:16:8:20 | access to property Model : UserData [property Name] : String | semmle.label | access to property Model : UserData [property Name] : String |
+| Views/Shared/Test23.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test2/Test10.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test2/Test10.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test2/Test11.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test2/Test11.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test/Test1.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test/Test1.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test/Test3.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test/Test3.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test/Test4.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test/Test4.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+| Views/Test/Test7.cshtml:8:16:8:20 | access to property Model : UserData | semmle.label | access to property Model : UserData |
+| Views/Test/Test7.cshtml:8:16:8:25 | access to property Name | semmle.label | access to property Name |
+subpaths
+#select
+| Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:124:42:124:50 | tainted18 : UserData | Areas/TestArea/Views/Shared/Test18.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:124:42:124:50 | tainted18 : UserData | User-provided value |
+| Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:119:42:119:50 | tainted17 : UserData | Areas/TestArea/Views/Test4/Test17.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:119:42:119:50 | tainted17 : UserData | User-provided value |
+| Pages/Shared/Test21.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:139:42:139:50 | tainted21 : UserData | Pages/Shared/Test21.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:139:42:139:50 | tainted21 : UserData | User-provided value |
+| Views/Custom2/Test16.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:111:42:111:50 | tainted16 : UserData | Views/Custom2/Test16.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:111:42:111:50 | tainted16 : UserData | User-provided value |
+| Views/Custom/Test3/Test15.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:106:42:106:50 | tainted15 : UserData | Views/Custom/Test3/Test15.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:106:42:106:50 | tainted15 : UserData | User-provided value |
+| Views/Other/Test5.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:33:41:33:48 | tainted5 : UserData | Views/Other/Test5.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:33:41:33:48 | tainted5 : UserData | User-provided value |
+| Views/Other/Test6.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:38:41:38:48 | tainted6 : UserData | Views/Other/Test6.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:38:41:38:48 | tainted6 : UserData | User-provided value |
+| Views/Other/Test8.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:48:41:48:48 | tainted8 : UserData | Views/Other/Test8.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:48:41:48:48 | tainted8 : UserData | User-provided value |
+| Views/Other/Test9.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:53:41:53:48 | tainted9 : UserData | Views/Other/Test9.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:53:41:53:48 | tainted9 : UserData | User-provided value |
+| Views/Other/Test13.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:81:42:81:50 | tainted13 : UserData | Views/Other/Test13.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:81:42:81:50 | tainted13 : UserData | User-provided value |
+| Views/Shared/Test2.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:18:41:18:48 | tainted2 : UserData | Views/Shared/Test2.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:18:41:18:48 | tainted2 : UserData | User-provided value |
+| Views/Shared/Test14.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:86:42:86:50 | tainted14 : UserData | Views/Shared/Test14.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:86:42:86:50 | tainted14 : UserData | User-provided value |
+| Views/Shared/Test19.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:129:42:129:50 | tainted19 : UserData | Views/Shared/Test19.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:129:42:129:50 | tainted19 : UserData | User-provided value |
+| Views/Shared/Test23.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:149:40:149:48 | tainted23 : String | Views/Shared/Test23.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:149:40:149:48 | tainted23 : String | User-provided value |
+| Views/Test2/Test10.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:60:42:60:50 | tainted10 : UserData | Views/Test2/Test10.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:60:42:60:50 | tainted10 : UserData | User-provided value |
+| Views/Test2/Test11.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:65:42:65:50 | tainted11 : UserData | Views/Test2/Test11.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:65:42:65:50 | tainted11 : UserData | User-provided value |
+| Views/Test/Test1.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:13:41:13:48 | tainted1 : UserData | Views/Test/Test1.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:13:41:13:48 | tainted1 : UserData | User-provided value |
+| Views/Test/Test3.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:23:41:23:48 | tainted3 : UserData | Views/Test/Test3.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:23:41:23:48 | tainted3 : UserData | User-provided value |
+| Views/Test/Test4.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:28:41:28:48 | tainted4 : UserData | Views/Test/Test4.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:28:41:28:48 | tainted4 : UserData | User-provided value |
+| Views/Test/Test7.cshtml:8:16:8:25 | access to property Name | Controllers/TestController.cs:43:41:43:48 | tainted7 : UserData | Views/Test/Test7.cshtml:8:16:8:25 | access to property Name | $@ flows to here and is written to HTML or JavaScript: Microsoft.AspNetCore.Mvc.ViewFeatures.HtmlHelper.Raw() method. | Controllers/TestController.cs:43:41:43:48 | tainted7 : UserData | User-provided value |
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.qlref b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.qlref
new file mode 100644
index 00000000000..faad1d6403c
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/XSS.qlref
@@ -0,0 +1 @@
+Security Features/CWE-079/XSS.ql
\ No newline at end of file
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/gen_files.py b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/gen_files.py
new file mode 100644
index 00000000000..a01398e8201
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/gen_files.py
@@ -0,0 +1,70 @@
+# A script for generating code from .cshtml files, mimicking the output of the C# compiler with an option that is not available from the codeql test runner.
+
+import sys
+import os
+
+work_dir = os.path.abspath(os.path.dirname(sys.argv[0]))
+gen_dir = f"{work_dir}/Generated"
+with open(f"{gen_dir}/Template.g") as f:
+ template = f.read()
+
+verbose = False
+
+
+def process_file(path: str):
+ """
+ Generates the file from the .cshtml file at `path`.
+ `path` is a relative filepath from `work_dir`.
+ """
+ # The location of the .cshtml file is the only relevant part for these tests; its contents are assumed to be the same.
+ assert path.endswith(".cshtml")
+ path = path.lstrip("/")
+ path_under = path.replace("/", "_")[:-len(".cshtml")]
+
+ gen = template.replace("$PATHSLASH", path).replace("$PATHUNDER", path_under)
+
+ out_path = f"{gen_dir}/{path_under}.cshtml.g.cs"
+ with open(out_path, "w") as f:
+ f.write(gen)
+
+ if verbose:
+ print(out_path)
+
+
+def process_dir(path: str):
+ """
+ Generates all the .cshtml files in the directory `path`.
+ `path` is a relative filepath from `work_dir`.
+ """
+ abs_path = f"{work_dir}/{path}"
+ assert os.path.isdir(abs_path)
+
+ for sub in os.listdir(abs_path):
+ sub_abs = f"{abs_path}/{sub}"
+ sub_rel = f"{path}/{sub}"
+
+ if sub.endswith(".cshtml") and os.path.isfile(sub_abs):
+ process_file(sub_rel)
+ elif os.path.isdir(sub_abs) and ".testproj" not in sub_abs:
+ process_dir(sub_rel)
+
+
+def print_usage():
+ print("""Usage: python3 gen_files.py [-v] [--verbose] [-h] [--help]
+
+Generates files from .cshtml files found in the directory tree of this script's parent folder, mimicking the C# compiler.
+`.testproj` is ignored.
+
+-h, --help: Displays this message and exits.
+-v, --verbose: Prints the name of each file generated.""")
+
+
+if __name__ == "__main__":
+ if "-h" in sys.argv or "--help" in sys.argv:
+ print_usage()
+ exit()
+
+ if "-v" in sys.argv or "--verbose" in sys.argv:
+ verbose = True
+
+ process_dir("")
diff --git a/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/options b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/options
new file mode 100644
index 00000000000..9864339f5c9
--- /dev/null
+++ b/csharp/ql/test/query-tests/Security Features/CWE-079/XSSRazorPages/options
@@ -0,0 +1,3 @@
+semmle-extractor-options: /nostdlib /noconfig
+semmle-extractor-options: --load-sources-from-project:${testdir}/../../../../resources/stubs/_frameworks/Microsoft.NETCore.App/Microsoft.NETCore.App.csproj
+semmle-extractor-options: --load-sources-from-project:../../../../resources/stubs/_frameworks/Microsoft.AspNetCore.App/Microsoft.AspNetCore.App.csproj
\ No newline at end of file
diff --git a/docs/codeql/codeql-for-visual-studio-code/using-the-codeql-model-editor.rst b/docs/codeql/codeql-for-visual-studio-code/using-the-codeql-model-editor.rst
index 95bdb926c32..0eaa4518118 100644
--- a/docs/codeql/codeql-for-visual-studio-code/using-the-codeql-model-editor.rst
+++ b/docs/codeql/codeql-for-visual-studio-code/using-the-codeql-model-editor.rst
@@ -18,7 +18,7 @@ When you open the model editor, it analyzes the currently selected CodeQL databa
The model editor has two different modes:
-- Application mode (default view): The editor lists each external framework used by the selected CodeQL database. When you expand a framework, a list of all calls to and from the external API is shown with the options available to model dataflow through each call. This mode is most useful for improving the CodeQL results for the specific codebase.
+- Application mode (default view): The editor lists each external framework used by the selected CodeQL database. When you expand a framework, a list of all calls to and from the external API is shown with the options available to model dataflow through each call. This mode is most useful for improving the CodeQL results for a specific codebase.
- Dependency mode: The editor identifies all of the publicly accessible APIs in the selected CodeQL database. This view guides you through modeling each public API that the codebase makes available. When you have finished modeling the entire API, you can save the model and use it to improve the CodeQL analysis for all codebases that use the dependency.
@@ -28,30 +28,45 @@ Displaying the CodeQL model editor
#. Open your CodeQL workspace in VS Code, for example, the ``vscode-codeql-starter`` workspace.
If you haven't updated the ``ql`` submodule for a while, update it from ``main`` to ensure that you have the queries used to gather data for the model editor.
#. Open the CodeQL extension and select the CodeQL database that you want to model from the "Databases" section of the left side pane.
-#. Use the command palette to run the “CodeQL: Open Model Editor (Beta)” command.
-#. The CodeQL model editor will open in a new tab and run a series of telemetry queries to identify APIs in the code.
-#. When the queries are complete, the APIs that have been identified are shown in the editor.
+#. In the left side panel, expand the "CodeQL method modeling" section and click **Start modeling** to display the model editor. Alternatively, use the command palette to run the “CodeQL: Open Model Editor (Beta)” command.
+#. The CodeQL model editor runs a series of telemetry queries to identify APIs in the code and the editor is displayed in a new tab.
+#. When the telemetry queries are complete, the APIs that have been identified are shown in the editor.
+
+.. tip::
+
+ The "CodeQL method modeling" section is a view that you can move from the primary sidebar to the secondary sidebar, when you want more space while you are modeling calls or methods. If you close the view, you can reopen it from the "Open Views" option in the **View** menu.
Modeling the calls your codebase makes to external APIs
-------------------------------------------------------
-You typically use this approach when you are looking at a specific codebase where you want to improve the precision of CodeQL results. This is usually when the codebase uses frameworks or libraries that are not supported by CodeQL and if the source code of the framework or library is not included in the analysis.
+You typically use this approach when you are looking at a specific codebase where you want to improve the precision of CodeQL results. This is useful when the codebase uses frameworks or libraries that are not supported by CodeQL and if the source code of the framework or library is not included in the analysis.
#. Select the CodeQL database that you want to improve CodeQL coverage for.
#. Display the CodeQL model editor. By default the editor runs in application mode, so the list of external APIs used by the selected codebase is shown.
.. image:: ../images/codeql-for-visual-studio-code/model-application-mode.png
:width: 800
- :alt: Screenshot of the "Application mode" view of the CodeQL model pack editor in Visual Studio Code showing three of the external frameworks used by the "sofa-jraft" codebase.
+ :alt: Screenshot of the "Application mode" view of the CodeQL model pack editor in Visual Studio Code showing two of the external Java frameworks used by the "sofa-jraft" codebase.
#. Click to expand an external API and view the list of calls from the codebase to the external dependency.
-#. Click **View** associated with an API call or method to show where it is used in your codebase.
.. image:: ../images/codeql-for-visual-studio-code/model-application-mode-expanded.png
:width: 800
:alt: Screenshot of the "Application mode" view of the CodeQL model pack editor in Visual Studio Code showing the calls to the "rocksdbjni" framework ready for modeling. The "View" option for the first call is highlighted with a dark orange outline.
-#. When you have determined how to model the call or method, define the **Model type**.
+#. Click **View** associated with an API call or method to show where it is used in your codebase.
+
+ .. image:: ../images/codeql-for-visual-studio-code/model-application-mode-view-code.png
+ :width: 800
+ :alt: Screenshot of a file showing a place where your codebase calls the API is highlighted with a dark orange outline.
+
+#. The file containing the first call from your codebase to the API is opened and a "CodeQL methods usage" view is displayed in the VS Code Panel (where the "Problems" and "Terminal" views are usually displayed). The "CodeQL methods usage" view lists of all the calls from your code to the API, grouped by method. You can click through each use to decide how to model your use of the method.
+
+ .. image:: ../images/codeql-for-visual-studio-code/model-application-mode-view-list.png
+ :width: 800
+ :alt: Screenshot of the "CodeQL methods usage" view. The currently displayed call to an external method is highlighted blue.
+
+#. When you have determined how to model your use of the method, you can define the **Model type** in the "CodeQL method modeling" tab of the CodeQL extension. This change is automatically reflected in the main model editor.
#. The remaining fields are updated with available options:
- **Source**: choose the **Output** element to model.
@@ -59,9 +74,9 @@ You typically use this approach when you are looking at a specific codebase wher
- **Flow summary**: choose the **Input** and **Output** elements to model.
#. Define the **Kind** of dataflow for the model.
-#. When you have finished modeling, click **Save all** or **Save** (shown at the bottom right of each expanded list of calls). The percentage of calls modeled in the editor is updated.
+#. When you have finished modeling, display the main model editor and click **Save all** or **Save** (shown at the bottom right of each expanded list of methods). The percentage of methods modeled in the editor is updated.
-The models are stored in your workspace at ``.github/codeql/extensions/``, where ```` is the name of the CodeQL database that you selected. That is, the name of the repository, hyphen, the language analyzed by CodeQL.
+The models are stored in your workspace at ``.github/codeql/extensions/``, where ```` is the name of the CodeQL database that you selected. That is, the name of the repository, hyphen, the language analyzed by CodeQL. For more information, see "`Using CodeQL model packs with code scanning <#using-codeql-model-packs-with-code-scanning>`__".
The models are stored in a series of YAML data extension files, one for each external API. For example:
@@ -101,7 +116,7 @@ You typically use this method when you want to model a framework or library that
#. Define the **Kind** of dataflow for the model.
#. When you have finished modeling, click **Save all** or **Save** (shown at the bottom right of each expanded list of calls). The percentage of calls modeled in the editor is updated.
-The models are stored in your workspace at ``.github/codeql/extensions/``, where ```` is the name of the CodeQL database that you selected. That is, the name of the repository, hyphen, the language analyzed by CodeQL.
+The models are stored in your workspace at ``.github/codeql/extensions/``, where ```` is the name of the CodeQL database that you selected. That is, the name of the repository, hyphen, the language analyzed by CodeQL. For more information, see "`Using CodeQL model packs with code scanning <#using-codeql-model-packs-with-code-scanning>`__".
The models are stored in a series of YAML data extension files, one for each public method. For example:
@@ -114,13 +129,22 @@ The models are stored in a series of YAML data extension files, one for each pub
The editor will create a separate model file for each package that you model.
-Testing CodeQL model packs
---------------------------
+Modeling methods with multiple potential flows
+----------------------------------------------
-You can test any CodeQL model packs you create in VS Code by toggling the "use model packs" setting on and off. This method works for both databases and for variant analysis repositories.
+Some methods support more than one data flow. It is important to model all the data flows for a method, otherwise you cannot detect all the potential problems associated with using the method. First you model one data flow for the method, and then use the **+** button in the method row to specify a second data flow model.
-- To run queries on a CodeQL database with any model packs that are stored within the ``.github/codeql/extensions`` directory of the workspace, update your ``settings.json`` file with: ``"codeQL.runningQueries.useModelPacks": all,``
-- To run queries on a CodeQL database without using model packs, update your ``settings.json`` file with: ``"codeQL.runningQueries.useModelPacks": none,``
+ .. image:: ../images/codeql-for-visual-studio-code/model-dependency-mode-plus.png
+ :width: 800
+ :alt: Screenshot of the "Dependency mode" view of the CodeQL model pack editor in Visual Studio Code showing one model for the ``com.alipay.sofa.jraft.option.BallotBoxOptions.getClosureQueue()`` method. The "+" button is outlined in dark orange. Click this button to create a second model for the method.
+
+Testing CodeQL model packs in VS Code
+-------------------------------------
+
+You can test any CodeQL model packs you create in VS Code by turning the "use model packs" setting on and off. This method works for both databases and for variant analysis repositories.
+
+- To run queries on a CodeQL database with any model packs that are stored within the ``.github/codeql/extensions`` directory of the workspace, update your ``settings.json`` file with: ``"codeQL.runningQueries.useExtensionPacks": "all",``
+- To run queries on a CodeQL database without using model packs, update your ``settings.json`` file with: ``"codeQL.runningQueries.useExtensionPacks": "none",``
If your model is working well, you should see a difference in the results of the two different runs. If you don't see any differences in results, you may need to introduce a known bug to verify that the model behaves as expected.
@@ -136,4 +160,4 @@ For more information, see the following articles on the GitHub Docs site:
- Default setup of code scanning: `Extending CodeQL coverage with CodeQL model packs in default setup `__
- Advanced setup of code scanning: `Extending CodeQL coverage with CodeQL model packs `__
-- CodeQL CLI setup in external CI system: `Using model packs to analyze calls to custom dependencies `__
+- CodeQL CLI setup in external CI system: `Using model packs to analyze calls to custom dependencies `__
diff --git a/docs/codeql/codeql-language-guides/customizing-library-models-for-java-and-kotlin.rst b/docs/codeql/codeql-language-guides/customizing-library-models-for-java-and-kotlin.rst
index cc8e4e51b7b..063bcf1e4a1 100644
--- a/docs/codeql/codeql-language-guides/customizing-library-models-for-java-and-kotlin.rst
+++ b/docs/codeql/codeql-language-guides/customizing-library-models-for-java-and-kotlin.rst
@@ -54,14 +54,14 @@ Data extensions use union semantics, which means that the tuples of all extensio
Publish data extension files in a CodeQL model pack to share
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-You can group one or more data extention files into a CodeQL model pack and publish it to the GitHub Container Registry. This makes it easy for anyone to download the model pack and use it to extend their analysis. For more information, see "`Creating a CodeQL model pack `__ and `Publishing and using CodeQL packs `__ in the CodeQL CLI documentation.
+You can group one or more data extension files into a CodeQL model pack and publish it to the GitHub Container Registry. This makes it easy for anyone to download the model pack and use it to extend their analysis. For more information, see `Creating a CodeQL model pack `__ and `Publishing and using CodeQL packs `__ in the CodeQL CLI documentation.
Extensible predicates used to create custom models in Java and Kotlin
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The CodeQL library for Java and Kotlin analysis exposes the following extensible predicates:
-- ``sourceModel(package, type, subtypes, name, signature, ext, output, kind, provenance)``. This is used to model sources of potentially tainted data.
+- ``sourceModel(package, type, subtypes, name, signature, ext, output, kind, provenance)``. This is used to model sources of potentially tainted data. The ``kind`` of the sources defined using this predicate determine which threat model they are associated with. Different threat models can be used to customize the sources used in an analysis. For more information, see ":ref:`Threat models `."
- ``sinkModel(package, type, subtypes, name, signature, ext, input, kind, provenance)``. This is used to model sinks where tainted data maybe used in a way that makes the code vulnerable.
- ``summaryModel(package, type, subtypes, name, signature, ext, input, output, kind, provenance)``. This is used to model flow through elements.
- ``neutralModel(package, type, name, signature, kind, provenance)``. This is similar to a summary model but used to model the flow of values that have only a minor impact on the dataflow analysis.
@@ -151,7 +151,7 @@ The sixth value should be left empty and is out of scope for this documentation.
The remaining values are used to define the ``access path``, the ``kind``, and the ``provenance`` (origin) of the source.
- The seventh value ``ReturnValue`` is the access path to the return of the method, which means that it is the return value that should be considered a source of tainted input.
-- The eighth value ``remote`` is the kind of the source. The source kind is used to define the queries where the source is in scope. ``remote`` applies to many of the security related queries as it means a remote source of untrusted data. As an example the SQL injection query uses ``remote`` sources.
+- The eighth value ``remote`` is the kind of the source. The source kind is used to define the threat model where the source is in scope. ``remote`` applies to many of the security related queries as it means a remote source of untrusted data. As an example the SQL injection query uses ``remote`` sources. For more information, see ":ref:`Threat models `."
- The ninth value ``manual`` is the provenance of the source, which is used to identify the origin of the source.
Example: Add flow through the ``concat`` method
@@ -291,3 +291,19 @@ The first four values identify the callable (in this case a method) to be modele
- The fourth value ``()`` is the method input type signature.
- The fifth value ``summary`` is the kind of the neutral.
- The sixth value ``manual`` is the provenance of the neutral.
+
+.. _threat-models:
+
+Threat models
+-------------
+
+.. include:: ../reusables/beta-note-threat-models-java.rst
+
+A threat model is a named class of dataflow sources that can be enabled or disabled independently. Threat models allow you to control the set of dataflow sources that you want to consider unsafe. For example, one codebase may only consider remote HTTP requests to be tainted, whereas another may also consider data from local files to be unsafe. You can use threat models to ensure that the relevant taint sources are used in a CodeQL analysis.
+
+The ``kind`` property of the ``sourceModel`` determines which threat model a source is associated with. There are two main categories:
+
+- ``remote`` which represents requests and responses from the network.
+- ``local`` which represents data from local files (``file``), command-line arguments (``commandargs``), database reads (``database``), and environment variables(``environment``).
+
+When running a CodeQL analysis, the ``remote`` threat model is included by default. You can optionally include other threat models as appropriate when using the CodeQL CLI and in GitHub code scanning. For more information, see `Analyzing your code with CodeQL queries `__ and `Customizing your advanced setup for code scanning `__.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.0.rst
new file mode 100644
index 00000000000..9142a12edfc
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.0.rst
@@ -0,0 +1,178 @@
+.. _codeql-cli-2.10.0:
+
+==========================
+CodeQL 2.10.0 (2022-06-27)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.10.0 runs a total of 339 security queries when configured with the Default suite (covering 142 CWE). The Extended suite enables an additional 104 queries (covering 30 more CWE). 4 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The :code:`--format=stats` option of :code:`codeql generate log-summary` has been renamed to :code:`--format=overall`. It now produces a richer JSON object that, in addition to the previous statistics about the run (which can be found in the :code:`stats` property) also records the most expensive predicates in the evaluation run.
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* The :code:`codeql resolve ml-model` command now requires one or more query specifications as command line arguments in order to determine the set of starting packs from which to initiate the resolution process. The command will locate all ML models in any qlpack that is a transitive dependency of any of the starting packs. Also, the output of the command has been expanded to include for each model the containing package's name, version, and path.
+
+* The :code:`buildMetadata` inside of compiled CodeQL packs no longer contains a :code:`creationTime` property. This was removed in order to ensure that the content of a CodeQL pack is identical when it is re-compiled.
+
+* The :code:`codeql pack download` command, when used with the :code:`--dir` option,
+ now downloads requested packs in directories corresponding to their version numbers. Previously,
+ :code:`codeql pack download --dir ./somewhere codeql/java-queries@0.1.2` would download the pack into the :code:`./somewhere/codeql/java-queries` directory. Now, it will download the pack into the
+ :code:`./somewhere/codeql/java-queries/0.1.2` directory. This allows you to download multiple versions of the same pack using a single command.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug where :code:`codeql pack download`, when used with the :code:`--dir` option, would not download a pack that is in the global package cache.
+
+* Fixed a bug where some versions of a CodeQL package could not be downloaded if there are more than 100 versions of this package in the package registry.
+
+* Fixed a bug where the :code:`--also-match` option for :code:`codeql resolve files` and :code:`codeql database index-files` does not work with relative paths.
+
+* Fixed a bug that caused :code:`codeql query decompile` to ignore the
+ :code:`--output` option when producing bytecode output (:code:`--kind=bytecode`),
+ writing only to :code:`stdout`.
+
+New Features
+~~~~~~~~~~~~
+
+* You can now include diagnostic messages in the summary produced by the :code:`--print-diagnostics-summary` option of the
+ :code:`codeql database interpret-results` and :code:`codeql database analyze` commands by running these commands at high verbosity levels.
+
+Query Packs
+-----------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* Improved library modeling for the query "Request without certificate validation" (:code:`py/request-without-cert-validation`), so it now also covers :code:`httpx`, :code:`aiohttp.client`, and :code:`urllib3`.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The syntax of the (source|sink|summary)model CSV format has been changed slightly for Java and C#. A new column called :code:`provenance` has been introduced, where the allowed values are :code:`manual` and :code:`generated`. The value used to indicate whether a model as been written by hand (:code:`manual`) or create by the CSV model generator (:code:`generated`).
+* All auto implemented public properties with public getters and setters on ASP.NET Core remote flow sources are now also considered to be tainted.
+
+Java
+""""
+
+* The query :code:`java/log-injection` now reports problems at the source (user-controlled data) instead of at the ultimate logging call. This was changed because user functions that wrap the ultimate logging call could result in most alerts being reported in an uninformative location.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`js/resource-exhaustion` query no longer treats the 3-argument version of :code:`Buffer.from` as a sink,
+ since it does not allocate a new buffer.
+
+Python
+""""""
+
+* The query "Use of a broken or weak cryptographic algorithm" (:code:`py/weak-cryptographic-algorithm`) now reports if a cryptographic operation is potentially insecure due to use of a weak block mode.
+
+Ruby
+""""
+
+* The query "Use of a broken or weak cryptographic algorithm" (:code:`rb/weak-cryptographic-algorithm`) now reports if a cryptographic operation is potentially insecure due to use of a weak block mode.
+
+New Queries
+~~~~~~~~~~~
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/improper-memoization`. The query finds cases where the parameter of a memoization method is not used in the memoization key.
+
+Query Metadata Changes
+~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The :code:`kind` query metadata was changed to :code:`diagnostic` on :code:`cs/compilation-error`, :code:`cs/compilation-message`, :code:`cs/extraction-error`, and :code:`cs/extraction-message`.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+C/C++
+"""""
+
+* :code:`UserType.getADeclarationEntry()` now yields all forward declarations when the user type is a :code:`class`, :code:`struct`, or :code:`union`.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 4.7.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Added a flow step for :code:`String.valueOf` calls on tainted :code:`android.text.Editable` objects.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* All new ECMAScript 2022 features are now supported.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+C#
+""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+Golang
+""""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+Java
+""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+Python
+""""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+Ruby
+""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.1.rst
new file mode 100644
index 00000000000..08a42da5c20
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.1.rst
@@ -0,0 +1,132 @@
+.. _codeql-cli-2.10.1:
+
+==========================
+CodeQL 2.10.1 (2022-07-19)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.10.1 runs a total of 340 security queries when configured with the Default suite (covering 143 CWE). The Extended suite enables an additional 104 queries (covering 30 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+New Features
+~~~~~~~~~~~~
+
+* Improved error message from :code:`codeql database analyze` when a query is missing :code:`@id` or :code:`@kind` query metadata.
+
+Query Packs
+-----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/cpp-all` package.
+
+C#
+""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/csharp-all` package.
+
+Java
+""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/java-all` package.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/javascript-all` package.
+
+Python
+""""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/python-all` package.
+
+Ruby
+""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/ruby-all` package.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* A new query "Improper verification of intent by broadcast receiver" (:code:`java/improper-intent-verification`) has been added.
+ This query finds instances of Android :code:`BroadcastReceiver`\ s that don't verify the action string of received intents when registered to receive system intents.
+
+Language Libraries
+------------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* :code:`AnalysedExpr::isNullCheck` and :code:`AnalysedExpr::isValidCheck` have been updated to handle variable accesses on the left-hand side of the C++ logical "and", and variable declarations in conditions.
+
+Java
+""""
+
+* Added data-flow models for :code:`java.util.Properties`. Additional results may be found where relevant data is stored in and then retrieved from a :code:`Properties` instance.
+* Added :code:`Modifier.isInline()`.
+* Removed Kotlin-specific database and QL structures for loops and :code:`break`\ /\ :code:`continue` statements. The Kotlin extractor was changed to reuse the Java structures for these constructs.
+* Added additional flow sources for uses of external storage on Android.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`chownr` library is now modeled as a sink for the :code:`js/path-injection` query.
+* Improved modeling of sensitive data sources, so common words like :code:`certain` and :code:`secretary` are no longer considered a certificate and a secret (respectively).
+* The :code:`gray-matter` library is now modeled as a sink for the :code:`js/code-injection` query.
+
+Python
+""""""
+
+* Improved modeling of sensitive data sources, so common words like :code:`certain` and :code:`secretary` are no longer considered a certificate and a secret (respectively).
+
+Ruby
+""""
+
+* Fixed a bug causing every expression in the database to be considered a system-command execution sink when calls to any of the following methods exist:
+
+ * The :code:`spawn`, :code:`fspawn`, :code:`popen4`, :code:`pspawn`, :code:`system`, :code:`_pspawn` methods and the backtick operator from the :code:`POSIX::spawn` gem.
+ * The :code:`execute_command`, :code:`rake`, :code:`rails_command`, and :code:`git` methods in :code:`Rails::Generation::Actions`.
+
+* Improved modeling of sensitive data sources, so common words like :code:`certain` and :code:`secretary` are no longer considered a certificate and a secret (respectively).
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* The documentation of API graphs (the :code:`API` module) has been expanded, and some of the members predicates of :code:`API::Node` have been renamed as follows:
+
+ * :code:`getAnImmediateUse` -> :code:`asSource`
+ * :code:`getARhs` -> :code:`asSink`
+ * :code:`getAUse` -> :code:`getAValueReachableFromSource`
+ * :code:`getAValueReachingRhs` -> :code:`getAValueReachingSink`
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* Added an :code:`ErrorType` class. An instance of this class will be used if an extractor is unable to extract a type, or if an up/downgrade script is unable to provide a type.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.2.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.2.rst
new file mode 100644
index 00000000000..e083daa616e
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.2.rst
@@ -0,0 +1,105 @@
+.. _codeql-cli-2.10.2:
+
+==========================
+CodeQL 2.10.2 (2022-08-02)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.10.2 runs a total of 341 security queries when configured with the Default suite (covering 144 CWE). The Extended suite enables an additional 104 queries (covering 30 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The option :code:`--compiler-spec` to :code:`codeql database create` (and
+ :code:`codeql database trace-command`) no longer works. It is replaced by
+ :code:`--extra-tracing-config`, which accepts a tracer configuration file in the new, Lua-based tracer configuration format instead. See
+ :code:`tools/tracer/base.lua` for the precise API available. If you need help help porting your existing compiler specification files, please file a public issue in https://github.com/github/codeql-cli-binaries,
+ or open a private ticket with GitHub support and request an escalation to engineering.
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* Versions of the CodeQL extension for Visual Studio Code released before February 2021 may not work correctly with this CLI, in particular if database upgrades are necessary. We recommend keeping your VS Code extension up-to-date.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The experimental :code:`codeql resolve ml-models` command has been deprecated. Advanced users calling this command should use the new
+ :code:`codeql resolve extensions` command instead.
+
+New Features
+~~~~~~~~~~~~
+
+* The :code:`codeql github upload-results` command now supports a :code:`--merge` option. If this option is provided, the command will accept the paths to multiple SARIF files, and will merge those files before uploading them as a single analysis. This option is recommended *only* for backwards compatibility with old analyses produced by the CodeQL Runner, which combined the results for multiple languages into a single analysis.
+
+Query Packs
+-----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* Contextual queries and the query libraries they depend on have been moved to the :code:`codeql/python-all` package.
+
+New Queries
+~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* A new query "Case-sensitive middleware path" (:code:`js/case-sensitive-middleware-path`) has been added.
+ It highlights middleware routes that can be bypassed due to having a case-sensitive regular expression path.
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/manually-checking-http-verb`, to detect cases when the HTTP verb for an incoming request is checked and then used as part of control flow.
+* Added a new experimental query, :code:`rb/weak-params`, to detect cases when the rails strong parameters pattern isn't followed and values flow into persistent store writes.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+C/C++
+"""""
+
+* Under certain circumstances a variable declaration that is not also a definition could be associated with a :code:`Variable` that did not have the definition as a :code:`VariableDeclarationEntry`. This is now fixed, and a unique :code:`Variable` will exist that has both the declaration and the definition as a :code:`VariableDeclarationEntry`.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The JUnit5 version of :code:`AssertNotNull` is now recognized, which removes related false positives in the nullness queries.
+* Added data flow models for :code:`java.util.Scanner`.
+
+Ruby
+""""
+
+* Calls to :code:`Arel.sql` are now recognised as propagating taint from their argument.
+* Calls to :code:`ActiveRecord::Relation#annotate` are now recognized as :code:`SqlExecution`\ s so that it will be considered as a sink for queries like rb/sql-injection.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* The QL predicate :code:`Expr::getUnderlyingExpr` has been added. It can be used to look through casts and not-null expressions and obtain the underlying expression to which they apply.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.3.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.3.rst
new file mode 100644
index 00000000000..a8c9211f3fc
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.3.rst
@@ -0,0 +1,111 @@
+.. _codeql-cli-2.10.3:
+
+==========================
+CodeQL 2.10.3 (2022-08-15)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.10.3 runs a total of 342 security queries when configured with the Default suite (covering 144 CWE). The Extended suite enables an additional 104 queries (covering 30 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+New Features
+~~~~~~~~~~~~
+
+* When called with :code:`--start-tracing`, the :code:`codeql database init` command now accepts extractor options for the indirect tracing environment via
+ :code:`--extractor-option`. Users should continue to specify extractor options for direct tracing environments by passing them to
+ :code:`codeql database trace-command` invocations.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.4.
+
+Query Packs
+-----------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The query :code:`java/sensitive-log` has been improved to no longer report results that are effectively duplicates due to one source flowing to another source.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The query :code:`cpp/bad-strncpy-size` now covers more :code:`strncpy`\ -like functions than before, including :code:`strxfrm`(:code:`_l`), :code:`wcsxfrm`(:code:`_l`), and :code:`stpncpy`. Users of this query may see an increase in results.
+
+Golang
+""""""
+
+* The query :code:`go/path-injection` no longer considers user-controlled numeric or boolean-typed data as potentially dangerous.
+
+Java
+""""
+
+* The query :code:`java/path-injection` now recognises vulnerable APIs defined using the :code:`SinkModelCsv` class with the :code:`create-file` type. Out of the box this includes Apache Commons-IO functions, as well as any user-defined sinks.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* A new query "Android :code:`WebView` that accepts all certificates" (:code:`java/improper-webview-certificate-validation`) has been added. This query finds implementations of :code:`WebViewClient`\ s that accept all certificates in the case of an SSL error.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The IR dataflow library now includes flow through global variables. This enables new findings in many scenarios.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Improved analysis of the Android class :code:`AsyncTask` so that data can properly flow through its methods according to the life-cycle steps described here: https://developer.android.com/reference/android/os/AsyncTask#the-4-steps.
+* Added a data-flow model for the :code:`setProperty` method of :code:`java.util.Properties`. Additional results may be found where relevant data is stored in and then retrieved from a :code:`Properties` instance.
+
+Python
+""""""
+
+* Change :code:`.getASubclass()` on :code:`API::Node` so it allows to follow subclasses even if the class has a class decorator.
+
+Ruby
+""""
+
+* Calls to methods generated by ActiveRecord associations are now recognised as instantiations of ActiveRecord objects. This increases the sensitivity of queries such as :code:`rb/sql-injection` and :code:`rb/stored-xss`.
+* Calls to :code:`ActiveRecord::Base.create` and :code:`ActiveRecord::Base.update` are now recognised as write accesses.
+* Arguments to :code:`Mime::Type#match?` and :code:`Mime::Type#=~` are now recognised as regular expression sources.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added a predicate :code:`getValueConstant` to :code:`AttributeArgument` that yields the argument value as an :code:`Expr` when the value is a constant expression.
+* A new class predicate :code:`MustFlowConfiguration::allowInterproceduralFlow` has been added to the :code:`semmle.code.cpp.ir.dataflow.MustFlow` library. The new predicate can be overridden to disable interprocedural flow.
+* Added subclasses of :code:`BuiltInOperations` for :code:`__builtin_bit_cast`, :code:`__builtin_shuffle`, :code:`__has_unique_object_representations`, :code:`__is_aggregate`, and :code:`__is_assignable`.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.4.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.4.rst
new file mode 100644
index 00000000000..b1436a7bf0a
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.4.rst
@@ -0,0 +1,216 @@
+.. _codeql-cli-2.10.4:
+
+==========================
+CodeQL 2.10.4 (2022-08-31)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.10.4 runs a total of 352 security queries when configured with the Default suite (covering 146 CWE). The Extended suite enables an additional 106 queries (covering 30 more CWE). 12 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+There are no user-facing CLI changes in this release.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The "Cleartext storage of sensitive information in buffer" (:code:`cpp/cleartext-storage-buffer`) query has been improved to produce fewer false positives.
+
+C#
+""
+
+* Parameters of delegates passed to routing endpoint calls like :code:`MapGet` in ASP.NET Core are now considered remote flow sources.
+* The query :code:`cs/unsafe-deserialization-untrusted-input` is not reporting on all calls of :code:`JsonConvert.DeserializeObject` any longer, it only covers cases that explicitly use unsafe serialization settings.
+* Added better support for the SQLite framework in the SQL injection query.
+* File streams are now considered stored flow sources. For example, reading query elements from a file can lead to a Second Order SQL injection alert.
+
+Java
+""""
+
+* The query :code:`java/static-initialization-vector` no longer requires a :code:`Cipher` object to be initialized with :code:`ENCRYPT_MODE` to be considered a valid sink. Also, several new sanitizers were added.
+* Improved sanitizers for :code:`java/sensitive-log`, which removes some false positives and improves performance a bit.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new query, :code:`java/android/implicitly-exported-component`, to detect if components are implicitly exported in the Android manifest.
+* A new query "Use of RSA algorithm without OAEP" (:code:`java/rsa-without-oaep`) has been added. This query finds uses of RSA encryption that don't use the OAEP scheme.
+* Added a new query, :code:`java/android/debuggable-attribute-enabled`, to detect if the :code:`android:debuggable` attribute is enabled in the Android manifest.
+* The query "Using a static initialization vector for encryption" (:code:`java/static-initialization-vector`) has been promoted from experimental to the main query pack. This query was originally `submitted as an experimental query by @artem-smotrakov `__.
+* A new query :code:`java/partial-path-traversal` finds partial path traversal vulnerabilities resulting from incorrectly using
+ :code:`String#startsWith` to compare canonical paths.
+* Added a new query, :code:`java/suspicious-regexp-range`, to detect character ranges in regular expressions that seem to match
+ too many characters.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added a new query, :code:`py/suspicious-regexp-range`, to detect character ranges in regular expressions that seem to match
+ too many characters.
+
+Python
+""""""
+
+* Added a new query, :code:`py/suspicious-regexp-range`, to detect character ranges in regular expressions that seem to match
+ too many characters.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/log-injection`, to detect cases where a malicious user may be able to forge log entries.
+* Added a new query, :code:`rb/incomplete-multi-character-sanitization`. The query finds string transformations that do not replace all occurrences of a multi-character substring.
+* Added a new query, :code:`rb/suspicious-regexp-range`, to detect character ranges in regular expressions that seem to match
+ too many characters.
+
+Query Metadata Changes
+~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The queries :code:`java/redos` and :code:`java/polynomial-redos` now have a tag for CWE-1333.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed that top-level :code:`for await` statements would produce a syntax error. These statements are now parsed correctly.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* All deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+
+C#
+""
+
+* All deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+
+Golang
+""""""
+
+* Go 1.19 is now supported, including adding new taint propagation steps for new standard-library functions introduced in this release.
+* Most deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+* Fixed data-flow to captured variable references.
+* We now assume that if a channel-typed field is only referred to twice in the user codebase, once in a send operation and once in a receive, then data flows from the send to the receive statement. This enables finding some cross-goroutine flow.
+
+Java
+""""
+
+* Added new flow steps for the classes :code:`java.nio.file.Path` and :code:`java.nio.file.Paths`.
+* The class :code:`AndroidFragment` now also models the Android Jetpack version of the :code:`Fragment` class (:code:`androidx.fragment.app.Fragment`).
+* Java 19 builds can now be extracted. There are no non-preview new language features in this release, so the only user-visible change is that the CodeQL extractor will now correctly trace compilations using the JDK 19 release of :code:`javac`.
+* Classes and methods that are seen with several different paths during the extraction process (for example, packaged into different JAR files) now report an arbitrarily selected location via their :code:`getLocation` and :code:`hasLocationInfo` predicates, rather than reporting all of them. This may lead to reduced alert duplication.
+* The query :code:`java/hardcoded-credential-api-call` now recognises methods that consume usernames, passwords and keys from the JSch, Ganymed, Apache SSHD, sshj, Trilead SSH-2, Apache FTPClient and MongoDB projects.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Most deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+
+Python
+""""""
+
+* Most deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+
+Ruby
+""""
+
+* Most deprecated predicates/classes/modules that have been deprecated for over a year have been deleted.
+* Calls to :code:`render` in Rails controllers and views are now recognized as HTTP response bodies.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Many classes/predicates/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+C#
+""
+
+* Many classes/predicates/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+Java
+""""
+
+* Many classes/predicates/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+* The utility files previously in the :code:`semmle.code.java.security.performance` package have been moved to the :code:`semmle.code.java.security.regexp` package.
+
+ The previous files still exist as deprecated aliases.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Many classes/predicates/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+* The utility files previously in the :code:`semmle.javascript.security.performance` package have been moved to the :code:`semmle.javascript.security.regexp` package.
+
+ The previous files still exist as deprecated aliases.
+
+Python
+""""""
+
+* Many classes/predicates/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+* The utility files previously in the :code:`semmle.python.security.performance` package have been moved to the :code:`semmle.python.security.regexp` package.
+
+ The previous files still exist as deprecated aliases.
+
+Ruby
+""""
+
+* The utility files previously in the :code:`codeql.ruby.security.performance` package have been moved to the :code:`codeql.ruby.security.regexp` package.
+
+ The previous files still exist as deprecated aliases.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added support for getting the link targets of global and namespace variables.
+* Added a :code:`BlockAssignExpr` class, which models a :code:`memcpy`\ -like operation used in compiler generated copy/move constructors and assignment operations.
+
+Java
+""""
+
+* Added a new predicate, :code:`requiresPermissions`, in the :code:`AndroidComponentXmlElement` and :code:`AndroidApplicationXmlElement` classes to detect if the element has explicitly set a value for its :code:`android:permission` attribute.
+* Added a new predicate, :code:`hasAnIntentFilterElement`, in the :code:`AndroidComponentXmlElement` class to detect if a component contains an intent filter element.
+* Added a new predicate, :code:`hasExportedAttribute`, in the :code:`AndroidComponentXmlElement` class to detect if a component has an :code:`android:exported` attribute.
+* Added a new class, :code:`AndroidCategoryXmlElement`, to represent a category element in an Android manifest file.
+* Added a new predicate, :code:`getACategoryElement`, in the :code:`AndroidIntentFilterXmlElement` class to get a category element of an intent filter.
+* Added a new predicate, :code:`isInBuildDirectory`, in the :code:`AndroidManifestXmlFile` class. This predicate detects if the manifest file is located in a build directory.
+* Added a new predicate, :code:`isDebuggable`, in the :code:`AndroidApplicationXmlElement` class. This predicate detects if the application element has its :code:`android:debuggable` attribute enabled.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.5.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.5.rst
new file mode 100644
index 00000000000..b7db2218faa
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.10.5.rst
@@ -0,0 +1,20 @@
+.. _codeql-cli-2.10.5:
+
+==========================
+CodeQL 2.10.5 (2022-09-13)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+New Features
+~~~~~~~~~~~~
+
+* You can now define which registries should be used for downloading and publishing CodeQL packs on a per-workspace basis by creating a :code:`codeql-workspace.yml` file and adding a :code:`registries` block. For more infomation, see `About CodeQL Workspaces `__.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.0.rst
new file mode 100644
index 00000000000..e02d1d53a91
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.0.rst
@@ -0,0 +1,365 @@
+.. _codeql-cli-2.11.0:
+
+==========================
+CodeQL 2.11.0 (2022-09-28)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.11.0 runs a total of 353 security queries when configured with the Default suite (covering 148 CWE). The Extended suite enables an additional 109 queries (covering 30 more CWE). 4 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Deprecations
+~~~~~~~~~~~~
+
+* The CodeQL CLI now uses Python 3 to extract both Python 2 and Python 3 databases. Correspondingly, support for using Python 2 to extract Python databases is now deprecated. Starting with version 2.11.3, you will need to install Python 3 to extract Python databases.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.4.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed a bug in the :code:`js/type-confusion-through-parameter-tampering` query that would cause it to ignore sanitizers in branching conditions. The query should now report fewer false positives.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Modernizations from "Cleartext storage of sensitive information in buffer" (:code:`cpp/cleartext-storage-buffer`) have been ported to the "Cleartext storage of sensitive information in file" (:code:`cpp/cleartext-storage-file`), "Cleartext transmission of sensitive information" (:code:`cpp/cleartext-transmission`) and "Cleartext storage of sensitive information in an SQLite database" (:code:`cpp/cleartext-storage-database`) queries. These changes may result in more correct results and fewer false positive results from these queries.
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+C#
+""
+
+* A new extractor option has been introduced for disabling CIL extraction. Either pass :code:`-Ocil=false` to the :code:`codeql` CLI or set the environment variable :code:`CODEQL_EXTRACTOR_CSHARP_OPTION_CIL=false`.
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+Golang
+""""""
+
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+Java
+""""
+
+* The Java extractor now populates the :code:`Method` relating to a :code:`MethodAccess` consistently for calls using an explicit and implicit :code:`this` qualifier. Previously if the method :code:`foo` was inherited from a specialised generic type :code:`ParentType`, then an explicit call :code:`this.foo()` would yield a :code:`MethodAccess` whose :code:`getMethod()` accessor returned the bound method :code:`ParentType.foo`, whereas an implicitly-qualified :code:`foo()` :code:`MethodAccess`\ 's :code:`getMethod()` would return the unbound method :code:`ParentType.foo`. Now both scenarios produce a bound method. This means that all data-flow queries may return more results where a relevant path transits a call to such an implicitly-qualified call to a member method with a bound generic type, while queries that inspect the result of :code:`MethodAccess.getMethod()` may need to tolerate bound generic methods in more circumstances. The queries :code:`java/iterator-remove-failure`, :code:`java/non-static-nested-class`, :code:`java/internal-representation-exposure`, :code:`java/subtle-inherited-call` and :code:`java/deprecated-call` have been amended to properly handle calls to bound generic methods, and in some instances may now produce more results in the explicit-\ :code:`this` case as well.
+* Added taint model for arguments of :code:`java.net.URI` constructors to the queries :code:`java/path-injection` and :code:`java/path-injection-local`.
+* Added new sinks related to Android's :code:`AlarmManager` to the query :code:`java/android/implicit-pendingintents`.
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Improved how the JavaScript parser handles ambiguities between plain JavaScript and dialects such as Flow and E4X that use the same file extension. The parser now prefers plain JavaScript if possible, falling back to dialects only if the source code can not be parsed as plain JavaScript. Previously, there were rare cases where parsing would fail because the parser would erroneously attempt to parse dialect-specific syntax in a regular JavaScript file.
+* The :code:`js/regexp/always-matches` query will no longer report an empty regular expression as always matching, as this is often the intended behavior.
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+Python
+""""""
+
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+Ruby
+""""
+
+* The :code:`rb/unsafe-deserialization` query now includes alerts for user-controlled data passed to :code:`Hash.from_trusted_xml`, since that method can deserialize YAML embedded in the XML, which in turn can result in deserialization of arbitrary objects.
+* The alert message of many queries have been changed to make the message consistent with other languages.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added a new medium-precision query, :code:`cpp/missing-check-scanf`, which detects :code:`scanf` output variables that are used without a proper return-value check to see that they were actually written. A variation of this query was originally contributed as an `experimental query by @ihsinme `__.
+
+Java
+""""
+
+* The query "Server-side template injection" (:code:`java/server-side-template-injection`) has been promoted from experimental to the main query pack. This query was originally `submitted as an experimental query by @porcupineyhairs `__.
+* Added a new query, :code:`java/android/backup-enabled`, to detect if Android applications allow backups.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/hardcoded-data-interpreted-as-code`, to detect cases where hardcoded data is executed as code, a technique associated with backdoors.
+
+Query Metadata Changes
+~~~~~~~~~~~~~~~~~~~~~~
+
+Golang
+""""""
+
+* Added the :code:`security-severity` tag and CWE tag to the :code:`go/insecure-hostkeycallback` query.
+
+Java
+""""
+
+* Removed the :code:`@security-severity` tag from several queries not in the :code:`Security/` folder that also had missing :code:`security` tags.
+
+Python
+""""""
+
+* Added the :code:`security-severity` tag the :code:`py/redos`, :code:`py/polynomial-redos`, and :code:`py/regex-injection` queries.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+C/C++
+"""""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+C#
+""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+Java
+""""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+Python
+""""""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+Ruby
+""""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The :code:`Member.getQualifiedName()` predicate result now includes the qualified name of the declaring type.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Many library models have been rewritten to use dataflow nodes instead of the AST.
+ The types of some classes have been changed, and these changes may break existing code.
+ Other classes and predicates have been renamed, in these cases the old name is still available as a deprecated feature.
+* The basetype of the following list of classes has changed from an expression to a dataflow node, and thus code using these classes might break.
+ The fix to these breakages is usually to use :code:`asExpr()` to get an expression from a dataflow node, or to use :code:`.flow()` to get a dataflow node from an expression.
+
+ * DOM.qll#WebStorageWrite
+ * CryptoLibraries.qll#CryptographicOperation
+ * Express.qll#Express::RequestBodyAccess
+ * HTTP.qll#HTTP::ResponseBody
+ * HTTP.qll#HTTP::CookieDefinition
+ * HTTP.qll#HTTP::ServerDefinition
+ * HTTP.qll#HTTP::RouteSetup
+ * NoSQL.qll#NoSql::Query
+ * SQL.qll#SQL::SqlString
+ * SQL.qll#SQL::SqlSanitizer
+ * HTTP.qll#ResponseBody
+ * HTTP.qll#CookieDefinition
+ * HTTP.qll#ServerDefinition
+ * HTTP.qll#RouteSetup
+ * HTTP.qll#HTTP::RedirectInvocation
+ * HTTP.qll#RedirectInvocation
+ * Express.qll#Express::RouterDefinition
+ * AngularJSCore.qll#LinkFunction
+ * Connect.qll#Connect::StandardRouteHandler
+ * CryptoLibraries.qll#CryptographicKeyCredentialsExpr
+ * AWS.qll#AWS::Credentials
+ * Azure.qll#Azure::Credentials
+ * Connect.qll#Connect::Credentials
+ * DigitalOcean.qll#DigitalOcean::Credentials
+ * Express.qll#Express::Credentials
+ * NodeJSLib.qll#NodeJSLib::Credentials
+ * PkgCloud.qll#PkgCloud::Credentials
+ * Request.qll#Request::Credentials
+ * ServiceDefinitions.qll#InjectableFunctionServiceRequest
+ * SensitiveActions.qll#SensitiveVariableAccess
+ * SensitiveActions.qll#CleartextPasswordExpr
+ * Connect.qll#Connect::ServerDefinition
+ * Restify.qll#Restify::ServerDefinition
+ * Connect.qll#Connect::RouteSetup
+ * Express.qll#Express::RouteSetup
+ * Fastify.qll#Fastify::RouteSetup
+ * Hapi.qll#Hapi::RouteSetup
+ * Koa.qll#Koa::RouteSetup
+ * Restify.qll#Restify::RouteSetup
+ * NodeJSLib.qll#NodeJSLib::RouteSetup
+ * Express.qll#Express::StandardRouteHandler
+ * Express.qll#Express::SetCookie
+ * Hapi.qll#Hapi::RouteHandler
+ * HTTP.qll#HTTP::Servers::StandardHeaderDefinition
+ * HTTP.qll#Servers::StandardHeaderDefinition
+ * Hapi.qll#Hapi::ServerDefinition
+ * Koa.qll#Koa::AppDefinition
+ * SensitiveActions.qll#SensitiveCall
+
+Ruby
+""""
+
+* :code:`import ruby` no longer brings the standard Ruby AST library into scope; it instead brings a module :code:`Ast` into scope, which must be imported. Alternatively, it is also possible to import :code:`codeql.ruby.AST`.
+* Changed the :code:`HTTP::Client::Request` concept from using :code:`MethodCall` as base class, to using :code:`DataFlow::Node` as base class. Any class that extends :code:`HTTP::Client::Request::Range` must be changed, but if you only use the member predicates of :code:`HTTP::Client::Request`, no changes are required.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The virtual dispatch relation used in data flow now favors summary models over source code for dispatch to interface methods from :code:`java.util` unless there is evidence that a specific source implementation is reachable. This should provide increased precision for any projects that include, for example, custom :code:`List` or :code:`Map` implementations.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 4.8.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Added new sinks to the query :code:`java/android/implicit-pendingintents` to take into account the classes :code:`androidx.core.app.NotificationManagerCompat` and :code:`androidx.core.app.AlarmManagerCompat`.
+* Added new flow steps for :code:`androidx.core.app.NotificationCompat` and its inner classes.
+* Added flow sinks, sources and summaries for the Kotlin standard library.
+* Added flow summary for :code:`org.springframework.data.repository.CrudRepository.save()`.
+* Added new flow steps for the following Android classes:
+
+ * :code:`android.content.ContentResolver`
+ * :code:`android.content.ContentProviderClient`
+ * :code:`android.content.ContentProviderOperation`
+ * :code:`android.content.ContentProviderOperation$Builder`
+ * :code:`android.content.ContentProviderResult`
+ * :code:`android.database.Cursor`
+
+* Added taint flow models for the :code:`java.lang.String.(charAt|getBytes)` methods.
+* Improved taint flow models for the :code:`java.lang.String.(replace|replaceFirst|replaceAll)` methods. Additional results may be found where users do not properly sanitize their inputs.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* A model for the :code:`mermaid` library has been added. XSS queries can now detect flow through the :code:`render` method of the :code:`mermaid` library.
+
+Python
+""""""
+
+* Changed :code:`CallNode.getArgByName` such that it has results for keyword arguments given after a dictionary unpacking argument, as the :code:`bar=2` argument in :code:`func(foo=1, **kwargs, bar=2)`.
+* :code:`getStarArg` member-predicate on :code:`Call` and :code:`CallNode` has been changed for calls that have multiple :code:`*args` arguments (for example :code:`func(42, *my_args, *other_args)`): Instead of producing no results, it will always have a result for the *first* such :code:`*args` argument.
+* Reads of global/non-local variables (without annotations) inside functions defined on classes now works properly in the case where the class had an attribute defined with the same name as the non-local variable.
+
+Ruby
+""""
+
+* Uses of :code:`ActionView::FileSystemResolver` are now recognized as filesystem accesses.
+* Accesses of ActiveResource models are now recognized as HTTP requests.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+C#
+""
+
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+Golang
+""""""
+
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+Java
+""""
+
+* The predicate :code:`Annotation.getAValue()` has been deprecated because it might lead to obtaining the value of the wrong annotation element by accident. :code:`getValue(string)` (or one of the value type specific predicates) should be used to explicitly specify the name of the annotation element.
+* The predicate :code:`Annotation.getAValue(string)` has been renamed to :code:`getAnArrayValue(string)`.
+* The predicate :code:`SuppressWarningsAnnotation.getASuppressedWarningLiteral()` has been deprecated because it unnecessarily restricts the result type; :code:`getASuppressedWarning()` should be used instead.
+* The predicates :code:`TargetAnnotation.getATargetExpression()` and :code:`RetentionAnnotation.getRetentionPolicyExpression()` have been deprecated because getting the enum constant read expression is rarely useful, instead the corresponding predicates for getting the name of the referenced enum constants should be used.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+Python
+""""""
+
+* Some unused predicates in :code:`SsaDefinitions.qll`, :code:`TObject.qll`, :code:`protocols.qll`, and the :code:`pointsto/` folder have been deprecated.
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+Ruby
+""""
+
+* Some classes/modules with upper-case acronyms in their name have been renamed to follow our style-guide.
+ The old name still exists as a deprecated alias.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added subclasses of :code:`BuiltInOperations` for :code:`__is_same`, :code:`__is_function`, :code:`__is_layout_compatible`, :code:`__is_pointer_interconvertible_base_of`, :code:`__is_array`, :code:`__array_rank`, :code:`__array_extent`, :code:`__is_arithmetic`, :code:`__is_complete_type`, :code:`__is_compound`, :code:`__is_const`, :code:`__is_floating_point`, :code:`__is_fundamental`, :code:`__is_integral`, :code:`__is_lvalue_reference`, :code:`__is_member_function_pointer`, :code:`__is_member_object_pointer`, :code:`__is_member_pointer`, :code:`__is_object`, :code:`__is_pointer`, :code:`__is_reference`, :code:`__is_rvalue_reference`, :code:`__is_scalar`, :code:`__is_signed`, :code:`__is_unsigned`, :code:`__is_void`, and :code:`__is_volatile`.
+
+Java
+""""
+
+* Added a new predicate, :code:`allowsBackup`, in the :code:`AndroidApplicationXmlElement` class. This predicate detects if the application element does not disable the :code:`android:allowBackup` attribute.
+* The predicates of the CodeQL class :code:`Annotation` have been improved:
+
+ * Convenience value type specific predicates have been added, such as :code:`getEnumConstantValue(string)` or :code:`getStringValue(string)`.
+ * Convenience predicates for elements with array values have been added, such as :code:`getAnEnumConstantArrayValue(string)`. While the behavior of the existing predicates has not changed, usage of them should be reviewed (or replaced with the newly added predicate) to make sure they work correctly for elements with array values.
+ * Some internal CodeQL usage of the :code:`Annotation` predicates has been adjusted and corrected; this might affect the results of some queries.
+
+* New predicates have been added to the CodeQL class :code:`Annotatable` to support getting declared and associated annotations. As part of that, :code:`hasAnnotation()` has been changed to also consider inherited annotations, to be consistent with :code:`hasAnnotation(string, string)` and :code:`getAnAnnotation()`. The newly added predicate :code:`hasDeclaredAnnotation()` can be used as replacement for the old functionality.
+* New predicates have been added to the CodeQL class :code:`AnnotationType` to simplify getting information about usage of JDK meta-annotations, such as :code:`@Retention`.
+
+Shared Libraries
+----------------
+
+Initial Release
+~~~~~~~~~~~~~~~
+
+Static Single Assignment (SSA)
+""""""""""""""""""""""""""""""
+
+* Initial release. Extracted common SSA code into a library pack to share code between languages.
+
+Database of Common Typographical Errors
+"""""""""""""""""""""""""""""""""""""""
+
+* Initial release. Share the database of common typographical errors between languages.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.1.rst
new file mode 100644
index 00000000000..f46576810cb
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.1.rst
@@ -0,0 +1,145 @@
+.. _codeql-cli-2.11.1:
+
+==========================
+CodeQL 2.11.1 (2022-10-11)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.11.1 runs a total of 354 security queries when configured with the Default suite (covering 148 CWE). The Extended suite enables an additional 109 queries (covering 30 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* Pack installation using the CodeQL Packaging beta will now fail if a compatible version cannot be found. This replaces the previous behavior where :code:`codeql pack download` and related commands would instead install the latest version of the pack in this situation.
+
+Bug Fixes
+~~~~~~~~~
+
+* It is no longer an error to call :code:`codeql pack create ` with a :code:`` option pointing to a file name. The CLI will walk up the directory tree and run the command in the first directory containing the :code:`qlpack.yml` or :code:`codeql-pack.yml` file.
+* Fixed a concurrency error observed when using :code:`codeql database import` or
+ :code:`codeql database finalize` with multiple threads and multiple additional databases on a C++ codebase.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The :code:`--[no-]count-lines` option to :code:`codeql database create` and related commands is now deprecated and will be removed in a future release of the CodeQL CLI (earliest 2.12.0). It is replaced by
+ :code:`--[no-]calculate-baseline` to reflect the additional baseline information that is now captured as of this release.
+
+New Features
+~~~~~~~~~~~~
+
+* Subcommands that compile QL accept a new :code:`--no-release-compatibility` option. It does nothing for now, but in the future it will be used to control a trade-off between query performance and compatibility with older/newer releases of the QL evaluator.
+* :code:`codeql database analyze` and related commands now support absolute paths containing the :code:`@` or :code:`:` characters when specifying which queries to run. To reference a query file, directory, or suite whose path contains a literal :code:`@` or :code:`:`, prefix the query specifier with :code:`path:`, for example:
+
+ .. code-block:: shell
+
+ codeql database analyze --format=sarif-latest --output=results path:C:/Users/ci/workspace@2/security/query.ql
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The alert message of many queries have been changed to better follow the style guide and make the message consistent with other languages.
+
+C#
+""
+
+* The alert message of many queries have been changed to better follow the style guide and make the message consistent with other languages.
+
+Java
+""""
+
+* The alert message of many queries have been changed to better follow the style guide and make the message consistent with other languages.
+* :code:`PathSanitizer.qll` has been promoted from experimental to the main query pack. This sanitizer was originally `submitted as part of an experimental query by @luchua-bc `__.
+* The queries :code:`java/path-injection`, :code:`java/path-injection-local` and :code:`java/zipslip` now use the sanitizers provided by :code:`PathSanitizer.qll`.
+
+Ruby
+""""
+
+* The :code:`rb/xxe` query has been updated to add the following sinks for XML external entity expansion:
+
+ #. Calls to parse XML using :code:`LibXML` when its :code:`default_substitute_entities` option is enabled.
+ #. Uses of the Rails methods :code:`ActiveSupport::XmlMini.parse`, :code:`Hash.from_xml`, and :code:`Hash.from_trusted_xml` when :code:`ActiveSupport::XmlMini` is configured to use :code:`LibXML` as its backend, and its :code:`default_substitute_entities` option is enabled.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new query, :code:`java/android/webview-debugging-enabled`, to detect instances of WebView debugging being enabled in production builds.
+
+Language Libraries
+------------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* :code:`DateTime` expressions are now considered simple type sanitizers. This affects a wide range of security queries.
+* ASP.NET Core controller definition has been made more precise. The amount of introduced taint sources or eliminated false positives should be low though, since the most common pattern is to derive all user defined ASP.NET Core controllers from the standard Controller class, which is not affected.
+
+Golang
+""""""
+
+* Added support for :code:`BeegoInput.RequestBody` as a source of untrusted data.
+
+Java
+""""
+
+* Added external flow sources for the intents received in exported Android services.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Several of the SQL and NoSQL library models have improved, leading to more results for the :code:`js/sql-injection` query,
+ and in some cases the :code:`js/missing-rate-limiting` query.
+
+Python
+""""""
+
+* Added the ability to refer to subscript operations in the API graph. It is now possible to write :code:`response().getMember("cookies").getASubscript()` to find code like :code:`resp.cookies["key"]` (assuming :code:`response` returns an API node for response objects).
+* Added modeling of creating Flask responses with :code:`flask.jsonify`.
+
+Ruby
+""""
+
+* The following classes have been moved from :code:`codeql.ruby.frameworks.ActionController` to :code:`codeql.ruby.frameworks.Rails`\ :
+
+ * :code:`ParamsCall`, now accessed as :code:`Rails::ParamsCall`.
+ * :code:`CookieCall`, now accessed as :code:`Rails::CookieCall`.
+
+* The following classes have been moved from :code:`codeql.ruby.frameworks.ActionView` to :code:`codeql.ruby.frameworks.Rails`\ :
+
+ * :code:`HtmlSafeCall`, now accessed as :code:`Rails::HtmlSafeCall`.
+ * :code:`HtmlEscapeCall`, now accessed as :code:`Rails::HtmlEscapeCall`.
+ * :code:`RenderCall`, now accessed as :code:`Rails::RenderCall`.
+ * :code:`RenderToCall`, now accessed as :code:`Rails::RenderToCall`.
+
+* Subclasses of :code:`ActionController::Metal` are now recognised as controllers.
+* :code:`ActionController::DataStreaming::send_file` is now recognized as a
+ :code:`FileSystemAccess`.
+* Various XSS sinks in the ActionView library are now recognized.
+* Calls to :code:`ActiveRecord::Base.create` are now recognized as model instantiations.
+* Various code executions, command executions and HTTP requests in the ActiveStorage library are now recognized.
+* :code:`MethodBase` now has two new predicates related to visibility: :code:`isPublic` and
+ :code:`isProtected`. These hold, respectively, if the method is public or protected.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.2.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.2.rst
new file mode 100644
index 00000000000..1156c88840f
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.2.rst
@@ -0,0 +1,175 @@
+.. _codeql-cli-2.11.2:
+
+==========================
+CodeQL 2.11.2 (2022-10-25)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.11.2 runs a total of 357 security queries when configured with the Default suite (covering 150 CWE). The Extended suite enables an additional 111 queries (covering 31 more CWE). 5 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* Bundling and publishing a CodeQL pack will no longer include nested CodeQL packs. If you want to include a nested pack in your published pack,
+ then you must explicitly include it using the :code:`include` property in the top-level :code:`qlpack.yml` file.
+
+ For example, if your package structure looks like this:
+
+ .. code-block:: text
+
+ qlpack.yml
+ nested-pack
+ ∟ qlpack.yml
+ query.ql
+
+ then the contents of :code:`nested-pack` will not be included by default within the published package. To include :code:`nested-pack`, add an entry like this to the top level :code:`qlpack.yml` file:
+
+ .. code-block:: yaml
+
+ include:
+ - nested-pack/**
+
+Bug Fixes
+~~~~~~~~~
+
+* Using the :code:`--codescanning-config=` option in
+ :code:`codeql database init` will now correctly process the :code:`paths` and
+ :code:`pathsIgnore` properties of the configuration file in a way that is identical to the behavior of the :code:`codeql-action`. Previously, :code:`paths` or :code:`pathsIgnore` entries that end in :code:`/**` or start with :code:`/` were incorrectly rejected by the CLI.
+
+* Fixed a bug where the :code:`--compilation-cache` option to
+ :code:`codeql pack publish` and :code:`codeql pack create` was being ignored when creating a query pack. Now, the indicated cache is used when pre-compiling the queries in it.
+
+* Fixed a bug that would make the "Show DIL" command in the VSCode extension display nothing.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* Emit a detailed warning if package resolution fails, the legacy
+ :code:`--search-path` option is provided, *and* there is at least one referenced pack that does not use legacy package resolution.
+ In this case, :code:`--additional-packs` should be used to extend the search to additional directories, instead of :code:`--search-path`.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+Python
+""""""
+
+* Fixed how :code:`flask.request` is modeled as a RemoteFlowSource, such that we show fewer duplicated alert messages for Code Scanning alerts. The import, such as :code:`from flask import request`, will now be shown as the first step in a path explanation.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The "Unterminated variadic call" (:code:`cpp/unterminated-variadic-call`) query has been tuned to produce fewer false positive results.
+* Fixed false positives from the "Unused static function" (:code:`cpp/unused-static-function`) query in files that had errors during compilation.
+
+Golang
+""""""
+
+* The alert messages of many queries were changed to better follow the style guide and make the messages consistent with other languages.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Removed some false positives from the :code:`js/file-system-race` query by requiring that the file-check dominates the file-access.
+* Improved taint tracking through :code:`JSON.stringify` in cases where a tainted value is stored somewhere in the input object.
+
+Python
+""""""
+
+* Added model of :code:`cx_Oracle`, :code:`oracledb`, :code:`phonenixdb` and :code:`pyodbc` PyPI packages as a SQL interface following PEP249, resulting in additional sinks for :code:`py/sql-injection`.
+* Added model of :code:`executemany` calls on PEP-249 compliant database APIs, resulting in additional sinks for :code:`py/sql-injection`.
+* Added model of :code:`pymssql` PyPI package as a SQL interface following PEP249, resulting in additional sinks for :code:`py/sql-injection`.
+* The alert messages of many queries were changed to better follow the style guide and make the messages consistent with other languages.
+
+Ruby
+""""
+
+* HTTP response header and body writes via :code:`ActionDispatch::Response` are now recognized.
+* The :code:`rb/path-injection` query now treats the :code:`file:` argument of the Rails :code:`render` method as a sink.
+* The alert messages of many queries were changed to better follow the style guide and make the messages consistent with other languages.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added a new medium-precision query, :code:`cpp/comma-before-misleading-indentation`, which detects instances of whitespace that have readability issues.
+
+Java
+""""
+
+* Added a new query, :code:`java/android/incomplete-provider-permissions`, to detect if an Android ContentProvider is not protected with a correct set of permissions.
+* A new query "Uncontrolled data used in content resolution" (:code:`java/androd/unsafe-content-uri-resolution`) has been added. This query finds paths from user-provided data to URI resolution operations in Android's :code:`ContentResolver` without previous validation or sanitization.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/non-constant-kernel-open`, to detect uses of Kernel.open and related methods with non-constant values.
+* Added a new query, :code:`rb/sensitive-get-query`, to detect cases where sensitive data is read from the query parameters of an HTTP :code:`GET` request.
+
+Language Libraries
+------------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Added support for common patterns involving :code:`Stream.collect` and common collectors like :code:`Collectors.toList()`.
+* The class :code:`TypeVariable` now also extends :code:`Modifiable`.
+* Added data flow steps for tainted Android intents that are sent to services and receivers.
+* Improved the data flow step for tainted Android intents that are sent to activities so that more cases are covered.
+
+Python
+""""""
+
+* Fixed labels in the API graph pertaining to definitions of subscripts. Previously, these were found by :code:`getMember` rather than :code:`getASubscript`.
+* Added edges for indices of subscripts to the API graph. Now a subscripted API node will have an edge to the API node for the index expression. So if :code:`foo` is matched by API node :code:`A`, then :code:`"key"` in :code:`foo["key"]` will be matched by the API node :code:`A.getIndex()`. This can be used to track the origin of the index.
+* Added member predicate :code:`getSubscriptAt(API::Node index)` to :code:`API::Node`. Like :code:`getASubscript()`, this will return an API node that matches a subscript of the node, but here it will be restricted to subscripts where the index matches the :code:`index` parameter.
+* Added convenience predicate :code:`getSubscript("key")` to obtain a subscript at a specific index, when the index happens to be a statically known string.
+
+Ruby
+""""
+
+* The hashing algorithms from :code:`Digest` and :code:`OpenSSL::Digest` are now recognized and can be flagged by the :code:`rb/weak-cryptographic-algorithm` query.
+* More sources of remote input arising from methods on :code:`ActionDispatch::Request` are now recognized.
+* The response value returned by the :code:`Faraday#run_request` method is now also considered a source of remote input.
+* :code:`ActiveJob::Serializers.deserialize` is considered to be a code execution sink.
+* Calls to :code:`params` in :code:`ActionMailer` classes are now treated as sources of remote user input.
+* Taint flow through :code:`ActionController::Parameters` is tracked more accurately.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Deprecated :code:`ContextStartActivityMethod`. Use :code:`StartActivityMethod` instead.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new predicate, :code:`hasIncompletePermissions`, in the :code:`AndroidProviderXmlElement` class. This predicate detects if a provider element does not provide both read and write permissions.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.3.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.3.rst
new file mode 100644
index 00000000000..893d8b52ae1
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.3.rst
@@ -0,0 +1,107 @@
+.. _codeql-cli-2.11.3:
+
+==========================
+CodeQL 2.11.3 (2022-11-11)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.11.3 runs a total of 358 security queries when configured with the Default suite (covering 150 CWE). The Extended suite enables an additional 111 queries (covering 31 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The :code:`codeql pack ls --format json` deep plumbing command now returns only the :code:`name` and :code:`version` properties for each found pack.
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* :code:`codeql pack download`, :code:`codeql pack install`, and :code:`codeql pack add` will ignore CodeQL packs with pre-release versions, unless the
+ :code:`--allow-prerelease` option is passed to the command. This brings these commands into alignment with :code:`codeql pack publish` that will avoid publishing CodeQL packs with pre-release versions unless the
+ :code:`--allow-prerelease` option is specified. Pre-release versions have the following format: :code:`X.Y.Z-qualifier` where :code:`X`, :code:`Y`, and :code:`Z` are respectively the major, minor, and patch number. :code:`qualifier` is the pre-release version. For more information about pre-releases, see the
+ \ `Semantic Versioning specification `__.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The :code:`--[no-]fast-compilation` option to :code:`codeql query compile` is now deprecated.
+
+New Features
+~~~~~~~~~~~~
+
+* :code:`codeql resolve files` and :code:`codeql database index-files` have a new
+ :code:`--find-any` option, which finds at most one match.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Apache Commons Text that is bundled with the CodeQL CLI has been updated to version 1.10.0. While previous releases shipped with version 1.6 of the library, no part of the CodeQL CLI references the :code:`StringSubstitutor` class that the recently disclosed
+ \ `CVE-2022-42889 `__ vulnerability applies to. We therefore do not believe that running previous releases of CodeQL exposes users to this vulnerability.
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.5.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Fixed a bug in :code:`cpp/jsf/av-rule-76` that caused the query to miss results when an implicitly-defined copy constructor or copy assignment operator was generated.
+
+Golang
+""""""
+
+* Query :code:`go/clear-text-logging` now excludes :code:`GetX` methods of protobuf :code:`Message` structs, except where taint is specifically known to belong to the right field. This is to avoid FPs where taint is written to one field and then spuriously read from another.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added sources for user defined path and query parameters in :code:`Next.js`.
+* The alert message of many queries have been changed to better follow the style guide and make the message consistent with other languages.
+
+Ruby
+""""
+
+* The :code:`rb/weak-cryptographic-algorithm` has been updated to no longer report uses of hash functions such as :code:`MD5` and :code:`SHA1` even if they are known to be weak. These hash algorithms are used very often in non-sensitive contexts, making the query too imprecise in practice.
+
+New Queries
+~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added a new query, :code:`js/second-order-command-line-injection`, to detect shell commands that may execute arbitrary code when the user has control over
+ the arguments to a command-line program.
+ This currently flags up unsafe invocations of git and hg.
+
+Language Libraries
+------------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Fixed bugs in the :code:`FormatLiteral` class that were causing :code:`getMaxConvertedLength` and related predicates to return no results when the format literal was :code:`%e`, :code:`%f` or :code:`%g` and an explicit precision was specified.
+
+Ruby
+""""
+
+* There was a bug in :code:`TaintTracking::localTaint` and :code:`TaintTracking::localTaintStep` such that they only tracked non-value-preserving flow steps. They have been fixed and now also include value-preserving steps.
+* Instantiations using :code:`Faraday::Connection.new` are now recognized as part of :code:`FaradayHttpRequest`\ s, meaning they will be considered as sinks for queries such as :code:`rb/request-forgery`.
+* Taint flow is now tracked through extension methods on :code:`Hash`, :code:`String` and
+ :code:`Object` provided by :code:`ActiveSupport`.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.4.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.4.rst
new file mode 100644
index 00000000000..24ebf7200be
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.4.rst
@@ -0,0 +1,147 @@
+.. _codeql-cli-2.11.4:
+
+==========================
+CodeQL 2.11.4 (2022-11-24)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.11.4 runs a total of 361 security queries when configured with the Default suite (covering 150 CWE). The Extended suite enables an additional 112 queries (covering 32 more CWE). 4 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* CodeQL 2.11.1 to 2.11.3 contained a bug in `indirect build tracing `__ on Windows when using :code:`codeql database init` with the |link-code-trace-process-level-1|_ flag.
+ In these versions, when :code:`--trace-process-level` was set to a value greater than zero,
+ (or left at the default value of 1), CodeQL attempted to inject its build tracer at a higher level in the process tree than the requested process level.
+ This could lead to errors of the form "No source code found" or
+ "Process tree ended before reaching required level".
+ From 2.11.4 onwards, the CodeQL build tracer is injected at the requested process level.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The :code:`--[no-]fast-compilation` option to :code:`codeql test run` is now deprecated.
+
+New Features
+~~~~~~~~~~~~
+
+* Kotlin support is now in beta. This means that Java analyses will also include Kotlin code by default. Kotlin support can be disabled by setting :code:`CODEQL_EXTRACTOR_JAVA_AGENT_DISABLE_KOTLIN` to :code:`true` in the environment.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed a bug that would cause the extractor to crash when an :code:`import` type is used in the :code:`extends` clause of an :code:`interface`.
+* Fixed an issue with multi-line strings in YAML files being associated with an invalid location,
+ causing alerts related to such strings to appear at the top of the YAML file.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for :code:`@hapi/glue` and Hapi plugins to the :code:`frameworks/Hapi.qll` library.
+
+Ruby
+""""
+
+* The :code:`rb/sql-injection` query now considers consider SQL constructions, such as calls to :code:`Arel.sql`, as sinks.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* The query :code:`java/insufficient-key-size` has been promoted from experimental to the main query pack. Its results will now appear by default. This query was originally `submitted as an experimental query by @luchua-bc `__.
+* Added a new query, :code:`java/android/sensitive-keyboard-cache`, to detect instances of sensitive information possibly being saved to the Android keyboard cache.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/shell-command-constructed-from-input`, to detect libraries that unsafely construct shell commands from their inputs.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 4.9.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The :code:`[Summary|Sink|Source]ModelCsv` classes have been deprecated and Models as Data models are defined as data extensions instead.
+
+Java
+""""
+
+* The ReDoS libraries in :code:`semmle.code.java.security.regexp` has been moved to a shared pack inside the :code:`shared/` folder, and the previous location has been deprecated.
+* Added data flow summaries for tainted Android intents sent to activities via :code:`Activity.startActivities`.
+
+Python
+""""""
+
+* The ReDoS libraries in :code:`semmle.code.python.security.regexp` have been moved to a shared pack inside the :code:`shared/` folder, and the previous location has been deprecated.
+
+Ruby
+""""
+
+* Data flow through the :code:`ActiveSupport` extension :code:`Enumerable#index_by` is now modeled.
+* The :code:`codeql.ruby.Concepts` library now has a :code:`SqlConstruction` class, in addition to the existing :code:`SqlExecution` class.
+* Calls to :code:`Arel.sql` are now modeled as instances of the new :code:`SqlConstruction` concept.
+* Arguments to RPC endpoints (public methods) on subclasses of :code:`ActionCable::Channel::Base` are now recognized as sources of remote user input.
+* Taint flow through the :code:`ActiveSupport` extensions :code:`Hash#reverse_merge` and :code:`Hash:reverse_merge!`, and their aliases, is now modeled more generally, where previously it was only modeled in the context of :code:`ActionController` parameters.
+* Calls to :code:`logger` in :code:`ActiveSupport` actions are now recognised as logger instances.
+* Calls to :code:`send_data` in :code:`ActiveSupport` actions are recognised as HTTP responses.
+* Calls to :code:`body_stream` in :code:`ActiveSupport` actions are recognised as HTTP request accesses.
+* The :code:`ActiveSupport` extensions :code:`Object#try` and :code:`Object#try!` are now recognised as code executions.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* Kotlin support is now in beta. This means that Java analyses will also include Kotlin code by default. Kotlin support can be disabled by setting :code:`CODEQL_EXTRACTOR_JAVA_AGENT_DISABLE_KOTLIN` to :code:`true` in the environment.
+* The new :code:`string Compilation.getInfo(string)` predicate provides access to some information about compilations.
+
+Shared Libraries
+----------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Regular Expression Analysis
+"""""""""""""""""""""""""""
+
+* Initial release. Extracted common regex related code, including the ReDoS analysis, into a library pack to share code between languages.
+
+.. |link-code-trace-process-level-1| replace:: :code:`--trace-process-level`\
+.. _link-code-trace-process-level-1: https://codeql.github.com/docs/codeql-cli/manual/database-init/#cmdoption-codeql-database-init-trace-process-level
+
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.5.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.5.rst
new file mode 100644
index 00000000000..6ea919788bd
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.5.rst
@@ -0,0 +1,20 @@
+.. _codeql-cli-2.11.5:
+
+==========================
+CodeQL 2.11.5 (2022-12-07)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug that could cause log summary generation to fail in vscode.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.6.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.6.rst
new file mode 100644
index 00000000000..81f0bc23a6f
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.11.6.rst
@@ -0,0 +1,39 @@
+.. _codeql-cli-2.11.6:
+
+==========================
+CodeQL 2.11.6 (2022-12-13)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* Java and Kotlin analyses in this release of the CLI and all earlier releases are incompatible with Kotlin 1.7.30 and later. To prevent code scanning alerts being spuriously dismissed, Java and Kotlin analyses will now fail when using Kotlin 1.7.30 or later.
+
+ If you are unable to use Kotlin 1.7.29 or earlier, you can disable Kotlin support by setting
+ :code:`CODEQL_EXTRACTOR_JAVA_AGENT_DISABLE_KOTLIN` to :code:`true` in the environment.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug where it was not possible to run queries in CodeQL query packs for C# that use the legacy :code:`libraryPathDependencies` property in their :code:`qlpack.yml` file. The associated error message complained about undefined extensional predicates.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Kotlin extraction will now fail if the Kotlin version in use is at least 1.7.30. This is to ensure using an as-yet-unsupported version is noticable, rather than silently failing to extract Kotlin code and therefore producing false-negative results.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.0.rst
new file mode 100644
index 00000000000..b0888bd8bea
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.0.rst
@@ -0,0 +1,325 @@
+.. _codeql-cli-2.12.0:
+
+==========================
+CodeQL 2.12.0 (2023-01-10)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.0 runs a total of 365 security queries when configured with the Default suite (covering 150 CWE). The Extended suite enables an additional 116 queries (covering 32 more CWE). 8 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The :code:`--[no-]count-lines` option to :code:`codeql database create` and related commands that was deprecated in 2.11.1 has been removed. Users of this option should instead pass
+ :code:`--[no-]calculate-baseline`.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug where the :code:`codeql pack install` command would fail if a `CodeQL configuration file `__ is used and the :code:`--additional-packs` option is specified.
+
+New Features
+~~~~~~~~~~~~
+
+* Query packs created by :code:`codeql pack create`, :code:`codeql pack bundle`, and :code:`codeql pack release` now contain precompiled queries in a new format that aims to be compatible with future (and, to a certain extent, past) releases of the CodeQL CLI. Previously the precompiled queries were in a format specific to each CLI release, and all other releases would need to re-compile queries.
+
+ Published packs contain precompiled queries in files with a :code:`.qlx` extension located next to each query's :code:`.ql` source file. In case of differences between the :code:`.ql` and :code:`.qlx` files, the :code:`.qlx` file takes priority when evaluating queries from the command line, so if you need to modify a published pack, be sure to delete the :code:`.qlx` files first.
+
+ A new :code:`--precompile` flag to :code:`codeql query compile` can be used to construct :code:`*.qlx` file explicitly, but in all usual cases it should be enough to rely on :code:`codeql pack create` doing the right thing.
+
+* The :code:`codeql database init` command now accepts a PAT that allows you to download queries from external, private repositories when using the :code:`--codescanning-config ` option. For example, you can specify the following queries block in the config file, which will checkout the main branch of the :code:`codeql-test/my-private-repository` repository and evaluate any queries found in that repository:
+
+ .. code-block:: yaml
+
+ queries:
+ - codeql-test/my-private-repository@main
+
+ If the repository is private, you can add a :code:`--external-repository-token-stdin` option and supply a PAT with appropriate permissions via standard input. For more information on queries and external repositories in Code Scanning, see `Using queries in QL packs `__.
+
+* The baseline information produced by :code:`codeql database init` and
+ :code:`codeql database create` now accounts for
+ |link-code-paths-and-code-paths-ignore-configuration-1|_.
+
+* In the VS Code extension, recursive calls will be marked with inlay hints. These can be disabled with the global inlay hints setting
+ (:code:`editor.inlayHints.enabled`). If you just want to disable them for
+ codeql the settings can be scoped to just codeql files (language id is :code:`ql`).
+ See `Language Specific Editor Settings `__ in the VS Code documentation for more information.
+
+* The CLI now gives a more helpful error message when asked to run queries on a database that has not been finalized.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+C#
+""
+
+* Fixes a bug where the Owin.qll framework library will look for "URI" instead of "Uri" in the OwinRequest class.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`// codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`// lgtm` and :code:`// lgtm[query-id]` comments can now also be placed on the line before an alert.
+* The :code:`cpp/missing-check-scanf` query no longer reports the free'ing of :code:`scanf` output variables as potential reads.
+
+C#
+""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`// codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`// lgtm` and :code:`// lgtm[query-id]` comments can now also be placed on the line before an alert.
+* The extensible predicates for Models as Data have been renamed (the :code:`ext` prefix has been removed). As an example, :code:`extSummaryModel` has been renamed to :code:`summaryModel`.
+
+Golang
+""""""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`// codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`// lgtm` and :code:`// lgtm[query-id]` comments can now also be placed on the line before an alert.
+
+Java
+""""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`// codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`// lgtm` and :code:`// lgtm[query-id]` comments can now also be placed on the line before an alert.
+* The extensible predicates for Models as Data have been renamed (the :code:`ext` prefix has been removed). As an example, :code:`extSummaryModel` has been renamed to :code:`summaryModel`.
+* The query :code:`java/misnamed-type` is now enabled for Kotlin.
+* The query :code:`java/non-serializable-field` is now enabled for Kotlin.
+* Fixed an issue in the query :code:`java/android/implicit-pendingintents` by which an implicit Pending Intent marked as immutable was not correctly recognized as such.
+* The query :code:`java/maven/non-https-url` no longer alerts about disabled repositories.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`// codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`// lgtm` and :code:`// lgtm[query-id]` comments can now also be placed on the line before an alert.
+
+Python
+""""""
+
+* The :code:`analysis/AlertSuppression.ql` query has moved to the root folder. Users that refer to this query by path should update their configurations. The query has been updated to support the new :code:`# codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`# lgtm` and :code:`# lgtm[query-id]` comments can now also be placed on the line before an alert.
+* Bumped the minimum keysize we consider secure for elliptic curve cryptography from 224 to 256 bits, following current best practices. This might effect results from the *Use of weak cryptographic key* (:code:`py/weak-crypto-key`) query.
+* Added modeling of :code:`getpass.getpass` as a source of passwords, which will be an additional source for :code:`py/clear-text-logging-sensitive-data`, :code:`py/clear-text-storage-sensitive-data`, and :code:`py/weak-sensitive-data-hashing`.
+
+Ruby
+""""
+
+* The :code:`AlertSuppression.ql` query has been updated to support the new :code:`# codeql[query-id]` supression comments. These comments can be used to suppress an alert and must be placed on a blank line before the alert. In addition the legacy :code:`# lgtm` and :code:`# lgtm[query-id]` comments can now also be placed on the line before an alert.
+* Extended the :code:`rb/kernel-open` query with following sinks: :code:`IO.write`, :code:`IO.binread`, :code:`IO.binwrite`, :code:`IO.foreach`, :code:`IO.readlines`, and :code:`URI.open`.
+
+New Queries
+~~~~~~~~~~~
+
+C#
+""
+
+* Added a new query, :code:`csharp/telemetry/supported-external-api`, to detect supported 3rd party APIs used in a codebase.
+
+Java
+""""
+
+* Added a new query, :code:`java/summary/generated-vs-manual-coverage`, to expose metrics for the number of API endpoints covered by generated versus manual MaD models.
+* Added a new query, :code:`java/telemetry/supported-external-api`, to detect supported 3rd party APIs used in a codebase.
+* Added a new query, :code:`java/android/missing-certificate-pinning`, to find network calls where certificate pinning is not implemented.
+* Added a new query, :code:`java/android-webview-addjavascriptinterface`, to detect the use of :code:`addJavascriptInterface`, which can lead to cross-site scripting.
+* Added a new query, :code:`java/android-websettings-file-access`, to detect configurations that enable file system access in Android WebViews.
+* Added a new query, :code:`java/android-websettings-javascript-enabled`, to detect if JavaScript execution is enabled in an Android WebView.
+* The query :code:`java/regex-injection` has been promoted from experimental to the main query pack. Its results will now appear by default. This query was originally `submitted as an experimental query by @edvraa `__.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/stack-trace-exposure`, to detect exposure of stack-traces to users via HTTP responses.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+Golang
+""""""
+
+* Fixed an issue in the taint tracking analysis where implicit reads were not allowed by default in sinks or additional taint steps that used flow states.
+
+Java
+""""
+
+* We now correctly handle empty block comments, like :code:`/**/`. Previously these could be mistaken for Javadoc comments and led to attribution of Javadoc tags to the wrong declaration.
+
+Python
+""""""
+
+* :code:`except*` is now supported.
+* The result of :code:`Try.getAHandler` and :code:`Try.getHandler()` is no longer of type :code:`ExceptStmt`, as handlers may also be :code:`ExceptGroupStmt`\ s (After Python 3.11 introduced PEP 654). Instead, it is of the new type :code:`ExceptionHandler` of which :code:`ExceptStmt` and :code:`ExceptGroupStmt` are subtypes. To support selecting only one type of handler, :code:`Try.getANormalHandler` and :code:`Try.getAGroupHandler` have been added. Existing uses of :code:`Try.getAHandler` for which it is important to select only normal handlers, will need to be updated to :code:`Try.getANormalHandler`.
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The predicates in the :code:`MustFlow::Configuration` class used by the :code:`MustFlow` library (:code:`semmle.code.cpp.ir.dataflow.MustFlow`) have changed to be defined directly in terms of the C++ IR instead of IR dataflow nodes.
+
+Golang
+""""""
+
+* The signature of :code:`allowImplicitRead` on :code:`DataFlow::Configuration` and :code:`TaintTracking::Configuration` has changed from :code:`allowImplicitRead(DataFlow::Node node, DataFlow::Content c)` to :code:`allowImplicitRead(DataFlow::Node node, DataFlow::ContentSet c)`.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* The *PAM authorization bypass due to incorrect usage* (:code:`py/pam-auth-bypass`) query has been converted to a taint-tracking query, resulting in significantly fewer false positives.
+
+Ruby
+""""
+
+* Flow through :code:`initialize` constructors is now taken into account. For example, in
+
+ .. code-block:: rb
+
+ class C
+ def initialize(x)
+ @field = x
+ end
+ end
+
+ C.new(y)
+
+ there will be flow from :code:`y` to the field :code:`@field` on the constructed :code:`C` object.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`ArgvSource` flow source now uses the second parameter of :code:`main` as its source instead of the uses of this parameter.
+* The :code:`ArgvSource` flow source has been generalized to handle cases where the argument vector of :code:`main` is not named :code:`argv`.
+* The :code:`getaddrinfo` function is now recognized as a flow source.
+* The :code:`secure_getenv` and :code:`_wgetenv` functions are now recognized as local flow sources.
+* The :code:`scanf` and :code:`fscanf` functions and their variants are now recognized as flow sources.
+* Deleted the deprecated :code:`getName` and :code:`getShortName` predicates from the :code:`Folder` class.
+
+C#
+""
+
+* C# 11: Added support for list- and slice patterns in the extractor.
+* Deleted the deprecated :code:`getNameWithoutBrackets` predicate from the :code:`ValueOrRefType` class in :code:`Type.qll`.
+* :code:`Element::hasQualifiedName/1` has been deprecated. Use :code:`hasQualifiedName/2` or :code:`hasQualifiedName/3` instead.
+* Added TCP/UDP sockets as taint sources.
+
+Golang
+""""""
+
+* The predicate :code:`getNumParameter` on :code:`FuncTypeExpr` has been changed to actually give the number of parameters. It previously gave the number of parameter declarations. :code:`getNumParameterDecl` has been introduced to preserve this functionality.
+* The definition of :code:`mayHaveSideEffects` for :code:`ReturnStmt` was incorrect when more than one expression was being returned. Such return statements were effectively considered to never have side effects. This has now been fixed. In rare circumstances :code:`globalValueNumber` may have incorrectly treated two values as the same when they were in fact distinct.
+* Queries that care about SQL, such as :code:`go/sql-injection`, now recognise SQL-consuming functions belonging to the :code:`gorqlite` and :code:`GoFrame` packages.
+* :code:`rsync` has been added to the list of commands which may evaluate its parameters as a shell command.
+
+Java
+""""
+
+* Added more dataflow models for frequently-used JDK APIs.
+* The extraction of Kotlin extension methods has been improved when default parameter values are present. The dispatch and extension receiver parameters are extracted in the correct order. The :code:`ExtensionMethod::getExtensionReceiverParameterIndex` predicate has been introduced to facilitate getting the correct extension parameter index.
+* The query :code:`java/insecure-cookie` now uses global dataflow to track secure cookies being set to the HTTP response object.
+* The library :code:`PathSanitizer.qll` has been improved to detect more path validation patterns in Kotlin.
+* Models as Data models for Java are defined as data extensions instead of being inlined in the code. New models should be added in the :code:`lib/ext` folder.
+* Added a taint model for the method :code:`java.nio.file.Path.getParent`.
+* Fixed a problem in the taint model for the method :code:`java.nio.file.Paths.get`.
+* Deleted the deprecated :code:`LocalClassDeclStmtNode` and :code:`LocalClassDeclStmt` classes from :code:`PrintAst.qll` and :code:`Statement.qll` respectively.
+* Deleted the deprecated :code:`getLocalClass` predicate from :code:`LocalTypeDeclStmt`, and the deprecated :code:`getLocalClassDeclStmt` predicate from :code:`LocalClassOrInterface`.
+* Added support for Android Manifest :code:`` elements in data flow sources.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Deleted the deprecated :code:`Instance` class from the :code:`Vue` module.
+* Deleted the deprecated :code:`VHtmlSourceWrite` class from :code:`DomBasedXssQuery.qll`.
+* Deleted all the deprecated :code:`[QueryName].qll` files from the :code:`javascript/ql/lib/semmle/javascript/security/dataflow` folder, use the corresponding :code:`[QueryName]Query.qll` files instead.
+* The ReDoS libraries in :code:`semmle.code.javascript.security.regexp` has been moved to a shared pack inside the :code:`shared/` folder, and the previous location has been deprecated.
+
+Python
+""""""
+
+* Added :code:`subprocess.getoutput` and :code:`subprocess.getoutputstatus` as new command injection sinks for the StdLib.
+* The data-flow library has been rewritten to no longer rely on the points-to analysis in order to resolve references to modules. Improvements in the module resolution can lead to more results.
+* Deleted the deprecated :code:`importNode` predicate from the :code:`DataFlowUtil.qll` file.
+* Deleted the deprecated features from :code:`PEP249.qll` that were not inside the :code:`PEP249` module.
+* Deleted the deprecated :code:`werkzeug` from the :code:`Werkzeug` module in :code:`Werkzeug.qll`.
+* Deleted the deprecated :code:`methodResult` predicate from :code:`PEP249::Cursor`.
+
+Ruby
+""""
+
+* Calls to :code:`Kernel.load`, :code:`Kernel.require`, :code:`Kernel.autoload` are now modeled as sinks for path injection.
+* Calls to :code:`mail` and :code:`inbound_mail` in :code:`ActionMailbox` controllers are now considered sources of remote input.
+* Calls to :code:`GlobalID::Locator.locate` and its variants are now recognized as instances of :code:`OrmInstantiation`.
+* Data flow through the :code:`ActiveSupport` extensions :code:`Enumerable#index_with`, :code:`Enumerable#pick`, :code:`Enumerable#pluck` and :code:`Enumerable#sole` are now modeled.
+* When resolving a method call, the analysis now also searches in sub-classes of the receiver's type.
+* Taint flow is now tracked through many common JSON parsing and generation methods.
+* The ReDoS libraries in :code:`codeql.ruby.security.regexp` has been moved to a shared pack inside the :code:`shared/` folder, and the previous location has been deprecated.
+* String literals and arrays of string literals in case expression patterns are now recognised as barrier guards.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Deprecated :code:`semmle.code.cpp.ir.dataflow.DefaultTaintTracking`. Use :code:`semmle.code.cpp.ir.dataflow.TaintTracking`.
+* Deprecated :code:`semmle.code.cpp.security.TaintTrackingImpl`. Use :code:`semmle.code.cpp.ir.dataflow.TaintTracking`.
+* Deprecated :code:`semmle.code.cpp.valuenumbering.GlobalValueNumberingImpl`. Use :code:`semmle.code.cpp.valuenumbering.GlobalValueNumbering`, which exposes the same API.
+
+Golang
+""""""
+
+* The :code:`BarrierGuard` class has been deprecated. Such barriers and sanitizers can now instead be created using the new :code:`BarrierGuard` parameterized module.
+
+New Features
+~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Improved support for `Restify `__ framework, leading to more results when scanning applications developed with this framework.
+* Added support for the `Spife `__ framework.
+
+Shared Libraries
+----------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Type Trackers
+"""""""""""""
+
+* Initial release. Includes a parameterized module implementing type-trackers.
+
+QL Detective Tutorial
+"""""""""""""""""""""
+
+* Initial release. Contains the library for the CodeQL detective tutorials, helping new users learn to write CodeQL queries.
+
+Utility Classes
+"""""""""""""""
+
+* Initial release. Includes common utility classes and modules: Unit, Boolean, and Option.
+
+.. |link-code-paths-and-code-paths-ignore-configuration-1| replace:: :code:`paths` and :code:`paths-ignore` configuration
+.. _link-code-paths-and-code-paths-ignore-configuration-1: https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#specifying-directories-to-scan
+
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.1.rst
new file mode 100644
index 00000000000..077673b28a8
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.1.rst
@@ -0,0 +1,99 @@
+.. _codeql-cli-2.12.1:
+
+==========================
+CodeQL 2.12.1 (2023-01-23)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.1 runs a total of 384 security queries when configured with the Default suite (covering 154 CWE). The Extended suite enables an additional 120 queries (covering 31 more CWE). 23 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+New Features
+~~~~~~~~~~~~
+
+* Added a new command-line flag :code:`--expect-discarded-cache`, which gives a hint to the evaluator that the evaluation cache will be discarded after analysis completes. This allows it to avoid some unnecessary writes to the cache, for predicates that aren't needed by the query/suite being evaluated.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`cpp/no-space-for-terminator` and :code:`cpp/uncontrolled-allocation-size` queries have been enhanced with heuristic detection of allocations. These queries now find more results.
+
+Golang
+""""""
+
+* Replacing "\r" or "\n" using the functions :code:`strings.ReplaceAll`, :code:`strings.Replace`, :code:`strings.Replacer.Replace` and :code:`strings.Replacer.WriteString` has been added as a sanitizer for the queries "Log entries created from user input".
+* The functions :code:`strings.Replacer.Replace` and :code:`strings.Replacer.WriteString` have been added as sanitizers for the query "Potentially unsafe quoting".
+
+Java
+""""
+
+* The name, description and alert message for the query :code:`java/concatenated-sql-query` have been altered to emphasize that the query flags the use of string concatenation to construct SQL queries, not the lack of appropriate escaping. The query's files have been renamed from :code:`SqlUnescaped.ql` and :code:`SqlUnescapedLib.qll` to :code:`SqlConcatenated.ql` and :code:`SqlConcatenatedLib.qll` respectively; in the unlikely event your custom configuration or queries refer to either of these files by name, those references will need to be adjusted. The query id remains :code:`java/concatenated-sql-query`, so alerts should not be re-raised as a result of this change.
+
+Ruby
+""""
+
+* The :code:`rb/unsafe-deserialization` query now recognizes input from STDIN as a source.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new query :code:`java/android/websettings-allow-content-access` to detect Android WebViews which do not disable access to :code:`content://` urls.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/unsafe-code-construction`, to detect libraries that unsafely construct code from their inputs.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* Added library support for generic attributes (also for CIL extracted attributes).
+* :code:`cil.ConstructedType::getName` was changed to include printing of the type arguments.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* Attributes on methods in CIL are now extracted (Bugfix).
+* Support for :code:`static virtual` and :code:`static abstract` interface members.
+* Support for *operators* in interface definitions.
+* C# 11: Added support for the unsigned right shift :code:`>>>` and unsigned right shift assignment :code:`>>>=` operators.
+* Query id's have been aligned such that they are prefixed with :code:`cs` instead of :code:`csharp`.
+
+Java
+""""
+
+* Added sink models for the constructors of :code:`org.springframework.jdbc.object.MappingSqlQuery` and :code:`org.springframework.jdbc.object.MappingSqlQueryWithParameters`.
+* Added more dataflow models for frequently-used JDK APIs.
+* Removed summary model for :code:`java.lang.String#endsWith(String)` and added neutral model for this API.
+* Added additional taint step for :code:`java.lang.String#endsWith(String)` to :code:`ConditionalBypassFlowConfig`.
+* Added :code:`AllowContentAccessMethod` to represent the :code:`setAllowContentAccess` method of the :code:`android.webkit.WebSettings` class.
+* Added an external flow source for the parameters of methods annotated with :code:`android.webkit.JavascriptInterface`.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.2.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.2.rst
new file mode 100644
index 00000000000..c420b0facd8
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.2.rst
@@ -0,0 +1,92 @@
+.. _codeql-cli-2.12.2:
+
+==========================
+CodeQL 2.12.2 (2023-02-07)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.2 runs a total of 385 security queries when configured with the Default suite (covering 154 CWE). The Extended suite enables an additional 121 queries (covering 31 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a QL evaluator bug introduced in release 2.12.1 which could in certain rare cases lead to wrong analysis results.
+
+* Fixed handling of :code:`-Xclang ` arguments passed to the :code:`clang` compiler which could cause missing extractions for C++ code bases.
+
+* Fixed a bug where the :code:`--overwrite` option was failing for database clusters.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.6.
+
+Query Packs
+-----------
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new query, :code:`java/android/sensitive-result-receiver`, to find instances of sensitive data being leaked to an untrusted :code:`ResultReceiver`.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/html-constructed-from-input`, to detect libraries that unsafely construct HTML from their inputs.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* Add extractor and library support for UTF-8 encoded strings.
+* The :code:`StringLiteral` class includes UTF-8 encoded strings.
+* In the DB Scheme :code:`@string_literal_expr` is renamed to :code:`@utf16_string_literal_expr`.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* C# 11: Added extractor support for :code:`ref` fields in :code:`ref struct` declarations.
+
+Java
+""""
+
+* Added sink models for the :code:`createQuery`, :code:`createNativeQuery`, and :code:`createSQLQuery` methods of the :code:`org.hibernate.query.QueryProducer` interface.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added sinks from the |link-code-node-pty-1|_ library to the :code:`js/code-injection` query.
+
+Ruby
+""""
+
+* Data flowing from the :code:`locals` argument of a Rails :code:`render` call is now tracked to uses of that data in an associated view.
+* Access to headers stored in the :code:`env` of Rack requests is now recognized as a source of remote input.
+* Ruby 3.2: anonymous rest and keyword rest arguments can now be passed as arguments, instead of just used in method parameters.
+
+.. |link-code-node-pty-1| replace:: :code:`node-pty`\
+.. _link-code-node-pty-1: https://www.npmjs.com/package/node-pty
+
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.3.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.3.rst
new file mode 100644
index 00000000000..3aa89e03406
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.3.rst
@@ -0,0 +1,132 @@
+.. _codeql-cli-2.12.3:
+
+==========================
+CodeQL 2.12.3 (2023-02-23)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.3 runs a total of 385 security queries when configured with the Default suite (covering 154 CWE). The Extended suite enables an additional 122 queries (covering 31 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug where the CLI would refuse to complete database creation if the OS reports less than about 1.5 GB of physical memory. Now an attempt will be made even on low-memory systems (but it might still run out of memory unless there's swap space available).
+
+New Features
+~~~~~~~~~~~~
+
+* The CodeQL compiler now produces better error messages when it is unable to find a QL library that the query being evaluated depends on.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The :code:`java/index-out-of-bounds` query has improved its handling of arrays of constant length, and may report additional results in those cases.
+
+Ruby
+""""
+
+* The :code:`rb/polynomial-redos` query now considers the entrypoints of the API of a gem as sources.
+
+New Queries
+~~~~~~~~~~~
+
+Golang
+""""""
+
+* Added a new query, :code:`go/unhandled-writable-file-close`, to detect instances where writable file handles are closed without appropriate checks for errors.
+
+Java
+""""
+
+* Added a new query, :code:`java/xxe-local`, which is a version of the XXE query that uses local sources (for example, reads from a local file).
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/regex/badly-anchored-regexp`, to detect regular expression validators that use :code:`^` and :code:`$` as anchors and therefore might match only a single line of a multi-line string.
+
+Query Metadata Changes
+~~~~~~~~~~~~~~~~~~~~~~
+
+Golang
+""""""
+
+* The precision of the :code:`go/log-injection` query was decreased from :code:`high` to :code:`medium`, since it may not be able to identify every way in which log data may be sanitized. This also aligns it with the precision of comparable queries for other languages.
+
+Language Libraries
+------------------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* Python 2 is no longer supported for extracting databases using the CodeQL CLI. As a consequence,
+ the previously deprecated support for :code:`pyxl` and :code:`spitfire` templates has also been removed. When extracting Python 2 code, having Python 2 installed is still recommended, as this ensures the correct version of the Python standard library is extracted.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* C# 11: Added extractor support for the :code:`scoped` modifier annotation on parameters and local variables.
+
+Golang
+""""""
+
+* Support for the Twirp framework has been added.
+
+Java
+""""
+
+* Removed the first argument of :code:`java.nio.file.Files#createTempDirectory(String,FileAttribute[])` as a "create-file" sink.
+* Added the first argument of :code:`java.nio.file.Files#copy` as a "read-file" sink for the :code:`java/path-injection` query.
+* The data flow library now disregards flow through code that is dead based on some basic constant propagation, for example, guards like :code:`if (1+1>3)`.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added dataflow sources for the `express-ws `__ library.
+
+Python
+""""""
+
+* Fixed module resolution so we properly recognize that in :code:`from import *`, where :code:`` is a package, the actual imports are made from the :code:`/__init__.py` file.
+
+Ruby
+""""
+
+* Ruby 3.1: one-line pattern matches are now supported. The AST nodes are named :code:`TestPattern` (:code:`expr in pattern`) and :code:`MatchPattern` (:code:`expr => pattern`).
+
+New Features
+~~~~~~~~~~~~
+
+Golang
+""""""
+
+* Go 1.20 is now supported. The extractor now functions as expected when Go 1.20 is installed; the definition of :code:`implementsComparable` has been updated according to Go 1.20's new, more-liberal rules; and taint flow models have been added for relevant, new standard-library functions.
+
+Java
+""""
+
+* Kotlin versions up to 1.8.20 are now supported.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.4.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.4.rst
new file mode 100644
index 00000000000..efd60528aad
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.4.rst
@@ -0,0 +1,115 @@
+.. _codeql-cli-2.12.4:
+
+==========================
+CodeQL 2.12.4 (2023-03-09)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The default value of the :code:`--mode` switch to :code:`codeql pack install` has changed. The default is now :code:`--mode minimal-update`.
+ Previously, it was :code:`use-lock`.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The :code:`--freeze` switch for :code:`codeql pack create`, :code:`codeql pack bundle`, and :code:`codeql pack publish` is now deprecated and ignored, as there is no longer a cache within a pack.
+* The :code:`--mode update` switch to :code:`codeql pack resolve-dependencies` is now deprecated. Instead, use the new :code:`--mode upgrade` switch, which has identical behavior.
+* The :code:`--mode` switch to :code:`codeql pack install` is now deprecated.
+
+ * Instead of :code:`--mode update`, use :code:`codeql pack upgrade`.
+ * Instead of :code:`--mode verify`, use :code:`codeql pack ci`.
+
+New Features
+~~~~~~~~~~~~
+
+* The per-pack compilation cache has been replaced with a global compilation cache found within :code:`~/.codeql`.
+* :code:`codeql pack install` now uses a new algorithm to determine which versions of the pack's dependencies to use, based on the `PubGrub `__ algorithm. The new algorithm is able to find a solution for many cases that the previous algorithm would fail to solve. When the new algorithm is unable to find a valid solution, it generates a detailed error message explaining why there is no valid solution.
+* Added a new command, :code:`codeql pack upgrade`. This command is similar to :code:`codeql pack install`,
+ except that it ignores any existing lock file, installs the latest compatible version of each dependency, and writes a new lock file. This is equivalent to :code:`codeql pack install --mode update`.
+ Note that the :code:`--mode` switch to :code:`codeql pack install` is now deprecated.
+* Added a new command, :code:`codeql pack ci`. This command is similar to :code:`codeql pack install`,
+ except if the existing lock file is missing, or if it conflicts with the version constraints in the :code:`qlpack.yml` file, the command generates an error. This is equivalent to
+ :code:`codeql pack install --mode verify`. Note that the :code:`--mode` switch to :code:`codeql pack install` is now deprecated.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Golang
+""""""
+
+* The query :code:`go/incorrect-integer-conversion` now correctly recognizes guards of the form :code:`if val <= x` to protect a conversion :code:`uintX(val)` when :code:`x` is in the range :code:`(math.MaxIntX, math.MaxUintX]`.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`js/regex-injection` query now recognizes environment variables and command-line arguments as sources.
+
+Language Libraries
+------------------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`CryptographicOperation` concept has been changed to use a range pattern. This is a breaking change and existing implementations of :code:`CryptographicOperation` will need to be updated in order to compile. These implementations can be updated by:
+
+ #. Extending :code:`CryptographicOperation::Range` rather than :code:`CryptographicOperation`
+ #. Renaming the :code:`getInput()` member predicate as :code:`getAnInput()`
+ #. Implementing the :code:`BlockMode getBlockMode()` member predicate. The implementation for this can be :code:`none()` if the operation is a hashing operation or an encryption operation using a stream cipher.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Python
+""""""
+
+* We use a new analysis for the call-graph (determining which function is called). This can lead to changed results. In most cases this is much more accurate than the old call-graph that was based on points-to, but we do lose a few valid edges in the call-graph, especially around methods that are not defined inside its class.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The query :code:`cs/static-field-written-by-instance` is updated to handle properties.
+* C# 11: Support for explicit interface member implementation of operators.
+* The extraction of member modifiers has been generalized, which could lead to the extraction of more modifiers.
+* C# 11: Added extractor and library support for :code:`file` scoped types.
+* C# 11: Added extractor support for :code:`required` fields and properties.
+* C# 11: Added library support for :code:`checked` operators.
+
+Java
+""""
+
+* Added new sinks for :code:`java/hardcoded-credential-api-call` to identify the use of hardcoded secrets in the creation and verification of JWT tokens using :code:`com.auth0.jwt`. These sinks are from `an experimental query submitted by @luchua `__.
+* The Java extractor now supports builds against JDK 20.
+* The query :code:`java/hardcoded-credential-api-call` now recognizes methods that accept user and password from the SQLServerDataSource class of the Microsoft JDBC Driver for SQL Server.
+
+Python
+""""""
+
+* Fixed module resolution so we properly recognize definitions made within if-then-else statements.
+* Added modeling of cryptographic operations in the :code:`hmac` library.
+
+Ruby
+""""
+
+* Flow is now tracked between ActionController :code:`before_filter` and :code:`after_filter` callbacks and their associated action methods.
+* Calls to :code:`ApplicationController#render` and :code:`ApplicationController::Renderer#render` are recognized as Rails rendering calls.
+* Support for `Twirp framework `__.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.5.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.5.rst
new file mode 100644
index 00000000000..d0d86f33a9a
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.5.rst
@@ -0,0 +1,238 @@
+.. _codeql-cli-2.12.5:
+
+==========================
+CodeQL 2.12.5 (2023-03-21)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.5 runs a total of 385 security queries when configured with the Default suite (covering 154 CWE). The Extended suite enables an additional 124 queries (covering 31 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fix a bug in :code:`codeql query run` where queries whose path contain colons cannot be run.
+
+New Features
+~~~~~~~~~~~~
+
+* The :code:`codeql pack install` command now accepts a :code:`--additional-packs` option. This option takes a list of directories to search for locally available packs when resolving which packs to install. Any pack that is found locally through :code:`--additional-packs` will override any other version of a pack found in the package registry.
+ Locally resolved packs are not added to the lock file.
+
+ Because the use of :code:`--additional-packs` when running
+ :code:`codeql pack install` makes running queries dependent on the local state of the machine initially invoking :code:`codeql pack install`, a warning is emitted if any pack is found outside of the package registry. This warning can be suppressed by using the
+ :code:`--no-strict-mode` option.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The following queries now recognize HTML sanitizers as propagating taint: :code:`js/sql-injection`,
+ :code:`js/path-injection`, :code:`js/server-side-unvalidated-url-redirection`, :code:`js/client-side-unvalidated-url-redirection`,
+ and :code:`js/request-forgery`.
+
+Deprecated Queries
+~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`NetworkToBufferSizeConfiguration` and :code:`UntrustedDataToExternalApiConfig` dataflow configurations have been deprecated. Please use :code:`NetworkToBufferSizeFlow` and :code:`UntrustedDataToExternalApiFlow`.
+* The :code:`LeapYearCheckConfiguration`, :code:`FiletimeYearArithmeticOperationCheckConfiguration`, and :code:`PossibleYearArithmeticOperationCheckConfiguration` dataflow configurations have been deprecated. Please use :code:`LeapYearCheckFlow`, :code:`FiletimeYearArithmeticOperationCheckFlow` and :code:`PossibleYearArithmeticOperationCheckFlow`.
+
+New Queries
+~~~~~~~~~~~
+
+Java
+""""
+
+* Added a new query, :code:`java/android/arbitrary-apk-installation`, to detect installation of APKs from untrusted sources.
+
+Python
+""""""
+
+* Added a new query, :code:`py/shell-command-constructed-from-input`, to detect libraries that unsafely construct shell commands from their inputs.
+
+Ruby
+""""
+
+* Added a new query, :code:`rb/zip-slip`, to detect arbitrary file writes during extraction of zip/tar archives.
+
+Language Libraries
+------------------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`semmle.code.cpp.commons.Buffer` and :code:`semmle.code.cpp.commons.NullTermination` libraries no longer expose :code:`semmle.code.cpp.dataflow.DataFlow`. Please import :code:`semmle.code.cpp.dataflow.DataFlow` directly.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* A new C/C++ dataflow library (:code:`semmle.code.cpp.dataflow.new.DataFlow`) has been added.
+ The new library behaves much more like the dataflow library of other CodeQL supported languages by following use-use dataflow paths instead of def-use dataflow paths.
+ The new library also better supports dataflow through indirections, and new predicates such as :code:`Node::asIndirectExpr` have been added to facilitate working with indirections.
+
+ The :code:`semmle.code.cpp.ir.dataflow.DataFlow` library is now identical to the new
+ :code:`semmle.code.cpp.dataflow.new.DataFlow` library.
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+C#
+""
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+Golang
+""""""
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+Java
+""""
+
+* Removed low-confidence call edges to known neutral call targets from the call graph used in data flow analysis. This includes, for example, custom :code:`List.contains` implementations when the best inferrable type at the call site is simply :code:`List`.
+* Added more sink and summary dataflow models for the following packages:
+
+ * :code:`java.io`
+ * :code:`java.lang`
+ * :code:`java.sql`
+ * :code:`javafx.scene.web`
+ * :code:`org.apache.commons.compress.archivers.tar`
+ * :code:`org.apache.http.client.utils`
+ * :code:`org.codehaus.cargo.container.installer`
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+Python
+""""""
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+Ruby
+""""
+
+* The main data flow and taint tracking APIs have been changed. The old APIs remain in place for now and translate to the new through a backwards-compatible wrapper. If multiple configurations are in scope simultaneously, then this may affect results slightly. The new API is quite similar to the old, but makes use of a configuration module instead of a configuration class.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Deleted the deprecated :code:`hasGeneratedCopyConstructor` and :code:`hasGeneratedCopyAssignmentOperator` predicates from the :code:`Folder` class.
+* Deleted the deprecated :code:`getPath` and :code:`getFolder` predicates from the :code:`XmlFile` class.
+* Deleted the deprecated :code:`getMustlockFunction`, :code:`getTrylockFunction`, :code:`getLockFunction`, and :code:`getUnlockFunction` predicates from the :code:`MutexType` class.
+* Deleted the deprecated :code:`getPosInBasicBlock` predicate from the :code:`SubBasicBlock` class.
+* Deleted the deprecated :code:`getExpr` predicate from the :code:`PointerDereferenceExpr` class.
+* Deleted the deprecated :code:`getUseInstruction` and :code:`getDefinitionInstruction` predicates from the :code:`Operand` class.
+* Deleted the deprecated :code:`isInParameter`, :code:`isInParameterPointer`, and :code:`isInQualifier` predicates from the :code:`FunctionInput` class.
+* Deleted the deprecated :code:`isOutParameterPointer`, :code:`isOutQualifier`, :code:`isOutReturnValue`, and :code:`isOutReturnPointer` predicate from the :code:`FunctionOutput` class.
+* Deleted the deprecated 3-argument :code:`isGuardPhi` predicate from the :code:`RangeSsaDefinition` class.
+
+C#
+""
+
+* Deleted the deprecated :code:`getPath` and :code:`getFolder` predicates from the :code:`XmlFile` class.
+* Deleted the deprecated :code:`getAssertionIndex`, and :code:`getAssertedParameter` predicates from the :code:`AssertMethod` class.
+* Deleted the deprecated :code:`OverridableMethod` and :code:`OverridableAccessor` classes.
+* The :code:`unsafe` predicate for :code:`Modifiable` has been extended to cover delegate return types and identify pointer-like types at any nest level. This is relevant for :code:`unsafe` declarations extracted from assemblies.
+
+Java
+""""
+
+* Deleted the deprecated :code:`getPath` and :code:`getFolder` predicates from the :code:`XmlFile` class.
+* Deleted the deprecated :code:`getRepresentedString` predicate from the :code:`StringLiteral` class.
+* Deleted the deprecated :code:`ServletWriterSource` class.
+* Deleted the deprecated :code:`getGroupID`, :code:`getArtefactID`, and :code:`artefactMatches` predicates from the :code:`MavenRepoJar` class.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Deleted the deprecated :code:`getPath` and :code:`getFolder` predicates from the :code:`XmlFile` class.
+* Deleted the deprecated :code:`getId` from the :code:`Function`, :code:`NamespaceDefinition`, and :code:`ImportEqualsDeclaration` classes.
+* Deleted the deprecated :code:`flowsTo` predicate from the :code:`HTTP::Servers::RequestSource` and :code:`HTTP::Servers::ResponseSource` class.
+* Deleted the deprecated :code:`getEventName` predicate from the :code:`SocketIO::ReceiveNode`, :code:`SocketIO::SendNode`, :code:`SocketIOClient::SendNode` classes.
+* Deleted the deprecated :code:`RateLimitedRouteHandlerExpr` and :code:`RouteHandlerExpressionWithRateLimiter` classes.
+* \ `Import assertions `__ are now supported.
+ Previously this feature was only supported in TypeScript code, but is now supported for plain JavaScript as well and is also accessible in the AST.
+
+Python
+""""""
+
+* Deleted the deprecated :code:`getPath` and :code:`getFolder` predicates from the :code:`XmlFile` class.
+
+Ruby
+""""
+
+* Data flow through :code:`initialize` methods is now taken into account also when the receiver of a :code:`new` call is an (implicit or explicit) :code:`self`.
+* The Active Record query methods :code:`reorder` and :code:`count_by_sql` are now recognized as SQL executions.
+* Calls to :code:`ActiveRecord::Connection#execute`, including those via subclasses, are now recognized as SQL executions.
+* Data flow through :code:`ActionController::Parameters#require` is now tracked properly.
+* The severity of parse errors was reduced to warning (previously error).
+* Deleted the deprecated :code:`getQualifiedName` predicate from the :code:`ConstantWriteAccess` class.
+* Deleted the deprecated :code:`getWhenBranch` and :code:`getAWhenBranch` predicates from the :code:`CaseExpr` class.
+* Deleted the deprecated :code:`Self`, :code:`PatternParameter`, :code:`Pattern`, :code:`VariablePattern`, :code:`TuplePattern`, and :code:`TuplePatternParameter` classes.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`WriteConfig` taint tracking configuration has been deprecated. Please use :code:`WriteFlow`.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
+
+C#
+""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
+
+Golang
+""""""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
+
+Java
+""""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
+
+Python
+""""""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
+
+Ruby
+""""
+
+* Added support for merging two :code:`PathGraph`\ s via disjoint union to allow results from multiple data flow computations in a single :code:`path-problem` query.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.6.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.6.rst
new file mode 100644
index 00000000000..8b7feb9e683
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.6.rst
@@ -0,0 +1,57 @@
+.. _codeql-cli-2.12.6:
+
+==========================
+CodeQL 2.12.6 (2023-04-04)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.12.6 runs a total of 386 security queries when configured with the Default suite (covering 154 CWE). The Extended suite enables an additional 124 queries (covering 31 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug in :code:`codeql database analyze` and related commands where the :code:`--max-paths` option was not respected correctly when multiple alerts with the same primary code location were grouped together.
+ (This grouping is the default behavior unless the :code:`--no-group-alerts` option is passed.)
+ This bug caused some SARIF files produced by CodeQL to exceed the limits on the number of paths (:code:`threadFlows`) accepted by code scanning,
+ leading to errors when uploading results.
+
+New Features
+~~~~~~~~~~~~
+
+* Several experimental subcommands have been added in support of the new `code scanning tool status page `__.
+ These include :code:`codeql database add-diagnostic`,
+ :code:`codeql database export-diagnostics`, and the
+ :code:`codeql diagnostic add` and :code:`codeql diagnostic export` plumbing subcommands.
+
+Known Issues
+~~~~~~~~~~~~
+
+* We recommend that customers using the CodeQL CLI in a third party CI system do not upgrade to this release, due to an issue with :code:`codeql github upload-results`. Instead, please use CodeQL 2.12.5, or, when available, CodeQL 2.12.7 or 2.13.1.
+
+ This issue occurs when uploading certain kinds of diagnostic information and causes the subcommand to fail with "A fatal error occurred: Invalid SARIF.", reporting an :code:`InvalidDefinitionException`.
+
+ Customers who wish to use CodeQL 2.12.6 or 2.13.0 can
+ work around the problem by passing :code:`--no-sarif-include-diagnostics` to any invocations of :code:`codeql database analyze` or :code:`codeql database interpret-results`.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Ruby
+""""
+
+* :code:`rb/sensitive-get-query` no longer reports flow paths from input parameters to sensitive use nodes. This avoids cases where many flow paths could be generated for a single parameter, which caused excessive paths to be generated.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.7.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.7.rst
new file mode 100644
index 00000000000..c0a25058f69
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.12.7.rst
@@ -0,0 +1,20 @@
+.. _codeql-cli-2.12.7:
+
+==========================
+CodeQL 2.12.7 (2023-04-18)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug in :code:`codeql database upload-results` where the subcommand would fail with "A fatal error occurred: Invalid SARIF.", reporting an :code:`InvalidDefinitionException`. This issue occurred when the SARIF file contained certain kinds of diagnostic information.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.0.rst
new file mode 100644
index 00000000000..032b7a71014
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.0.rst
@@ -0,0 +1,322 @@
+.. _codeql-cli-2.13.0:
+
+==========================
+CodeQL 2.13.0 (2023-04-20)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.13.0 runs a total of 388 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 124 queries (covering 30 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* In :code:`codeql pack add`, the dependency that is added to the :code:`qlpack.yml` file will now allow any version of the pack that is compatible with the specified version (:code:`^version`) in the following cases:
+
+ * When no version is specified (:code:`codeql pack add codeql/cpp-all`).
+ * When the version is specified as :code:`latest` (:code:`codeql pack add codeql/cpp-all@latest`).
+ * When a single version is specified (:code:`codeql pack add codeql/cpp-all@1.0.0`).
+
+ The :code:`^version` dependency allows any version of that pack with no breaking changes since :code:`version`.
+ For example, :code:`^1.2.3` would allow versions :code:`1.2.3`, :code:`1.2.5`, and :code:`1.4.0`, but not :code:`2.0.0`, because changing the major version number to :code:`2` indicates a breaking change.
+
+ Using :code:`^version` ensures that the added pack is not needlessly constrained to an exact version by default.
+
+* Upper-case variable names are no longer accepted by the QL compiler.
+
+ Such variable names have produced a deprecation warning since release 2.9.2 (released 2022-05-16), so QL code that compiles without warnings with a recent release of the CLI should still work.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The possibility to omit :code:`override` annotations on class member predicates that override a base class predicate has been deprecated.
+ This is to avoid confusion with shadowing behaviour in the presence of final member predicates.
+
+ .. code-block:: ql
+
+ class Foo extends Base {
+ final predicate foo() { ... }
+
+ predicate bar() { ... }
+
+ predicate baz() { ... }
+ }
+
+ class Bar extends Foo {
+ // This method shadows Foo::foo.
+ predicate foo() { ... }
+
+ // This used to override Foo::bar with a warning, is now deprecated.
+ predicate bar() { ... }
+
+ // This correctly overrides Foo::baz
+ override predicate baz() { ... }
+ }
+
+New Features
+~~~~~~~~~~~~
+
+* :code:`codeql database analyze` and related commands now export file coverage information by default. GHAS customers using CodeQL in third-party CI systems will now see file coverage information on the
+ \ `tool status page `__ without needing to modify their CI workflows.
+
+Known Issues
+~~~~~~~~~~~~
+
+* We recommend that customers using the CodeQL CLI in a third party CI system do not upgrade to this release, due to an issue with :code:`codeql github upload-results`. Instead, please use CodeQL 2.12.5, or, when available, CodeQL 2.12.7 or 2.13.1. For more information, see the
+ "Known issues" section for CodeQL 2.12.6.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed a bug where a destructuring pattern could not be parsed if it had a property named :code:`get` or :code:`set` with a default value.
+
+Python
+""""""
+
+* Nonlocal variables are excluded from alerts.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The query :code:`cpp/tainted-arithmetic` now also flags possible overflows in arithmetic assignment operations.
+
+C#
+""
+
+* The query :code:`cs/web/debug-binary` now disregards the :code:`debug` attribute in case there is a transformation that removes it.
+
+Golang
+""""""
+
+* The receiver arguments of :code:`net/http.Header.Set` and :code:`.Del` are no longer flagged by query :code:`go/untrusted-data-to-external-api`.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`DisablingCertificateValidation.ql` query has been updated to check :code:`createServer` from :code:`https` for disabled certificate validation.
+* Improved the model of jQuery to account for XSS sinks where the HTML string is provided via a callback. This may lead to more results for the :code:`js/xss` query.
+* The :code:`js/weak-cryptographic-algorithm` query now flags cryptograhic operations using a weak block mode,
+ such as AES-ECB.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The query :code:`cpp/redundant-null-check-simple` has been promoted to Code Scanning. The query finds cases where a pointer is compared to null after it has already been dereferenced. Such comparisons likely indicate a bug at the place where the pointer is dereferenced, or where the pointer is compared to null.
+
+Java
+""""
+
+* The query :code:`java/insecure-ldap-auth` has been promoted from experimental to the main query pack. This query detects transmission of cleartext credentials in LDAP authentication. Insecure LDAP authentication causes sensitive information to be vulnerable to remote attackers. This query was originally `submitted as an experimental query by @luchua-bc `__
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/server-side-template-injection`, to detect cases where user input may be embedded into a template's code in an unsafe manner.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+C/C++
+"""""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+C#
+""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+Golang
+""""""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+Java
+""""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+Python
+""""""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular, :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+Ruby
+""""
+
+* Fixed some accidental predicate visibility in the backwards-compatible wrapper for data flow configurations. In particular :code:`DataFlow::hasFlowPath`, :code:`DataFlow::hasFlow`, :code:`DataFlow::hasFlowTo`, and :code:`DataFlow::hasFlowToExpr` were accidentally exposed in a single version.
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The internal :code:`SsaConsistency` module has been moved from :code:`SSAConstruction` to :code:`SSAConsitency`, and the deprecated :code:`SSAConsistency` module has been removed.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 5.0.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`BufferAccess` library (:code:`semmle.code.cpp.security.BufferAccess`) no longer matches buffer accesses inside unevaluated contexts (such as inside :code:`sizeof` or :code:`decltype` expressions). As a result, queries using this library may see fewer false positives.
+
+Java
+""""
+
+* Fixed a bug in the regular expression used to identify sensitive information in :code:`SensitiveActions::getCommonSensitiveInfoRegex`. This may affect the results of the queries :code:`java/android/sensitive-communication`, :code:`java/android/sensitive-keyboard-cache`, and :code:`java/sensitive-log`.
+* Added a summary model for the :code:`java.lang.UnsupportedOperationException(String)` constructor.
+* The filenames embedded in :code:`Compilation.toString()` now use :code:`/` as the path separator on all platforms.
+* Added models for the following packages:
+
+ * :code:`java.lang`
+ * :code:`java.net`
+ * :code:`java.nio.file`
+ * :code:`java.io`
+ * :code:`java.lang.module`
+ * :code:`org.apache.commons.httpclient.util`
+ * :code:`org.apache.commons.io`
+ * :code:`org.apache.http.client`
+ * :code:`org.eclipse.jetty.client`
+ * :code:`com.google.common.io`
+ * :code:`kotlin.io`
+
+* Added the :code:`TaintedPathQuery.qll` library to provide the :code:`TaintedPathFlow` and :code:`TaintedPathLocalFlow` taint-tracking modules to reason about tainted path vulnerabilities.
+* Added the :code:`ZipSlipQuery.qll` library to provide the :code:`ZipSlipFlow` taint-tracking module to reason about zip-slip vulnerabilities.
+* Added the :code:`InsecureBeanValidationQuery.qll` library to provide the :code:`BeanValidationFlow` taint-tracking module to reason about bean validation vulnerabilities.
+* Added the :code:`XssQuery.qll` library to provide the :code:`XssFlow` taint-tracking module to reason about cross site scripting vulnerabilities.
+* Added the :code:`LdapInjectionQuery.qll` library to provide the :code:`LdapInjectionFlow` taint-tracking module to reason about LDAP injection vulnerabilities.
+* Added the :code:`ResponseSplittingQuery.qll` library to provide the :code:`ResponseSplittingFlow` taint-tracking module to reason about response splitting vulnerabilities.
+* Added the :code:`ExternallyControlledFormatStringQuery.qll` library to provide the :code:`ExternallyControlledFormatStringFlow` taint-tracking module to reason about externally controlled format string vulnerabilities.
+* Improved the handling of addition in the range analysis. This can cause in minor changes to the results produced by :code:`java/index-out-of-bounds` and :code:`java/constant-comparison`.
+* A new models as data sink kind :code:`command-injection` has been added.
+* The queries :code:`java/command-line-injection` and :code:`java/concatenated-command-line` now can be extended using the :code:`command-injection` models as data sink kind.
+* Added more sink and summary dataflow models for the following packages:
+
+ * :code:`java.net`
+ * :code:`java.nio.file`
+ * :code:`javax.imageio.stream`
+ * :code:`javax.naming`
+ * :code:`javax.servlet`
+ * :code:`org.geogebra.web.full.main`
+ * :code:`hudson`
+ * :code:`hudson.cli`
+ * :code:`hudson.lifecycle`
+ * :code:`hudson.model`
+ * :code:`hudson.scm`
+ * :code:`hudson.util`
+ * :code:`hudson.util.io`
+
+* Added the extensible abstract class :code:`JndiInjectionSanitizer`. Now this class can be extended to add more sanitizers to the :code:`java/jndi-injection` query.
+* Added a summary model for the :code:`nativeSQL` method of the :code:`java.sql.Connection` interface.
+* Added sink and summary dataflow models for the Jenkins and Netty frameworks.
+* The Models as Data syntax for selecting the qualifier has been changed from :code:`-1` to :code:`this` (e.g. :code:`Argument[-1]` is now written as :code:`Argument[this]`).
+* Added sources and flow step models for the Netty framework up to version 4.1.
+* Added more dataflow models for frequently-used JDK APIs.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* :code:`router.push` and :code:`router.replace` in :code:`Next.js` are now considered as XSS sink.
+* The crypto-js module in :code:`CryptoLibraries.qll` now supports progressive hashing with algo.update().
+
+Python
+""""""
+
+* Added modeling of SQL execution in the packages :code:`sqlite3.dbapi2`, :code:`cassandra-driver`, :code:`aiosqlite`, and the functions :code:`sqlite3.Connection.executescript`\ /\ :code:`sqlite3.Cursor.executescript` and :code:`asyncpg.connection.connect()`.
+* Fixed module resolution so we allow imports of definitions that have had an attribute assigned to it, such as :code:`class Foo; Foo.bar = 42`.
+
+Ruby
+""""
+
+* Control flow graph: the evaluation order of scope expressions and receivers in multiple assignments has been adjusted to match the changes made in Ruby
+ 3.1 and 3.2.
+* The clear-text storage (:code:`rb/clear-text-storage-sensitive-data`) and logging (:code:`rb/clear-text-logging-sensitive-data`) queries now use built-in flow through hashes, for improved precision. This may result in both new true positives and less false positives.
+* Accesses of :code:`params` in Sinatra applications are now recognized as HTTP input accesses.
+* Data flow is tracked from Sinatra route handlers to ERB files.
+* Data flow is tracked between basic Sinatra filters (those without URL patterns) and their corresponding route handlers.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The single-parameter predicates :code:`ArrayOrVectorAggregateLiteral.getElementExpr` and :code:`ClassAggregateLiteral.getFieldExpr` have been deprecated in favor of :code:`ArrayOrVectorAggregateLiteral.getAnElementExpr` and :code:`ClassAggregateLiteral.getAFieldExpr`.
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+* The :code:`SslContextCallAbstractConfig`, :code:`SslContextCallConfig`, :code:`SslContextCallBannedProtocolConfig`, :code:`SslContextCallTls12ProtocolConfig`, :code:`SslContextCallTls13ProtocolConfig`, :code:`SslContextCallTlsProtocolConfig`, :code:`SslContextFlowsToSetOptionConfig`, :code:`SslOptionConfig` dataflow configurations from :code:`BoostorgAsio` have been deprecated. Please use :code:`SslContextCallConfigSig`, :code:`SslContextCallGlobal`, :code:`SslContextCallFlow`, :code:`SslContextCallBannedProtocolFlow`, :code:`SslContextCallTls12ProtocolFlow`, :code:`SslContextCallTls13ProtocolFlow`, :code:`SslContextCallTlsProtocolFlow`, :code:`SslContextFlowsToSetOptionFlow`.
+
+C#
+""
+
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+
+Golang
+""""""
+
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+
+Java
+""""
+
+* The :code:`execTainted` predicate in :code:`CommandLineQuery.qll` has been deprecated and replaced with the predicate :code:`execIsTainted`.
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+* The :code:`WebViewDubuggingQuery` library has been renamed to :code:`WebViewDebuggingQuery` to fix the typo in the file name. :code:`WebViewDubuggingQuery` is now deprecated.
+
+Python
+""""""
+
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+
+Ruby
+""""
+
+* The recently introduced new data flow and taint tracking APIs have had a number of module and predicate renamings. The old APIs remain in place for now.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added overridable predicates :code:`getSizeExpr` and :code:`getSizeMult` to the :code:`BufferAccess` class (:code:`semmle.code.cpp.security.BufferAccess.qll`). This makes it possible to model a larger class of buffer reads and writes using the library.
+
+Java
+""""
+
+* Predicates :code:`Compilation.getExpandedArgument` and :code:`Compilation.getAnExpandedArgument` has been added.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.1.rst
new file mode 100644
index 00000000000..70d05d4029b
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.1.rst
@@ -0,0 +1,118 @@
+.. _codeql-cli-2.13.1:
+
+==========================
+CodeQL 2.13.1 (2023-05-03)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.13.1 runs a total of 389 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 125 queries (covering 32 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug in :code:`codeql database upload-results` where the subcommand would fail with "A fatal error occurred: Invalid SARIF.", reporting an :code:`InvalidDefinitionException`. This issue occurred when the SARIF file contained certain kinds of diagnostic information.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.7.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixes an issue that would cause TypeScript extraction to hang in rare cases when extracting code containing recursive generic type aliases.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* Additional sinks modelling writes to unencrypted local files have been added to :code:`ExternalLocationSink`, used by the :code:`cs/cleartext-storage` and :code:`cs/exposure-of-sensitive-information` queries.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Improved the call graph to better handle the case where a function is stored on a plain object and subsequently copied to a new host object via an :code:`extend` call.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* A new query :code:`cpp/double-free` has been added. The query finds possible cases of deallocating the same pointer twice. The precision of the query has been set to "medium".
+* The query :code:`cpp/use-after-free` has been modernized and assigned the precision "medium". The query finds cases of where a pointer is dereferenced after its memory has been deallocated.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The Yaml.qll library was moved into a shared library pack named :code:`codeql/yaml` to make it possible for other languages to re-use it. This change should be backwards compatible for existing JavaScript queries.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Golang
+""""""
+
+* Taking a slice is now considered a sanitizer for :code:`SafeUrlFlow`.
+
+Java
+""""
+
+* Changed some models of Spring's :code:`FileCopyUtils.copy` to be path injection sinks instead of summaries.
+* Added models for the following packages:
+
+ * java.nio.file
+
+* Added models for `Apache HttpComponents `__ versions 4 and 5.
+* Added sanitizers that recognize line breaks to the query :code:`java/log-injection`.
+* Added new flow steps for :code:`java.util.StringJoiner`.
+
+Python
+""""""
+
+* Added support for querying the contents of YAML files.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The :code:`sensitiveResultReceiver` predicate in :code:`SensitiveResultReceiverQuery.qll` has been deprecated and replaced with :code:`isSensitiveResultReceiver` in order to use the new dataflow API.
+
+Shared Libraries
+----------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+YAML Data Analysis
+""""""""""""""""""
+
+* Initial release. Extracted YAML related code into a library pack to share code between languages.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.3.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.3.rst
new file mode 100644
index 00000000000..a4756a19a77
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.3.rst
@@ -0,0 +1,202 @@
+.. _codeql-cli-2.13.3:
+
+==========================
+CodeQL 2.13.3 (2023-05-31)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug that could cause the compiler to infer incorrect binding sets for non-direct calls to overriding member predicates that have stronger binding sets than their root definitions.
+
+* Fixed a bug that could have caused the compiler to incorrectly infer that a class matched a type signature. The bug only affected classes with overriding member predicates that had stronger binding sets than their root definitions.
+
+* Fixed a bug where a query could not be run from VS Code when there were packs nested within sibling directories
+ of the query.
+
+New Features
+~~~~~~~~~~~~
+
+* This release enhances our preliminary Swift support, setting the stage for the upcoming public beta.
+
+* The :code:`codeql database bundle` command now supports the :code:`--[no]-include-temp` option. When enabled, this option will include the :code:`temp` folder of the database directory in the zip file of the bundled database. This folder includes generated packages and queries, and query suites.
+
+* The structured log produced by :code:`codeql generate log-summary` now includes a Boolean :code:`isCached` field for predicate events, where a :code:`true` value indicates the predicate is a wrapper implementing the :code:`cached` annotation on another predicate. The wrapper depends on the underlying predicate that the annotation was found on, and will usually have the same name, but it has a separate :code:`raHash`.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed a spurious diagnostic warning about comments in JSON files being illegal.
+ Comments in JSON files are in fact fully supported, and the diagnostic message was misleading.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added taint sources from the :code:`@actions/core` and :code:`@actions/github` packages.
+* Added command-injection sinks from the :code:`@actions/exec` package.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The query :code:`java/groovy-injection` now recognizes :code:`groovy.text.TemplateEngine.createTemplate` as a sink.
+* The queries :code:`java/xxe` and :code:`java/xxe-local` now recognize the second argument of calls to :code:`XPath.evaluate` as a sink.
+* Experimental sinks for the query "Resolving XML external entity in user-controlled data" (:code:`java/xxe`) have been promoted to the main query pack. These sinks were originally `submitted as part of an experimental query by @haby0 `__.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`js/indirect-command-line-injection` query no longer flags command arguments that cannot be interpreted as a shell string.
+* The :code:`js/unsafe-deserialization` query no longer flags deserialization through the :code:`js-yaml` library, except when it is used with an unsafe schema.
+* The Forge module in :code:`CryptoLibraries.qll` now correctly classifies SHA-512/224,
+ SHA-512/256, and SHA-512/384 hashes used in message digests as NonKeyCiphers.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* In the intermediate representation, handling of control flow after non-returning calls has been improved. This should remove false positives in queries that use the intermedite representation or libraries based on it, including the new data flow library.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`StdNamespace` class now also includes all inline namespaces that are children of :code:`std` namespace.
+* The new dataflow (:code:`semmle.code.cpp.dataflow.new.DataFlow`) and taint-tracking libraries (:code:`semmle.code.cpp.dataflow.new.TaintTracking`) now support tracking flow through static local variables.
+
+C#
+""
+
+* The :code:`cs/log-forging`, :code:`cs/cleartext-storage`, and :code:`cs/exposure-of-sensitive-information` queries now correctly handle unsanitized arguments to :code:`ILogger` extension methods.
+* Updated the :code:`neutralModel` extensible predicate to include a :code:`kind` column.
+
+Golang
+""""""
+
+* Fixed data flow through variadic function parameters. The arguments corresponding to a variadic parameter are no longer returned by :code:`CallNode.getArgument(int i)` and :code:`CallNode.getAnArgument()`, and hence aren't :code:`ArgumentNode`\ s. They now have one result, which is an :code:`ImplicitVarargsSlice` node. For example, a call :code:`f(a, b, c)` to a function :code:`f(T...)` is treated like :code:`f([]T{a, b, c})`. The old behaviour is preserved by :code:`CallNode.getSyntacticArgument(int i)` and :code:`CallNode.getASyntacticArgument()`. :code:`CallExpr.getArgument(int i)` and :code:`CallExpr.getAnArgument()` are unchanged, and will still have three results in the example given.
+
+Java
+""""
+
+* Added SQL injection sinks for Spring JDBC's :code:`NamedParameterJdbcOperations`.
+
+* Added models for the following packages:
+
+ * org.apache.hadoop.fs
+
+* Added the :code:`ArithmeticCommon.qll` library to provide predicates for reasoning about arithmetic operations.
+
+* Added the :code:`ArithmeticTaintedLocalQuery.qll` library to provide the :code:`ArithmeticTaintedLocalOverflowFlow` and :code:`ArithmeticTaintedLocalUnderflowFlow` taint-tracking modules to reason about arithmetic with unvalidated user input.
+
+* Added the :code:`ArithmeticTaintedQuery.qll` library to provide the :code:`RemoteUserInputOverflow` and :code:`RemoteUserInputUnderflow` taint-tracking modules to reason about arithmetic with unvalidated user input.
+
+* Added the :code:`ArithmeticUncontrolledQuery.qll` library to provide the :code:`ArithmeticUncontrolledOverflowFlow` and :code:`ArithmeticUncontrolledUnderflowFlow` taint-tracking modules to reason about arithmetic with uncontrolled user input.
+
+* Added the :code:`ArithmeticWithExtremeValuesQuery.qll` library to provide the :code:`MaxValueFlow` and :code:`MinValueFlow` dataflow modules to reason about arithmetic with extreme values.
+
+* Added the :code:`BrokenCryptoAlgorithmQuery.qll` library to provide the :code:`InsecureCryptoFlow` taint-tracking module to reason about broken cryptographic algorithm vulnerabilities.
+
+* Added the :code:`ExecTaintedLocalQuery.qll` library to provide the :code:`LocalUserInputToArgumentToExecFlow` taint-tracking module to reason about command injection vulnerabilities caused by local data flow.
+
+* Added the :code:`ExternallyControlledFormatStringLocalQuery.qll` library to provide the :code:`ExternallyControlledFormatStringLocalFlow` taint-tracking module to reason about format string vulnerabilities caused by local data flow.
+
+* Added the :code:`ImproperValidationOfArrayConstructionCodeSpecifiedQuery.qll` library to provide the :code:`BoundedFlowSourceFlow` dataflow module to reason about improper validation of code-specified sizes used for array construction.
+
+* Added the :code:`ImproperValidationOfArrayConstructionLocalQuery.qll` library to provide the :code:`ImproperValidationOfArrayConstructionLocalFlow` taint-tracking module to reason about improper validation of local user-provided sizes used for array construction caused by local data flow.
+
+* Added the :code:`ImproperValidationOfArrayConstructionQuery.qll` library to provide the :code:`ImproperValidationOfArrayConstructionFlow` taint-tracking module to reason about improper validation of user-provided size used for array construction.
+
+* Added the :code:`ImproperValidationOfArrayIndexCodeSpecifiedQuery.qll` library to provide the :code:`BoundedFlowSourceFlow` data flow module to reason about about improper validation of code-specified array index.
+
+* Added the :code:`ImproperValidationOfArrayIndexLocalQuery.qll` library to provide the :code:`ImproperValidationOfArrayIndexLocalFlow` taint-tracking module to reason about improper validation of a local user-provided array index.
+
+* Added the :code:`ImproperValidationOfArrayIndexQuery.qll` library to provide the :code:`ImproperValidationOfArrayIndexFlow` taint-tracking module to reason about improper validation of user-provided array index.
+
+* Added the :code:`InsecureCookieQuery.qll` library to provide the :code:`SecureCookieFlow` taint-tracking module to reason about insecure cookie vulnerabilities.
+
+* Added the :code:`MaybeBrokenCryptoAlgorithmQuery.qll` library to provide the :code:`InsecureCryptoFlow` taint-tracking module to reason about broken cryptographic algorithm vulnerabilities.
+
+* Added the :code:`NumericCastTaintedQuery.qll` library to provide the :code:`NumericCastTaintedFlow` taint-tracking module to reason about numeric cast vulnerabilities.
+
+* Added the :code:`ResponseSplittingLocalQuery.qll` library to provide the :code:`ResponseSplittingLocalFlow` taint-tracking module to reason about response splitting vulnerabilities caused by local data flow.
+
+* Added the :code:`SqlConcatenatedQuery.qll` library to provide the :code:`UncontrolledStringBuilderSourceFlow` taint-tracking module to reason about SQL injection vulnerabilities caused by concatenating untrusted strings.
+
+* Added the :code:`SqlTaintedLocalQuery.qll` library to provide the :code:`LocalUserInputToArgumentToSqlFlow` taint-tracking module to reason about SQL injection vulnerabilities caused by local data flow.
+
+* Added the :code:`StackTraceExposureQuery.qll` library to provide the :code:`printsStackExternally`, :code:`stringifiedStackFlowsExternally`, and :code:`getMessageFlowsExternally` predicates to reason about stack trace exposure vulnerabilities.
+
+* Added the :code:`TaintedPermissionQuery.qll` library to provide the :code:`TaintedPermissionFlow` taint-tracking module to reason about tainted permission vulnerabilities.
+
+* Added the :code:`TempDirLocalInformationDisclosureQuery.qll` library to provide the :code:`TempDirSystemGetPropertyToCreate` taint-tracking module to reason about local information disclosure vulnerabilities caused by local data flow.
+
+* Added the :code:`UnsafeHostnameVerificationQuery.qll` library to provide the :code:`TrustAllHostnameVerifierFlow` taint-tracking module to reason about insecure hostname verification vulnerabilities.
+
+* Added the :code:`UrlRedirectLocalQuery.qll` library to provide the :code:`UrlRedirectLocalFlow` taint-tracking module to reason about URL redirection vulnerabilities caused by local data flow.
+
+* Added the :code:`UrlRedirectQuery.qll` library to provide the :code:`UrlRedirectFlow` taint-tracking module to reason about URL redirection vulnerabilities.
+
+* Added the :code:`XPathInjectionQuery.qll` library to provide the :code:`XPathInjectionFlow` taint-tracking module to reason about XPath injection vulnerabilities.
+
+* Added the :code:`XssLocalQuery.qll` library to provide the :code:`XssLocalFlow` taint-tracking module to reason about XSS vulnerabilities caused by local data flow.
+
+* Moved the :code:`url-open-stream` sink models to experimental and removed :code:`url-open-stream` as a sink option from the `Customizing Library Models for Java `__ documentation.
+
+* Added models for the Apache Commons Net library.
+
+* Updated the :code:`neutralModel` extensible predicate to include a :code:`kind` column.
+
+* Added models for the :code:`io.jsonwebtoken` library.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Improved the queries for injection vulnerabilities in GitHub Actions workflows (:code:`js/actions/command-injection` and :code:`js/actions/pull-request-target`) and the associated library :code:`semmle.javascript.Actions`. These now support steps defined in composite actions, in addition to steps defined in Actions workflow files. It supports more potentially untrusted input values. Additionally to the shell injections it now also detects injections in :code:`actions/github-script`. It also detects simple injections from user controlled :code:`${{ env.name }}`. Additionally to the :code:`yml` extension now it also supports workflows with the :code:`yaml` extension.
+
+Python
+""""""
+
+* Type tracking is now aware of reads of captured variables (variables defined in an outer scope). This leads to a richer API graph, and may lead to more results in some queries.
+* Added more content-flow/field-flow for dictionaries, by adding support for reads through :code:`mydict.get("key")` and :code:`mydict.setdefault("key", value)`, and store steps through :code:`dict["key"] = value` and :code:`mydict.setdefault("key", value)`.
+
+Ruby
+""""
+
+* Support for the :code:`sqlite3` gem has been added. Method calls that execute queries against an SQLite3 database that may be vulnerable to injection attacks will now be recognized.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added an AST-based interface (:code:`semmle.code.cpp.rangeanalysis.new.RangeAnalysis`) for the relative range analysis library.
+* A new predicate :code:`BarrierGuard::getAnIndirectBarrierNode` has been added to the new dataflow library (:code:`semmle.code.cpp.dataflow.new.DataFlow`) to mark indirect expressions as barrier nodes using the :code:`BarrierGuard` API.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.4.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.4.rst
new file mode 100644
index 00000000000..5d1e1c05c9c
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.4.rst
@@ -0,0 +1,245 @@
+.. _codeql-cli-2.13.4:
+
+==========================
+CodeQL 2.13.4 (2023-06-19)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.13.4 runs a total of 390 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 125 queries (covering 32 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed an issue where indirect build tracing did not work in Azure DevOps pipeline jobs in Windows containers. To use indirect build tracing in such environments, ensure both the :code:`--begin-tracing` and
+ :code:`--trace-process-name=CExecSvc.exe` arguments are passed to
+ :code:`codeql database init`.
+* Improved the error message for the :code:`codeql pack create` command when the pack being published has a dependency with no scope in its name.
+
+New Features
+~~~~~~~~~~~~
+
+* Temporary files and folders created by the CodeQL CLI will now be cleaned up when each CLI command (and its internal JVM) shuts down normally.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+Python
+""""""
+
+* The display name (:code:`@name`) of the :code:`py/unsafe-deserialization` query has been updated in favor of consistency with other languages.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The :code:`java/summary/lines-of-code` query now only counts lines of Java code. The new :code:`java/summary/lines-of-code-kotlin` counts lines of Kotlin code.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed an issue where calls to a method named :code:`search` would lead to false positive alerts related to regular expressions.
+ This happened when the call was incorrectly seen as a call to :code:`String.prototype.search`, since this function converts its first argument to a regular expression. The analysis is now more restrictive about when to treat :code:`search` calls as regular expression sinks.
+
+Ruby
+""""
+
+* Fixed a bug that would occur when an :code:`initialize` method returns :code:`self` or one of its parameters.
+ In such cases, the corresponding calls to :code:`new` would be associated with an incorrect return type.
+ This could result in inaccurate call target resolution and cause false positive alerts.
+* Fixed an issue where calls to :code:`delete` or :code:`assoc` with a constant-valued argument would be analyzed imprecisely,
+ as if the argument value was not a known constant.
+
+Swift
+"""""
+
+* Fixed some false positive results from the :code:`swift/string-length-conflation` query, caused by imprecise sinks.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added a new query, :code:`cpp/overrun-write`, to detect buffer overflows in C-style functions that manipulate buffers.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+Swift
+"""""
+
+* Fixed a number of inconsistencies in the abstract syntax tree (AST) and in the control-flow graph (CFG). This may lead to more results in queries that use these libraries, or libraries that depend on them (such as dataflow).
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The extractor has been changed to run after the traced compiler call. This allows inspecting compiler generated files, such as the output of source generators. With this change, :code:`.cshtml` files and their generated :code:`.cshtml.g.cs` counterparts are extracted on dotnet 6 and above.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 5.1.
+
+Swift
+"""""
+
+* Incorporated the cross-language :code:`SensitiveDataHeuristics.qll` heuristics library into the Swift :code:`SensitiveExprs.qll` library. This adds a number of new heuristics enhancing detection from the library.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Deleted the deprecated :code:`hasCopyConstructor` predicate from the :code:`Class` class in :code:`Class.qll`.
+* Deleted many deprecated predicates and classes with uppercase :code:`AST`, :code:`SSA`, :code:`CFG`, :code:`API`, etc. in their names. Use the PascalCased versions instead.
+* Deleted the deprecated :code:`CodeDuplication.qll` file.
+
+C#
+""
+
+* C#: Analysis of the :code:`dotnet test` command supplied with a :code:`dll` or :code:`exe` file as argument no longer fails due to the addition of an erroneous :code:`-p:SharedCompilation=false` argument.
+* Deleted the deprecated :code:`WebConfigXML`, :code:`ConfigurationXMLElement`, :code:`LocationXMLElement`, :code:`SystemWebXMLElement`, :code:`SystemWebServerXMLElement`, :code:`CustomErrorsXMLElement`, and :code:`HttpRuntimeXMLElement` classes from :code:`WebConfig.qll`. The non-deprecated names with PascalCased Xml suffixes should be used instead.
+* Deleted the deprecated :code:`Record` class from both :code:`Types.qll` and :code:`Type.qll`.
+* Deleted the deprecated :code:`StructuralComparisonConfiguration` class from :code:`StructuralComparison.qll`, use :code:`sameGvn` instead.
+* Deleted the deprecated :code:`isParameterOf` predicate from the :code:`ParameterNode` class.
+* Deleted the deprecated :code:`SafeExternalAPICallable`, :code:`ExternalAPIDataNode`, :code:`UntrustedDataToExternalAPIConfig`, :code:`UntrustedExternalAPIDataNode`, and :code:`ExternalAPIUsedWithUntrustedData` classes from :code:`ExternalAPIsQuery.qll`. The non-deprecated names with PascalCased Api suffixes should be used instead.
+* Updated the following C# sink kind names. Any custom data extensions that use these sink kinds will need to be updated accordingly in order to continue working.
+
+ * :code:`code` to :code:`code-injection`
+ * :code:`sql` to :code:`sql-injection`
+ * :code:`html` to :code:`html-injection`
+ * :code:`xss` to :code:`js-injection`
+ * :code:`remote` to :code:`file-content-store`
+
+Java
+""""
+
+* Added flow through the block arguments of :code:`kotlin.io.use` and :code:`kotlin.with`.
+
+* Added models for the following packages:
+
+ * com.alibaba.druid.sql
+ * com.fasterxml.jackson.databind
+ * com.jcraft.jsch
+ * io.netty.handler.ssl
+ * okhttp3
+ * org.antlr.runtime
+ * org.fusesource.leveldbjni
+ * org.influxdb
+ * org.springframework.core.io
+ * org.yaml.snakeyaml
+
+* Deleted the deprecated :code:`getRHS` predicate from the :code:`LValue` class, use :code:`getRhs` instead.
+
+* Deleted the deprecated :code:`getCFGNode` predicate from the :code:`SsaVariable` class, use :code:`getCfgNode` instead.
+
+* Deleted many deprecated predicates and classes with uppercase :code:`XML`, :code:`JSON`, :code:`URL`, :code:`API`, etc. in their names. Use the PascalCased versions instead.
+
+* Added models for the following packages:
+
+ * java.lang
+ * java.nio.file
+
+* Added dataflow models for the Gson deserialization library.
+
+* Added models for the following packages:
+
+ * okhttp3
+
+* Added more dataflow models for the Play Framework.
+
+* Modified the models related to :code:`java.nio.file.Files.copy` so that generic :code:`[Input|Output]Stream` arguments are not considered file-related sinks.
+
+* Dataflow analysis has a new flow step through constructors of transitive subtypes of :code:`java.io.InputStream` that wrap an underlying data source. Previously, the step only existed for direct subtypes of :code:`java.io.InputStream`.
+
+* Path creation sinks modeled in :code:`PathCreation.qll` have been added to the models-as-data sink kind :code:`path-injection`.
+
+* Updated the regular expression in the :code:`HostnameSanitizer` sanitizer in the :code:`semmle.code.java.security.RequestForgery` library to better detect strings prefixed with a hostname.
+
+* Changed the :code:`android-widget` Java source kind to :code:`remote`. Any custom data extensions that use the :code:`android-widget` source kind will need to be updated accordingly in order to continue working.
+
+* Updated the following Java sink kind names. Any custom data extensions will need to be updated accordingly in order to continue working.
+
+ * :code:`sql` to :code:`sql-injection`
+ * :code:`url-redirect` to :code:`url-redirection`
+ * :code:`xpath` to :code:`xpath-injection`
+ * :code:`ssti` to :code:`template-injection`
+ * :code:`logging` to :code:`log-injection`
+ * :code:`groovy` to :code:`groovy-injection`
+ * :code:`jexl` to :code:`jexl-injection`
+ * :code:`mvel` to :code:`mvel-injection`
+ * :code:`xslt` to :code:`xslt-injection`
+ * :code:`ldap` to :code:`ldap-injection`
+ * :code:`pending-intent-sent` to :code:`pending-intents`
+ * :code:`intent-start` to :code:`intent-redirection`
+ * :code:`set-hostname-verifier` to :code:`hostname-verification`
+ * :code:`header-splitting` to :code:`response-splitting`
+ * :code:`xss` to :code:`html-injection` and :code:`js-injection`
+ * :code:`write-file` to :code:`file-system-store`
+ * :code:`create-file` and :code:`read-file` to :code:`path-injection`
+ * :code:`open-url` and :code:`jdbc-url` to :code:`request-forgery`
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Deleted many deprecated predicates and classes with uppercase :code:`XML`, :code:`JSON`, :code:`URL`, :code:`API`, etc. in their names. Use the PascalCased versions instead.
+* Deleted the deprecated :code:`localTaintStep` predicate from :code:`DataFlow.qll`.
+* Deleted the deprecated :code:`stringStep`, and :code:`localTaintStep` predicates from :code:`TaintTracking.qll`.
+* Deleted many modules that started with a lowercase letter. Use the versions that start with an uppercase letter instead.
+* Deleted the deprecated :code:`HtmlInjectionConfiguration` and :code:`JQueryHtmlOrSelectorInjectionConfiguration` classes from :code:`DomBasedXssQuery.qll`, use :code:`Configuration` instead.
+* Deleted the deprecated :code:`DefiningIdentifier` class and the :code:`Definitions.qll` file it was in. Use :code:`SsaDefinition` instead.
+* Deleted the deprecated :code:`definitionReaches`, :code:`localDefinitionReaches`, :code:`getAPseudoDefinitionInput`, :code:`nextDefAfter`, and :code:`localDefinitionOverwrites` predicates from :code:`DefUse.qll`.
+* Updated the following JavaScript sink kind names. Any custom data extensions that use these sink kinds will need to be updated accordingly in order to continue working.
+
+ * :code:`command-line-injection` to :code:`command-injection`
+ * :code:`credentials[kind]` to :code:`credentials-kind`
+
+* Added a support of sub modules in :code:`node_modules`.
+
+Ruby
+""""
+
+* Deleted many deprecated predicates and classes with uppercase :code:`URL`, :code:`XSS`, etc. in their names. Use the PascalCased versions instead.
+* Deleted the deprecated :code:`getValueText` predicate from the :code:`Expr`, :code:`StringComponent`, and :code:`ExprCfgNode` classes. Use :code:`getConstantValue` instead.
+* Deleted the deprecated :code:`VariableReferencePattern` class, use :code:`ReferencePattern` instead.
+* Deleted all deprecated aliases in :code:`StandardLibrary.qll`, use :code:`codeql.ruby.frameworks.Core` and :code:`codeql.ruby.frameworks.Stdlib` instead.
+* Support for the :code:`sequel` gem has been added. Method calls that execute queries against a database that may be vulnerable to injection attacks will now be recognized.
+* Support for the :code:`mysql2` gem has been added. Method calls that execute queries against an MySQL database that may be vulnerable to injection attacks will now be recognized.
+* Support for the :code:`pg` gem has been added. Method calls that execute queries against a PostgreSQL database that may be vulnerable to injection attacks will now be recognized.
+
+Swift
+"""""
+
+* Some models for the :code:`Data` class have been generalized to :code:`DataProtocol` so that they apply more widely.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* Kotlin versions up to 1.9.0 are now supported.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.5.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.5.rst
new file mode 100644
index 00000000000..86a3eefad73
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.13.5.rst
@@ -0,0 +1,20 @@
+.. _codeql-cli-2.13.5:
+
+==========================
+CodeQL 2.13.5 (2023-07-05)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+New Features
+~~~~~~~~~~~~
+
+* The Swift extractor now supports Swift 5.8.1.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.0.rst
new file mode 100644
index 00000000000..509212b8e08
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.0.rst
@@ -0,0 +1,269 @@
+.. _codeql-cli-2.14.0:
+
+==========================
+CodeQL 2.14.0 (2023-07-13)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.14.0 runs a total of 390 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 127 queries (covering 33 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* The legacy option :code:`--search-path` will now be used, if provided, when searching for the dependencies of packages that have no lock file.
+* CodeQL query packs that specify their dependencies using the legacy
+ :code:`libraryPathDependencies` property in :code:`qlpack.yml`\ /\ :code:`codeql-pack.yml` files are no longer permitted to contain a :code:`codeql-pack.lock.yml` lock file.
+ This will lead to a compilation error. This change is intended to prevent confusing behavior arising from a mix of legacy (unversioned) and modern
+ (versioned) package dependencies. To fix this error, either delete the lock file, or convert :code:`libraryPathDependencies` to :code:`dependencies`.
+* CodeQL CLI commands that create packages or update package lock files, such as :code:`codeql pack publish` and :code:`codeql pack create`, will no longer work on query packs that specify their dependencies using the legacy
+ :code:`libraryPathDependencies` property. To fix this error, convert
+ :code:`libraryPathDependencies` to :code:`dependencies`.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed super calls on final base classes (or final aliases) so that they are now dispatched the same way as super calls on instanceof supertypes.
+* Fixed a bug where running :code:`codeql database finalize` with a large number of threads would fail due to running out of file descriptors.
+* Fixed a bug where :code:`codeql database create --overwrite` would not work with database clusters.
+* Fixed a bug where the CodeQL documentation coverage statistics were incorrect.
+* Fixed a bug where the generated CodeQL libarary documentation could generate invalid uris on windows.
+
+Deprecations
+~~~~~~~~~~~~
+
+* Missing override annotations on class member predicates now raise errors rather than warnings. This is to avoid confusion with the shadowing behaviour in the presence of final member predicates.
+
+ .. code-block:: ql
+
+ class Foo extends Base {
+ final predicate foo() { ... }
+
+ predicate bar() { ... }
+ }
+
+ class Bar extends Foo {
+ // This method shadows Foo::foo.
+ predicate foo() { ... }
+
+ // This used to override Foo::bar with a warning, now raises error.
+ predicate bar() { ... }
+ }
+
+Improvements
+~~~~~~~~~~~~
+
+* Unqualified imports can now be marked as deprecated to indicate that the import may be removed in the future. Usage of names only reachable through deprecated imports will generate deprecation warnings.
+* Classes declared inside a parameterized modules can final extend parameters of the module as well as types that are declared outside the parameterized module.
+* Fields are fully functional when extending types from within a module instantiation.
+* Files with a :code:`.yaml` extension will now be included in compiled CodeQL packs. Previously, files with this extension were excluded even though :code:`.yml` files were included.
+* When interpreting results (e.g., using :code:`bqrs interpret` or
+ :code:`database interpret-results`), extra placeholders in alert messages are treated as normal text. Previously, results with more placeholders than placeholder values were skipped.
+* Windows users of the CodeQL extension for VS Code will see faster start times.
+* In VS Code, errors in the current file are rechecked when dependencies change.
+* In VS Code, autocomplete in large QL files is now faster.
+* Member predicates can shadow final member predicates of the same arity even when the signatures are not fully matching.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+C#
+""
+
+* The query "Arbitrary file write during zip extraction ("Zip Slip")" (:code:`cs/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+Golang
+""""""
+
+* The query "Arbitrary file write during zip extraction ("zip slip")" (:code:`go/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+Java
+""""
+
+* The query "Arbitrary file write during archive extraction ("Zip Slip")" (:code:`java/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The query "Arbitrary file write during zip extraction ("Zip Slip")" (:code:`js/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+Python
+""""""
+
+* The query "Arbitrary file write during archive extraction ("Zip Slip")" (:code:`py/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+Ruby
+""""
+
+* The experimental query "Arbitrary file write during zipfile/tarfile extraction" (:code:`ruby/zipslip`) has been renamed to "Arbitrary file access during archive extraction ("Zip Slip")."
+
+Swift
+"""""
+
+* Functions and methods modeled as flow summaries are no longer shown in the path of :code:`path-problem` queries. This results in more succinct paths for most security queries.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`cpp/comparison-with-wider-type` query now correctly handles relational operations on signed operators. As a result the query may find more results.
+
+Java
+""""
+
+* New models have been added for :code:`org.apache.commons.lang`.
+* The query :code:`java/unsafe-deserialization` has been updated to take into account :code:`SerialKiller`, a library used to prevent deserialization of arbitrary classes.
+
+Ruby
+""""
+
+* Fixed a bug in how :code:`map_filter` calls are analyzed. Previously, such calls would appear to the return the receiver of the call, but now the return value of the callback is properly taken into account.
+
+New Queries
+~~~~~~~~~~~
+
+C#
+""
+
+* Added a new query, :code:`cs/web/missing-function-level-access-control`, to find instances of missing authorization checks.
+
+Language Libraries
+------------------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+Swift
+"""""
+
+* The :code:`BraceStmt` AST node's :code:`AstNode getElement(index)` member predicate no longer returns :code:`VarDecl`\ s after the :code:`PatternBindingDecl` that declares them. Instead, a new :code:`VarDecl getVariable(index)` predicate has been introduced for accessing the variables declared in a :code:`BraceStmt`.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The data flow library now performs type strengthening. This increases precision for all data flow queries by excluding paths that can be inferred to be impossible due to incompatible types.
+
+Java
+""""
+
+* The data flow library now performs type strengthening. This increases precision for all data flow queries by excluding paths that can be inferred to be impossible due to incompatible types.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Deleted the deprecated :code:`getURL` predicate from the :code:`Container`, :code:`Folder`, and :code:`File` classes. Use the :code:`getLocation` predicate instead.
+
+C#
+""
+
+* Additional support for :code:`command-injection`, :code:`ldap-injection`, :code:`log-injection`, and :code:`url-redirection` sink kinds for Models as Data.
+
+Golang
+""""""
+
+* When a result of path query flows through a function modeled using :code:`DataFlow::FunctionModel` or :code:`TaintTracking::FunctionModel`, the path now includes nodes corresponding to the input and output to the function. This brings it in line with functions modeled using Models-as-Data.
+
+Java
+""""
+
+* Added automatically-generated dataflow models for :code:`javax.portlet`.
+* Added a missing summary model for the method :code:`java.net.URL.toString`.
+* Added automatically-generated dataflow models for the following frameworks and libraries:
+
+ * :code:`hudson`
+ * :code:`jenkins`
+ * :code:`net.sf.json`
+ * :code:`stapler`
+
+* Added more models for the Hudson framework.
+* Added more models for the Stapler framework.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added models for the Webix Framework.
+
+Python
+""""""
+
+* Deleted many models that used the old dataflow library, the new models can be found in the :code:`python/ql/lib/semmle/python/frameworks` folder.
+* More precise modeling of several container functions (such as :code:`sorted`, :code:`reversed`) and methods (such as :code:`set.add`, :code:`list.append`).
+* Added modeling of taint flow through the template argument of :code:`flask.render_template_string` and :code:`flask.stream_template_string`.
+* Deleted many deprecated predicates and classes with uppercase :code:`API`, :code:`HTTP`, :code:`XSS`, :code:`SQL`, etc. in their names. Use the PascalCased versions instead.
+* Deleted the deprecated :code:`getName()` predicate from the :code:`Container` class, use :code:`getAbsolutePath()` instead.
+* Deleted many deprecated module names that started with a lowercase letter, use the versions that start with an uppercase letter instead.
+* Deleted many deprecated predicates in :code:`PointsTo.qll`.
+* Deleted many deprecated files from the :code:`semmle.python.security` package.
+* Deleted the deprecated :code:`BottleRoutePointToExtension` class from :code:`Extensions.qll`.
+* Type tracking is now aware of flow summaries. This leads to a richer API graph, and may lead to more results in some queries.
+
+Ruby
+""""
+
+* More kinds of rack applications are now recognized.
+* Rack::Response instances are now recognized as potential responses from rack applications.
+* HTTP redirect responses from Rack applications are now recognized as a potential sink for open redirect alerts.
+* Additional sinks for :code:`rb/unsafe-deserialization` have been added. This includes various methods from the :code:`yaml` and :code:`plist` gems, which deserialize YAML and Property List data, respectively.
+
+Swift
+"""""
+
+* Added a data flow model for :code:`swap(_:_:)`.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Golang
+""""""
+
+* The :code:`LogInjection::Configuration` taint flow configuration class has been deprecated. Use the :code:`LogInjection::Flow` module instead.
+
+Java
+""""
+
+* The :code:`ExecCallable` class in :code:`ExternalProcess.qll` has been deprecated.
+
+Ruby
+""""
+
+* The :code:`Configuration` taint flow configuration class from :code:`codeql.ruby.security.InsecureDownloadQuery` has been deprecated. Use the :code:`Flow` module instead.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`ProductFlow::StateConfigSig` signature now includes default predicates for :code:`isBarrier1`, :code:`isBarrier2`, :code:`isAdditionalFlowStep1`, and :code:`isAdditionalFlowStep1`. Hence, it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Python
+""""""
+
+* It is now possible to specify flow summaries in the format "MyPkg;Member[list_map];Argument[1].ListElement;Argument[0].Parameter[0];value"
+
+Swift
+"""""
+
+* Added new libraries :code:`Regex.qll` and :code:`RegexTreeView.qll` for reasoning about regular expressions in Swift code and places where they are evaluated.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.1.rst
new file mode 100644
index 00000000000..72e9e816a4e
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.1.rst
@@ -0,0 +1,215 @@
+.. _codeql-cli-2.14.1:
+
+==========================
+CodeQL 2.14.1 (2023-07-27)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.14.1 runs a total of 392 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 127 queries (covering 33 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+There are no user-facing CLI changes in this release.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`cpp/uninitialized-local` query now excludes uninitialized uses that are explicitly cast to void and are expression statements. As a result, the query will report less false positives.
+
+Java
+""""
+
+* The query "Unsafe resource fetching in Android WebView" (:code:`java/android/unsafe-android-webview-fetch`) now recognizes WebViews where :code:`setJavascriptEnabled`, :code:`setAllowFileAccess`, :code:`setAllowUniversalAccessFromFileURLs`, and/or :code:`setAllowFileAccessFromFileURLs` are set inside the function block of the Kotlin :code:`apply` function.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The :code:`fs/promises` package is now recognised as an alias for :code:`require('fs').promises`.
+* The :code:`js/path-injection` query can now track taint through calls to :code:`path.join()` with a spread argument, such as :code:`path.join(baseDir, ...args)`.
+
+Python
+""""""
+
+* Fixed modeling of :code:`aiohttp.ClientSession` so we properly handle :code:`async with` uses. This can impact results of server-side request forgery queries (:code:`py/full-ssrf`, :code:`py/partial-ssrf`).
+
+Ruby
+""""
+
+* Improved resolution of calls performed on an object created with :code:`Proc.new`.
+
+New Queries
+~~~~~~~~~~~
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/xpath-injection`, to detect cases where XPath statements are constructed from user input in an unsafe manner.
+
+Swift
+"""""
+
+* Added new query "Regular expression injection" (:code:`swift/regex-injection`). The query finds places where user input is used to construct a regular expression without proper escaping.
+* Added new query "Inefficient regular expression" (:code:`swift/redos`). This query finds regular expressions that require exponential time to match certain inputs and may make an application vulnerable to denial-of-service attacks.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Ruby
+""""
+
+* The API graph library (:code:`codeql.ruby.ApiGraphs`) has been significantly improved, with better support for inheritance,
+ and data-flow nodes can now be converted to API nodes by calling :code:`.track()` or :code:`.backtrack()` on the node.
+ API graphs allow for efficient modelling of how a given value is used by the code base, or how values produced by the code base are consumed by a library. See the documentation for :code:`API::Node` for details and examples.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+* The :code:`IRGuards` library has improved handling of pointer addition and subtraction operations.
+
+C#
+""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+
+Golang
+""""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+* Parameter nodes now exist for unused parameters as well as used parameters.
+* Add support for v4 of the `Go Micro framework `__.
+* Support for the `Bun framework `__ has been added.
+* Support for `gqlgen `__ has been added.
+* Support for the `go-pg framework `__ has been improved.
+
+Java
+""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+
+* Added models for Apache Commons Lang3 :code:`ToStringBuilder.reflectionToString` method.
+
+* Added support for the Kotlin method :code:`apply`.
+
+* Added models for the following packages:
+
+ * java.io
+ * java.lang
+ * java.net
+ * java.nio.channels
+ * java.nio.file
+ * java.util.zip
+ * okhttp3
+ * org.gradle.api.file
+ * retrofit2
+
+Python
+""""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+* Add support for Models as Data for Reflected XSS query
+* Parameters with a default value are now considered a :code:`DefinitionNode`. This improvement was motivated by allowing type-tracking and API graphs to follow flow from such a default value to a use by a captured variable.
+
+Ruby
+""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+* The :code:`'QUERY_STRING'` field of a Rack :code:`env` parameter is now recognized as a source of remote user input.
+* Query parameters and cookies from :code:`Rack::Response` objects are recognized as potential sources of remote flow input.
+* Calls to :code:`Rack::Utils.parse_query` now propagate taint.
+
+Swift
+"""""
+
+* Data flow configurations can now include a predicate :code:`neverSkip(Node node)` in order to ensure inclusion of certain nodes in the path explanations. The predicate defaults to the end-points of the additional flow steps provided in the configuration, which means that such steps now always are visible by default in path explanations.
+* The regular expression library now understands mode flags specified by :code:`Regex` methods and the :code:`NSRegularExpression` initializer.
+* The regular expression library now understands mode flags specified at the beginning of a regular expression (for example :code:`(?is)`).
+* Added detail to the taint model for :code:`URL`.
+* Added new heuristics to :code:`SensitiveExprs.qll`, enhancing detection from the library.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The library :code:`semmle.code.cpp.dataflow.DataFlow` has been deprecated. Please use :code:`semmle.code.cpp.dataflow.new.DataFlow` instead.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+C#
+""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Golang
+""""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Java
+""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+* A :code:`Class.isFileClass()` predicate, to identify Kotlin file classes, has been added.
+
+Python
+""""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Ruby
+""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Swift
+"""""
+
+* The :code:`DataFlow::StateConfigSig` signature module has gained default implementations for :code:`isBarrier/2` and :code:`isAdditionalFlowStep/4`.
+ Hence it is no longer needed to provide :code:`none()` implementations of these predicates if they are not needed.
+
+Shared Libraries
+----------------
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Utility Classes
+"""""""""""""""
+
+* The :code:`InlineExpectationsTest` class has been deprecated. Use :code:`TestSig` and :code:`MakeTest` instead.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.2.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.2.rst
new file mode 100644
index 00000000000..7e3f8da75a2
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.2.rst
@@ -0,0 +1,159 @@
+.. _codeql-cli-2.14.2:
+
+==========================
+CodeQL 2.14.2 (2023-08-11)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.14.2 runs a total of 393 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 127 queries (covering 33 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The functionality provided by the :code:`codeql execute query-server` subcommand has been removed. The subcommand now responds to all JSON RPC requests with an error response. Correspondingly, this release is no longer compatible with versions of the CodeQL extension for Visual Studio Code prior to 1.7.6.
+
+ This change also breaks third-party CodeQL IDE integrations that still rely on the :code:`codeql execute query-server` subcommand. Maintainers of such CodeQL IDE integrations should migrate to the :code:`codeql execute query-server2` subcommand at the earliest opportunity.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed bug that made the :code:`--warnings=hide` option do nothing in
+ :code:`codeql database analyze` and other commands that *evaluate* queries.
+
+Improvements
+~~~~~~~~~~~~
+
+* Switched from prefix filtering of autocomplete suggestions in the language server to client-side filtering. This improves autocomplete suggestions in contexts with an autocompletion prefix.
+
+* The CodeQL language server now checks query metadata for errors. This allows Visual Studio Code users to see errors in their query metadata without needing to compile the query.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* The sanitizer in :code:`java/potentially-weak-cryptographic-algorithm` has been improved, so the query may yield additional results.
+
+New Queries
+~~~~~~~~~~~
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/ldap-injection`, to detect cases where user input is incorporated into LDAP queries without proper validation or sanitization, potentially leading to LDAP injection vulnerabilities.
+
+Swift
+"""""
+
+* Added new query "Command injection" (:code:`swift/command-line-injection`). The query finds places where user input is used to execute system commands without proper escaping.
+* Added new query "Bad HTML filtering regexp" (:code:`swift/bad-tag-filter`). This query finds regular expressions that match HTML tags in a way that is not robust and can easily lead to security issues.
+
+Language Libraries
+------------------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`shouldPrintFunction` predicate from :code:`PrintAstConfiguration` has been replaced by :code:`shouldPrintDeclaration`. Users should now override :code:`shouldPrintDeclaration` if they want to limit the declarations that should be printed.
+* The :code:`shouldPrintFunction` predicate from :code:`PrintIRConfiguration` has been replaced by :code:`shouldPrintDeclaration`. Users should now override :code:`shouldPrintDeclaration` if they want to limit the declarations that should be printed.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`PrintAST` library now also prints global and namespace variables and their initializers.
+
+Swift
+"""""
+
+* Added :code:`DataFlow::ArrayContent`, which will provide more accurate flow through arrays.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`_Float128x` type is no longer exposed as a builtin type. As this type could not occur any code base, this should only affect queries that explicitly looked at the builtin types.
+
+Golang
+""""""
+
+* Logrus' :code:`WithContext` methods are no longer treated as if they output the values stored in that context to a log message.
+
+Java
+""""
+
+* Fixed a typo in the :code:`StdlibRandomSource` class in :code:`RandomDataSource.qll`, which caused the class to improperly model calls to the :code:`nextBytes` method. Queries relying on :code:`StdlibRandomSource` may see an increase in results.
+* Improved the precision of virtual dispatch of :code:`java.io.InputStream` methods. Now, calls to these methods will not dispatch to arbitrary implementations of :code:`InputStream` if there is a high-confidence alternative (like a models-as-data summary).
+* Added more dataflow steps for :code:`java.io.InputStream`\ s that wrap other :code:`java.io.InputStream`\ s.
+* Added models for the Struts 2 framework.
+* Improved the modeling of Struts 2 sources of untrusted data by tainting the whole object graph of the objects unmarshaled from an HTTP request.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added :code:`log-injection` as a customizable sink kind for log injection.
+
+Swift
+"""""
+
+* Flow through forced optional unwrapping (:code:`!`) is modelled more accurately.
+* Added flow models for :code:`Sequence.withContiguousStorageIfAvailable`.
+* Added taint flow for :code:`NSUserActivity.referrerURL`.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* A :code:`Diagnostic.getCompilationInfo()` predicate has been added.
+
+Shared Libraries
+----------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Control Flow Analysis
+"""""""""""""""""""""
+
+* Initial release. Adds a shared library for control flow analyses.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* Initial release. Moves the shared inter-procedural data-flow library into its own qlpack.
+
+New Features
+~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* The :code:`StateConfigSig` signature now supports a unary :code:`isSink` predicate that does not specify the :code:`FlowState` for which the given node is a sink. Instead, any :code:`FlowState` is considered a valid :code:`FlowState` for such a sink.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.3.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.3.rst
new file mode 100644
index 00000000000..040c791cf2c
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.3.rst
@@ -0,0 +1,114 @@
+.. _codeql-cli-2.14.3:
+
+==========================
+CodeQL 2.14.3 (2023-08-25)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Breaking Changes
+~~~~~~~~~~~~~~~~
+
+* The :code:`.tool.extensions` property in the SARIF generated by :code:`codeql database analyze` now contains the following packs:
+
+ * The containing query pack for each query that was evaluated.
+ * Each model pack that was specified via the :code:`--model-packs` option, regardless of whether that model pack affected any of the evaluated queries.
+
+ Library packs are no longer included in the list.
+
+ Previously, this property contained every query and library pack that was available on the search path, regardless of whether that pack was used during the evaluation.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.8.
+
+* When :code:`codeql test` generates :code:`.actual` files, they will in some cases list the query predicates in a different order than past versions.
+ There is no need to update :code:`.expected` files, as :code:`codeql test` sorts their results accordingly before diffing.
+ However, when there are genuine changes in expected results, the generated :code:`.actual` file can show additional changes against the
+ :code:`.expected` due to the reordering.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+Python
+""""""
+
+* Fixed the computation of locations for imports with aliases in jump-to-definition.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Java
+""""
+
+* Improved support for flow through captured variables that properly adheres to inter-procedural control flow.
+
+Swift
+"""""
+
+* Added :code:`DataFlow::CollectionContent`, which will enable more accurate flow through collections.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The query library for :code:`cs/hardcoded-credentials` now excludes benign properties such as :code:`UserNameClaimType` and :code:`AllowedUserNameCharacters` from :code:`Microsoft.AspNetCore.Identity` options classes.
+
+Java
+""""
+
+* Modified the :code:`getSecureAlgorithmName` predicate in :code:`Encryption.qll` to also include :code:`SHA-256` and :code:`SHA-512`. Previously only the versions of the names without dashes were considered secure.
+* Add support for :code:`WithElement` and :code:`WithoutElement` for MaD access paths.
+
+Python
+""""""
+
+* Support analyzing packages (folders with python code) that do not have :code:`__init__.py` files, although this is technically required, we see real world projects that don't have this.
+* Added modeling of AWS Lambda handlers that can be identified with :code:`AWS::Serverless::Function` in YAML files, where the event parameter is modeled as a remote-flow-source.
+* Improvements of the :code:`aiohttp` models including remote-flow-sources from type annotations, new path manipulation, and SSRF sinks.
+
+Ruby
+""""
+
+* Flow between positional arguments and splat parameters (:code:`*args`) is now tracked more precisely.
+* Flow between splat arguments (:code:`*args`) and positional parameters is now tracked more precisely.
+
+Swift
+"""""
+
+* Added local flow sources for :code:`UITextInput` and related classes.
+* Flow through forced optional unwrapping (:code:`!`) on the left side of assignment now works in most cases.
+* :code:`Type.getName` now gets the name of the type alone without any enclosing types. Use :code:`Type.getFullName` for the old behaviour.
+
+Shared Libraries
+----------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* Initial release. Adds a library to implement flow through captured variables that properly adheres to inter-procedural control flow.
+
+New Features
+~~~~~~~~~~~~
+
+YAML Data Analysis
+""""""""""""""""""
+
+* Added library for serverless functions. Currently used by JavaScript and Python.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.4.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.4.rst
new file mode 100644
index 00000000000..dd2309e557e
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.4.rst
@@ -0,0 +1,197 @@
+.. _codeql-cli-2.14.4:
+
+==========================
+CodeQL 2.14.4 (2023-09-12)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.14.4 runs a total of 394 security queries when configured with the Default suite (covering 155 CWE). The Extended suite enables an additional 129 queries (covering 35 more CWE). 3 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* The CodeQL CLI no longer supports the :code:`SEMMLE_JAVA_ARGS` environment variable.
+ All previous versions of the CodeQL CLI perform command substitution on the
+ :code:`SEMMLE_JAVA_ARGS` value (for example, replacing :code:`'$(echo foo)'` with :code:`'foo'`)
+ when starting a new Java virtual machine, which, depending on the execution environment, may have security implications. Users are advised to check their environments for possible :code:`SEMMLE_JAVA_ARGS` misuse.
+
+Bug Fixes
+~~~~~~~~~
+
+* :code:`codeql database init` (and :code:`github/codeql-action/init@v2` on GitHub Actions)
+ should no longer hang or crash for traced languages on 64-bit Windows machines when certain antivirus software is installed.
+* During :code:`codeql pack create` and :code:`codeql pack publish`, a source version of a pack coming from :code:`--additional-packs` can explicitly be used to override a requested pack version even if this source version is incompatible with the requested version in the pack file. Previously, this would fail with a confusing error message.
+* Fixed a bug where :code:`codeql database interpret-results` hangs when a path query produces a result that has no paths from source to sink.
+
+New Features
+~~~~~~~~~~~~
+
+* The Java extractor now supports files that use Lombok.
+
+Miscellaneous
+~~~~~~~~~~~~~
+
+* The build of Eclipse Temurin OpenJDK that is bundled with the CodeQL CLI has been updated to version 17.0.8.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed an extractor crash that would occur in rare cases when a TypeScript file contains a self-referential namespace alias.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The "Comparison where assignment was intended" query (:code:`cpp/compare-where-assign-meant`) no longer reports comparisons that appear in macro expansions.
+* Some queries that had repeated results corresponding to different levels of indirection for :code:`argv` now only have a single result.
+* The :code:`cpp/non-constant-format` query no longer considers an assignment on the right-hand side of another assignment to be a source of non-constant format strings. As a result, the query may now produce fewer results.
+
+Java
+""""
+
+* The queries "Resolving XML external entity in user-controlled data" (:code:`java/xxe`) and "Resolving XML external entity in user-controlled data from local source" (:code:`java/xxe-local`) now recognize sinks in the MDHT library.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Files larger than 10 MB are no longer be extracted or analyzed.
+* Imports can now be resolved in more cases, where a non-constant string expression is passed to a :code:`require()` call.
+
+Python
+""""""
+
+* Improved *Reflected server-side cross-site scripting* (:code:`py/reflective-xss`) query to not alert on data passed to :code:`flask.jsonify`. Since these HTTP responses are returned with mime-type :code:`application/json`, they do not pose a security risk for XSS.
+* Updated path explanations for :code:`@kind path-problem` queries to always include left hand side of assignments, making paths easier to understand.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added a new query, :code:`cpp/invalid-pointer-deref`, to detect out-of-bounds pointer reads and writes.
+
+Java
+""""
+
+* Added the :code:`java/trust-boundary-violation` query to detect trust boundary violations between HTTP requests and the HTTP session. Also added the :code:`trust-boundary-violation` sink kind for sinks which may cross a trust boundary, such as calls to the :code:`HttpSession#setAttribute` method.
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/improper-ldap-auth`, to detect cases where user input is used during LDAP authentication without proper validation or sanitization, potentially leading to authentication bypass.
+
+Swift
+"""""
+
+* Added new query "Incomplete regular expression for hostnames" (:code:`swift/incomplete-hostname-regexp`). This query finds regular expressions matching a URL or hostname that may match more hostnames than expected.
+
+Language Libraries
+------------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added support for TypeScript 5.2.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* :code:`delete` and :code:`delete[]` are now modeled as calls to the relevant :code:`operator delete` in the IR. In the case of a dynamic delete call a new instruction :code:`VirtualDeleteFunctionAddress` is used to represent a function that dispatches to the correct delete implementation.
+* Only the 2 level indirection of :code:`argv` (corresponding to :code:`**argv`) is consided for :code:`FlowSource`.
+
+C#
+""
+
+* The :code:`--nostdlib` extractor option for the standalone extractor has been removed.
+
+Golang
+""""""
+
+* Added `http.Error `__ to XSS sanitzers.
+
+Java
+""""
+
+* Fixed the MaD signature specifications to use proper nested type names.
+* Added new sanitizer to Java command injection model
+* Added more dataflow models for JAX-RS.
+* The predicate :code:`JaxWsEndpoint::getARemoteMethod` no longer requires the result to be annotated with :code:`@WebMethod`. Instead, the requirements listed in the JAX-RPC Specification 1.1 for required parameter and return types are used. Applications using JAX-RS may see an increase in results.
+
+Python
+""""""
+
+* Regular expressions containing multiple parse mode flags are now interpretted correctly. For example :code:`"(?is)abc.*"` with both the :code:`i` and :code:`s` flags.
+* Added :code:`shlex.quote` as a sanitizer for the :code:`py/shell-command-constructed-from-input` query.
+
+Swift
+"""""
+
+* Flow through optional chaining and forced unwrapping in keypaths is now supported by the data flow library.
+* Added flow models of collection :code:`.withContiguous[Mutable]StorageIfAvailable`, :code:`.withUnsafe[Mutable]BufferPointer` and :code:`.withUnsafe[Mutable]Bytes` methods.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* :code:`getAllocatorCall` on :code:`DeleteExpr` and :code:`DeleteArrayExpr` has been deprecated. :code:`getDeallocatorCall` should be used instead.
+
+New Features
+~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Added :code:`DeleteOrDeleteArrayExpr` as a super type of :code:`DeleteExpr` and :code:`DeleteArrayExpr`
+
+Java
+""""
+
+* Kotlin versions up to 1.9.10 are now supported.
+
+Shared Libraries
+----------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* The shared taint-tracking library is now part of the dataflow qlpack.
+
+New Features
+~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* The various inline flow test libraries have been consolidated as a shared library part in the dataflow qlpack.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.5.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.5.rst
new file mode 100644
index 00000000000..4b2153a825c
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.5.rst
@@ -0,0 +1,20 @@
+.. _codeql-cli-2.14.5:
+
+==========================
+CodeQL 2.14.5 (2023-09-14)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a JavaScript extractor crash that was introduced in 2.14.4.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.6.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.6.rst
new file mode 100644
index 00000000000..6bae48d4d1d
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.14.6.rst
@@ -0,0 +1,31 @@
+.. _codeql-cli-2.14.6:
+
+==========================
+CodeQL 2.14.6 (2023-09-26)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* The tracking of RAM usage has been improved. This fixes some cases where CodeQL uses more RAM than requested.
+
+Query Packs
+-----------
+
+Bug Fixes
+~~~~~~~~~
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Fixed an extractor crash that could occur in projects containing TypeScript files larger than 10 MB.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.0.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.0.rst
new file mode 100644
index 00000000000..ddbdcd8971b
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.0.rst
@@ -0,0 +1,232 @@
+.. _codeql-cli-2.15.0:
+
+==========================
+CodeQL 2.15.0 (2023-10-11)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.15.0 runs a total of 397 security queries when configured with the Default suite (covering 157 CWE). The Extended suite enables an additional 128 queries (covering 33 more CWE). 2 security queries have been added with this release.
+
+CodeQL CLI
+----------
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed an issue with analyzing Python projects using Python 3.12.
+
+Deprecations
+~~~~~~~~~~~~
+
+* :code:`pragma[assume_small_delta]` is now deprecated. The pragma has no effect and should be removed.
+
+* Missing override annotations on class fields now raise errors rather than warnings. This is to avoid confusion with the shadowing behavior in the presence of final fields.
+
+* The CodeQL CLI no longer supports ML-powered alerts. For more information,
+ including details of our work in the AI-powered security technology space,
+ see
+ "\ `CodeQL code scanning deprecates ML-powered alerts `__."
+
+New Features
+~~~~~~~~~~~~
+
+* The output of :code:`codeql version --format json` now includes a :code:`features` property. Each key in the map identifies a feature of the CodeQL CLI. The value for a key is always :code:`true`. Going forward, whenever a significant new feature is added to the CodeQL CLI, a corresponding entry will be added to the
+ :code:`features` map. This is intended to make it easier for tools that invoke the CodeQL CLI to know if the particular version of the CLI they are invoking supports a given feature, without having to know exactly what CLI version introduced that feature.
+
+Improvements
+~~~~~~~~~~~~
+
+* You can now specify the CodeQL languages C/C++, Java/Kotlin, and JavaScript/TypeScript using :code:`--language c-cpp`, :code:`--language java-kotlin`, and
+ :code:`--language javascript-typescript` respectively. These new CodeQL language names convey more clearly what languages each CodeQL language will analyze.
+
+ You can also reference these CodeQL languages via their secondary language names (C/C++ via :code:`--language c` or :code:`--language cpp`, Java/Kotlin via
+ :code:`--language java` or :code:`--language kotlin`, and JavaScript/TypeScript via
+ :code:`--language javascript` or :code:`--language typescript`), however we recommend you refer to them via the new primary CodeQL language names for improved clarity.
+
+* CodeQL now respects custom home directories set by the :code:`$HOME` environment variable on MacOS and Linux and :code:`%USERPROFILE%` on Windows. When set, CodeQL will use the variable's value to change the default location of downloaded packages and the global compilation cache.
+
+* This release improves the quality of
+ \ `file coverage information `__ for repositories that vendor their dependencies. This is currently supported for Go and JavaScript projects.
+
+QL Language
+~~~~~~~~~~~
+
+* The QL language now has two new methods :code:`codePointAt` and :code:`codePointCount` on the :code:`string` type. The methods both return integers and act the same as the similarly named Java methods on strings. For example, :code:`"abc".codePointAt(2)` is :code:`99` and :code:`("a" + 128512.toUnicode() + "c").codePointAt(1)` is a :code:`128512`.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The queries :code:`cpp/double-free` and :code:`cpp/use-after-free` find fewer false positives in cases where a non-returning function is called.
+* The number of duplicated dataflow paths reported by queries has been significantly reduced.
+
+Python
+""""""
+
+* Improved *URL redirection from remote source* (:code:`py/url-redirection`) query to not alert when URL has been checked with :code:`django.utils.http. url_has_allowed_host_and_scheme`.
+* Extended the :code:`py/command-line-injection` query with sinks from Python's :code:`asyncio` module.
+
+Ruby
+""""
+
+* Built-in Ruby queries now use the new DataFlow API.
+
+Swift
+"""""
+
+* Adder barriers for numeric type values to the injection-like queries, to reduce false positive results where the user input that can be injected is constrainted to a numerical value. The queries updated by this change are: "Predicate built from user-controlled sources" (:code:`swift/predicate-injection`), "Database query built from user-controlled sources" (:code:`swift/sql-injection`), "Uncontrolled format string" (:code:`swift/uncontrolled-format-string`), "JavaScript Injection" (:code:`swift/unsafe-js-eval`) and "Regular expression injection" (:code:`swift/regex-injection`).
+* Added additional taint steps to the :code:`swift/cleartext-transmission`, :code:`swift/cleartext-logging` and :code:`swift/cleartext-storage-preferences` queries to identify data within sensitive containers. This is similar to an existing additional taint step in the :code:`swift/cleartext-storage-database` query.
+* Added new logging sinks to the :code:`swift/cleartext-logging` query.
+* Added sqlite3 and SQLite.swift path injection sinks for the :code:`swift/path-injection` query.
+
+New Queries
+~~~~~~~~~~~
+
+C#
+""
+
+* Added a new query, :code:`cs/web/insecure-direct-object-reference`, to find instances of missing authorization checks for resources selected by an ID parameter.
+
+Python
+""""""
+
+* The query :code:`py/nosql-injection` for finding NoSQL injection vulnerabilities is now available in the default security suite.
+
+Query Metadata Changes
+~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The :code:`cpp/double-free` query has been further improved to reduce false positives and its precision has been increased from :code:`medium` to :code:`high`.
+* The :code:`cpp/use-after-free` query has been further improved to reduce false positives and its precision has been increased from :code:`medium` to :code:`high`.
+
+Language Libraries
+------------------
+
+Bug Fixes
+~~~~~~~~~
+
+Java
+""""
+
+* The regular expressions library no longer incorrectly matches mode flag characters against the input.
+
+Python
+""""""
+
+* Subterms of regular expressions encoded as single-line string literals now have better source-location information.
+
+Swift
+"""""
+
+* The regular expressions library no longer incorrectly matches mode flag characters against the input.
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Ruby
+""""
+
+* Improved support for flow through captured variables that properly adheres to inter-procedural control flow.
+
+Swift
+"""""
+
+* The predicates :code:`getABaseType`, :code:`getABaseTypeDecl`, :code:`getADerivedType` and :code:`getADerivedTypeDecl` on :code:`Type` and :code:`TypeDecl` now behave more usefully and consistently. They now explore through type aliases used in base class declarations, and include protocols added in extensions.
+
+ To examine base class declarations at a low level without these enhancements, use :code:`TypeDecl.getInheritedType`.
+
+ :code:`Type.getABaseType` (only) previously resolved a type alias it was called directly on. This behaviour no longer exists. To find any base type of a type that could be an alias, the construct :code:`Type.getUnderlyingType().getABaseType*()` is recommended.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Functions that do not return due to calling functions that don't return (e.g. :code:`exit`) are now detected as non-returning in the IR and dataflow.
+* Treat functions that reach the end of the function as returning in the IR.
+ They used to be treated as unreachable but it is allowed in C.
+* The :code:`DataFlow::asDefiningArgument` predicate now takes its argument from the range starting at :code:`1` instead of :code:`2`. Queries that depend on the single-parameter version of :code:`DataFlow::asDefiningArgument` should have their arguments updated accordingly.
+
+Golang
+""""""
+
+* Added Numeric and Boolean types to SQL injection sanitzers.
+
+Java
+""""
+
+* Fixed a control-flow bug where case rule statements would incorrectly include a fall-through edge.
+* Added support for default cases as proper guards in switch expressions to match switch statements.
+* Improved the class :code:`ArithExpr` of the :code:`Overflow.qll` module to also include compound operators. Because of this, new alerts may be raised in queries related to overflows/underflows.
+* Added new dataflow models for the Apache CXF framework.
+* Regular expressions containing multiple parse mode flags are now interpretted correctly. For example :code:`"(?is)abc.*"` with both the :code:`i` and :code:`s` flags.
+
+Python
+""""""
+
+* Django Rest Framework better handles custom :code:`ModelViewSet` classes functions
+* Regular expression fragments residing inside implicitly concatenated strings now have better location information.
+
+Swift
+"""""
+
+* Modelled varargs function in :code:`NSString` more accurately.
+* Modelled :code:`CustomStringConvertible.description` and :code:`CustomDebugStringConvertible.debugDescription`, replacing ad-hoc models of these properties on derived classes.
+* The regular expressions library now accepts a wider range of mode flags in a regular expression mode flag group (such as :code:`(?u)`). The :code:`(?w`) flag has been renamed from "UNICODE" to "UNICODEBOUNDARY", and the :code:`(?u)` flag is called "UNICODE" in the libraries.
+* Renamed :code:`TypeDecl.getBaseType/1` to :code:`getInheritedType`.
+* Flow through writes via keypaths is now supported by the data flow library.
+* Added flow through variadic arguments, and the :code:`getVaList` function.
+* Added flow steps through :code:`Dictionary` keys and values.
+* Added taint models for :code:`Numeric` conversions.
+
+Deprecated APIs
+~~~~~~~~~~~~~~~
+
+Swift
+"""""
+
+* The :code:`ArrayContent` type in the data flow library has been deprecated and made an alias for the :code:`CollectionContent` type, to better reflect the hierarchy of the Swift standard library. Uses of :code:`ArrayElement` in model files will be interpreted as referring to :code:`CollectionContent`.
+
+New Features
+~~~~~~~~~~~~
+
+Java
+""""
+
+* Kotlin versions up to 1.9.20 are now supported.
+
+Shared Libraries
+----------------
+
+Major Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* Added support for type-based call edge pruning. This removes data flow call edges that are incompatible with the set of flow paths that reach it based on type information. This improves dispatch precision for constructs like lambdas, :code:`Object.toString()` calls, and the visitor pattern. For now this is only enabled for Java and C#.
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Dataflow Analysis
+"""""""""""""""""
+
+* The :code:`isBarrierIn` and :code:`isBarrierOut` predicates in :code:`DataFlow::StateConfigSig` now have overloaded variants that block a specific :code:`FlowState`.
diff --git a/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.1.rst b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.1.rst
new file mode 100644
index 00000000000..7b9dcf0442d
--- /dev/null
+++ b/docs/codeql/codeql-overview/codeql-changelog/codeql-cli-2.15.1.rst
@@ -0,0 +1,215 @@
+.. _codeql-cli-2.15.1:
+
+==========================
+CodeQL 2.15.1 (2023-10-19)
+==========================
+
+.. contents:: Contents
+ :depth: 2
+ :local:
+ :backlinks: none
+
+This is an overview of changes in the CodeQL CLI and relevant CodeQL query and library packs. For additional updates on changes to the CodeQL code scanning experience, check out the `code scanning section on the GitHub blog `__, `relevant GitHub Changelog updates `__, `changes in the CodeQL extension for Visual Studio Code `__, and the `CodeQL Action changelog `__.
+
+Security Coverage
+-----------------
+
+CodeQL 2.15.1 runs a total of 398 security queries when configured with the Default suite (covering 158 CWE). The Extended suite enables an additional 128 queries (covering 33 more CWE). 1 security query has been added with this release.
+
+CodeQL CLI
+----------
+
+Potentially Breaking Changes
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+* The query server's :code:`evaluation/trimCache` command was previously equivalent to the :code:`codeql database cleanup --mode=gentle` CLI command, but is now equivalent to using :code:`--mode=normal`. The new meaning of the command is to clear the entire evaluation cache of a database except for predicates annotated with the :code:`cached` keyword.
+
+Bug Fixes
+~~~~~~~~~
+
+* Fixed a bug where the :code:`$CODEQL_JAVA_HOME` environment variable was erroneously ignored for certain subsidiary Java processes started by
+ :code:`codeql`.
+* Fixed a bug in the CodeQL build tracer on Apple Silicon machines that prevented database creation if System Integrity Protection was disabled.
+
+Deprecations
+~~~~~~~~~~~~
+
+* The accepted values of the :code:`--mode` option for :code:`codeql database cleanup` have been renamed to bring them in line with what they are called in the VSCode extension and the query server:
+
+ * :code:`--mode=brutal` is now :code:`--mode=clear`.
+ * :code:`--mode=normal` is now :code:`--mode=trim`.
+ * :code:`--mode=light` is now :code:`--mode=fit`.
+ * The old names are deprecated, but will be accepted for backwards-compatibility reasons until further notice.
+
+Improvements
+~~~~~~~~~~~~
+
+* The list of failed tests at the end of a :code:`codeql test run` is now sorted lexicographically.
+* The syntax of DIL now more closely resembles the QL source code that it is compiled from. In particular, conjunctions and disjunctions now use the familiar :code:`and` and :code:`or` keywords, and clauses are enclosed in curly braces.
+
+Query Packs
+-----------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C#
+""
+
+* The :code:`cs/web/insecure-direct-object-reference` and :code:`cs/web/missing-function-level-access-control` have been improved to better recognize attributes on generic classes.
+
+Golang
+""""""
+
+* The query "Incorrect conversion between integer types" (:code:`go/incorrect-integer-conversion`) has been improved. It can now detect parsing an unsigned integer type (like :code:`uint32`) and converting it to the signed integer type of the same size (like :code:`int32`), which may lead to more results. It also treats :code:`int` and :code:`uint` more carefully, which may lead to more results or fewer incorrect results.
+
+Java
+""""
+
+* Most data flow queries that track flow from *remote* flow sources now use the current *threat model* configuration instead. This doesn't lead to any changes in the produced alerts (as the default configuration is *remote* flow sources) unless the threat model configuration is changed.
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* Added the :code:`AmdModuleDefinition::Range` class, making it possible to define custom aliases for the AMD :code:`define` function.
+
+Swift
+"""""
+
+* Added more new logging sinks to the :code:`swift/cleartext-logging` query.
+* Added sinks for the GRDB database library to the :code:`swift/hardcoded-key` query.
+* Added sqlite3 and SQLite.swift sinks and flow summaries for the :code:`swift/hardcoded-key` query.
+* Added sqlite3 and SQLite.swift sinks and flow summaries for the :code:`swift/cleartext-storage-database` query.
+
+New Queries
+~~~~~~~~~~~
+
+C/C++
+"""""
+
+* The query :code:`cpp/redundant-null-check-simple` has been promoted to Code Scanning. The query finds cases where a pointer is compared to null after it has already been dereferenced. Such comparisons likely indicate a bug at the place where the pointer is dereferenced, or where the pointer is compared to null.
+
+ Note: This query was incorrectly noted as being promoted to Code Scanning in CodeQL version 2.14.6.
+
+Ruby
+""""
+
+* Added a new experimental query, :code:`rb/jwt-empty-secret-or-algorithm`, to detect when application uses an empty secret or weak algorithm.
+* Added a new experimental query, :code:`rb/jwt-missing-verification`, to detect when the application does not verify a JWT payload.
+
+Language Libraries
+------------------
+
+Minor Analysis Improvements
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+C/C++
+"""""
+
+* Deleted the deprecated :code:`AnalysedString` class, use the new name :code:`AnalyzedString`.
+* Deleted the deprecated :code:`isBarrierGuard` predicate from the dataflow library and its uses, use :code:`isBarrier` and the :code:`BarrierGuard` module instead.
+
+C#
+""
+
+* Deleted the deprecated :code:`isBarrierGuard` predicate from the dataflow library and its uses, use :code:`isBarrier` and the :code:`BarrierGuard` module instead.
+
+Golang
+""""""
+
+* Deleted the deprecated :code:`isBarrierGuard` predicate from the dataflow library and its uses, use :code:`isBarrier` and the :code:`BarrierGuard` module instead.
+* Support has been added for file system access sinks in the following libraries: \ `net/http `__, `Afero `__, `beego `__, `Echo `__, `Fiber `__, `Gin `__, `Iris `__.
+* Added :code:`GoKit.qll` to :code:`go.qll` enabling the GoKit framework by default
+
+Java
+""""
+
+* The :code:`isBarrier`, :code:`isBarrierIn`, :code:`isBarrierOut`, and :code:`isAdditionalFlowStep` methods of the taint-tracking configurations for local queries in the :code:`ArithmeticTaintedLocalQuery`, :code:`ExternallyControlledFormatStringLocalQuery`, :code:`ImproperValidationOfArrayIndexQuery`, :code:`NumericCastTaintedQuery`, :code:`ResponseSplittingLocalQuery`, :code:`SqlTaintedLocalQuery`, and :code:`XssLocalQuery` libraries have been changed to match their remote counterpart configurations.
+* Deleted the deprecated :code:`isBarrierGuard` predicate from the dataflow library and its uses, use :code:`isBarrier` and the :code:`BarrierGuard` module instead.
+* Deleted the deprecated :code:`getAValue` predicate from the :code:`Annotation` class.
+* Deleted the deprecated alias :code:`FloatingPointLiteral`, use :code:`FloatLiteral` instead.
+* Deleted the deprecated :code:`getASuppressedWarningLiteral` predicate from the :code:`SuppressWarningsAnnotation` class.
+* Deleted the deprecated :code:`getATargetExpression` predicate form the :code:`TargetAnnotation` class.
+* Deleted the deprecated :code:`getRetentionPolicyExpression` predicate from the :code:`RetentionAnnotation` class.
+* Deleted the deprecated :code:`conditionCheck` predicate from :code:`Preconditions.qll`.
+* Deleted the deprecated :code:`semmle.code.java.security.performance` folder, use :code:`semmle.code.java.security.regexp` instead.
+* Deleted the deprecated :code:`ExternalAPI` class from :code:`ExternalApi.qll`, use :code:`ExternalApi` instead.
+* Modified the :code:`EnvInput` class in :code:`semmle.code.java.dataflow.FlowSources` to include :code:`environment` and :code:`file` source nodes.
+ There are no changes to results unless you add source models using the :code:`environment` or :code:`file` source kinds.
+* Added :code:`environment` source models for the following methods:
+
+ * :code:`java.lang.System#getenv`
+ * :code:`java.lang.System#getProperties`
+ * :code:`java.lang.System#getProperty`
+ * :code:`java.util.Properties#get`
+ * :code:`java.util.Properties#getProperty`
+
+* Added :code:`file` source models for the following methods:
+
+ * the :code:`java.io.FileInputStream` constructor
+ * :code:`hudson.FilePath#newInputStreamDenyingSymlinkAsNeeded`
+ * :code:`hudson.FilePath#openInputStream`
+ * :code:`hudson.FilePath#read`
+ * :code:`hudson.FilePath#readFromOffset`
+ * :code:`hudson.FilePath#readToString`
+
+* Modified the :code:`DatabaseInput` class in :code:`semmle.code.java.dataflow.FlowSources` to include :code:`database` source nodes.
+ There are no changes to results unless you add source models using the :code:`database` source kind.
+* Added :code:`database` source models for the following method:
+
+ * :code:`java.sql.ResultSet#getString`
+
+JavaScript/TypeScript
+"""""""""""""""""""""
+
+* The contents of :code:`.jsp` files are now extracted, and any :code:`