diff options
author | Calin Juravle <calin@google.com> | 2015-01-26 18:54:32 +0000 |
---|---|---|
committer | Nicolas Geoffray <ngeoffray@google.com> | 2015-01-29 12:01:26 +0000 |
commit | 10e244f9e7f6d96a95c910a2bedef5bd3810c637 (patch) | |
tree | bc2b90ce716129115c05f79e21c58fe13b01fd20 /test/444-checker-nce | |
parent | ab7f56d9b9838811cb01773e45999e2cda4aa03a (diff) | |
download | art-10e244f9e7f6d96a95c910a2bedef5bd3810c637.tar.gz art-10e244f9e7f6d96a95c910a2bedef5bd3810c637.tar.bz2 art-10e244f9e7f6d96a95c910a2bedef5bd3810c637.zip |
optimizing: NullCheck elimination
How it works:
- run a type analysis to propagate null information on instructions
- during the last instruction simplifier remove null checks for which
the input is known to be not null
The current type analysis is actually a nullability analysis but it will
be reused in follow up CLs to propagate type information: so it keeps
the more convenient name.
Change-Id: I54bb1d32ab24604b4d677d1ecdaf8d60a5ff5ce9
Diffstat (limited to 'test/444-checker-nce')
-rw-r--r-- | test/444-checker-nce/expected.txt | 0 | ||||
-rw-r--r-- | test/444-checker-nce/info.txt | 1 | ||||
-rw-r--r-- | test/444-checker-nce/src/Main.java | 229 |
3 files changed, 230 insertions, 0 deletions
diff --git a/test/444-checker-nce/expected.txt b/test/444-checker-nce/expected.txt new file mode 100644 index 0000000000..e69de29bb2 --- /dev/null +++ b/test/444-checker-nce/expected.txt diff --git a/test/444-checker-nce/info.txt b/test/444-checker-nce/info.txt new file mode 100644 index 0000000000..78ad0b9426 --- /dev/null +++ b/test/444-checker-nce/info.txt @@ -0,0 +1 @@ +Tests for NullCheck elimination. diff --git a/test/444-checker-nce/src/Main.java b/test/444-checker-nce/src/Main.java new file mode 100644 index 0000000000..cdca3321ab --- /dev/null +++ b/test/444-checker-nce/src/Main.java @@ -0,0 +1,229 @@ +/* + * Copyright (C) 2015 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +public class Main { + + // CHECK-START: Main Main.keepTest(Main) instruction_simplifier_after_types (before) + // CHECK: NullCheck + // CHECK: InvokeStaticOrDirect + + // CHECK-START: Main Main.keepTest(Main) instruction_simplifier_after_types (after) + // CHECK: NullCheck + // CHECK: InvokeStaticOrDirect + public Main keepTest(Main m) { + return m.g(); + } + + // CHECK-START: Main Main.thisTest() instruction_simplifier (before) + // CHECK: NullCheck + // CHECK: InvokeStaticOrDirect + + // CHECK-START: Main Main.thisTest() instruction_simplifier (after) + // CHECK-NOT: NullCheck + // CHECK: InvokeStaticOrDirect + public Main thisTest() { + return g(); + } + + // CHECK-START: Main Main.newInstanceRemoveTest() instruction_simplifier (before) + // CHECK-DAG: NewInstance + // CHECK-DAG: NullCheck + // CHECK-DAG: InvokeStaticOrDirect + // CHECK-DAG: NullCheck + // CHECK-DAG: InvokeStaticOrDirect + + // CHECK-START: Main Main.newInstanceRemoveTest() instruction_simplifier (after) + // CHECK-NOT: NullCheck + public Main newInstanceRemoveTest() { + Main m = new Main(); + return m.g(); + } + + // CHECK-START: Main Main.newArrayRemoveTest() instruction_simplifier (before) + // CHECK-DAG: NewArray + // CHECK-DAG: NullCheck + // CHECK-DAG: ArrayGet + + // CHECK-START: Main Main.newArrayRemoveTest() instruction_simplifier (after) + // CHECK-DAG: NewArray + // CHECK-NOT: NullCheck + // CHECK-DAG: ArrayGet + public Main newArrayRemoveTest() { + Main[] ms = new Main[1]; + return ms[0]; + } + + // CHECK-START: Main Main.ifRemoveTest(boolean) instruction_simplifier_after_types (before) + // CHECK-DAG: NewInstance + // CHECK-DAG: NullCheck + + // CHECK-START: Main Main.ifRemoveTest(boolean) instruction_simplifier_after_types (after) + // CHECK-DAG: NewInstance + // CHECK-NOT: NullCheck + public Main ifRemoveTest(boolean flag) { + Main m = null; + if (flag) { + m = new Main(); + } else { + m = new Main(1); + } + return m.g(); + } + + // CHECK-START: Main Main.ifKeepTest(boolean) instruction_simplifier_after_types (before) + // CHECK-DAG: NewInstance + // CHECK-DAG: NullCheck + + // CHECK-START: Main Main.ifKeepTest(boolean) instruction_simplifier_after_types (after) + // CHECK-DAG: NewInstance + // CHECK-DAG: NullCheck + public Main ifKeepTest(boolean flag) { + Main m = null; + if (flag) { + m = new Main(1); + } + return m.g(); + } + + // CHECK-START: Main Main.forRemoveTest(int) instruction_simplifier_after_types (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.forRemoveTest(int) instruction_simplifier_after_types (after) + // CHECK-NOT: NullCheck + public Main forRemoveTest(int count) { + Main a = new Main(); + Main m = new Main(); + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = a; + } + } + return m.g(); + } + + // CHECK-START: Main Main.forKeepTest(int) instruction_simplifier_after_types (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.forKeepTest(int) instruction_simplifier_after_types (after) + // CHECK: NullCheck + public Main forKeepTest(int count) { + Main a = new Main(); + Main m = new Main(); + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = a; + } else { + m = null; + } + } + return m.g(); + } + + // CHECK-START: Main Main.phiFlowRemoveTest(int) instruction_simplifier_after_types (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.phiFlowRemoveTest(int) instruction_simplifier_after_types (after) + // CHECK-NOT: NullCheck + public Main phiFlowRemoveTest(int count) { + Main a = new Main(); + Main m = new Main(); + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = a; + } + } + Main n = new Main(); + for (int i = 0; i < count; i++) { + if (i % 3 == 0) { + n = m; + } + } + return n.g(); + } + + // CHECK-START: Main Main.phiFlowKeepTest(int) instruction_simplifier_after_types (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.phiFlowKeepTest(int) instruction_simplifier_after_types (after) + // CHECK: NullCheck + public Main phiFlowKeepTest(int count) { + Main a = new Main(); + Main m = new Main(); + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = a; + } else { + m = null; + } + } + Main n = new Main(); + for (int i = 0; i < count; i++) { + if (i % 3 == 0) { + n = m; + } + } + return n.g(); + } + + // CHECK-START: Main Main.scopeRemoveTest(int, Main) instruction_simplifier (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.scopeRemoveTest(int, Main) instruction_simplifier (after) + // CHECK-NOT: NullCheck + public Main scopeRemoveTest(int count, Main a) { + Main m = null; + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = new Main(); + m.g(); + } else { + m = a; + } + } + return m; + } + + // CHECK-START: Main Main.scopeKeepTest(int, Main) instruction_simplifier_after_types (before) + // CHECK: NullCheck + + // CHECK-START: Main Main.scopeKeepTest(int, Main) instruction_simplifier_after_types (after) + // CHECK: NullCheck + public Main scopeKeepTest(int count, Main a) { + Main m = new Main(); + for (int i = 0; i < count; i++) { + if (i % 2 == 0) { + m = a; + } else { + m = a; + m.g(); + } + } + return m; + } + + public Main() {} + public Main(int dummy) {} + + private Main g() { + // avoids inlining + throw new RuntimeException(); + } + + public static void main(String[] args) { + new Main(); + } + +} |