[llvm] [CallingConv] Return ArrayRef from AllocateRegBlock() (NFC) (PR #124120)

Nikita Popov via llvm-commits llvm-commits at lists.llvm.org
Thu Jan 23 06:36:38 PST 2025


https://github.com/nikic updated https://github.com/llvm/llvm-project/pull/124120

>From 01ddd7dc53626d9ab7203a93434885367cc20db5 Mon Sep 17 00:00:00 2001
From: Nikita Popov <npopov at redhat.com>
Date: Thu, 23 Jan 2025 15:28:24 +0100
Subject: [PATCH] [CallingConv] Return ArrayRef from AllocateRegBlock() (NFC)

Instead of returning the first register, return the ArrayRef
containing the whole block.

Existing users rely on the fact that the register block only
contains adjacently-numbered registers and it's possible to get
the remaining registers in the block by just incrementing the
register. Returning an ArrayRef allows more generic usage with
non-adjacent registers.
---
 llvm/include/llvm/CodeGen/CallingConvLower.h   | 15 ++++++++-------
 .../AArch64/AArch64CallingConvention.cpp       | 18 +++++++++---------
 llvm/lib/Target/ARM/ARMCallingConv.cpp         | 10 +++++-----
 3 files changed, 22 insertions(+), 21 deletions(-)

diff --git a/llvm/include/llvm/CodeGen/CallingConvLower.h b/llvm/include/llvm/CodeGen/CallingConvLower.h
index 85171138d1eb9d..7ad27cd01336a6 100644
--- a/llvm/include/llvm/CodeGen/CallingConvLower.h
+++ b/llvm/include/llvm/CodeGen/CallingConvLower.h
@@ -357,12 +357,13 @@ class CCState {
     return Reg;
   }
 
-  /// AllocateRegBlock - Attempt to allocate a block of RegsRequired consecutive
-  /// registers. If this is not possible, return zero. Otherwise, return the first
-  /// register of the block that were allocated, marking the entire block as allocated.
-  MCPhysReg AllocateRegBlock(ArrayRef<MCPhysReg> Regs, unsigned RegsRequired) {
+  /// Attempt to allocate a block of RegsRequired consecutive registers.
+  /// If this is not possible, return an empty range. Otherwise, return a
+  /// range of consecutive registers, marking the entire block as allocated.
+  ArrayRef<MCPhysReg> AllocateRegBlock(ArrayRef<MCPhysReg> Regs,
+                                       unsigned RegsRequired) {
     if (RegsRequired > Regs.size())
-      return 0;
+      return {};
 
     for (unsigned StartIdx = 0; StartIdx <= Regs.size() - RegsRequired;
          ++StartIdx) {
@@ -379,11 +380,11 @@ class CCState {
         for (unsigned BlockIdx = 0; BlockIdx < RegsRequired; ++BlockIdx) {
           MarkAllocated(Regs[StartIdx + BlockIdx]);
         }
-        return Regs[StartIdx];
+        return Regs.slice(StartIdx, RegsRequired);
       }
     }
     // No block was available
-    return 0;
+    return {};
   }
 
   /// Version of AllocateReg with list of registers to be shadowed.
diff --git a/llvm/lib/Target/AArch64/AArch64CallingConvention.cpp b/llvm/lib/Target/AArch64/AArch64CallingConvention.cpp
index fa04ccfba30f06..991d710c979b9e 100644
--- a/llvm/lib/Target/AArch64/AArch64CallingConvention.cpp
+++ b/llvm/lib/Target/AArch64/AArch64CallingConvention.cpp
@@ -176,27 +176,27 @@ static bool CC_AArch64_Custom_Block(unsigned &ValNo, MVT &ValVT, MVT &LocVT,
   // [N x i32] arguments get packed into x-registers on Darwin's arm64_32
   // because that's how the armv7k Clang front-end emits small structs.
   unsigned EltsPerReg = (IsDarwinILP32 && LocVT.SimpleTy == MVT::i32) ? 2 : 1;
-  unsigned RegResult = State.AllocateRegBlock(
+  ArrayRef<MCPhysReg> RegResult = State.AllocateRegBlock(
       RegList, alignTo(PendingMembers.size(), EltsPerReg) / EltsPerReg);
-  if (RegResult && EltsPerReg == 1) {
-    for (auto &It : PendingMembers) {
-      It.convertToReg(RegResult);
+  if (!RegResult.empty() && EltsPerReg == 1) {
+    for (const auto &[It, Reg] : zip(PendingMembers, RegResult)) {
+      It.convertToReg(Reg);
       State.addLoc(It);
-      ++RegResult;
     }
     PendingMembers.clear();
     return true;
-  } else if (RegResult) {
+  } else if (!RegResult.empty()) {
     assert(EltsPerReg == 2 && "unexpected ABI");
     bool UseHigh = false;
     CCValAssign::LocInfo Info;
+    unsigned RegIdx = 0;
     for (auto &It : PendingMembers) {
       Info = UseHigh ? CCValAssign::AExtUpper : CCValAssign::ZExt;
-      State.addLoc(CCValAssign::getReg(It.getValNo(), MVT::i32, RegResult,
-                                       MVT::i64, Info));
+      State.addLoc(CCValAssign::getReg(It.getValNo(), MVT::i32,
+                                       RegResult[RegIdx], MVT::i64, Info));
       UseHigh = !UseHigh;
       if (!UseHigh)
-        ++RegResult;
+        ++RegIdx;
     }
     PendingMembers.clear();
     return true;
diff --git a/llvm/lib/Target/ARM/ARMCallingConv.cpp b/llvm/lib/Target/ARM/ARMCallingConv.cpp
index 5a88fff41aeb1d..66a76a8c7a95a1 100644
--- a/llvm/lib/Target/ARM/ARMCallingConv.cpp
+++ b/llvm/lib/Target/ARM/ARMCallingConv.cpp
@@ -228,12 +228,12 @@ static bool CC_ARM_AAPCS_Custom_Aggregate(unsigned ValNo, MVT ValVT,
     break;
   }
 
-  unsigned RegResult = State.AllocateRegBlock(RegList, PendingMembers.size());
-  if (RegResult) {
-    for (CCValAssign &PendingMember : PendingMembers) {
-      PendingMember.convertToReg(RegResult);
+  ArrayRef<MCPhysReg> RegResult =
+      State.AllocateRegBlock(RegList, PendingMembers.size());
+  if (!RegResult.empty()) {
+    for (const auto &[PendingMember, Reg] : zip(PendingMembers, RegResult)) {
+      PendingMember.convertToReg(Reg);
       State.addLoc(PendingMember);
-      ++RegResult;
     }
     PendingMembers.clear();
     return true;



More information about the llvm-commits mailing list