Skip to content

Commit

Permalink
Introduce CodeGenerator constructors and initialize functions
Browse files Browse the repository at this point in the history
* Create a new CodeGenerator constructor that takes a TR::Compilation parameter.
  The constructor hierarchy only contains member initialization lists.

  A mirrored hierarchy was created to permit downstream projets to adapt
  to the hierarchy changes.  The default constructors will eventually be
  deleted and replaced with private empty stubs.

  This constructor will eventually be invoked via a static factory function.

* Create a CodeGenerator::initialize() method to be called after object
  construction to initialize the CodeGenerator object.  The initialize()
  functions take the place of the original constructor bodies and must be
  invoked in the same order.

Signed-off-by: Daryl Maier <maier@ca.ibm.com>
  • Loading branch information
0xdaryl committed Sep 21, 2020
1 parent e537f3b commit 4e028e2
Show file tree
Hide file tree
Showing 18 changed files with 1,272 additions and 29 deletions.
115 changes: 115 additions & 0 deletions compiler/aarch64/codegen/OMRCodeGenerator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,121 @@
#include "il/Node_inlines.hpp"
#include "il/StaticSymbol.hpp"


OMR::ARM64::CodeGenerator::CodeGenerator(TR::Compilation *comp) :
OMR::CodeGenerator(comp),
_dataSnippetList(getTypedAllocator<TR::ARM64ConstantDataSnippet*>(comp->allocator())),
_outOfLineCodeSectionList(getTypedAllocator<TR_ARM64OutOfLineCodeSection*>(comp->allocator())),
_firstTimeLiveOOLRegisterList(NULL)
{
}

void
OMR::ARM64::CodeGenerator::initialize()
{
self()->OMR::CodeGenerator::initialize();

TR::CodeGenerator *cg = self();
TR::Compilation *comp = self()->comp();

// Initialize Linkage for Code Generator
cg->initializeLinkage();

_unlatchedRegisterList =
(TR::RealRegister**)cg->trMemory()->allocateHeapMemory(sizeof(TR::RealRegister*)*(TR::RealRegister::NumRegisters + 1));

_unlatchedRegisterList[0] = 0; // mark that list is empty

_linkageProperties = &cg->getLinkage()->getProperties();

cg->setStackPointerRegister(cg->machine()->getRealRegister(_linkageProperties->getStackPointerRegister()));
cg->setMethodMetaDataRegister(cg->machine()->getRealRegister(_linkageProperties->getMethodMetaDataRegister()));

// Tactical GRA settings
//
cg->setGlobalRegisterTable(_linkageProperties->getRegisterAllocationOrder());
_numGPR = _linkageProperties->getNumAllocatableIntegerRegisters();
_numFPR = _linkageProperties->getNumAllocatableFloatRegisters();
cg->setLastGlobalGPR(_numGPR - 1);
cg->setLastGlobalFPR(_numGPR + _numFPR - 1);

cg->getLinkage()->initARM64RealRegisterLinkage();
cg->setSupportsGlRegDeps();
cg->setSupportsGlRegDepOnFirstBlock();

cg->addSupportedLiveRegisterKind(TR_GPR);
cg->addSupportedLiveRegisterKind(TR_FPR);
cg->setLiveRegisters(new (cg->trHeapMemory()) TR_LiveRegisters(comp), TR_GPR);
cg->setLiveRegisters(new (cg->trHeapMemory()) TR_LiveRegisters(comp), TR_FPR);

cg->setSupportsVirtualGuardNOPing();

cg->setSupportsRecompilation();

cg->setSupportsSelect();

_numberBytesReadInaccessible = 0;
_numberBytesWriteInaccessible = 0;

if (TR::Compiler->vm.hasResumableTrapHandler(comp))
cg->setHasResumableTrapHandler();

if (!comp->getOption(TR_DisableRegisterPressureSimulation))
{
for (int32_t i = 0; i < TR_numSpillKinds; i++)
_globalRegisterBitVectors[i].init(cg->getNumberOfGlobalRegisters(), cg->trMemory());

for (TR_GlobalRegisterNumber grn=0; grn < cg->getNumberOfGlobalRegisters(); grn++)
{
TR::RealRegister::RegNum reg = (TR::RealRegister::RegNum)cg->getGlobalRegister(grn);
if (cg->getFirstGlobalGPR() <= grn && grn <= cg->getLastGlobalGPR())
_globalRegisterBitVectors[ TR_gprSpill ].set(grn);
else if (cg->getFirstGlobalFPR() <= grn && grn <= cg->getLastGlobalFPR())
_globalRegisterBitVectors[ TR_fprSpill ].set(grn);

if (!cg->getProperties().getPreserved(reg))
_globalRegisterBitVectors[ TR_volatileSpill ].set(grn);
if (cg->getProperties().getIntegerArgument(reg) || cg->getProperties().getFloatArgument(reg))
_globalRegisterBitVectors[ TR_linkageSpill ].set(grn);
}
}

// Calculate inverse of getGlobalRegister function
//
TR_GlobalRegisterNumber grn;
int i;

TR_GlobalRegisterNumber globalRegNumbers[TR::RealRegister::NumRegisters];
for (i = 0; i < cg->getNumberOfGlobalGPRs(); i++)
{
grn = cg->getFirstGlobalGPR() + i;
globalRegNumbers[cg->getGlobalRegister(grn)] = grn;
}
for (i = 0; i < cg->getNumberOfGlobalFPRs(); i++)
{
grn = cg->getFirstGlobalFPR() + i;
globalRegNumbers[cg->getGlobalRegister(grn)] = grn;
}

// Initialize linkage reg arrays
TR::ARM64LinkageProperties linkageProperties = cg->getProperties();
for (i = 0; i < linkageProperties.getNumIntArgRegs(); i++)
_gprLinkageGlobalRegisterNumbers[i] = globalRegNumbers[linkageProperties.getIntegerArgumentRegister(i)];
for (i = 0; i < linkageProperties.getNumFloatArgRegs(); i++)
_fprLinkageGlobalRegisterNumbers[i] = globalRegNumbers[linkageProperties.getFloatArgumentRegister(i)];

if (comp->getOption(TR_TraceRA))
{
cg->setGPRegisterIterator(new (cg->trHeapMemory()) TR::RegisterIterator(cg->machine(), TR::RealRegister::FirstGPR, TR::RealRegister::LastGPR));
cg->setFPRegisterIterator(new (cg->trHeapMemory()) TR::RegisterIterator(cg->machine(), TR::RealRegister::FirstFPR, TR::RealRegister::LastFPR));
}

cg->getLinkage()->setParameterLinkageRegisterIndex(comp->getJittedMethodSymbol());

if (comp->target().isSMP())
cg->setEnforceStoreOrder();
}

OMR::ARM64::CodeGenerator::CodeGenerator() :
OMR::CodeGenerator(),
_dataSnippetList(getTypedAllocator<TR::ARM64ConstantDataSnippet*>(TR::comp()->allocator())),
Expand Down
10 changes: 8 additions & 2 deletions compiler/aarch64/codegen/OMRCodeGenerator.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -150,10 +150,16 @@ namespace ARM64
class OMR_EXTENSIBLE CodeGenerator : public OMR::CodeGenerator
{

public:
protected:

CodeGenerator(TR::Compilation *comp);

public:

CodeGenerator();

void initialize();

/**
* @brief AArch64 hook to begin instruction selection
*/
Expand Down Expand Up @@ -474,7 +480,7 @@ class OMR_EXTENSIBLE CodeGenerator : public OMR::CodeGenerator
/**
* @brief Returns bit mask for real register
* @param[in] reg: real register number
*
*
* @return bit mask for real register
*/
static uint32_t registerBitMask(int32_t reg);
Expand Down
172 changes: 172 additions & 0 deletions compiler/arm/codegen/OMRCodeGenerator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,178 @@ TR::Linkage *OMR::ARM::CodeGenerator::createLinkage(TR_LinkageConventions lc)
return linkage;
}

OMR::ARM::CodeGenerator::CodeGenerator(TR::Compilation *comp)
: OMR::CodeGenerator(comp),
_frameRegister(NULL),
_constantData(NULL),
_outOfLineCodeSectionList(comp->trMemory()),
_internalControlFlowNestingDepth(0),
_internalControlFlowSafeNestingDepth(0)
{
}

void
OMR::ARM::CodeGenerator::initialize()
{
self()->OMR::CodeGenerator::initialize();

TR::CodeGenerator *cg = self();
TR::Compilation *comp = self()->comp();

// Initialize Linkage for Code Generator
cg->initializeLinkage();

_unlatchedRegisterList =
(TR::RealRegister**)cg->trMemory()->allocateHeapMemory(sizeof(TR::RealRegister*)*(TR::RealRegister::NumRegisters + 1));

_unlatchedRegisterList[0] = 0; // mark that list is empty

_linkageProperties = &cg->getLinkage()->getProperties();
_linkageProperties->setEndianness(comp->target().cpu.isBigEndian());

if (!comp->getOption(TR_FullSpeedDebug))
cg->setSupportsDirectJNICalls();
cg->setSupportsVirtualGuardNOPing();

if(comp->target().isLinux())
{
// only hardhat linux-arm builds have the required gcc soft libraries
// that allow the vm to be compiled with -msoft-float.
// With -msoft-float any floating point return value is placed in gr0 for single precision and
// gr0 and gr1 for double precision. This is where the jit expects the result following a directToJNI call.
// The floating point return value on non-hardhat linux-arm builds is through the coprocessor register f0.
// Therefore the HasHardFloatReturn flag must be set to force generation of instructions to move the result
// from f0 to gr0/gr1 following a directToJNI dispatch.

#if !defined(HARDHAT) && !defined(__VFP_FP__) // gcc does not support VFP with -mfloat-abi=hard yet
cg->setHasHardFloatReturn();
#endif
}

if (!debug("hasFramePointer"))
cg->setFrameRegister(cg->machine()->getRealRegister(_linkageProperties->getStackPointerRegister()));
else
cg->setFrameRegister(cg->machine()->getRealRegister(_linkageProperties->getFramePointerRegister()));

cg->setMethodMetaDataRegister(cg->machine()->getRealRegister(_linkageProperties->getMethodMetaDataRegister()));

// Tactical GRA settings
#if 1 // PPC enables below, but seem no longer used?
cg->setGlobalGPRPartitionLimit(TR::Machine::getGlobalGPRPartitionLimit());
cg->setGlobalFPRPartitionLimit(TR::Machine::getGlobalFPRPartitionLimit());
#endif
cg->setGlobalRegisterTable(TR::Machine::getGlobalRegisterTable());
_numGPR = _linkageProperties->getNumAllocatableIntegerRegisters();
cg->setLastGlobalGPR(TR::Machine::getLastGlobalGPRRegisterNumber());
cg->setLast8BitGlobalGPR(TR::Machine::getLast8BitGlobalGPRRegisterNumber());
cg->setLastGlobalFPR(TR::Machine::getLastGlobalFPRRegisterNumber());
_numFPR = _linkageProperties->getNumAllocatableFloatRegisters();

// TODO: Disable FP-GRA since current GRA does not work well with ARM linkage (where Float register usage is limited).
cg->setDisableFpGRA();

cg->setSupportsRecompilation();

cg->setSupportsGlRegDeps();
cg->setSupportsGlRegDepOnFirstBlock();
cg->setPerformsChecksExplicitly();
cg->setConsiderAllAutosAsTacticalGlobalRegisterCandidates();
cg->setSupportsScaledIndexAddressing();
cg->setSupportsAlignedAccessOnly();
cg->setSupportsPrimitiveArrayCopy();
cg->setSupportsReferenceArrayCopy();
cg->setSupportsLoweringConstIDiv();
cg->setSupportsNewInstanceImplOpt();

#ifdef J9_PROJECT_SPECIFIC
cg->setAheadOfTimeCompile(new (cg->trHeapMemory()) TR::AheadOfTimeCompile(cg));
#endif
cg->getLinkage()->initARMRealRegisterLinkage();
//To enable this, we must change OMR::ARM::Linkage::saveArguments to support GRA registers
//cg->getLinkage()->setParameterLinkageRegisterIndex(comp->getJittedMethodSymbol());

_numberBytesReadInaccessible = 0;
_numberBytesWriteInaccessible = 0;

cg->setSupportsJavaFloatSemantics();
cg->setSupportsInliningOfTypeCoersionMethods();

if (comp->target().isLinux())
{
// On AIX and Linux, we are very far away from address
// wrapping-around.
_maxObjectSizeGuaranteedNotToOverflow = 0x10000000;
cg->setSupportsDivCheck();
if (!comp->getOption(TR_DisableTraps))
cg->setHasResumableTrapHandler();
}
else
{
TR_ASSERT(0, "unknown target");
}

// Tactical GRA
if (!comp->getOption(TR_DisableRegisterPressureSimulation))
{
for (int32_t i = 0; i < TR_numSpillKinds; i++)
_globalRegisterBitVectors[i].init(cg->getNumberOfGlobalRegisters(), cg->trMemory());

for (TR_GlobalRegisterNumber grn=0; grn < cg->getNumberOfGlobalRegisters(); grn++)
{
TR::RealRegister::RegNum reg = (TR::RealRegister::RegNum)cg->getGlobalRegister(grn);
if (cg->getFirstGlobalGPR() <= grn && grn <= cg->getLastGlobalGPR())
_globalRegisterBitVectors[ TR_gprSpill ].set(grn);
else if (cg->getFirstGlobalFPR() <= grn && grn <= cg->getLastGlobalFPR())
_globalRegisterBitVectors[ TR_fprSpill ].set(grn);

if (!cg->getProperties().getPreserved(reg))
_globalRegisterBitVectors[ TR_volatileSpill ].set(grn);
if (cg->getProperties().getIntegerArgument(reg) || cg->getProperties().getFloatArgument(reg))
_globalRegisterBitVectors[ TR_linkageSpill ].set(grn);
}

}

// Calculate inverse of getGlobalRegister function
//
TR_GlobalRegisterNumber grn;
int i;

TR_GlobalRegisterNumber globalRegNumbers[TR::RealRegister::NumRegisters];
for (i=0; i < cg->getNumberOfGlobalGPRs(); i++)
{
grn = cg->getFirstGlobalGPR() + i;
globalRegNumbers[cg->getGlobalRegister(grn)] = grn;
}
for (i=0; i < cg->getNumberOfGlobalFPRs(); i++)
{
grn = cg->getFirstGlobalFPR() + i;
globalRegNumbers[cg->getGlobalRegister(grn)] = grn;
}

// Initialize linkage reg arrays
TR::ARMLinkageProperties linkageProperties = cg->getProperties();
for (i=0; i < linkageProperties.getNumIntArgRegs(); i++)
_gprLinkageGlobalRegisterNumbers[i] = globalRegNumbers[linkageProperties.getIntegerArgumentRegister(i)];
for (i=0; i < linkageProperties.getNumFloatArgRegs(); i++)
_fprLinkageGlobalRegisterNumbers[i] = globalRegNumbers[linkageProperties.getFloatArgumentRegister(i)];

if (comp->getOption(TR_TraceRA))
{
cg->setGPRegisterIterator(new (cg->trHeapMemory()) TR::RegisterIterator(cg->machine(), TR::RealRegister::FirstGPR, TR::RealRegister::LastGPR));
cg->setFPRegisterIterator(new (cg->trHeapMemory()) TR::RegisterIterator(cg->machine(), TR::RealRegister::FirstFPR, TR::RealRegister::LastFPR));
}

if (!comp->compileRelocatableCode())
{
cg->setSupportsProfiledInlining();
}

// Disable optimizations for max min by default on arm
comp->setOption(TR_DisableMaxMinOptimization);
}


OMR::ARM::CodeGenerator::CodeGenerator()
: OMR::CodeGenerator(),
_frameRegister(NULL),
Expand Down
14 changes: 10 additions & 4 deletions compiler/arm/codegen/OMRCodeGenerator.hpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*******************************************************************************
* Copyright (c) 2000, 2018 IBM Corp. and others
* Copyright (c) 2000, 2020 IBM Corp. and others
*
* This program and the accompanying materials are made available under
* the terms of the Eclipse Public License 2.0 which accompanies this
Expand Down Expand Up @@ -112,10 +112,16 @@ class CodeGenerator;
class OMR_EXTENSIBLE CodeGenerator : public OMR::CodeGenerator
{

public:
protected:

CodeGenerator(TR::Compilation *comp);

public:

CodeGenerator();

void initialize();

CodeGenerator(); /* @@ */
CodeGenerator(TR::Compilation * comp);
TR::Linkage *createLinkage(TR_LinkageConventions lc);

void beginInstructionSelection();
Expand Down

0 comments on commit 4e028e2

Please sign in to comment.