Conanap created this revision.
Herald added subscribers: steven.zhang, shchenz, kbarton, hiraditya, nemanjai.
Conanap requested review of this revision.
Herald added projects: clang, LLVM.
Herald added subscribers: llvm-commits, cfe-commits.

Implemented builtins for mtmsr, mfspr, mtspr on PowerPC;
the patch is intended for XL Compatibility.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D106130

Files:
  clang/include/clang/Basic/BuiltinsPPC.def
  clang/lib/Basic/Targets/PPC.cpp
  clang/lib/CodeGen/CGBuiltin.cpp
  clang/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.c
  llvm/include/llvm/IR/IntrinsicsPowerPC.td
  llvm/lib/Target/PowerPC/PPCInstr64Bit.td
  llvm/lib/Target/PowerPC/PPCInstrInfo.td
  llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-64bit-only.ll
  llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-aix32.ll
  llvm/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.ll

Index: llvm/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.ll
===================================================================
--- llvm/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.ll
+++ llvm/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.ll
@@ -1,15 +1,20 @@
 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; NOTE: Had to manually modify the last test case (mtmsr) to allow the
+; NOTE: common check of mtmsr instead of 4 different check prefixes
 ; RUN: llc -verify-machineinstrs -mtriple=powerpc64le-unknown-linux-gnu \
 ; RUN:   -mcpu=pwr8 < %s | FileCheck %s
 ; RUN: llc -verify-machineinstrs -mtriple=powerpc64-unknown-linux-gnu \
 ; RUN:   -mcpu=pwr7 < %s | FileCheck %s
-; RUN: llc -verify-machineinstrs -mtriple=powerpc-unknown-aix \
-; RUN:   -mcpu=pwr7 < %s | FileCheck %s --check-prefix=CHECK-AIX
 ; RUN: llc -verify-machineinstrs -mtriple=powerpc64-unknown-aix \
 ; RUN:   -mcpu=pwr7 < %s | FileCheck %s
+; RUN: llc -verify-machineinstrs -mtriple=powerpc-unknown-aix \
+; RUN:   -mcpu=pwr7 < %s | FileCheck %s --check-prefix=CHECK-32BIT
 
 declare i32 @llvm.ppc.mftbu()
 declare i32 @llvm.ppc.mfmsr()
+declare void @llvm.ppc.mtmsr(i32)
+
+@ula = external local_unnamed_addr global i64, align 8
 
 define dso_local zeroext i32 @test_mftbu() {
 ; CHECK-LABEL: test_mftbu:
@@ -18,10 +23,10 @@
 ; CHECK-NEXT:    clrldi 3, 3, 32
 ; CHECK-NEXT:    blr
 ;
-; CHECK-AIX-LABEL: test_mftbu:
-; CHECK-AIX:       # %bb.0: # %entry
-; CHECK-AIX-NEXT:    mftbu 3
-; CHECK-AIX-NEXT:    blr
+; CHECK-32BIT-LABEL: test_mftbu:
+; CHECK-32BIT:       # %bb.0: # %entry
+; CHECK-32BIT-NEXT:    mftbu 3
+; CHECK-32BIT-NEXT:    blr
 entry:
   %0 = tail call i32 @llvm.ppc.mftbu()
   ret i32 %0
@@ -34,13 +39,31 @@
 ; CHECK-NEXT:    clrldi 3, 3, 32
 ; CHECK-NEXT:    blr
 ;
-; CHECK-AIX-LABEL: test_mfmsr:
-; CHECK-AIX:       # %bb.0: # %entry
-; CHECK-AIX-NEXT:    mfmsr 4
-; CHECK-AIX-NEXT:    li 3, 0
-; CHECK-AIX-NEXT:    blr
+; CHECK-32BIT-LABEL: test_mfmsr:
+; CHECK-32BIT:       # %bb.0: # %entry
+; CHECK-32BIT-NEXT:    mfmsr 4
+; CHECK-32BIT-NEXT:    li 3, 0
+; CHECK-32BIT-NEXT:    blr
 entry:
   %0 = tail call i32 @llvm.ppc.mfmsr()
   %conv = zext i32 %0 to i64
   ret i64 %conv
 }
