mirror of
https://github.com/dlang/dmd.git
synced 2025-04-26 05:00:16 +03:00
go over cdfunc() for AArch64 (#20941)
This commit is contained in:
parent
37469bfae8
commit
5cd254f9e0
2 changed files with 14 additions and 52 deletions
|
@ -1297,7 +1297,6 @@ void cdfunc(ref CGstate cg, ref CodeBuilder cdb, elem* e, ref regm_t pretregs)
|
||||||
//printf("stackpushsave: %d\n", stackpushsave);
|
//printf("stackpushsave: %d\n", stackpushsave);
|
||||||
cgstate.stackclean++;
|
cgstate.stackclean++;
|
||||||
regm_t keepmsk = 0;
|
regm_t keepmsk = 0;
|
||||||
int xmmcnt = 0;
|
|
||||||
tym_t tyf = tybasic(e.E1.Ety); // the function type
|
tym_t tyf = tybasic(e.E1.Ety); // the function type
|
||||||
|
|
||||||
// Easier to deal with parameters as an array: parameters[0..np]
|
// Easier to deal with parameters as an array: parameters[0..np]
|
||||||
|
@ -1362,9 +1361,7 @@ void cdfunc(ref CGstate cg, ref CodeBuilder cdb, elem* e, ref regm_t pretregs)
|
||||||
parameters[i].reg = NOREG;
|
parameters[i].reg = NOREG;
|
||||||
uint alignsize = el_alignsize(ep);
|
uint alignsize = el_alignsize(ep);
|
||||||
parameters[i].numalign = 0;
|
parameters[i].numalign = 0;
|
||||||
if (alignsize > stackalign &&
|
if (alignsize > stackalign)
|
||||||
(I64 || (alignsize >= 16 &&
|
|
||||||
(config.exe & (EX_OSX | EX_LINUX) && (tyaggregate(ep.Ety) || tyvector(ep.Ety))))))
|
|
||||||
{
|
{
|
||||||
if (alignsize > STACKALIGN)
|
if (alignsize > STACKALIGN)
|
||||||
{
|
{
|
||||||
|
@ -1386,8 +1383,8 @@ void cdfunc(ref CGstate cg, ref CodeBuilder cdb, elem* e, ref regm_t pretregs)
|
||||||
}
|
}
|
||||||
|
|
||||||
//printf("numpara = %d, cgstate.stackpush = %d\n", numpara, stackpush);
|
//printf("numpara = %d, cgstate.stackpush = %d\n", numpara, stackpush);
|
||||||
assert((numpara & (REGSIZE - 1)) == 0);
|
assert((numpara & (REGSIZE - 1)) == 0); // check alignment
|
||||||
assert((cgstate.stackpush & (REGSIZE - 1)) == 0);
|
assert((cgstate.stackpush & (REGSIZE - 1)) == 0); // check alignment
|
||||||
|
|
||||||
/* Should consider reordering the order of evaluation of the parameters
|
/* Should consider reordering the order of evaluation of the parameters
|
||||||
* so that args that go into registers are evaluated after args that get
|
* so that args that go into registers are evaluated after args that get
|
||||||
|
@ -1453,9 +1450,8 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
//printf("funcargtos1 = %d\n", cast(int)funcargtos);
|
//printf("funcargtos1 = %d\n", cast(int)funcargtos);
|
||||||
|
|
||||||
// TODO AArch64
|
// TODO AArch64
|
||||||
/* Parameters go into the registers RDI,RSI,RDX,RCX,R8,R9
|
/* Parameters go into the registers x0..x7
|
||||||
* float and double parameters go into XMM0..XMM7
|
* floating point parameters go into q0..q7 (16 bytes each)
|
||||||
* For variadic functions, count of XMM registers used goes in AL
|
|
||||||
*/
|
*/
|
||||||
foreach (i; 0 .. np)
|
foreach (i; 0 .. np)
|
||||||
{
|
{
|
||||||
|
@ -1487,7 +1483,6 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
for (reg_t j = 0; tosave; j++)
|
for (reg_t j = 0; tosave; j++)
|
||||||
{
|
{
|
||||||
regm_t mi = mask(j);
|
regm_t mi = mask(j);
|
||||||
assert(j <= XMM7);
|
|
||||||
if (mi & tosave)
|
if (mi & tosave)
|
||||||
{
|
{
|
||||||
uint idx;
|
uint idx;
|
||||||
|
@ -1506,29 +1501,24 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
{
|
{
|
||||||
// Goes in register preg, not stack
|
// Goes in register preg, not stack
|
||||||
regm_t retregs = mask(preg);
|
regm_t retregs = mask(preg);
|
||||||
if (retregs & XMMREGS)
|
|
||||||
++xmmcnt;
|
|
||||||
reg_t preg2 = parameters[i].reg2;
|
reg_t preg2 = parameters[i].reg2;
|
||||||
reg_t mreg,lreg;
|
reg_t mreg,lreg;
|
||||||
if (preg2 != NOREG || tybasic(ep.Ety) == TYcfloat)
|
if (preg2 != NOREG || tybasic(ep.Ety) == TYcfloat)
|
||||||
{
|
{
|
||||||
assert(ep.Eoper != OPstrthis);
|
assert(ep.Eoper != OPstrthis);
|
||||||
if (mask(preg2) & XMMREGS)
|
|
||||||
++xmmcnt;
|
|
||||||
if (tybasic(ep.Ety) == TYcfloat)
|
if (tybasic(ep.Ety) == TYcfloat)
|
||||||
{
|
{
|
||||||
lreg = ST01;
|
assert(0);
|
||||||
mreg = NOREG;
|
|
||||||
}
|
}
|
||||||
else if (tyrelax(ep.Ety) == TYcent)
|
else if (tyrelax(ep.Ety) == TYcent)
|
||||||
{
|
{
|
||||||
lreg = mask(preg ) & mLSW ? cast(reg_t)preg : AX;
|
lreg = mask(preg ) & mLSW ? cast(reg_t)preg : 0;
|
||||||
mreg = mask(preg2) & mMSW ? cast(reg_t)preg2 : DX;
|
mreg = mask(preg2) & mMSW ? cast(reg_t)preg2 : 1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
lreg = XMM0;
|
lreg = 32;
|
||||||
mreg = XMM1;
|
mreg = 33;
|
||||||
}
|
}
|
||||||
retregs = (mask(mreg) | mask(lreg)) & ~mask(NOREG);
|
retregs = (mask(mreg) | mask(lreg)) & ~mask(NOREG);
|
||||||
CodeBuilder cdbsave;
|
CodeBuilder cdbsave;
|
||||||
|
@ -1541,7 +1531,6 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
for (reg_t j = 0; tosave; j++)
|
for (reg_t j = 0; tosave; j++)
|
||||||
{
|
{
|
||||||
regm_t mi = mask(j);
|
regm_t mi = mask(j);
|
||||||
assert(j <= XMM7);
|
|
||||||
if (mi & tosave)
|
if (mi & tosave)
|
||||||
{
|
{
|
||||||
uint idx;
|
uint idx;
|
||||||
|
@ -1615,6 +1604,7 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
(modregrm(0,4,SP) << 8) | modregxrm(2,preg,4), FL.const_,delta);
|
(modregrm(0,4,SP) << 8) | modregxrm(2,preg,4), FL.const_,delta);
|
||||||
if (I64)
|
if (I64)
|
||||||
code_orrex(cdb.last(), REX_W);
|
code_orrex(cdb.last(), REX_W);
|
||||||
|
assert(0); // TODO AArch64
|
||||||
}
|
}
|
||||||
else if (ep.Eoper == OPstrpar && config.exe == EX_WIN64 && type_size(ep.ET) == 0)
|
else if (ep.Eoper == OPstrpar && config.exe == EX_WIN64 && type_size(ep.ET) == 0)
|
||||||
{
|
{
|
||||||
|
@ -1638,29 +1628,6 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
cdb.genadjesp(sz);
|
cdb.genadjesp(sz);
|
||||||
cgstate.stackpush += sz;
|
cgstate.stackpush += sz;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Variadic functions store XMM parameters into their corresponding GP registers
|
|
||||||
*/
|
|
||||||
for (int i = 0; i < np; i++)
|
|
||||||
{
|
|
||||||
int preg = parameters[i].reg;
|
|
||||||
regm_t retregs = mask(preg);
|
|
||||||
if (retregs & XMMREGS)
|
|
||||||
{
|
|
||||||
reg_t reg;
|
|
||||||
switch (preg)
|
|
||||||
{
|
|
||||||
case XMM0: reg = CX; break;
|
|
||||||
case XMM1: reg = DX; break;
|
|
||||||
case XMM2: reg = R8; break;
|
|
||||||
case XMM3: reg = R9; break;
|
|
||||||
|
|
||||||
default: assert(0);
|
|
||||||
}
|
|
||||||
getregs(cdb,mask(reg));
|
|
||||||
//cdb.gen2(STOD,(REX_W << 16) | modregxrmx(3,preg-XMM0,reg)); // MOVD reg,preg
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Restore any register parameters we saved
|
// Restore any register parameters we saved
|
||||||
|
@ -1668,14 +1635,6 @@ printf("numalign: %d numpara: %d\n", numalign, numpara);
|
||||||
cdb.append(cdbrestore);
|
cdb.append(cdbrestore);
|
||||||
keepmsk |= saved;
|
keepmsk |= saved;
|
||||||
|
|
||||||
// Variadic functions store the number of XMM registers used in AL
|
|
||||||
if (config.exe != EX_WIN64 && e.Eflags & EFLAGS_variadic && !cg.AArch64)
|
|
||||||
{
|
|
||||||
getregs(cdb,mAX);
|
|
||||||
movregconst(cdb,AX,xmmcnt,1);
|
|
||||||
keepmsk |= mAX;
|
|
||||||
}
|
|
||||||
|
|
||||||
//printf("funcargtos: %d cgstate.funcargtos: %d\n", cast(int)funcargtos, cast(int)cgstate.funcargtos);
|
//printf("funcargtos: %d cgstate.funcargtos: %d\n", cast(int)funcargtos, cast(int)cgstate.funcargtos);
|
||||||
assert(funcargtos == 0 && cgstate.funcargtos == ~0);
|
assert(funcargtos == 0 && cgstate.funcargtos == ~0);
|
||||||
cgstate.stackclean--;
|
cgstate.stackclean--;
|
||||||
|
|
|
@ -67,6 +67,7 @@ nothrow:
|
||||||
@trusted
|
@trusted
|
||||||
void REGSAVE_save(ref REGSAVE regsave, ref CodeBuilder cdb, reg_t reg, out uint idx)
|
void REGSAVE_save(ref REGSAVE regsave, ref CodeBuilder cdb, reg_t reg, out uint idx)
|
||||||
{
|
{
|
||||||
|
// TODO AArch64 floating point registers
|
||||||
if (!regsave.alignment)
|
if (!regsave.alignment)
|
||||||
regsave.alignment = REGSIZE;
|
regsave.alignment = REGSIZE;
|
||||||
idx = regsave.idx;
|
idx = regsave.idx;
|
||||||
|
@ -94,6 +95,7 @@ void REGSAVE_save(ref REGSAVE regsave, ref CodeBuilder cdb, reg_t reg, out uint
|
||||||
@trusted
|
@trusted
|
||||||
void REGSAVE_restore(const ref REGSAVE regsave, ref CodeBuilder cdb, reg_t reg, uint idx)
|
void REGSAVE_restore(const ref REGSAVE regsave, ref CodeBuilder cdb, reg_t reg, uint idx)
|
||||||
{
|
{
|
||||||
|
// TODO AArch64 floating point registers
|
||||||
// LDR reg,[BP, #idx]
|
// LDR reg,[BP, #idx]
|
||||||
code cs;
|
code cs;
|
||||||
cs.reg = reg;
|
cs.reg = reg;
|
||||||
|
@ -897,6 +899,7 @@ void gentstreg(ref CodeBuilder cdb, reg_t reg, uint sf)
|
||||||
@trusted
|
@trusted
|
||||||
void genmovreg(ref CodeBuilder cdb, reg_t to, reg_t from, tym_t ty = TYMAX)
|
void genmovreg(ref CodeBuilder cdb, reg_t to, reg_t from, tym_t ty = TYMAX)
|
||||||
{
|
{
|
||||||
|
// TODO ftype and TYMAX ?
|
||||||
if (to <= 31)
|
if (to <= 31)
|
||||||
{
|
{
|
||||||
// integer
|
// integer
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue