Skip to content

Commit e043195

Browse files
[AArch64] Add support for intent to read prefetch intrinsic (#179709)
This patch adds support in Clang for the PRFM IR instruction, by adding the following builtin: void __pldir(void const *addr); This builtin is described in the following ACLE proposal: ARM-software/acle#406
1 parent f22a178 commit e043195

10 files changed

Lines changed: 59 additions & 1 deletion

File tree

clang/include/clang/Basic/BuiltinsAArch64.def

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,8 @@ TARGET_BUILTIN(__builtin_arm_jcvt, "Zid", "nc", "v8.3a")
9696
// Prefetch
9797
BUILTIN(__builtin_arm_prefetch, "vvC*UiUiUiUi", "nc")
9898

99+
BUILTIN(__builtin_arm_prefetch_ir, "vvC*", "nc")
100+
99101
// Range Prefetch
100102
BUILTIN(__builtin_arm_range_prefetch_x, "vvC*UiUiiUiiz", "n")
101103
BUILTIN(__builtin_arm_range_prefetch, "vvC*UiUiWUi", "n")

clang/lib/Headers/arm_acle.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,7 @@ __swp(uint32_t __x, volatile uint32_t *__p) {
115115
#else
116116
#define __plix(cache_level, retention_policy, addr) \
117117
__builtin_arm_prefetch(addr, 0, cache_level, retention_policy, 0)
118+
#define __pldir(addr) __builtin_arm_prefetch_ir(addr)
118119
#endif
119120

120121
/* 7.7 NOP */

clang/test/CodeGen/arm_acle.c

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -186,6 +186,19 @@ void test_pldx_range() {
186186

187187
#endif
188188

189+
#if defined(__ARM_64BIT_STATE)
190+
191+
// AArch64-LABEL: @test_pldir(
192+
// AArch64-NEXT: entry:
193+
// AArch64-NEXT: call void @llvm.aarch64.prefetch.ir(ptr null)
194+
// AArch64-NEXT: ret void
195+
//
196+
void test_pldir() {
197+
__pldir(0);
198+
}
199+
200+
#endif
201+
189202
// AArch32-LABEL: @test_pldx(
190203
// AArch32-NEXT: entry:
191204
// AArch32-NEXT: call void @llvm.prefetch.p0(ptr null, i32 1, i32 3, i32 1)

clang/test/CodeGen/builtins-arm64.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,11 @@ void range_prefetch_x(void) {
111111
// CHECK: call {{.*}} @llvm.aarch64.range.prefetch(ptr null, i32 0, i32 0, i64 0)
112112
}
113113

114+
void read_intent_prefetch() {
115+
// CHECK: call {{.*}} @llvm.aarch64.prefetch.ir(ptr null)
116+
__builtin_arm_prefetch_ir(0);
117+
}
118+
114119
__attribute__((target("v8.5a")))
115120
int32_t jcvt(double v) {
116121
//CHECK-LABEL: @jcvt(

llvm/include/llvm/IR/IntrinsicsAArch64.td

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,11 @@ def int_aarch64_prefetch : Intrinsic<[],
7676
]>,
7777
ClangBuiltin<"__builtin_arm_prefetch">;
7878

79+
def int_aarch64_prefetch_ir : Intrinsic<[], [llvm_ptr_ty],
80+
[IntrHasSideEffects, IntrInaccessibleMemOrArgMemOnly,
81+
IntrWillReturn, ReadOnly<ArgIndex<0>>]>,
82+
ClangBuiltin<"__builtin_arm_prefetch_ir">;
83+
7984
def int_aarch64_range_prefetch : Intrinsic<[],
8085
[llvm_ptr_ty, llvm_i32_ty, llvm_i32_ty, llvm_i64_ty],
8186
[IntrInaccessibleMemOrArgMemOnly, IntrWillReturn, ReadOnly<ArgIndex<0>>,

llvm/lib/Target/AArch64/AArch64ISelLowering.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6321,6 +6321,11 @@ SDValue AArch64TargetLowering::LowerINTRINSIC_VOID(SDValue Op,
63216321
DAG.getTargetConstant(PrfOp, DL, MVT::i32), Addr,
63226322
Metadata);
63236323
}
6324+
case Intrinsic::aarch64_prefetch_ir:
6325+
return DAG.getNode(AArch64ISD::PREFETCH, DL, MVT::Other,
6326+
Op.getOperand(0), // Chain
6327+
DAG.getTargetConstant(24, DL, MVT::i32), // Rt
6328+
Op.getOperand(2)); // Addr
63246329
case Intrinsic::aarch64_sme_str:
63256330
case Intrinsic::aarch64_sme_ldr: {
63266331
return LowerSMELdrStr(Op, DAG, IntNo == Intrinsic::aarch64_sme_ldr);

llvm/lib/Target/AArch64/AArch64SystemOperands.td

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -435,6 +435,7 @@ let Requires = [{ {AArch64::FeaturePRFM_SLC} }] in {
435435
def : PRFM<"pst", 0b10, "slc", 0b11, "keep", 0b0>;
436436
def : PRFM<"pst", 0b10, "slc", 0b11, "strm", 0b1>;
437437
}
438+
def : PRFM<"ir", 0b11, "", 0b00, "", 0b0>;
438439

439440
//===----------------------------------------------------------------------===//
440441
// SVE Prefetch instruction options.

llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1769,6 +1769,12 @@ bool AArch64LegalizerInfo::legalizeIntrinsic(LegalizerHelper &Helper,
17691769
MI.eraseFromParent();
17701770
return true;
17711771
}
1772+
case Intrinsic::aarch64_prefetch_ir: {
1773+
auto &AddrVal = MI.getOperand(1);
1774+
MIB.buildInstr(AArch64::G_AARCH64_PREFETCH).addImm(24).add(AddrVal);
1775+
MI.eraseFromParent();
1776+
return true;
1777+
}
17721778
case Intrinsic::aarch64_neon_uaddv:
17731779
case Intrinsic::aarch64_neon_saddv:
17741780
case Intrinsic::aarch64_neon_umaxv:
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 6
2+
; RUN: llc -mtriple=aarch64 -mattr=+v9a -mattr=+pcdphint --global-isel=0 < %s | FileCheck %s
3+
; RUN: llc -mtriple=aarch64 -mattr=+v9a -mattr=+pcdphint --global-isel=1 < %s | FileCheck %s
4+
5+
define void @read_intent_prefetch(ptr %a, i64 %metadata) {
6+
; CHECK-LABEL: read_intent_prefetch:
7+
; CHECK: // %bb.0:
8+
; CHECK-NEXT: prfm ir, [x0]
9+
; CHECK-NEXT: ret
10+
call void @llvm.aarch64.prefetch.ir(ptr %a)
11+
ret void
12+
}

llvm/test/MC/AArch64/armv9.6a-pcdphint.s

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
// RUN: not llvm-mc -triple=aarch64 -show-encoding < %s 2>&1 \
44
// RUN: | FileCheck %s --check-prefixes=CHECK-ERROR
55
// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+pcdphint < %s \
6-
// RUN: | llvm-objdump -d --mattr=+pcdphint - | FileCheck %s --check-prefix=CHECK-INST
6+
// RUN: | llvm-objdump -d --mattr=+pcdphint --no-print-imm-hex - | FileCheck %s --check-prefix=CHECK-INST
77
// RUN: llvm-mc -triple=aarch64 -filetype=obj -mattr=+pcdphint < %s \
88
// RUN: | llvm-objdump -d --mattr=-pcdphint - | FileCheck %s --check-prefix=CHECK-UNKNOWN
99
// Disassemble encoding and check the re-encoding (-show-encoding) matches.
@@ -23,3 +23,11 @@ stshh strm
2323
// CHECK-ENCODING: encoding: [0x3f,0x96,0x01,0xd5]
2424
// CHECK-ERROR: error: instruction requires: pcdphint
2525
// CHECK-UNKNOWN: d501963f msr S0_1_C9_C6_1, xzr
26+
27+
prfm ir, [x0]
28+
// CHECK-INST: prfm ir, [x0]
29+
// CHECK-ENCODING: [0x18,0x00,0x80,0xf9]
30+
31+
prfm ir, [x2, #800]
32+
// CHECK-INST: prfm ir, [x2, #800]
33+
// CHECK-ENCODING: [0x58,0x90,0x81,0xf9]

0 commit comments

Comments
 (0)