mirror of
https://github.com/github/codeql.git
synced 2026-05-04 13:15:21 +02:00
QL code and tests for C#/C++/JavaScript.
This commit is contained in:
@@ -0,0 +1,3 @@
|
||||
| tst.js:5:2:5:5 | else | This else branch belongs to $@, but its indentation suggests it belongs to $@. | tst.js:3:3:3:4 | if | this if statement | tst.js:2:2:2:3 | if | this other if statement |
|
||||
| tst.js:21:4:21:7 | else | This else branch belongs to $@, but its indentation suggests it belongs to $@. | tst.js:19:3:19:4 | if | this if statement | tst.js:18:2:18:3 | if | this other if statement |
|
||||
| tst.js:40:2:40:5 | else | This else branch belongs to $@, but its indentation suggests it belongs to $@. | tst.js:38:3:38:4 | if | this if statement | tst.js:37:7:37:8 | if | this other if statement |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/DanglingElse.ql
|
||||
@@ -0,0 +1,79 @@
|
||||
function bad1() {
|
||||
if (cond1())
|
||||
if (cond2())
|
||||
return 23;
|
||||
else
|
||||
return 42;
|
||||
}
|
||||
|
||||
function good1() {
|
||||
if (cond1())
|
||||
if (cond2())
|
||||
return 23;
|
||||
else
|
||||
return 42;
|
||||
}
|
||||
|
||||
function bad2() {
|
||||
if (cond1()) {
|
||||
if (cond2()) {
|
||||
return 23;
|
||||
} else {
|
||||
return 42;
|
||||
}}
|
||||
}
|
||||
|
||||
function good2() {
|
||||
if (cond1())
|
||||
if (cond2())
|
||||
return 23;
|
||||
else
|
||||
return 42;
|
||||
}
|
||||
|
||||
function bad3() {
|
||||
if (cond1())
|
||||
return 23;
|
||||
else if (cond2())
|
||||
if (cond2())
|
||||
return 42;
|
||||
else
|
||||
return 42;
|
||||
}
|
||||
|
||||
|
||||
function good3() {
|
||||
if (cond1())
|
||||
if (cond2())
|
||||
return 23;
|
||||
else
|
||||
return 42;
|
||||
}
|
||||
|
||||
function good4() {
|
||||
if (cond1()) {
|
||||
if (cond2())
|
||||
return 23;
|
||||
} else
|
||||
return 42;
|
||||
}
|
||||
|
||||
function good5() {
|
||||
if (cond1())
|
||||
(function inner() {
|
||||
if (cond2())
|
||||
return 23;
|
||||
else
|
||||
return 42;
|
||||
}());
|
||||
}
|
||||
|
||||
function good6() {
|
||||
if (true) {
|
||||
} else if (true) {
|
||||
if (true) {
|
||||
} else if (true) {
|
||||
} else {
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
| tst.js:2:1:2:9 | while(c ... reak;\\n} | This loop executes at most once. |
|
||||
| tst.js:13:3:13:29 | for (; ... et;\\n } | This loop executes at most once. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/EphemeralLoop.ql
|
||||
@@ -0,0 +1,3 @@
|
||||
// EMSCRIPTEN_START_ASM
|
||||
do { ; } while(0);
|
||||
// EMSCRIPTEN_END_ASM
|
||||
@@ -0,0 +1,32 @@
|
||||
// NOT OK
|
||||
while(c){
|
||||
switch(c){
|
||||
case "/":
|
||||
break;
|
||||
default:
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
// NOT OK
|
||||
function f() {
|
||||
for (; k < numprecincts;) {
|
||||
var packet = createPacket(resolution, k, l);
|
||||
k++;
|
||||
return packet;
|
||||
}
|
||||
}
|
||||
|
||||
// OK
|
||||
var oHasProps = false;
|
||||
for (var p in o) {
|
||||
oHasProps = true;
|
||||
break;
|
||||
}
|
||||
|
||||
// OK
|
||||
while(c){
|
||||
if (c === '"')
|
||||
break;
|
||||
console.log(c);
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
| tst.js:3:2:3:11 | if (foo ... n true; | $@ may implicitly return 'undefined' here, while $@ an explicit value is returned. | tst.js:2:1:5:1 | functio ... true;\\n} | Function f | tst.js:4:3:4:14 | return true; | elsewhere |
|
||||
| tst.js:101:2:101:11 | if (foo ... n true; | $@ may implicitly return 'undefined' here, while $@ an explicit value is returned. | tst.js:100:9:103:1 | functio ... true;\\n} | Function u | tst.js:102:3:102:14 | return true; | elsewhere |
|
||||
| tst.js:107:2:107:7 | if (b)\\n\\t\\treturn 1; | $@ may implicitly return 'undefined' here, while $@ an explicit value is returned. | tst.js:106:1:109:1 | functio ... rn 1;\\n} | Function v | tst.js:108:3:108:11 | return 1; | elsewhere |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/ImplicitReturn.ql
|
||||
109
javascript/ql/test/query-tests/Statements/ImplicitReturn/tst.js
Normal file
109
javascript/ql/test/query-tests/Statements/ImplicitReturn/tst.js
Normal file
@@ -0,0 +1,109 @@
|
||||
// NOT OK
|
||||
function f() {
|
||||
if (foo())
|
||||
return true;
|
||||
}
|
||||
|
||||
// OK
|
||||
function g() {
|
||||
if (foo())
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
// OK
|
||||
function h() {
|
||||
open();
|
||||
try {
|
||||
return bar();
|
||||
} finally {
|
||||
close();
|
||||
}
|
||||
}
|
||||
|
||||
// OK
|
||||
function k(x) {
|
||||
switch (x) {
|
||||
case 1:
|
||||
return 23;
|
||||
case 2:
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// OK
|
||||
function l() {
|
||||
return 23;
|
||||
alert("Hi");
|
||||
}
|
||||
|
||||
// OK
|
||||
function m() {
|
||||
if (foo())
|
||||
return true;
|
||||
throw new Error("not foo!");
|
||||
}
|
||||
|
||||
// OK
|
||||
function n() {
|
||||
if (foo())
|
||||
return true;
|
||||
throwError("not foo!");
|
||||
}
|
||||
|
||||
function throwError(msg) {
|
||||
throw new Error(msg);
|
||||
}
|
||||
|
||||
function foo() {
|
||||
return true;
|
||||
}
|
||||
|
||||
//
|
||||
// OK: dual-use constructor
|
||||
function Point(x, y) {
|
||||
if (!(this instanceof Point))
|
||||
return new Point(x, y);
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
}
|
||||
|
||||
// OK: infinite loops
|
||||
function q(n) {
|
||||
for (var i=0;;++i)
|
||||
if (i>2*n)
|
||||
return i;
|
||||
}
|
||||
|
||||
function r(n) {
|
||||
while (true) {
|
||||
if (n-->0)
|
||||
return 23;
|
||||
}
|
||||
}
|
||||
|
||||
function s(n) {
|
||||
do {
|
||||
if (n++>56)
|
||||
return n-2;
|
||||
} while(1);
|
||||
}
|
||||
|
||||
function t(n) {
|
||||
do {
|
||||
if (n++>56)
|
||||
return n-2;
|
||||
} while("true");
|
||||
}
|
||||
|
||||
// NOT OK
|
||||
var u = function() {
|
||||
if (foo())
|
||||
return true;
|
||||
};
|
||||
|
||||
// NOT OK
|
||||
function v(b) {
|
||||
if (b)
|
||||
return 1;
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
| tst.js:6:1:7:1 | for (j ... -j) {\\n} | This loop counts downward, but its variable is bounded upward. |
|
||||
| tst.js:10:1:11:1 | for (va ... ++) {\\n} | This loop counts upward, but its variable is bounded downward. |
|
||||
| tst.js:18:1:19:13 | for (i= ... i] = 0; | This loop counts downward, but its variable is bounded upward. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/InconsistentLoopOrientation.ql
|
||||
@@ -0,0 +1,19 @@
|
||||
// OK
|
||||
for (j = i - 1; j >= 0; --j) {
|
||||
}
|
||||
|
||||
// NOT OK
|
||||
for (j = i + 1; j < strLength; --j) {
|
||||
}
|
||||
|
||||
// NOT OK
|
||||
for (var i = 0, l = c.length; i > l; i ++) {
|
||||
}
|
||||
|
||||
// OK
|
||||
for (i=lower-1; i>=0; --i)
|
||||
a[i] = 0;
|
||||
|
||||
// NOT OK
|
||||
for (i=upper+1; i<a.length; --i)
|
||||
a[i] = 0;
|
||||
@@ -0,0 +1 @@
|
||||
| tst.js:3:3:3:9 | return; | This return statement implicitly returns 'undefined', whereas $@ returns an explicit value. | tst.js:4:2:4:11 | return 42; | another return statement in the same function |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/InconsistentReturn.ql
|
||||
@@ -0,0 +1,5 @@
|
||||
function f() {
|
||||
if (someCond())
|
||||
return;
|
||||
return 42;
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
| nonCaseLabelInSwitch.js:4:3:4:7 | case2 | Non-case labels in switch statements are confusing. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/LabelInCase.ql
|
||||
@@ -0,0 +1,19 @@
|
||||
switch (a) {
|
||||
case 0:
|
||||
case 1:
|
||||
case2:
|
||||
f();
|
||||
break;
|
||||
default:
|
||||
g();
|
||||
}
|
||||
|
||||
switch (a) {
|
||||
case 0:
|
||||
case 1:
|
||||
case2:
|
||||
f();
|
||||
break;
|
||||
default:
|
||||
g();
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
| tst.html:7:9:7:12 | x--; | The indentation of this statement suggests that it is controlled by $@, while in fact it is not. | tst.html:5:7:5:16 | if (x > ... x--; | this statement |
|
||||
| tst.js:4:3:4:6 | g(); | The indentation of this statement suggests that it is controlled by $@, while in fact it is not. | tst.js:2:2:2:12 | if (cond())\\n\\t\\tf(); | this statement |
|
||||
| tst.js:25:3:25:6 | h(); | The indentation of this statement suggests that it is controlled by $@, while in fact it is not. | tst.js:21:2:21:12 | if (con ... \\n\\t\\tg(); | this statement |
|
||||
| tst.js:37:3:37:6 | g(); | The indentation of this statement suggests that it is controlled by $@, while in fact it is not. | tst.js:35:2:35:15 | while ( ... \\n\\t\\tf(); | this statement |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/MisleadingIndentationAfterControlStmt.ql
|
||||
@@ -0,0 +1,4 @@
|
||||
if (foo)
|
||||
{
|
||||
}
|
||||
;
|
||||
@@ -0,0 +1,12 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>Title</title>
|
||||
<script>
|
||||
if (x > 0)
|
||||
x--;
|
||||
x--;
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,122 @@
|
||||
function bad1() {
|
||||
if (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function good1() {
|
||||
if (cond()) {
|
||||
f();
|
||||
}
|
||||
g();
|
||||
}
|
||||
|
||||
function good2() {
|
||||
if (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function bad2() {
|
||||
if (cond())
|
||||
f();
|
||||
else
|
||||
g();
|
||||
h();
|
||||
}
|
||||
|
||||
function good3() {
|
||||
if (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function wbad1() {
|
||||
while (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function wgood1() {
|
||||
while (cond()) {
|
||||
f();
|
||||
}
|
||||
g();
|
||||
}
|
||||
|
||||
function wgood2() {
|
||||
while (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function wgood3() {
|
||||
while (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function dgood() {
|
||||
do
|
||||
f();
|
||||
while (false);
|
||||
g();
|
||||
}
|
||||
|
||||
function tgood() {
|
||||
try {
|
||||
if (cond())
|
||||
throw new Error();
|
||||
} finally {}
|
||||
f();
|
||||
}
|
||||
|
||||
function good4() {
|
||||
if (cond())
|
||||
f();
|
||||
g();
|
||||
}
|
||||
|
||||
function good5() {
|
||||
try {
|
||||
} catch (e) {
|
||||
}
|
||||
}
|
||||
|
||||
function good6() {
|
||||
try {
|
||||
} catch (e) {
|
||||
};
|
||||
}
|
||||
|
||||
function good7() {
|
||||
if (e) {
|
||||
try {
|
||||
} catch (e) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function good8() {
|
||||
if (e) {
|
||||
try {
|
||||
} catch (e) {
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
function good9() {
|
||||
if(e){
|
||||
try{
|
||||
} catch(e){
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
function good10() {
|
||||
if(e){
|
||||
try{
|
||||
}catch(e){
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
| tst.js:3:16:3:18 | i>5 | This for statement uses the same loop variable as an enclosing $@. | tst.js:1:1:9:1 | for (va ... , k);\\n} | for statement |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/NestedLoopsSameVariable.ql
|
||||
@@ -0,0 +1,9 @@
|
||||
for (var i=0; i<10; ++i) {
|
||||
// NOT OK
|
||||
for (var j=i; i>5; --i)
|
||||
f(i, j);
|
||||
|
||||
// OK
|
||||
for (var k=0; k<i; ++k)
|
||||
f(i, k);
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
| tst.js:3:2:3:15 | return x = 23; | The assignment to x is useless, since it is a local variable and will go out of scope. |
|
||||
| tst.js:9:2:9:15 | return x = 23; | The assignment to x is useless, since it is a local variable and will go out of scope. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/ReturnAssignsLocal.ql
|
||||
@@ -0,0 +1,61 @@
|
||||
// NOT OK
|
||||
function f(x) {
|
||||
return x = 23;
|
||||
}
|
||||
|
||||
// NOT OK
|
||||
function g() {
|
||||
var x;
|
||||
return x = 23;
|
||||
}
|
||||
|
||||
// OK
|
||||
function h() {
|
||||
return x = 23;
|
||||
}
|
||||
|
||||
// OK
|
||||
function k() {
|
||||
try {
|
||||
return x = 23;
|
||||
} catch(x) {}
|
||||
}
|
||||
|
||||
// OK: the return statement assigns to a global, not the catch variable
|
||||
function l() {
|
||||
try {
|
||||
throw new Error();
|
||||
} catch(x) {}
|
||||
return x = 23;
|
||||
}
|
||||
|
||||
// OK
|
||||
function m() {
|
||||
var x = 23;
|
||||
return function() {
|
||||
return x = x + 19;
|
||||
};
|
||||
}
|
||||
|
||||
// OK
|
||||
function n(x) {
|
||||
global_getter = function() {
|
||||
return x;
|
||||
};
|
||||
return x = 23;
|
||||
}
|
||||
|
||||
// OK
|
||||
function p() {
|
||||
var x;
|
||||
return {
|
||||
g: function g() {
|
||||
return function h() {
|
||||
return x = 42;
|
||||
}
|
||||
},
|
||||
h: function() {
|
||||
return x;
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
| tst.html:9:66:9:78 | return false; | Return statement outside function. |
|
||||
| tst.js:2:1:2:10 | return 42; | Return statement outside function. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/ReturnOutsideFunction.ql
|
||||
@@ -0,0 +1,5 @@
|
||||
// not a syntax error, but still NOT OK
|
||||
return 42;
|
||||
|
||||
// semmle-extractor-options: --platform
|
||||
// semmle-extractor-options: node
|
||||
@@ -0,0 +1,14 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>Test</title>
|
||||
<script>
|
||||
function validateForm() { return true; }
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
<form name="f" onSubmit="validateForm(this);" action="javascript:return false;" method="post" enctype="multipart/form-data">
|
||||
</form>
|
||||
<form name="g" onsubmit="return validateForm(this);" method="post">
|
||||
</form>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,2 @@
|
||||
// NOT OK
|
||||
return 42;
|
||||
@@ -0,0 +1 @@
|
||||
| tst.js:4:7:4:11 | let x | For loop variable x is not used in the loop body. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/SuspiciousUnusedLoopIterationVariable.ql
|
||||
@@ -0,0 +1,129 @@
|
||||
// BAD
|
||||
function countOccurrences(xs, p) {
|
||||
var count = 0;
|
||||
for (let x of xs)
|
||||
if (p())
|
||||
++count;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function countOccurrences(xs, p) {
|
||||
var count = 0;
|
||||
for (let x of xs)
|
||||
if (p(x))
|
||||
++count;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function countOccurrences(xs, p) {
|
||||
var count = 0;
|
||||
for (let unused of xs)
|
||||
if (p())
|
||||
++count;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function isEmpty(o) {
|
||||
for (var x in o)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
// OK
|
||||
function getNumElt(o) {
|
||||
var count = 0;
|
||||
for (var x of o)
|
||||
++count;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function getNumElt(o) {
|
||||
var count = 0;
|
||||
for (var x of o) {
|
||||
++count;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function getNumElt(o) {
|
||||
var count = 0;
|
||||
for (var x of o)
|
||||
count = count + 1;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function getNumElt(o) {
|
||||
var count = 0;
|
||||
for (var x of o)
|
||||
count = 1 + count;
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function getNumElt(o) {
|
||||
var count = 0;
|
||||
for (var x of o) {
|
||||
console.log("Counting...");
|
||||
count += 1;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
// OK
|
||||
function f(o) {
|
||||
for (var p in o)
|
||||
(function() {
|
||||
console.log(p);
|
||||
})();
|
||||
}
|
||||
|
||||
// OK
|
||||
function lastProp(o) {
|
||||
var key;
|
||||
for (key in obj);
|
||||
return key;
|
||||
}
|
||||
|
||||
// OK
|
||||
function g() {
|
||||
for (var unused in {"toString": null})
|
||||
hasDontEnumBug = false;
|
||||
}
|
||||
|
||||
// OK
|
||||
function is_empty(obj) {
|
||||
var empty = true;
|
||||
for (var key in obj) {
|
||||
empty = false;
|
||||
break;
|
||||
}
|
||||
return empty;
|
||||
}
|
||||
|
||||
// OK
|
||||
function f(objs) {
|
||||
var non_empties = 0;
|
||||
for (var obj in objs) {
|
||||
for (var key in obj) {
|
||||
non_empties += 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return non_empties;
|
||||
}
|
||||
|
||||
// OK: dead loops are not flagged
|
||||
function countOccurrencesDead(xs, p) {
|
||||
return;
|
||||
var count = 0;
|
||||
for (let x of xs)
|
||||
if (p())
|
||||
++count;
|
||||
return count;
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
| tst.js:5:2:5:12 | var a = 42; | This statement is unreachable. |
|
||||
| tst.js:38:1:38:4 | f(); | This statement is unreachable. |
|
||||
| tst.js:63:2:63:3 | y; | This statement is unreachable. |
|
||||
@@ -0,0 +1 @@
|
||||
Statements/UnreachableStatement.ql
|
||||
@@ -0,0 +1,2 @@
|
||||
class A {
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
;
|
||||
|
||||
function f() {
|
||||
return 23;
|
||||
var a = 42;
|
||||
}
|
||||
|
||||
function g(x) {
|
||||
switch(x) {
|
||||
case 0:
|
||||
return 23;
|
||||
break;
|
||||
default:
|
||||
return 42;
|
||||
}
|
||||
}
|
||||
|
||||
function h(i) {
|
||||
while(true) {
|
||||
if (!f(i++)) {
|
||||
break;;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function k() {
|
||||
try {
|
||||
h();
|
||||
} catch(e) {
|
||||
;
|
||||
}
|
||||
|
||||
for (var p in {});
|
||||
for (var i=0; i<10; ++i);
|
||||
}
|
||||
|
||||
throw new Error();
|
||||
f();
|
||||
|
||||
function l(x) {
|
||||
switch(x) {
|
||||
default:
|
||||
return 42;
|
||||
case 0:
|
||||
return 23;
|
||||
}
|
||||
}
|
||||
|
||||
function m(x) {
|
||||
switch(x) {
|
||||
case 0:
|
||||
return 23;
|
||||
default:
|
||||
return 42;
|
||||
case 1:
|
||||
return 56;
|
||||
}
|
||||
}
|
||||
|
||||
if (true)
|
||||
x;
|
||||
else
|
||||
y;
|
||||
|
||||
function f(){
|
||||
if (x) {
|
||||
return;; // trailing ';' is unreachable, but alert is squelched
|
||||
}
|
||||
|
||||
if (x) {
|
||||
return y;
|
||||
} else {
|
||||
return z;
|
||||
}; // ';' is unreachable, but alert is squelched
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
export function foo(x: number): number {
|
||||
let y : A = x;
|
||||
return y;
|
||||
type A = number; // OK.
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
| UselessConditional.js:5:7:5:12 | !lines | This expression always evaluates to false. |
|
||||
| UselessConditional.js:12:34:12:79 | (v = ne ... k] = v) | This logical 'and' expression can be replaced with a comma expression. |
|
||||
| UselessConditional.js:17:9:17:9 | a | Variable 'a' always evaluates to false here. |
|
||||
| UselessConditional.js:18:9:18:9 | b | Variable 'b' always evaluates to false here. |
|
||||
| UselessConditional.js:21:9:21:9 | a | Variable 'a' always evaluates to false here. |
|
||||
| UselessConditional.js:22:9:22:9 | b | Variable 'b' always evaluates to false here. |
|
||||
| UselessConditional.js:26:6:26:6 | x | Variable 'x' always evaluates to true here. |
|
||||
| UselessConditional.js:27:7:27:13 | new X() | This expression always evaluates to true. |
|
||||
| UselessConditional.js:28:7:28:7 | x | Variable 'x' always evaluates to true here. |
|
||||
| UselessConditional.js:29:8:29:8 | x | Variable 'x' always evaluates to true here. |
|
||||
| UselessConditional.js:30:8:30:14 | new X() | This expression always evaluates to true. |
|
||||
| UselessConditional.js:33:7:33:7 | x | Variable 'x' always evaluates to false here. |
|
||||
@@ -0,0 +1,47 @@
|
||||
function getLastLine(input) {
|
||||
var lines = [], nextLine;
|
||||
while ((nextLine = readNextLine(input)))
|
||||
lines.push(nextLine);
|
||||
if (!lines)
|
||||
throw new Error("No lines!");
|
||||
return lines[lines.length-1];
|
||||
}
|
||||
|
||||
function lookup(cache, k) {
|
||||
var v;
|
||||
return k in cache ? cache[k] : (v = new Entry(recompute())) && (cache[k] = v);
|
||||
}
|
||||
|
||||
function test(a, b) {
|
||||
if (!a && !b) {
|
||||
if (a);
|
||||
if (b);
|
||||
}
|
||||
if (!(a || b)) {
|
||||
if (a);
|
||||
if (b);
|
||||
}
|
||||
|
||||
var x = new X();
|
||||
if(x){}
|
||||
if (new X()){}
|
||||
if((x)){}
|
||||
if(((x))){}
|
||||
if ((new X())){}
|
||||
|
||||
x = 0n;
|
||||
if (x) // NOT OK
|
||||
;
|
||||
}
|
||||
|
||||
async function awaitFlow(){
|
||||
var v;
|
||||
|
||||
if (y)
|
||||
v = await f()
|
||||
|
||||
if (v) { // OK
|
||||
}
|
||||
}
|
||||
|
||||
// semmle-extractor-options: --experimental
|
||||
@@ -0,0 +1 @@
|
||||
Statements/UselessConditional.ql
|
||||
@@ -0,0 +1,8 @@
|
||||
function getLastLine(input) {
|
||||
var lines = [], nextLine;
|
||||
while ((nextLine = readNextLine(input)))
|
||||
lines.push(nextLine);
|
||||
if (!lines.length)
|
||||
throw new Error("No lines!");
|
||||
return lines[lines.length-1];
|
||||
}
|
||||
Reference in New Issue
Block a user