Added 16-bit mode
This commit is contained in:
parent
9a5ac60946
commit
2c7496a525
5 changed files with 146 additions and 32 deletions
|
@ -75,3 +75,28 @@ char regindex_ind[8][8] = {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
extern int address_long INIT(1), operand_long INIT(1);
|
extern int address_long INIT(1), operand_long INIT(1);
|
||||||
|
extern int use32 INIT(1);
|
||||||
|
|
||||||
|
/* For 16-bit addressing: copied from i86 assembler */
|
||||||
|
#ifndef extern
|
||||||
|
extern char sr_m[8];
|
||||||
|
#else
|
||||||
|
char sr_m[8] = {
|
||||||
|
-1, -1, -1, 7, -1, 6, 4, 5
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef extern
|
||||||
|
extern char dr_m[8][8];
|
||||||
|
#else
|
||||||
|
char dr_m[8][8] = {
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1,
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1,
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1,
|
||||||
|
-1, -1, -1, -1, -1, -1, 0, 1,
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1,
|
||||||
|
-1, -1, -1, -1, -1, -1, 2, 3,
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1,
|
||||||
|
-1, -1, -1, -1, -1, -1, -1, -1
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
|
@ -8,6 +8,10 @@
|
||||||
* INTEL 80386 tokens
|
* INTEL 80386 tokens
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
%token <y_word> ATOGGLE
|
||||||
|
%token <y_word> OTOGGLE
|
||||||
|
%token <y_word> USE16
|
||||||
|
%token <y_word> USE32
|
||||||
%token <y_word> R32
|
%token <y_word> R32
|
||||||
%token <y_word> R16
|
%token <y_word> R16
|
||||||
%token <y_word> R8
|
%token <y_word> R8
|
||||||
|
|
|
@ -10,6 +10,8 @@
|
||||||
* No system registers for now ...
|
* No system registers for now ...
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
0, USE16, 0, ".use16",
|
||||||
|
0, USE32, 0, ".use32",
|
||||||
0, R32, 0, "ax",
|
0, R32, 0, "ax",
|
||||||
0, R32, 1, "cx",
|
0, R32, 1, "cx",
|
||||||
0, R32, 2, "dx",
|
0, R32, 2, "dx",
|
||||||
|
@ -213,10 +215,10 @@
|
||||||
0, NOTOP, 071, "idiv",
|
0, NOTOP, 071, "idiv",
|
||||||
0, PREFIX, 0144, "fseg",
|
0, PREFIX, 0144, "fseg",
|
||||||
0, PREFIX, 0145, "gseg",
|
0, PREFIX, 0145, "gseg",
|
||||||
0, PREFIX, 0146, "o16", /* operand size toggle */
|
0, OTOGGLE, 0146, "o16", /* operand size toggle */
|
||||||
0, PREFIX, 0146, "o32", /* operand size toggle */
|
0, OTOGGLE, 0346, "o32", /* operand size toggle */
|
||||||
0, PREFIX, 0147, "a16", /* address size toggle */
|
0, ATOGGLE, 0147, "a16", /* address size toggle */
|
||||||
0, PREFIX, 0147, "a32", /* address size toggle */
|
0, ATOGGLE, 0347, "a32", /* address size toggle */
|
||||||
0, PREFIX, 0360, "lock",
|
0, PREFIX, 0360, "lock",
|
||||||
0, PREFIX, 0362, "rep",
|
0, PREFIX, 0362, "rep",
|
||||||
0, PREFIX, 0362, "repne",
|
0, PREFIX, 0362, "repne",
|
||||||
|
|
|
@ -8,17 +8,36 @@
|
||||||
|
|
||||||
operation
|
operation
|
||||||
:
|
:
|
||||||
prefix oper
|
USE16
|
||||||
{ address_long = 1; operand_long = 1; }
|
{ use32 = 0; address_long = 0; operand_long = 0; }
|
||||||
|
|
|
||||||
|
USE32
|
||||||
|
{ use32 = 1; address_long = 1; operand_long = 1; }
|
||||||
|
| prefix oper
|
||||||
|
{ address_long = use32; operand_long = use32; }
|
||||||
| prefix1 /* to allow for only prefixes on a line */
|
| prefix1 /* to allow for only prefixes on a line */
|
||||||
;
|
;
|
||||||
prefix : /* empty */
|
prefix : /* empty */
|
||||||
| prefix1
|
| prefix1
|
||||||
;
|
;
|
||||||
prefix1: prefix PREFIX
|
prefix1: prefix PREFIX { emit1($2); }
|
||||||
{ if ($2 == 0146) operand_long = ! operand_long;
|
|
|
||||||
if ($2 == 0147) address_long = ! address_long;
|
prefix ATOGGLE
|
||||||
emit1($2);
|
{ if ((($2&0200) >> 7) == address_long) {
|
||||||
|
if (pass == PASS_3) warning("address size toggle ignored");
|
||||||
|
} else {
|
||||||
|
emit1($2 & 0177);
|
||||||
|
address_long = ! address_long;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
prefix OTOGGLE
|
||||||
|
{ if ((($2&0200) >> 7) == operand_long) {
|
||||||
|
if (pass == PASS_3) warning("operand size toggle ignored");
|
||||||
|
} else {
|
||||||
|
emit1($2 & 0177);
|
||||||
|
operand_long = ! operand_long;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
oper : NOOP_1
|
oper : NOOP_1
|
||||||
|
@ -177,8 +196,15 @@ st_i : ST '(' absexp ')'
|
||||||
|
|
||||||
;
|
;
|
||||||
mem : '(' expr ')'
|
mem : '(' expr ')'
|
||||||
{ rm_2 = 05; exp_2 = $2; reg_2 = 05; mod_2 = 0;
|
{ if (address_long) {
|
||||||
|
rm_2 = 05; reg_2 = 05; mod_2 = 0;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
reg_2 = 06;
|
||||||
|
}
|
||||||
|
exp_2 = $2;
|
||||||
RELOMOVE(rel_2, relonami);
|
RELOMOVE(rel_2, relonami);
|
||||||
|
|
||||||
}
|
}
|
||||||
| bases
|
| bases
|
||||||
{ exp_2.val = 0; exp_2.typ = S_ABS; indexed();}
|
{ exp_2.val = 0; exp_2.typ = S_ABS; indexed();}
|
||||||
|
@ -188,11 +214,21 @@ mem : '(' expr ')'
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
bases : '(' R32 ')'
|
bases : '(' R32 ')'
|
||||||
{ reg_2 = $2; sib_2 = 0; rm_2 = 0;}
|
{ if (address_long) {
|
||||||
|
reg_2 = $2; sib_2 = 0; rm_2 = 0;
|
||||||
|
}
|
||||||
|
else reg_2 = sr_m[$2];
|
||||||
|
}
|
||||||
| '(' R32 ')' '(' R32 scale ')'
|
| '(' R32 ')' '(' R32 scale ')'
|
||||||
{ rm_2 = 04; sib_2 |= regindex_ind[$2][$5];
|
{ if (address_long) {
|
||||||
|
rm_2 = 04;
|
||||||
|
sib_2 |= regindex_ind[$2][$5];
|
||||||
reg_2 = $2;
|
reg_2 = $2;
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
|
reg_2 = dr_m[$2][$5];
|
||||||
|
}
|
||||||
|
}
|
||||||
| '(' R32 '*' absexp ')'
|
| '(' R32 '*' absexp ')'
|
||||||
{ if ($4 == 1) {
|
{ if ($4 == 1) {
|
||||||
reg_2 = $2; sib_2 = 0; rm_2 = 0;
|
reg_2 = $2; sib_2 = 0; rm_2 = 0;
|
||||||
|
|
|
@ -8,7 +8,40 @@
|
||||||
* INTEL 80386 special routines
|
* INTEL 80386 special routines
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
ea_1_16(param)
|
||||||
|
{
|
||||||
|
if ((reg_1 & 070) || (param & ~070)) {
|
||||||
|
serror("bad operand");
|
||||||
|
}
|
||||||
|
emit1(reg_1 | param);
|
||||||
|
switch(reg_1 >> 6) {
|
||||||
|
case 0:
|
||||||
|
if (reg_1 == 6 || (reg_1 & 040)) {
|
||||||
|
#ifdef RELOCATION
|
||||||
|
RELOMOVE(relonami, rel_1);
|
||||||
|
newrelo(exp_1.typ, RELO2);
|
||||||
|
#endif
|
||||||
|
emit2(exp_1.val);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
emit1(exp_1.val);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
#ifdef RELOCATION
|
||||||
|
RELOMOVE(relonami, rel_1);
|
||||||
|
newrelo(exp_1.typ, RELO2);
|
||||||
|
#endif
|
||||||
|
emit2(exp_1.val);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ea_1(param) {
|
ea_1(param) {
|
||||||
|
if (! address_long) {
|
||||||
|
ea_1_16(param);
|
||||||
|
return;
|
||||||
|
}
|
||||||
if (is_expr(reg_1)) {
|
if (is_expr(reg_1)) {
|
||||||
serror("bad operand");
|
serror("bad operand");
|
||||||
return;
|
return;
|
||||||
|
@ -49,6 +82,10 @@ checkscale(val)
|
||||||
{
|
{
|
||||||
int v = val;
|
int v = val;
|
||||||
|
|
||||||
|
if (! address_long) {
|
||||||
|
serror("scaling not allowed in 16-bit mode");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
if (v != val) v = 0;
|
if (v != val) v = 0;
|
||||||
switch(v) {
|
switch(v) {
|
||||||
case 1:
|
case 1:
|
||||||
|
@ -93,6 +130,7 @@ regsize(sz)
|
||||||
}
|
}
|
||||||
|
|
||||||
indexed() {
|
indexed() {
|
||||||
|
if (address_long) {
|
||||||
mod_2 = 0;
|
mod_2 = 0;
|
||||||
if (sib_2 == -1)
|
if (sib_2 == -1)
|
||||||
serror("register error");
|
serror("register error");
|
||||||
|
@ -111,6 +149,15 @@ indexed() {
|
||||||
mod_2 = 02;
|
mod_2 = 02;
|
||||||
else if (exp_2.val != 0 || reg_2 == 5)
|
else if (exp_2.val != 0 || reg_2 == 5)
|
||||||
mod_2 = 01;
|
mod_2 = 01;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (reg_2 & ~7)
|
||||||
|
serror("register error");
|
||||||
|
if (exp_2.typ != S_ABS || fitb(exp_2.val) == 0)
|
||||||
|
reg_2 |= 0200;
|
||||||
|
else if (exp_2.val != 0 || reg_2 == 6)
|
||||||
|
reg_2 |= 0100;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ebranch(opc,exp)
|
ebranch(opc,exp)
|
||||||
|
@ -245,7 +292,7 @@ adsize_exp(exp, relpc)
|
||||||
emit4((long)(exp.val));
|
emit4((long)(exp.val));
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
if (! fitw(exp.val)) {
|
if (! fitw(exp.val) && pass == PASS_3) {
|
||||||
warning("offset does not fit in 2 bytes; remove prefix");
|
warning("offset does not fit in 2 bytes; remove prefix");
|
||||||
}
|
}
|
||||||
#ifdef RELOCATION
|
#ifdef RELOCATION
|
||||||
|
|
Loading…
Add table
Reference in a new issue