diff --git a/src/hotspot/share/c1/c1_LinearScan.cpp b/src/hotspot/share/c1/c1_LinearScan.cpp index 990d9f7bd4a..84846e8e43d 100644 --- a/src/hotspot/share/c1/c1_LinearScan.cpp +++ b/src/hotspot/share/c1/c1_LinearScan.cpp @@ -643,7 +643,8 @@ void LinearScan::compute_local_live_sets() { CodeEmitInfo* info = visitor.info_at(k); ValueStack* stack = info->stack(); for_each_state_value(stack, value, - set_live_gen_kill(value, op, live_gen, live_kill) + set_live_gen_kill(value, op, live_gen, live_kill); + local_has_fpu_registers = local_has_fpu_registers || value->type()->is_float_kind(); ); } @@ -1659,22 +1660,33 @@ void LinearScan::allocate_registers() { Interval* precolored_cpu_intervals, *not_precolored_cpu_intervals; Interval* precolored_fpu_intervals, *not_precolored_fpu_intervals; - // allocate cpu registers + // collect cpu intervals create_unhandled_lists(&precolored_cpu_intervals, ¬_precolored_cpu_intervals, is_precolored_cpu_interval, is_virtual_cpu_interval); - // allocate fpu registers + // collect fpu intervals create_unhandled_lists(&precolored_fpu_intervals, ¬_precolored_fpu_intervals, is_precolored_fpu_interval, is_virtual_fpu_interval); - - // the fpu interval allocation cannot be moved down below with the fpu section as + // this fpu interval collection cannot be moved down below with the allocation section as // the cpu_lsw.walk() changes interval positions. + if (!has_fpu_registers()) { +#ifdef ASSERT + assert(not_precolored_fpu_intervals == Interval::end(), "missed an uncolored fpu interval"); +#else + if (not_precolored_fpu_intervals != Interval::end()) { + BAILOUT("missed an uncolored fpu interval"); + } +#endif + } + + // allocate cpu registers LinearScanWalker cpu_lsw(this, precolored_cpu_intervals, not_precolored_cpu_intervals); cpu_lsw.walk(); cpu_lsw.finish_allocation(); if (has_fpu_registers()) { + // allocate fpu registers LinearScanWalker fpu_lsw(this, precolored_fpu_intervals, not_precolored_fpu_intervals); fpu_lsw.walk(); fpu_lsw.finish_allocation(); diff --git a/test/hotspot/jtreg/compiler/c1/TestLinearScanHasFPURegisters.java b/test/hotspot/jtreg/compiler/c1/TestLinearScanHasFPURegisters.java new file mode 100644 index 00000000000..da71e09954e --- /dev/null +++ b/test/hotspot/jtreg/compiler/c1/TestLinearScanHasFPURegisters.java @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2021, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8268366 + * @run main/othervm -Xbatch -XX:+TieredCompilation -XX:TieredStopAtLevel=1 + * compiler.c1.TestLinearScanHasFPURegisters + */ + +package compiler.c1; + +public class TestLinearScanHasFPURegisters { + void test(String[] args) { + String arr[] = new String[4]; + float f = -1; + try { + arr[0] = "-1"; // exception edge 1 with value -1 + if (args.length > 1) { + f = 42; + arr[1] = "42"; // exception edge 2 with value 42 + } + } catch (Exception e) { + // exception handler block with incoming phi for "f" + for (int i = 0; i < 1; ++i) { + f = f; // generates bytecodes, but no JIT IR + } + } + } + public static void main(String[] args) { + TestLinearScanHasFPURegisters t = new TestLinearScanHasFPURegisters(); + for (int i = 0; i < 1000; ++i) { + t.test(args); + } + } +}