Linear implementation of Tarjan's algorithm
Maurizio Cimadamore
maurizio.cimadamore at oracle.com
Wed Oct 25 20:16:51 UTC 2017
Thanks for testing - I imagined something similar - our target here is
what is said in the bug report:
"In JDK 7, compilation takes less than a second." (this is with 100 points).
Your tests show that the smaller the inference graph, the smaller the
gain (you start from 2x, and you end with 5x). But for bigger graphs,
these kind of improvements are not going to cut it (still 2mins against
<1s in JDK 7).
And, if you fix this at a deeper level, so that the incorporation has to
do less work, then you go back to subsecond compilation, in which case
the contribution of your optimization is likely to be negligible.
So, I don't want to sound overly critical (I realize I can sound that
way sometimes) - you did a great experiment, and it's showing some good
numbers - but the real problem here is that in JDK 7, _no matter how
many nodes you had_ compilation always stayed subsecond. So, when I see
a compilation time that increase depending on how many nested call you
add, I worry - because, no matter how you optimize, you can always add
few extra nodes and go back being as slow as you were (or more!) before
the optimization.
During JDK 9 we did a great job at optimizing this pattern:
m1(m2(m3 .... mN() ) ) ) )
I think it's time we do something similar for
m(g1(), g2(), ... gN())
Note that when we made incorporation smart enough to detect the first
case, all other performance related concerns became negligible - I'm
hoping we can pull a similar trick here (and we have few ideas on how to
do that).
Cheers
Maurizio
On 25/10/17 18:45, B. Blaser wrote:
> On 25 October 2017 at 18:51, Maurizio Cimadamore
> <maurizio.cimadamore at oracle.com> wrote:
>>
>> On 25/10/17 17:34, B. Blaser wrote:
>>> On 25 October 2017 at 18:16, Maurizio Cimadamore
>>> <maurizio.cimadamore at oracle.com> wrote:
>>>>
>>>> On 25/10/17 14:41, B. Blaser wrote:
>>>>> On 23 October 2017 at 17:58, Maurizio Cimadamore
>>>>> <maurizio.cimadamore at oracle.com> wrote:
>>>>>> To have a better idea of the kind of performance issues we are having
>>>>>> in
>>>>>> this area, take a look here:
>>>>>>
>>>>>> https://bugs.openjdk.java.net/browse/JDK-8152289
>>>>>>
>>>>>> I'm slightly pessimistic that any of the performance fixes discussed
>>>>>> here
>>>>>> in
>>>>>> the last few weeks would actually make a difference here - the sad
>>>>>> reality
>>>>>> is that the cost of doing incorporation dominates pretty much
>>>>>> everything
>>>>>> else. And the name of the game to address these kind of issues seem to
>>>>>> be
>>>>>> to
>>>>>> attempt to reduce the size of the inference graph by finding
>>>>>> similarities
>>>>>> between variables [1]/minimize number of propagation steps as much as
>>>>>> possible [2], etc.
>>>>> Of course, 'contains()' isn't the bottleneck here. But with an
>>>>> 'HashStack', this method is up to 10 times faster than with a 'List'
>>>>> (in this example).
>>>>>
>>>>> That said, I observed in the light of your comments that a very large
>>>>> number of same upper bound pairs are checked multiple times. So, I
>>>>> tried to put them in a cache that is cleared at every upper bound
>>>>> change, as here under. It seems to be 3-4 times faster than before for
>>>>> this issue with 60 nodes (on my computer).
>>>>>
>>>>> What do you think?
>>>> Did you try it with the test case in JDK-8152289?
>>> Yes, with 20/60/100 points (the gain is different but always appreciable).
>>> Of course, only the cache is important (the gain with 'contains()' is
>>> only of some milliseconds).
>> Could you post some before/after times please?
> On a quite slow CPU (before -> after):
> * 20 points - 13s -> 6s
> * 60 points - 90s -> 24s
> * 100 points - 551s -> 110s
>
> Bernard
>
>> Thanks
>> Maurizio
>>
>>> Bernard
>>>
>>>
>>>> Maurizio
>>>>
>>>>> Bernard
>>>>>
>>>>>
>>>>> diff --git
>>>>> a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Infer.java
>>>>> b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Infer.java
>>>>> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Infer.java
>>>>> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Infer.java
>>>>> @@ -939,13 +939,15 @@
>>>>> @Override
>>>>> void apply(InferenceContext inferenceContext, Warner warn) {
>>>>> List<Type> boundList =
>>>>> uv.getBounds(InferenceBound.UPPER).stream()
>>>>> + .filter(b2 -> t != b2)
>>>>> + .filter(b2 -> !upperBoundCache.contains(new
>>>>> Pair<>(t,
>>>>> b2)))
>>>>> .collect(types.closureCollector(true,
>>>>> types::isSameType));
>>>>> +
>>>>> for (Type b2 : boundList) {
>>>>> - if (t == b2) continue;
>>>>> /* This wildcard check is temporary workaround.
>>>>> This code may need to be
>>>>> * revisited once spec bug JDK-7034922 is fixed.
>>>>> */
>>>>> - if (t != b2 && !t.hasTag(WILDCARD) &&
>>>>> !b2.hasTag(WILDCARD)) {
>>>>> + if (!t.hasTag(WILDCARD) && !b2.hasTag(WILDCARD)) {
>>>>> for (Pair<Type, Type> commonSupers :
>>>>> getParameterizedSupers(t, b2)) {
>>>>> List<Type> allParamsSuperBound1 =
>>>>> commonSupers.fst.allparams();
>>>>> List<Type> allParamsSuperBound2 =
>>>>> commonSupers.snd.allparams();
>>>>> @@ -964,6 +966,8 @@
>>>>> Assert.check(allParamsSuperBound1.isEmpty()
>>>>> && allParamsSuperBound2.isEmpty());
>>>>> }
>>>>> }
>>>>> + upperBoundCache.add(new Pair<>(t, b2));
>>>>> + upperBoundCache.add(new Pair<>(b2, t));
>>>>> }
>>>>> }
>>>>> }
>>>>> @@ -1086,6 +1090,7 @@
>>>>> }
>>>>>
>>>>> if (ib == InferenceBound.UPPER) {
>>>>> + upperBoundCache.clear();
>>>>> actions.add(new CheckUpperBounds(uv, t));
>>>>> }
>>>>>
>>>>> @@ -1125,6 +1130,7 @@
>>>>> }
>>>>> } finally {
>>>>> incorporationCache.clear();
>>>>> + upperBoundCache.clear();
>>>>> }
>>>>> }
>>>>>
>>>>> @@ -1247,6 +1253,7 @@
>>>>>
>>>>> /** an incorporation cache keeps track of all executed
>>>>> incorporation-related operations */
>>>>> Map<IncorporationBinaryOp, Boolean> incorporationCache = new
>>>>> HashMap<>();
>>>>> + HashSet<Pair<Type, Type>> upperBoundCache = new HashSet<>();
>>>>>
>>>>> protected static class BoundFilter implements Filter<Type> {
>>>>>
>>>>>
>>>>>> [1] - https://bugs.openjdk.java.net/browse/JDK-8046685
>>>>>> [2] - https://bugs.openjdk.java.net/browse/JDK-8067767
>>>>>>
>>>>>> Maurizio
>>>>
More information about the compiler-dev
mailing list