+
+define dso_local void @test_mtmsr() {
+; CHECK-LABEL: test_mtmsr:
+; CHECK:    mtmsr 3
+; CHECK-NEXT:    blr
+;
+; CHECK-32BIT-LABEL: test_mtmsr:
+; CHECK-32BIT:       # %bb.0: # %entry
+; CHECK-32BIT-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-32BIT-NEXT:    lwz 3, 4(3)
+; CHECK-32BIT-NEXT:    mtmsr 3, 0
+; CHECK-32BIT-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  %conv = trunc i64 %0 to i32
+  call void @llvm.ppc.mtmsr(i32 %conv)
+  ret void
+}
Index: llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-aix32.ll
===================================================================
--- /dev/null
+++ llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-aix32.ll
@@ -0,0 +1,123 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; RUN: llc -verify-machineinstrs -mtriple=powerpc-unknown-aix \
+; RUN:   -mcpu=pwr7 < %s | FileCheck %s
+
+declare i32 @llvm.ppc.mfspr.i32(i32 immarg)
+declare void @llvm.ppc.mtspr.i32(i32 immarg, i32)
+
+@ula = external dso_local global i32, align 4
+
+define dso_local i32 @test_mfxer() {
+; CHECK-LABEL: test_mfxer:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfxer 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = call i32 @llvm.ppc.mfspr.i32(i32 1)
+  ret i32 %0
+}
+
+define dso_local i32 @test_mflr() {
+; CHECK-LABEL: test_mflr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 8
+; CHECK-NEXT:    blr
+entry:
+  %0 = call i32 @llvm.ppc.mfspr.i32(i32 8)
+  ret i32 %0
+}
+
+define dso_local i32 @test_mfctr() {
+; CHECK-LABEL: test_mfctr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 9
+; CHECK-NEXT:    blr
+entry:
+  %0 = call i32 @llvm.ppc.mfspr.i32(i32 9)
+  ret i32 %0
+}
+
+define dso_local i32 @test_mfppr() {
+; CHECK-LABEL: test_mfppr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 896
+; CHECK-NEXT:    blr
+entry:
+  %0 = call i32 @llvm.ppc.mfspr.i32(i32 896)
+  ret i32 %0
+}
+
+define dso_local i32 @test_mfppr32() {
+; CHECK-LABEL: test_mfppr32:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 898
+; CHECK-NEXT:    blr
+entry:
+  %0 = call i32 @llvm.ppc.mfspr.i32(i32 898)
+  ret i32 %0
+}
+
+define dso_local void @test_mtxer() {
+; CHECK-LABEL: test_mtxer:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-NEXT:    lwz 3, 0(3)
+; CHECK-NEXT:    mtxer 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = load i32, i32* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i32(i32 1, i32 %0)
+  ret void
+}
+
+define dso_local void @test_mtlr() {
+; CHECK-LABEL: test_mtlr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-NEXT:    lwz 3, 0(3)
+; CHECK-NEXT:    mtspr 8, 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = load i32, i32* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i32(i32 8, i32 %0)
+  ret void
+}
+
+define dso_local void @test_mtctr() {
+; CHECK-LABEL: test_mtctr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-NEXT:    lwz 3, 0(3)
+; CHECK-NEXT:    mtspr 9, 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = load i32, i32* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i32(i32 9, i32 %0)
+  ret void
+}
+
+define dso_local void @test_mtppr() {
+; CHECK-LABEL: test_mtppr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-NEXT:    lwz 3, 0(3)
+; CHECK-NEXT:    mtspr 896, 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = load i32, i32* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i32(i32 896, i32 %0)
+  ret void
+}
+
+define dso_local void @test_mtppr32() {
+; CHECK-LABEL: test_mtppr32:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    lwz 3, L..C0(2) # @ula
+; CHECK-NEXT:    lwz 3, 0(3)
+; CHECK-NEXT:    mtspr 898, 3
+; CHECK-NEXT:    blr
+entry:
+  %0 = load i32, i32* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i32(i32 898, i32 %0)
+  ret void
+}
Index: llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-64bit-only.ll
===================================================================
--- /dev/null
+++ llvm/test/CodeGen/builtins-ppc-xlcompat-mfspr-mtspr-64bit-only.ll
@@ -0,0 +1,192 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
+; RUN: llc -verify-machineinstrs -mtriple=powerpc64le-unknown-linux-gnu \
+; RUN:   -mcpu=pwr8 < %s | FileCheck %s
+; RUN: llc -verify-machineinstrs -mtriple=powerpc64-unknown-linux-gnu \
+; RUN:   -mcpu=pwr7 < %s | FileCheck %s
+; RUN: llc -verify-machineinstrs -mtriple=powerpc64-unknown-aix \
+; RUN:   -mcpu=pwr7 < %s | FileCheck %s --check-prefix=CHECK-AIX64
+
+declare i64 @llvm.ppc.mfspr.i64(i32 immarg)
+declare void @llvm.ppc.mtspr.i64(i32 immarg, i64)
+
+@ula = external local_unnamed_addr global i64, align 8
+
+define dso_local i64 @test_mfxer() {
+; CHECK-LABEL: test_mfxer:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfxer 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mfxer:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    mfxer 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = call i64 @llvm.ppc.mfspr.i64(i32 1)
+  ret i64 %0
+}
+
+define dso_local i64 @test_mflr() {
+; CHECK-LABEL: test_mflr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mflr 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mflr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    mfspr 3, 8
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = call i64 @llvm.ppc.mfspr.i64(i32 8)
+  ret i64 %0
+}
+
+define dso_local i64 @test_mfctr() {
+; CHECK-LABEL: test_mfctr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfctr 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mfctr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    mfspr 3, 9
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = call i64 @llvm.ppc.mfspr.i64(i32 9)
+  ret i64 %0
+}
+
+define dso_local i64 @test_mfppr() {
+; CHECK-LABEL: test_mfppr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 896
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mfppr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    mfspr 3, 896
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = call i64 @llvm.ppc.mfspr.i64(i32 896)
+  ret i64 %0
+}
+
+define dso_local i64 @test_mfppr32() {
+; CHECK-LABEL: test_mfppr32:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    mfspr 3, 898
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mfppr32:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    mfspr 3, 898
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = call i64 @llvm.ppc.mfspr.i64(i32 898)
+  ret i64 %0
+}
+
+define dso_local void @test_mtxer() {
+; CHECK-LABEL: test_mtxer:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    addis 3, 2, .LC0@toc@ha
+; CHECK-NEXT:    ld 3, .LC0@toc@l(3)
+; CHECK-NEXT:    ld 3, 0(3)
+; CHECK-NEXT:    mtxer 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mtxer:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    ld 3, L..C0(2) # @ula
+; CHECK-AIX64-NEXT:    ld 3, 0(3)
+; CHECK-AIX64-NEXT:    mtxer 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i64(i32 1, i64 %0)
+  ret void
+}
+
+define dso_local void @test_mtlr() {
+; CHECK-LABEL: test_mtlr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    addis 3, 2, .LC0@toc@ha
+; CHECK-NEXT:    ld 3, .LC0@toc@l(3)
+; CHECK-NEXT:    ld 3, 0(3)
+; CHECK-NEXT:    mtlr 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mtlr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    ld 3, L..C0(2) # @ula
+; CHECK-AIX64-NEXT:    ld 3, 0(3)
+; CHECK-AIX64-NEXT:    mtspr 8, 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i64(i32 8, i64 %0)
+  ret void
+}
+
+define dso_local void @test_mtctr() {
+; CHECK-LABEL: test_mtctr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    addis 3, 2, .LC0@toc@ha
+; CHECK-NEXT:    ld 3, .LC0@toc@l(3)
+; CHECK-NEXT:    ld 3, 0(3)
+; CHECK-NEXT:    mtctr 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mtctr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    ld 3, L..C0(2) # @ula
+; CHECK-AIX64-NEXT:    ld 3, 0(3)
+; CHECK-AIX64-NEXT:    mtspr 9, 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i64(i32 9, i64 %0)
+  ret void
+}
+
+define dso_local void @test_mtppr() {
+; CHECK-LABEL: test_mtppr:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    addis 3, 2, .LC0@toc@ha
+; CHECK-NEXT:    ld 3, .LC0@toc@l(3)
+; CHECK-NEXT:    ld 3, 0(3)
+; CHECK-NEXT:    mtspr 896, 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mtppr:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    ld 3, L..C0(2) # @ula
+; CHECK-AIX64-NEXT:    ld 3, 0(3)
+; CHECK-AIX64-NEXT:    mtspr 896, 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i64(i32 896, i64 %0)
+  ret void
+}
+
+define dso_local void @test_mtppr32() {
+; CHECK-LABEL: test_mtppr32:
+; CHECK:       # %bb.0: # %entry
+; CHECK-NEXT:    addis 3, 2, .LC0@toc@ha
+; CHECK-NEXT:    ld 3, .LC0@toc@l(3)
+; CHECK-NEXT:    ld 3, 0(3)
+; CHECK-NEXT:    mtspr 898, 3
+; CHECK-NEXT:    blr
+;
+; CHECK-AIX64-LABEL: test_mtppr32:
+; CHECK-AIX64:       # %bb.0: # %entry
+; CHECK-AIX64-NEXT:    ld 3, L..C0(2) # @ula
+; CHECK-AIX64-NEXT:    ld 3, 0(3)
+; CHECK-AIX64-NEXT:    mtspr 898, 3
+; CHECK-AIX64-NEXT:    blr
+entry:
+  %0 = load i64, i64* @ula, align 8
+  tail call void @llvm.ppc.mtspr.i64(i32 898, i64 %0)
+  ret void
+}
Index: llvm/lib/Target/PowerPC/PPCInstrInfo.td
===================================================================
--- llvm/lib/Target/PowerPC/PPCInstrInfo.td
+++ llvm/lib/Target/PowerPC/PPCInstrInfo.td
@@ -5439,6 +5439,12 @@
 
 def : Pat<(int_ppc_mfmsr), (MFMSR)>;
 def : Pat<(int_ppc_mftbu), (MFTB 269)>;
