Added immediate constant stuff in ARM CodeGen.

git-svn-id: http://svn.purei.org/purei/trunk@522 b36208d7-6611-0410-8bec-b1987f11c4a2
This commit is contained in:
jpd002 2009-05-13 00:03:11 +00:00
parent 7b7c69d8b0
commit b51b5facfd
4 changed files with 63 additions and 18 deletions

View file

@ -218,6 +218,11 @@ void CArmAssembler::Mov(REGISTER rd, const RegisterAluOperand& operand)
WriteWord(opcode); WriteWord(opcode);
} }
void CArmAssembler::Mov(REGISTER rd, const ImmediateAluOperand& operand)
{
MovCc(CONDITION_AL, rd, operand);
}
void CArmAssembler::MovCc(CONDITION condition, REGISTER rd, const ImmediateAluOperand& operand) void CArmAssembler::MovCc(CONDITION condition, REGISTER rd, const ImmediateAluOperand& operand)
{ {
InstructionAlu instruction; InstructionAlu instruction;

View file

@ -177,6 +177,7 @@ public:
void Ldr(REGISTER, REGISTER, const LdrAddress&); void Ldr(REGISTER, REGISTER, const LdrAddress&);
void Mov(REGISTER, REGISTER); void Mov(REGISTER, REGISTER);
void Mov(REGISTER, const RegisterAluOperand&); void Mov(REGISTER, const RegisterAluOperand&);
void Mov(REGISTER, const ImmediateAluOperand&);
void MovCc(CONDITION, REGISTER, const ImmediateAluOperand&); void MovCc(CONDITION, REGISTER, const ImmediateAluOperand&);
void Mvn(REGISTER, REGISTER); void Mvn(REGISTER, REGISTER);
void Or(REGISTER, REGISTER, REGISTER); void Or(REGISTER, REGISTER, REGISTER);

View file

@ -964,7 +964,42 @@ void CCodeGen::LoadRelativeInRegister(CArmAssembler::REGISTER registerId, uint32
m_assembler.Ldr(registerId, g_baseRegister, CArmAssembler::MakeImmediateLdrAddress(relative)); m_assembler.Ldr(registerId, g_baseRegister, CArmAssembler::MakeImmediateLdrAddress(relative));
} }
uint32 CCodeGen::RotateRight(uint32 value)
{
uint32 carry = value & 1;
value >>= 1;
value |= carry << 31;
return value;
}
uint32 CCodeGen::RotateLeft(uint32 value)
{
uint32 carry = value >> 31;
value <<= 1;
value |= carry;
return value;
}
void CCodeGen::LoadConstantInRegister(CArmAssembler::REGISTER registerId, uint32 constant) void CCodeGen::LoadConstantInRegister(CArmAssembler::REGISTER registerId, uint32 constant)
{
uint32 shadowConstant = constant;
int shiftAmount = -1;
for(unsigned int i = 0; i < 16; i++)
{
if((shadowConstant & 0xFF) == shadowConstant)
{
shiftAmount = i;
break;
}
shadowConstant = RotateLeft(shadowConstant);
shadowConstant = RotateLeft(shadowConstant);
}
if(shiftAmount != -1)
{
m_assembler.Mov(registerId, CArmAssembler::MakeImmediateAluOperand(shadowConstant, shiftAmount));
}
else
{ {
//Search for an existing literal //Search for an existing literal
unsigned int literalPtr = -1; unsigned int literalPtr = -1;
@ -992,6 +1027,7 @@ void CCodeGen::LoadConstantInRegister(CArmAssembler::REGISTER registerId, uint32
//Write a blank instruction //Write a blank instruction
m_stream->Write32(0); m_stream->Write32(0);
} }
}
void CCodeGen::DumpLiteralPool() void CCodeGen::DumpLiteralPool()
{ {

View file

@ -161,6 +161,9 @@ private:
void PushReg(CArmAssembler::REGISTER); void PushReg(CArmAssembler::REGISTER);
uint32 RotateRight(uint32);
uint32 RotateLeft(uint32);
void LoadRelativeInRegister(CArmAssembler::REGISTER, uint32); void LoadRelativeInRegister(CArmAssembler::REGISTER, uint32);
void LoadConstantInRegister(CArmAssembler::REGISTER, uint32); void LoadConstantInRegister(CArmAssembler::REGISTER, uint32);