-
Notifications
You must be signed in to change notification settings - Fork 13.6k
[IRTranslator] Handle ptrtoaddr #139601
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: users/arichardson/spr/main.irtranslator-handle-ptrtoaddr
Are you sure you want to change the base?
[IRTranslator] Handle ptrtoaddr #139601
Conversation
Created using spr 1.3.6-beta.1
@llvm/pr-subscribers-backend-amdgpu Author: Alexander Richardson (arichardson) ChangesWe lower ptrtoaddr by emitting a G_PTRTOINT, truncating that to the This has exposed an issue in the GlobalIsel postlegalizer combines where Full diff: https://github.com/llvm/llvm-project/pull/139601.diff 3 Files Affected:
diff --git a/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h b/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
index fcdc733d92c7f..41d03c9fb3ed5 100644
--- a/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
+++ b/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
@@ -486,9 +486,7 @@ class IRTranslator : public MachineFunctionPass {
bool translatePtrToInt(const User &U, MachineIRBuilder &MIRBuilder) {
return translateCast(TargetOpcode::G_PTRTOINT, U, MIRBuilder);
}
- bool translatePtrToAddr(const User &U, MachineIRBuilder &MIRBuilder) {
- return translatePtrToInt(U, MIRBuilder);
- }
+ bool translatePtrToAddr(const User &U, MachineIRBuilder &MIRBuilder);
bool translateTrunc(const User &U, MachineIRBuilder &MIRBuilder) {
return translateCast(TargetOpcode::G_TRUNC, U, MIRBuilder);
}
diff --git a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
index 8ab2533afc15f..5666c9e9f45bc 100644
--- a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
+++ b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
@@ -1583,6 +1583,26 @@ bool IRTranslator::translateCast(unsigned Opcode, const User &U,
return true;
}
+bool IRTranslator::translatePtrToAddr(const User &U,
+ MachineIRBuilder &MIRBuilder) {
+ if (containsBF16Type(U))
+ return false;
+
+ uint32_t Flags = 0;
+ if (const Instruction *I = dyn_cast<Instruction>(&U))
+ Flags = MachineInstr::copyFlagsFromInstruction(*I);
+
+ Register Op = getOrCreateVReg(*U.getOperand(0));
+ Type *PtrTy = U.getOperand(0)->getType();
+ LLT AddrTy = getLLTForType(*DL->getIndexType(PtrTy), *DL);
+ auto IntPtrTy = getLLTForType(*DL->getIntPtrType(PtrTy), *DL);
+ auto PtrToInt = MIRBuilder.buildPtrToInt(IntPtrTy, Op);
+ PtrToInt->setFlags(Flags);
+ auto Addr = MIRBuilder.buildTrunc(AddrTy, PtrToInt.getReg(0));
+ MIRBuilder.buildZExtOrTrunc(getOrCreateVReg(U), Addr.getReg(0));
+ return true;
+}
+
bool IRTranslator::translateGetElementPtr(const User &U,
MachineIRBuilder &MIRBuilder) {
Value &Op0 = *U.getOperand(0);
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll
new file mode 100644
index 0000000000000..30f9dbfcaacf8
--- /dev/null
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll
@@ -0,0 +1,187 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 5
+; RUN: llc -mtriple=amdgcn -global-isel -verify-machineinstrs --print-changed --debug < %s | FileCheck %s --check-prefixes=CHECK,GISEL
+; RUN: llc -mtriple=amdgcn -verify-machineinstrs < %s | FileCheck %s --check-prefixes=CHECK,SDAG
+;; Check that we can lower ptrtoaddr differently from ptrtoint.
+;; Includes an ignored argument so the registers actually need to be written
+
+define i128 @ptrtoint(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i128
+ ret i128 %ret
+}
+
+define i48 @ptrtoaddr(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoaddr:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i48
+ ret i48 %ret
+}
+
+define <2 x i128> @ptrtoint_vec(ptr addrspace(8) %ignored, <2 x ptr addrspace(8)> %ptr) {
+; GISEL-LABEL: ptrtoint_vec:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, v8
+; GISEL-NEXT: v_mov_b32_e32 v5, v9
+; GISEL-NEXT: v_mov_b32_e32 v6, v10
+; GISEL-NEXT: v_mov_b32_e32 v7, v11
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_vec:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_mov_b32_e32 v4, v8
+; SDAG-NEXT: v_mov_b32_e32 v5, v9
+; SDAG-NEXT: v_mov_b32_e32 v6, v10
+; SDAG-NEXT: v_mov_b32_e32 v7, v11
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint <2 x ptr addrspace(8)> %ptr to <2 x i128>
+ ret <2 x i128> %ret
+}
+
+define <2 x i64> @ptrtoaddr_vec(ptr addrspace(8) %ignored, <2 x ptr addrspace(8)> %ptr) {
+; GISEL-LABEL: ptrtoaddr_vec:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v8
+; GISEL-NEXT: v_mov_b32_e32 v3, v9
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr_vec:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v2, v8
+; SDAG-NEXT: v_and_b32_e32 v1, 0xffff, v5
+; SDAG-NEXT: v_and_b32_e32 v3, 0xffff, v9
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr <2 x ptr addrspace(8)> %ptr to <2 x i64>
+ ret <2 x i64> %ret
+}
+
+define i256 @ptrtoint_ext(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint_ext:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, 0
+; GISEL-NEXT: v_mov_b32_e32 v5, 0
+; GISEL-NEXT: v_mov_b32_e32 v6, 0
+; GISEL-NEXT: v_mov_b32_e32 v7, 0
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_ext:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_mov_b32_e32 v4, 0
+; SDAG-NEXT: v_mov_b32_e32 v5, 0
+; SDAG-NEXT: v_mov_b32_e32 v6, 0
+; SDAG-NEXT: v_mov_b32_e32 v7, 0
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i256
+ ret i256 %ret
+}
+
+;; FIXME: this is wrong for the GlobalISel case, we are removing the trunc:
+;; https://github.com/llvm/llvm-project/issues/139598
+define i256 @ptrtoaddr_ext(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoaddr_ext:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, 0
+; GISEL-NEXT: v_mov_b32_e32 v5, 0
+; GISEL-NEXT: v_mov_b32_e32 v6, 0
+; GISEL-NEXT: v_mov_b32_e32 v7, 0
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr_ext:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_and_b32_e32 v1, 0xffff, v5
+; SDAG-NEXT: v_mov_b32_e32 v2, 0
+; SDAG-NEXT: v_mov_b32_e32 v3, 0
+; SDAG-NEXT: v_mov_b32_e32 v4, 0
+; SDAG-NEXT: v_mov_b32_e32 v5, 0
+; SDAG-NEXT: v_mov_b32_e32 v6, 0
+; SDAG-NEXT: v_mov_b32_e32 v7, 0
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i256
+ ret i256 %ret
+}
+
+define i64 @ptrtoint_trunc(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint_trunc:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_trunc:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i64
+ ret i64 %ret
+}
+
+define i16 @ptrtoaddr_trunc(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; CHECK-LABEL: ptrtoaddr_trunc:
+; CHECK: ; %bb.0:
+; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; CHECK-NEXT: v_mov_b32_e32 v0, v4
+; CHECK-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i16
+ ret i16 %ret
+}
|
@llvm/pr-subscribers-llvm-globalisel Author: Alexander Richardson (arichardson) ChangesWe lower ptrtoaddr by emitting a G_PTRTOINT, truncating that to the This has exposed an issue in the GlobalIsel postlegalizer combines where Full diff: https://github.com/llvm/llvm-project/pull/139601.diff 3 Files Affected:
diff --git a/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h b/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
index fcdc733d92c7f..41d03c9fb3ed5 100644
--- a/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
+++ b/llvm/include/llvm/CodeGen/GlobalISel/IRTranslator.h
@@ -486,9 +486,7 @@ class IRTranslator : public MachineFunctionPass {
bool translatePtrToInt(const User &U, MachineIRBuilder &MIRBuilder) {
return translateCast(TargetOpcode::G_PTRTOINT, U, MIRBuilder);
}
- bool translatePtrToAddr(const User &U, MachineIRBuilder &MIRBuilder) {
- return translatePtrToInt(U, MIRBuilder);
- }
+ bool translatePtrToAddr(const User &U, MachineIRBuilder &MIRBuilder);
bool translateTrunc(const User &U, MachineIRBuilder &MIRBuilder) {
return translateCast(TargetOpcode::G_TRUNC, U, MIRBuilder);
}
diff --git a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
index 8ab2533afc15f..5666c9e9f45bc 100644
--- a/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
+++ b/llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
@@ -1583,6 +1583,26 @@ bool IRTranslator::translateCast(unsigned Opcode, const User &U,
return true;
}
+bool IRTranslator::translatePtrToAddr(const User &U,
+ MachineIRBuilder &MIRBuilder) {
+ if (containsBF16Type(U))
+ return false;
+
+ uint32_t Flags = 0;
+ if (const Instruction *I = dyn_cast<Instruction>(&U))
+ Flags = MachineInstr::copyFlagsFromInstruction(*I);
+
+ Register Op = getOrCreateVReg(*U.getOperand(0));
+ Type *PtrTy = U.getOperand(0)->getType();
+ LLT AddrTy = getLLTForType(*DL->getIndexType(PtrTy), *DL);
+ auto IntPtrTy = getLLTForType(*DL->getIntPtrType(PtrTy), *DL);
+ auto PtrToInt = MIRBuilder.buildPtrToInt(IntPtrTy, Op);
+ PtrToInt->setFlags(Flags);
+ auto Addr = MIRBuilder.buildTrunc(AddrTy, PtrToInt.getReg(0));
+ MIRBuilder.buildZExtOrTrunc(getOrCreateVReg(U), Addr.getReg(0));
+ return true;
+}
+
bool IRTranslator::translateGetElementPtr(const User &U,
MachineIRBuilder &MIRBuilder) {
Value &Op0 = *U.getOperand(0);
diff --git a/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll b/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll
new file mode 100644
index 0000000000000..30f9dbfcaacf8
--- /dev/null
+++ b/llvm/test/CodeGen/AMDGPU/GlobalISel/ptrtoint-ptrtoaddr-p8.ll
@@ -0,0 +1,187 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 5
+; RUN: llc -mtriple=amdgcn -global-isel -verify-machineinstrs --print-changed --debug < %s | FileCheck %s --check-prefixes=CHECK,GISEL
+; RUN: llc -mtriple=amdgcn -verify-machineinstrs < %s | FileCheck %s --check-prefixes=CHECK,SDAG
+;; Check that we can lower ptrtoaddr differently from ptrtoint.
+;; Includes an ignored argument so the registers actually need to be written
+
+define i128 @ptrtoint(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i128
+ ret i128 %ret
+}
+
+define i48 @ptrtoaddr(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoaddr:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i48
+ ret i48 %ret
+}
+
+define <2 x i128> @ptrtoint_vec(ptr addrspace(8) %ignored, <2 x ptr addrspace(8)> %ptr) {
+; GISEL-LABEL: ptrtoint_vec:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, v8
+; GISEL-NEXT: v_mov_b32_e32 v5, v9
+; GISEL-NEXT: v_mov_b32_e32 v6, v10
+; GISEL-NEXT: v_mov_b32_e32 v7, v11
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_vec:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_mov_b32_e32 v4, v8
+; SDAG-NEXT: v_mov_b32_e32 v5, v9
+; SDAG-NEXT: v_mov_b32_e32 v6, v10
+; SDAG-NEXT: v_mov_b32_e32 v7, v11
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint <2 x ptr addrspace(8)> %ptr to <2 x i128>
+ ret <2 x i128> %ret
+}
+
+define <2 x i64> @ptrtoaddr_vec(ptr addrspace(8) %ignored, <2 x ptr addrspace(8)> %ptr) {
+; GISEL-LABEL: ptrtoaddr_vec:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v8
+; GISEL-NEXT: v_mov_b32_e32 v3, v9
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr_vec:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v2, v8
+; SDAG-NEXT: v_and_b32_e32 v1, 0xffff, v5
+; SDAG-NEXT: v_and_b32_e32 v3, 0xffff, v9
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr <2 x ptr addrspace(8)> %ptr to <2 x i64>
+ ret <2 x i64> %ret
+}
+
+define i256 @ptrtoint_ext(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint_ext:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, 0
+; GISEL-NEXT: v_mov_b32_e32 v5, 0
+; GISEL-NEXT: v_mov_b32_e32 v6, 0
+; GISEL-NEXT: v_mov_b32_e32 v7, 0
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_ext:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v3, v7
+; SDAG-NEXT: v_mov_b32_e32 v2, v6
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_mov_b32_e32 v4, 0
+; SDAG-NEXT: v_mov_b32_e32 v5, 0
+; SDAG-NEXT: v_mov_b32_e32 v6, 0
+; SDAG-NEXT: v_mov_b32_e32 v7, 0
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i256
+ ret i256 %ret
+}
+
+;; FIXME: this is wrong for the GlobalISel case, we are removing the trunc:
+;; https://github.com/llvm/llvm-project/issues/139598
+define i256 @ptrtoaddr_ext(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoaddr_ext:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: v_mov_b32_e32 v2, v6
+; GISEL-NEXT: v_mov_b32_e32 v3, v7
+; GISEL-NEXT: v_mov_b32_e32 v4, 0
+; GISEL-NEXT: v_mov_b32_e32 v5, 0
+; GISEL-NEXT: v_mov_b32_e32 v6, 0
+; GISEL-NEXT: v_mov_b32_e32 v7, 0
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoaddr_ext:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: v_and_b32_e32 v1, 0xffff, v5
+; SDAG-NEXT: v_mov_b32_e32 v2, 0
+; SDAG-NEXT: v_mov_b32_e32 v3, 0
+; SDAG-NEXT: v_mov_b32_e32 v4, 0
+; SDAG-NEXT: v_mov_b32_e32 v5, 0
+; SDAG-NEXT: v_mov_b32_e32 v6, 0
+; SDAG-NEXT: v_mov_b32_e32 v7, 0
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i256
+ ret i256 %ret
+}
+
+define i64 @ptrtoint_trunc(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; GISEL-LABEL: ptrtoint_trunc:
+; GISEL: ; %bb.0:
+; GISEL-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; GISEL-NEXT: v_mov_b32_e32 v0, v4
+; GISEL-NEXT: v_mov_b32_e32 v1, v5
+; GISEL-NEXT: s_setpc_b64 s[30:31]
+;
+; SDAG-LABEL: ptrtoint_trunc:
+; SDAG: ; %bb.0:
+; SDAG-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; SDAG-NEXT: v_mov_b32_e32 v1, v5
+; SDAG-NEXT: v_mov_b32_e32 v0, v4
+; SDAG-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoint ptr addrspace(8) %ptr to i64
+ ret i64 %ret
+}
+
+define i16 @ptrtoaddr_trunc(ptr addrspace(8) %ignored, ptr addrspace(8) %ptr) {
+; CHECK-LABEL: ptrtoaddr_trunc:
+; CHECK: ; %bb.0:
+; CHECK-NEXT: s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
+; CHECK-NEXT: v_mov_b32_e32 v0, v4
+; CHECK-NEXT: s_setpc_b64 s[30:31]
+ %ret = ptrtoaddr ptr addrspace(8) %ptr to i16
+ ret i16 %ret
+}
|
Type *PtrTy = U.getOperand(0)->getType(); | ||
LLT AddrTy = getLLTForType(*DL->getIndexType(PtrTy), *DL); | ||
auto IntPtrTy = getLLTForType(*DL->getIntPtrType(PtrTy), *DL); | ||
auto PtrToInt = MIRBuilder.buildPtrToInt(IntPtrTy, Op); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not introduce a G_PTRTOADDR?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would be perfectly happy with that, not familar with GlobalIsel so not sure what the threshold is for adding a new operation. Happy to do that if it's cleaner?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In general I expect a 1:1 mapping with IR opcodes
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I tried this in #140300 but it seems to me that adding this node introduces a lot of complexity for no real gain. I don't think we track provenance at the MIR level, so having the dedicated node probably doesn't enable much optimization over G_PTRTOINT+G_TRUNC?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe, but what if some legalization wants to introduce a ptrtoaddr? Are there any cases where that's useful?
We lower ptrtoaddr by emitting a G_PTRTOINT, truncating that to the
address size and then truncate/zext to the final integer type.
This has exposed an issue in the GlobalIsel postlegalizer combines where
the truncate is incorrectly being removed.
See #139598