+def : Pat<(i32 (int_ppc_mfspr i32:$SPR)),
+          (MFSPR $SPR)>;
+def : Pat<(int_ppc_mtspr i32:$SPR, gprc:$RT),
+          (MTSPR $SPR, $RT)>;
+def : Pat<(int_ppc_mtmsr gprc:$RS),
+          (MTMSR $RS, 0)>;
 
 let Predicates = [IsISA2_07] in {
   def : Pat<(int_ppc_lharx xoaddr:$dst),
Index: llvm/lib/Target/PowerPC/PPCInstr64Bit.td
===================================================================
--- llvm/lib/Target/PowerPC/PPCInstr64Bit.td
+++ llvm/lib/Target/PowerPC/PPCInstr64Bit.td
@@ -412,7 +412,6 @@
 def MTSPR8 : XFXForm_1<31, 467, (outs), (ins i32imm:$SPR, g8rc:$RT),
                        "mtspr $SPR, $RT", IIC_SprMTSPR>;
 
-
 //===----------------------------------------------------------------------===//
 // 64-bit SPR manipulation instrs.
 
@@ -1729,3 +1728,7 @@
 // trapd
 def : Pat<(int_ppc_trapd g8rc:$A),
           (TDI 24, $A, 0)>;
+def : Pat<(i64 (int_ppc_mfspr i32:$SPR)),
+          (MFSPR8 $SPR)>;
+def : Pat<(int_ppc_mtspr i32:$SPR, g8rc:$RT),
+          (MTSPR8 $SPR, $RT)>;
Index: llvm/include/llvm/IR/IntrinsicsPowerPC.td
===================================================================
--- llvm/include/llvm/IR/IntrinsicsPowerPC.td
+++ llvm/include/llvm/IR/IntrinsicsPowerPC.td
@@ -1578,4 +1578,9 @@
                       Intrinsic<[llvm_i32_ty], [], [IntrNoMem]>;
   def int_ppc_mfmsr : GCCBuiltin<"__builtin_ppc_mfmsr">,
                       Intrinsic<[llvm_i32_ty], [], [IntrNoMem]>;
+  def int_ppc_mfspr : Intrinsic<[llvm_anyint_ty], [llvm_i32_ty], [ImmArg<ArgIndex<0>>]>;
+  def int_ppc_mtmsr
+      : GCCBuiltin<"__builtin_ppc_mtmsr">, Intrinsic<[], [llvm_i32_ty], []>;
+  def int_ppc_mtspr
+      : Intrinsic<[], [llvm_i32_ty, llvm_anyint_ty], [ImmArg<ArgIndex<0>>]>;
 }
