8287925: AArch64: intrinsics for compareUnsigned method in Integer and Long
Reviewed-by: adinn, aph
This commit is contained in:
parent
3a66737001
commit
195f31371f
@ -1,5 +1,5 @@
|
||||
//
|
||||
// Copyright (c) 2003, 2022, Oracle and/or its affiliates. All rights reserved.
|
||||
// Copyright (c) 2003, 2023, Oracle and/or its affiliates. All rights reserved.
|
||||
// Copyright (c) 2014, 2021, Red Hat, Inc. All rights reserved.
|
||||
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
//
|
||||
@ -9654,6 +9654,90 @@ instruct get_and_addIi_no_resAcq(indirect mem, Universe dummy, immIAddSub incr)
|
||||
ins_pipe(pipe_serial);
|
||||
%}
|
||||
|
||||
// Manifest a CmpU result in an integer register.
|
||||
// (src1 < src2) ? -1 : ((src1 > src2) ? 1 : 0)
|
||||
instruct cmpU3_reg_reg(iRegINoSp dst, iRegI src1, iRegI src2, rFlagsReg flags)
|
||||
%{
|
||||
match(Set dst (CmpU3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"cmpw $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lo\t# CmpU3(reg)"
|
||||
%}
|
||||
ins_encode %{
|
||||
__ cmpw($src1$$Register, $src2$$Register);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
__ cnegw($dst$$Register, $dst$$Register, Assembler::LO);
|
||||
%}
|
||||
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
instruct cmpU3_reg_imm(iRegINoSp dst, iRegI src1, immIAddSub src2, rFlagsReg flags)
|
||||
%{
|
||||
match(Set dst (CmpU3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"subsw zr, $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lo\t# CmpU3(imm)"
|
||||
%}
|
||||
ins_encode %{
|
||||
__ subsw(zr, $src1$$Register, (int32_t)$src2$$constant);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
__ cnegw($dst$$Register, $dst$$Register, Assembler::LO);
|
||||
%}
|
||||
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
// Manifest a CmpUL result in an integer register.
|
||||
// (src1 < src2) ? -1 : ((src1 > src2) ? 1 : 0)
|
||||
instruct cmpUL3_reg_reg(iRegINoSp dst, iRegL src1, iRegL src2, rFlagsReg flags)
|
||||
%{
|
||||
match(Set dst (CmpUL3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"cmp $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lo\t# CmpUL3(reg)"
|
||||
%}
|
||||
ins_encode %{
|
||||
__ cmp($src1$$Register, $src2$$Register);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
__ cnegw($dst$$Register, $dst$$Register, Assembler::LO);
|
||||
%}
|
||||
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
instruct cmpUL3_reg_imm(iRegINoSp dst, iRegL src1, immLAddSub src2, rFlagsReg flags)
|
||||
%{
|
||||
match(Set dst (CmpUL3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"subs zr, $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lo\t# CmpUL3(imm)"
|
||||
%}
|
||||
ins_encode %{
|
||||
__ subs(zr, $src1$$Register, (int32_t)$src2$$constant);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
__ cnegw($dst$$Register, $dst$$Register, Assembler::LO);
|
||||
%}
|
||||
|
||||
ins_pipe(pipe_class_default);
|
||||
%}
|
||||
|
||||
// Manifest a CmpL result in an integer register.
|
||||
// (src1 < src2) ? -1 : ((src1 > src2) ? 1 : 0)
|
||||
instruct cmpL3_reg_reg(iRegINoSp dst, iRegL src1, iRegL src2, rFlagsReg flags)
|
||||
@ -9661,13 +9745,12 @@ instruct cmpL3_reg_reg(iRegINoSp dst, iRegL src1, iRegL src2, rFlagsReg flags)
|
||||
match(Set dst (CmpL3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 6);
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"cmp $src1, $src2"
|
||||
"csetw $dst, ne"
|
||||
"cnegw $dst, lt"
|
||||
"cmp $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lt\t# CmpL3(reg)"
|
||||
%}
|
||||
// format %{ "CmpL3 $dst, $src1, $src2" %}
|
||||
ins_encode %{
|
||||
__ cmp($src1$$Register, $src2$$Register);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
@ -9682,19 +9765,14 @@ instruct cmpL3_reg_imm(iRegINoSp dst, iRegL src1, immLAddSub src2, rFlagsReg fla
|
||||
match(Set dst (CmpL3 src1 src2));
|
||||
effect(KILL flags);
|
||||
|
||||
ins_cost(INSN_COST * 6);
|
||||
ins_cost(INSN_COST * 3);
|
||||
format %{
|
||||
"cmp $src1, $src2"
|
||||
"csetw $dst, ne"
|
||||
"cnegw $dst, lt"
|
||||
"subs zr, $src1, $src2\n\t"
|
||||
"csetw $dst, ne\n\t"
|
||||
"cnegw $dst, lt\t# CmpL3(imm)"
|
||||
%}
|
||||
ins_encode %{
|
||||
int32_t con = (int32_t)$src2$$constant;
|
||||
if (con < 0) {
|
||||
__ adds(zr, $src1$$Register, -con);
|
||||
} else {
|
||||
__ subs(zr, $src1$$Register, con);
|
||||
}
|
||||
__ subs(zr, $src1$$Register, (int32_t)$src2$$constant);
|
||||
__ csetw($dst$$Register, Assembler::NE);
|
||||
__ cnegw($dst$$Register, $dst$$Register, Assembler::LT);
|
||||
%}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2022, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2022, 2023, 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
|
||||
@ -29,8 +29,8 @@ import jdk.test.lib.Utils;
|
||||
/*
|
||||
* @test
|
||||
* @key randomness
|
||||
* @bug 8283726
|
||||
* @requires os.arch=="amd64" | os.arch=="x86_64"
|
||||
* @bug 8283726 8287925
|
||||
* @requires os.arch=="amd64" | os.arch=="x86_64" | os.arch=="aarch64"
|
||||
* @summary Test the intrinsics implementation of Integer/Long::compareUnsigned
|
||||
* @library /test/lib /
|
||||
* @run driver compiler.intrinsics.TestCompareUnsigned
|
||||
@ -73,13 +73,74 @@ public class TestCompareUnsigned {
|
||||
return Integer.compareUnsigned(x, y);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_U3, "1"})
|
||||
public int compareIntWithImm1(int x) {
|
||||
return Integer.compareUnsigned(x, 42);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_U3, "1"})
|
||||
public int compareIntWithImm2(int x) {
|
||||
return Integer.compareUnsigned(x, 42 << 12);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_U3, "1"})
|
||||
public int compareIntWithImm3(int x) {
|
||||
return Integer.compareUnsigned(x, 42 << 24);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_U3, "1"})
|
||||
public int compareIntWithImm4(int x) {
|
||||
return Integer.compareUnsigned(x, Integer.MIN_VALUE);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLong(long x, long y) {
|
||||
return Long.compareUnsigned(x, y);
|
||||
}
|
||||
|
||||
@Run(test = {"lessThanInt", "lessThanLong", "compareInt", "compareLong"})
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLongWithImm1(long x) {
|
||||
return Long.compareUnsigned(x, 42);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLongWithImm2(long x) {
|
||||
return Long.compareUnsigned(x, 42 << 12);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLongWithImm3(long x) {
|
||||
return Long.compareUnsigned(x, 42 << 24);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLongWithImm4(long x) {
|
||||
return Long.compareUnsigned(x, Integer.MIN_VALUE);
|
||||
}
|
||||
|
||||
@Test
|
||||
@IR(counts = {IRNode.CMP_UL3, "1"})
|
||||
public int compareLongWithImm5(long x) {
|
||||
return Long.compareUnsigned(x, Long.MIN_VALUE);
|
||||
}
|
||||
|
||||
@Run(test = {"lessThanInt", "lessThanLong",
|
||||
"compareInt",
|
||||
"compareIntWithImm1", "compareIntWithImm2",
|
||||
"compareIntWithImm3", "compareIntWithImm4",
|
||||
"compareLong",
|
||||
"compareLongWithImm1", "compareLongWithImm2",
|
||||
"compareLongWithImm3", "compareLongWithImm4",
|
||||
"compareLongWithImm5"})
|
||||
public void runTests() {
|
||||
var random = Utils.getRandomInstance();
|
||||
for (int i = 0; i < 1000; i++) {
|
||||
@ -89,6 +150,10 @@ public class TestCompareUnsigned {
|
||||
Asserts.assertEquals(compareInt(x, x), 0);
|
||||
Asserts.assertEquals(lessThanInt(x, y), expectedResult(x, y) < 0 ? TRUE_VALUE : FALSE_VALUE);
|
||||
Asserts.assertEquals(compareInt(x, y), expectedResult(x, y));
|
||||
Asserts.assertEquals(compareIntWithImm1(x), expectedResult(x, 42));
|
||||
Asserts.assertEquals(compareIntWithImm2(x), expectedResult(x, 42 << 12));
|
||||
Asserts.assertEquals(compareIntWithImm3(x), expectedResult(x, 42 << 24));
|
||||
Asserts.assertEquals(compareIntWithImm4(x), expectedResult(x, Integer.MIN_VALUE));
|
||||
}
|
||||
for (int i = 0; i < 1000; i++) {
|
||||
long x = random.nextLong();
|
||||
@ -97,6 +162,11 @@ public class TestCompareUnsigned {
|
||||
Asserts.assertEquals(compareLong(x, x), 0);
|
||||
Asserts.assertEquals(lessThanLong(x, y), expectedResult(x, y) < 0 ? TRUE_VALUE : FALSE_VALUE);
|
||||
Asserts.assertEquals(compareLong(x, y), expectedResult(x, y));
|
||||
Asserts.assertEquals(compareLongWithImm1(x), expectedResult(x, 42));
|
||||
Asserts.assertEquals(compareLongWithImm2(x), expectedResult(x, 42 << 12));
|
||||
Asserts.assertEquals(compareLongWithImm3(x), expectedResult(x, 42 << 24));
|
||||
Asserts.assertEquals(compareLongWithImm4(x), expectedResult(x, Integer.MIN_VALUE));
|
||||
Asserts.assertEquals(compareLongWithImm5(x), expectedResult(x, Long.MIN_VALUE));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user