📄 inasm68.c
字号:
}
return 1;
}
//-------------------------------------------------------------------------
int asm_enterauto(ENODE *node, int inbr, int *rinbr, int *reg1, int *reg2, int
*rt1, int *rt2)
{
if (node && ((node)->nodetype == en_autocon || (node)->nodetype ==
en_autoreg))
{
if (*reg1 >= 0 && *reg2 >= 0)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
if (reg1 < 0)
{
*reg1 = 7;
if (prm_linkreg)
*reg1 = linkreg;
*rt1 = am_areg;
}
else
{
if (inbr)
*rinbr = 1;
*reg2 = 7;
if (prm_linkreg)
*reg2 = linkreg;
*rt2 = am_areg;
}
return 1;
}
return 2;
}
//-------------------------------------------------------------------------
static AMODE *asm_mem(void)
{
int reg1 = - 1, reg2 = - 1, scale = 1, temp, inbr = 0, usebr = 0;
int rinbr = 0, rg1t = 0, rg2t = 0, thisscale = 0;
int scalesize = 0;
ENODE *node = 0, *node0 = 0, *node1 = 0;
AMODE *rv;
int gotident = FALSE, autonode = FALSE;
if (lastst == minus)
{
getsym();
if (lastst != openpa)
{
asm_err(ERR_AMODEEXPECT);
return 0;
}
getsym();
if (lastst != kw_asmreg || keyimage->regtype != am_areg)
{
asm_err(ERR_AAREGEXPECT);
return 0;
}
regimage = keyimage;
getsym();
if (lastst != closepa)
{
asm_err(ERR_AMODEEXPECT);
return 0;
}
rv = xalloc(sizeof(AMODE));
rv->mode = am_adec;
rv->preg = regimage->regnum;
getsym();
return rv;
}
getsym();
if (lastst == openbr)
{
if (!prm_68020)
{
asm_err(ERR_AINVSELPROC);
return 0;
}
inbr = 1;
usebr = 1;
getsym();
}
while (TRUE)
{
int rg;
regimage = keyimage;
if (regimage)
rg = regimage->regnum;
switch (lastst)
{
case closebr:
if (!inbr)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
inbr = 0;
getsym();
break;
case kw_asmreg:
getsym();
scalesize = asm_getsize();
if (scalesize != 0 && scalesize != 2 && scalesize != 4)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
if (lastst == star)
{
getsym();
scale = intexpr(0);
thisscale = 1;
}
if (inbr)
{
if (reg1 == - 1 && thisscale)
{
asm_err(ERR_AMODEEXPECT);
return 0;
}
if (reg2 != - 1)
{
asm_err(ERR_ATOOMANYREGS);
return 0;
}
if (reg1 == - 1)
{
if (regimage->regtype != am_areg && regimage->regtype
!= am_pc)
{
asm_err(ERR_AAREGEXPECT);
return 0;
}
reg1 = rg;
rg1t = regimage->regtype;
}
else
{
rinbr = 1;
reg2 = rg;
rg2t = regimage->regtype;
}
}
else
{
if (reg1 == - 1 && !usebr)
{
if (thisscale)
{
if (reg2 != - 1)
{
asm_err(ERR_ATOOMANYREGS);
return 0;
}
reg2 = rg;
rg2t = regimage->regtype;
}
else
{
reg1 = rg;
rg1t = regimage->regtype;
}
}
else
{
if (reg2 != - 1)
{
asm_err(ERR_ATOOMANYREGS);
return 0;
}
rg2t = regimage->regtype;
reg2 = rg;
}
}
break;
case plus:
case minus:
case iconst:
if (usebr)
{
if (inbr)
{
if (node0)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
node0 = makeintnode(en_icon, intexpr(0));
}
else
{
if (node1)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
node1 = makeintnode(en_icon, intexpr(0));
}
}
else
if (!node0)
node0 = makeintnode(en_icon, intexpr(0));
else
if (!node1)
node1 = makeintnode(en_icon, intexpr(0));
else
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
break;
case id:
if (gotident)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
node = asm_ident();
if (lastst == plus)
{
getsym();
node = makenode(en_add, node, makeintnode(en_icon, intexpr
(0)));
}
gotident = TRUE;
switch (asm_enterauto(node, inbr, &rinbr, ®1, ®2, &rg1t,
&rg2t))
{
case 0:
return 0;
case 1:
autonode = TRUE;
break;
case 2:
autonode = FALSE;
break;
}
if (usebr)
{
if (inbr)
{
if (node0)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
node0 = node;
}
else
{
if (node1)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
node1 = node;
}
}
else
if (!node0)
node0 = node;
else
if (!node1)
node1 = node;
else
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
break;
default:
asm_err(ERR_AILLADDRESS);
return 0;
}
if (lastst == begin)
break;
if (lastst == closepa)
{
getsym();
break;
}
if (lastst == closebr)
continue;
if (lastst != comma)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
getsym();
}
if (rg2t == am_pc && scale != 1)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
/* swap to get dreg in second pos */
if (((reg1 != - 1 && rg1t == am_dreg) && reg2 != - 1 && scale == 1) ||
rg2t == am_pc)
{
int rg3t = rg1t;
int reg3 = reg1;
reg2 = reg1;
rg2t = rg1t;
reg1 = reg3;
rg1t = rg3t;
}
if (!prm_68020)
{
if (reg1 == - 1 && reg2 == - 1 && (node1 || !node0))
{
asm_err(ERR_AINVSELPROC);
return 0;
}
if (reg1 == - 1 && reg2 != - 1 && (rg2t != am_areg || scale != 1))
{
asm_err(ERR_AINVSELPROC);
return 0;
}
}
if (reg1 == - 1 && reg2 == - 1 && !node0)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
if (scale != 1 && scale != 2 && scale != 4 && scale != 8)
{
asm_err(ERR_ASCALE);
return 0;
}
if (scale == 1)
scale = 0;
else if (scale == 2)
scale = 1;
else if (scale == 4)
scale = 2;
else if (scale == 8)
scale = 3;
if (rg1t == am_dreg)
{
asm_err(ERR_AAREGEXPECT);
return 0;
}
if (node1 && !usebr)
{
asm_err(ERR_AINVINDXMODE);
return 0;
}
rv = xalloc(sizeof(AMODE));
if (node1)
{
rv->offset = node1;
}
rv->preg = reg1;
rv->sreg = reg2;
rv->scale = scale;
if (usebr)
{
if (!node0)
rv->offset = makeintnode(en_icon, 0);
else
rv->offset = node0;
if (!node1)
rv->offset2 = makeintnode(en_icon, 0);
else
rv->offset2 = node1;
rv->sz = scalesize;
if (rinbr)
{
if (reg1 == - 1 && reg2 == - 1)
rv->mode = am_iimem;
else
if (reg1 != - 1)
{
if (reg2 != - 1)
{
if (rg1t == am_pc)
{
if (rg2t == am_areg)
rv->mode = am_iiprepca;
else
rv->mode = am_iiprepcd;
}
else
if (rg2t == am_areg)
rv->mode = am_iiprea;
else
rv->mode = am_iipred;
}
else
if (rg1t == am_pc)
rv->mode = am_iiprepca;
else
rv->mode = am_iiprea;
}
else
if (rg2t == am_areg)
rv->mode = am_iiprea;
else
rv->mode = am_iipred;
}
else
{
if (reg1 == - 1 && reg2 == - 1)
rv->mode = am_iimem;
else
if (reg1 != - 1)
{
if (reg2 != - 1)
{
if (rg1t == am_pc)
{
if (rg2t == am_areg)
rv->mode = am_iipostpca;
else
rv->mode = am_iipostpcd;
}
else
if (rg2t == am_areg)
rv->mode = am_iiposta;
else
rv->mode = am_iipostd;
}
else
if (rg1t == am_pc)
rv->mode = am_iipostpca;
else
rv->mode = am_iiposta;
}
else
if (rg2t == am_areg)
rv->mode = am_iiposta;
else
rv->mode = am_iipostd;
}
}
else
{
if (reg1 != - 1)
{
if (reg2 != - 1)
{
if (!node0)
rv->offset = makeintnode(en_icon, 0);
else
rv->offset = node0;
if (rg1t == am_pc)
{
if (rg2t == am_areg)
rv->mode = am_pcindxaddr;
else
rv->mode = am_pcindxdata;
}
else
if (rg2t == am_areg)
rv->mode = am_baseindxaddr;
else
rv->mode = am_baseindxdata;
rv->sz = scalesize;
if (rv->mode == am_immed && (rv->offset->v.i &0xffff0000) &&
!prm_68020)
generror(ERR_AINVSELPROC, 0, 0);
}
else
{
if (!node0)
{
rv->offset = makeintnode(en_icon, 0);
if (rg1t == am_pc)
{
rv->mode = am_pcindx;
}
else
if (lastst == plus)
{
getsym();
rv->mode = am_ainc;
}
else
rv->mode = am_ind;
}
else
{
rv->offset = node0;
if (rg1t == am_pc)
rv->mode = am_pcindx;
else
{
rv->mode = am_indx;
}
if (rv->mode == am_immed && (rv->offset->v.i &0xffff0000)
&& !prm_68020)
generror(ERR_AINVSELPROC, 0, 0);
}
}
}
else if (reg2 != - 1)
{
if (!node0)
rv->offset = makeintnode(en_icon, 0);
else
rv->offset = node0;
if (rg2t == am_areg)
rv->mode = am_baseindxaddr;
else
rv->mode = am_baseindxdata;
rv->sz = scalesize;
if (rv->mode == am_immed && (rv->offset->v.i &0xffff0000) &&
!prm_68020)
generror(ERR_AINVSELPROC, 0, 0);
}
else
{
rv->mode = am_adirect;
rv->preg = asm_getsize();
rv->offset = node0;
if (!rv->length)
if (prm_smalldata)
rv->length = 2;
else
rv->length = 4;
}
}
return rv;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -