/// CHECK-START: int Main.$noinline$testDifferentFields(Point, Point, boolean, boolean) load_store_elimination (after) /// CHECK-DAG: InstanceFieldSet field_name:Point.x /// CHECK-DAG: InstanceFieldSet field_name:Point.y
/// CHECK-START: int Main.$noinline$testDifferentFields(Point, Point, boolean, boolean) load_store_elimination (after) /// CHECK-NOT: InstanceFieldGet field_name:Point.x /// CHECK-NOT: InstanceFieldGet field_name:Point.y
// Consistency check to make sure the try/catches weren't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testDifferentFields(Point, Point, boolean, boolean) load_store_elimination (after) /// CHECK: TryBoundary kind:entry /// CHECK: TryBoundary kind:entry
// Different fields shouldn't alias. privatestaticint $noinline$testDifferentFields(
Point obj1, Point obj2, boolean boolean_throw, boolean boolean_other_throw) { try { if (boolean_throw) { thrownew Error();
}
} catch (Error e) { return0;
}
obj1.x = 1;
obj2.y = 2; int result = obj1.x + obj2.y; try { if (boolean_other_throw) { thrownew Error();
}
} catch (Error e) { return0;
} return result;
}
// Consistency check to make sure the try/catches weren't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testRedundantStore(Point, boolean, boolean) load_store_elimination (after) /// CHECK-DAG: TryBoundary kind:entry /// CHECK-DAG: TryBoundary kind:entry
// Redundant store of the same value. privatestaticint $noinline$testRedundantStore(
Point obj, boolean boolean_throw, boolean boolean_other_throw) { try { if (boolean_throw) { thrownew Error();
}
} catch (Error e) { return0;
}
obj.y = 1;
obj.y = 1; try { if (boolean_other_throw) { thrownew Error();
}
} catch (Error e) { return0;
} return obj.y;
}
// Consistency check to make sure the try/catch wasn't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testTryCatchBlocking(Point, boolean) load_store_elimination (after) /// CHECK: TryBoundary kind:entry
// We cannot remove the Get since we might have thrown. privatestaticint $noinline$testTryCatchBlocking(Point obj, boolean boolean_throw) {
obj.y = 1; try { if (boolean_throw) { thrownew Error();
}
} catch (Error e) {
} return obj.y;
}
// Consistency check to make sure the try/catch wasn't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testTryCatchPhi(Point, boolean) load_store_elimination (after) /// CHECK-DAG: TryBoundary kind:entry
// We either threw and we set the value in the catch, or we didn't throw and we set the value // before the catch. We can solve that with a Phi and skip the get. privatestaticint $noinline$testTryCatchPhi(Point obj, boolean boolean_throw) {
obj.y = 1; try { if (boolean_throw) { thrownew Error();
}
} catch (Error e) {
obj.y = 2;
} return obj.y;
}
// Consistency check to make sure the try/catch wasn't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testTryCatchPhiWithTwoCatches(Point, int[]) load_store_elimination (after) /// CHECK-DAG: TryBoundary kind:entry privatestaticint $noinline$testTryCatchPhiWithTwoCatches(Point obj, int[] numbers) {
obj.y = 1; try { if (numbers[0] == 1) { thrownew Error();
}
} catch (ArrayIndexOutOfBoundsException e) {
obj.y = 2;
} catch (Error e) {
obj.y = 3;
} return obj.y;
}
// Check that we don't eliminate the first store to `main.sumForKeepStoreInsideTryCatch` since it // is observable.
// Consistency check to make sure the try/catch wasn't removed by an earlier pass. /// CHECK-START: int Main.$noinline$testKeepStoreInsideTry() load_store_elimination (after) /// CHECK-DAG: TryBoundary kind:entry
/// CHECK-START: int Main.$noinline$testDontKeepStoreInsideCatch(int[]) load_store_elimination (after) /// CHECK-NOT: InstanceFieldSet field_name:Main.sumForKeepStoreInsideTryCatch privatestaticint $noinline$testDontKeepStoreInsideCatch(int[] array) {
Main main = new Main(); int value = 0; try {
value = array[0];
} catch (Exception e) { // These sets can be eliminated even though we have invokes since this catch is not part of an // outer try.
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(10);
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(20);
} return main.sumForKeepStoreInsideTryCatch + value;
}
/// CHECK-START: int Main.$noinline$testKeepStoreInsideCatchWithOuterTry(int[]) load_store_elimination (after) /// CHECK: InstanceFieldSet field_name:Main.sumForKeepStoreInsideTryCatch /// CHECK: InstanceFieldSet field_name:Main.sumForKeepStoreInsideTryCatch /// CHECK-NOT: InstanceFieldSet field_name:Main.sumForKeepStoreInsideTryCatch privatestaticint $noinline$testKeepStoreInsideCatchWithOuterTry(int[] array) {
Main main = new Main(); int value = 0; try { try {
value = array[0];
} catch (Exception e) { // These sets can't be eliminated since this catch is part of a outer try.
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(10);
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(20);
}
} catch (Exception e) {
value = 100000;
}
/// CHECK-START: int Main.$noinline$testDontKeepStoreInsideFinally(int[]) load_store_elimination (after) /// CHECK-NOT: InstanceFieldSet field_name:Main.sumForKeepStoreInsideTryCatch privatestaticint $noinline$testDontKeepStoreInsideFinally(int[] array) {
Main main = new Main(); int value = 0; try {
value = array[0];
} finally { // These sets can be eliminated even though we have invokes since this catch is not part of an // outer try.
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(10);
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(20);
} return main.sumForKeepStoreInsideTryCatch + value;
}
// Checks that we are able to do LSE inside of catches which are outside of try blocks.
// This store potentially can be eliminated too, but our phi creation logic doesn't realize it can // create a Phi for `main.sumForKeepStoreInsideTryCatch` and skip a store+load.
privatestaticint $noinline$testDontKeepStoreInsideOuterCatch(int[] array) {
Main main = new Main(); int value = 0; try {
value = array[0];
} catch (ArrayIndexOutOfBoundsException expected) { // These sets and gets are not considered to be part of a try so they are free to be // eliminated.
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(10);
main.sumForKeepStoreInsideTryCatch += $noinline$returnValue(20); try {
value = array[0];
} catch (ArrayIndexOutOfBoundsException expectedToo) {
value = 100000;
}
}
// Like `test40` from 530-checker-lse but with $inline$ for the inner method so we check that we // have the array set inside try catches too. // Since we are inlining, we know the parameters and are able to elimnate (some) of the // `ArraySet`s. privatestaticint $noinline$test40() { int[] array = newint[1]; try {
$inline$fillArrayTest40(array, 100, 0);
System.out.println("UNREACHABLE");
} catch (Throwable expected) {
}
assertEquals(1, array[0]); try {
$inline$fillArrayTest40(array, 100, 1);
System.out.println("UNREACHABLE");
} catch (Throwable expected) {
}
assertEquals(2, array[0]);
$inline$fillArrayTest40(array, 100, 2);
assertEquals(150, array[0]); return array[0];
}
// Check that the stores to array[0] are not eliminated since we can throw in between the stores. privatestaticvoid $inline$fillArrayTest40(int[] array, int a, int b) {
array[0] = 1; int x = a / b;
array[0] = 2; int y = a / (b - 1);
array[0] = x + y;
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.