📄 outas386.c
字号:
case en_lucon:
case en_ccon:
case en_absacon:
fprintf(outputFile,"0%lXH",offset->v.i);
break;
case en_rcon:
case en_fcon:
case en_lrcon:
fprintf(outputFile,"%f",offset->v.f);
break;
case en_labcon:
case en_nalabcon:
/* if (!prm_nasm && !prm_flat)
fprintf(outputFile,"CS:");
*/ fprintf(outputFile,"L_%d",offset->v.i);
break;
case en_napccon:
case en_nacon:
fprintf(outputFile,"%s",offset->v.p[0]);
break;
case en_add:
putconst(offset->v.p[0]);
fprintf(outputFile,"+");
putconst(offset->v.p[1]);
break;
case en_sub:
putconst(offset->v.p[0]);
fprintf(outputFile,"-");
putconst(offset->v.p[1]);
break;
case en_uminus:
fprintf(outputFile,"-");
putconst(offset->v.p[0]);
break;
default:
DIAG("illegal constant node.");
break;
}
}
void putlen(int l)
/*
* append the length field to an instruction.
*/
{
if (l!= 10 && l != 8 && l != 6 && l != 4 && l != 1 && l != 2 && l != 0)
DIAG("illegal length field.");
}
void putsizedreg(char *string, int reg, int size)
{
static char *byteregs[] = { "AL","CL","DL","BL","AH","CH","DH","BH" };
static char *wordregs[] = { "AX", "CX", "DX","BX","SP","BP","SI","DI" };
static char *longregs[] = { "EAX", "ECX", "EDX","EBX","ESP","EBP","ESI","EDI" };
if (size == 4)
fprintf(outputFile,string,longregs[reg]);
else if (size == 1)
fprintf(outputFile,string,byteregs[reg]);
else
fprintf(outputFile,string,wordregs[reg]);
}
void pointersize(int size)
{
if (prm_nasm && skipsize)
return;
/* if (needpointer)
*/ switch (size) {
case 10:
fprintf(outputFile,"TBYTE ");
break;
case 8:
fprintf(outputFile,"QWORD ");
break;
case 6:
if (!uses_float) {
fprintf(outputFile,"FWORD ");
break;
}
case 4:
fprintf(outputFile,"DWORD ");
break;
case 2:
fprintf(outputFile,"WORD ");
break;
case 1:
fprintf(outputFile,"BYTE ");
break;
default:
DIAG("Bad pointer");
}
if (!prm_nasm)
fprintf(outputFile,"PTR ");
}
void putseg(int seg, int usecolon)
{
if (!seg)
return;
seg-=1;
seg<<=1;
fputc(segregs[seg], outputFile);
fputc(segregs[seg+1], outputFile);
if (usecolon)
fputc(':', outputFile);
}
void putamode(AMODE *ap)
/*
* output a general addressing mode.
*/
{ int oldnasm, l;
switch( ap->mode )
{
case am_seg:
putseg(ap->seg,0);
break;
case am_screg:
fprintf(outputFile,"CR%d",ap->preg);
break;
case am_sdreg:
fprintf(outputFile,"DR%d",ap->preg);
break;
case am_streg:
fprintf(outputFile,"TR%d",ap->preg);
break;
case am_immed:
if (ap->length && (ap->offset->nodetype == en_labcon
|| ap->offset->nodetype == en_nacon || ap->offset->nodetype == en_nalabcon
|| ap->offset->nodetype == en_napccon)) {
if (!prm_nasm)
fprintf(outputFile,"OFFSET ");
else
if (!nosize)
fprintf(outputFile,"DWORD ");
}
else
if (prm_nasm && addsize)
pointersize(ap->length);
putconst(ap->offset);
break;
case am_direct:
pointersize(ap->length);
putseg(ap->seg,TRUE);
/* if (!prm_flat)
fprintf(outputFile,"DS:");
*/ fprintf(outputFile,"[");
oldnasm = prm_nasm;
prm_nasm = TRUE;
putconst(ap->offset);
fputc(']',outputFile);
prm_nasm = oldnasm;
break;
case am_dreg:
putsizedreg("%s",ap->preg,ap->length);
break;
case am_freg:
fprintf(outputFile,"ST(%d)",ap->preg);
break;
case am_indisp:
pointersize(ap->length);
putseg(ap->seg,TRUE);
putsizedreg("[%s",ap->preg,4);
if (ap->offset) {
fputc('+',outputFile);
putconst(ap->offset);
}
fputc(']',outputFile);
break;
case am_indispscale: {
int scale = 1,t=ap->scale;
while (t--)
scale <<=1;
pointersize(ap->length);
putseg(ap->seg,TRUE);
if (ap->preg == -1)
fputc('[',outputFile);
else
putsizedreg("[%s+",ap->preg,4);
putsizedreg("%s",ap->sreg,4);
if (scale != 1)
fprintf(outputFile,"*%d",scale);
if (ap->offset) {
fputc('+',outputFile);
putconst(ap->offset);
}
fputc(']',outputFile);
}
break;
default:
DIAG("illegal address mode.");
break;
}
}
void put_code(OCODE *cd)
/*
* outputFile a generic instruction.
*/
{
int op = cd->opcode,len=0,len2=0;
AMODE *aps = cd->oper1,*apd = cd->oper2, *ap3 = cd->oper3;
if (!prm_asmfile)
return;
if (op == op_line) {
if (!prm_lines)
return;
fprintf(outputFile,";\n; Line %d:\t%s\n;\n",(int)apd,(char *)aps);
return;
}
if (aps)
len = aps->length;
if (apd)
len2 = apd->length;
needpointer = (len != len2) || ((!aps || aps->mode !=am_dreg) && (!apd || apd->mode !=am_dreg));
putop(op);
if (prm_nasm && op >=op_ja && op <= op_jns)
fprintf(outputFile,"\tNEAR");
switch (op) {
case op_rep:
case op_repz:
case op_repe:
case op_repnz:
case op_repne:
case op_lock:
return;
}
putlen(len);
if( aps != 0 ) {
fprintf(outputFile,"\t");
if (op == op_dd)
nosize = TRUE;
putamode(aps);
nosize = FALSE;
if( apd != 0 )
{
fprintf(outputFile,",");
putamode(apd);
}
if( ap3 != 0 )
{
fprintf(outputFile,",");
putamode(ap3);
}
}
fprintf(outputFile,"\n");
}
void gen_strlab(SYM *s)
/*
* generate a named label.
*/
{
if (prm_asmfile)
if (curseg == dataseg || curseg == bssxseg) {
newlabel = TRUE;
fprintf(outputFile,"\n%s",s->name);
outcol = strlen(s->name)+1;
}
else
if (currentfunc->pascaldefn) {
char buf[100],*q=buf,*p=s->name;
if (prm_cmangle)
p++;
while(*p)
*q++=toupper(*p++);
*q++ = 0;
fprintf(outputFile,"%s:\n",buf);
}
else
fprintf(outputFile,"%s:\n",s->name);
}
void put_label(int lab)
/*
* outputFile a compiler generated label.
*/
{
if (prm_asmfile)
fprintf(outputFile,"L_%d:\n",lab);
}
void put_staticlabel(long label)
{
if (prm_asmfile) {
nl();
if (curseg == dataseg || curseg == bssxseg) {
newlabel = TRUE;
fprintf(outputFile,"\nL_%ld",label);
outcol = 8;
}
else
fprintf(outputFile,"L_%ld:\n",label);
}
}
void genfloat(float val)
/*
* Output a float value
*/
{ if (prm_asmfile)
if( gentype == floatgen && outcol < 60) {
fprintf(outputFile,",%f",val);
outcol += 8;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDD\t%f",val);
gentype = floatgen;
outcol = 19;
}
}
void gendouble(double val)
/*
* Output a double value
*/
{ if (prm_asmfile)
if( gentype == doublegen && outcol < 60) {
fprintf(outputFile,",%f",val);
outcol += 8;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDQ\t%f",val);
gentype = doublegen;
outcol = 19;
}
}
void genlongdouble(double val)
/*
* Output a double value
*/
{ if (prm_asmfile)
if( gentype == longdoublegen && outcol < 60) {
fprintf(outputFile,",%f",val);
outcol += 8;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDT\t%f",val);
gentype = longdoublegen;
outcol = 19;
}
}
int genstring(char *str, int uselong)
/*
* Generate a string literal
*/
{
if (uselong) {
while (*(short *)str) {
genword(*((short *)str));
str+=2;
}
return pstrlen(str)*2;
}
else {
while (*str)
genbyte(*str++);
return strlen(str);
}
}
void genbyte(long val)
/*
* Output a byte value
*/
{ if (prm_asmfile)
if( gentype == bytegen && outcol < 60) {
fprintf(outputFile,",0%XH",val & 0x00ff);
outcol += 4;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDB\t0%XH",val & 0x00ff);
gentype = bytegen;
outcol = 19;
}
}
void genword(long val)
/*
* Output a word value
*/
{ if (prm_asmfile)
if( gentype == wordgen && outcol < 58) {
fprintf(outputFile,",0%XH",val & 0x0ffff);
outcol += 6;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDW\t0%XH",val & 0x0ffff);
gentype = wordgen;
outcol = 21;
}
}
void genlong(long val)
/*
* Output a long value
*/
{ if (prm_asmfile)
if( gentype == longgen && outcol < 56) {
fprintf(outputFile,",0%lXH",val);
outcol += 10;
}
else {
if (!newlabel)
nl();
else newlabel = FALSE;
fprintf(outputFile,"\tDD\t0%lXH",val);
gentype = longgen;
outcol = 25;
}
}
void gensrref(SYM *sp, int val)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -