mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2024-12-13 04:30:23 +00:00
Add support for BlockAddress values in ARM constant pools.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@85806 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
69e8445ced
commit
28989a8ddc
@ -428,6 +428,7 @@ void Emitter<CodeEmitter>::emitConstPoolInstruction(const MachineInstr &MI) {
|
||||
DEBUG(errs() << " ** ARM constant pool #" << CPI << " @ "
|
||||
<< (void*)MCE.getCurrentPCValue() << " " << *ACPV << '\n');
|
||||
|
||||
assert(ACPV->isGlobalValue() && "unsupported constant pool value");
|
||||
GlobalValue *GV = ACPV->getGV();
|
||||
if (GV) {
|
||||
Reloc::Model RelocM = TM.getRelocationModel();
|
||||
|
@ -13,19 +13,21 @@
|
||||
|
||||
#include "ARMConstantPoolValue.h"
|
||||
#include "llvm/ADT/FoldingSet.h"
|
||||
#include "llvm/Constant.h"
|
||||
#include "llvm/Constants.h"
|
||||
#include "llvm/GlobalValue.h"
|
||||
#include "llvm/Type.h"
|
||||
#include "llvm/Support/raw_ostream.h"
|
||||
#include <cstdlib>
|
||||
using namespace llvm;
|
||||
|
||||
ARMConstantPoolValue::ARMConstantPoolValue(GlobalValue *gv, unsigned id,
|
||||
ARMConstantPoolValue::ARMConstantPoolValue(Constant *cval, unsigned id,
|
||||
ARMCP::ARMCPKind K,
|
||||
unsigned char PCAdj,
|
||||
const char *Modif,
|
||||
bool AddCA)
|
||||
: MachineConstantPoolValue((const Type*)gv->getType()),
|
||||
GV(gv), S(NULL), LabelId(id), Kind(K), PCAdjust(PCAdj),
|
||||
: MachineConstantPoolValue((const Type*)cval->getType()),
|
||||
CVal(cval), S(NULL), LabelId(id), Kind(K), PCAdjust(PCAdj),
|
||||
Modifier(Modif), AddCurrentAddress(AddCA) {}
|
||||
|
||||
ARMConstantPoolValue::ARMConstantPoolValue(LLVMContext &C,
|
||||
@ -34,14 +36,22 @@ ARMConstantPoolValue::ARMConstantPoolValue(LLVMContext &C,
|
||||
const char *Modif,
|
||||
bool AddCA)
|
||||
: MachineConstantPoolValue((const Type*)Type::getInt32Ty(C)),
|
||||
GV(NULL), S(strdup(s)), LabelId(id), Kind(ARMCP::CPValue), PCAdjust(PCAdj),
|
||||
Modifier(Modif), AddCurrentAddress(AddCA) {}
|
||||
CVal(NULL), S(strdup(s)), LabelId(id), Kind(ARMCP::CPExtSymbol),
|
||||
PCAdjust(PCAdj), Modifier(Modif), AddCurrentAddress(AddCA) {}
|
||||
|
||||
ARMConstantPoolValue::ARMConstantPoolValue(GlobalValue *gv, const char *Modif)
|
||||
: MachineConstantPoolValue((const Type*)Type::getInt32Ty(gv->getContext())),
|
||||
GV(gv), S(NULL), LabelId(0), Kind(ARMCP::CPValue), PCAdjust(0),
|
||||
CVal(gv), S(NULL), LabelId(0), Kind(ARMCP::CPValue), PCAdjust(0),
|
||||
Modifier(Modif) {}
|
||||
|
||||
GlobalValue *ARMConstantPoolValue::getGV() const {
|
||||
return dyn_cast_or_null<GlobalValue>(CVal);
|
||||
}
|
||||
|
||||
BlockAddress *ARMConstantPoolValue::getBlockAddress() const {
|
||||
return dyn_cast_or_null<BlockAddress>(CVal);
|
||||
}
|
||||
|
||||
int ARMConstantPoolValue::getExistingMachineCPValue(MachineConstantPool *CP,
|
||||
unsigned Alignment) {
|
||||
unsigned AlignMask = Alignment - 1;
|
||||
@ -51,7 +61,7 @@ int ARMConstantPoolValue::getExistingMachineCPValue(MachineConstantPool *CP,
|
||||
(Constants[i].getAlignment() & AlignMask) == 0) {
|
||||
ARMConstantPoolValue *CPV =
|
||||
(ARMConstantPoolValue *)Constants[i].Val.MachineCPVal;
|
||||
if (CPV->GV == GV &&
|
||||
if (CPV->CVal == CVal &&
|
||||
CPV->S == S &&
|
||||
CPV->LabelId == LabelId &&
|
||||
CPV->PCAdjust == PCAdjust)
|
||||
@ -68,7 +78,7 @@ ARMConstantPoolValue::~ARMConstantPoolValue() {
|
||||
|
||||
void
|
||||
ARMConstantPoolValue::AddSelectionDAGCSEId(FoldingSetNodeID &ID) {
|
||||
ID.AddPointer(GV);
|
||||
ID.AddPointer(CVal);
|
||||
ID.AddPointer(S);
|
||||
ID.AddInteger(LabelId);
|
||||
ID.AddInteger(PCAdjust);
|
||||
@ -80,8 +90,8 @@ void ARMConstantPoolValue::dump() const {
|
||||
|
||||
|
||||
void ARMConstantPoolValue::print(raw_ostream &O) const {
|
||||
if (GV)
|
||||
O << GV->getName();
|
||||
if (CVal)
|
||||
O << CVal->getName();
|
||||
else
|
||||
O << S;
|
||||
if (Modifier) O << "(" << Modifier << ")";
|
||||
|
@ -18,31 +18,35 @@
|
||||
|
||||
namespace llvm {
|
||||
|
||||
class Constant;
|
||||
class BlockAddress;
|
||||
class GlobalValue;
|
||||
class LLVMContext;
|
||||
|
||||
namespace ARMCP {
|
||||
enum ARMCPKind {
|
||||
CPValue,
|
||||
CPExtSymbol,
|
||||
CPBlockAddress,
|
||||
CPLSDA
|
||||
};
|
||||
}
|
||||
|
||||
/// ARMConstantPoolValue - ARM specific constantpool value. This is used to
|
||||
/// represent PC relative displacement between the address of the load
|
||||
/// instruction and the global value being loaded, i.e. (&GV-(LPIC+8)).
|
||||
/// instruction and the constant being loaded, i.e. (&GV-(LPIC+8)).
|
||||
class ARMConstantPoolValue : public MachineConstantPoolValue {
|
||||
GlobalValue *GV; // GlobalValue being loaded.
|
||||
Constant *CVal; // Constant being loaded.
|
||||
const char *S; // ExtSymbol being loaded.
|
||||
unsigned LabelId; // Label id of the load.
|
||||
ARMCP::ARMCPKind Kind; // Value or LSDA?
|
||||
ARMCP::ARMCPKind Kind; // Kind of constant.
|
||||
unsigned char PCAdjust; // Extra adjustment if constantpool is pc relative.
|
||||
// 8 for ARM, 4 for Thumb.
|
||||
const char *Modifier; // GV modifier i.e. (&GV(modifier)-(LPIC+8))
|
||||
bool AddCurrentAddress;
|
||||
|
||||
public:
|
||||
ARMConstantPoolValue(GlobalValue *gv, unsigned id,
|
||||
ARMConstantPoolValue(Constant *cval, unsigned id,
|
||||
ARMCP::ARMCPKind Kind = ARMCP::CPValue,
|
||||
unsigned char PCAdj = 0, const char *Modifier = NULL,
|
||||
bool AddCurrentAddress = false);
|
||||
@ -53,14 +57,17 @@ public:
|
||||
ARMConstantPoolValue();
|
||||
~ARMConstantPoolValue();
|
||||
|
||||
|
||||
GlobalValue *getGV() const { return GV; }
|
||||
GlobalValue *getGV() const;
|
||||
const char *getSymbol() const { return S; }
|
||||
BlockAddress *getBlockAddress() const;
|
||||
const char *getModifier() const { return Modifier; }
|
||||
bool hasModifier() const { return Modifier != NULL; }
|
||||
bool mustAddCurrentAddress() const { return AddCurrentAddress; }
|
||||
unsigned getLabelId() const { return LabelId; }
|
||||
unsigned char getPCAdjustment() const { return PCAdjust; }
|
||||
bool isGlobalValue() const { return Kind == ARMCP::CPValue; }
|
||||
bool isExtSymbol() const { return Kind == ARMCP::CPExtSymbol; }
|
||||
bool isBlockAddress() { return Kind == ARMCP::CPBlockAddress; }
|
||||
bool isLSDA() { return Kind == ARMCP::CPLSDA; }
|
||||
|
||||
virtual unsigned getRelocationInfo() const {
|
||||
@ -69,7 +76,6 @@ public:
|
||||
return 2;
|
||||
}
|
||||
|
||||
|
||||
virtual int getExistingMachineCPValue(MachineConstantPool *CP,
|
||||
unsigned Alignment);
|
||||
|
||||
|
@ -159,7 +159,6 @@ namespace {
|
||||
printDataDirective(MCPV->getType());
|
||||
|
||||
ARMConstantPoolValue *ACPV = static_cast<ARMConstantPoolValue*>(MCPV);
|
||||
GlobalValue *GV = ACPV->getGV();
|
||||
std::string Name;
|
||||
|
||||
if (ACPV->isLSDA()) {
|
||||
@ -167,7 +166,10 @@ namespace {
|
||||
raw_svector_ostream(LSDAName) << MAI->getPrivateGlobalPrefix() <<
|
||||
"_LSDA_" << getFunctionNumber();
|
||||
Name = LSDAName.str();
|
||||
} else if (GV) {
|
||||
} else if (ACPV->isBlockAddress()) {
|
||||
Name = GetBlockAddressSymbol(ACPV->getBlockAddress())->getName();
|
||||
} else if (ACPV->isGlobalValue()) {
|
||||
GlobalValue *GV = ACPV->getGV();
|
||||
bool isIndirect = Subtarget->isTargetDarwin() &&
|
||||
Subtarget->GVIsIndirectSymbol(GV, TM.getRelocationModel());
|
||||
if (!isIndirect)
|
||||
@ -188,8 +190,10 @@ namespace {
|
||||
StubSym = OutContext.GetOrCreateSymbol(NameStr.str());
|
||||
}
|
||||
}
|
||||
} else
|
||||
} else {
|
||||
assert(ACPV->isExtSymbol() && "unrecognized constant pool value");
|
||||
Name = Mang->makeNameProper(ACPV->getSymbol());
|
||||
}
|
||||
O << Name;
|
||||
|
||||
if (ACPV->hasModifier()) O << "(" << ACPV->getModifier() << ")";
|
||||
|
Loading…
Reference in New Issue
Block a user