From 73fa680224694716dab5cc775a4587979121a384 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Mon, 26 Apr 2021 15:38:12 +0100 Subject: [PATCH 1/9] Add support for CSV-specified flow to or from fields. --- .../dataflow/internal/FlowSummaryImplSpecific.qll | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll index d28dd2206ac..bf6556712da 100644 --- a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll +++ b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll @@ -70,9 +70,23 @@ predicate summaryElement(DataFlowCallable c, string input, string output, string ) } +bindingset[name] +private FieldContent interpretField(string name) { + exists(string splitRegex, string package, string className, string fieldName | + splitRegex = "^(.*)\\.([^.]+)\\.([^.]+)$" and + package = name.regexpCapture(splitRegex, 1) and + className = name.regexpCapture(splitRegex, 2) and + fieldName = name.regexpCapture(splitRegex, 3) + | + result.getField().hasQualifiedName(package, className, fieldName) + ) +} + /** Gets the summary component for specification component `c`, if any. */ bindingset[c] SummaryComponent interpretComponentSpecific(string c) { + c.matches("Field %") and result = SummaryComponent::content(interpretField(c.splitAt(" ", 1))) + or c = "ArrayElement" and result = SummaryComponent::content(any(ArrayContent c0)) or c = "Element" and result = SummaryComponent::content(any(CollectionContent c0)) From 472a2a64ddda6dd4c59e707297f48d6eb3ffacf4 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Mon, 26 Apr 2021 15:39:09 +0100 Subject: [PATCH 2/9] Add models for Apache Commons tuples --- .../code/java/frameworks/apache/Lang.qll | 59 +++++ .../apache-commons-lang3/PairTest.java | 112 ++++++++++ .../apache-commons-lang3/TripleTest.java | 130 +++++++++++ .../commons/lang3/tuple/ImmutablePair.java | 195 +++++++++++++++++ .../commons/lang3/tuple/ImmutableTriple.java | 137 ++++++++++++ .../commons/lang3/tuple/MutablePair.java | 158 ++++++++++++++ .../commons/lang3/tuple/MutableTriple.java | 152 +++++++++++++ .../org/apache/commons/lang3/tuple/Pair.java | 204 ++++++++++++++++++ .../apache/commons/lang3/tuple/Triple.java | 164 ++++++++++++++ 9 files changed, 1311 insertions(+) create mode 100644 java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java create mode 100644 java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutablePair.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutableTriple.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutablePair.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutableTriple.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Pair.java create mode 100644 java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Triple.java diff --git a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll index 38469bf6b76..97f91f20a27 100644 --- a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll +++ b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll @@ -789,3 +789,62 @@ private class ApacheToStringBuilderModel extends SummaryModelCsv { ] } } + +/** + * Value-propagating models for `Pair`, `ImmutablePair` and `MutablePair`. + */ +private class ApachePairModel extends SummaryModelCsv { + override predicate row(string row) { + row = + [ + "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;left;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;setLeft;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;setRight;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;setValue;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutablePair.right of ReturnValue;value" + ] + } +} + +/** + * Value-propagating models for `Triple`, `ImmutableTriple` and `MutableTriple`. + */ +private class ApacheTripleModel extends SummaryModelCsv { + override predicate row(string row) { + row = + [ + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setLeft;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setMiddle;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setRight;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutableTriple.middle of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.MutableTriple.right of ReturnValue;value" + ] + } +} diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java new file mode 100644 index 00000000000..87aeb2b8f8c --- /dev/null +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java @@ -0,0 +1,112 @@ +import org.apache.commons.lang3.tuple.Pair; +import org.apache.commons.lang3.tuple.ImmutablePair; +import org.apache.commons.lang3.tuple.MutablePair; + +class PairTest { + String taint() { return "tainted"; } + + private static class IntSource { + static int taint() { return 0; } + } + + void sink(Object o) {} + + void test() throws Exception { + + ImmutablePair taintedLeft = ImmutablePair.of(taint(), "clean-right"); + ImmutablePair taintedRight = ImmutablePair.of("clean-left", taint()); + Pair taintedLeft2_ = ImmutablePair.left(taint()); + ImmutablePair taintedLeft2 = (ImmutablePair)taintedLeft2_; + Pair taintedRight2_ = ImmutablePair.right(taint()); + ImmutablePair taintedRight2 = (ImmutablePair)taintedRight2_; + + // Check flow through ImmutablePairs: + sink(taintedLeft.getLeft()); // $hasValueFlow + sink(taintedLeft.getRight()); + sink(taintedLeft.getKey()); // $hasValueFlow + sink(taintedLeft.getValue()); + sink(taintedLeft.left); // $hasValueFlow + sink(taintedLeft.right); + sink(taintedRight.getLeft()); + sink(taintedRight.getRight()); // $hasValueFlow + sink(taintedRight.getKey()); + sink(taintedRight.getValue()); // $hasValueFlow + sink(taintedRight.left); + sink(taintedRight.right); // $hasValueFlow + sink(taintedLeft2.getLeft()); // $hasValueFlow + sink(taintedLeft2.getRight()); + sink(taintedLeft2.getKey()); // $hasValueFlow + sink(taintedLeft2.getValue()); + sink(taintedLeft2.left); // $hasValueFlow + sink(taintedLeft2.right); + sink(taintedRight2.getLeft()); + sink(taintedRight2.getRight()); // $hasValueFlow + sink(taintedRight2.getKey()); + sink(taintedRight2.getValue()); // $hasValueFlow + sink(taintedRight2.left); + sink(taintedRight2.right); // $hasValueFlow + + // Check flow also works via an alias of type Pair: + sink(taintedLeft2_.getLeft()); // $hasValueFlow + sink(taintedLeft2_.getRight()); + sink(taintedLeft2_.getKey()); // $hasValueFlow + sink(taintedLeft2_.getValue()); + sink(taintedRight2_.getLeft()); + sink(taintedRight2_.getRight()); // $hasValueFlow + sink(taintedRight2_.getKey()); + sink(taintedRight2_.getValue()); // $hasValueFlow + + // Check flow through MutablePairs: + MutablePair taintedLeftMutable = MutablePair.of(taint(), "clean-right"); + MutablePair taintedRightMutable = MutablePair.of("clean-left", taint()); + MutablePair setTaintLeft = MutablePair.of("clean-left", "clean-right"); + setTaintLeft.setLeft(taint()); + MutablePair setTaintRight = MutablePair.of("clean-left", "clean-right"); + setTaintRight.setRight(taint()); + MutablePair setTaintValue = MutablePair.of("clean-left", "clean-right"); + setTaintValue.setValue(taint()); + + sink(taintedLeftMutable.getLeft()); // $hasValueFlow + sink(taintedLeftMutable.getRight()); + sink(taintedLeftMutable.getKey()); // $hasValueFlow + sink(taintedLeftMutable.getValue()); + sink(taintedLeftMutable.left); // $hasValueFlow + sink(taintedLeftMutable.right); + sink(taintedRightMutable.getLeft()); + sink(taintedRightMutable.getRight()); // $hasValueFlow + sink(taintedRightMutable.getKey()); + sink(taintedRightMutable.getValue()); // $hasValueFlow + sink(taintedRightMutable.left); + sink(taintedRightMutable.right); // $hasValueFlow + sink(setTaintLeft.getLeft()); // $hasValueFlow + sink(setTaintLeft.getRight()); + sink(setTaintLeft.getKey()); // $hasValueFlow + sink(setTaintLeft.getValue()); + sink(setTaintLeft.left); // $hasValueFlow + sink(setTaintLeft.right); + sink(setTaintRight.getLeft()); + sink(setTaintRight.getRight()); // $hasValueFlow + sink(setTaintRight.getKey()); + sink(setTaintRight.getValue()); // $hasValueFlow + sink(setTaintRight.left); + sink(setTaintRight.right); // $hasValueFlow + sink(setTaintValue.getLeft()); + sink(setTaintValue.getRight()); // $hasValueFlow + sink(setTaintValue.getKey()); + sink(setTaintValue.getValue()); // $hasValueFlow + sink(setTaintValue.left); + sink(setTaintValue.right); // $hasValueFlow + + // Check flow also works via an alias of type Pair: + Pair taintedLeftMutableAlias = taintedLeftMutable; + Pair taintedRightMutableAlias = taintedRightMutable; + sink(taintedLeftMutableAlias.getLeft()); // $hasValueFlow + sink(taintedLeftMutableAlias.getRight()); + sink(taintedLeftMutableAlias.getKey()); // $hasValueFlow + sink(taintedLeftMutableAlias.getValue()); + sink(taintedRightMutableAlias.getLeft()); + sink(taintedRightMutableAlias.getRight()); // $hasValueFlow + sink(taintedRightMutableAlias.getKey()); + sink(taintedRightMutableAlias.getValue()); // $hasValueFlow + } +} \ No newline at end of file diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java new file mode 100644 index 00000000000..a298b63f02c --- /dev/null +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java @@ -0,0 +1,130 @@ +import org.apache.commons.lang3.tuple.Triple; +import org.apache.commons.lang3.tuple.ImmutableTriple; +import org.apache.commons.lang3.tuple.MutableTriple; + +class TripleTest { + String taint() { return "tainted"; } + + private static class IntSource { + static int taint() { return 0; } + } + + void sink(Object o) {} + + void test() throws Exception { + + ImmutableTriple taintedLeft = ImmutableTriple.of(taint(), "clean-middle", "clean-right"); + ImmutableTriple taintedMiddle = ImmutableTriple.of("clean-left", taint(), "clean-right"); + ImmutableTriple taintedRight = ImmutableTriple.of("clean-left", "clean-middle", taint()); + + // Check flow through ImmutableTriples: + sink(taintedLeft.getLeft()); // $hasValueFlow + sink(taintedLeft.getMiddle()); + sink(taintedLeft.getRight()); + sink(taintedLeft.left); // $hasValueFlow + sink(taintedLeft.middle); + sink(taintedLeft.right); + sink(taintedMiddle.getLeft()); + sink(taintedMiddle.getMiddle()); // $hasValueFlow + sink(taintedMiddle.getRight()); + sink(taintedMiddle.left); + sink(taintedMiddle.middle); // $hasValueFlow + sink(taintedMiddle.right); + sink(taintedRight.getLeft()); + sink(taintedRight.getMiddle()); + sink(taintedRight.getRight()); // $hasValueFlow + sink(taintedRight.left); + sink(taintedRight.middle); + sink(taintedRight.right); // $hasValueFlow + + Triple taintedLeft2 = taintedLeft; + Triple taintedMiddle2 = taintedMiddle; + Triple taintedRight2 = taintedRight; + + // Check flow also works via an alias of type Triple: + sink(taintedLeft2.getLeft()); // $hasValueFlow + sink(taintedLeft2.getMiddle()); + sink(taintedLeft2.getRight()); + sink(taintedMiddle2.getLeft()); + sink(taintedMiddle2.getMiddle()); // $hasValueFlow + sink(taintedMiddle2.getRight()); + sink(taintedRight2.getLeft()); + sink(taintedRight2.getMiddle()); + sink(taintedRight2.getRight()); // $hasValueFlow + + MutableTriple mutableTaintedLeft = MutableTriple.of(taint(), "clean-middle", "clean-right"); + MutableTriple mutableTaintedMiddle = MutableTriple.of("clean-left", taint(), "clean-right"); + MutableTriple mutableTaintedRight = MutableTriple.of("clean-left", "clean-middle", taint()); + MutableTriple setTaintedLeft = MutableTriple.of("clean-left", "clean-middle", "clean-right"); + setTaintedLeft.setLeft(taint()); + MutableTriple setTaintedMiddle = MutableTriple.of("clean-left", "clean-middle", "clean-right"); + setTaintedMiddle.setMiddle(taint()); + MutableTriple setTaintedRight = MutableTriple.of("clean-left", "clean-middle", "clean-right"); + setTaintedRight.setRight(taint()); + + // Check flow through MutableTriples: + sink(mutableTaintedLeft.getLeft()); // $hasValueFlow + sink(mutableTaintedLeft.getMiddle()); + sink(mutableTaintedLeft.getRight()); + sink(mutableTaintedLeft.left); // $hasValueFlow + sink(mutableTaintedLeft.middle); + sink(mutableTaintedLeft.right); + sink(mutableTaintedMiddle.getLeft()); + sink(mutableTaintedMiddle.getMiddle()); // $hasValueFlow + sink(mutableTaintedMiddle.getRight()); + sink(mutableTaintedMiddle.left); + sink(mutableTaintedMiddle.middle); // $hasValueFlow + sink(mutableTaintedMiddle.right); + sink(mutableTaintedRight.getLeft()); + sink(mutableTaintedRight.getMiddle()); + sink(mutableTaintedRight.getRight()); // $hasValueFlow + sink(mutableTaintedRight.left); + sink(mutableTaintedRight.middle); + sink(mutableTaintedRight.right); // $hasValueFlow + sink(setTaintedLeft.getLeft()); // $hasValueFlow + sink(setTaintedLeft.getMiddle()); + sink(setTaintedLeft.getRight()); + sink(setTaintedLeft.left); // $hasValueFlow + sink(setTaintedLeft.middle); + sink(setTaintedLeft.right); + sink(setTaintedMiddle.getLeft()); + sink(setTaintedMiddle.getMiddle()); // $hasValueFlow + sink(setTaintedMiddle.getRight()); + sink(setTaintedMiddle.left); + sink(setTaintedMiddle.middle); // $hasValueFlow + sink(setTaintedMiddle.right); + sink(setTaintedRight.getLeft()); + sink(setTaintedRight.getMiddle()); + sink(setTaintedRight.getRight()); // $hasValueFlow + sink(setTaintedRight.left); + sink(setTaintedRight.middle); + sink(setTaintedRight.right); // $hasValueFlow + + Triple mutableTaintedLeft2 = mutableTaintedLeft; + Triple mutableTaintedMiddle2 = mutableTaintedMiddle; + Triple mutableTaintedRight2 = mutableTaintedRight; + Triple setTaintedLeft2 = setTaintedLeft; + Triple setTaintedMiddle2 = setTaintedMiddle; + Triple setTaintedRight2 = setTaintedRight; + + // Check flow also works via an alias of type Triple: + sink(mutableTaintedLeft2.getLeft()); // $hasValueFlow + sink(mutableTaintedLeft2.getMiddle()); + sink(mutableTaintedLeft2.getRight()); + sink(mutableTaintedMiddle2.getLeft()); + sink(mutableTaintedMiddle2.getMiddle()); // $hasValueFlow + sink(mutableTaintedMiddle2.getRight()); + sink(mutableTaintedRight2.getLeft()); + sink(mutableTaintedRight2.getMiddle()); + sink(mutableTaintedRight2.getRight()); // $hasValueFlow + sink(setTaintedLeft2.getLeft()); // $hasValueFlow + sink(setTaintedLeft2.getMiddle()); + sink(setTaintedLeft2.getRight()); + sink(setTaintedMiddle2.getLeft()); + sink(setTaintedMiddle2.getMiddle()); // $hasValueFlow + sink(setTaintedMiddle2.getRight()); + sink(setTaintedRight2.getLeft()); + sink(setTaintedRight2.getMiddle()); + sink(setTaintedRight2.getRight()); // $hasValueFlow + } +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutablePair.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutablePair.java new file mode 100644 index 00000000000..ee4cacd78a6 --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutablePair.java @@ -0,0 +1,195 @@ +/* + * 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.tuple; + +import java.util.Map; + +/** + *

An immutable pair consisting of two {@code Object} elements.

+ * + *

Although the implementation is immutable, there is no restriction on the objects + * that may be stored. If mutable objects are stored in the pair, then the pair + * itself effectively becomes mutable. The class is also {@code final}, so a subclass + * can not add undesirable behavior.

+ * + *

#ThreadSafe# if both paired objects are thread-safe

+ * + * @param the left element type + * @param the right element type + * + * @since 3.0 + */ +public final class ImmutablePair extends Pair { + + /** + * An empty array. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final ImmutablePair[] EMPTY_ARRAY = null; + + /** + * An immutable pair of nulls. + */ + // This is not defined with generics to avoid warnings in call sites. + @SuppressWarnings("rawtypes") + private static final ImmutablePair NULL = null; + + /** Serialization version */ + private static final long serialVersionUID = 4954918890077093841L; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static ImmutablePair[] emptyArray() { + return null; + } + + /** + *

Creates an immutable pair of two objects inferring the generic types.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param left the left element, may be null + * @return a pair formed from the two parameters, not null + * @since 3.11 + */ + public static Pair left(final L left) { + return null; + } + + /** + * Returns an immutable pair of nulls. + * + * @param the left element of this pair. Value is {@code null}. + * @param the right element of this pair. Value is {@code null}. + * @return an immutable pair of nulls. + * @since 3.6 + */ + public static ImmutablePair nullPair() { + return null; + } + + /** + *

Creates an immutable pair of two objects inferring the generic types.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param left the left element, may be null + * @param right the right element, may be null + * @return a pair formed from the two parameters, not null + */ + public static ImmutablePair of(final L left, final R right) { + return null; + } + + /** + *

Creates an immutable pair from an existing pair.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param pair the existing pair. + * @return a pair formed from the two parameters, not null + * @since 3.10 + */ + public static ImmutablePair of(final Map.Entry pair) { + return null; + } + + /** + *

Creates an immutable pair of two objects inferring the generic types.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param right the right element, may be null + * @return a pair formed from the two parameters, not null + * @since 3.11 + */ + public static Pair right(final R right) { + return null; + } + + /** Left object */ + public final L left; + + /** Right object */ + public final R right; + + /** + * Create a new pair instance. + * + * @param left the left value, may be null + * @param right the right value, may be null + */ + public ImmutablePair(final L left, final R right) { + this.left = null; + this.right = null; + } + + /** + * {@inheritDoc} + */ + @Override + public L getLeft() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public R getRight() { + return null; + } + + /** + *

Throws {@code UnsupportedOperationException}.

+ * + *

This pair is immutable, so this operation is not supported.

+ * + * @param value the value to set + * @return never + * @throws UnsupportedOperationException as this operation is not supported + */ + @Override + public R setValue(final R value) { + return null; + } + +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutableTriple.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutableTriple.java new file mode 100644 index 00000000000..846fcbd9052 --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/ImmutableTriple.java @@ -0,0 +1,137 @@ +/* + * 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.tuple; + +/** + *

An immutable triple consisting of three {@code Object} elements.

+ * + *

Although the implementation is immutable, there is no restriction on the objects + * that may be stored. If mutable objects are stored in the triple, then the triple + * itself effectively becomes mutable. The class is also {@code final}, so a subclass + * can not add undesirable behavior.

+ * + *

#ThreadSafe# if all three objects are thread-safe

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * + * @since 3.2 + */ +public final class ImmutableTriple extends Triple { + + /** + * An empty array. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final ImmutableTriple[] EMPTY_ARRAY = null; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the middle element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static ImmutableTriple[] emptyArray() { + return null; + } + + /** + * Returns an immutable triple of nulls. + * + * @param the left element of this triple. Value is {@code null}. + * @param the middle element of this triple. Value is {@code null}. + * @param the right element of this triple. Value is {@code null}. + * @return an immutable triple of nulls. + * @since 3.6 + */ + public static ImmutableTriple nullTriple() { + return null; + } + + /** + *

Obtains an immutable triple of three objects inferring the generic types.

+ * + *

This factory allows the triple to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * @param left the left element, may be null + * @param middle the middle element, may be null + * @param right the right element, may be null + * @return a triple formed from the three parameters, not null + */ + public static ImmutableTriple of(final L left, final M middle, final R right) { + return null; + } + /** Left object */ + public final L left; + /** Middle object */ + public final M middle; + + /** Right object */ + public final R right; + + /** + * Create a new triple instance. + * + * @param left the left value, may be null + * @param middle the middle value, may be null + * @param right the right value, may be null + */ + public ImmutableTriple(final L left, final M middle, final R right) { + this.left = null; + this.middle = null; + this.right = null; + } + + //----------------------------------------------------------------------- + /** + * {@inheritDoc} + */ + @Override + public L getLeft() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public M getMiddle() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public R getRight() { + return null; + } +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutablePair.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutablePair.java new file mode 100644 index 00000000000..5826a2145fc --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutablePair.java @@ -0,0 +1,158 @@ +/* + * 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.tuple; + +import java.util.Map; + +/** + *

A mutable pair consisting of two {@code Object} elements.

+ * + *

Not #ThreadSafe#

+ * + * @param the left element type + * @param the right element type + * + * @since 3.0 + */ +public class MutablePair extends Pair { + + /** + * An empty array. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final MutablePair[] EMPTY_ARRAY = null; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static MutablePair[] emptyArray() { + return null; + } + + /** + *

Creates a mutable pair of two objects inferring the generic types.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param left the left element, may be null + * @param right the right element, may be null + * @return a pair formed from the two parameters, not null + */ + public static MutablePair of(final L left, final R right) { + return null; + } + + /** + *

Creates a mutable pair from an existing pair.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param pair the existing pair. + * @return a pair formed from the two parameters, not null + */ + public static MutablePair of(final Map.Entry pair) { + return null; + } + + /** Left object */ + public L left; + + /** Right object */ + public R right; + + /** + * Create a new pair instance of two nulls. + */ + public MutablePair() { + } + + /** + * Create a new pair instance. + * + * @param left the left value, may be null + * @param right the right value, may be null + */ + public MutablePair(final L left, final R right) { + this.left = null; + this.right = null; + } + + //----------------------------------------------------------------------- + /** + * {@inheritDoc} + */ + @Override + public L getLeft() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public R getRight() { + return null; + } + + /** + * Sets the left element of the pair. + * + * @param left the new value of the left element, may be null + */ + public void setLeft(final L left) { + + } + + /** + * Sets the right element of the pair. + * + * @param right the new value of the right element, may be null + */ + public void setRight(final R right) { + + } + + /** + * Sets the {@code Map.Entry} value. + * This sets the right element of the pair. + * + * @param value the right value to set, not null + * @return the old value for the right element + */ + @Override + public R setValue(final R value) { + return null; + } + +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutableTriple.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutableTriple.java new file mode 100644 index 00000000000..dc489c44293 --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/MutableTriple.java @@ -0,0 +1,152 @@ +/* + * 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.tuple; + +/** + *

A mutable triple consisting of three {@code Object} elements.

+ * + *

Not #ThreadSafe#

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * + * @since 3.2 + */ +public class MutableTriple extends Triple { + + /** + * The empty array singleton. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final MutableTriple[] EMPTY_ARRAY = null; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the middle element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static MutableTriple[] emptyArray() { + return null; + } + + /** + *

Obtains a mutable triple of three objects inferring the generic types.

+ * + *

This factory allows the triple to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * @param left the left element, may be null + * @param middle the middle element, may be null + * @param right the right element, may be null + * @return a triple formed from the three parameters, not null + */ + public static MutableTriple of(final L left, final M middle, final R right) { + return null; + } + /** Left object */ + public L left; + /** Middle object */ + public M middle; + + /** Right object */ + public R right; + + /** + * Create a new triple instance of three nulls. + */ + public MutableTriple() { + } + + /** + * Create a new triple instance. + * + * @param left the left value, may be null + * @param middle the middle value, may be null + * @param right the right value, may be null + */ + public MutableTriple(final L left, final M middle, final R right) { + this.left = null; + this.middle = null; + this.right = null; + } + + //----------------------------------------------------------------------- + /** + * {@inheritDoc} + */ + @Override + public L getLeft() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public M getMiddle() { + return null; + } + + /** + * {@inheritDoc} + */ + @Override + public R getRight() { + return null; + } + + /** + * Sets the left element of the triple. + * + * @param left the new value of the left element, may be null + */ + public void setLeft(final L left) { + + } + + /** + * Sets the middle element of the triple. + * + * @param middle the new value of the middle element, may be null + */ + public void setMiddle(final M middle) { + + } + + /** + * Sets the right element of the triple. + * + * @param right the new value of the right element, may be null + */ + public void setRight(final R right) { + + } +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Pair.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Pair.java new file mode 100644 index 00000000000..1f23f886e5b --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Pair.java @@ -0,0 +1,204 @@ +/* + * 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.tuple; + +import java.io.Serializable; +import java.util.Map; + +/** + *

A pair consisting of two elements.

+ * + *

This class is an abstract implementation defining the basic API. + * It refers to the elements as 'left' and 'right'. It also implements the + * {@code Map.Entry} interface where the key is 'left' and the value is 'right'.

+ * + *

Subclass implementations may be mutable or immutable. + * However, there is no restriction on the type of the stored objects that may be stored. + * If mutable objects are stored in the pair, then the pair itself effectively becomes mutable.

+ * + * @param the left element type + * @param the right element type + * + * @since 3.0 + */ +public abstract class Pair implements Map.Entry, Comparable>, Serializable { + + /** Serialization version */ + private static final long serialVersionUID = 4954918890077093841L; + + /** + * An empty array. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final Pair[] EMPTY_ARRAY = null; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static Pair[] emptyArray() { + return null; + } + + /** + *

Creates an immutable pair of two objects inferring the generic types.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param left the left element, may be null + * @param right the right element, may be null + * @return a pair formed from the two parameters, not null + */ + public static Pair of(final L left, final R right) { + return null; + } + + /** + *

Creates an immutable pair from an existing pair.

+ * + *

This factory allows the pair to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the right element type + * @param pair the existing pair. + * @return a pair formed from the two parameters, not null + * @since 3.10 + */ + public static Pair of(final Map.Entry pair) { + return null; + } + + //----------------------------------------------------------------------- + /** + *

Compares the pair based on the left element followed by the right element. + * The types must be {@code Comparable}.

+ * + * @param other the other pair, not null + * @return negative if this is less, zero if equal, positive if greater + */ + @Override + public int compareTo(final Pair other) { + return 0; + } + + /** + *

Compares this pair to another based on the two elements.

+ * + * @param obj the object to compare to, null returns false + * @return true if the elements of the pair are equal + */ + @Override + public boolean equals(final Object obj) { + return false; + } + + /** + *

Gets the key from this pair.

+ * + *

This method implements the {@code Map.Entry} interface returning the + * left element as the key.

+ * + * @return the left element as the key, may be null + */ + @Override + public final L getKey() { + return null; + } + + //----------------------------------------------------------------------- + /** + *

Gets the left element from this pair.

+ * + *

When treated as a key-value pair, this is the key.

+ * + * @return the left element, may be null + */ + public abstract L getLeft(); + + /** + *

Gets the right element from this pair.

+ * + *

When treated as a key-value pair, this is the value.

+ * + * @return the right element, may be null + */ + public abstract R getRight(); + + /** + *

Gets the value from this pair.

+ * + *

This method implements the {@code Map.Entry} interface returning the + * right element as the value.

+ * + * @return the right element as the value, may be null + */ + @Override + public R getValue() { + return null; + } + + /** + *

Returns a suitable hash code. + * The hash code follows the definition in {@code Map.Entry}.

+ * + * @return the hash code + */ + @Override + public int hashCode() { + return 0; + } + + /** + *

Returns a String representation of this pair using the format {@code ($left,$right)}.

+ * + * @return a string describing this object, not null + */ + @Override + public String toString() { + return ""; + } + + /** + *

Formats the receiver using the given format.

+ * + *

This uses {@link java.util.Formattable} to perform the formatting. Two variables may + * be used to embed the left and right elements. Use {@code %1$s} for the left + * element (key) and {@code %2$s} for the right element (value). + * The default format used by {@code toString()} is {@code (%1$s,%2$s)}.

+ * + * @param format the format string, optionally containing {@code %1$s} and {@code %2$s}, not null + * @return the formatted string, not null + */ + public String toString(final String format) { + return ""; + } + +} \ No newline at end of file diff --git a/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Triple.java b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Triple.java new file mode 100644 index 00000000000..d8453f7e3cd --- /dev/null +++ b/java/ql/test/stubs/apache-commons-lang3-3.7/org/apache/commons/lang3/tuple/Triple.java @@ -0,0 +1,164 @@ +/* + * 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.tuple; + +import java.io.Serializable; + +/** + *

A triple consisting of three elements.

+ * + *

This class is an abstract implementation defining the basic API. + * It refers to the elements as 'left', 'middle' and 'right'.

+ * + *

Subclass implementations may be mutable or immutable. + * However, there is no restriction on the type of the stored objects that may be stored. + * If mutable objects are stored in the triple, then the triple itself effectively becomes mutable.

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * + * @since 3.2 + */ +public abstract class Triple implements Comparable>, Serializable { + + /** + * An empty array. + *

+ * Consider using {@link #emptyArray()} to avoid generics warnings. + *

+ * + * @since 3.10. + */ + public static final Triple[] EMPTY_ARRAY = null; + + /** + * Returns the empty array singleton that can be assigned without compiler warning. + * + * @param the left element type + * @param the middle element type + * @param the right element type + * @return the empty array singleton that can be assigned without compiler warning. + * + * @since 3.10. + */ + @SuppressWarnings("unchecked") + public static Triple[] emptyArray() { + return null; + } + + /** + *

Obtains an immutable triple of three objects inferring the generic types.

+ * + *

This factory allows the triple to be created using inference to + * obtain the generic types.

+ * + * @param the left element type + * @param the middle element type + * @param the right element type + * @param left the left element, may be null + * @param middle the middle element, may be null + * @param right the right element, may be null + * @return a triple formed from the three parameters, not null + */ + public static Triple of(final L left, final M middle, final R right) { + return null; + } + + //----------------------------------------------------------------------- + /** + *

Compares the triple based on the left element, followed by the middle element, + * finally the right element. + * The types must be {@code Comparable}.

+ * + * @param other the other triple, not null + * @return negative if this is less, zero if equal, positive if greater + */ + @Override + public int compareTo(final Triple other) { + return 0; + } + + /** + *

Compares this triple to another based on the three elements.

+ * + * @param obj the object to compare to, null returns false + * @return true if the elements of the triple are equal + */ + @Override + public boolean equals(final Object obj) { + return false; + } + + //----------------------------------------------------------------------- + /** + *

Gets the left element from this triple.

+ * + * @return the left element, may be null + */ + public abstract L getLeft(); + + /** + *

Gets the middle element from this triple.

+ * + * @return the middle element, may be null + */ + public abstract M getMiddle(); + + /** + *

Gets the right element from this triple.

+ * + * @return the right element, may be null + */ + public abstract R getRight(); + + /** + *

Returns a suitable hash code.

+ * + * @return the hash code + */ + @Override + public int hashCode() { + return 0; + } + + /** + *

Returns a String representation of this triple using the format {@code ($left,$middle,$right)}.

+ * + * @return a string describing this object, not null + */ + @Override + public String toString() { + return ""; + } + + /** + *

Formats the receiver using the given format.

+ * + *

This uses {@link java.util.Formattable} to perform the formatting. Three variables may + * be used to embed the left and right elements. Use {@code %1$s} for the left + * element, {@code %2$s} for the middle and {@code %3$s} for the right element. + * The default format used by {@code toString()} is {@code (%1$s,%2$s,%3$s)}.

+ * + * @param format the format string, optionally containing {@code %1$s}, {@code %2$s} and {@code %3$s}, not null + * @return the formatted string, not null + */ + public String toString(final String format) { + return ""; + } + +} From 365aab9bd9fd10035d4f128dc1e3cb053715db1f Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Tue, 27 Apr 2021 12:18:20 +0100 Subject: [PATCH 3/9] Improve matching of Field specifiers; add Field recognition in tests From eebaab8fe9216c1175bd7dc986e7d04592979e4f Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Tue, 11 May 2021 12:05:28 +0100 Subject: [PATCH 4/9] Order left and right consistently --- java/ql/src/semmle/code/java/frameworks/apache/Lang.qll | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll index 97f91f20a27..99463a51e6d 100644 --- a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll +++ b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll @@ -805,8 +805,8 @@ private class ApachePairModel extends SummaryModelCsv { "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;left;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", "org.apache.commons.lang3.tuple;MutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", From fbaa3821581dcd37c67380b1fa4575bd6d40774d Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Tue, 11 May 2021 12:05:38 +0100 Subject: [PATCH 5/9] Add tests for Pair.of and Triple.of --- .../frameworks/apache-commons-lang3/PairTest.java | 10 ++++++++++ .../apache-commons-lang3/TripleTest.java | 15 +++++++++++++++ 2 files changed, 25 insertions(+) diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java index 87aeb2b8f8c..e86d0461145 100644 --- a/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java @@ -19,6 +19,8 @@ class PairTest { ImmutablePair taintedLeft2 = (ImmutablePair)taintedLeft2_; Pair taintedRight2_ = ImmutablePair.right(taint()); ImmutablePair taintedRight2 = (ImmutablePair)taintedRight2_; + Pair taintedLeft3 = Pair.of(taint(), "clean-right"); + Pair taintedRight3 = Pair.of("clean-left", taint()); // Check flow through ImmutablePairs: sink(taintedLeft.getLeft()); // $hasValueFlow @@ -45,6 +47,14 @@ class PairTest { sink(taintedRight2.getValue()); // $hasValueFlow sink(taintedRight2.left); sink(taintedRight2.right); // $hasValueFlow + sink(taintedLeft3.getLeft()); // $hasValueFlow + sink(taintedLeft3.getRight()); + sink(taintedLeft3.getKey()); // $hasValueFlow + sink(taintedLeft3.getValue()); + sink(taintedRight3.getLeft()); + sink(taintedRight3.getRight()); // $hasValueFlow + sink(taintedRight3.getKey()); + sink(taintedRight3.getValue()); // $hasValueFlow // Check flow also works via an alias of type Pair: sink(taintedLeft2_.getLeft()); // $hasValueFlow diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java index a298b63f02c..2057f34ac96 100644 --- a/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java @@ -52,6 +52,21 @@ class TripleTest { sink(taintedRight2.getMiddle()); sink(taintedRight2.getRight()); // $hasValueFlow + // Check flow via Triple.of: + Triple taintedLeft3 = Triple.of(taint(), "clean-middle", "clean-right"); + Triple taintedMiddle3 = Triple.of("clean-left", taint(), "clean-right"); + Triple taintedRight3 = Triple.of("clean-left", "clean-middle", taint()); + + sink(taintedLeft3.getLeft()); // $hasValueFlow + sink(taintedLeft3.getMiddle()); + sink(taintedLeft3.getRight()); + sink(taintedMiddle3.getLeft()); + sink(taintedMiddle3.getMiddle()); // $hasValueFlow + sink(taintedMiddle3.getRight()); + sink(taintedRight3.getLeft()); + sink(taintedRight3.getMiddle()); + sink(taintedRight3.getRight()); // $hasValueFlow + MutableTriple mutableTaintedLeft = MutableTriple.of(taint(), "clean-middle", "clean-right"); MutableTriple mutableTaintedMiddle = MutableTriple.of("clean-left", taint(), "clean-right"); MutableTriple mutableTaintedRight = MutableTriple.of("clean-left", "clean-middle", taint()); From 2cc1f468711fe5c88c3795f46aa0ef5cea683f44 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Tue, 11 May 2021 12:16:44 +0100 Subject: [PATCH 6/9] Model constructors for (Imm|M)utable(Pair|Triple) --- .../code/java/frameworks/apache/Lang.qll | 10 ++++++ .../apache-commons-lang3/PairTest.java | 28 +++++++++++++++ .../apache-commons-lang3/TripleTest.java | 36 +++++++++++++++++++ 3 files changed, 74 insertions(+) diff --git a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll index 99463a51e6d..34ec3dc391e 100644 --- a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll +++ b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll @@ -803,12 +803,16 @@ private class ApachePairModel extends SummaryModelCsv { "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];value", "org.apache.commons.lang3.tuple;ImmutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;left;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", "org.apache.commons.lang3.tuple;MutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;MutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;MutablePair;false;setLeft;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];value", @@ -830,12 +834,18 @@ private class ApacheTripleModel extends SummaryModelCsv { "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of Argument[-1];value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.left of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.right of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];value", "org.apache.commons.lang3.tuple;MutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;MutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];ReturnValue;value", "org.apache.commons.lang3.tuple;MutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];ReturnValue;value", diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java index e86d0461145..6db15beb181 100644 --- a/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/PairTest.java @@ -21,6 +21,8 @@ class PairTest { ImmutablePair taintedRight2 = (ImmutablePair)taintedRight2_; Pair taintedLeft3 = Pair.of(taint(), "clean-right"); Pair taintedRight3 = Pair.of("clean-left", taint()); + ImmutablePair taintedLeft4 = new ImmutablePair(taint(), "clean-right"); + ImmutablePair taintedRight4 = new ImmutablePair("clean-left", taint()); // Check flow through ImmutablePairs: sink(taintedLeft.getLeft()); // $hasValueFlow @@ -55,6 +57,18 @@ class PairTest { sink(taintedRight3.getRight()); // $hasValueFlow sink(taintedRight3.getKey()); sink(taintedRight3.getValue()); // $hasValueFlow + sink(taintedLeft4.getLeft()); // $hasValueFlow + sink(taintedLeft4.getRight()); + sink(taintedLeft4.getKey()); // $hasValueFlow + sink(taintedLeft4.getValue()); + sink(taintedLeft4.left); // $hasValueFlow + sink(taintedLeft4.right); + sink(taintedRight4.getLeft()); + sink(taintedRight4.getRight()); // $hasValueFlow + sink(taintedRight4.getKey()); + sink(taintedRight4.getValue()); // $hasValueFlow + sink(taintedRight4.left); + sink(taintedRight4.right); // $hasValueFlow // Check flow also works via an alias of type Pair: sink(taintedLeft2_.getLeft()); // $hasValueFlow @@ -75,6 +89,8 @@ class PairTest { setTaintRight.setRight(taint()); MutablePair setTaintValue = MutablePair.of("clean-left", "clean-right"); setTaintValue.setValue(taint()); + MutablePair taintedLeftMutableConstructed = new MutablePair(taint(), "clean-right"); + MutablePair taintedRightMutableConstructed = new MutablePair("clean-left", taint()); sink(taintedLeftMutable.getLeft()); // $hasValueFlow sink(taintedLeftMutable.getRight()); @@ -106,6 +122,18 @@ class PairTest { sink(setTaintValue.getValue()); // $hasValueFlow sink(setTaintValue.left); sink(setTaintValue.right); // $hasValueFlow + sink(taintedLeftMutableConstructed.getLeft()); // $hasValueFlow + sink(taintedLeftMutableConstructed.getRight()); + sink(taintedLeftMutableConstructed.getKey()); // $hasValueFlow + sink(taintedLeftMutableConstructed.getValue()); + sink(taintedLeftMutableConstructed.left); // $hasValueFlow + sink(taintedLeftMutableConstructed.right); + sink(taintedRightMutableConstructed.getLeft()); + sink(taintedRightMutableConstructed.getRight()); // $hasValueFlow + sink(taintedRightMutableConstructed.getKey()); + sink(taintedRightMutableConstructed.getValue()); // $hasValueFlow + sink(taintedRightMutableConstructed.left); + sink(taintedRightMutableConstructed.right); // $hasValueFlow // Check flow also works via an alias of type Pair: Pair taintedLeftMutableAlias = taintedLeftMutable; diff --git a/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java index 2057f34ac96..b6f9c53cc7e 100644 --- a/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java +++ b/java/ql/test/library-tests/frameworks/apache-commons-lang3/TripleTest.java @@ -67,6 +67,21 @@ class TripleTest { sink(taintedRight3.getMiddle()); sink(taintedRight3.getRight()); // $hasValueFlow + // Check flow via constructor: + ImmutableTriple taintedLeft4 = new ImmutableTriple(taint(), "clean-middle", "clean-right"); + ImmutableTriple taintedMiddle4 = new ImmutableTriple("clean-left", taint(), "clean-right"); + ImmutableTriple taintedRight4 = new ImmutableTriple("clean-left", "clean-middle", taint()); + + sink(taintedLeft4.getLeft()); // $hasValueFlow + sink(taintedLeft4.getMiddle()); + sink(taintedLeft4.getRight()); + sink(taintedMiddle4.getLeft()); + sink(taintedMiddle4.getMiddle()); // $hasValueFlow + sink(taintedMiddle4.getRight()); + sink(taintedRight4.getLeft()); + sink(taintedRight4.getMiddle()); + sink(taintedRight4.getRight()); // $hasValueFlow + MutableTriple mutableTaintedLeft = MutableTriple.of(taint(), "clean-middle", "clean-right"); MutableTriple mutableTaintedMiddle = MutableTriple.of("clean-left", taint(), "clean-right"); MutableTriple mutableTaintedRight = MutableTriple.of("clean-left", "clean-middle", taint()); @@ -76,6 +91,9 @@ class TripleTest { setTaintedMiddle.setMiddle(taint()); MutableTriple setTaintedRight = MutableTriple.of("clean-left", "clean-middle", "clean-right"); setTaintedRight.setRight(taint()); + MutableTriple mutableTaintedLeftConstructed = new MutableTriple(taint(), "clean-middle", "clean-right"); + MutableTriple mutableTaintedMiddleConstructed = new MutableTriple("clean-left", taint(), "clean-right"); + MutableTriple mutableTaintedRightConstructed = new MutableTriple("clean-left", "clean-middle", taint()); // Check flow through MutableTriples: sink(mutableTaintedLeft.getLeft()); // $hasValueFlow @@ -114,6 +132,24 @@ class TripleTest { sink(setTaintedRight.left); sink(setTaintedRight.middle); sink(setTaintedRight.right); // $hasValueFlow + sink(mutableTaintedLeftConstructed.getLeft()); // $hasValueFlow + sink(mutableTaintedLeftConstructed.getMiddle()); + sink(mutableTaintedLeftConstructed.getRight()); + sink(mutableTaintedLeftConstructed.left); // $hasValueFlow + sink(mutableTaintedLeftConstructed.middle); + sink(mutableTaintedLeftConstructed.right); + sink(mutableTaintedMiddleConstructed.getLeft()); + sink(mutableTaintedMiddleConstructed.getMiddle()); // $hasValueFlow + sink(mutableTaintedMiddleConstructed.getRight()); + sink(mutableTaintedMiddleConstructed.left); + sink(mutableTaintedMiddleConstructed.middle); // $hasValueFlow + sink(mutableTaintedMiddleConstructed.right); + sink(mutableTaintedRightConstructed.getLeft()); + sink(mutableTaintedRightConstructed.getMiddle()); + sink(mutableTaintedRightConstructed.getRight()); // $hasValueFlow + sink(mutableTaintedRightConstructed.left); + sink(mutableTaintedRightConstructed.middle); + sink(mutableTaintedRightConstructed.right); // $hasValueFlow Triple mutableTaintedLeft2 = mutableTaintedLeft; Triple mutableTaintedMiddle2 = mutableTaintedMiddle; From 5cf0243dd09f826bd0f04f06baa63a0144493219 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Tue, 11 May 2021 12:19:17 +0100 Subject: [PATCH 7/9] Add change note --- java/change-notes/2021-05-11-apache-tuples.md | 2 ++ 1 file changed, 2 insertions(+) create mode 100644 java/change-notes/2021-05-11-apache-tuples.md diff --git a/java/change-notes/2021-05-11-apache-tuples.md b/java/change-notes/2021-05-11-apache-tuples.md new file mode 100644 index 00000000000..2eab20ecd4f --- /dev/null +++ b/java/change-notes/2021-05-11-apache-tuples.md @@ -0,0 +1,2 @@ +lgtm,codescanning +* Added models for the Apache Commons Lang tuple types (Pair, Triple and their immutable and mutable implementations). This may lead to more results from any query using data-flow analysis where a relevant path uses one of these container types. From 74b2a2c7a6fb21ccc56c1958208af0a341d41e74 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Thu, 17 Jun 2021 12:45:44 +0100 Subject: [PATCH 8/9] Improve style of interpretField --- .../internal/FlowSummaryImplSpecific.qll | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll index bf6556712da..f2a54793b7a 100644 --- a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll +++ b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll @@ -70,14 +70,13 @@ predicate summaryElement(DataFlowCallable c, string input, string output, string ) } -bindingset[name] -private FieldContent interpretField(string name) { - exists(string splitRegex, string package, string className, string fieldName | - splitRegex = "^(.*)\\.([^.]+)\\.([^.]+)$" and - package = name.regexpCapture(splitRegex, 1) and - className = name.regexpCapture(splitRegex, 2) and - fieldName = name.regexpCapture(splitRegex, 3) - | +private FieldContent parseField(string c) { + External::specSplit(_, c, _) and + exists(string fieldRegex, string package, string className, string fieldName | + fieldRegex = "^Field (.*)\\.([^.]+)\\.([^.]+)$" and + package = c.regexpCapture(fieldRegex, 1) and + className = c.regexpCapture(fieldRegex, 2) and + fieldName = c.regexpCapture(fieldRegex, 3) and result.getField().hasQualifiedName(package, className, fieldName) ) } @@ -85,7 +84,7 @@ private FieldContent interpretField(string name) { /** Gets the summary component for specification component `c`, if any. */ bindingset[c] SummaryComponent interpretComponentSpecific(string c) { - c.matches("Field %") and result = SummaryComponent::content(interpretField(c.splitAt(" ", 1))) + result = SummaryComponent::content(parseField(c)) or c = "ArrayElement" and result = SummaryComponent::content(any(ArrayContent c0)) or From d28c95d16c4a0cc7d7c48f8e890e94c2e43968e7 Mon Sep 17 00:00:00 2001 From: Chris Smowton Date: Thu, 17 Jun 2021 12:49:25 +0100 Subject: [PATCH 9/9] Field foo of -> Field[foo] of --- .../internal/FlowSummaryImplSpecific.qll | 2 +- .../code/java/frameworks/apache/Lang.qll | 94 +++++++++---------- 2 files changed, 48 insertions(+), 48 deletions(-) diff --git a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll index f2a54793b7a..974982a9c29 100644 --- a/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll +++ b/java/ql/src/semmle/code/java/dataflow/internal/FlowSummaryImplSpecific.qll @@ -73,7 +73,7 @@ predicate summaryElement(DataFlowCallable c, string input, string output, string private FieldContent parseField(string c) { External::specSplit(_, c, _) and exists(string fieldRegex, string package, string className, string fieldName | - fieldRegex = "^Field (.*)\\.([^.]+)\\.([^.]+)$" and + fieldRegex = "^Field\\[(.*)\\.([^.]+)\\.([^.]+)\\]$" and package = c.regexpCapture(fieldRegex, 1) and className = c.regexpCapture(fieldRegex, 2) and fieldName = c.regexpCapture(fieldRegex, 3) and diff --git a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll index 34ec3dc391e..bf47d627686 100644 --- a/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll +++ b/java/ql/src/semmle/code/java/frameworks/apache/Lang.qll @@ -797,29 +797,29 @@ private class ApachePairModel extends SummaryModelCsv { override predicate row(string row) { row = [ - "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutablePair.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutablePair.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;left;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutablePair.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutablePair.right of ReturnValue;value", - "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutablePair;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;MutablePair;false;getRight;;;Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;MutablePair;false;setLeft;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutablePair;false;setRight;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutablePair;false;setValue;;;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutablePair.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutablePair.right of ReturnValue;value" + "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getKey;;;Field[org.apache.commons.lang3.tuple.MutablePair.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;getValue;;;Field[org.apache.commons.lang3.tuple.MutablePair.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;Pair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;ImmutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;getLeft;;;Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;getRight;;;Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;left;;;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;right;;;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutablePair.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutablePair.right] of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.MutablePair.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;MutablePair;(java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.MutablePair.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;getLeft;;;Field[org.apache.commons.lang3.tuple.MutablePair.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;getRight;;;Field[org.apache.commons.lang3.tuple.MutablePair.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;setLeft;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutablePair.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;setRight;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutablePair.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;setValue;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutablePair.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.MutablePair.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutablePair;false;of;(java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.MutablePair.right] of ReturnValue;value" ] } } @@ -831,30 +831,30 @@ private class ApacheTripleModel extends SummaryModelCsv { override predicate row(string row) { row = [ - "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", - "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of Argument[-1];value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.ImmutableTriple.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.ImmutableTriple.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.ImmutableTriple.middle of ReturnValue;value", - "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.ImmutableTriple.right of ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;getLeft;;;Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;getMiddle;;;Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;getRight;;;Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;setLeft;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;setMiddle;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.middle of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;setRight;;;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.right of Argument[-1];value", - "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field org.apache.commons.lang3.tuple.MutableTriple.left of ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field org.apache.commons.lang3.tuple.MutableTriple.middle of ReturnValue;value", - "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field org.apache.commons.lang3.tuple.MutableTriple.right of ReturnValue;value" + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutableTriple.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutableTriple.middle] of ReturnValue;value", + "org.apache.commons.lang3.tuple;Triple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field[org.apache.commons.lang3.tuple.ImmutableTriple.right] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutableTriple.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutableTriple.middle] of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;ImmutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field[org.apache.commons.lang3.tuple.ImmutableTriple.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getLeft;;;Field[org.apache.commons.lang3.tuple.ImmutableTriple.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getMiddle;;;Field[org.apache.commons.lang3.tuple.ImmutableTriple.middle] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;getRight;;;Field[org.apache.commons.lang3.tuple.ImmutableTriple.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.ImmutableTriple.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.ImmutableTriple.middle] of ReturnValue;value", + "org.apache.commons.lang3.tuple;ImmutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field[org.apache.commons.lang3.tuple.ImmutableTriple.right] of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.MutableTriple.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.MutableTriple.middle] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;MutableTriple;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field[org.apache.commons.lang3.tuple.MutableTriple.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getLeft;;;Field[org.apache.commons.lang3.tuple.MutableTriple.left] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getMiddle;;;Field[org.apache.commons.lang3.tuple.MutableTriple.middle] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;getRight;;;Field[org.apache.commons.lang3.tuple.MutableTriple.right] of Argument[-1];ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setLeft;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutableTriple.left] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setMiddle;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutableTriple.middle] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;setRight;;;Argument[0];Field[org.apache.commons.lang3.tuple.MutableTriple.right] of Argument[-1];value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[0];Field[org.apache.commons.lang3.tuple.MutableTriple.left] of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[1];Field[org.apache.commons.lang3.tuple.MutableTriple.middle] of ReturnValue;value", + "org.apache.commons.lang3.tuple;MutableTriple;false;of;(java.lang.Object,java.lang.Object,java.lang.Object);;Argument[2];Field[org.apache.commons.lang3.tuple.MutableTriple.right] of ReturnValue;value" ] } }