mirror of
https://github.com/github/codeql.git
synced 2026-04-28 18:25:24 +02:00
Merge branch 'main' into cwe-346
This commit is contained in:
343
java/ql/test/TestUtilities/InlineExpectationsTest.qll
Normal file
343
java/ql/test/TestUtilities/InlineExpectationsTest.qll
Normal file
@@ -0,0 +1,343 @@
|
||||
/**
|
||||
* Provides a library for writing QL tests whose success or failure is based on expected results
|
||||
* embedded in the test source code as comments, rather than a `.expected` file.
|
||||
*
|
||||
* To add this framework to a new language:
|
||||
* - Add a file `InlineExpectationsTestPrivate.qll` that defines a `LineComment` class. This class
|
||||
* must support a `getContents` method that returns the contents of the given comment, _excluding_
|
||||
* the comment indicator itself. It should also define `toString` and `getLocation` as usual.
|
||||
*
|
||||
* To create a new inline expectations test:
|
||||
* - Declare a class that extends `InlineExpectationsTest`. In the characteristic predicate of the
|
||||
* new class, bind `this` to a unique string (usually the name of the test).
|
||||
* - Override the `hasActualResult()` predicate to produce the actual results of the query. For each
|
||||
* result, specify a `Location`, a text description of the element for which the result was
|
||||
* reported, a short string to serve as the tag to identify expected results for this test, and the
|
||||
* expected value of the result.
|
||||
* - Override `getARelevantTag()` to return the set of tags that can be produced by
|
||||
* `hasActualResult()`. Often this is just a single tag.
|
||||
*
|
||||
* Example:
|
||||
* ```ql
|
||||
* class ConstantValueTest extends InlineExpectationsTest {
|
||||
* ConstantValueTest() { this = "ConstantValueTest" }
|
||||
*
|
||||
* override string getARelevantTag() {
|
||||
* // We only use one tag for this test.
|
||||
* result = "const"
|
||||
* }
|
||||
*
|
||||
* override predicate hasActualResult(
|
||||
* Location location, string element, string tag, string value
|
||||
* ) {
|
||||
* exists(Expr e |
|
||||
* tag = "const" and // The tag for this test.
|
||||
* value = e.getValue() and // The expected value. Will only hold for constant expressions.
|
||||
* location = e.getLocation() and // The location of the result to be reported.
|
||||
* element = e.toString() // The display text for the result.
|
||||
* )
|
||||
* }
|
||||
* }
|
||||
* ```
|
||||
*
|
||||
* There is no need to write a `select` clause or query predicate. All of the differences between
|
||||
* expected results and actual results will be reported in the `failures()` query predicate.
|
||||
*
|
||||
* To annotate the test source code with an expected result, place a comment starting with a `$` on the
|
||||
* same line as the expected result, with text of the following format as the body of the comment:
|
||||
*
|
||||
* `tag=expected-value`
|
||||
*
|
||||
* Where `tag` is the value of the `tag` parameter from `hasActualResult()`, and `expected-value` is
|
||||
* the value of the `value` parameter from `hasActualResult()`. The `=expected-value` portion may be
|
||||
* omitted, in which case `expected-value` is treated as the empty string. Multiple expectations may
|
||||
* be placed in the same comment. Any actual result that
|
||||
* appears on a line that does not contain a matching expected result comment will be reported with
|
||||
* a message of the form "Unexpected result: tag=value". Any expected result comment for which there
|
||||
* is no matching actual result will be reported with a message of the form
|
||||
* "Missing result: tag=expected-value".
|
||||
*
|
||||
* Example:
|
||||
* ```cpp
|
||||
* int i = x + 5; // $const=5
|
||||
* int j = y + (7 - 3) // $const=7 const=3 const=4 // The result of the subtraction is a constant.
|
||||
* ```
|
||||
*
|
||||
* For tests that contain known missing and spurious results, it is possible to further
|
||||
* annotate that a particular expected result is known to be spurious, or that a particular
|
||||
* missing result is known to be missing:
|
||||
*
|
||||
* `$ SPURIOUS: tag=expected-value` // Spurious result
|
||||
* `$ MISSING: tag=expected-value` // Missing result
|
||||
*
|
||||
* A spurious expectation is treated as any other expected result, except that if there is no
|
||||
* matching actual result, the message will be of the form "Fixed spurious result: tag=value". A
|
||||
* missing expectation is treated as if there were no expected result, except that if a
|
||||
* matching expected result is found, the message will be of the form
|
||||
* "Fixed missing result: tag=value".
|
||||
*
|
||||
* A single line can contain all the expected, spurious and missing results of that line. For instance:
|
||||
* `$ tag1=value1 SPURIOUS: tag2=value2 MISSING: tag3=value3`.
|
||||
*
|
||||
* If the same result value is expected for two or more tags on the same line, there is a shorthand
|
||||
* notation available:
|
||||
*
|
||||
* `tag1,tag2=expected-value`
|
||||
*
|
||||
* is equivalent to:
|
||||
*
|
||||
* `tag1=expected-value tag2=expected-value`
|
||||
*/
|
||||
|
||||
private import InlineExpectationsTestPrivate
|
||||
|
||||
/**
|
||||
* Base class for tests with inline expectations. The test extends this class to provide the actual
|
||||
* results of the query, which are then compared with the expected results in comments to produce a
|
||||
* list of failure messages that point out where the actual results differ from the expected
|
||||
* results.
|
||||
*/
|
||||
abstract class InlineExpectationsTest extends string {
|
||||
bindingset[this]
|
||||
InlineExpectationsTest() { any() }
|
||||
|
||||
/**
|
||||
* Returns all tags that can be generated by this test. Most tests will only ever produce a single
|
||||
* tag. Any expected result comments for a tag that is not returned by the `getARelevantTag()`
|
||||
* predicate for an active test will be ignored. This makes it possible to write multiple tests in
|
||||
* different `.ql` files that all query the same source code.
|
||||
*/
|
||||
abstract string getARelevantTag();
|
||||
|
||||
/**
|
||||
* Returns the actual results of the query that is being tested. Each result consist of the
|
||||
* following values:
|
||||
* - `location` - The source code location of the result. Any expected result comment must appear
|
||||
* on the start line of this location.
|
||||
* - `element` - Display text for the element on which the result is reported.
|
||||
* - `tag` - The tag that marks this result as coming from this test. This must be one of the tags
|
||||
* returned by `getARelevantTag()`.
|
||||
* - `value` - The value of the result, which will be matched against the value associated with
|
||||
* `tag` in any expected result comment on that line.
|
||||
*/
|
||||
abstract predicate hasActualResult(Location location, string element, string tag, string value);
|
||||
|
||||
final predicate hasFailureMessage(FailureLocatable element, string message) {
|
||||
exists(ActualResult actualResult |
|
||||
actualResult.getTest() = this and
|
||||
element = actualResult and
|
||||
(
|
||||
exists(FalseNegativeExpectation falseNegative |
|
||||
falseNegative.matchesActualResult(actualResult) and
|
||||
message = "Fixed missing result:" + falseNegative.getExpectationText()
|
||||
)
|
||||
or
|
||||
not exists(ValidExpectation expectation | expectation.matchesActualResult(actualResult)) and
|
||||
message = "Unexpected result: " + actualResult.getExpectationText()
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(ValidExpectation expectation |
|
||||
not exists(ActualResult actualResult | expectation.matchesActualResult(actualResult)) and
|
||||
expectation.getTag() = getARelevantTag() and
|
||||
element = expectation and
|
||||
(
|
||||
expectation instanceof GoodExpectation and
|
||||
message = "Missing result:" + expectation.getExpectationText()
|
||||
or
|
||||
expectation instanceof FalsePositiveExpectation and
|
||||
message = "Fixed spurious result:" + expectation.getExpectationText()
|
||||
)
|
||||
)
|
||||
or
|
||||
exists(InvalidExpectation expectation |
|
||||
element = expectation and
|
||||
message = "Invalid expectation syntax: " + expectation.getExpectation()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* RegEx pattern to match a comment containing one or more expected results. The comment must have
|
||||
* `$` as its first non-whitespace character. Any subsequent character
|
||||
* is treated as part of the expected results, except that the comment may contain a `//` sequence
|
||||
* to treat the remainder of the line as a regular (non-interpreted) comment.
|
||||
*/
|
||||
private string expectationCommentPattern() { result = "\\s*\\$((?:[^/]|/[^/])*)(?://.*)?" }
|
||||
|
||||
/**
|
||||
* The possible columns in an expectation comment. The `TDefaultColumn` branch represents the first
|
||||
* column in a comment. This column is not precedeeded by a name. `TNamedColumn(name)` represents a
|
||||
* column containing expected results preceeded by the string `name:`.
|
||||
*/
|
||||
private newtype TColumn =
|
||||
TDefaultColumn() or
|
||||
TNamedColumn(string name) { name = ["MISSING", "SPURIOUS"] }
|
||||
|
||||
bindingset[start, content]
|
||||
private int getEndOfColumnPosition(int start, string content) {
|
||||
result =
|
||||
min(string name, int cand |
|
||||
exists(TNamedColumn(name)) and
|
||||
cand = content.indexOf(name + ":") and
|
||||
cand > start
|
||||
|
|
||||
cand
|
||||
)
|
||||
or
|
||||
not exists(string name |
|
||||
exists(TNamedColumn(name)) and
|
||||
content.indexOf(name + ":") > start
|
||||
) and
|
||||
result = content.length()
|
||||
}
|
||||
|
||||
private predicate getAnExpectation(
|
||||
LineComment comment, TColumn column, string expectation, string tags, string value
|
||||
) {
|
||||
exists(string content |
|
||||
content = comment.getContents().regexpCapture(expectationCommentPattern(), 1) and
|
||||
(
|
||||
column = TDefaultColumn() and
|
||||
exists(int end |
|
||||
end = getEndOfColumnPosition(0, content) and
|
||||
expectation = content.prefix(end).regexpFind(expectationPattern(), _, _).trim()
|
||||
)
|
||||
or
|
||||
exists(string name, int start, int end |
|
||||
column = TNamedColumn(name) and
|
||||
start = content.indexOf(name + ":") + name.length() + 1 and
|
||||
end = getEndOfColumnPosition(start, content) and
|
||||
expectation = content.substring(start, end).regexpFind(expectationPattern(), _, _).trim()
|
||||
)
|
||||
)
|
||||
) and
|
||||
tags = expectation.regexpCapture(expectationPattern(), 1) and
|
||||
if exists(expectation.regexpCapture(expectationPattern(), 2))
|
||||
then value = expectation.regexpCapture(expectationPattern(), 2)
|
||||
else value = ""
|
||||
}
|
||||
|
||||
private string getColumnString(TColumn column) {
|
||||
column = TDefaultColumn() and result = ""
|
||||
or
|
||||
column = TNamedColumn(result)
|
||||
}
|
||||
|
||||
/**
|
||||
* RegEx pattern to match a single expected result, not including the leading `$`. It consists of one or
|
||||
* more comma-separated tags containing only letters, digits, `-` and `_` (note that the first character
|
||||
* must not be a digit), optionally followed by `=` and the expected value.
|
||||
*/
|
||||
private string expectationPattern() {
|
||||
exists(string tag, string tags, string value |
|
||||
tag = "[A-Za-z-_][A-Za-z-_0-9]*" and
|
||||
tags = "((?:" + tag + ")(?:\\s*,\\s*" + tag + ")*)" and
|
||||
value = "((?:\"[^\"]*\"|'[^']*'|\\S+)*)" and
|
||||
result = tags + "(?:=" + value + ")?"
|
||||
)
|
||||
}
|
||||
|
||||
private newtype TFailureLocatable =
|
||||
TActualResult(
|
||||
InlineExpectationsTest test, Location location, string element, string tag, string value
|
||||
) {
|
||||
test.hasActualResult(location, element, tag, value)
|
||||
} or
|
||||
TValidExpectation(LineComment comment, string tag, string value, string knownFailure) {
|
||||
exists(TColumn column, string tags |
|
||||
getAnExpectation(comment, column, _, tags, value) and
|
||||
tag = tags.splitAt(",") and
|
||||
knownFailure = getColumnString(column)
|
||||
)
|
||||
} or
|
||||
TInvalidExpectation(LineComment comment, string expectation) {
|
||||
getAnExpectation(comment, _, expectation, _, _) and
|
||||
not expectation.regexpMatch(expectationPattern())
|
||||
}
|
||||
|
||||
class FailureLocatable extends TFailureLocatable {
|
||||
string toString() { none() }
|
||||
|
||||
Location getLocation() { none() }
|
||||
|
||||
final string getExpectationText() { result = getTag() + "=" + getValue() }
|
||||
|
||||
string getTag() { none() }
|
||||
|
||||
string getValue() { none() }
|
||||
}
|
||||
|
||||
class ActualResult extends FailureLocatable, TActualResult {
|
||||
InlineExpectationsTest test;
|
||||
Location location;
|
||||
string element;
|
||||
string tag;
|
||||
string value;
|
||||
|
||||
ActualResult() { this = TActualResult(test, location, element, tag, value) }
|
||||
|
||||
override string toString() { result = element }
|
||||
|
||||
override Location getLocation() { result = location }
|
||||
|
||||
InlineExpectationsTest getTest() { result = test }
|
||||
|
||||
override string getTag() { result = tag }
|
||||
|
||||
override string getValue() { result = value }
|
||||
}
|
||||
|
||||
abstract private class Expectation extends FailureLocatable {
|
||||
LineComment comment;
|
||||
|
||||
override string toString() { result = comment.toString() }
|
||||
|
||||
override Location getLocation() { result = comment.getLocation() }
|
||||
}
|
||||
|
||||
private class ValidExpectation extends Expectation, TValidExpectation {
|
||||
string tag;
|
||||
string value;
|
||||
string knownFailure;
|
||||
|
||||
ValidExpectation() { this = TValidExpectation(comment, tag, value, knownFailure) }
|
||||
|
||||
override string getTag() { result = tag }
|
||||
|
||||
override string getValue() { result = value }
|
||||
|
||||
string getKnownFailure() { result = knownFailure }
|
||||
|
||||
predicate matchesActualResult(ActualResult actualResult) {
|
||||
getLocation().getStartLine() = actualResult.getLocation().getStartLine() and
|
||||
getLocation().getFile() = actualResult.getLocation().getFile() and
|
||||
getTag() = actualResult.getTag() and
|
||||
getValue() = actualResult.getValue()
|
||||
}
|
||||
}
|
||||
|
||||
/* Note: These next three classes correspond to all the possible values of type `TColumn`. */
|
||||
class GoodExpectation extends ValidExpectation {
|
||||
GoodExpectation() { getKnownFailure() = "" }
|
||||
}
|
||||
|
||||
class FalsePositiveExpectation extends ValidExpectation {
|
||||
FalsePositiveExpectation() { getKnownFailure() = "SPURIOUS" }
|
||||
}
|
||||
|
||||
class FalseNegativeExpectation extends ValidExpectation {
|
||||
FalseNegativeExpectation() { getKnownFailure() = "MISSING" }
|
||||
}
|
||||
|
||||
class InvalidExpectation extends Expectation, TInvalidExpectation {
|
||||
string expectation;
|
||||
|
||||
InvalidExpectation() { this = TInvalidExpectation(comment, expectation) }
|
||||
|
||||
string getExpectation() { result = expectation }
|
||||
}
|
||||
|
||||
query predicate failures(FailureLocatable element, string message) {
|
||||
exists(InlineExpectationsTest test | test.hasFailureMessage(element, message))
|
||||
}
|
||||
12
java/ql/test/TestUtilities/InlineExpectationsTestPrivate.qll
Normal file
12
java/ql/test/TestUtilities/InlineExpectationsTestPrivate.qll
Normal file
@@ -0,0 +1,12 @@
|
||||
import java
|
||||
|
||||
/**
|
||||
* A class representing line comments in Java, which is simply Javadoc restricted
|
||||
* to EOL comments, with an extra accessor used by the InlineExpectations core code
|
||||
*/
|
||||
class LineComment extends Javadoc {
|
||||
LineComment() { isEolComment(this) }
|
||||
|
||||
/** Gets the contents of the given comment, _without_ the preceding comment marker (`//`). */
|
||||
string getContents() { result = this.getChild(0).toString() }
|
||||
}
|
||||
@@ -1,7 +1,5 @@
|
||||
| UnsafeCertTrustTest.java:27:4:27:74 | init(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:42:4:42:38 | init(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:55:3:60:4 | setDefaultHostnameVerifier(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:73:3:73:57 | setDefaultHostnameVerifier(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:124:25:124:52 | createSSLEngine(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:135:25:135:52 | createSSLEngine(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:144:34:144:83 | createSocket(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:92:25:92:52 | createSSLEngine(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:103:25:103:52 | createSSLEngine(...) | Unsafe configuration of trusted certificates |
|
||||
| UnsafeCertTrustTest.java:112:34:112:83 | createSocket(...) | Unsafe configuration of trusted certificates |
|
||||
|
||||
@@ -48,31 +48,6 @@ public class UnsafeCertTrustTest {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Test the implementation of trusting all hostnames as an anonymous class
|
||||
*/
|
||||
public void testTrustAllHostnameOfAnonymousClass() {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // Noncompliant
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Test the implementation of trusting all hostnames as a variable
|
||||
*/
|
||||
public void testTrustAllHostnameOfVariable() {
|
||||
HostnameVerifier verifier = new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // Noncompliant
|
||||
}
|
||||
};
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(verifier);
|
||||
}
|
||||
|
||||
private static final X509TrustManager TRUST_ALL_CERTIFICATES = new X509TrustManager() {
|
||||
@Override
|
||||
public void checkClientTrusted(final X509Certificate[] chain, final String authType)
|
||||
@@ -109,17 +84,10 @@ public class UnsafeCertTrustTest {
|
||||
}
|
||||
};
|
||||
|
||||
public static final HostnameVerifier ALLOW_ALL_HOSTNAME_VERIFIER = new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // Noncompliant
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Test the endpoint identification of SSL engine is set to null
|
||||
*/
|
||||
public void testSSLEngineEndpointIdSetNull() {
|
||||
public void testSSLEngineEndpointIdSetNull() throws java.security.NoSuchAlgorithmException {
|
||||
SSLContext sslContext = SSLContext.getInstance("TLS");
|
||||
SSLEngine sslEngine = sslContext.createSSLEngine();
|
||||
SSLParameters sslParameters = sslEngine.getSSLParameters();
|
||||
@@ -130,7 +98,7 @@ public class UnsafeCertTrustTest {
|
||||
/**
|
||||
* Test the endpoint identification of SSL engine is not set
|
||||
*/
|
||||
public void testSSLEngineEndpointIdNotSet() {
|
||||
public void testSSLEngineEndpointIdNotSet() throws java.security.NoSuchAlgorithmException {
|
||||
SSLContext sslContext = SSLContext.getInstance("TLS");
|
||||
SSLEngine sslEngine = sslContext.createSSLEngine();
|
||||
}
|
||||
@@ -138,7 +106,7 @@ public class UnsafeCertTrustTest {
|
||||
/**
|
||||
* Test the endpoint identification of SSL socket is not set
|
||||
*/
|
||||
public void testSSLSocketEndpointIdNotSet() {
|
||||
public void testSSLSocketEndpointIdNotSet() throws java.security.NoSuchAlgorithmException, java.io.IOException {
|
||||
SSLContext sslContext = SSLContext.getInstance("TLS");
|
||||
final SSLSocketFactory socketFactory = sslContext.getSocketFactory();
|
||||
SSLSocket socket = (SSLSocket) socketFactory.createSocket("www.example.com", 443);
|
||||
@@ -147,7 +115,7 @@ public class UnsafeCertTrustTest {
|
||||
/**
|
||||
* Test the endpoint identification of regular socket is not set
|
||||
*/
|
||||
public void testSocketEndpointIdNotSet() {
|
||||
public void testSocketEndpointIdNotSet() throws java.io.IOException {
|
||||
SocketFactory socketFactory = SocketFactory.getDefault();
|
||||
Socket socket = socketFactory.createSocket("www.example.com", 80);
|
||||
}
|
||||
@@ -159,4 +127,4 @@ public class UnsafeCertTrustTest {
|
||||
// ConnectionFactory connectionFactory = new ConnectionFactory();
|
||||
// connectionFactory.useSslProtocol();
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
| JxBrowserWithoutCertValidationV6_23_1.java:17:27:17:39 | new Browser(...) | This JxBrowser instance may not check HTTPS certificates. |
|
||||
@@ -0,0 +1 @@
|
||||
experimental/Security/CWE/CWE-295/JxBrowserWithoutCertValidation.ql
|
||||
@@ -0,0 +1,36 @@
|
||||
import com.teamdev.jxbrowser.chromium.Browser;
|
||||
import com.teamdev.jxbrowser.chromium.LoadHandler;
|
||||
import com.teamdev.jxbrowser.chromium.LoadParams;
|
||||
import com.teamdev.jxbrowser.chromium.CertificateErrorParams;
|
||||
|
||||
public class JxBrowserWithoutCertValidationV6_23_1 {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
badUsage();
|
||||
|
||||
goodUsage();
|
||||
|
||||
}
|
||||
|
||||
private static void badUsage() {
|
||||
Browser browser = new Browser();
|
||||
browser.loadURL("https://example.com");
|
||||
// no further calls
|
||||
// BAD: The browser ignores any certificate error by default!
|
||||
}
|
||||
|
||||
private static void goodUsage() {
|
||||
Browser browser = new Browser();
|
||||
browser.setLoadHandler(new LoadHandler() {
|
||||
public boolean onLoad(LoadParams params) {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean onCertificateError(CertificateErrorParams params) {
|
||||
return true; // GOOD: This means that loading will be cancelled on certificate errors
|
||||
}
|
||||
}); // GOOD: A secure `LoadHandler` is used.
|
||||
browser.loadURL("https://example.com");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
//semmle-extractor-options: --javac-args -cp ${testdir}/../../../../stubs/jxbrowser-6.23.1
|
||||
@@ -0,0 +1 @@
|
||||
experimental/Security/CWE/CWE-295/JxBrowserWithoutCertValidation.ql
|
||||
@@ -0,0 +1,36 @@
|
||||
import com.teamdev.jxbrowser.chromium.Browser;
|
||||
import com.teamdev.jxbrowser.chromium.LoadHandler;
|
||||
import com.teamdev.jxbrowser.chromium.LoadParams;
|
||||
import com.teamdev.jxbrowser.chromium.CertificateErrorParams;
|
||||
|
||||
public class JxBrowserWithoutCertValidationV6_24 {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
||||
goodUsage();
|
||||
|
||||
goodUsage2();
|
||||
|
||||
}
|
||||
|
||||
private static void goodUsage() {
|
||||
Browser browser = new Browser();
|
||||
browser.loadURL("https://example.com");
|
||||
// no further calls
|
||||
// GOOD: On version 6.24 the browser properly validates certificates by default!
|
||||
}
|
||||
|
||||
private static void goodUsage2() {
|
||||
Browser browser = new Browser();
|
||||
browser.setLoadHandler(new LoadHandler() {
|
||||
public boolean onLoad(LoadParams params) {
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean onCertificateError(CertificateErrorParams params) {
|
||||
return true; // GOOD: This means that loading will be cancelled on certificate errors
|
||||
}
|
||||
}); // GOOD: A secure `LoadHandler` is used.
|
||||
browser.loadURL("https://example.com");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
//semmle-extractor-options: --javac-args -cp ${testdir}/../../../../stubs/jxbrowser-6.24
|
||||
@@ -29,7 +29,7 @@ class InsecureJavaMail {
|
||||
final Session session = Session.getInstance(properties, authenticator);
|
||||
}
|
||||
|
||||
public void testSimpleMail() {
|
||||
public void testSimpleMail() throws Exception {
|
||||
Email email = new SimpleEmail();
|
||||
email.setHostName("config.hostName");
|
||||
email.setSmtpPort(25);
|
||||
@@ -42,4 +42,4 @@ class InsecureJavaMail {
|
||||
email.addTo("toAddress");
|
||||
email.send();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
}
|
||||
|
||||
// GOOD - save sensitive information in encrypted format
|
||||
public void testSetSharedPrefs2(Context context, String name, String password) {
|
||||
public void testSetSharedPrefs2(Context context, String name, String password) throws Exception {
|
||||
SharedPreferences sharedPrefs = context.getSharedPreferences("user_prefs", Context.MODE_PRIVATE);
|
||||
Editor editor = sharedPrefs.edit();
|
||||
editor.putString("name", encrypt(name));
|
||||
@@ -28,7 +28,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
editor.commit();
|
||||
}
|
||||
|
||||
private static String encrypt(String cleartext) {
|
||||
private static String encrypt(String cleartext) throws Exception {
|
||||
// Use an encryption or hashing algorithm in real world. The demo below just returns its hash.
|
||||
MessageDigest digest = MessageDigest.getInstance("SHA-256");
|
||||
byte[] hash = digest.digest(cleartext.getBytes(StandardCharsets.UTF_8));
|
||||
@@ -37,7 +37,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
}
|
||||
|
||||
// GOOD - save sensitive information in encrypted format using separate variables
|
||||
public void testSetSharedPrefs3(Context context, String name, String password) {
|
||||
public void testSetSharedPrefs3(Context context, String name, String password) throws Exception {
|
||||
String encUsername = encrypt(name);
|
||||
String encPassword = encrypt(password);
|
||||
SharedPreferences sharedPrefs = context.getSharedPreferences("user_prefs", Context.MODE_PRIVATE);
|
||||
@@ -49,7 +49,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
|
||||
|
||||
// GOOD - save sensitive information using the built-in `EncryptedSharedPreferences` class in androidx
|
||||
public void testSetSharedPrefs4(Context context, String name, String password) {
|
||||
public void testSetSharedPrefs4(Context context, String name, String password) throws Exception {
|
||||
MasterKey masterKey = new MasterKey.Builder(context, MasterKey.DEFAULT_MASTER_KEY_ALIAS)
|
||||
.setKeyScheme(MasterKey.KeyScheme.AES256_GCM)
|
||||
.build();
|
||||
@@ -69,7 +69,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
}
|
||||
|
||||
// GOOD - save sensitive information using the built-in `EncryptedSharedPreferences` class in androidx
|
||||
public void testSetSharedPrefs5(Context context, String name, String password) {
|
||||
public void testSetSharedPrefs5(Context context, String name, String password) throws Exception {
|
||||
MasterKey masterKey = new MasterKey.Builder(context, MasterKey.DEFAULT_MASTER_KEY_ALIAS)
|
||||
.setKeyScheme(MasterKey.KeyScheme.AES256_GCM)
|
||||
.build();
|
||||
@@ -89,7 +89,7 @@ public class CleartextStorageSharedPrefs extends Activity {
|
||||
}
|
||||
|
||||
// GOOD - save sensitive information using the built-in `EncryptedSharedPreferences` class in androidx
|
||||
public void testSetSharedPrefs6(Context context, String name, String password) {
|
||||
public void testSetSharedPrefs6(Context context, String name, String password) throws Exception {
|
||||
MasterKey masterKey = new MasterKey.Builder(context, MasterKey.DEFAULT_MASTER_KEY_ALIAS)
|
||||
.setKeyScheme(MasterKey.KeyScheme.AES256_GCM)
|
||||
.build();
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
| InsufficientKeySize.java:9:9:9:24 | init(...) | Key size should be at least 128 bits for AES encryption. |
|
||||
| InsufficientKeySize.java:17:9:17:36 | initialize(...) | Key size should be at least 2048 bits for RSA encryption. |
|
||||
| InsufficientKeySize.java:25:9:25:36 | initialize(...) | Key size should be at least 2048 bits for DSA encryption. |
|
||||
| InsufficientKeySize.java:34:9:34:39 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:38:9:38:67 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:48:9:48:39 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:53:9:53:39 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:58:9:58:40 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:68:9:68:40 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:78:9:78:40 | initialize(...) | Key size should be at least 256 bits for EC encryption. |
|
||||
| InsufficientKeySize.java:87:9:87:37 | initialize(...) | Key size should be at least 2048 bits for DH encryption. |
|
||||
@@ -0,0 +1,93 @@
|
||||
import java.security.KeyPairGenerator;
|
||||
import java.security.spec.ECGenParameterSpec;
|
||||
import javax.crypto.KeyGenerator;
|
||||
|
||||
public class InsufficientKeySize {
|
||||
public void CryptoMethod() throws java.security.NoSuchAlgorithmException, java.security.InvalidAlgorithmParameterException {
|
||||
KeyGenerator keyGen1 = KeyGenerator.getInstance("AES");
|
||||
// BAD: Key size is less than 128
|
||||
keyGen1.init(64);
|
||||
|
||||
KeyGenerator keyGen2 = KeyGenerator.getInstance("AES");
|
||||
// GOOD: Key size is no less than 128
|
||||
keyGen2.init(128);
|
||||
|
||||
KeyPairGenerator keyPairGen1 = KeyPairGenerator.getInstance("RSA");
|
||||
// BAD: Key size is less than 2048
|
||||
keyPairGen1.initialize(1024);
|
||||
|
||||
KeyPairGenerator keyPairGen2 = KeyPairGenerator.getInstance("RSA");
|
||||
// GOOD: Key size is no less than 2048
|
||||
keyPairGen2.initialize(2048);
|
||||
|
||||
KeyPairGenerator keyPairGen3 = KeyPairGenerator.getInstance("DSA");
|
||||
// BAD: Key size is less than 2048
|
||||
keyPairGen3.initialize(1024);
|
||||
|
||||
KeyPairGenerator keyPairGen4 = KeyPairGenerator.getInstance("DSA");
|
||||
// GOOD: Key size is no less than 2048
|
||||
keyPairGen4.initialize(2048);
|
||||
|
||||
KeyPairGenerator keyPairGen5 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec1 = new ECGenParameterSpec("secp112r1");
|
||||
keyPairGen5.initialize(ecSpec1);
|
||||
|
||||
KeyPairGenerator keyPairGen6 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
keyPairGen6.initialize(new ECGenParameterSpec("secp112r1"));
|
||||
|
||||
KeyPairGenerator keyPairGen7 = KeyPairGenerator.getInstance("EC");
|
||||
// GOOD: Key size is no less than 256
|
||||
ECGenParameterSpec ecSpec2 = new ECGenParameterSpec("secp256r1");
|
||||
keyPairGen7.initialize(ecSpec2);
|
||||
|
||||
KeyPairGenerator keyPairGen8 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec3 = new ECGenParameterSpec("X9.62 prime192v2");
|
||||
keyPairGen8.initialize(ecSpec3);
|
||||
|
||||
KeyPairGenerator keyPairGen9 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec4 = new ECGenParameterSpec("X9.62 c2tnb191v3");
|
||||
keyPairGen9.initialize(ecSpec4);
|
||||
|
||||
KeyPairGenerator keyPairGen10 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec5 = new ECGenParameterSpec("sect163k1");
|
||||
keyPairGen10.initialize(ecSpec5);
|
||||
|
||||
KeyPairGenerator keyPairGen11 = KeyPairGenerator.getInstance("EC");
|
||||
// GOOD: Key size is no less than 256
|
||||
ECGenParameterSpec ecSpec6 = new ECGenParameterSpec("X9.62 c2tnb359v1");
|
||||
keyPairGen11.initialize(ecSpec6);
|
||||
|
||||
KeyPairGenerator keyPairGen12 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec7 = new ECGenParameterSpec("prime192v2");
|
||||
keyPairGen12.initialize(ecSpec7);
|
||||
|
||||
KeyPairGenerator keyPairGen13 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is no less than 256
|
||||
ECGenParameterSpec ecSpec8 = new ECGenParameterSpec("prime256v1");
|
||||
keyPairGen13.initialize(ecSpec8);
|
||||
|
||||
KeyPairGenerator keyPairGen14 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is less than 256
|
||||
ECGenParameterSpec ecSpec9 = new ECGenParameterSpec("c2tnb191v1");
|
||||
keyPairGen14.initialize(ecSpec9);
|
||||
|
||||
KeyPairGenerator keyPairGen15 = KeyPairGenerator.getInstance("EC");
|
||||
// BAD: Key size is no less than 256
|
||||
ECGenParameterSpec ecSpec10 = new ECGenParameterSpec("c2tnb431r1");
|
||||
keyPairGen15.initialize(ecSpec10);
|
||||
|
||||
KeyPairGenerator keyPairGen16 = KeyPairGenerator.getInstance("dh");
|
||||
// BAD: Key size is less than 2048
|
||||
keyPairGen16.initialize(1024);
|
||||
|
||||
KeyPairGenerator keyPairGen17 = KeyPairGenerator.getInstance("DH");
|
||||
// GOOD: Key size is no less than 2048
|
||||
keyPairGen17.initialize(2048);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
experimental/Security/CWE/CWE-326/InsufficientKeySize.ql
|
||||
@@ -57,7 +57,7 @@ public class InsecureBasicAuth {
|
||||
/**
|
||||
* Test basic authentication with Apache HTTP POST request using the URI constructor with one argument.
|
||||
*/
|
||||
public void testApacheHttpRequest4(String username, String password) {
|
||||
public void testApacheHttpRequest4(String username, String password) throws Exception {
|
||||
String uriStr = "http://www.example.com/rest/getuser.do?uid=abcdx";
|
||||
URI uri = new URI(uriStr);
|
||||
HttpRequestBase post = new HttpPost(uri);
|
||||
@@ -74,7 +74,7 @@ public class InsecureBasicAuth {
|
||||
/**
|
||||
* Test basic authentication with Apache HTTP POST request using a URI constructor with multiple arguments.
|
||||
*/
|
||||
public void testApacheHttpRequest5(String username, String password) {
|
||||
public void testApacheHttpRequest5(String username, String password) throws Exception {
|
||||
HttpRequestBase post = new HttpPost(new URI("http", "www.example.com", "/test", "abc=123", null));
|
||||
post.setHeader("Accept", "application/json");
|
||||
post.setHeader("Content-type", "application/json");
|
||||
@@ -122,7 +122,7 @@ public class InsecureBasicAuth {
|
||||
/**
|
||||
* Test basic authentication with Java HTTP URL connection using the `URL(String spec)` constructor.
|
||||
*/
|
||||
public void testHttpUrlConnection(String username, String password) {
|
||||
public void testHttpUrlConnection(String username, String password) throws Exception {
|
||||
String urlStr = "http://www.example.com/rest/getuser.do?uid=abcdx";
|
||||
String authString = username + ":" + password;
|
||||
String encoding = Base64.getEncoder().encodeToString(authString.getBytes("UTF-8"));
|
||||
@@ -136,7 +136,7 @@ public class InsecureBasicAuth {
|
||||
/**
|
||||
* Test basic authentication with Java HTTP URL connection using the `URL(String protocol, String host, String file)` constructor.
|
||||
*/
|
||||
public void testHttpUrlConnection2(String username, String password) {
|
||||
public void testHttpUrlConnection2(String username, String password) throws Exception {
|
||||
String host = "www.example.com";
|
||||
String path = "/rest/getuser.do?uid=abcdx";
|
||||
String protocol = "http";
|
||||
@@ -152,7 +152,7 @@ public class InsecureBasicAuth {
|
||||
/**
|
||||
* Test basic authentication with Java HTTP URL connection using a constructor with private URL.
|
||||
*/
|
||||
public void testHttpUrlConnection3(String username, String password) {
|
||||
public void testHttpUrlConnection3(String username, String password) throws Exception {
|
||||
String host = "LOCALHOST";
|
||||
String authString = username + ":" + password;
|
||||
String encoding = Base64.getEncoder().encodeToString(authString.getBytes("UTF-8"));
|
||||
@@ -161,4 +161,4 @@ public class InsecureBasicAuth {
|
||||
conn.setDoOutput(true);
|
||||
conn.setRequestProperty("Authorization", "Basic " + encoding);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,70 @@
|
||||
edges
|
||||
| InsecureLdapAuth.java:11:20:11:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:20:49:20:59 | environment |
|
||||
| InsecureLdapAuth.java:17:3:17:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:20:49:20:59 | environment |
|
||||
| InsecureLdapAuth.java:25:20:25:39 | ... + ... : String | InsecureLdapAuth.java:34:49:34:59 | environment |
|
||||
| InsecureLdapAuth.java:31:3:31:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:34:49:34:59 | environment |
|
||||
| InsecureLdapAuth.java:45:3:45:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:48:49:48:59 | environment |
|
||||
| InsecureLdapAuth.java:53:20:53:50 | "ldap://ad.your-server.com:636" : String | InsecureLdapAuth.java:63:49:63:59 | environment |
|
||||
| InsecureLdapAuth.java:59:3:59:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:63:49:63:59 | environment |
|
||||
| InsecureLdapAuth.java:62:3:62:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:63:49:63:59 | environment |
|
||||
| InsecureLdapAuth.java:68:20:68:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:77:49:77:59 | environment |
|
||||
| InsecureLdapAuth.java:88:3:88:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:91:49:91:59 | environment |
|
||||
| InsecureLdapAuth.java:96:20:96:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:105:59:105:69 | environment |
|
||||
| InsecureLdapAuth.java:102:3:102:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:105:59:105:69 | environment |
|
||||
| InsecureLdapAuth.java:111:20:111:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:120:49:120:59 | environment |
|
||||
| InsecureLdapAuth.java:117:3:117:13 | environment [post update] : Hashtable | InsecureLdapAuth.java:120:49:120:59 | environment |
|
||||
| InsecureLdapAuth.java:124:3:124:5 | env [post update] : Hashtable | InsecureLdapAuth.java:137:10:137:20 | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:128:3:128:5 | env [post update] : Hashtable | InsecureLdapAuth.java:141:16:141:26 | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:128:3:128:5 | env [post update] : Hashtable | InsecureLdapAuth.java:152:16:152:26 | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:135:20:135:39 | ... + ... : String | InsecureLdapAuth.java:142:50:142:60 | environment |
|
||||
| InsecureLdapAuth.java:137:10:137:20 | environment [post update] : Hashtable | InsecureLdapAuth.java:142:50:142:60 | environment |
|
||||
| InsecureLdapAuth.java:141:16:141:26 | environment [post update] : Hashtable | InsecureLdapAuth.java:142:50:142:60 | environment |
|
||||
| InsecureLdapAuth.java:147:20:147:39 | ... + ... : String | InsecureLdapAuth.java:153:50:153:60 | environment |
|
||||
| InsecureLdapAuth.java:152:16:152:26 | environment [post update] : Hashtable | InsecureLdapAuth.java:153:50:153:60 | environment |
|
||||
nodes
|
||||
| InsecureLdapAuth.java:11:20:11:50 | "ldap://ad.your-server.com:389" : String | semmle.label | "ldap://ad.your-server.com:389" : String |
|
||||
| InsecureLdapAuth.java:17:3:17:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:20:49:20:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:20:49:20:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:25:20:25:39 | ... + ... : String | semmle.label | ... + ... : String |
|
||||
| InsecureLdapAuth.java:31:3:31:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:34:49:34:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:34:49:34:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:45:3:45:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:48:49:48:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:53:20:53:50 | "ldap://ad.your-server.com:636" : String | semmle.label | "ldap://ad.your-server.com:636" : String |
|
||||
| InsecureLdapAuth.java:59:3:59:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:62:3:62:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:63:49:63:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:63:49:63:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:63:49:63:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:68:20:68:50 | "ldap://ad.your-server.com:389" : String | semmle.label | "ldap://ad.your-server.com:389" : String |
|
||||
| InsecureLdapAuth.java:77:49:77:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:88:3:88:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:91:49:91:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:96:20:96:50 | "ldap://ad.your-server.com:389" : String | semmle.label | "ldap://ad.your-server.com:389" : String |
|
||||
| InsecureLdapAuth.java:102:3:102:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:105:59:105:69 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:105:59:105:69 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:111:20:111:50 | "ldap://ad.your-server.com:389" : String | semmle.label | "ldap://ad.your-server.com:389" : String |
|
||||
| InsecureLdapAuth.java:117:3:117:13 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:120:49:120:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:120:49:120:59 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:124:3:124:5 | env [post update] : Hashtable | semmle.label | env [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:128:3:128:5 | env [post update] : Hashtable | semmle.label | env [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:135:20:135:39 | ... + ... : String | semmle.label | ... + ... : String |
|
||||
| InsecureLdapAuth.java:137:10:137:20 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:141:16:141:26 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:142:50:142:60 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:142:50:142:60 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:142:50:142:60 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:147:20:147:39 | ... + ... : String | semmle.label | ... + ... : String |
|
||||
| InsecureLdapAuth.java:152:16:152:26 | environment [post update] : Hashtable | semmle.label | environment [post update] : Hashtable |
|
||||
| InsecureLdapAuth.java:153:50:153:60 | environment | semmle.label | environment |
|
||||
| InsecureLdapAuth.java:153:50:153:60 | environment | semmle.label | environment |
|
||||
#select
|
||||
| InsecureLdapAuth.java:20:49:20:59 | environment | InsecureLdapAuth.java:11:20:11:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:20:49:20:59 | environment | Insecure LDAP authentication from $@. | InsecureLdapAuth.java:11:20:11:50 | "ldap://ad.your-server.com:389" | LDAP connection string |
|
||||
| InsecureLdapAuth.java:34:49:34:59 | environment | InsecureLdapAuth.java:25:20:25:39 | ... + ... : String | InsecureLdapAuth.java:34:49:34:59 | environment | Insecure LDAP authentication from $@. | InsecureLdapAuth.java:25:20:25:39 | ... + ... | LDAP connection string |
|
||||
| InsecureLdapAuth.java:105:59:105:69 | environment | InsecureLdapAuth.java:96:20:96:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:105:59:105:69 | environment | Insecure LDAP authentication from $@. | InsecureLdapAuth.java:96:20:96:50 | "ldap://ad.your-server.com:389" | LDAP connection string |
|
||||
| InsecureLdapAuth.java:120:49:120:59 | environment | InsecureLdapAuth.java:111:20:111:50 | "ldap://ad.your-server.com:389" : String | InsecureLdapAuth.java:120:49:120:59 | environment | Insecure LDAP authentication from $@. | InsecureLdapAuth.java:111:20:111:50 | "ldap://ad.your-server.com:389" | LDAP connection string |
|
||||
| InsecureLdapAuth.java:153:50:153:60 | environment | InsecureLdapAuth.java:147:20:147:39 | ... + ... : String | InsecureLdapAuth.java:153:50:153:60 | environment | Insecure LDAP authentication from $@. | InsecureLdapAuth.java:147:20:147:39 | ... + ... | LDAP connection string |
|
||||
@@ -0,0 +1,155 @@
|
||||
import java.util.Hashtable;
|
||||
|
||||
import javax.naming.Context;
|
||||
import javax.naming.directory.DirContext;
|
||||
import javax.naming.directory.InitialDirContext;
|
||||
import javax.naming.ldap.InitialLdapContext;
|
||||
|
||||
public class InsecureLdapAuth {
|
||||
// BAD - Test LDAP authentication in cleartext using `DirContext`.
|
||||
public void testCleartextLdapAuth(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://ad.your-server.com:389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// BAD - Test LDAP authentication in cleartext using `DirContext`.
|
||||
public void testCleartextLdapAuth(String ldapUserName, String password, String serverName) throws Exception {
|
||||
String ldapUrl = "ldap://"+serverName+":389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// GOOD - Test LDAP authentication over SSL.
|
||||
public void testSslLdapAuth(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldaps://ad.your-server.com:636";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// GOOD - Test LDAP authentication over SSL.
|
||||
public void testSslLdapAuth2(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://ad.your-server.com:636";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
environment.put(Context.SECURITY_PROTOCOL, "ssl");
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// GOOD - Test LDAP authentication with SASL authentication.
|
||||
public void testSaslLdapAuth(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://ad.your-server.com:389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "DIGEST-MD5 GSSAPI");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// GOOD - Test LDAP authentication in cleartext connecting to local LDAP server.
|
||||
public void testCleartextLdapAuth2(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://localhost:389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
// BAD - Test LDAP authentication in cleartext using `InitialLdapContext`.
|
||||
public void testCleartextLdapAuth3(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://ad.your-server.com:389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
environment.put(Context.REFERRAL, "follow");
|
||||
environment.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
environment.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
environment.put(Context.SECURITY_CREDENTIALS, password);
|
||||
InitialLdapContext ldapContext = new InitialLdapContext(environment, null);
|
||||
}
|
||||
|
||||
|
||||
// BAD - Test LDAP authentication in cleartext using `DirContext` and string literals.
|
||||
public void testCleartextLdapAuth4(String ldapUserName, String password) throws Exception {
|
||||
String ldapUrl = "ldap://ad.your-server.com:389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put("java.naming.factory.initial",
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put("java.naming.provider.url", ldapUrl);
|
||||
environment.put("java.naming.referral", "follow");
|
||||
environment.put("java.naming.security.authentication", "simple");
|
||||
environment.put("java.naming.security.principal", ldapUserName);
|
||||
environment.put("java.naming.security.credentials", password);
|
||||
DirContext dirContext = new InitialDirContext(environment);
|
||||
}
|
||||
|
||||
private void setSSL(Hashtable env) {
|
||||
env.put(Context.SECURITY_PROTOCOL, "ssl");
|
||||
}
|
||||
|
||||
private void setBasicAuth(Hashtable env, String ldapUserName, String password) {
|
||||
env.put(Context.SECURITY_AUTHENTICATION, "simple");
|
||||
env.put(Context.SECURITY_PRINCIPAL, ldapUserName);
|
||||
env.put(Context.SECURITY_CREDENTIALS, password);
|
||||
}
|
||||
|
||||
// GOOD - Test LDAP authentication with `ssl` configuration and basic authentication.
|
||||
public void testCleartextLdapAuth5(String ldapUserName, String password, String serverName) throws Exception {
|
||||
String ldapUrl = "ldap://"+serverName+":389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
setSSL(environment);
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
setBasicAuth(environment, ldapUserName, password);
|
||||
DirContext dirContext = new InitialLdapContext(environment, null);
|
||||
}
|
||||
|
||||
// BAD - Test LDAP authentication with basic authentication.
|
||||
public void testCleartextLdapAuth6(String ldapUserName, String password, String serverName) throws Exception {
|
||||
String ldapUrl = "ldap://"+serverName+":389";
|
||||
Hashtable<String, String> environment = new Hashtable<String, String>();
|
||||
environment.put(Context.INITIAL_CONTEXT_FACTORY,
|
||||
"com.sun.jndi.ldap.LdapCtxFactory");
|
||||
environment.put(Context.PROVIDER_URL, ldapUrl);
|
||||
setBasicAuth(environment, ldapUserName, password);
|
||||
DirContext dirContext = new InitialLdapContext(environment, null);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
experimental/Security/CWE/CWE-522/InsecureLdapAuth.ql
|
||||
@@ -1 +1 @@
|
||||
experimental/CWE-918/RequestForgery.ql
|
||||
experimental/Security/CWE/CWE-918/RequestForgery.ql
|
||||
|
||||
@@ -26,7 +26,7 @@ public class SpringSSRF extends HttpServlet {
|
||||
String fooResourceUrl = request2.getParameter("uri");;
|
||||
RestTemplate restTemplate = new RestTemplate();
|
||||
HttpEntity<String> request = new HttpEntity<>(new String("bar"));
|
||||
|
||||
try {
|
||||
{
|
||||
ResponseEntity<String> response =
|
||||
restTemplate.getForEntity(fooResourceUrl + "/1", String.class);
|
||||
@@ -68,5 +68,6 @@ public class SpringSSRF extends HttpServlet {
|
||||
{
|
||||
restTemplate.put(fooResourceUrl, new String("object"));
|
||||
}
|
||||
} catch (org.springframework.web.client.RestClientException | java.net.URISyntaxException e) {}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public class Browser extends java.lang.Object {
|
||||
public void setLoadHandler(LoadHandler handler) {
|
||||
}
|
||||
|
||||
public void loadURL(String url) {
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public final class CertificateErrorParams extends Object {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public interface LoadHandler {
|
||||
boolean onCertificateError(CertificateErrorParams params);
|
||||
|
||||
boolean onLoad(LoadParams params);
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public final class LoadParams extends Object {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public interface BoundsListener {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public class Browser extends java.lang.Object {
|
||||
public void setLoadHandler(LoadHandler handler) {
|
||||
}
|
||||
|
||||
public void loadURL(String url) {
|
||||
}
|
||||
|
||||
public void addBoundsListener(BoundsListener listener) {
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public final class CertificateErrorParams extends Object {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public interface LoadHandler {
|
||||
boolean onCertificateError(CertificateErrorParams params);
|
||||
|
||||
boolean onLoad(LoadParams params);
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
package com.teamdev.jxbrowser.chromium;
|
||||
|
||||
public final class LoadParams extends Object {
|
||||
|
||||
}
|
||||
@@ -43,28 +43,28 @@ class Test {
|
||||
new Bogus().exec("Irrelevant version of exec");
|
||||
}
|
||||
|
||||
void apacheExecute1() {
|
||||
void apacheExecute1() throws IOException {
|
||||
String line = "AcroRd32.exe /p /h some.file";
|
||||
CommandLine cmdLine = CommandLine.parse(line);
|
||||
DefaultExecutor executor = new DefaultExecutor();
|
||||
int exitValue = executor.execute(cmdLine);
|
||||
}
|
||||
|
||||
void apacheExecute2() {
|
||||
void apacheExecute2() throws IOException {
|
||||
String line = "AcroRd32.exe /p /h some.file";
|
||||
CommandLine cmdLine = CommandLine.parse(line, null);
|
||||
DefaultExecutor executor = new DefaultExecutor();
|
||||
int exitValue = executor.execute(cmdLine);
|
||||
}
|
||||
|
||||
void apacheExecute3() {
|
||||
void apacheExecute3() throws IOException {
|
||||
CommandLine cmdLine = new CommandLine("AcroRd32.exe");
|
||||
cmdLine.addArguments("/p /h some.file");
|
||||
DefaultExecutor executor = new DefaultExecutor();
|
||||
int exitValue = executor.execute(cmdLine);
|
||||
}
|
||||
|
||||
void apacheExecute4() {
|
||||
void apacheExecute4() throws IOException {
|
||||
CommandLine cmdLine = new CommandLine("AcroRd32.exe");
|
||||
cmdLine.addArguments("/p /h some.file", false);
|
||||
DefaultExecutor executor = new DefaultExecutor();
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
class Test {
|
||||
public static void main(String[] args) {
|
||||
public static void main(String[] args) throws java.io.IOException {
|
||||
// Relative paths
|
||||
Runtime.getRuntime().exec("make");
|
||||
Runtime.getRuntime().exec("m");
|
||||
|
||||
@@ -88,8 +88,8 @@ public class CommentedCode {
|
||||
*   ;
|
||||
*   ;
|
||||
*/
|
||||
return -1;
|
||||
}
|
||||
|
||||
// public static int commentedOutMethod(){
|
||||
//
|
||||
// return 123;
|
||||
|
||||
@@ -32,7 +32,7 @@ public class A {
|
||||
case 0: return p;
|
||||
case 1: return s;
|
||||
case 2: return b1.getElem();
|
||||
case 3: return b2.getElem();
|
||||
default:return b2.getElem();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@@ -8,7 +8,7 @@ import java.util.List;
|
||||
import org.apache.commons.io.IOUtils;
|
||||
|
||||
class Test {
|
||||
public static void ioutils() {
|
||||
public static void ioutils() throws java.io.FileNotFoundException, java.io.IOException {
|
||||
InputStream inp = new FileInputStream("test"); // user input
|
||||
|
||||
InputStream buf = IOUtils.buffer(inp);
|
||||
|
||||
@@ -14,7 +14,7 @@ class Test {
|
||||
return "tainted";
|
||||
}
|
||||
|
||||
public static void jacksonObjectMapper() {
|
||||
public static void jacksonObjectMapper() throws java.io.FileNotFoundException, java.io.UnsupportedEncodingException {
|
||||
String s = taint();
|
||||
ObjectMapper om = new ObjectMapper();
|
||||
File file = new File("testFile");
|
||||
@@ -32,7 +32,7 @@ class Test {
|
||||
System.out.println(reconstructed);
|
||||
}
|
||||
|
||||
public static void jacksonObjectWriter() {
|
||||
public static void jacksonObjectWriter() throws java.io.FileNotFoundException, java.io.UnsupportedEncodingException {
|
||||
String s = taint();
|
||||
ObjectWriter ow = new ObjectWriter();
|
||||
File file = new File("testFile");
|
||||
|
||||
@@ -15,7 +15,7 @@ public class A {
|
||||
sink(b2);
|
||||
}
|
||||
|
||||
void test2() {
|
||||
void test2() throws IOException {
|
||||
ByteArrayOutputStream bOutput = new ByteArrayOutputStream();
|
||||
bOutput.write(taint());
|
||||
byte[] b = bOutput.toByteArray();
|
||||
@@ -25,11 +25,11 @@ public class A {
|
||||
sink(b2);
|
||||
}
|
||||
|
||||
void streamWrite(ByteArrayOutputStream baos, byte[] data) {
|
||||
void streamWrite(ByteArrayOutputStream baos, byte[] data) throws IOException {
|
||||
baos.write(data);
|
||||
}
|
||||
|
||||
void test3(ByteArrayOutputStream baos) {
|
||||
void test3(ByteArrayOutputStream baos) throws IOException {
|
||||
streamWrite(baos, taint());
|
||||
sink(baos.toByteArray());
|
||||
}
|
||||
@@ -38,11 +38,11 @@ public class A {
|
||||
ByteArrayOutputStream baos = new ByteArrayOutputStream();
|
||||
}
|
||||
|
||||
void streamWriteHolder(BaosHolder bh, byte[] data) {
|
||||
void streamWriteHolder(BaosHolder bh, byte[] data) throws IOException {
|
||||
bh.baos.write(data);
|
||||
}
|
||||
|
||||
void test4(BaosHolder bh) {
|
||||
void test4(BaosHolder bh) throws IOException {
|
||||
streamWriteHolder(bh, taint());
|
||||
sink(bh.baos.toByteArray());
|
||||
}
|
||||
@@ -51,7 +51,7 @@ public class A {
|
||||
byte[] data = new byte[10];
|
||||
}
|
||||
|
||||
void test5_a(DataHolder dh) {
|
||||
void test5_a(DataHolder dh) throws IOException {
|
||||
ByteArrayInputStream bais = new ByteArrayInputStream(taint());
|
||||
bais.read(dh.data);
|
||||
test5_b(dh);
|
||||
|
||||
@@ -11,7 +11,7 @@ public class B {
|
||||
|
||||
public static void sink(Object o) { }
|
||||
|
||||
public static void maintest() {
|
||||
public static void maintest() throws java.io.UnsupportedEncodingException, java.net.MalformedURLException {
|
||||
String[] args = taint();
|
||||
// tainted - access to main args
|
||||
String[] aaaargs = args;
|
||||
|
||||
@@ -4,21 +4,21 @@ import android.app.Activity;
|
||||
|
||||
public class IntentSources extends Activity {
|
||||
|
||||
public void test() {
|
||||
public void test() throws java.io.IOException {
|
||||
|
||||
String trouble = this.getIntent().getStringExtra("key");
|
||||
Runtime.getRuntime().exec(trouble);
|
||||
|
||||
}
|
||||
|
||||
public void test2() {
|
||||
public void test2() throws java.io.IOException {
|
||||
|
||||
String trouble = getIntent().getStringExtra("key");
|
||||
Runtime.getRuntime().exec(trouble);
|
||||
|
||||
}
|
||||
|
||||
public void test3() {
|
||||
public void test3() throws java.io.IOException {
|
||||
|
||||
String trouble = getIntent().getExtras().getString("key");
|
||||
Runtime.getRuntime().exec(trouble);
|
||||
@@ -29,9 +29,9 @@ public class IntentSources extends Activity {
|
||||
|
||||
class OtherClass {
|
||||
|
||||
public void test(IntentSources is) {
|
||||
public void test(IntentSources is) throws java.io.IOException {
|
||||
String trouble = is.getIntent().getStringExtra("key");
|
||||
Runtime.getRuntime().exec(trouble);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,5 +4,5 @@ import java.rmi.Remote;
|
||||
import java.rmi.RemoteException;
|
||||
|
||||
public interface RmiFlow extends Remote {
|
||||
String listDirectory(String path);
|
||||
String listDirectory(String path) throws java.io.IOException;
|
||||
}
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
package security.library.dataflow;
|
||||
|
||||
public class RmiFlowImpl implements RmiFlow {
|
||||
public String listDirectory(String path) {
|
||||
public String listDirectory(String path) throws java.io.IOException {
|
||||
String command = "ls " + path;
|
||||
Runtime.getRuntime().exec(command);
|
||||
return "pretend there are some results here";
|
||||
}
|
||||
|
||||
public String notRemotable(String path) {
|
||||
public String notRemotable(String path) throws java.io.IOException {
|
||||
String command = "ls " + path;
|
||||
Runtime.getRuntime().exec(command);
|
||||
return "pretend there are some results here";
|
||||
|
||||
@@ -5,21 +5,21 @@
|
||||
| A.java:41:5:41:53 | getInputStream(...) | A.java:41:5:41:53 | getInputStream(...) |
|
||||
| A.java:42:5:42:45 | getInputStream(...) | A.java:42:5:42:45 | getInputStream(...) |
|
||||
| A.java:43:5:43:47 | getHostName(...) | A.java:43:5:43:47 | getHostName(...) |
|
||||
| IntentSources.java:9:20:9:35 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1057:19:1057:32 | parameter this |
|
||||
| IntentSources.java:9:20:9:35 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1059:19:1059:32 | parameter this |
|
||||
| IntentSources.java:9:20:9:35 | getIntent(...) | IntentSources.java:9:20:9:35 | getIntent(...) |
|
||||
| IntentSources.java:9:20:9:35 | getIntent(...) | IntentSources.java:9:20:9:57 | getStringExtra(...) |
|
||||
| IntentSources.java:9:20:9:35 | getIntent(...) | IntentSources.java:10:29:10:35 | trouble |
|
||||
| IntentSources.java:16:20:16:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1057:19:1057:32 | parameter this |
|
||||
| IntentSources.java:16:20:16:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1059:19:1059:32 | parameter this |
|
||||
| IntentSources.java:16:20:16:30 | getIntent(...) | IntentSources.java:16:20:16:30 | getIntent(...) |
|
||||
| IntentSources.java:16:20:16:30 | getIntent(...) | IntentSources.java:16:20:16:52 | getStringExtra(...) |
|
||||
| IntentSources.java:16:20:16:30 | getIntent(...) | IntentSources.java:17:29:17:35 | trouble |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1356:19:1356:27 | parameter this |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/os/BaseBundle.java:599:19:599:27 | parameter this |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1358:19:1358:27 | parameter this |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/os/BaseBundle.java:600:19:600:27 | parameter this |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | IntentSources.java:23:20:23:30 | getIntent(...) |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | IntentSources.java:23:20:23:42 | getExtras(...) |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | IntentSources.java:23:20:23:59 | getString(...) |
|
||||
| IntentSources.java:23:20:23:30 | getIntent(...) | IntentSources.java:24:29:24:35 | trouble |
|
||||
| IntentSources.java:33:20:33:33 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1057:19:1057:32 | parameter this |
|
||||
| IntentSources.java:33:20:33:33 | getIntent(...) | ../../../stubs/google-android-9.0.0/android/content/Intent.java:1059:19:1059:32 | parameter this |
|
||||
| IntentSources.java:33:20:33:33 | getIntent(...) | IntentSources.java:33:20:33:33 | getIntent(...) |
|
||||
| IntentSources.java:33:20:33:33 | getIntent(...) | IntentSources.java:33:20:33:55 | getStringExtra(...) |
|
||||
| IntentSources.java:33:20:33:33 | getIntent(...) | IntentSources.java:34:29:34:35 | trouble |
|
||||
|
||||
@@ -36,7 +36,7 @@ class ViableCallable {
|
||||
i2.f("", 0l);
|
||||
}
|
||||
|
||||
<TMock> TMock Mock() { throw new Exception(); }
|
||||
<TMock> TMock Mock() { throw new Error(); }
|
||||
|
||||
void CreateTypeInstance() {
|
||||
Run(new C2<Boolean>(), null, null, null);
|
||||
@@ -63,7 +63,7 @@ abstract class C1<T1_C1, T2_C1> {
|
||||
M(x, 8);
|
||||
}
|
||||
|
||||
public void f(T1_C1 x, T2_C1 y) { throw new Exception(); }
|
||||
public void f(T1_C1 x, T2_C1 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
interface I1<T_I1> {
|
||||
@@ -80,27 +80,27 @@ interface I2<T_I2> {
|
||||
|
||||
class C2<T_C2> extends C1<String, T_C2> implements I1<T_C2> {
|
||||
@Override
|
||||
public <T3_C2> T_C2 M(String x, T3_C2 y) { throw new Exception(); }
|
||||
public <T3_C2> T_C2 M(String x, T3_C2 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
class C3 extends C1<String, Long> implements I2<Long> {
|
||||
@Override
|
||||
public <T3_C3> Long M(String x, T3_C3 y) { throw new Exception(); }
|
||||
public <T3_C3> Long M(String x, T3_C3 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
class C4<T_C4> extends C1<T_C4[], Boolean> {
|
||||
@Override
|
||||
public <T3_C4> Boolean M(T_C4[] x, T3_C4 y) { throw new Exception(); }
|
||||
public <T3_C4> Boolean M(T_C4[] x, T3_C4 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
class C5 extends C1<String, Boolean> {
|
||||
@Override
|
||||
public <T3_C5> Boolean M(String x, T3_C5 y) { throw new Exception(); }
|
||||
public <T3_C5> Boolean M(String x, T3_C5 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
class C6<T1_C6, T2_C6> extends C1<T1_C6, T2_C6> {
|
||||
@Override
|
||||
public <T3_C6> T2_C6 M(T1_C6 x, T3_C6 y) { throw new Exception(); }
|
||||
public <T3_C6> T2_C6 M(T1_C6 x, T3_C6 y) { throw new Error(); }
|
||||
|
||||
public void Run(T1_C6 x) {
|
||||
// Viable callables: C6.M(), C7.M()
|
||||
@@ -113,7 +113,7 @@ class C6<T1_C6, T2_C6> extends C1<T1_C6, T2_C6> {
|
||||
|
||||
class C7<T1_C7> extends C6<T1_C7, Byte> {
|
||||
@Override
|
||||
public <T3_C7> Byte M(T1_C7 x, T3_C7 y) { throw new Exception(); }
|
||||
public <T3_C7> Byte M(T1_C7 x, T3_C7 y) { throw new Error(); }
|
||||
|
||||
public void Run(T1_C7 x) {
|
||||
// Viable callables: C7.M()
|
||||
@@ -129,11 +129,11 @@ class C7<T1_C7> extends C6<T1_C7, Byte> {
|
||||
|
||||
class C8<T_C8, T2_C8> extends C1<String, T2_C8> {
|
||||
@Override
|
||||
public <T3_C8> T2_C8 M(String x, T3_C8 y) { throw new Exception(); }
|
||||
public <T3_C8> T2_C8 M(String x, T3_C8 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
class C9<T_C9> extends C8<Boolean, Boolean> {
|
||||
@Override
|
||||
public <T3_C9> Boolean M(String x, T3_C9 y) { throw new Exception(); }
|
||||
public <T3_C9> Boolean M(String x, T3_C9 y) { throw new Error(); }
|
||||
}
|
||||
|
||||
|
||||
@@ -20,10 +20,10 @@ class ViableCallable2 {
|
||||
}
|
||||
|
||||
class A {
|
||||
public void m() { throw new Exception(); }
|
||||
public void m() { throw new Error(); }
|
||||
}
|
||||
|
||||
class B extends A {
|
||||
@Override
|
||||
public void m() { throw new Exception(); }
|
||||
public void m() { throw new Error(); }
|
||||
}
|
||||
|
||||
@@ -0,0 +1,278 @@
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import java.nio.charset.Charset;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
|
||||
class Test {
|
||||
String taint() { return "tainted"; }
|
||||
|
||||
void sink(Object o) {}
|
||||
|
||||
void test() throws Exception {
|
||||
|
||||
// All these calls should convey taint to `sink` except as noted.
|
||||
sink(StringUtils.abbreviate(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviate(taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviate(taint(), "...", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviate("Untainted", taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviate(taint(), "...", 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviate("Untainted", taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviateMiddle(taint(), "...", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.abbreviateMiddle("Untainted", taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.appendIfMissing(taint(), "suffix", "candsuffix1", "candsuffix2")); // $hasTaintFlow=y
|
||||
sink(StringUtils.appendIfMissing("prefix", taint(), "candsuffix1", "candsuffix2")); // $hasTaintFlow=y
|
||||
// (next 2 calls) GOOD: candidate suffixes do not flow to the return value.
|
||||
sink(StringUtils.appendIfMissing("prefix", "suffix", taint(), "candsuffix2"));
|
||||
sink(StringUtils.appendIfMissing("prefix", "suffix", "candsuffix1", taint()));
|
||||
sink(StringUtils.appendIfMissingIgnoreCase(taint(), "suffix", "candsuffix1", "candsuffix2")); // $hasTaintFlow=y
|
||||
sink(StringUtils.appendIfMissingIgnoreCase("prefix", taint(), "candsuffix1", "candsuffix2")); // $hasTaintFlow=y
|
||||
// (next 2 calls) GOOD: candidate suffixes do not flow to the return value.
|
||||
sink(StringUtils.appendIfMissingIgnoreCase("prefix", "suffix", taint(), "candsuffix2"));
|
||||
sink(StringUtils.appendIfMissingIgnoreCase("prefix", "suffix", "candsuffix1", taint()));
|
||||
sink(StringUtils.capitalize(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.center(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.center(taint(), 0, 'x')); // $hasTaintFlow=y
|
||||
sink(StringUtils.center(taint(), 0, "padding string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.center("Center me", 0, taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.chomp(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.chomp(taint(), "separator")); // $hasTaintFlow=y
|
||||
// GOOD: separator does not flow to the return value.
|
||||
sink(StringUtils.chomp("Chomp me", taint()));
|
||||
sink(StringUtils.chop(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultIfBlank(taint(), "default")); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultIfBlank("Perhaps blank", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultIfEmpty(taint(), "default")); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultIfEmpty("Perhaps empty", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultString(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultString(taint(), "default string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.defaultString("perhaps null", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.deleteWhitespace(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.difference(taint(), "rhs")); // $hasTaintFlow=y
|
||||
sink(StringUtils.difference("lhs", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.firstNonBlank(taint(), "second string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.firstNonBlank("first string", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.firstNonEmpty(taint(), "second string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.firstNonEmpty("first string", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.getBytes(taint(), (Charset)null)); // $hasTaintFlow=y
|
||||
sink(StringUtils.getBytes(taint(), "some charset")); // $hasTaintFlow=y
|
||||
// GOOD: charset names are not a source of taint
|
||||
sink(StringUtils.getBytes("some string", taint()));
|
||||
sink(StringUtils.getCommonPrefix(taint(), "second string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.getCommonPrefix("first string", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.getDigits(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.getIfBlank(taint(), () -> "default")); // $hasTaintFlow=y
|
||||
sink(StringUtils.getIfEmpty(taint(), () -> "default")); // $hasTaintFlow=y
|
||||
// BAD (but not detected yet): latent taint in lambdas
|
||||
sink(StringUtils.getIfBlank("maybe blank", () -> taint()));
|
||||
sink(StringUtils.getIfEmpty("maybe blank", () -> taint()));
|
||||
// GOOD: byte arrays render as numbers, so can't usefully convey most forms
|
||||
// of tainted data.
|
||||
sink(StringUtils.join(StringUtils.getBytes(taint(), "UTF-8"), ' '));
|
||||
sink(StringUtils.join(StringUtils.getBytes(taint(), "UTF-8"), ' ', 0, 0));
|
||||
sink(StringUtils.join(taint().toCharArray(), ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taint().toCharArray(), ' ', 0, 0)); // $hasTaintFlow=y
|
||||
// Testing the Iterable<?> overloads of `join`
|
||||
List<String> taintedList = new ArrayList<>();
|
||||
taintedList.add(taint());
|
||||
sink(StringUtils.join(taintedList, ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedList, "sep")); // $hasTaintFlow=y
|
||||
List<String> untaintedList = new ArrayList<>();
|
||||
sink(StringUtils.join(untaintedList, taint())); // $hasTaintFlow=y
|
||||
// Testing the Iterator<?> overloads of `join`
|
||||
sink(StringUtils.join(taintedList.iterator(), ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedList.iterator(), "sep")); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(untaintedList.iterator(), taint())); // $hasTaintFlow=y
|
||||
// Testing the List<?> overloads of `join`, which have start/end indices
|
||||
sink(StringUtils.join(taintedList, ' ', 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedList, "sep", 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(untaintedList, taint(), 0, 0)); // $hasTaintFlow=y
|
||||
// Testing the Object[] overloads of `join`, which may have start/end indices
|
||||
Object[] taintedArray = new Object[] { taint() };
|
||||
sink(StringUtils.join(taintedArray, ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedArray, "sep")); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedArray, ' ', 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(taintedArray, "sep", 0, 0)); // $hasTaintFlow=y
|
||||
Object[] untaintedArray = new Object[] { "safe" };
|
||||
sink(StringUtils.join(untaintedArray, taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.join(untaintedArray, taint(), 0, 0)); // $hasTaintFlow=y
|
||||
// Testing the variadic overload of `join` and `joinWith`
|
||||
sink(StringUtils.join(taint(), "other string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.join("other string before", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.joinWith("separator", taint(), "other string")); // $hasTaintFlow=y
|
||||
sink(StringUtils.joinWith("separator", "other string before", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.joinWith(taint(), "other string before", "other string after")); // $hasTaintFlow=y
|
||||
// End of `join` tests
|
||||
sink(StringUtils.left(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.leftPad(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.leftPad(taint(), 0, ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.leftPad(taint(), 0, "padding")); // $hasTaintFlow=y
|
||||
sink(StringUtils.leftPad("to pad", 0, taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.lowerCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.lowerCase(taint(), Locale.UK)); // $hasTaintFlow=y
|
||||
sink(StringUtils.mid(taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.normalizeSpace(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.overlay(taint(), "overlay", 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.overlay("underlay", taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.prependIfMissing(taint(), "append prefix", "check prefix 1", "check prefix 2")); // $hasTaintFlow=y
|
||||
sink(StringUtils.prependIfMissing("original string", taint(), "check prefix 1", "check prefix 2")); // $hasTaintFlow=y
|
||||
// (next 2 calls) GOOD: args 3+ are checked against but do not propagate to the return value
|
||||
sink(StringUtils.prependIfMissing("original string", "append prefix", taint(), "check prefix 2"));
|
||||
sink(StringUtils.prependIfMissing("original string", "append prefix", "check prefix 1", taint()));
|
||||
sink(StringUtils.prependIfMissingIgnoreCase(taint(), "append prefix", "check prefix 1", "check prefix 2")); // $hasTaintFlow=y
|
||||
sink(StringUtils.prependIfMissingIgnoreCase("original string", taint(), "check prefix 1", "check prefix 2")); // $hasTaintFlow=y
|
||||
// (next 2 calls) GOOD: args 3+ are checked against but do not propagate to the return value
|
||||
sink(StringUtils.prependIfMissingIgnoreCase("original string", "append prefix", taint(), "check prefix 2"));
|
||||
sink(StringUtils.prependIfMissingIgnoreCase("original string", "append prefix", "check prefix 1", taint()));
|
||||
sink(StringUtils.remove(taint(), ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.remove(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeAll(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeEnd(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeEndIgnoreCase(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeFirst(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeIgnoreCase(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removePattern(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeStart(taint(), "delete me")); // $hasTaintFlow=y
|
||||
sink(StringUtils.removeStartIgnoreCase(taint(), "delete me")); // $hasTaintFlow=y
|
||||
// GOOD (next 9 calls): the removed string doesn't propagate to the return value
|
||||
sink(StringUtils.remove("remove from", taint()));
|
||||
sink(StringUtils.removeAll("remove from", taint()));
|
||||
sink(StringUtils.removeEnd("remove from", taint()));
|
||||
sink(StringUtils.removeEndIgnoreCase("remove from", taint()));
|
||||
sink(StringUtils.removeFirst("remove from", taint()));
|
||||
sink(StringUtils.removeIgnoreCase("remove from", taint()));
|
||||
sink(StringUtils.removePattern("remove from", taint()));
|
||||
sink(StringUtils.removeStart("remove from", taint()));
|
||||
sink(StringUtils.removeStartIgnoreCase("remove from", taint()));
|
||||
sink(StringUtils.repeat(taint(), 1)); // $hasTaintFlow=y
|
||||
sink(StringUtils.repeat(taint(), "separator", 1)); // $hasTaintFlow=y
|
||||
sink(StringUtils.repeat("repeat me", taint(), 1)); // $hasTaintFlow=y
|
||||
sink(StringUtils.replace(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replace("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replace(taint(), "search", "replacement", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.replace("haystack", "search", taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceAll(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceAll("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceChars(taint(), 'a', 'b')); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceChars(taint(), "abc", "xyz")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceChars("haystack", "abc", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceEach(taint(), new String[] { "search" }, new String[] { "replacement" })); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceEach("haystack", new String[] { "search" }, new String[] { taint() })); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceEachRepeatedly(taint(), new String[] { "search" }, new String[] { "replacement" })); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceEachRepeatedly("haystack", new String[] { "search" }, new String[] { taint() })); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceFirst(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceFirst("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceIgnoreCase(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceIgnoreCase("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceOnce(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceOnce("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceOnceIgnoreCase(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replaceOnceIgnoreCase("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.replacePattern(taint(), "search", "replacement")); // $hasTaintFlow=y
|
||||
sink(StringUtils.replacePattern("haystack", "search", taint())); // $hasTaintFlow=y
|
||||
// GOOD (next 11 calls): searched string in replace methods does not flow to the return value.
|
||||
sink(StringUtils.replace("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replace("haystack", taint(), "replacement", 0));
|
||||
sink(StringUtils.replaceAll("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replaceChars("haystack", taint(), "xyz"));
|
||||
sink(StringUtils.replaceEach("haystack", new String[] { taint() }, new String[] { "replacement" }));
|
||||
sink(StringUtils.replaceEachRepeatedly("haystack", new String[] { taint() }, new String[] { "replacement" }));
|
||||
sink(StringUtils.replaceFirst("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replaceIgnoreCase("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replaceOnce("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replaceOnceIgnoreCase("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.replacePattern("haystack", taint(), "replacement"));
|
||||
sink(StringUtils.reverse(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.reverseDelimited(taint(), ',')); // $hasTaintFlow=y
|
||||
sink(StringUtils.right(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.rightPad(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.rightPad(taint(), 0, ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.rightPad(taint(), 0, "padding")); // $hasTaintFlow=y
|
||||
sink(StringUtils.rightPad("to pad", 0, taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.rotate(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.split(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.split(taint(), ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.split(taint(), " ,; // $hasTaintFlow=y")); // $hasTaintFlow=y
|
||||
sink(StringUtils.split(taint(), " ,; // $hasTaintFlow=y", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByCharacterType(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByCharacterTypeCamelCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByWholeSeparator(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByWholeSeparator(taint(), "separator", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByWholeSeparatorPreserveAllTokens(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitByWholeSeparatorPreserveAllTokens(taint(), "separator", 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitPreserveAllTokens(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitPreserveAllTokens(taint(), ' ')); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitPreserveAllTokens(taint(), " ,;")); // $hasTaintFlow=y
|
||||
sink(StringUtils.splitPreserveAllTokens(taint(), " ,;", 0)); // $hasTaintFlow=y
|
||||
// GOOD (next 8 calls): separators don't propagate to the return value
|
||||
sink(StringUtils.split("to split", taint()));
|
||||
sink(StringUtils.split("to split", taint(), 0));
|
||||
sink(StringUtils.splitPreserveAllTokens("to split", taint(), 0));
|
||||
sink(StringUtils.splitByWholeSeparator("to split", taint()));
|
||||
sink(StringUtils.splitByWholeSeparator("to split", taint(), 0));
|
||||
sink(StringUtils.splitByWholeSeparatorPreserveAllTokens("to split", taint()));
|
||||
sink(StringUtils.splitByWholeSeparatorPreserveAllTokens("to split", taint(), 0));
|
||||
sink(StringUtils.splitPreserveAllTokens("to split", taint()));
|
||||
sink(StringUtils.strip(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.strip(taint(), "charstoremove")); // $hasTaintFlow=y
|
||||
sink(StringUtils.stripAccents(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.stripAll(new String[] { taint() }, "charstoremove")); // $hasTaintFlow=y
|
||||
sink(StringUtils.stripEnd(taint(), "charstoremove")); // $hasTaintFlow=y
|
||||
sink(StringUtils.stripStart(taint(), "charstoremove")); // $hasTaintFlow=y
|
||||
// GOOD (next 4 calls): stripped chars do not flow to the return value.
|
||||
sink(StringUtils.strip("original text", taint()));
|
||||
sink(StringUtils.stripAll(new String[] { "original text" }, taint()));
|
||||
sink(StringUtils.stripEnd("original text", taint()));
|
||||
sink(StringUtils.stripStart("original text", taint()));
|
||||
sink(StringUtils.stripToEmpty(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.stripToNull(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.substring(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.substring(taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringAfter(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringAfter(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringAfterLast(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringAfterLast(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringBefore(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringBeforeLast(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringBetween(taint(), "separator")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringBetween(taint(), "start-tag", "end-tag")); // $hasTaintFlow=y
|
||||
sink(StringUtils.substringsBetween(taint(), "start-tag", "end-tag")[0]); // $hasTaintFlow=y
|
||||
// GOOD (next 9 calls): separators and bounding tags do not flow to the return value.
|
||||
sink(StringUtils.substringAfter("original text", taint()));
|
||||
sink(StringUtils.substringAfterLast("original text", taint()));
|
||||
sink(StringUtils.substringBefore("original text", taint()));
|
||||
sink(StringUtils.substringBeforeLast("original text", taint()));
|
||||
sink(StringUtils.substringBetween("original text", taint()));
|
||||
sink(StringUtils.substringBetween("original text", taint(), "end-tag"));
|
||||
sink(StringUtils.substringBetween("original text", "start-tag", taint()));
|
||||
sink(StringUtils.substringsBetween("original text", taint(), "end-tag")[0]);
|
||||
sink(StringUtils.substringsBetween("original text", "start-tag", taint())[0]);
|
||||
sink(StringUtils.swapCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.toCodePoints(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.toEncodedString(StringUtils.getBytes(taint(), "charset"), null)); // $hasTaintFlow=y
|
||||
sink(StringUtils.toRootLowerCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.toRootUpperCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.toString(StringUtils.getBytes(taint(), "charset"), "charset")); // $hasTaintFlow=y
|
||||
sink(StringUtils.trim(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.trimToEmpty(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.trimToNull(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.truncate(taint(), 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.truncate(taint(), 0, 0)); // $hasTaintFlow=y
|
||||
sink(StringUtils.uncapitalize(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.unwrap(taint(), '"')); // $hasTaintFlow=y
|
||||
sink(StringUtils.unwrap(taint(), "separator")); // $hasTaintFlow=y
|
||||
// GOOD: the wrapper string does not flow to the return value.
|
||||
sink(StringUtils.unwrap("original string", taint()));
|
||||
sink(StringUtils.upperCase(taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.upperCase(taint(), null)); // $hasTaintFlow=y
|
||||
sink(StringUtils.valueOf(taint().toCharArray())); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrap(taint(), '"')); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrap(taint(), "wrapper token")); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrap("wrap me", taint())); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrapIfMissing(taint(), '"')); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrapIfMissing(taint(), "wrapper token")); // $hasTaintFlow=y
|
||||
sink(StringUtils.wrapIfMissing("wrap me", taint())); // $hasTaintFlow=y
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
import java
|
||||
import semmle.code.java.dataflow.TaintTracking
|
||||
import TestUtilities.InlineExpectationsTest
|
||||
|
||||
class Conf extends TaintTracking::Configuration {
|
||||
Conf() { this = "qltest:frameworks:apache-commons-lang3" }
|
||||
|
||||
override predicate isSource(DataFlow::Node n) {
|
||||
n.asExpr().(MethodAccess).getMethod().hasName("taint")
|
||||
}
|
||||
|
||||
override predicate isSink(DataFlow::Node n) {
|
||||
exists(MethodAccess ma | ma.getMethod().hasName("sink") | n.asExpr() = ma.getAnArgument())
|
||||
}
|
||||
}
|
||||
|
||||
class HasFlowTest extends InlineExpectationsTest {
|
||||
HasFlowTest() { this = "HasFlowTest" }
|
||||
|
||||
override string getARelevantTag() { result = "hasTaintFlow" }
|
||||
|
||||
override predicate hasActualResult(Location location, string element, string tag, string value) {
|
||||
tag = "hasTaintFlow" and
|
||||
exists(DataFlow::Node src, DataFlow::Node sink, Conf conf | conf.hasFlow(src, sink) |
|
||||
sink.getLocation() = location and
|
||||
element = sink.toString() and
|
||||
value = "y"
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
//semmle-extractor-options: --javac-args -cp ${testdir}/../../../stubs/apache-commons-lang3-3.7
|
||||
122
java/ql/test/library-tests/frameworks/guava/TestCollect.java
Normal file
122
java/ql/test/library-tests/frameworks/guava/TestCollect.java
Normal file
@@ -0,0 +1,122 @@
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.SortedSet;
|
||||
import java.util.SortedMap;
|
||||
import java.util.Comparator;
|
||||
|
||||
class TestCollect {
|
||||
String taint() { return "tainted"; }
|
||||
|
||||
void sink(Object o) {}
|
||||
|
||||
void test1() {
|
||||
String x = taint();
|
||||
|
||||
ImmutableSet<String> xs = ImmutableSet.of(x, "y", "z");
|
||||
sink(xs.asList());
|
||||
|
||||
ImmutableSet<String> ys = ImmutableSet.of("a", "b", "c");
|
||||
|
||||
sink(Sets.filter(Sets.union(xs, ys), y -> true));
|
||||
|
||||
sink(Sets.newHashSet("a", "b", "c", "d", x));
|
||||
}
|
||||
|
||||
void test2() {
|
||||
sink(ImmutableList.of(taint(), taint(), taint(), taint())); // expect 4 alerts
|
||||
sink(ImmutableMap.of(taint(), taint(), taint(), taint())); // expect 2 alerts
|
||||
sink(ImmutableMultimap.of(taint(), taint(), taint(), taint())); // expect 2 alerts
|
||||
sink(ImmutableTable.of(taint(),taint(), taint())); // expect 1 alert
|
||||
}
|
||||
|
||||
void test3() {
|
||||
String x = taint();
|
||||
|
||||
ImmutableList.Builder<String> b = ImmutableList.builder();
|
||||
|
||||
b.add("a");
|
||||
sink(b);
|
||||
b.add(x);
|
||||
sink(b.build());
|
||||
|
||||
b = ImmutableList.builder();
|
||||
|
||||
b.add("a").add(x);
|
||||
sink(b.build());
|
||||
|
||||
sink(ImmutableList.builder().add("a").add(x).build());
|
||||
|
||||
ImmutableMap.Builder<String, String> b2 = ImmutableMap.builder();
|
||||
b2.put(x,"v");
|
||||
sink(b2);
|
||||
b2.put("k",x);
|
||||
sink(b2.build());
|
||||
}
|
||||
|
||||
void test4(Table<String, String, String> t1, Table<String, String, String> t2, Table<String, String, String> t3) {
|
||||
String x = taint();
|
||||
t1.put(x, "c", "v");
|
||||
sink(t1);
|
||||
t1.put("r", x, "v");
|
||||
sink(t1);
|
||||
t1.put("r", "c", x);
|
||||
sink(t1);
|
||||
sink(t1.row("r"));
|
||||
|
||||
t2.putAll(t1);
|
||||
for (Table.Cell<String,String,String> c : t2.cellSet()) {
|
||||
sink(c.getValue());
|
||||
}
|
||||
|
||||
sink(t1.remove("r", "c"));
|
||||
|
||||
t3.row("r").put("c", x);
|
||||
sink(t3); // Not detected
|
||||
}
|
||||
|
||||
void test4(Multimap<String, String> m1, Multimap<String, String> m2, Multimap<String, String> m3,
|
||||
Multimap<String, String> m4, Multimap<String, String> m5){
|
||||
String x = taint();
|
||||
m1.put("k", x);
|
||||
sink(m1);
|
||||
sink(m1.get("k"));
|
||||
|
||||
m2.putAll("k", ImmutableList.of("a", x, "b"));
|
||||
sink(m2);
|
||||
|
||||
m3.putAll(m1);
|
||||
sink(m3);
|
||||
|
||||
m4.replaceValues("k", m1.replaceValues("k", ImmutableList.of("a")));
|
||||
for (Map.Entry<String, String> e : m4.entries()) {
|
||||
sink(e.getValue());
|
||||
}
|
||||
|
||||
m5.asMap().get("k").add(x);
|
||||
sink(m5); // Not detected
|
||||
}
|
||||
|
||||
void test5(Comparator<String> comp, SortedSet<String> sorS, SortedMap<String, String> sorM) {
|
||||
ImmutableSortedSet<String> s = ImmutableSortedSet.of(taint());
|
||||
|
||||
sink(s);
|
||||
sink(ImmutableSortedSet.copyOf(s));
|
||||
sink(ImmutableSortedSet.copyOf(comp, s));
|
||||
|
||||
sorS.add(taint());
|
||||
sink(ImmutableSortedSet.copyOfSorted(sorS));
|
||||
|
||||
sink(ImmutableList.sortedCopyOf(s));
|
||||
sink(ImmutableList.sortedCopyOf(comp, s));
|
||||
|
||||
ImmutableSortedMap<String, String> m = ImmutableSortedMap.of("k", taint());
|
||||
|
||||
sink(m);
|
||||
sink(ImmutableSortedMap.copyOf(m));
|
||||
sink(ImmutableSortedMap.copyOf(m, comp));
|
||||
|
||||
sorM.put("k", taint());
|
||||
sink(ImmutableSortedMap.copyOfSorted(sorM));
|
||||
}
|
||||
}
|
||||
@@ -6,7 +6,7 @@ import com.google.common.base.Joiner;
|
||||
import java.util.Map;
|
||||
import java.util.HashMap;
|
||||
|
||||
class Test {
|
||||
class TestStrings {
|
||||
String taint() { return "tainted"; }
|
||||
|
||||
void sink(Object o) {}
|
||||
@@ -1,17 +1,52 @@
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:17:14:17:41 | padStart(...) |
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:18:14:18:39 | padEnd(...) |
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:19:14:19:33 | repeat(...) |
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:20:14:20:56 | emptyToNull(...) |
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:21:14:21:40 | lenientFormat(...) |
|
||||
| Test.java:15:20:15:26 | taint(...) | Test.java:24:14:24:51 | lenientFormat(...) |
|
||||
| Test.java:28:20:28:26 | taint(...) | Test.java:32:14:32:23 | split(...) |
|
||||
| Test.java:28:20:28:26 | taint(...) | Test.java:33:14:33:29 | splitToList(...) |
|
||||
| Test.java:28:20:28:26 | taint(...) | Test.java:35:14:35:50 | split(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:46:14:46:54 | appendTo(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:47:14:47:26 | toString(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:48:14:48:51 | appendTo(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:49:14:49:26 | toString(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:52:14:52:42 | appendTo(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:57:14:57:56 | join(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:58:14:58:82 | join(...) |
|
||||
| Test.java:39:20:39:26 | taint(...) | Test.java:60:14:60:58 | join(...) |
|
||||
| TestCollect.java:14:20:14:26 | taint(...) | TestCollect.java:17:14:17:24 | asList(...) |
|
||||
| TestCollect.java:14:20:14:26 | taint(...) | TestCollect.java:21:14:21:55 | filter(...) |
|
||||
| TestCollect.java:14:20:14:26 | taint(...) | TestCollect.java:23:14:23:51 | newHashSet(...) |
|
||||
| TestCollect.java:27:31:27:37 | taint(...) | TestCollect.java:27:14:27:65 | of(...) |
|
||||
| TestCollect.java:27:40:27:46 | taint(...) | TestCollect.java:27:14:27:65 | of(...) |
|
||||
| TestCollect.java:27:49:27:55 | taint(...) | TestCollect.java:27:14:27:65 | of(...) |
|
||||
| TestCollect.java:27:58:27:64 | taint(...) | TestCollect.java:27:14:27:65 | of(...) |
|
||||
| TestCollect.java:28:39:28:45 | taint(...) | TestCollect.java:28:14:28:64 | of(...) |
|
||||
| TestCollect.java:28:57:28:63 | taint(...) | TestCollect.java:28:14:28:64 | of(...) |
|
||||
| TestCollect.java:29:44:29:50 | taint(...) | TestCollect.java:29:14:29:69 | of(...) |
|
||||
| TestCollect.java:29:62:29:68 | taint(...) | TestCollect.java:29:14:29:69 | of(...) |
|
||||
| TestCollect.java:30:49:30:55 | taint(...) | TestCollect.java:30:14:30:56 | of(...) |
|
||||
| TestCollect.java:34:20:34:26 | taint(...) | TestCollect.java:41:14:41:22 | build(...) |
|
||||
| TestCollect.java:34:20:34:26 | taint(...) | TestCollect.java:46:14:46:22 | build(...) |
|
||||
| TestCollect.java:34:20:34:26 | taint(...) | TestCollect.java:48:14:48:60 | build(...) |
|
||||
| TestCollect.java:34:20:34:26 | taint(...) | TestCollect.java:54:14:54:23 | build(...) |
|
||||
| TestCollect.java:58:20:58:26 | taint(...) | TestCollect.java:64:14:64:15 | t1 |
|
||||
| TestCollect.java:58:20:58:26 | taint(...) | TestCollect.java:65:14:65:24 | row(...) |
|
||||
| TestCollect.java:58:20:58:26 | taint(...) | TestCollect.java:69:18:69:29 | getValue(...) |
|
||||
| TestCollect.java:58:20:58:26 | taint(...) | TestCollect.java:72:14:72:32 | remove(...) |
|
||||
| TestCollect.java:80:20:80:26 | taint(...) | TestCollect.java:82:14:82:15 | m1 |
|
||||
| TestCollect.java:80:20:80:26 | taint(...) | TestCollect.java:83:14:83:24 | get(...) |
|
||||
| TestCollect.java:80:20:80:26 | taint(...) | TestCollect.java:86:14:86:15 | m2 |
|
||||
| TestCollect.java:80:20:80:26 | taint(...) | TestCollect.java:89:14:89:15 | m3 |
|
||||
| TestCollect.java:80:20:80:26 | taint(...) | TestCollect.java:93:18:93:29 | getValue(...) |
|
||||
| TestCollect.java:101:62:101:68 | taint(...) | TestCollect.java:103:14:103:14 | s |
|
||||
| TestCollect.java:101:62:101:68 | taint(...) | TestCollect.java:104:14:104:41 | copyOf(...) |
|
||||
| TestCollect.java:101:62:101:68 | taint(...) | TestCollect.java:105:14:105:47 | copyOf(...) |
|
||||
| TestCollect.java:101:62:101:68 | taint(...) | TestCollect.java:110:14:110:42 | sortedCopyOf(...) |
|
||||
| TestCollect.java:101:62:101:68 | taint(...) | TestCollect.java:111:14:111:48 | sortedCopyOf(...) |
|
||||
| TestCollect.java:107:18:107:24 | taint(...) | TestCollect.java:108:14:108:50 | copyOfSorted(...) |
|
||||
| TestCollect.java:113:75:113:81 | taint(...) | TestCollect.java:115:14:115:14 | m |
|
||||
| TestCollect.java:113:75:113:81 | taint(...) | TestCollect.java:116:14:116:41 | copyOf(...) |
|
||||
| TestCollect.java:113:75:113:81 | taint(...) | TestCollect.java:117:14:117:47 | copyOf(...) |
|
||||
| TestCollect.java:119:23:119:29 | taint(...) | TestCollect.java:120:14:120:50 | copyOfSorted(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:17:14:17:41 | padStart(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:18:14:18:39 | padEnd(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:19:14:19:33 | repeat(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:20:14:20:56 | emptyToNull(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:21:14:21:40 | lenientFormat(...) |
|
||||
| TestStrings.java:15:20:15:26 | taint(...) | TestStrings.java:24:14:24:51 | lenientFormat(...) |
|
||||
| TestStrings.java:28:20:28:26 | taint(...) | TestStrings.java:32:14:32:23 | split(...) |
|
||||
| TestStrings.java:28:20:28:26 | taint(...) | TestStrings.java:33:14:33:29 | splitToList(...) |
|
||||
| TestStrings.java:28:20:28:26 | taint(...) | TestStrings.java:35:14:35:50 | split(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:46:14:46:54 | appendTo(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:47:14:47:26 | toString(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:48:14:48:51 | appendTo(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:49:14:49:26 | toString(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:52:14:52:42 | appendTo(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:57:14:57:56 | join(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:58:14:58:82 | join(...) |
|
||||
| TestStrings.java:39:20:39:26 | taint(...) | TestStrings.java:60:14:60:58 | join(...) |
|
||||
|
||||
@@ -41,7 +41,7 @@ public class Logic {
|
||||
}
|
||||
|
||||
private static void checkTrue(boolean b, String msg) {
|
||||
if (!b) throw new Exception(msg);
|
||||
if (!b) throw new Error (msg);
|
||||
}
|
||||
|
||||
private static void checkFalse(boolean b, String msg) {
|
||||
|
||||
@@ -3,7 +3,7 @@ class Test {
|
||||
void test(int x) {
|
||||
z = 0;
|
||||
if (x < 0) {
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
int y = 0;
|
||||
while(x >= 0) {
|
||||
|
||||
@@ -18,7 +18,7 @@ class PathCreation {
|
||||
File f = new File(new File("dir"), "sub");
|
||||
}
|
||||
|
||||
public void testNewFileWithURI() {
|
||||
public void testNewFileWithURI() throws java.net.URISyntaxException {
|
||||
File f = new File(new URI("dir"));
|
||||
}
|
||||
|
||||
@@ -27,7 +27,7 @@ class PathCreation {
|
||||
Path p2 = Path.of("dir", "sub");
|
||||
}
|
||||
|
||||
public void testPathOfWithURI() {
|
||||
public void testPathOfWithURI() throws java.net.URISyntaxException {
|
||||
Path p = Path.of(new URI("dir"));
|
||||
}
|
||||
|
||||
@@ -36,7 +36,7 @@ class PathCreation {
|
||||
Path p2 = Paths.get("dir", "sub");
|
||||
}
|
||||
|
||||
public void testPathsGetWithURI() {
|
||||
public void testPathsGetWithURI() throws java.net.URISyntaxException {
|
||||
Path p = Paths.get(new URI("dir"));
|
||||
}
|
||||
|
||||
@@ -53,19 +53,19 @@ class PathCreation {
|
||||
Path p = Path.of("dir").resolve("sub");
|
||||
}
|
||||
|
||||
public void testNewFileWriterWithString() {
|
||||
public void testNewFileWriterWithString() throws java.io.IOException {
|
||||
FileWriter fw = new FileWriter("dir");
|
||||
}
|
||||
|
||||
public void testNewFileReaderWithString() {
|
||||
public void testNewFileReaderWithString() throws java.io.FileNotFoundException {
|
||||
FileReader fr = new FileReader("dir");
|
||||
}
|
||||
|
||||
public void testNewFileOutputStreamWithString() {
|
||||
public void testNewFileOutputStreamWithString() throws java.io.FileNotFoundException {
|
||||
FileOutputStream fos = new FileOutputStream("dir");
|
||||
}
|
||||
|
||||
public void testNewFileInputStreamWithString() {
|
||||
public void testNewFileInputStreamWithString() throws java.io.FileNotFoundException {
|
||||
FileInputStream fis = new FileInputStream("dir");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,7 +14,7 @@ public class ReflectiveAccess {
|
||||
return classContainingAnnotation.getAnnotation(annotationClass);
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException {
|
||||
Class<?> testClass = Class.forName("reflection.ReflectiveAccess$TestClass");
|
||||
|
||||
testClass.newInstance();
|
||||
|
||||
@@ -5,8 +5,8 @@ class TestThrow2 {
|
||||
{
|
||||
try {
|
||||
thrower();
|
||||
} catch (Exception e) {
|
||||
} catch (Throwable e) {
|
||||
;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,3 +2,4 @@ name: codeql-java-tests
|
||||
version: 0.0.0
|
||||
libraryPathDependencies: codeql-java
|
||||
extractor: java
|
||||
tests: .
|
||||
|
||||
@@ -100,7 +100,7 @@ class CloseReader {
|
||||
private void init(InputStreamReader reader) {
|
||||
fileRd = new BufferedReader(reader);
|
||||
}
|
||||
public void readStuff() {
|
||||
public void readStuff() throws java.io.IOException {
|
||||
System.out.println(fileRd.readLine());
|
||||
fileRd.close();
|
||||
}
|
||||
|
||||
@@ -30,21 +30,21 @@ public class A {
|
||||
break;
|
||||
} while (c.cond());
|
||||
|
||||
// --- while, for loops ---
|
||||
|
||||
while (false) {
|
||||
if (c.cond())
|
||||
continue; // GOOD [never reached, if the condition changed so it was then the result would no longer apply]
|
||||
if (c.cond())
|
||||
break;
|
||||
}
|
||||
|
||||
for (i = 0; false; i++) {
|
||||
if (c.cond())
|
||||
continue; // GOOD [never reached, if the condition changed so it was then the result would no longer apply]
|
||||
if (c.cond())
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// --- nested loops ---
|
||||
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
class IAmAGoodCloneable implements Cloneable {
|
||||
public Object clone() {
|
||||
public Object clone() throws CloneNotSupportedException {
|
||||
return super.clone();
|
||||
}
|
||||
}
|
||||
|
||||
class Sub1 extends IAmAGoodCloneable { public Object clone() { return super.clone(); } }
|
||||
class Sub1 extends IAmAGoodCloneable { public Object clone() throws CloneNotSupportedException { return super.clone(); } }
|
||||
|
||||
class IAmABadCloneable implements Cloneable {
|
||||
public Object clone() {
|
||||
|
||||
@@ -3,7 +3,7 @@ class GoodReturn {
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
getClass().hashCode();
|
||||
return getClass().hashCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -171,7 +171,7 @@ public class C {
|
||||
|
||||
private void verifyBool(boolean b) {
|
||||
if (!b) {
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -192,7 +192,7 @@ public class C {
|
||||
|
||||
private void verifyNotNull(Object obj) {
|
||||
if (obj == null) {
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -5,7 +5,7 @@ public class A {
|
||||
|
||||
public A(int[] arr2, int n) {
|
||||
if (arr2.length % 2 != 0)
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
this.arr2 = arr2;
|
||||
this.arr3 = new int[n << 1];
|
||||
}
|
||||
@@ -168,7 +168,7 @@ public class A {
|
||||
if (n > 0) {
|
||||
a = n > 0 ? new int[3 * n] : null;
|
||||
}
|
||||
int sum;
|
||||
int sum = 0;
|
||||
if (a != null) {
|
||||
for (int i = 0; i < a.length; i += 3) {
|
||||
sum += a[i + 2]; // OK
|
||||
|
||||
@@ -7,9 +7,9 @@ class UseBraces
|
||||
void f() { }
|
||||
void g() { }
|
||||
void h() { }
|
||||
void test()
|
||||
void test(boolean bb)
|
||||
{
|
||||
int x, y;
|
||||
int x = 0, y;
|
||||
int[] branches = new int[10];
|
||||
|
||||
// If-then statement
|
||||
@@ -67,27 +67,27 @@ class UseBraces
|
||||
|
||||
// While statement
|
||||
|
||||
while(false)
|
||||
while(bb)
|
||||
{
|
||||
f();
|
||||
}
|
||||
g(); // No alert
|
||||
|
||||
|
||||
while(false)
|
||||
while(bb)
|
||||
f();
|
||||
g();
|
||||
|
||||
while(false)
|
||||
while(bb )
|
||||
f();
|
||||
g(); // Alert
|
||||
g(); // No alert
|
||||
|
||||
while(false)
|
||||
while(bb )
|
||||
f(); g(); // Alert
|
||||
|
||||
|
||||
while(false)
|
||||
while(bb)
|
||||
if (x != 0) x = 1;
|
||||
|
||||
// Do-while statement
|
||||
|
||||
@@ -3,7 +3,7 @@ class Test {
|
||||
void test(int x) {
|
||||
z = getInt();
|
||||
if (x < 0 || z < 0) {
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
int y = 0;
|
||||
if (x >= 0) y++; // useless test due to test in line 5 being false
|
||||
|
||||
@@ -7,7 +7,7 @@ public class A {
|
||||
new Object();
|
||||
} catch(Exception e) {
|
||||
if (e == null) { // Useless check
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -16,7 +16,7 @@ public class A {
|
||||
if (o instanceof A) {
|
||||
A a = (A)o;
|
||||
if (a != null) { // Useless check
|
||||
throw new Exception();
|
||||
throw new Error();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,7 +16,7 @@ public class ReflectionTest {
|
||||
public int shadowedField;
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
public static void main(String[] args) throws NoSuchFieldException {
|
||||
// Ensure the two classes are live, otherwise we might hide some results
|
||||
new ParentClass();
|
||||
new ChildClass();
|
||||
|
||||
@@ -19,7 +19,7 @@ public class ReflectionMethodTest {
|
||||
public void test4() { }
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws InstantiationException, IllegalAccessException, ClassNotFoundException {
|
||||
public static void main(String[] args) throws InstantiationException, IllegalAccessException, ClassNotFoundException, NoSuchMethodException {
|
||||
// Get class by name
|
||||
Class.forName("ReflectionTest$TestObject1").getMethod("test1");
|
||||
// Use classloader
|
||||
|
||||
@@ -3,7 +3,7 @@ import java.nio.file.*;
|
||||
import java.util.zip.*;
|
||||
|
||||
public class ZipTest {
|
||||
public void m1(ZipEntry entry, File dir) {
|
||||
public void m1(ZipEntry entry, File dir) throws Exception {
|
||||
String name = entry.getName();
|
||||
File file = new File(dir, name);
|
||||
FileOutputStream os = new FileOutputStream(file); // ZipSlip
|
||||
@@ -11,7 +11,7 @@ public class ZipTest {
|
||||
FileWriter fw = new FileWriter(file); // ZipSlip
|
||||
}
|
||||
|
||||
public void m2(ZipEntry entry, File dir) {
|
||||
public void m2(ZipEntry entry, File dir) throws Exception {
|
||||
String name = entry.getName();
|
||||
File file = new File(dir, name);
|
||||
File canFile = file.getCanonicalFile();
|
||||
@@ -21,7 +21,7 @@ public class ZipTest {
|
||||
FileOutputStream os = new FileOutputStream(file); // OK
|
||||
}
|
||||
|
||||
public void m3(ZipEntry entry, File dir) {
|
||||
public void m3(ZipEntry entry, File dir) throws Exception {
|
||||
String name = entry.getName();
|
||||
File file = new File(dir, name);
|
||||
if (!file.toPath().normalize().startsWith(dir.toPath()))
|
||||
@@ -29,20 +29,20 @@ public class ZipTest {
|
||||
FileOutputStream os = new FileOutputStream(file); // OK
|
||||
}
|
||||
|
||||
private void validate(File tgtdir, File file) {
|
||||
private void validate(File tgtdir, File file) throws Exception {
|
||||
File canFile = file.getCanonicalFile();
|
||||
if (!canFile.toPath().startsWith(tgtdir.toPath()))
|
||||
throw new Exception();
|
||||
}
|
||||
|
||||
public void m4(ZipEntry entry, File dir) {
|
||||
public void m4(ZipEntry entry, File dir) throws Exception {
|
||||
String name = entry.getName();
|
||||
File file = new File(dir, name);
|
||||
validate(dir, file);
|
||||
FileOutputStream os = new FileOutputStream(file); // OK
|
||||
}
|
||||
|
||||
public void m5(ZipEntry entry, File dir) {
|
||||
public void m5(ZipEntry entry, File dir) throws Exception {
|
||||
String name = entry.getName();
|
||||
File file = new File(dir, name);
|
||||
Path absfile = file.toPath().toAbsolutePath().normalize();
|
||||
@@ -52,7 +52,7 @@ public class ZipTest {
|
||||
FileOutputStream os = new FileOutputStream(file); // OK
|
||||
}
|
||||
|
||||
public void m6(ZipEntry entry, Path dir) {
|
||||
public void m6(ZipEntry entry, Path dir) throws Exception {
|
||||
String canonicalDest = dir.toFile().getCanonicalPath();
|
||||
Path target = dir.resolve(entry.getName());
|
||||
String canonicalTarget = target.toFile().getCanonicalPath();
|
||||
|
||||
@@ -3,7 +3,7 @@ import java.util.List;
|
||||
import java.util.ArrayList;
|
||||
|
||||
class Test {
|
||||
public static void shellCommand(String arg) {
|
||||
public static void shellCommand(String arg) throws java.io.IOException {
|
||||
ProcessBuilder pb = new ProcessBuilder("/bin/bash -c echo " + arg);
|
||||
pb.start();
|
||||
|
||||
@@ -25,7 +25,7 @@ class Test {
|
||||
pb.start();
|
||||
}
|
||||
|
||||
public static void nonShellCommand(String arg) {
|
||||
public static void nonShellCommand(String arg) throws java.io.IOException {
|
||||
ProcessBuilder pb = new ProcessBuilder("./customTool " + arg);
|
||||
pb.start();
|
||||
|
||||
@@ -46,7 +46,7 @@ class Test {
|
||||
pb.start();
|
||||
}
|
||||
|
||||
public static void relativeCommand() {
|
||||
public static void relativeCommand() throws java.io.IOException {
|
||||
ProcessBuilder pb = new ProcessBuilder("ls");
|
||||
pb.start();
|
||||
|
||||
@@ -54,11 +54,11 @@ class Test {
|
||||
pb.start();
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
public static void main(String[] args) throws java.io.IOException {
|
||||
String arg = args.length > 1 ? args[1] : "default";
|
||||
|
||||
shellCommand(arg);
|
||||
nonShellCommand(arg);
|
||||
relativeCommand();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
edges
|
||||
| UnsafeHostnameVerification.java:66:37:80:9 | new (...) : new HostnameVerifier(...) { ... } | UnsafeHostnameVerification.java:81:55:81:62 | verifier |
|
||||
| UnsafeHostnameVerification.java:88:37:93:9 | new (...) : new HostnameVerifier(...) { ... } | UnsafeHostnameVerification.java:94:55:94:62 | verifier |
|
||||
| UnsafeHostnameVerification.java:97:72:102:5 | new (...) : new HostnameVerifier(...) { ... } | UnsafeHostnameVerification.java:34:59:34:85 | ALLOW_ALL_HOSTNAME_VERIFIER |
|
||||
nodes
|
||||
| UnsafeHostnameVerification.java:14:55:19:9 | new (...) | semmle.label | new (...) |
|
||||
| UnsafeHostnameVerification.java:26:55:26:71 | ...->... | semmle.label | ...->... |
|
||||
| UnsafeHostnameVerification.java:34:59:34:85 | ALLOW_ALL_HOSTNAME_VERIFIER | semmle.label | ALLOW_ALL_HOSTNAME_VERIFIER |
|
||||
| UnsafeHostnameVerification.java:47:55:47:71 | ...->... | semmle.label | ...->... |
|
||||
| UnsafeHostnameVerification.java:59:59:59:85 | ...->... | semmle.label | ...->... |
|
||||
| UnsafeHostnameVerification.java:66:37:80:9 | new (...) : new HostnameVerifier(...) { ... } | semmle.label | new (...) : new HostnameVerifier(...) { ... } |
|
||||
| UnsafeHostnameVerification.java:81:55:81:62 | verifier | semmle.label | verifier |
|
||||
| UnsafeHostnameVerification.java:88:37:93:9 | new (...) : new HostnameVerifier(...) { ... } | semmle.label | new (...) : new HostnameVerifier(...) { ... } |
|
||||
| UnsafeHostnameVerification.java:94:55:94:62 | verifier | semmle.label | verifier |
|
||||
| UnsafeHostnameVerification.java:97:72:102:5 | new (...) : new HostnameVerifier(...) { ... } | semmle.label | new (...) : new HostnameVerifier(...) { ... } |
|
||||
#select
|
||||
| UnsafeHostnameVerification.java:14:55:19:9 | new (...) | UnsafeHostnameVerification.java:14:55:19:9 | new (...) | UnsafeHostnameVerification.java:14:55:19:9 | new (...) | $@ that is defined $@ and accepts any certificate as valid, is used here. | UnsafeHostnameVerification.java:14:55:19:9 | new (...) | This hostname verifier | UnsafeHostnameVerification.java:14:59:14:74 | new HostnameVerifier(...) { ... } | here |
|
||||
| UnsafeHostnameVerification.java:26:55:26:71 | ...->... | UnsafeHostnameVerification.java:26:55:26:71 | ...->... | UnsafeHostnameVerification.java:26:55:26:71 | ...->... | $@ that is defined $@ and accepts any certificate as valid, is used here. | UnsafeHostnameVerification.java:26:55:26:71 | ...->... | This hostname verifier | UnsafeHostnameVerification.java:26:55:26:71 | new HostnameVerifier(...) { ... } | here |
|
||||
| UnsafeHostnameVerification.java:47:55:47:71 | ...->... | UnsafeHostnameVerification.java:47:55:47:71 | ...->... | UnsafeHostnameVerification.java:47:55:47:71 | ...->... | $@ that is defined $@ and accepts any certificate as valid, is used here. | UnsafeHostnameVerification.java:47:55:47:71 | ...->... | This hostname verifier | UnsafeHostnameVerification.java:47:55:47:71 | new HostnameVerifier(...) { ... } | here |
|
||||
| UnsafeHostnameVerification.java:81:55:81:62 | verifier | UnsafeHostnameVerification.java:66:37:80:9 | new (...) : new HostnameVerifier(...) { ... } | UnsafeHostnameVerification.java:81:55:81:62 | verifier | $@ that is defined $@ and accepts any certificate as valid, is used here. | UnsafeHostnameVerification.java:66:37:80:9 | new (...) : new HostnameVerifier(...) { ... } | This hostname verifier | UnsafeHostnameVerification.java:66:41:66:56 | new HostnameVerifier(...) { ... } | here |
|
||||
| UnsafeHostnameVerification.java:94:55:94:62 | verifier | UnsafeHostnameVerification.java:88:37:93:9 | new (...) : new HostnameVerifier(...) { ... } | UnsafeHostnameVerification.java:94:55:94:62 | verifier | $@ that is defined $@ and accepts any certificate as valid, is used here. | UnsafeHostnameVerification.java:88:37:93:9 | new (...) : new HostnameVerifier(...) { ... } | This hostname verifier | UnsafeHostnameVerification.java:88:41:88:56 | new HostnameVerifier(...) { ... } | here |
|
||||
@@ -0,0 +1,103 @@
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.HttpsURLConnection;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import java.security.cert.Certificate;
|
||||
|
||||
public class UnsafeHostnameVerification {
|
||||
|
||||
private static final boolean DISABLE_VERIFICATION = true;
|
||||
|
||||
/**
|
||||
* Test the implementation of trusting all hostnames as an anonymous class
|
||||
*/
|
||||
public void testTrustAllHostnameOfAnonymousClass() {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // BAD, always returns true
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Test the implementation of trusting all hostnames as a lambda.
|
||||
*/
|
||||
public void testTrustAllHostnameLambda() {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier((name, s) -> true); // BAD, always returns true
|
||||
}
|
||||
|
||||
/**
|
||||
* Test an all-trusting hostname verifier that is guarded by a flag
|
||||
*/
|
||||
public void testGuardedByFlagTrustAllHostname() {
|
||||
if (DISABLE_VERIFICATION) {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(ALLOW_ALL_HOSTNAME_VERIFIER); // GOOD: The all-trusting
|
||||
// hostname verifier is guarded
|
||||
// by a feature flag
|
||||
}
|
||||
}
|
||||
|
||||
public void testGuardedByFlagAccrossCalls() {
|
||||
if (DISABLE_VERIFICATION) {
|
||||
functionThatActuallyDisablesVerification();
|
||||
}
|
||||
}
|
||||
|
||||
private void functionThatActuallyDisablesVerification() {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier((name, s) -> true); // GOOD [but detected as BAD], because we only
|
||||
// check guards inside a function
|
||||
// and not accross function calls. This is considerer GOOD because the call to
|
||||
// `functionThatActuallyDisablesVerification` is guarded by a feature flag in
|
||||
// `testGuardedByFlagAccrossCalls`.
|
||||
// Although this is not ideal as another function could directly call
|
||||
// `functionThatActuallyDisablesVerification` WITHOUT checking the feature flag.
|
||||
}
|
||||
|
||||
public void testTrustAllHostnameDependingOnDerivedValue() {
|
||||
String enabled = System.getProperty("disableHostnameVerification");
|
||||
if (Boolean.parseBoolean(enabled)) {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier((hostname, session) -> true); // GOOD, because it depends on a
|
||||
// feature
|
||||
// flag.
|
||||
}
|
||||
}
|
||||
|
||||
public void testTrustAllHostnameWithExceptions() {
|
||||
HostnameVerifier verifier = new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
try { verify(hostname, session.getPeerCertificates()); } catch (Exception e) { throw new RuntimeException(); }
|
||||
return true; // GOOD [but detected as BAD]. The verification of the certificate is done in
|
||||
// another method and
|
||||
// in the case of a mismatch, an `Exception` is thrown so the `return true`
|
||||
// statement never gets executed.
|
||||
}
|
||||
|
||||
// Black-box method that properly verifies the certificate but throws an
|
||||
// `Exception` in the case of a mismatch.
|
||||
private void verify(String hostname, Certificate[] certs) {
|
||||
}
|
||||
};
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(verifier);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test the implementation of trusting all hostnames as a variable
|
||||
*/
|
||||
public void testTrustAllHostnameOfVariable() {
|
||||
HostnameVerifier verifier = new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // BAD, always returns true
|
||||
}
|
||||
};
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(verifier);
|
||||
}
|
||||
|
||||
public static final HostnameVerifier ALLOW_ALL_HOSTNAME_VERIFIER = new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true; // BAD, always returns true
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
Security/CWE/CWE-297/UnsafeHostnameVerification.ql
|
||||
@@ -3,7 +3,7 @@ import javax.net.ssl.HttpsURLConnection;
|
||||
import java.io.*;
|
||||
|
||||
class Test {
|
||||
public void m1(HttpURLConnection connection) {
|
||||
public void m1(HttpURLConnection connection) throws java.io.IOException {
|
||||
InputStream input;
|
||||
if (connection instanceof HttpsURLConnection) {
|
||||
input = connection.getInputStream(); // OK
|
||||
|
||||
@@ -31,7 +31,7 @@ class Test {
|
||||
return true;
|
||||
}
|
||||
|
||||
public void doConnect(int desiredPort, String username) {
|
||||
public void doConnect(int desiredPort, String username) throws Exception {
|
||||
ServerSocket listenSocket = new ServerSocket(desiredPort);
|
||||
|
||||
if (isAuthenticated(username)) {
|
||||
@@ -56,7 +56,7 @@ class Test {
|
||||
|
||||
}
|
||||
|
||||
public void doConnectChannel(int desiredPort, String username) {
|
||||
public void doConnectChannel(int desiredPort, String username) throws Exception {
|
||||
ServerSocketChannel listenChannel = ServerSocketChannel.open();
|
||||
SocketAddress port = new InetSocketAddress(desiredPort);
|
||||
listenChannel.bind(port);
|
||||
|
||||
@@ -9,32 +9,32 @@ import org.yaml.snakeyaml.constructor.Constructor;
|
||||
import org.yaml.snakeyaml.Yaml;
|
||||
|
||||
public class A {
|
||||
public Object deserialize1(Socket sock) {
|
||||
public Object deserialize1(Socket sock) throws java.io.IOException, ClassNotFoundException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
ObjectInputStream in = new ObjectInputStream(inputStream);
|
||||
return in.readObject(); // unsafe
|
||||
}
|
||||
|
||||
public Object deserialize2(Socket sock) {
|
||||
public Object deserialize2(Socket sock) throws java.io.IOException, ClassNotFoundException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
ObjectInputStream in = new ObjectInputStream(inputStream);
|
||||
return in.readUnshared(); // unsafe
|
||||
}
|
||||
|
||||
public Object deserialize3(Socket sock) {
|
||||
public Object deserialize3(Socket sock) throws java.io.IOException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
XMLDecoder d = new XMLDecoder(inputStream);
|
||||
return d.readObject(); // unsafe
|
||||
}
|
||||
|
||||
public Object deserialize4(Socket sock) {
|
||||
public Object deserialize4(Socket sock) throws java.io.IOException {
|
||||
XStream xs = new XStream();
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
Reader reader = new InputStreamReader(inputStream);
|
||||
return xs.fromXML(reader); // unsafe
|
||||
}
|
||||
|
||||
public void deserialize5(Socket sock) {
|
||||
public void deserialize5(Socket sock) throws java.io.IOException {
|
||||
Kryo kryo = new Kryo();
|
||||
Input input = new Input(sock.getInputStream());
|
||||
A a1 = kryo.readObject(input, A.class); // unsafe
|
||||
@@ -42,20 +42,20 @@ public class A {
|
||||
Object o = kryo.readClassAndObject(input); // unsafe
|
||||
}
|
||||
|
||||
private Kryo getSafeKryo() {
|
||||
private Kryo getSafeKryo() throws java.io.IOException {
|
||||
Kryo kryo = new Kryo();
|
||||
kryo.setRegistrationRequired(true);
|
||||
// ... kryo.register(A.class) ...
|
||||
return kryo;
|
||||
}
|
||||
|
||||
public void deserialize6(Socket sock) {
|
||||
public void deserialize6(Socket sock) throws java.io.IOException {
|
||||
Kryo kryo = getSafeKryo();
|
||||
Input input = new Input(sock.getInputStream());
|
||||
Object o = kryo.readClassAndObject(input); // OK
|
||||
}
|
||||
|
||||
public void deserializeSnakeYaml(Socket sock) {
|
||||
public void deserializeSnakeYaml(Socket sock) throws java.io.IOException {
|
||||
Yaml yaml = new Yaml();
|
||||
InputStream input = sock.getInputStream();
|
||||
Object o = yaml.load(input); //unsafe
|
||||
@@ -65,7 +65,7 @@ public class A {
|
||||
A o5 = yaml.loadAs(new InputStreamReader(input), A.class); //unsafe
|
||||
}
|
||||
|
||||
public void deserializeSnakeYaml2(Socket sock) {
|
||||
public void deserializeSnakeYaml2(Socket sock) throws java.io.IOException {
|
||||
Yaml yaml = new Yaml(new Constructor());
|
||||
InputStream input = sock.getInputStream();
|
||||
Object o = yaml.load(input); //unsafe
|
||||
@@ -75,7 +75,7 @@ public class A {
|
||||
A o5 = yaml.loadAs(new InputStreamReader(input), A.class); //unsafe
|
||||
}
|
||||
|
||||
public void deserializeSnakeYaml3(Socket sock) {
|
||||
public void deserializeSnakeYaml3(Socket sock) throws java.io.IOException {
|
||||
Yaml yaml = new Yaml(new SafeConstructor());
|
||||
InputStream input = sock.getInputStream();
|
||||
Object o = yaml.load(input); //OK
|
||||
@@ -85,13 +85,13 @@ public class A {
|
||||
A o5 = yaml.loadAs(new InputStreamReader(input), A.class); //OK
|
||||
}
|
||||
|
||||
public void deserializeSnakeYaml4(Socket sock) {
|
||||
public void deserializeSnakeYaml4(Socket sock) throws java.io.IOException {
|
||||
Yaml yaml = new Yaml(new Constructor(A.class));
|
||||
InputStream input = sock.getInputStream();
|
||||
Object o = yaml.load(input); //OK
|
||||
Object o2 = yaml.loadAll(input); //OK
|
||||
Object o3 = yaml.parse(new InputStreamReader(input)); //OK
|
||||
A o4 = yaml.loadAs(input, A.class); //OK
|
||||
A o5 = yaml.loadAs(new InputStreamReader(input), A.class); //OK
|
||||
Object o = yaml.load(input); //unsafe
|
||||
Object o2 = yaml.loadAll(input); //unsafe
|
||||
Object o3 = yaml.parse(new InputStreamReader(input)); //unsafe
|
||||
A o4 = yaml.loadAs(input, A.class); //unsafe
|
||||
A o5 = yaml.loadAs(new InputStreamReader(input), A.class); //unsafe
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,19 +3,19 @@ import java.net.Socket;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
|
||||
public class B {
|
||||
public Object deserializeJson1(Socket sock) {
|
||||
public Object deserializeJson1(Socket sock) throws java.io.IOException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
return JSON.parseObject(inputStream, null); // unsafe
|
||||
}
|
||||
|
||||
public Object deserializeJson2(Socket sock) {
|
||||
public Object deserializeJson2(Socket sock) throws java.io.IOException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
byte[] bytes = new byte[100];
|
||||
inputStream.read(bytes);
|
||||
return JSON.parse(bytes); // unsafe
|
||||
}
|
||||
|
||||
public Object deserializeJson3(Socket sock) {
|
||||
public Object deserializeJson3(Socket sock) throws java.io.IOException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
byte[] bytes = new byte[100];
|
||||
inputStream.read(bytes);
|
||||
@@ -23,7 +23,7 @@ public class B {
|
||||
return JSON.parseObject(s); // unsafe
|
||||
}
|
||||
|
||||
public Object deserializeJson4(Socket sock) {
|
||||
public Object deserializeJson4(Socket sock) throws java.io.IOException {
|
||||
InputStream inputStream = sock.getInputStream();
|
||||
byte[] bytes = new byte[100];
|
||||
inputStream.read(bytes);
|
||||
|
||||
@@ -16,6 +16,11 @@ edges
|
||||
| A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:73:28:73:55 | new InputStreamReader(...) |
|
||||
| A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:74:24:74:28 | input |
|
||||
| A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:75:24:75:51 | new InputStreamReader(...) |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:91:26:91:30 | input |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:92:30:92:34 | input |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:93:28:93:55 | new InputStreamReader(...) |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:94:24:94:28 | input |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:95:24:95:51 | new InputStreamReader(...) |
|
||||
| B.java:7:31:7:51 | getInputStream(...) : InputStream | B.java:8:29:8:39 | inputStream |
|
||||
| B.java:12:31:12:51 | getInputStream(...) : InputStream | B.java:15:23:15:27 | bytes |
|
||||
| B.java:19:31:19:51 | getInputStream(...) : InputStream | B.java:23:29:23:29 | s |
|
||||
@@ -46,6 +51,12 @@ nodes
|
||||
| A.java:73:28:73:55 | new InputStreamReader(...) | semmle.label | new InputStreamReader(...) |
|
||||
| A.java:74:24:74:28 | input | semmle.label | input |
|
||||
| A.java:75:24:75:51 | new InputStreamReader(...) | semmle.label | new InputStreamReader(...) |
|
||||
| A.java:90:25:90:45 | getInputStream(...) : InputStream | semmle.label | getInputStream(...) : InputStream |
|
||||
| A.java:91:26:91:30 | input | semmle.label | input |
|
||||
| A.java:92:30:92:34 | input | semmle.label | input |
|
||||
| A.java:93:28:93:55 | new InputStreamReader(...) | semmle.label | new InputStreamReader(...) |
|
||||
| A.java:94:24:94:28 | input | semmle.label | input |
|
||||
| A.java:95:24:95:51 | new InputStreamReader(...) | semmle.label | new InputStreamReader(...) |
|
||||
| B.java:7:31:7:51 | getInputStream(...) : InputStream | semmle.label | getInputStream(...) : InputStream |
|
||||
| B.java:8:29:8:39 | inputStream | semmle.label | inputStream |
|
||||
| B.java:12:31:12:51 | getInputStream(...) : InputStream | semmle.label | getInputStream(...) : InputStream |
|
||||
@@ -74,6 +85,11 @@ nodes
|
||||
| A.java:73:17:73:56 | parse(...) | A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:73:28:73:55 | new InputStreamReader(...) | Unsafe deserialization of $@. | A.java:70:25:70:45 | getInputStream(...) | user input |
|
||||
| A.java:74:12:74:38 | loadAs(...) | A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:74:24:74:28 | input | Unsafe deserialization of $@. | A.java:70:25:70:45 | getInputStream(...) | user input |
|
||||
| A.java:75:12:75:61 | loadAs(...) | A.java:70:25:70:45 | getInputStream(...) : InputStream | A.java:75:24:75:51 | new InputStreamReader(...) | Unsafe deserialization of $@. | A.java:70:25:70:45 | getInputStream(...) | user input |
|
||||
| A.java:91:16:91:31 | load(...) | A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:91:26:91:30 | input | Unsafe deserialization of $@. | A.java:90:25:90:45 | getInputStream(...) | user input |
|
||||
| A.java:92:17:92:35 | loadAll(...) | A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:92:30:92:34 | input | Unsafe deserialization of $@. | A.java:90:25:90:45 | getInputStream(...) | user input |
|
||||
| A.java:93:17:93:56 | parse(...) | A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:93:28:93:55 | new InputStreamReader(...) | Unsafe deserialization of $@. | A.java:90:25:90:45 | getInputStream(...) | user input |
|
||||
| A.java:94:12:94:38 | loadAs(...) | A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:94:24:94:28 | input | Unsafe deserialization of $@. | A.java:90:25:90:45 | getInputStream(...) | user input |
|
||||
| A.java:95:12:95:61 | loadAs(...) | A.java:90:25:90:45 | getInputStream(...) : InputStream | A.java:95:24:95:51 | new InputStreamReader(...) | Unsafe deserialization of $@. | A.java:90:25:90:45 | getInputStream(...) | user input |
|
||||
| B.java:8:12:8:46 | parseObject(...) | B.java:7:31:7:51 | getInputStream(...) : InputStream | B.java:8:29:8:39 | inputStream | Unsafe deserialization of $@. | B.java:7:31:7:51 | getInputStream(...) | user input |
|
||||
| B.java:15:12:15:28 | parse(...) | B.java:12:31:12:51 | getInputStream(...) : InputStream | B.java:15:23:15:27 | bytes | Unsafe deserialization of $@. | B.java:12:31:12:51 | getInputStream(...) | user input |
|
||||
| B.java:23:12:23:30 | parseObject(...) | B.java:19:31:19:51 | getInputStream(...) : InputStream | B.java:23:29:23:29 | s | Unsafe deserialization of $@. | B.java:19:31:19:51 | getInputStream(...) | user input |
|
||||
|
||||
@@ -102,7 +102,7 @@ class DocumentBuilderTests {
|
||||
builder.parse(source.getInputStream()); //unsafe
|
||||
}
|
||||
|
||||
private static DocumentBuilderFactory getDocumentBuilderFactory() {
|
||||
private static DocumentBuilderFactory getDocumentBuilderFactory() throws Exception {
|
||||
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
|
||||
String feature = "";
|
||||
feature = "http://xml.org/sax/features/external-parameter-entities";
|
||||
@@ -115,8 +115,8 @@ class DocumentBuilderTests {
|
||||
private static final ThreadLocal<DocumentBuilder> XML_DOCUMENT_BUILDER = new ThreadLocal<DocumentBuilder>() {
|
||||
@Override
|
||||
protected DocumentBuilder initialValue() {
|
||||
DocumentBuilderFactory factory = getDocumentBuilderFactory();
|
||||
try {
|
||||
DocumentBuilderFactory factory = getDocumentBuilderFactory();
|
||||
return factory.newDocumentBuilder();
|
||||
} catch (Exception ex) {
|
||||
throw new RuntimeException(ex);
|
||||
|
||||
@@ -31,11 +31,11 @@ class Test {
|
||||
new FileInputStream(f2);
|
||||
}
|
||||
|
||||
public static void readFile(File f) {
|
||||
public static void readFile(File f) throws java.io.FileNotFoundException {
|
||||
new FileReader(f);
|
||||
}
|
||||
|
||||
public static void setWorldWritable(File f) {
|
||||
f.setWritable(true, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
| MethodAccessLockOrder.java:29:4:29:40 | transferFrom(...) | Synchronization here and $@ may be performed in reverse order starting $@ and result in deadlock. | MethodAccessLockOrder.java:8:21:8:41 | subtract(...) | here | MethodAccessLockOrder.java:31:4:31:40 | transferFrom(...) | here |
|
||||
| MethodAccessLockOrder.java:29:11:29:47 | transferFrom(...) | Synchronization here and $@ may be performed in reverse order starting $@ and result in deadlock. | MethodAccessLockOrder.java:8:21:8:41 | subtract(...) | here | MethodAccessLockOrder.java:31:11:31:47 | transferFrom(...) | here |
|
||||
| ReentrantLockOrder.java:11:4:11:21 | lock(...) | Synchronization here and $@ may be performed in reverse order starting $@ and result in deadlock. | ReentrantLockOrder.java:12:4:12:21 | lock(...) | here | ReentrantLockOrder.java:28:4:28:21 | lock(...) | here |
|
||||
| ReentrantLockOrder.java:28:4:28:21 | lock(...) | Synchronization here and $@ may be performed in reverse order starting $@ and result in deadlock. | ReentrantLockOrder.java:29:4:29:21 | lock(...) | here | ReentrantLockOrder.java:11:4:11:21 | lock(...) | here |
|
||||
| SynchronizedStmtLockOrder.java:8:16:8:26 | primaryLock | Synchronization here and $@ may be performed in reverse order starting $@ and result in deadlock. | SynchronizedStmtLockOrder.java:9:17:9:27 | savingsLock | here | SynchronizedStmtLockOrder.java:22:16:22:26 | savingsLock | here |
|
||||
|
||||
@@ -26,9 +26,9 @@ class MethodAccessLockOrder {
|
||||
public boolean initiateTransfer(boolean fromSavings, int amount) {
|
||||
// AVOID: inconsistent lock order
|
||||
if (fromSavings) {
|
||||
primary.transferFrom(savings, amount);
|
||||
return primary.transferFrom(savings, amount);
|
||||
} else {
|
||||
savings.transferFrom(primary, amount);
|
||||
return savings.transferFrom(primary, amount);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,963 @@
|
||||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package org.apache.commons.lang3;
|
||||
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.nio.charset.Charset;
|
||||
import java.text.Normalizer;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
import java.util.StringJoiner;
|
||||
import java.util.function.Supplier;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
|
||||
public class StringUtils {
|
||||
public static boolean isEmpty(final CharSequence cs) {
|
||||
return true;
|
||||
public static String abbreviate(final String str, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public static String abbreviate(final String str, final int offset, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String abbreviate(final String str, final String abbrevMarker, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String abbreviate(final String str, final String abbrevMarker, int offset, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String abbreviateMiddle(final String str, final String middle, final int length) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String appendIfMissing(final String str, final CharSequence suffix, final CharSequence... suffixes) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String appendIfMissingIgnoreCase(final String str, final CharSequence suffix, final CharSequence... suffixes) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String capitalize(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String center(final String str, final int size) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String center(String str, final int size, final char padChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String center(String str, final int size, String padStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String chomp(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String chomp(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String chop(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int compare(final String str1, final String str2) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int compare(final String str1, final String str2, final boolean nullIsLess) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int compareIgnoreCase(final String str1, final String str2) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int compareIgnoreCase(final String str1, final String str2, final boolean nullIsLess) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static boolean contains(final CharSequence seq, final CharSequence searchSeq) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean contains(final CharSequence seq, final int searchChar) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsAny(final CharSequence cs, final char... searchChars) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsAny(final CharSequence cs, final CharSequence searchChars) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsAny(final CharSequence cs, final CharSequence... searchCharSequences) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsAnyIgnoreCase(final CharSequence cs, final CharSequence... searchCharSequences) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsIgnoreCase(final CharSequence str, final CharSequence searchStr) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsNone(final CharSequence cs, final char... searchChars) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsNone(final CharSequence cs, final String invalidChars) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsOnly(final CharSequence cs, final char... valid) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsOnly(final CharSequence cs, final String validChars) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean containsWhitespace(final CharSequence seq) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static int countMatches(final CharSequence str, final char ch) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int countMatches(final CharSequence str, final CharSequence sub) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T defaultIfBlank(final T str, final T defaultStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T defaultIfEmpty(final T str, final T defaultStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String defaultString(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String defaultString(final String str, final String defaultStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String deleteWhitespace(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String difference(final String str1, final String str2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static boolean endsWith(final CharSequence str, final CharSequence suffix) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean endsWithAny(final CharSequence sequence, final CharSequence... searchStrings) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean endsWithIgnoreCase(final CharSequence str, final CharSequence suffix) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean equals(final CharSequence cs1, final CharSequence cs2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean equalsAny(final CharSequence string, final CharSequence... searchStrings) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean equalsAnyIgnoreCase(final CharSequence string, final CharSequence...searchStrings) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean equalsIgnoreCase(final CharSequence cs1, final CharSequence cs2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T firstNonBlank(final T... values) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T firstNonEmpty(final T... values) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static byte[] getBytes(final String string, final Charset charset) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static byte[] getBytes(final String string, final String charset) throws UnsupportedEncodingException {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String getCommonPrefix(final String... strs) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String getDigits(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int getFuzzyDistance(final CharSequence term, final CharSequence query, final Locale locale) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T getIfBlank(final T str, final Supplier<T> defaultSupplier) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <T extends CharSequence> T getIfEmpty(final T str, final Supplier<T> defaultSupplier) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static double getJaroWinklerDistance(final CharSequence first, final CharSequence second) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int getLevenshteinDistance(CharSequence s, CharSequence t) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int getLevenshteinDistance(CharSequence s, CharSequence t, final int threshold) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOf(final CharSequence seq, final CharSequence searchSeq) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOf(final CharSequence seq, final CharSequence searchSeq, final int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOf(final CharSequence seq, final int searchChar) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOf(final CharSequence seq, final int searchChar, final int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfAny(final CharSequence cs, final char... searchChars) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfAny(final CharSequence str, final CharSequence... searchStrs) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfAny(final CharSequence cs, final String searchChars) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfAnyBut(final CharSequence cs, final char... searchChars) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfAnyBut(final CharSequence seq, final CharSequence searchChars) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfDifference(final CharSequence... css) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfDifference(final CharSequence cs1, final CharSequence cs2) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfIgnoreCase(final CharSequence str, final CharSequence searchStr) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int indexOfIgnoreCase(final CharSequence str, final CharSequence searchStr, int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static boolean isAllBlank(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAllEmpty(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAllLowerCase(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAllUpperCase(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAlpha(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAlphanumeric(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAlphanumericSpace(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAlphaSpace(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAnyBlank(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAnyEmpty(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isAsciiPrintable(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isBlank(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isEmpty(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isMixedCase(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNoneBlank(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNoneEmpty(final CharSequence... css) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNotBlank(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNotEmpty(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNumeric(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isNumericSpace(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean isWhitespace(final CharSequence cs) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static String join(final boolean[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final boolean[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final byte[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final byte[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final char[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final char[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final double[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final double[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final float[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final float[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final int[] array, final char separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final int[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Iterable<?> iterable, final char separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Iterable<?> iterable, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Iterator<?> iterator, final char separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Iterator<?> iterator, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final List<?> list, final char separator, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final List<?> list, final String separator, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final long[] array, final char separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final long[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Object[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Object[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Object[] array, final String delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final Object[] array, String delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final short[] array, final char delimiter) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String join(final short[] array, final char delimiter, final int startIndex, final int endIndex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <T> String join(final T... elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String joinWith(final String delimiter, final Object... array) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int lastIndexOf(final CharSequence seq, final CharSequence searchSeq) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOf(final CharSequence seq, final CharSequence searchSeq, final int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOf(final CharSequence seq, final int searchChar) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOf(final CharSequence seq, final int searchChar, final int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOfAny(final CharSequence str, final CharSequence... searchStrs) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOfIgnoreCase(final CharSequence str, final CharSequence searchStr) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastIndexOfIgnoreCase(final CharSequence str, final CharSequence searchStr, int startPos) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static int lastOrdinalIndexOf(final CharSequence str, final CharSequence searchStr, final int ordinal) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static String left(final String str, final int len) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String leftPad(final String str, final int size) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String leftPad(final String str, final int size, final char padChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String leftPad(final String str, final int size, String padStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int length(final CharSequence cs) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static String lowerCase(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String lowerCase(final String str, final Locale locale) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String mid(final String str, int pos, final int len) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String normalizeSpace(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int ordinalIndexOf(final CharSequence str, final CharSequence searchStr, final int ordinal) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static String overlay(final String str, String overlay, int start, int end) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String prependIfMissing(final String str, final CharSequence prefix, final CharSequence... prefixes) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String prependIfMissingIgnoreCase(final String str, final CharSequence prefix, final CharSequence... prefixes) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String remove(final String str, final char remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String remove(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeAll(final String text, final String regex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeEnd(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeEndIgnoreCase(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeFirst(final String text, final String regex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeIgnoreCase(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removePattern(final String source, final String regex) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeStart(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String removeStartIgnoreCase(final String str, final String remove) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String repeat(final char ch, final int repeat) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String repeat(final String str, final int repeat) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String repeat(final String str, final String separator, final int repeat) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replace(final String text, final String searchString, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replace(final String text, final String searchString, final String replacement, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceAll(final String text, final String regex, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceChars(final String str, final char searchChar, final char replaceChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceChars(final String str, final String searchChars, String replaceChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceEach(final String text, final String[] searchList, final String[] replacementList) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceEachRepeatedly(final String text, final String[] searchList, final String[] replacementList) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceFirst(final String text, final String regex, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceIgnoreCase(final String text, final String searchString, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceIgnoreCase(final String text, final String searchString, final String replacement, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceOnce(final String text, final String searchString, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replaceOnceIgnoreCase(final String text, final String searchString, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String replacePattern(final String source, final String regex, final String replacement) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String reverse(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String reverseDelimited(final String str, final char separatorChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String right(final String str, final int len) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String rightPad(final String str, final int size) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String rightPad(final String str, final int size, final char padChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String rightPad(final String str, final int size, String padStr) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String rotate(final String str, final int shift) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] split(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] split(final String str, final char separatorChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] split(final String str, final String separatorChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] split(final String str, final String separatorChars, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByCharacterType(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByCharacterTypeCamelCase(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByWholeSeparator(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByWholeSeparator( final String str, final String separator, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByWholeSeparatorPreserveAllTokens(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitByWholeSeparatorPreserveAllTokens(final String str, final String separator, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitPreserveAllTokens(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitPreserveAllTokens(final String str, final char separatorChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitPreserveAllTokens(final String str, final String separatorChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] splitPreserveAllTokens(final String str, final String separatorChars, final int max) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static boolean startsWith(final CharSequence str, final CharSequence prefix) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean startsWithAny(final CharSequence sequence, final CharSequence... searchStrings) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean startsWithIgnoreCase(final CharSequence str, final CharSequence prefix) {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static String strip(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String strip(String str, final String stripChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String stripAccents(final String input) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] stripAll(final String... strs) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] stripAll(final String[] strs, final String stripChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String stripEnd(final String str, final String stripChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String stripStart(final String str, final String stripChars) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String stripToEmpty(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String stripToNull(String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substring(final String str, int start) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substring(final String str, int start, int end) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringAfter(final String str, final int separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringAfter(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringAfterLast(final String str, final int separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringAfterLast(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringBefore(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringBeforeLast(final String str, final String separator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringBetween(final String str, final String tag) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String substringBetween(final String str, final String open, final String close) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String[] substringsBetween(final String str, final String open, final String close) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String swapCase(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static int[] toCodePoints(final CharSequence cs) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String toEncodedString(final byte[] bytes, final Charset charset) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String toRootLowerCase(final String source) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String toRootUpperCase(final String source) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String toString(final byte[] bytes, final String charsetName) throws UnsupportedEncodingException {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String trim(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String trimToEmpty(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String trimToNull(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String truncate(final String str, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String truncate(final String str, final int offset, final int maxWidth) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String uncapitalize(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String unwrap(final String str, final char wrapChar) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String unwrap(final String str, final String wrapToken) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String upperCase(final String str) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String upperCase(final String str, final Locale locale) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String valueOf(final char[] value) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String wrap(final String str, final char wrapWith) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String wrap(final String str, final String wrapWith) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String wrapIfMissing(final String str, final char wrapWith) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static String wrapIfMissing(final String str, final String wrapWith) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public StringUtils() {
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1019,6 +1019,7 @@ public class Activity {
|
||||
* @see Activity#requireViewById(int)
|
||||
*/
|
||||
public <T> T findViewById(int id) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1141,4 +1142,4 @@ public class Activity {
|
||||
*/
|
||||
public void startActivities(Intent[] intents, Bundle options) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -821,6 +821,7 @@ public class Intent implements Parcelable, Cloneable {
|
||||
*/
|
||||
@Deprecated
|
||||
public static Intent getIntent(String uri) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -845,6 +846,7 @@ public class Intent implements Parcelable, Cloneable {
|
||||
* @see #toUri
|
||||
*/
|
||||
public static Intent parseUri(String uri, int flags) {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -2069,4 +2071,4 @@ public class Intent implements Parcelable, Cloneable {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -97,6 +97,7 @@ public class BaseBundle {
|
||||
* @hide
|
||||
*/
|
||||
public String getPairValue() {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -229,6 +229,7 @@ public final class Parcel {
|
||||
}
|
||||
|
||||
public final float[] createFloatArray() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public final void readFloatArray(float[] val) {
|
||||
|
||||
@@ -85,6 +85,7 @@ public final class EncryptedSharedPreferences implements SharedPreferences {
|
||||
PrefKeyEncryptionScheme prefKeyEncryptionScheme,
|
||||
PrefValueEncryptionScheme prefValueEncryptionScheme)
|
||||
throws GeneralSecurityException, IOException {
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -168,4 +169,4 @@ public final class EncryptedSharedPreferences implements SharedPreferences {
|
||||
public void unregisterOnSharedPreferenceChangeListener(
|
||||
OnSharedPreferenceChangeListener listener) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,7 +25,7 @@ public final class Splitter {
|
||||
}
|
||||
|
||||
public Splitter omitEmptyStrings() {
|
||||
return null;;
|
||||
return null;
|
||||
}
|
||||
|
||||
public Iterable<String> split(final CharSequence sequence) {
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Copyright (C) 2012 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.Set;
|
||||
|
||||
abstract class AbstractMultimap<K, V> implements Multimap<K, V> {
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsValue(Object value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsEntry(Object key, Object value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean remove(Object key, Object value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean put(K key, V value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean putAll(K key, Iterable<? extends V> values) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean putAll(Multimap<? extends K, ? extends V> multimap) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<V> replaceValues(K key, Iterable<? extends V> values) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<Entry<K, V>> entries() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<K> keySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Multiset<K> keys() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<V> values() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<K, Collection<V>> asMap() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Copyright (C) 2013 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
|
||||
* in compliance with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software distributed under the License
|
||||
* is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
|
||||
* or implied. See the License for the specific language governing permissions and limitations under
|
||||
* the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
abstract class AbstractTable<R, C, V> implements Table<R, C, V> {
|
||||
@Override
|
||||
public boolean containsRow(Object rowKey) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsColumn(Object columnKey) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<R> rowKeySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<C> columnKeySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsValue(Object value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(Object rowKey, Object columnKey) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public V get(Object rowKey, Object columnKey) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void clear() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public V remove(Object rowKey, Object columnKey) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public V put(R rowKey, C columnKey, V value) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void putAll(Table<? extends R, ? extends C, ? extends V> table) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<Cell<R, C, V>> cellSet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<V> values() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
/*
|
||||
* Copyright (C) 2008 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.AbstractCollection;
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
|
||||
public abstract class ImmutableCollection<E> extends AbstractCollection<E> implements Serializable {
|
||||
ImmutableCollection() {}
|
||||
|
||||
public ImmutableList<E> asList() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public abstract static class Builder<E> {
|
||||
Builder() {}
|
||||
|
||||
public abstract Builder<E> add(E element);
|
||||
|
||||
public Builder<E> add(E... elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<E> addAll(Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<E> addAll(Iterator<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public abstract ImmutableCollection<E> build();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,101 @@
|
||||
/*
|
||||
* Copyright (C) 2007 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
public abstract class ImmutableList<E> extends ImmutableCollection<E>
|
||||
implements List<E>{
|
||||
|
||||
public static <E> ImmutableList<E> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> of(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> of(E e1, E e2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> of(E e1, E e2, E e3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> of(E e1, E e2, E e3, E e4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> of(
|
||||
E e1, E e2, E e3, E e4, E e5, E e6, E e7, E e8, E e9, E e10, E e11, E e12, E... others) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> copyOf(Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> copyOf(Collection<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> copyOf(Iterator<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> copyOf(E[] elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E extends Comparable<? super E>> ImmutableList<E> sortedCopyOf(
|
||||
Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableList<E> sortedCopyOf(
|
||||
Comparator<? super E> comparator, Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
ImmutableList() {}
|
||||
|
||||
public ImmutableList<E> reverse() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> Builder<E> builder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static final class Builder<E> extends ImmutableCollection.Builder<E> {
|
||||
@Override
|
||||
public Builder<E> add(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ImmutableList<E> build() {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,149 @@
|
||||
/*
|
||||
* Copyright (C) 2008 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Comparator;
|
||||
import java.util.Map;
|
||||
|
||||
public abstract class ImmutableMap<K, V> implements Map<K, V> {
|
||||
public static <K, V> ImmutableMap<K, V> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> of(K k1, V v1) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> of(K k1, V v1, K k2, V v2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> of(K k1, V v1, K k2, V v2, K k3, V v3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> of(K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> of(
|
||||
K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4, K k5, V v5) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> Builder<K, V> builder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> Builder<K, V> builderWithExpectedSize(int expectedSize) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder<K, V> {
|
||||
public Builder() {
|
||||
}
|
||||
|
||||
public Builder<K, V> put(K key, V value) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> put(Entry<? extends K, ? extends V> entry) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(Map<? extends K, ? extends V> map) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(Iterable<? extends Entry<? extends K, ? extends V>> entries) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> orderEntriesByValue(Comparator<? super V> valueComparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public ImmutableMap<K, V> build() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
public static <K, V> ImmutableMap<K, V> copyOf(Map<? extends K, ? extends V> map) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMap<K, V> copyOf(
|
||||
Iterable<? extends Entry<? extends K, ? extends V>> entries) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final V put(K k, V v) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final void putAll(Map<? extends K, ? extends V> map) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public final V remove(Object o) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final void clear() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsKey(Object key) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsValue(Object value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract V get(Object key);
|
||||
|
||||
@Override
|
||||
public ImmutableSet<Entry<K, V>> entrySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ImmutableSet<K> keySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ImmutableCollection<V> values() {
|
||||
return null;
|
||||
}
|
||||
|
||||
// public ImmutableSetMultimap<K, V> asMultimap() {
|
||||
// return null;
|
||||
// }
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* Copyright (C) 2008 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Comparator;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
|
||||
public abstract class ImmutableMultimap<K, V> extends AbstractMultimap<K, V> {
|
||||
public static <K, V> ImmutableMultimap<K, V> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> of(K k1, V v1) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> of(K k1, V v1, K k2, V v2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> of(K k1, V v1, K k2, V v2, K k3, V v3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> of(K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> of(
|
||||
K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4, K k5, V v5) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> Builder<K, V> builder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder<K, V> {
|
||||
public Builder() {
|
||||
}
|
||||
|
||||
public Builder<K, V> put(K key, V value) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> put(Entry<? extends K, ? extends V> entry) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(Iterable<? extends Entry<? extends K, ? extends V>> entries) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(K key, Iterable<? extends V> values) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(K key, V... values) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> putAll(Multimap<? extends K, ? extends V> multimap) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> orderKeysBy(Comparator<? super K> keyComparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<K, V> orderValuesBy(Comparator<? super V> valueComparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public ImmutableMultimap<K, V> build() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
public static <K, V> ImmutableMultimap<K, V> copyOf(Multimap<? extends K, ? extends V> multimap) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableMultimap<K, V> copyOf(
|
||||
Iterable<? extends Entry<? extends K, ? extends V>> entries) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ImmutableCollection<V> removeAll(Object key) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void clear() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract ImmutableCollection<V> get(K key);
|
||||
|
||||
public abstract ImmutableMultimap<V, K> inverse();
|
||||
|
||||
@Override
|
||||
public boolean containsKey(Object key) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int size() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,125 @@
|
||||
/*
|
||||
* Copyright (C) 2008 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
|
||||
public abstract class ImmutableMultiset<E> extends ImmutableCollection<E>
|
||||
implements Multiset<E> {
|
||||
|
||||
public static <E> ImmutableMultiset<E> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E e1, E e2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E e1, E e2, E e3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E e1, E e2, E e3, E e4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E e1, E e2, E e3, E e4, E e5) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> of(E e1, E e2, E e3, E e4, E e5, E e6, E... others) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> copyOf(E[] elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> copyOf(Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableMultiset<E> copyOf(Iterator<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(Object object) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final int add(E element, int occurrences) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final int remove(Object element, int occurrences) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final int setCount(E element, int count) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public final boolean setCount(E element, int oldCount, int newCount) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public abstract ImmutableSet<E> elementSet();
|
||||
|
||||
@Override
|
||||
public ImmutableSet<Entry<E>> entrySet() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> Builder<E> builder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder<E> extends ImmutableCollection.Builder<E> {
|
||||
public Builder() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Builder<E> add(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<E> addCopies(E element, int occurrences) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public Builder<E> setCount(E element, int count) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ImmutableMultiset<E> build() {
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,86 @@
|
||||
/*
|
||||
* Copyright (C) 2007 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.Set;
|
||||
|
||||
public abstract class ImmutableSet<E> extends ImmutableCollection<E> implements Set<E> {
|
||||
public static <E> ImmutableSet<E> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E e1, E e2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E e1, E e2, E e3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E e1, E e2, E e3, E e4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E e1, E e2, E e3, E e4, E e5) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> of(E e1, E e2, E e3, E e4, E e5, E e6, E... others) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> copyOf(Collection<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> copyOf(Iterable<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> copyOf(Iterator<? extends E> elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <E> ImmutableSet<E> copyOf(E[] elements) {
|
||||
return null;
|
||||
}
|
||||
|
||||
ImmutableSet() {}
|
||||
|
||||
public static <E> Builder<E> builder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder<E> extends ImmutableCollection.Builder<E> {
|
||||
public Builder() {
|
||||
}
|
||||
|
||||
public Builder<E> add(E element) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public ImmutableSet<E> build() {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,105 @@
|
||||
/*
|
||||
* Copyright (C) 2009 The Guava Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package com.google.common.collect;
|
||||
|
||||
import java.util.Comparator;
|
||||
import java.util.Map;
|
||||
import java.util.SortedMap;
|
||||
|
||||
public final class ImmutableSortedMap<K, V> extends ImmutableMap<K, V>{
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> of() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<? super K>, V> ImmutableSortedMap<K, V> of(K k1, V v1) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<? super K>, V> ImmutableSortedMap<K, V> of(
|
||||
K k1, V v1, K k2, V v2) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<? super K>, V> ImmutableSortedMap<K, V> of(
|
||||
K k1, V v1, K k2, V v2, K k3, V v3) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<? super K>, V> ImmutableSortedMap<K, V> of(
|
||||
K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<? super K>, V> ImmutableSortedMap<K, V> of(
|
||||
K k1, V v1, K k2, V v2, K k3, V v3, K k4, V v4, K k5, V v5) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> copyOf(Map<? extends K, ? extends V> map) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> copyOf(
|
||||
Map<? extends K, ? extends V> map, Comparator<? super K> comparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> copyOf(
|
||||
Iterable<? extends Entry<? extends K, ? extends V>> entries) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> copyOf(
|
||||
Iterable<? extends Entry<? extends K, ? extends V>> entries,
|
||||
Comparator<? super K> comparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> ImmutableSortedMap<K, V> copyOfSorted(SortedMap<K, ? extends V> map) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public V get(Object key) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int size() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<?>, V> Builder<K, V> naturalOrder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K, V> Builder<K, V> orderedBy(Comparator<K> comparator) {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static <K extends Comparable<?>, V> Builder<K, V> reverseOrder() {
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder<K, V> extends ImmutableMap.Builder<K, V> {
|
||||
public Builder(Comparator<? super K> comparator) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user