Index: clang/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.c
===================================================================
--- clang/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.c
+++ clang/test/CodeGen/builtins-ppc-xlcompat-move-tofrom-regs.c
@@ -3,10 +3,13 @@
 // RUN: %clang_cc1 -O2 -triple powerpc64le-unknown-unknown \
 // RUN:   -emit-llvm %s -o - -target-cpu pwr8 | FileCheck %s
 // RUN: %clang_cc1 -O2 -triple powerpc-unknown-aix \
-// RUN:   -emit-llvm %s -o - -target-cpu pwr7 | FileCheck %s
+// RUN:   -emit-llvm %s -o - -target-cpu pwr7 | \
+// RUN:   FileCheck %s --check-prefix=CHECK-32BIT
 // RUN: %clang_cc1 -O2 -triple powerpc64-unknown-aix \
 // RUN:   -emit-llvm %s -o - -target-cpu pwr7 | FileCheck %s
 
+extern unsigned long ula;
+
 unsigned int test_mftbu(void) {
   // CHECK-LABEL: @test_mftbu
   // CHECK: %0 = tail call i32 @llvm.ppc.mftbu()
@@ -18,3 +21,23 @@
   // CHECK: %0 = tail call i32 @llvm.ppc.mfmsr()
   return __mfmsr();
 }
