diff options
author | 2014-07-30 19:31:04 +0700 | |
---|---|---|
committer | 2014-07-31 02:35:49 +0700 | |
commit | 54659e3a2c83d3949957a10436e55e525a430a15 (patch) | |
tree | c49f155975190dedff9794c89fc738edaed3f999 | |
parent | f90283f61d6ca37abf3a9fb8447d05e79caf0160 (diff) |
ART: LoadConstWide should clobber temp reg
If we have 2+ LoadConstWide(FP) calls in one method it is possible
that LoadConstWide will load the method poiner only once. In some
cases, for example, if we have branches, initialization might not be
done and it may lead to a segmentation fault.
Change-Id: If45fc2d1109d7ce9bd272f5c56446b2a6884daac
Signed-off-by: Alexei Zavjalov <alexei.zavjalov@intel.com>
-rw-r--r-- | compiler/dex/quick/x86/utility_x86.cc | 1 | ||||
-rw-r--r-- | test/083-compiler-regressions/expected.txt | 1 | ||||
-rw-r--r-- | test/083-compiler-regressions/src/Main.java | 15 |
3 files changed, 17 insertions, 0 deletions
diff --git a/compiler/dex/quick/x86/utility_x86.cc b/compiler/dex/quick/x86/utility_x86.cc index ccffe5bf6a..a77d79e56d 100644 --- a/compiler/dex/quick/x86/utility_x86.cc +++ b/compiler/dex/quick/x86/utility_x86.cc @@ -591,6 +591,7 @@ LIR* X86Mir2Lir::LoadConstantWide(RegStorage r_dest, int64_t value) { kDouble, kNotVolatile); res->target = data_target; res->flags.fixup = kFixupLoad; + Clobber(rl_method.reg); store_method_addr_used_ = true; } else { if (val_lo == 0) { diff --git a/test/083-compiler-regressions/expected.txt b/test/083-compiler-regressions/expected.txt index 9f57dbd75e..f8d92cc221 100644 --- a/test/083-compiler-regressions/expected.txt +++ b/test/083-compiler-regressions/expected.txt @@ -37,3 +37,4 @@ ManyFloatArgs passes atomicLong passes LiveFlags passes trip 3 LiveFlags passes trip 1 +minDoubleWith3ConstsTest passes diff --git a/test/083-compiler-regressions/src/Main.java b/test/083-compiler-regressions/src/Main.java index 748b0dee5c..c089c527ab 100644 --- a/test/083-compiler-regressions/src/Main.java +++ b/test/083-compiler-regressions/src/Main.java @@ -58,6 +58,21 @@ public class Main { ManyFloatArgs(); atomicLong(); LiveFlags.test(); + minDoubleWith3ConstsTest(); + } + + public static double minDouble(double a, double b, double c) { + return Math.min(Math.min(a, b), c); + } + + public static void minDoubleWith3ConstsTest() { + double result = minDouble(1.2, 2.5, Double.NaN); + if (Double.isNaN(result)) { + System.out.println("minDoubleWith3ConstsTest passes"); + } else { + System.out.println("minDoubleWith3ConstsTest fails: " + result + + " (expecting NaN)"); + } } public static void atomicLong() { |