Skip to content

Commit 53ff1a3

Browse files
committed
Merge branch 'main' of github.com:github/codeql into python-port-sql-injection
2 parents 77d4cbc + 7535772 commit 53ff1a3

File tree

821 files changed

+21774
-11171
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

821 files changed

+21774
-11171
lines changed

change-notes/1.26/analysis-cpp.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,5 +26,6 @@ The following changes in version 1.26 affect C/C++ analysis in all applications.
2626
* The models library now models many taint flows through `std::istream` and `std::ostream`.
2727
* The models library now models some taint flows through `std::shared_ptr`, `std::unique_ptr`, `std::make_shared` and `std::make_unique`.
2828
* The models library now models many taint flows through `std::pair`, `std::map`, `std::unordered_map`, `std::set` and `std::unordered_set`.
29+
* The models library now models `bcopy`.
2930
* The `SimpleRangeAnalysis` library now supports multiplications of the form
3031
`e1 * e2` and `x *= e2` when `e1` and `e2` are unsigned or constant.

change-notes/1.26/analysis-javascript.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,15 @@
22

33
## General improvements
44

5+
* Angular-specific taint sources and sinks are now recognized by the security queries.
6+
57
* Support for the following frameworks and libraries has been improved:
8+
- [@angular/*](https://www.npmjs.com/package/@angular/core)
69
- [AWS Serverless](https://docs.aws.amazon.com/serverless-application-model/latest/developerguide/sam-resource-function.html)
710
- [Alibaba Serverless](https://www.alibabacloud.com/help/doc-detail/156876.htm)
11+
- [debounce](https://www.npmjs.com/package/debounce)
812
- [bluebird](https://www.npmjs.com/package/bluebird)
13+
- [call-limit](https://www.npmjs.com/package/call-limit)
914
- [express](https://www.npmjs.com/package/express)
1015
- [fast-json-stable-stringify](https://www.npmjs.com/package/fast-json-stable-stringify)
1116
- [fast-safe-stringify](https://www.npmjs.com/package/fast-safe-stringify)
@@ -15,11 +20,15 @@
1520
- [json-stable-stringify](https://www.npmjs.com/package/json-stable-stringify)
1621
- [json-stringify-safe](https://www.npmjs.com/package/json-stringify-safe)
1722
- [json3](https://www.npmjs.com/package/json3)
23+
- [jQuery throttle / debounce](https://github.com/cowboy/jquery-throttle-debounce)
1824
- [lodash](https://www.npmjs.com/package/lodash)
25+
- [lodash.debounce](https://www.npmjs.com/package/lodash.debounce)
26+
- [lodash.throttle](https://www.npmjs.com/package/lodash.throttle)
1927
- [needle](https://www.npmjs.com/package/needle)
2028
- [object-inspect](https://www.npmjs.com/package/object-inspect)
2129
- [pretty-format](https://www.npmjs.com/package/pretty-format)
2230
- [stringify-object](https://www.npmjs.com/package/stringify-object)
31+
- [throttle-debounce](https://www.npmjs.com/package/throttle-debounce)
2332
- [underscore](https://www.npmjs.com/package/underscore)
2433

2534
* Analyzing files with the ".cjs" extension is now supported.
@@ -43,7 +52,10 @@
4352
| Unsafe jQuery plugin (`js/unsafe-jquery-plugin`) | More results | This query now detects more unsafe uses of nested option properties. |
4453
| Client-side URL redirect (`js/client-side-unvalidated-url-redirection`) | More results | This query now recognizes some unsafe uses of `importScripts()` inside WebWorkers. |
4554
| Missing CSRF middleware (`js/missing-token-validation`) | More results | This query now recognizes writes to cookie and session variables as potentially vulnerable to CSRF attacks. |
55+
| Missing CSRF middleware (`js/missing-token-validation`) | Fewer results | This query now recognizes more ways of protecting against CSRF attacks. |
56+
| Client-side cross-site scripting (`js/xss`) | More results | This query now tracks data flow from `location.hash` more precisely. |
4657

4758

4859
## Changes to libraries
4960
* The predicate `TypeAnnotation.hasQualifiedName` now works in more cases when the imported library was not present during extraction.
61+
* The class `DomBasedXss::Configuration` has been deprecated, as it has been split into `DomBasedXss::HtmlInjectionConfiguration` and `DomBasedXss::JQueryHtmlOrSelectorInjectionConfiguration`. Unless specifically working with jQuery sinks, subclasses should instead be based on `HtmlInjectionConfiguration`. To use both configurations in a query, see [Xss.ql](https://github.com/github/codeql/blob/main/javascript/ql/src/Security/CWE-079/Xss.ql) for an example.

cpp/ql/src/Likely Bugs/Arithmetic/IntMultToLong.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,3 +4,5 @@ long j = i * i; //Wrong: due to overflow on the multiplication between ints,
44

55
long k = (long) i * i; //Correct: the multiplication is done on longs instead of ints,
66
//and will not overflow
7+
8+
long l = static_cast<long>(i) * i; //Correct: modern C++

cpp/ql/src/semmle/code/cpp/Parameter.qll

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ class Parameter extends LocalScopeVariable, @parameter {
3636
* 1. The name given to the parameter at the function's definition or
3737
* (for catch block parameters) at the catch block.
3838
* 2. A name given to the parameter at a function declaration.
39-
* 3. The name "p#i" where i is the index of the parameter.
39+
* 3. The name "(unnamed parameter i)" where i is the index of the parameter.
4040
*/
4141
override string getName() {
4242
exists(VariableDeclarationEntry vde |
@@ -46,7 +46,7 @@ class Parameter extends LocalScopeVariable, @parameter {
4646
)
4747
or
4848
not exists(getANamedDeclarationEntry()) and
49-
result = "p#" + this.getIndex().toString()
49+
result = "(unnamed parameter " + this.getIndex().toString() + ")"
5050
}
5151

5252
override string getAPrimaryQlClass() { result = "Parameter" }
@@ -111,7 +111,8 @@ class Parameter extends LocalScopeVariable, @parameter {
111111
* Holds if this parameter has a name.
112112
*
113113
* In other words, this predicate holds precisely when the result of
114-
* `getName()` is not "p#i" (where `i` is the index of the parameter).
114+
* `getName()` is not "(unnamed parameter i)" (where `i` is the index
115+
* of the parameter).
115116
*/
116117
predicate isNamed() { exists(getANamedDeclarationEntry()) }
117118

cpp/ql/src/semmle/code/cpp/controlflow/Dereferenced.qll

Lines changed: 11 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -4,47 +4,25 @@
44

55
import cpp
66
import Nullness
7+
import semmle.code.cpp.models.interfaces.ArrayFunction
78

89
/**
910
* Holds if the call `fc` will dereference argument `i`.
1011
*/
1112
predicate callDereferences(FunctionCall fc, int i) {
12-
exists(string name |
13-
fc.getTarget().hasGlobalOrStdName(name) and
13+
exists(ArrayFunction af |
14+
fc.getTarget() = af and
1415
(
15-
name = "bcopy" and i in [0 .. 1]
16-
or
17-
name = "memcpy" and i in [0 .. 1]
18-
or
19-
name = "memmove" and i in [0 .. 1]
20-
or
21-
name = "strcpy" and i in [0 .. 1]
22-
or
23-
name = "strncpy" and i in [0 .. 1]
24-
or
25-
name = "strdup" and i = 0
26-
or
27-
name = "strndup" and i = 0
28-
or
29-
name = "strlen" and i = 0
30-
or
31-
name = "printf" and fc.getArgument(i).getType() instanceof PointerType
32-
or
33-
name = "fprintf" and fc.getArgument(i).getType() instanceof PointerType
34-
or
35-
name = "sprintf" and fc.getArgument(i).getType() instanceof PointerType
36-
or
37-
name = "snprintf" and fc.getArgument(i).getType() instanceof PointerType
38-
or
39-
name = "vprintf" and fc.getArgument(i).getType() instanceof PointerType
40-
or
41-
name = "vfprintf" and fc.getArgument(i).getType() instanceof PointerType
42-
or
43-
name = "vsprintf" and fc.getArgument(i).getType() instanceof PointerType
44-
or
45-
name = "vsnprintf" and fc.getArgument(i).getType() instanceof PointerType
16+
af.hasArrayInput(i) or
17+
af.hasArrayOutput(i)
4618
)
4719
)
20+
or
21+
exists(FormattingFunction ff |
22+
fc.getTarget() = ff and
23+
i >= ff.getFirstFormatArgumentIndex() and
24+
fc.getArgument(i).getType() instanceof PointerType
25+
)
4826
}
4927

5028
/**

cpp/ql/src/semmle/code/cpp/ir/implementation/aliased_ssa/Instruction.qll

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -804,12 +804,26 @@ class CopyValueInstruction extends CopyInstruction, UnaryInstruction {
804804
final override UnaryOperand getSourceValueOperand() { result = getAnOperand() }
805805
}
806806

807+
/**
808+
* Gets a string describing the location pointed to by the specified address operand.
809+
*/
810+
private string getAddressOperandDescription(AddressOperand operand) {
811+
result = operand.getDef().(VariableAddressInstruction).getIRVariable().toString()
812+
or
813+
not operand.getDef() instanceof VariableAddressInstruction and
814+
result = "?"
815+
}
816+
807817
/**
808818
* An instruction that returns a register result containing a copy of its memory operand.
809819
*/
810820
class LoadInstruction extends CopyInstruction {
811821
LoadInstruction() { getOpcode() instanceof Opcode::Load }
812822

823+
final override string getImmediateString() {
824+
result = getAddressOperandDescription(getSourceAddressOperand())
825+
}
826+
813827
/**
814828
* Gets the operand that provides the address of the value being loaded.
815829
*/
@@ -829,6 +843,10 @@ class LoadInstruction extends CopyInstruction {
829843
class StoreInstruction extends CopyInstruction {
830844
StoreInstruction() { getOpcode() instanceof Opcode::Store }
831845

846+
final override string getImmediateString() {
847+
result = getAddressOperandDescription(getDestinationAddressOperand())
848+
}
849+
832850
/**
833851
* Gets the operand that provides the address of the location to which the value will be stored.
834852
*/

cpp/ql/src/semmle/code/cpp/ir/implementation/raw/Instruction.qll

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -804,12 +804,26 @@ class CopyValueInstruction extends CopyInstruction, UnaryInstruction {
804804
final override UnaryOperand getSourceValueOperand() { result = getAnOperand() }
805805
}
806806

807+
/**
808+
* Gets a string describing the location pointed to by the specified address operand.
809+
*/
810+
private string getAddressOperandDescription(AddressOperand operand) {
811+
result = operand.getDef().(VariableAddressInstruction).getIRVariable().toString()
812+
or
813+
not operand.getDef() instanceof VariableAddressInstruction and
814+
result = "?"
815+
}
816+
807817
/**
808818
* An instruction that returns a register result containing a copy of its memory operand.
809819
*/
810820
class LoadInstruction extends CopyInstruction {
811821
LoadInstruction() { getOpcode() instanceof Opcode::Load }
812822

823+
final override string getImmediateString() {
824+
result = getAddressOperandDescription(getSourceAddressOperand())
825+
}
826+
813827
/**
814828
* Gets the operand that provides the address of the value being loaded.
815829
*/
@@ -829,6 +843,10 @@ class LoadInstruction extends CopyInstruction {
829843
class StoreInstruction extends CopyInstruction {
830844
StoreInstruction() { getOpcode() instanceof Opcode::Store }
831845

846+
final override string getImmediateString() {
847+
result = getAddressOperandDescription(getDestinationAddressOperand())
848+
}
849+
832850
/**
833851
* Gets the operand that provides the address of the location to which the value will be stored.
834852
*/

cpp/ql/src/semmle/code/cpp/ir/implementation/unaliased_ssa/Instruction.qll

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -804,12 +804,26 @@ class CopyValueInstruction extends CopyInstruction, UnaryInstruction {
804804
final override UnaryOperand getSourceValueOperand() { result = getAnOperand() }
805805
}
806806

807+
/**
808+
* Gets a string describing the location pointed to by the specified address operand.
809+
*/
810+
private string getAddressOperandDescription(AddressOperand operand) {
811+
result = operand.getDef().(VariableAddressInstruction).getIRVariable().toString()
812+
or
813+
not operand.getDef() instanceof VariableAddressInstruction and
814+
result = "?"
815+
}
816+
807817
/**
808818
* An instruction that returns a register result containing a copy of its memory operand.
809819
*/
810820
class LoadInstruction extends CopyInstruction {
811821
LoadInstruction() { getOpcode() instanceof Opcode::Load }
812822

823+
final override string getImmediateString() {
824+
result = getAddressOperandDescription(getSourceAddressOperand())
825+
}
826+
813827
/**
814828
* Gets the operand that provides the address of the value being loaded.
815829
*/
@@ -829,6 +843,10 @@ class LoadInstruction extends CopyInstruction {
829843
class StoreInstruction extends CopyInstruction {
830844
StoreInstruction() { getOpcode() instanceof Opcode::Store }
831845

846+
final override string getImmediateString() {
847+
result = getAddressOperandDescription(getDestinationAddressOperand())
848+
}
849+
832850
/**
833851
* Gets the operand that provides the address of the location to which the value will be stored.
834852
*/

cpp/ql/src/semmle/code/cpp/models/implementations/Memcpy.qll

Lines changed: 40 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -10,64 +10,76 @@ import semmle.code.cpp.models.interfaces.SideEffect
1010
import semmle.code.cpp.models.interfaces.Taint
1111

1212
/**
13-
* The standard functions `memcpy` and `memmove`, and the gcc variant
14-
* `__builtin___memcpy_chk`
13+
* The standard functions `memcpy`, `memmove` and `bcopy`; and the gcc variant
14+
* `__builtin___memcpy_chk`.
1515
*/
16-
class MemcpyFunction extends ArrayFunction, DataFlowFunction, SideEffectFunction, TaintFunction {
16+
class MemcpyFunction extends ArrayFunction, DataFlowFunction, SideEffectFunction {
1717
MemcpyFunction() {
18-
this.hasName("memcpy") or
19-
this.hasName("memmove") or
20-
this.hasName("__builtin___memcpy_chk")
18+
// memcpy(dest, src, num)
19+
// memmove(dest, src, num)
20+
// memmove(dest, src, num, remaining)
21+
this.hasName(["memcpy", "memmove", "__builtin___memcpy_chk"])
22+
or
23+
// bcopy(src, dest, num)
24+
this.hasGlobalOrStdName("bcopy")
2125
}
2226

23-
override predicate hasArrayInput(int bufParam) { bufParam = 1 }
27+
/**
28+
* Gets the index of the parameter that is the source buffer for the copy.
29+
*/
30+
int getParamSrc() { if this.hasGlobalOrStdName("bcopy") then result = 0 else result = 1 }
31+
32+
/**
33+
* Gets the index of the parameter that is the destination buffer for the
34+
* copy.
35+
*/
36+
int getParamDest() { if this.hasGlobalOrStdName("bcopy") then result = 1 else result = 0 }
37+
38+
/**
39+
* Gets the index of the parameter that is the size of the copy (in bytes).
40+
*/
41+
int getParamSize() { result = 2 }
42+
43+
override predicate hasArrayInput(int bufParam) { bufParam = getParamSrc() }
2444

25-
override predicate hasArrayOutput(int bufParam) { bufParam = 0 }
45+
override predicate hasArrayOutput(int bufParam) { bufParam = getParamDest() }
2646

2747
override predicate hasDataFlow(FunctionInput input, FunctionOutput output) {
28-
input.isParameterDeref(1) and
29-
output.isParameterDeref(0)
48+
input.isParameterDeref(getParamSrc()) and
49+
output.isParameterDeref(getParamDest())
3050
or
31-
input.isParameterDeref(1) and
51+
input.isParameterDeref(getParamSrc()) and
3252
output.isReturnValueDeref()
3353
or
34-
input.isParameter(0) and
54+
input.isParameter(getParamDest()) and
3555
output.isReturnValue()
3656
}
3757

38-
override predicate hasTaintFlow(FunctionInput input, FunctionOutput output) {
39-
input.isParameter(2) and
40-
output.isParameterDeref(0)
41-
or
42-
input.isParameter(2) and
43-
output.isReturnValueDeref()
44-
}
45-
4658
override predicate hasArrayWithVariableSize(int bufParam, int countParam) {
4759
(
48-
bufParam = 0 or
49-
bufParam = 1
60+
bufParam = getParamDest() or
61+
bufParam = getParamSrc()
5062
) and
51-
countParam = 2
63+
countParam = getParamSize()
5264
}
5365

5466
override predicate hasOnlySpecificReadSideEffects() { any() }
5567

5668
override predicate hasOnlySpecificWriteSideEffects() { any() }
5769

5870
override predicate hasSpecificWriteSideEffect(ParameterIndex i, boolean buffer, boolean mustWrite) {
59-
i = 0 and buffer = true and mustWrite = true
71+
i = getParamDest() and buffer = true and mustWrite = true
6072
}
6173

6274
override predicate hasSpecificReadSideEffect(ParameterIndex i, boolean buffer) {
63-
i = 1 and buffer = true
75+
i = getParamSrc() and buffer = true
6476
}
6577

6678
override ParameterIndex getParameterSizeIndex(ParameterIndex i) {
67-
result = 2 and
79+
result = getParamSize() and
6880
(
69-
i = 0 or
70-
i = 1
81+
i = getParamDest() or
82+
i = getParamSrc()
7183
)
7284
}
7385
}

0 commit comments

Comments
 (0)