+
+void test_mtmsr(void) {
+  // CHECK-LABEL: @test_mtmsr
+  // CHECK: tail call void @llvm.ppc.mtmsr(i32 %conv)
+  // CHECK-32BIT-LABEL: @test_mtmsr
+  // CHECK-32BIT: tail call void @llvm.ppc.mtmsr(i32 %0)
+  __mtmsr(ula);
+}
+
+unsigned long test_mfspr(void) {
+  // CHECK-LABEL: @test_mfspr
+  // CHECK: %0 = tail call i64 @llvm.ppc.mfspr.i64(i32 898)
+  return __mfspr(898);
+}
+
+void test_mtspr(void) {
+  // CHECK-LABEL: @test_mtspr
+  // CHECK: tail call void @llvm.ppc.mtspr.i64(i32 1, i64 %0)
+  __mtspr(1, ula);
+}
Index: clang/lib/CodeGen/CGBuiltin.cpp
===================================================================
--- clang/lib/CodeGen/CGBuiltin.cpp
+++ clang/lib/CodeGen/CGBuiltin.cpp
@@ -15582,6 +15582,20 @@
   case PPC::BI__builtin_ppc_ldarx:
   case PPC::BI__builtin_ppc_lwarx:
     return emitPPCLoadReserveIntrinsic(*this, BuiltinID, E);
+  case PPC::BI__builtin_ppc_mfspr: {
+    llvm::Type *RetType = CGM.getDataLayout().getTypeSizeInBits(VoidPtrTy) == 32
+                              ? Int32Ty
+                              : Int64Ty;
+    Function *F = CGM.getIntrinsic(Intrinsic::ppc_mfspr, RetType);
+    return Builder.CreateCall(F, Ops);
+  }
+  case PPC::BI__builtin_ppc_mtspr: {
+    llvm::Type *RetType = CGM.getDataLayout().getTypeSizeInBits(VoidPtrTy) == 32
+                              ? Int32Ty
+                              : Int64Ty;
+    Function *F = CGM.getIntrinsic(Intrinsic::ppc_mtspr, RetType);
+    return Builder.CreateCall(F, Ops);
+  }
   }
 }
 
Index: clang/lib/Basic/Targets/PPC.cpp
===================================================================
--- clang/lib/Basic/Targets/PPC.cpp
+++ clang/lib/Basic/Targets/PPC.cpp
@@ -137,6 +137,9 @@
   Builder.defineMacro("__dcbtt", "__builtin_ppc_dcbtt");
   Builder.defineMacro("__mftbu", "__builtin_ppc_mftbu");
   Builder.defineMacro("__mfmsr", "__builtin_ppc_mfmsr");
+  Builder.defineMacro("__mtmsr", "__builtin_ppc_mtmsr");
+  Builder.defineMacro("__mfspr", "__builtin_ppc_mfspr");
+  Builder.defineMacro("__mtspr", "__builtin_ppc_mtspr");
 }
 
 /// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific
Index: clang/include/clang/Basic/BuiltinsPPC.def
===================================================================
--- clang/include/clang/Basic/BuiltinsPPC.def
+++ clang/include/clang/Basic/BuiltinsPPC.def
@@ -78,6 +78,9 @@
 BUILTIN(__builtin_ppc_dcbtt, "vv*", "")
 BUILTIN(__builtin_ppc_mftbu, "Ui","")
 BUILTIN(__builtin_ppc_mfmsr, "Ui", "")
+BUILTIN(__builtin_ppc_mfspr, "ULiiC", "")
+BUILTIN(__builtin_ppc_mtmsr, "vUi", "")
+BUILTIN(__builtin_ppc_mtspr, "viCULi", "")
 
 BUILTIN(__builtin_ppc_get_timebase, "ULLi", "n")
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to