Skip to content

Commit bd3c4d4

Browse files
committed
Merge branch 'master' of https://github.com/github/codeql into pr/erik-krogh/3478
2 parents 8717f7b + 6041d52 commit bd3c4d4

File tree

167 files changed

+7187
-2309
lines changed

Some content is hidden

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

167 files changed

+7187
-2309
lines changed

change-notes/1.25/analysis-javascript.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
* Support for the following frameworks and libraries has been improved:
66
- [bluebird](http://bluebirdjs.com/)
7+
- [express](https://www.npmjs.com/package/express)
78
- [fstream](https://www.npmjs.com/package/fstream)
89
- [jGrowl](https://github.com/stanlemon/jGrowl)
910
- [jQuery](https://jquery.com/)
@@ -17,6 +18,7 @@
1718
|---------------------------------------------------------------------------------|-------------------------------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
1819
| Cross-site scripting through DOM (`js/xss-through-dom`) | security, external/cwe/cwe-079, external/cwe/cwe-116 | Highlights potential XSS vulnerabilities where existing text from the DOM is used as HTML. Results are not shown on LGTM by default. |
1920
| Incomplete HTML attribute sanitization (`js/incomplete-html-attribute-sanitization`) | security, external/cwe/cwe-20, external/cwe/cwe-079, external/cwe/cwe-116 | Highlights potential XSS vulnerabilities due to incomplete sanitization of HTML meta-characters. Results are shown on LGTM by default. |
21+
| Unsafe expansion of self-closing HTML tag (`js/unsafe-html-expansion`) | security, external/cwe/cwe-079, external/cwe/cwe-116 | Highlights potential XSS vulnerabilities caused by unsafe expansion of self-closing HTML tags. |
2022

2123
## Changes to existing queries
2224

@@ -25,10 +27,16 @@
2527
| Misspelled variable name (`js/misspelled-variable-name`) | Message changed | The message for this query now correctly identifies the misspelled variable in additional cases. |
2628
| Uncontrolled data used in path expression (`js/path-injection`) | More results | This query now recognizes additional file system calls. |
2729
| Uncontrolled command line (`js/command-line-injection`) | More results | This query now recognizes additional command execution calls. |
30+
| Client-side URL redirect (`js/client-side-unvalidated-url-redirection`) | Less results | This query now recognizes additional safe patterns of doing URL redirects. |
31+
| Client-side cross-site scripting (`js/xss`) | Less results | This query now recognizes additional safe strings based on URLs. |
32+
| Incomplete URL scheme check (`js/incomplete-url-scheme-check`) | More results | This query now recognizes additional url scheme checks. |
33+
| Prototype pollution in utility function (`js/prototype-pollution-utility`) | More results | This query now recognizes additional utility functions as vulnerable to prototype polution. |
2834
| Expression has no effect (`js/useless-expression`) | Less results | This query no longer flags an expression when that expression is the only content of the containing file. |
2935
| Unknown directive (`js/unknown-directive`) | Less results | This query no longer flags directives generated by the Babel compiler. |
3036
| Code injection (`js/code-injection`) | More results | More potential vulnerabilities involving NoSQL code operators are now recognized. |
37+
| Zip Slip (`js/zipslip`) | More results | This query now recognizes additional vulnerabilities. |
3138

3239
## Changes to libraries
3340

41+
* A library `semmle.javascript.explore.CallGraph` has been added to help write queries for exploring the call graph.
3442
* Added data flow for `Map` and `Set`, and added matching type-tracking steps that can accessed using the `CollectionsTypeTracking` module.

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

Lines changed: 4 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -184,17 +184,8 @@ class Function extends Declaration, ControlFlowNode, AccessHolder, @function {
184184
* For example: for a function `int Foo(int p1, int p2)` this would
185185
* return `int p1, int p2`.
186186
*/
187-
string getParameterString() { result = getParameterStringFrom(0) }
188-
189-
private string getParameterStringFrom(int index) {
190-
index = getNumberOfParameters() and
191-
result = ""
192-
or
193-
index = getNumberOfParameters() - 1 and
194-
result = getParameter(index).getTypedName()
195-
or
196-
index < getNumberOfParameters() - 1 and
197-
result = getParameter(index).getTypedName() + ", " + getParameterStringFrom(index + 1)
187+
string getParameterString() {
188+
result = concat(int i | | min(getParameter(i).getTypedName()), ", " order by i)
198189
}
199190

200191
/** Gets a call to this function. */
@@ -616,18 +607,8 @@ class FunctionDeclarationEntry extends DeclarationEntry, @fun_decl {
616607
* For example: for a function 'int Foo(int p1, int p2)' this would
617608
* return 'int p1, int p2'.
618609
*/
619-
string getParameterString() { result = getParameterStringFrom(0) }
620-
621-
private string getParameterStringFrom(int index) {
622-
index = getNumberOfParameters() and
623-
result = ""
624-
or
625-
index = getNumberOfParameters() - 1 and
626-
result = getParameterDeclarationEntry(index).getTypedName()
627-
or
628-
index < getNumberOfParameters() - 1 and
629-
result =
630-
getParameterDeclarationEntry(index).getTypedName() + ", " + getParameterStringFrom(index + 1)
610+
string getParameterString() {
611+
result = concat(int i | | min(getParameterDeclarationEntry(i).getTypedName()), ", " order by i)
631612
}
632613

633614
/**

cpp/ql/src/semmle/code/cpp/exprs/Access.qll

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,13 @@ private import semmle.code.cpp.dataflow.EscapesTree
66
/**
77
* A C/C++ access expression. This refers to a function, variable, or enum constant.
88
*/
9-
abstract class Access extends Expr, NameQualifiableElement {
9+
class Access extends Expr, NameQualifiableElement, @access {
10+
// As `@access` is a union type containing `@routineexpr` (which describes function accesses
11+
// that are called), we need to exclude function calls.
12+
Access() { this instanceof @routineexpr implies not iscall(underlyingElement(this), _) }
13+
1014
/** Gets the accessed function, variable, or enum constant. */
11-
abstract Declaration getTarget();
15+
Declaration getTarget() { none() } // overridden in subclasses
1216

1317
override predicate mayBeImpure() { none() }
1418

cpp/ql/src/semmle/code/cpp/exprs/Cast.qll

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ private import semmle.code.cpp.internal.ResolveClass
77
* Instances of this class are not present in the main AST which is navigated by parent/child links. Instead,
88
* instances of this class are attached to nodes in the main AST via special conversion links.
99
*/
10-
abstract class Conversion extends Expr {
10+
class Conversion extends Expr, @conversion {
1111
/** Gets the expression being converted. */
1212
Expr getExpr() { result.getConversion() = this }
1313

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

Lines changed: 84 additions & 52 deletions
Original file line numberDiff line numberDiff line change
@@ -14,19 +14,66 @@ private newtype TOperand =
1414
not Construction::isInCycle(useInstr) and
1515
strictcount(Construction::getRegisterOperandDefinition(useInstr, tag)) = 1
1616
} or
17-
TNonPhiMemoryOperand(
18-
Instruction useInstr, MemoryOperandTag tag, Instruction defInstr, Overlap overlap
19-
) {
20-
defInstr = Construction::getMemoryOperandDefinition(useInstr, tag, overlap) and
21-
not Construction::isInCycle(useInstr) and
22-
strictcount(Construction::getMemoryOperandDefinition(useInstr, tag, _)) = 1
17+
TNonPhiMemoryOperand(Instruction useInstr, MemoryOperandTag tag) {
18+
useInstr.getOpcode().hasOperand(tag)
2319
} or
2420
TPhiOperand(
2521
PhiInstruction useInstr, Instruction defInstr, IRBlock predecessorBlock, Overlap overlap
2622
) {
2723
defInstr = Construction::getPhiOperandDefinition(useInstr, predecessorBlock, overlap)
2824
}
2925

26+
/**
27+
* Base class for all register operands. This is a placeholder for the IPA union type that we will
28+
* eventually use for this purpose.
29+
*/
30+
private class RegisterOperandBase extends TRegisterOperand {
31+
/** Gets a textual representation of this element. */
32+
abstract string toString();
33+
}
34+
35+
/**
36+
* Returns the register operand with the specified parameters.
37+
*/
38+
private RegisterOperandBase registerOperand(
39+
Instruction useInstr, RegisterOperandTag tag, Instruction defInstr
40+
) {
41+
result = TRegisterOperand(useInstr, tag, defInstr)
42+
}
43+
44+
/**
45+
* Base class for all non-Phi memory operands. This is a placeholder for the IPA union type that we
46+
* will eventually use for this purpose.
47+
*/
48+
private class NonPhiMemoryOperandBase extends TNonPhiMemoryOperand {
49+
/** Gets a textual representation of this element. */
50+
abstract string toString();
51+
}
52+
53+
/**
54+
* Returns the non-Phi memory operand with the specified parameters.
55+
*/
56+
private NonPhiMemoryOperandBase nonPhiMemoryOperand(Instruction useInstr, MemoryOperandTag tag) {
57+
result = TNonPhiMemoryOperand(useInstr, tag)
58+
}
59+
60+
/**
61+
* Base class for all Phi operands. This is a placeholder for the IPA union type that we will
62+
* eventually use for this purpose.
63+
*/
64+
private class PhiOperandBase extends TPhiOperand {
65+
abstract string toString();
66+
}
67+
68+
/**
69+
* Returns the Phi operand with the specified parameters.
70+
*/
71+
private PhiOperandBase phiOperand(
72+
Instruction useInstr, Instruction defInstr, IRBlock predecessorBlock, Overlap overlap
73+
) {
74+
result = TPhiOperand(useInstr, defInstr, predecessorBlock, overlap)
75+
}
76+
3077
/**
3178
* A source operand of an `Instruction`. The operand represents a value consumed by the instruction.
3279
*/
@@ -165,8 +212,8 @@ class Operand extends TOperand {
165212
*/
166213
class MemoryOperand extends Operand {
167214
MemoryOperand() {
168-
this = TNonPhiMemoryOperand(_, _, _, _) or
169-
this = TPhiOperand(_, _, _, _)
215+
this instanceof NonPhiMemoryOperandBase or
216+
this instanceof PhiOperandBase
170217
}
171218

172219
/**
@@ -200,18 +247,15 @@ class MemoryOperand extends Operand {
200247
*/
201248
class NonPhiOperand extends Operand {
202249
Instruction useInstr;
203-
Instruction defInstr;
204250
OperandTag tag;
205251

206252
NonPhiOperand() {
207-
this = TRegisterOperand(useInstr, tag, defInstr) or
208-
this = TNonPhiMemoryOperand(useInstr, tag, defInstr, _)
253+
this = registerOperand(useInstr, tag, _) or
254+
this = nonPhiMemoryOperand(useInstr, tag)
209255
}
210256

211257
final override Instruction getUse() { result = useInstr }
212258

213-
final override Instruction getAnyDef() { result = defInstr }
214-
215259
final override string getDumpLabel() { result = tag.getLabel() }
216260

217261
final override int getDumpSortOrder() { result = tag.getSortOrder() }
@@ -222,22 +266,41 @@ class NonPhiOperand extends Operand {
222266
/**
223267
* An operand that consumes a register (non-memory) result.
224268
*/
225-
class RegisterOperand extends NonPhiOperand, TRegisterOperand {
269+
class RegisterOperand extends NonPhiOperand, RegisterOperandBase {
226270
override RegisterOperandTag tag;
271+
Instruction defInstr;
272+
273+
RegisterOperand() { this = registerOperand(useInstr, tag, defInstr) }
274+
275+
final override string toString() { result = tag.toString() }
276+
277+
final override Instruction getAnyDef() { result = defInstr }
227278

228279
final override Overlap getDefinitionOverlap() {
229280
// All register results overlap exactly with their uses.
230281
result instanceof MustExactlyOverlap
231282
}
232283
}
233284

234-
class NonPhiMemoryOperand extends NonPhiOperand, MemoryOperand, TNonPhiMemoryOperand {
285+
class NonPhiMemoryOperand extends NonPhiOperand, MemoryOperand, NonPhiMemoryOperandBase {
235286
override MemoryOperandTag tag;
236-
Overlap overlap;
237287

238-
NonPhiMemoryOperand() { this = TNonPhiMemoryOperand(useInstr, tag, defInstr, overlap) }
288+
NonPhiMemoryOperand() { this = nonPhiMemoryOperand(useInstr, tag) }
239289

240-
final override Overlap getDefinitionOverlap() { result = overlap }
290+
final override string toString() { result = tag.toString() }
291+
292+
final override Instruction getAnyDef() {
293+
result = unique(Instruction defInstr | hasDefinition(defInstr, _))
294+
}
295+
296+
final override Overlap getDefinitionOverlap() { hasDefinition(_, result) }
297+
298+
pragma[noinline]
299+
private predicate hasDefinition(Instruction defInstr, Overlap overlap) {
300+
defInstr = Construction::getMemoryOperandDefinition(useInstr, tag, overlap) and
301+
not Construction::isInCycle(useInstr) and
302+
strictcount(Construction::getMemoryOperandDefinition(useInstr, tag, _)) = 1
303+
}
241304
}
242305

243306
class TypedOperand extends NonPhiMemoryOperand {
@@ -254,8 +317,6 @@ class TypedOperand extends NonPhiMemoryOperand {
254317
*/
255318
class AddressOperand extends RegisterOperand {
256319
override AddressOperandTag tag;
257-
258-
override string toString() { result = "Address" }
259320
}
260321

261322
/**
@@ -264,8 +325,6 @@ class AddressOperand extends RegisterOperand {
264325
*/
265326
class BufferSizeOperand extends RegisterOperand {
266327
override BufferSizeOperandTag tag;
267-
268-
override string toString() { result = "BufferSize" }
269328
}
270329

271330
/**
@@ -274,62 +333,48 @@ class BufferSizeOperand extends RegisterOperand {
274333
*/
275334
class LoadOperand extends TypedOperand {
276335
override LoadOperandTag tag;
277-
278-
override string toString() { result = "Load" }
279336
}
280337

281338
/**
282339
* The source value operand of a `Store` instruction.
283340
*/
284341
class StoreValueOperand extends RegisterOperand {
285342
override StoreValueOperandTag tag;
286-
287-
override string toString() { result = "StoreValue" }
288343
}
289344

290345
/**
291346
* The sole operand of a unary instruction (e.g. `Convert`, `Negate`, `Copy`).
292347
*/
293348
class UnaryOperand extends RegisterOperand {
294349
override UnaryOperandTag tag;
295-
296-
override string toString() { result = "Unary" }
297350
}
298351

299352
/**
300353
* The left operand of a binary instruction (e.g. `Add`, `CompareEQ`).
301354
*/
302355
class LeftOperand extends RegisterOperand {
303356
override LeftOperandTag tag;
304-
305-
override string toString() { result = "Left" }
306357
}
307358

308359
/**
309360
* The right operand of a binary instruction (e.g. `Add`, `CompareEQ`).
310361
*/
311362
class RightOperand extends RegisterOperand {
312363
override RightOperandTag tag;
313-
314-
override string toString() { result = "Right" }
315364
}
316365

317366
/**
318367
* The condition operand of a `ConditionalBranch` or `Switch` instruction.
319368
*/
320369
class ConditionOperand extends RegisterOperand {
321370
override ConditionOperandTag tag;
322-
323-
override string toString() { result = "Condition" }
324371
}
325372

326373
/**
327374
* The operand representing the target function of an `Call` instruction.
328375
*/
329376
class CallTargetOperand extends RegisterOperand {
330377
override CallTargetOperandTag tag;
331-
332-
override string toString() { result = "CallTarget" }
333378
}
334379

335380
/**
@@ -347,43 +392,34 @@ class ArgumentOperand extends RegisterOperand {
347392
*/
348393
class ThisArgumentOperand extends ArgumentOperand {
349394
override ThisArgumentOperandTag tag;
350-
351-
override string toString() { result = "ThisArgument" }
352395
}
353396

354397
/**
355398
* An operand representing an argument to a function call.
356399
*/
357400
class PositionalArgumentOperand extends ArgumentOperand {
358401
override PositionalArgumentOperandTag tag;
359-
int argIndex;
360-
361-
PositionalArgumentOperand() { argIndex = tag.getArgIndex() }
362-
363-
override string toString() { result = "Arg(" + argIndex + ")" }
364402

365403
/**
366404
* Gets the zero-based index of the argument.
367405
*/
368-
final int getIndex() { result = argIndex }
406+
final int getIndex() { result = tag.getArgIndex() }
369407
}
370408

371409
class SideEffectOperand extends TypedOperand {
372410
override SideEffectOperandTag tag;
373-
374-
override string toString() { result = "SideEffect" }
375411
}
376412

377413
/**
378414
* An operand of a `PhiInstruction`.
379415
*/
380-
class PhiInputOperand extends MemoryOperand, TPhiOperand {
416+
class PhiInputOperand extends MemoryOperand, PhiOperandBase {
381417
PhiInstruction useInstr;
382418
Instruction defInstr;
383419
IRBlock predecessorBlock;
384420
Overlap overlap;
385421

386-
PhiInputOperand() { this = TPhiOperand(useInstr, defInstr, predecessorBlock, overlap) }
422+
PhiInputOperand() { this = phiOperand(useInstr, defInstr, predecessorBlock, overlap) }
387423

388424
override string toString() { result = "Phi" }
389425

@@ -413,8 +449,6 @@ class PhiInputOperand extends MemoryOperand, TPhiOperand {
413449
class ChiTotalOperand extends NonPhiMemoryOperand {
414450
override ChiTotalOperandTag tag;
415451

416-
override string toString() { result = "ChiTotal" }
417-
418452
final override MemoryAccessKind getMemoryAccess() { result instanceof ChiTotalMemoryAccess }
419453
}
420454

@@ -424,7 +458,5 @@ class ChiTotalOperand extends NonPhiMemoryOperand {
424458
class ChiPartialOperand extends NonPhiMemoryOperand {
425459
override ChiPartialOperandTag tag;
426460

427-
override string toString() { result = "ChiPartial" }
428-
429461
final override MemoryAccessKind getMemoryAccess() { result instanceof ChiPartialMemoryAccess }
430462
}

0 commit comments

Comments
 (0)