fix argument alignment for Darwin/ARM

This commit is contained in:
Joel Dice 2011-08-10 21:33:56 -06:00
parent 39cffb8933
commit 44f7bd9fe0
6 changed files with 43 additions and 16 deletions

View File

@ -1834,7 +1834,19 @@ class MyArchitecture: public Assembler::Architecture {
}
virtual bool argumentAlignment() {
#ifdef __APPLE__
return false;
#else
return true;
#endif
}
virtual bool argumentRegisterAlignment() {
#ifdef __APPLE__
return false;
#else
return true;
#endif
}
virtual unsigned argumentRegisterCount() {

View File

@ -128,6 +128,12 @@ dynamicCall(void* function, uintptr_t* arguments, uint8_t* argumentTypes,
unsigned argumentCount, unsigned argumentsSize UNUSED,
unsigned returnType UNUSED)
{
#ifdef __APPLE__
const unsigned Alignment = 1;
#else
const unsigned Alignment = 2;
#endif
const unsigned GprCount = 4;
uintptr_t gprTable[GprCount];
unsigned gprIndex = 0;
@ -140,19 +146,21 @@ dynamicCall(void* function, uintptr_t* arguments, uint8_t* argumentTypes,
switch (argumentTypes[ati]) {
case DOUBLE_TYPE:
case INT64_TYPE: {
if (gprIndex + (8 / BytesPerWord) <= GprCount) { // pass argument on registers
if (gprIndex & 1) { // 8-byte alignment
memset(gprTable + gprIndex, 0, 4); // probably not necessary, but for good luck
if (gprIndex + Alignment <= GprCount) { // pass argument on registers
if (gprIndex % Alignment) { // 8-byte alignment
memset(gprTable + gprIndex, 0, 4); // probably not necessary, but for good luck
++gprIndex;
}
memcpy(gprTable + gprIndex, arguments + ai, 8);
gprIndex += 8 / BytesPerWord;
} else { // pass argument on stack
} else { // pass argument on stack
gprIndex = GprCount;
if (stackIndex & 1) { // 8-byte alignment
memset(stack + stackIndex, 0, 4); // probably not necessary, but for good luck
if (stackIndex % Alignment) { // 8-byte alignment
memset(stack + stackIndex, 0, 4); // probably not necessary, but for good luck
++stackIndex;
}
memcpy(stack + stackIndex, arguments + ai, 8);
stackIndex += 8 / BytesPerWord;
}

View File

@ -330,6 +330,7 @@ class Assembler {
virtual unsigned frameFootprint(unsigned footprint) = 0;
virtual unsigned argumentFootprint(unsigned footprint) = 0;
virtual bool argumentAlignment() = 0;
virtual bool argumentRegisterAlignment() = 0;
virtual unsigned argumentRegisterCount() = 0;
virtual int argumentRegister(unsigned index) = 0;

View File

@ -3179,21 +3179,19 @@ class CallEvent: public Event {
unsigned argumentIndex = 0;
while (true) {
unsigned footprint;
if (argumentIndex + 1 < argumentCount
and s->value->nextWord == s->next->value)
{
footprint = 2;
} else {
footprint = 1;
}
unsigned footprint
= (argumentIndex + 1 < argumentCount
and s->value->nextWord == s->next->value)
? 2 : 1;
if (footprint > 1 and index & 1 and c->arch->argumentAlignment()) {
if (index % (c->arch->argumentAlignment() ? footprint : 1)) {
++ index;
}
SiteMask targetMask;
if (index + footprint <= c->arch->argumentRegisterCount()) {
if (index + (c->arch->argumentRegisterAlignment() ? footprint : 1)
<= c->arch->argumentRegisterCount())
{
int number = c->arch->argumentRegister(index);
if (DebugReads) {

View File

@ -2135,6 +2135,10 @@ class MyArchitecture: public Assembler::Architecture {
return AlignArguments;
}
virtual bool argumentRegisterAlignment() {
return true;
}
virtual unsigned argumentRegisterCount() {
return 8;
}

View File

@ -2824,6 +2824,10 @@ class MyArchitecture: public Assembler::Architecture {
return false;
}
virtual bool argumentRegisterAlignment() {
return false;
}
virtual unsigned argumentRegisterCount() {
#ifdef PLATFORM_WINDOWS
if (BytesPerWord == 8) return 4; else