Skip to content

Commit bfb9e86

Browse files
committed
Revert "[CHERIoT] Pass two-cap-sized return values and arguments in registers"
This reverts commit 5bda199.
1 parent fd09919 commit bfb9e86

File tree

3 files changed

+22
-1631
lines changed

3 files changed

+22
-1631
lines changed

clang/lib/CodeGen/Targets/RISCV.cpp

Lines changed: 22 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -35,36 +35,6 @@ class RISCVABIInfo : public DefaultABIInfo {
3535
llvm::Type *&Field2Ty,
3636
CharUnits &Field2Off) const;
3737

38-
/// CHERI(oT)-specific: Figure out how many registers are needed to pass a
39-
/// value of the given type and size directly in register(s). The value of
40-
/// `-1` means that the value should be passed indirectly.
41-
///
42-
/// Note: `Size` is in bits.
43-
int8_t getCapRegsForStruct(uint64_t Size, QualType Ty) const {
44-
auto &T = getTarget();
45-
auto CapWidth = T.getCHERICapabilityWidth();
46-
47-
if (Size % CapWidth)
48-
return -1;
49-
50-
auto *RT = Ty->getAs<RecordType>();
51-
52-
StringRef TargetABI = T.getABI();
53-
bool IsCheriot = TargetABI == "cheriot" || TargetABI == "cheriot-baremetal";
54-
55-
auto Q = Size / CapWidth;
56-
57-
if (RT && getContext().containsCapabilities(RT->getDecl())) {
58-
if (Q == 1)
59-
return 1;
60-
61-
if (IsCheriot && Q == 2)
62-
return 2;
63-
}
64-
65-
return -1;
66-
}
67-
6838
public:
6939
RISCVABIInfo(CodeGen::CodeGenTypes &CGT, unsigned XLen, unsigned FLen,
7040
bool EABI)
@@ -458,16 +428,19 @@ ABIArgInfo RISCVABIInfo::classifyArgumentType(QualType Ty, bool IsFixed,
458428
if (isEmptyRecord(getContext(), Ty, true) && Size == 0)
459429
return ABIArgInfo::getIgnore();
460430

461-
auto CapRegsForStruct = getCapRegsForStruct(Size, Ty);
462-
bool ForcePassInCapRegs = CapRegsForStruct > 0;
463-
bool IsSingleCapability =
464-
Ty->isCHERICapabilityType(getContext()) || CapRegsForStruct == 1;
431+
bool IsSingleCapRecord = false;
432+
if (auto *RT = Ty->getAs<RecordType>())
433+
IsSingleCapRecord = Size == getTarget().getCHERICapabilityWidth() &&
434+
getContext().containsCapabilities(RT->getDecl());
435+
436+
bool IsCapability = Ty->isCHERICapabilityType(getContext()) ||
437+
IsSingleCapRecord;
465438

466439
// Capabilities (including single-capability records, which are treated the
467440
// same as a single capability) are passed indirectly for hybrid varargs.
468441
// Anything larger is bigger than 2*XLEN and thus automatically passed
469442
// indirectly anyway.
470-
if (!IsFixed && IsSingleCapability &&
443+
if (!IsFixed && IsCapability &&
471444
!getContext().getTargetInfo().areAllPointersCapabilities()) {
472445
if (ArgGPRsLeft)
473446
ArgGPRsLeft -= 1;
@@ -522,9 +495,9 @@ ABIArgInfo RISCVABIInfo::classifyArgumentType(QualType Ty, bool IsFixed,
522495
// TODO: Pairs involving capabilities should be passed in registers too like
523496
// int/fp pairs (requires thought for fp+cap when out of FPRs).
524497
int NeededArgGPRs = 1;
525-
if (!IsSingleCapability && !IsFixed && NeededAlign == 2 * XLen)
498+
if (!IsCapability && !IsFixed && NeededAlign == 2 * XLen)
526499
NeededArgGPRs = 2 + (EABI && XLen == 32 ? 0 : (ArgGPRsLeft % 2));
527-
else if (!IsSingleCapability && Size > XLen && Size <= 2 * XLen)
500+
else if (!IsCapability && Size > XLen && Size <= 2 * XLen)
528501
NeededArgGPRs = 2;
529502

530503
if (NeededArgGPRs > ArgGPRsLeft) {
@@ -555,7 +528,7 @@ ABIArgInfo RISCVABIInfo::classifyArgumentType(QualType Ty, bool IsFixed,
555528
return ABIArgInfo::getDirect();
556529
}
557530

558-
if (ForcePassInCapRegs)
531+
if (IsSingleCapRecord)
559532
return ABIArgInfo::getDirect();
560533

561534
if (const VectorType *VT = Ty->getAs<VectorType>())
@@ -620,18 +593,21 @@ RValue RISCVABIInfo::EmitVAArg(CodeGenFunction &CGF, Address VAListAddr,
620593
if (EABI && XLen == 32 && !IsCheriot)
621594
TInfo.Align = std::min(TInfo.Align, CharUnits::fromQuantity(4));
622595

623-
uint64_t Size = TInfo.Width.getQuantity() * 8;
596+
bool IsSingleCapRecord = false;
597+
CharUnits CapabilityWidth =
598+
CharUnits::fromQuantity(getTarget().getCHERICapabilityWidth() / 8);
599+
if (const auto *RT = Ty->getAs<RecordType>())
600+
IsSingleCapRecord = TInfo.Width == CapabilityWidth &&
601+
getContext().containsCapabilities(RT->getDecl());
624602

625-
auto CapRegsForStruct = getCapRegsForStruct(Size, Ty);
626-
bool IsSingleCapability =
627-
Ty->isCHERICapabilityType(getContext()) || CapRegsForStruct == 1;
603+
bool IsCapability = Ty->isCHERICapabilityType(getContext()) ||
604+
IsSingleCapRecord;
628605

629606
// Arguments bigger than 2*Xlen bytes are passed indirectly, as are
630607
// capabilities for the hybrid ABI.
631-
bool IsIndirect =
632-
TInfo.Width > 2 * SlotSize ||
633-
(!getContext().getTargetInfo().areAllPointersCapabilities() &&
634-
IsSingleCapability);
608+
bool IsIndirect = TInfo.Width > 2 * SlotSize ||
609+
(!getContext().getTargetInfo().areAllPointersCapabilities() &&
610+
IsCapability);
635611

636612
return emitVoidPtrVAArg(CGF, VAListAddr, Ty, IsIndirect, TInfo, SlotSize,
637613
/*AllowHigherAlign=*/true, Slot);

0 commit comments

Comments
 (0)