1418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames/* 2fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * Copyright (C) 2015 The Android Open Source Project 3fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * 4fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * Licensed under the Apache License, Version 2.0 (the "License"); 5fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * you may not use this file except in compliance with the License. 6fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * You may obtain a copy of the License at 7fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * 8fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * http://www.apache.org/licenses/LICENSE-2.0 9fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * 10fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * Unless required by applicable law or agreed to in writing, software 11fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * distributed under the License is distributed on an "AS IS" BASIS, 12fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * See the License for the specific language governing permissions and 14fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain * limitations under the License. 15fb7fc7b1e11523b6e4f444f0f54de0b49cd0c4e1Roland Levillain */ 16418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 17418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Ramespublic class Main { 18418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 19418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames // A dummy value to defeat inlining of these routines. 20418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames static boolean doThrow = false; 21418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 22418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static void assertIntEquals(int expected, int result) { 23418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (expected != result) { 24418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames throw new Error("Expected: " + expected + ", found: " + result); 25418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 26418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 27418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 28418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static void assertLongEquals(long expected, long result) { 29418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (expected != result) { 30418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames throw new Error("Expected: " + expected + ", found: " + result); 31418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 32418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 33418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 34418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 35418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test basic merging of `MUL+ADD` into `MULADD`. 36418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 37418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 38418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm64 (before) 39418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 40418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:i\d+>> ParameterValue 41418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:i\d+>> ParameterValue 42418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 43418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 44418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Add>>] 45418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 46418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm64 (after) 47418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 48418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:i\d+>> ParameterValue 49418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:i\d+>> ParameterValue 504a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulAdd:i\d+>> MultiplyAccumulate [<<Acc>>,<<Left>>,<<Right>>] kind:Add 51418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<MulAdd>>] 52418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 53418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm64 (after) 54418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Mul 55418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Add 56418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 57418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulAdd(int, int, int) disassembly (after) 58418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: madd w{{\d+}}, w{{\d+}}, w{{\d+}}, w{{\d+}} 59418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 604a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm (before) 614a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 624a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 634a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 644a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 654a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 664a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Add>>] 674a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 684a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm (after) 694a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 704a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 714a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 724a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulAdd:i\d+>> MultiplyAccumulate [<<Acc>>,<<Left>>,<<Right>>] kind:Add 734a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<MulAdd>>] 744a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 754a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulAdd(int, int, int) instruction_simplifier_arm (after) 764a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Mul 774a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Add 784a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 794a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulAdd(int, int, int) disassembly (after) 804a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: mla r{{\d+}}, r{{\d+}}, r{{\d+}}, r{{\d+}} 814a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 82418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static int $opt$noinline$mulAdd(int acc, int left, int right) { 83418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 84418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return acc + left * right; 85418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 86418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 87418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 88418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test basic merging of `MUL+SUB` into `MULSUB`. 89418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 90418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 91418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulSub(long, long, long) instruction_simplifier_arm64 (before) 92418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 93418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:j\d+>> ParameterValue 94418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:j\d+>> ParameterValue 95418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 96418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 97418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Sub>>] 98418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 99418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulSub(long, long, long) instruction_simplifier_arm64 (after) 100418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 101418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:j\d+>> ParameterValue 102418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:j\d+>> ParameterValue 1034a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulSub:j\d+>> MultiplyAccumulate [<<Acc>>,<<Left>>,<<Right>>] kind:Sub 104418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<MulSub>>] 105418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 106418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulSub(long, long, long) instruction_simplifier_arm64 (after) 107418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Mul 108418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Sub 109418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 110418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulSub(long, long, long) disassembly (after) 111418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: msub x{{\d+}}, x{{\d+}}, x{{\d+}}, x{{\d+}} 112418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 1134a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulSub(long, long, long) instruction_simplifier_arm (before) 1144a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:j\d+>> ParameterValue 1154a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 1164a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 1174a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 1184a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 1194a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Sub>>] 1204a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 1214a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulSub(long, long, long) instruction_simplifier_arm (after) 1224a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 1234a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 124418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static long $opt$noinline$mulSub(long acc, long left, long right) { 125418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 126418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return acc - left * right; 127418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 128418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 129418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 130418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test that we do not create a multiply-accumulate instruction when there 131418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * are other uses of the multiplication that cannot merge it. 132418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 133418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 134418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm64 (before) 135418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 136418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:i\d+>> ParameterValue 137418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:i\d+>> ParameterValue 138418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 139418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 140418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Or:i\d+>> Or [<<Mul>>,<<Add>>] 141418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Or>>] 142418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 143418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm64 (after) 144418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 145418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:i\d+>> ParameterValue 146418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:i\d+>> ParameterValue 147418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 148418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 149418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Or:i\d+>> Or [<<Mul>>,<<Add>>] 150418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Or>>] 151418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 152418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm64 (after) 1534a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 1544a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 1554a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm (before) 1564a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 1574a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 1584a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 1594a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 1604a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 1614a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Or:i\d+>> Or [<<Mul>>,<<Add>>] 1624a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Or>>] 1634a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 1644a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm (after) 1654a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 1664a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 1674a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 1684a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 1694a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:i\d+>> Add [<<Acc>>,<<Mul>>] 1704a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Or:i\d+>> Or [<<Mul>>,<<Add>>] 1714a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Or>>] 1724a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 1734a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$multipleUses1(int, int, int) instruction_simplifier_arm (after) 1744a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 175418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 176418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static int $opt$noinline$multipleUses1(int acc, int left, int right) { 177418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 178418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames int temp = left * right; 179418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return temp | (acc + temp); 180418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 181418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 182418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 183418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test that we do not create a multiply-accumulate instruction even when all 184418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * uses of the multiplication can merge it. 185418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 186418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 187418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm64 (before) 188418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 189418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:j\d+>> ParameterValue 190418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:j\d+>> ParameterValue 191418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 192418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:j\d+>> Add [<<Acc>>,<<Mul>>] 193418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 194418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Res:j\d+>> Add [<<Add>>,<<Sub>>] 195418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Res>>] 196418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 197418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm64 (after) 198418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 199418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Left:j\d+>> ParameterValue 200418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Right:j\d+>> ParameterValue 201418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 202418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:j\d+>> Add [<<Acc>>,<<Mul>>] 203418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 204418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Res:j\d+>> Add [<<Add>>,<<Sub>>] 205418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Res>>] 206418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 207418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm64 (after) 2084a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 2094a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2104a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm (before) 2114a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:j\d+>> ParameterValue 2124a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 2134a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 2144a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 2154a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:j\d+>> Add [<<Acc>>,<<Mul>>] 2164a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 2174a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Res:j\d+>> Add [<<Add>>,<<Sub>>] 2184a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Res>>] 2194a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2204a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm (after) 2214a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:j\d+>> ParameterValue 2224a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 2234a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 2244a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 2254a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:j\d+>> Add [<<Acc>>,<<Mul>>] 2264a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Sub:j\d+>> Sub [<<Acc>>,<<Mul>>] 2274a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Res:j\d+>> Add [<<Add>>,<<Sub>>] 2284a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Res>>] 2294a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2304a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$multipleUses2(long, long, long) instruction_simplifier_arm (after) 2314a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 232418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 233418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 234418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static long $opt$noinline$multipleUses2(long acc, long left, long right) { 235418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 236418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames long temp = left * right; 237418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return (acc + temp) + (acc - temp); 238418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 239418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 240418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 241418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 242418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test the interpretation of `a * (b + 1)` as `a + (a * b)`. 243418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 244418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 245418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm64 (before) 246418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 247418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Var:i\d+>> ParameterValue 248418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Const1:i\d+>> IntConstant 1 249418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Add:i\d+>> Add [<<Var>>,<<Const1>>] 250418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:i\d+>> Mul [<<Acc>>,<<Add>>] 251418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Mul>>] 252418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 253418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm64 (after) 254418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:i\d+>> ParameterValue 255418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Var:i\d+>> ParameterValue 2564a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulAdd:i\d+>> MultiplyAccumulate [<<Acc>>,<<Acc>>,<<Var>>] kind:Add 257418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<MulAdd>>] 258418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 259418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm64 (after) 260418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Mul 261418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Add 262418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 263418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: int Main.$opt$noinline$mulPlusOne(int, int) disassembly (after) 264418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: madd w{{\d+}}, w{{\d+}}, w{{\d+}}, w{{\d+}} 265418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 2664a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm (before) 2674a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 2684a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Var:i\d+>> ParameterValue 2694a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Const1:i\d+>> IntConstant 1 2704a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Add:i\d+>> Add [<<Var>>,<<Const1>>] 2714a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Acc>>,<<Add>>] 2724a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Mul>>] 2734a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2744a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm (after) 2754a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:i\d+>> ParameterValue 2764a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Var:i\d+>> ParameterValue 2774a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulAdd:i\d+>> MultiplyAccumulate [<<Acc>>,<<Acc>>,<<Var>>] kind:Add 2784a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<MulAdd>>] 2794a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2804a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulPlusOne(int, int) instruction_simplifier_arm (after) 2814a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Mul 2824a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Add 2834a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 2844a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulPlusOne(int, int) disassembly (after) 2854a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: mla r{{\d+}}, r{{\d+}}, r{{\d+}}, r{{\d+}} 2864a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 287418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static int $opt$noinline$mulPlusOne(int acc, int var) { 288418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 289418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return acc * (var + 1); 290418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 291418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 292418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 293418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /** 294418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames * Test the interpretation of `a * (1 - b)` as `a - (a * b)`. 295418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames */ 296418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 297418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulMinusOne(long, long) instruction_simplifier_arm64 (before) 298418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 299418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Var:j\d+>> ParameterValue 300418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Const1:j\d+>> LongConstant 1 301418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Sub:j\d+>> Sub [<<Const1>>,<<Var>>] 302418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Mul:j\d+>> Mul [<<Acc>>,<<Sub>>] 303418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<Mul>>] 304418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 305418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulMinusOne(long, long) instruction_simplifier_arm64 (after) 306418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Acc:j\d+>> ParameterValue 307418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: <<Var:j\d+>> ParameterValue 3084a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulSub:j\d+>> MultiplyAccumulate [<<Acc>>,<<Acc>>,<<Var>>] kind:Sub 309418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: Return [<<MulSub>>] 310418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 311418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulMinusOne(long, long) instruction_simplifier_arm64 (after) 312418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Mul 313418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-NOT: Sub 314418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 315418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK-START-ARM64: long Main.$opt$noinline$mulMinusOne(long, long) disassembly (after) 316418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames /// CHECK: msub x{{\d+}}, x{{\d+}}, x{{\d+}}, x{{\d+}} 317418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 3184a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulMinusOne(long, long) instruction_simplifier_arm (before) 3194a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Acc:j\d+>> ParameterValue 3204a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Var:j\d+>> ParameterValue 3214a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Const1:j\d+>> LongConstant 1 3224a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Sub:j\d+>> Sub [<<Const1>>,<<Var>>] 3234a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Acc>>,<<Sub>>] 3244a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Mul>>] 3254a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3264a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulMinusOne(long, long) instruction_simplifier_arm (after) 3274a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 328418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static long $opt$noinline$mulMinusOne(long acc, long var) { 329418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames if (doThrow) throw new Error(); 330418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames return acc * (1 - var); 331418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 332418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 3334a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /** 3344a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko * Test basic merging of `MUL+NEG` into `MULNEG`. 3354a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko */ 3364a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3374a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm64 (before) 3384a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 3394a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 3404a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 3414a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:i\d+>> Neg [<<Mul>>] 3424a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 3434a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3444a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm64 (after) 3454a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 3464a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 3474a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Const0:i\d+>> IntConstant 0 3484a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulNeg:i\d+>> MultiplyAccumulate [<<Const0>>,<<Left>>,<<Right>>] kind:Sub 3494a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<MulNeg>>] 3504a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3514a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm64 (after) 3524a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Mul 3534a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Neg 3544a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3554a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: int Main.$opt$noinline$mulNeg(int, int) disassembly (after) 3564a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: mneg w{{\d+}}, w{{\d+}}, w{{\d+}} 3574a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3584a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm (before) 3594a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 3604a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 3614a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 3624a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:i\d+>> Neg [<<Mul>>] 3634a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 3644a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3654a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm (after) 3664a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:i\d+>> ParameterValue 3674a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:i\d+>> ParameterValue 3684a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:i\d+>> Mul [<<Left>>,<<Right>>] 3694a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:i\d+>> Neg [<<Mul>>] 3704a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 3714a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3724a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: int Main.$opt$noinline$mulNeg(int, int) instruction_simplifier_arm (after) 3734a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 3744a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3754a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko public static int $opt$noinline$mulNeg(int left, int right) { 3764a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko if (doThrow) throw new Error(); 3774a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko return - (left * right); 3784a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko } 3794a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3804a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /** 3814a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko * Test basic merging of `MUL+NEG` into `MULNEG`. 3824a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko */ 3834a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3844a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm64 (before) 3854a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 3864a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 3874a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 3884a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:j\d+>> Neg [<<Mul>>] 3894a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 3904a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3914a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm64 (after) 3924a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 3934a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 3944a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Const0:j\d+>> LongConstant 0 3954a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<MulNeg:j\d+>> MultiplyAccumulate [<<Const0>>,<<Left>>,<<Right>>] kind:Sub 3964a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<MulNeg>>] 3974a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 3984a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm64 (after) 3994a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Mul 4004a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: Neg 4014a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 4024a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM64: long Main.$opt$noinline$mulNeg(long, long) disassembly (after) 4034a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: mneg x{{\d+}}, x{{\d+}}, x{{\d+}} 4044a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 4054a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm (before) 4064a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 4074a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 4084a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 4094a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:j\d+>> Neg [<<Mul>>] 4104a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 4114a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 4124a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm (after) 4134a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Left:j\d+>> ParameterValue 4144a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Right:j\d+>> ParameterValue 4154a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Mul:j\d+>> Mul [<<Left>>,<<Right>>] 4164a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: <<Neg:j\d+>> Neg [<<Mul>>] 4174a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK: Return [<<Neg>>] 4184a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 4194a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-START-ARM: long Main.$opt$noinline$mulNeg(long, long) instruction_simplifier_arm (after) 4204a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko /// CHECK-NOT: MultiplyAccumulate 4214a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko 4224a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko public static long $opt$noinline$mulNeg(long left, long right) { 4234a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko if (doThrow) throw new Error(); 4244a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko return - (left * right); 4254a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko } 426418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames 4279cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulAdd(int[], int[]) instruction_simplifier$after_bce (before) 428f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 429f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 430f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecAdd loop:<<Loop>> outer_loop:none 431f34dd206d0073fb3949be872224420a8488f551fArtem Serov 4329cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulAdd(int[], int[]) instruction_simplifier$after_bce (after) 433f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 434f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecMultiplyAccumulate kind:Add loop:<<Loop>> outer_loop:none 435f34dd206d0073fb3949be872224420a8488f551fArtem Serov 4369cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulAdd(int[], int[]) instruction_simplifier$after_bce (after) 437bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMul 438bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecAdd 439bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 440f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static void SimdMulAdd(int[] array1, int[] array2) { 441f34dd206d0073fb3949be872224420a8488f551fArtem Serov for (int j = 0; j < 100; j++) { 442f34dd206d0073fb3949be872224420a8488f551fArtem Serov array2[j] += 12345 * array1[j]; 443f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 444f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 445f34dd206d0073fb3949be872224420a8488f551fArtem Serov 446bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulAddLong(long[], long[]) instruction_simplifier$after_bce (before) 447bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 448bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 449bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecAdd loop:<<Loop>> outer_loop:none 450bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 451bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulAddLong(long[], long[]) instruction_simplifier$after_bce (after) 452bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 453bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMultiplyAccumulate kind:Add loop:<<Loop>> outer_loop:none 454bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 455bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulAddLong(long[], long[]) instruction_simplifier$after_bce (after) 456bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMul 457bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecAdd 458bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic public static void SimdMulAddLong(long[] array1, long[] array2) { 459bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic for (int j = 0; j < 100; j++) { 460bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic array2[j] += 12345 * array1[j]; 461bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 462bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 463bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 4649cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulSub(int[], int[]) instruction_simplifier$after_bce (before) 465f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 466f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 467f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecSub loop:<<Loop>> outer_loop:none 468f34dd206d0073fb3949be872224420a8488f551fArtem Serov 4699cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulSub(int[], int[]) instruction_simplifier$after_bce (after) 470f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 471f34dd206d0073fb3949be872224420a8488f551fArtem Serov /// CHECK-DAG: VecMultiplyAccumulate kind:Sub loop:<<Loop>> outer_loop:none 472f34dd206d0073fb3949be872224420a8488f551fArtem Serov 4739cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulSub(int[], int[]) instruction_simplifier$after_bce (after) 474bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMul 475bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecSub 476bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 477f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static void SimdMulSub(int[] array1, int[] array2) { 478f34dd206d0073fb3949be872224420a8488f551fArtem Serov for (int j = 0; j < 100; j++) { 479f34dd206d0073fb3949be872224420a8488f551fArtem Serov array2[j] -= 12345 * array1[j]; 480f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 481f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 482f34dd206d0073fb3949be872224420a8488f551fArtem Serov 483bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulSubLong(long[], long[]) instruction_simplifier$after_bce (before) 484bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 485bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 486bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecSub loop:<<Loop>> outer_loop:none 487bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 488bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulSubLong(long[], long[]) instruction_simplifier$after_bce (after) 489bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 490bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMultiplyAccumulate kind:Sub loop:<<Loop>> outer_loop:none 491bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 492bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulSubLong(long[], long[]) instruction_simplifier$after_bce (after) 493bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMul 494bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecSub 495bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic public static void SimdMulSubLong(long[] array1, long[] array2) { 496bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic for (int j = 0; j < 100; j++) { 497bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic array2[j] -= 12345 * array1[j]; 498bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 499bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 500bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 5019cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulMultipleUses(int[], int[]) instruction_simplifier$after_bce (before) 502bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 503bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 504bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecSub loop:<<Loop>> outer_loop:none 505bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 5069cb7fe4daf872fd0cb312489af263ebc622033a8Aart Bik /// CHECK-START-{ARM64,MIPS64}: void Main.SimdMulMultipleUses(int[], int[]) instruction_simplifier$after_bce (after) 507bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMultiplyAccumulate 508bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 509f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static void SimdMulMultipleUses(int[] array1, int[] array2) { 510f34dd206d0073fb3949be872224420a8488f551fArtem Serov for (int j = 0; j < 100; j++) { 511f34dd206d0073fb3949be872224420a8488f551fArtem Serov int temp = 12345 * array1[j]; 512f34dd206d0073fb3949be872224420a8488f551fArtem Serov array2[j] -= temp; 513f34dd206d0073fb3949be872224420a8488f551fArtem Serov array1[j] = temp; 514f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 515f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 516f34dd206d0073fb3949be872224420a8488f551fArtem Serov 517bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulMultipleUsesLong(long[], long[]) instruction_simplifier$after_bce (before) 518bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: Phi loop:<<Loop:B\d+>> outer_loop:none 519bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecMul loop:<<Loop>> outer_loop:none 520bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-DAG: VecSub loop:<<Loop>> outer_loop:none 521bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 522bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-START-MIPS64: void Main.SimdMulMultipleUsesLong(long[], long[]) instruction_simplifier$after_bce (after) 523bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic /// CHECK-NOT: VecMultiplyAccumulate 524bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic public static void SimdMulMultipleUsesLong(long[] array1, long[] array2) { 525bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic for (int j = 0; j < 100; j++) { 526bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic long temp = 12345 * array1[j]; 527bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic array2[j] -= temp; 528bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic array1[j] = temp; 529bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 530bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 531bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 532f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static final int ARRAY_SIZE = 1000; 533f34dd206d0073fb3949be872224420a8488f551fArtem Serov 534f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static void initArray(int[] array) { 535f34dd206d0073fb3949be872224420a8488f551fArtem Serov for (int i = 0; i < ARRAY_SIZE; i++) { 536f34dd206d0073fb3949be872224420a8488f551fArtem Serov array[i] = i; 537f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 538f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 539f34dd206d0073fb3949be872224420a8488f551fArtem Serov 540bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic public static void initArrayLong(long[] array) { 541bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic for (int i = 0; i < ARRAY_SIZE; i++) { 542bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic array[i] = i; 543bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 544bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 545bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 546f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static int calcArraySum(int[] array) { 547f34dd206d0073fb3949be872224420a8488f551fArtem Serov int sum = 0; 548f34dd206d0073fb3949be872224420a8488f551fArtem Serov for (int i = 0; i < ARRAY_SIZE; i++) { 549f34dd206d0073fb3949be872224420a8488f551fArtem Serov sum += array[i]; 550f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 551f34dd206d0073fb3949be872224420a8488f551fArtem Serov return sum; 552f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 553f34dd206d0073fb3949be872224420a8488f551fArtem Serov 554bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic public static long calcArraySumLong(long[] array) { 555bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic long sum = 0; 556bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic for (int i = 0; i < ARRAY_SIZE; i++) { 557bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic sum += array[i]; 558bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 559bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic return sum; 560bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic } 561bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 562f34dd206d0073fb3949be872224420a8488f551fArtem Serov public static void testSimdMultiplyAccumulate() { 563f34dd206d0073fb3949be872224420a8488f551fArtem Serov int[] array1 = new int[ARRAY_SIZE]; 564f34dd206d0073fb3949be872224420a8488f551fArtem Serov int[] array2 = new int[ARRAY_SIZE]; 565bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic long[] array3 = new long[ARRAY_SIZE]; 566bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic long[] array4 = new long[ARRAY_SIZE]; 567f34dd206d0073fb3949be872224420a8488f551fArtem Serov 568f34dd206d0073fb3949be872224420a8488f551fArtem Serov initArray(array1); 569f34dd206d0073fb3949be872224420a8488f551fArtem Serov initArray(array2); 570f34dd206d0073fb3949be872224420a8488f551fArtem Serov SimdMulSub(array1, array2); 571f34dd206d0073fb3949be872224420a8488f551fArtem Serov assertIntEquals(-60608250, calcArraySum(array2)); 572f34dd206d0073fb3949be872224420a8488f551fArtem Serov 573bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic initArrayLong(array3); 574bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic initArrayLong(array4); 575bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic SimdMulSubLong(array3, array4); 576bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic assertLongEquals(-60608250, calcArraySumLong(array4)); 577bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 578f34dd206d0073fb3949be872224420a8488f551fArtem Serov initArray(array1); 579f34dd206d0073fb3949be872224420a8488f551fArtem Serov initArray(array2); 580f34dd206d0073fb3949be872224420a8488f551fArtem Serov SimdMulAdd(array1, array2); 581f34dd206d0073fb3949be872224420a8488f551fArtem Serov assertIntEquals(61607250, calcArraySum(array2)); 582bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic 583bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic initArrayLong(array3); 584bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic initArrayLong(array4); 585bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic SimdMulAddLong(array3, array4); 586bc5460b850a0fa2d8dcf6c8d36b0eb86f8fe46a8Lena Djokic assertLongEquals(61607250, calcArraySumLong(array4)); 587f34dd206d0073fb3949be872224420a8488f551fArtem Serov } 588f34dd206d0073fb3949be872224420a8488f551fArtem Serov 589418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames public static void main(String[] args) { 590418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertIntEquals(7, $opt$noinline$mulAdd(1, 2, 3)); 591418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertLongEquals(-26, $opt$noinline$mulSub(4, 5, 6)); 592418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertIntEquals(79, $opt$noinline$multipleUses1(7, 8, 9)); 593418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertLongEquals(20, $opt$noinline$multipleUses2(10, 11, 12)); 594418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertIntEquals(195, $opt$noinline$mulPlusOne(13, 14)); 595418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames assertLongEquals(-225, $opt$noinline$mulMinusOne(15, 16)); 5964a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko assertIntEquals(-306, $opt$noinline$mulNeg(17, 18)); 5974a0dad67867f389e01a5a6c0fe381d210f687c0dArtem Udovichenko assertLongEquals(-380, $opt$noinline$mulNeg(19, 20)); 598f34dd206d0073fb3949be872224420a8488f551fArtem Serov 599f34dd206d0073fb3949be872224420a8488f551fArtem Serov testSimdMultiplyAccumulate(); 600418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames } 601418318f4d50e0cfc2d54330d7623ee030d4d727dAlexandre Rames} 602