mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2024-12-19 01:34:32 +00:00
48e1bd7287
sequence - AArch64 target support This patch turns off madd/msub generation in the DAGCombiner and generates them in the MachineCombiner instead. It replaces the original code sequence with the combined sequence when it is beneficial to do so. When there is no machine model support it always generates the madd/msub instruction. This is true also when the objective is to optimize for code size: when the combined sequence is shorter is always chosen and does not get evaluated. When there is a machine model the combined instruction sequence is evaluated for critical path and resource length using machine trace metrics and the original code sequence is replaced when it is determined to be faster. rdar://16319955 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@214669 91177308-0d34-0410-b5e6-96231b3b80d8
164 lines
4.4 KiB
LLVM
164 lines
4.4 KiB
LLVM
; RUN: llc -verify-machineinstrs -o - %s -mtriple=arm64-apple-ios7.0 -mcpu=cyclone | FileCheck %s
|
|
|
|
define i32 @test_madd32(i32 %val0, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_madd32:
|
|
%mid = mul i32 %val1, %val2
|
|
%res = add i32 %val0, %mid
|
|
; CHECK: madd {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i32 %res
|
|
}
|
|
|
|
define i64 @test_madd64(i64 %val0, i64 %val1, i64 %val2) {
|
|
; CHECK-LABEL: test_madd64:
|
|
%mid = mul i64 %val1, %val2
|
|
%res = add i64 %val0, %mid
|
|
; CHECK: madd {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i32 @test_msub32(i32 %val0, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_msub32:
|
|
%mid = mul i32 %val1, %val2
|
|
%res = sub i32 %val0, %mid
|
|
; CHECK: msub {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i32 %res
|
|
}
|
|
|
|
define i64 @test_msub64(i64 %val0, i64 %val1, i64 %val2) {
|
|
; CHECK-LABEL: test_msub64:
|
|
%mid = mul i64 %val1, %val2
|
|
%res = sub i64 %val0, %mid
|
|
; CHECK: msub {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_smaddl(i64 %acc, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_smaddl:
|
|
%ext1 = sext i32 %val1 to i64
|
|
%ext2 = sext i32 %val2 to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = add i64 %acc, %prod
|
|
; CHECK: smaddl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_smsubl(i64 %acc, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_smsubl:
|
|
%ext1 = sext i32 %val1 to i64
|
|
%ext2 = sext i32 %val2 to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = sub i64 %acc, %prod
|
|
; CHECK: smsubl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_umaddl(i64 %acc, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_umaddl:
|
|
%ext1 = zext i32 %val1 to i64
|
|
%ext2 = zext i32 %val2 to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = add i64 %acc, %prod
|
|
; CHECK: umaddl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_umsubl(i64 %acc, i32 %val1, i32 %val2) {
|
|
; CHECK-LABEL: test_umsubl:
|
|
%ext1 = zext i32 %val1 to i64
|
|
%ext2 = zext i32 %val2 to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = sub i64 %acc, %prod
|
|
; CHECK: umsubl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_smulh(i64 %lhs, i64 %rhs) {
|
|
; CHECK-LABEL: test_smulh:
|
|
%ext1 = sext i64 %lhs to i128
|
|
%ext2 = sext i64 %rhs to i128
|
|
%res = mul i128 %ext1, %ext2
|
|
%high = lshr i128 %res, 64
|
|
%val = trunc i128 %high to i64
|
|
; CHECK: smulh {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %val
|
|
}
|
|
|
|
define i64 @test_umulh(i64 %lhs, i64 %rhs) {
|
|
; CHECK-LABEL: test_umulh:
|
|
%ext1 = zext i64 %lhs to i128
|
|
%ext2 = zext i64 %rhs to i128
|
|
%res = mul i128 %ext1, %ext2
|
|
%high = lshr i128 %res, 64
|
|
%val = trunc i128 %high to i64
|
|
; CHECK: umulh {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %val
|
|
}
|
|
|
|
define i32 @test_mul32(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_mul32:
|
|
%res = mul i32 %lhs, %rhs
|
|
; CHECK: mul {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i32 %res
|
|
}
|
|
|
|
define i64 @test_mul64(i64 %lhs, i64 %rhs) {
|
|
; CHECK-LABEL: test_mul64:
|
|
%res = mul i64 %lhs, %rhs
|
|
; CHECK: mul {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i32 @test_mneg32(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_mneg32:
|
|
%prod = mul i32 %lhs, %rhs
|
|
%res = sub i32 0, %prod
|
|
; CHECK: mneg {{w[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i32 %res
|
|
}
|
|
|
|
define i64 @test_mneg64(i64 %lhs, i64 %rhs) {
|
|
; CHECK-LABEL: test_mneg64:
|
|
%prod = mul i64 %lhs, %rhs
|
|
%res = sub i64 0, %prod
|
|
; CHECK: mneg {{x[0-9]+}}, {{x[0-9]+}}, {{x[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_smull(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_smull:
|
|
%ext1 = sext i32 %lhs to i64
|
|
%ext2 = sext i32 %rhs to i64
|
|
%res = mul i64 %ext1, %ext2
|
|
; CHECK: smull {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_umull(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_umull:
|
|
%ext1 = zext i32 %lhs to i64
|
|
%ext2 = zext i32 %rhs to i64
|
|
%res = mul i64 %ext1, %ext2
|
|
; CHECK: umull {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_smnegl(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_smnegl:
|
|
%ext1 = sext i32 %lhs to i64
|
|
%ext2 = sext i32 %rhs to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = sub i64 0, %prod
|
|
; CHECK: smnegl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i64 %res
|
|
}
|
|
|
|
define i64 @test_umnegl(i32 %lhs, i32 %rhs) {
|
|
; CHECK-LABEL: test_umnegl:
|
|
%ext1 = zext i32 %lhs to i64
|
|
%ext2 = zext i32 %rhs to i64
|
|
%prod = mul i64 %ext1, %ext2
|
|
%res = sub i64 0, %prod
|
|
; CHECK: umnegl {{x[0-9]+}}, {{w[0-9]+}}, {{w[0-9]+}}
|
|
ret i64 %res
|
|
}
|