aboutsummaryrefslogtreecommitdiffstats
path: root/code166.c
diff options
context:
space:
mode:
Diffstat (limited to 'code166.c')
-rw-r--r--code166.c1697
1 files changed, 1697 insertions, 0 deletions
diff --git a/code166.c b/code166.c
new file mode 100644
index 0000000..edf95af
--- /dev/null
+++ b/code166.c
@@ -0,0 +1,1697 @@
+/* code166.c */
+/*****************************************************************************/
+/* AS-Portierung */
+/* */
+/* AS-Codegenerator Siemens 80C16x */
+/* */
+/* Historie: 11.11.1996 (alaaf) Grundsteinlegung */
+/* 9. 5.1998 Registersymbole */
+/* 3. 1.1999 ChkPC angepasst */
+/* */
+/*****************************************************************************/
+
+#include "stdinc.h"
+#include <string.h>
+#include <ctype.h>
+
+#include "nls.h"
+#include "strutil.h"
+#include "bpemu.h"
+#include "asmdef.h"
+#include "asmsub.h"
+#include "asmpars.h"
+#include "codepseudo.h"
+#include "codevars.h"
+
+typedef struct
+ {
+ char *Name;
+ CPUVar MinCPU;
+ Word Code1,Code2;
+ } BaseOrder;
+
+typedef struct
+ {
+ char *Name;
+ Byte Code;
+ } SimpOrder;
+
+typedef struct
+ {
+ char *Name;
+ Byte Code;
+ } Condition;
+
+
+#define FixedOrderCount 10
+#define ConditionCount 20
+#define ALU2OrderCount 8
+#define ShiftOrderCount 5
+#define Bit2OrderCount 6
+#define LoopOrderCount 4
+#define DivOrderCount 4
+#define BJmpOrderCount 4
+#define MulOrderCount 3
+
+#define DPPCount 4
+static char *RegNames[6]={"DPP0","DPP1","DPP2","DPP3","CP","SP"};
+
+static CPUVar CPU80C166,CPU80C167;
+
+static BaseOrder *FixedOrders;
+static Condition *Conditions;
+static int TrueCond;
+static char **ALU2Orders;
+static SimpOrder *ShiftOrders;
+static SimpOrder *Bit2Orders;
+static SimpOrder *LoopOrders;
+static char **DivOrders;
+static char **BJmpOrders;
+static char **MulOrders;
+
+static SimpProc SaveInitProc;
+static LongInt DPPAssumes[DPPCount];
+static IntType MemInt,MemInt2;
+static Byte OpSize;
+
+static Boolean DPPChanged[DPPCount],N_DPPChanged[DPPCount];
+static Boolean SPChanged,CPChanged,N_SPChanged,N_CPChanged;
+
+static ShortInt ExtCounter;
+static enum {MemModeStd,MemModeNoCheck,MemModeZeroPage,MemModeFixedBank,MemModeFixedPage} MemMode;
+ /* normal EXTS Rn EXTP Rn EXTS nn EXTP nn */
+static Word MemPage;
+static Boolean ExtSFRs;
+
+/*-------------------------------------------------------------------------*/
+
+ static void AddFixed(char *NName, CPUVar NMin, Word NCode1, Word NCode2)
+BEGIN
+ if (InstrZ>=FixedOrderCount) exit(255);
+ FixedOrders[InstrZ].Name=NName;
+ FixedOrders[InstrZ].MinCPU=NMin;
+ FixedOrders[InstrZ].Code1=NCode1;
+ FixedOrders[InstrZ++].Code2=NCode2;
+END
+
+ static void AddShift(char *NName, Byte NCode)
+BEGIN
+ if (InstrZ>=ShiftOrderCount) exit(255);
+ ShiftOrders[InstrZ].Name=NName;
+ ShiftOrders[InstrZ++].Code=NCode;
+END
+
+ static void AddBit2(char *NName, Byte NCode)
+BEGIN
+ if (InstrZ>=Bit2OrderCount) exit(255);
+ Bit2Orders[InstrZ].Name=NName;
+ Bit2Orders[InstrZ++].Code=NCode;
+END
+
+ static void AddLoop(char *NName, Byte NCode)
+BEGIN
+ if (InstrZ>=LoopOrderCount) exit(255);
+ LoopOrders[InstrZ].Name=NName;
+ LoopOrders[InstrZ++].Code=NCode;
+END
+
+ static void AddCondition(char *NName, Byte NCode)
+BEGIN
+ if (InstrZ>=ConditionCount) exit(255);
+ Conditions[InstrZ].Name=NName;
+ Conditions[InstrZ++].Code=NCode;
+END
+
+ static void InitFields(void)
+BEGIN
+ FixedOrders=(BaseOrder *) malloc(FixedOrderCount*sizeof(BaseOrder)); InstrZ=0;
+ AddFixed("DISWDT",CPU80C166,0x5aa5,0xa5a5);
+ AddFixed("EINIT" ,CPU80C166,0x4ab5,0xb5b5);
+ AddFixed("IDLE" ,CPU80C166,0x7887,0x8787);
+ AddFixed("NOP" ,CPU80C166,0x00cc,0x0000);
+ AddFixed("PWRDN" ,CPU80C166,0x6897,0x9797);
+ AddFixed("RET" ,CPU80C166,0x00cb,0x0000);
+ AddFixed("RETI" ,CPU80C166,0x88fb,0x0000);
+ AddFixed("RETS" ,CPU80C166,0x00db,0x0000);
+ AddFixed("SRST" ,CPU80C166,0x48b7,0xb7b7);
+ AddFixed("SRVWDT",CPU80C166,0x58a7,0xa7a7);
+
+ Conditions=(Condition *) malloc(sizeof(Condition)*ConditionCount); InstrZ=0;
+ TrueCond=InstrZ; AddCondition("UC" ,0x0); AddCondition("Z" ,0x2);
+ AddCondition("NZ" ,0x3); AddCondition("V" ,0x4);
+ AddCondition("NV" ,0x5); AddCondition("N" ,0x6);
+ AddCondition("NN" ,0x7); AddCondition("C" ,0x8);
+ AddCondition("NC" ,0x9); AddCondition("EQ" ,0x2);
+ AddCondition("NE" ,0x3); AddCondition("ULT",0x8);
+ AddCondition("ULE",0xf); AddCondition("UGE",0x9);
+ AddCondition("UGT",0xe); AddCondition("SLT",0xc);
+ AddCondition("SLE",0xb); AddCondition("SGE",0xd);
+ AddCondition("SGT",0xa); AddCondition("NET",0x1);
+
+ ALU2Orders=(char **) malloc(sizeof(char *)*ALU2OrderCount); InstrZ=0;
+ ALU2Orders[InstrZ++]="ADD" ; ALU2Orders[InstrZ++]="ADDC";
+ ALU2Orders[InstrZ++]="SUB" ; ALU2Orders[InstrZ++]="SUBC";
+ ALU2Orders[InstrZ++]="CMP" ; ALU2Orders[InstrZ++]="XOR" ;
+ ALU2Orders[InstrZ++]="AND" ; ALU2Orders[InstrZ++]="OR" ;
+
+ ShiftOrders=(SimpOrder *) malloc(sizeof(SimpOrder)*ShiftOrderCount); InstrZ=0;
+ AddShift("ASHR",0xac); AddShift("ROL" ,0x0c);
+ AddShift("ROR" ,0x2c); AddShift("SHL" ,0x4c);
+ AddShift("SHR" ,0x6c);
+
+ Bit2Orders=(SimpOrder *) malloc(sizeof(SimpOrder)*Bit2OrderCount); InstrZ=0;
+ AddBit2("BAND",0x6a); AddBit2("BCMP" ,0x2a);
+ AddBit2("BMOV",0x4a); AddBit2("BMOVN",0x3a);
+ AddBit2("BOR" ,0x5a); AddBit2("BXOR" ,0x7a);
+
+ LoopOrders=(SimpOrder *) malloc(sizeof(SimpOrder)*LoopOrderCount); InstrZ=0;
+ AddLoop("CMPD1",0xa0); AddLoop("CMPD2",0xb0);
+ AddLoop("CMPI1",0x80); AddLoop("CMPI2",0x90);
+
+ DivOrders=(char **) malloc(sizeof(char *)*DivOrderCount); InstrZ=0;
+ DivOrders[InstrZ++]="DIV"; DivOrders[InstrZ++]="DIVU";
+ DivOrders[InstrZ++]="DIVL"; DivOrders[InstrZ++]="DIVLU";
+
+ BJmpOrders=(char **) malloc(sizeof(char *)*BJmpOrderCount); InstrZ=0;
+ BJmpOrders[InstrZ++]="JB"; BJmpOrders[InstrZ++]="JNB";
+ BJmpOrders[InstrZ++]="JBC"; BJmpOrders[InstrZ++]="JNBS";
+
+ MulOrders=(char **) malloc(sizeof(char *)*MulOrderCount); InstrZ=0;
+ MulOrders[InstrZ++]="MUL"; MulOrders[InstrZ++]="MULU";
+ MulOrders[InstrZ++]="PRIOR";
+END
+
+ static void DeinitFields(void)
+BEGIN
+ free(FixedOrders);
+ free(Conditions);
+ free(ALU2Orders);
+ free(ShiftOrders);
+ free(Bit2Orders);
+ free(LoopOrders);
+ free(DivOrders);
+ free(BJmpOrders);
+ free(MulOrders);
+END
+
+/*-------------------------------------------------------------------------*/
+
+#define ModNone (-1)
+#define ModReg 0
+#define MModReg (1 << ModReg)
+#define ModImm 1
+#define MModImm (1 << ModImm)
+#define ModIReg 2
+#define MModIReg (1 << ModIReg)
+#define ModPreDec 3
+#define MModPreDec (1 << ModPreDec)
+#define ModPostInc 4
+#define MModPostInc (1 << ModPostInc)
+#define ModIndex 5
+#define MModIndex (1 << ModIndex)
+#define ModAbs 6
+#define MModAbs (1 << ModAbs)
+#define ModMReg 7
+#define MModMReg (1 << ModMReg)
+#define ModLAbs 8
+#define MModLAbs (1 << ModLAbs)
+
+static Byte AdrMode;
+static Byte AdrVals[2];
+static ShortInt AdrType;
+
+ static Boolean IsReg(char *Asc, Byte *Erg, Boolean WordWise)
+BEGIN
+ Boolean err;
+ char *s;
+
+ if (FindRegDef(Asc,&s)) Asc=s;
+
+ if ((strlen(Asc)<2) OR (toupper(*Asc)!='R')) return False;
+ else if ((strlen(Asc)>2) AND (toupper(Asc[1])=='L') AND (NOT WordWise))
+ BEGIN
+ *Erg=ConstLongInt(Asc+2,&err); *Erg<<=1;
+ return ((err) AND (*Erg<=15));
+ END
+ else if ((strlen(Asc)>2) AND (toupper(Asc[1])=='H') AND (NOT WordWise))
+ BEGIN
+ *Erg=ConstLongInt(Asc+2,&err); *Erg<<=1; (*Erg)++;
+ return ((err) AND (*Erg<=15));
+ END
+ else
+ BEGIN
+ *Erg=ConstLongInt(Asc+1,&err);
+ return ((err) AND (*Erg<=15));
+ END
+END
+
+ static Boolean IsRegM1(char *Asc, Byte *Erg, Boolean WordWise)
+BEGIN
+ char tmp;
+ int l;
+ Boolean b;
+
+ if (*Asc!='\0')
+ BEGIN
+ tmp=Asc[l=(strlen(Asc)-1)]; Asc[l]='\0';
+ b=IsReg(Asc,Erg,WordWise);
+ Asc[l]=tmp;
+ return b;
+ END
+ else return False;
+END
+
+ static LongInt SFRStart(void)
+BEGIN
+ return (ExtSFRs) ? 0xf000 : 0xfe00;
+END
+
+ static LongInt SFREnd(void)
+BEGIN
+ return (ExtSFRs) ? 0xf1de : 0xffde;
+END
+
+ static Boolean CalcPage(LongInt *Adr, Boolean DoAnyway)
+BEGIN
+ int z;
+ Word Bank;
+
+ switch (MemMode)
+ BEGIN
+ case MemModeStd:
+ z=0;
+ while ((z<=3) AND (((*Adr) >> 14)!=DPPAssumes[z])) z++;
+ if (z>3)
+ BEGIN
+ WrError(110); (*Adr)&=0xffff; return (DoAnyway);
+ END
+ else
+ BEGIN
+ *Adr=((*Adr) & 0x3fff)+(z << 14);
+ if (DPPChanged[z]) WrXError(200,RegNames[z]);
+ return True;
+ END
+ case MemModeZeroPage:
+ (*Adr)&=0x3fff;
+ return True;
+ case MemModeFixedPage:
+ Bank=(*Adr) >> 14; (*Adr)&=0x3fff;
+ if (Bank!=MemPage)
+ BEGIN
+ WrError(110); return (DoAnyway);
+ END
+ else return True;
+ case MemModeNoCheck:
+ (*Adr)&=0xffff;
+ return True;
+ case MemModeFixedBank:
+ Bank=(*Adr) >> 16; (*Adr)&=0xffff;
+ if (Bank!=MemPage)
+ BEGIN
+ WrError(110); return (DoAnyway);
+ END
+ else return True;
+ default:
+ return False;
+ END
+END
+
+ static void DecideAbsolute(Boolean InCode, LongInt DispAcc, Word Mask, Boolean Dest)
+BEGIN
+#define DPPAdr 0xfe00
+#define SPAdr 0xfe12
+#define CPAdr 0xfe10
+
+ int z;
+
+ if (InCode)
+ if (((EProgCounter() >> 16)==(DispAcc >> 16)) AND ((Mask & MModAbs)!=0))
+ BEGIN
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc);
+ END
+ else
+ BEGIN
+ AdrType=ModLAbs; AdrCnt=2; AdrMode=DispAcc >> 16;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc);
+ END
+ else if (((Mask & MModMReg)!=0) AND (DispAcc>=SFRStart()) AND (DispAcc<=SFREnd()) AND ((DispAcc&1)==0))
+ BEGIN
+ AdrType=ModMReg; AdrCnt=1; AdrVals[0]=(DispAcc-SFRStart()) >> 1;
+ END
+ else switch (MemMode)
+ BEGIN
+ case MemModeStd:
+ z=0;
+ while ((z<=3) AND ((DispAcc >> 14)!=DPPAssumes[z])) z++;
+ if (z>3)
+ BEGIN
+ WrError(110); z=(DispAcc >> 14) & 3;
+ END
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=(Hi(DispAcc) & 0x3f)+(z << 6);
+ if (DPPChanged[z]) WrXError(200,RegNames[z]);
+ break;
+ case MemModeZeroPage:
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc) & 0x3f;
+ break;
+ case MemModeFixedPage:
+ if ((DispAcc >> 14)!=MemPage) WrError(110);
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc) & 0x3f;
+ break;
+ case MemModeNoCheck:
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc);
+ break;
+ case MemModeFixedBank:
+ if ((DispAcc >> 16)!=MemPage) WrError(110);
+ AdrType=ModAbs; AdrCnt=2;
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc);
+ break;
+ END
+
+ if ((AdrType!=ModNone) AND (Dest))
+ switch ((Word)DispAcc)
+ BEGIN
+ case SPAdr : N_SPChanged=True; break;
+ case CPAdr : N_CPChanged=True; break;
+ case DPPAdr :
+ case DPPAdr+1 : N_DPPChanged[0]=True; break;
+ case DPPAdr+2 :
+ case DPPAdr+3 : N_DPPChanged[1]=True; break;
+ case DPPAdr+4 :
+ case DPPAdr+5 : N_DPPChanged[2]=True; break;
+ case DPPAdr+6 :
+ case DPPAdr+7 : N_DPPChanged[3]=True; break;
+ END
+END
+
+ static void DecodeAdr(char *Asc, Word Mask, Boolean InCode, Boolean Dest)
+BEGIN
+ LongInt HDisp,DispAcc;
+ char *PPos,*MPos;
+ String Part;
+ Boolean OK,NegFlag,NNegFlag;
+ Byte HReg;
+
+ AdrType=ModNone; AdrCnt=0;
+
+ /* immediate ? */
+
+ if (*Asc=='#')
+ BEGIN
+ switch (OpSize)
+ BEGIN
+ case 0:
+ AdrVals[0]=EvalIntExpression(Asc+1,Int8,&OK);
+ AdrVals[1]=0;
+ break;
+ case 1:
+ HDisp=EvalIntExpression(Asc+1,Int16,&OK);
+ AdrVals[0]=Lo(HDisp); AdrVals[1]=Hi(HDisp);
+ break;
+ END
+ if (OK)
+ BEGIN
+ AdrType=ModImm; AdrCnt=OpSize+1;
+ END
+ END
+
+ /* Register ? */
+
+ else if (IsReg(Asc,&AdrMode,OpSize==1))
+ BEGIN
+ if ((Mask & MModReg)!=0) AdrType=ModReg;
+ else
+ BEGIN
+ AdrType=ModMReg; AdrVals[0]=0xf0+AdrMode; AdrCnt=1;
+ END
+ if (CPChanged) WrXError(200,RegNames[4]);
+ END
+
+ /* indirekt ? */
+
+ else if ((*Asc=='[') AND (Asc[strlen(Asc)-1]==']'))
+ BEGIN
+ strcpy(Asc,Asc+1); Asc[strlen(Asc)-1]='\0';
+
+ /* Predekrement ? */
+
+ if ((strlen(Asc)>2) AND (*Asc=='-') AND (IsReg(Asc+1,&AdrMode,True)))
+ AdrType=ModPreDec;
+
+ /* Postinkrement ? */
+
+ else if ((strlen(Asc)>2) AND (Asc[strlen(Asc)-1]=='+') AND (IsRegM1(Asc,&AdrMode,True)))
+ AdrType=ModPostInc;
+
+ /* indiziert ? */
+
+ else
+ BEGIN
+ NegFlag=False; DispAcc=0; AdrMode=0xff;
+ while (*Asc!='\0')
+ BEGIN
+ MPos=QuotPos(Asc,'-'); PPos=QuotPos(Asc,'+');
+ if (((MPos<PPos) OR (PPos==Nil)) AND (MPos!=Nil))
+ BEGIN
+ PPos=MPos; NNegFlag=True;
+ END
+ else NNegFlag=False;
+ if (PPos==Nil)
+ BEGIN
+ strmaxcpy(Part,Asc,255); *Asc='\0';
+ END
+ else
+ BEGIN
+ *PPos='\0'; strmaxcpy(Part,Asc,255); strcpy(Asc,PPos+1);
+ END
+ if (IsReg(Part,&HReg,True))
+ if ((NegFlag) OR (AdrMode!=0xff)) WrError(1350); else AdrMode=HReg;
+ else
+ BEGIN
+ if (*Part=='#') strcpy(Part,Part+1);
+ HDisp=EvalIntExpression(Part,Int32,&OK);
+ if (OK)
+ if (NegFlag) DispAcc-=HDisp; else DispAcc+=HDisp;
+ END
+ NegFlag=NNegFlag;
+ END
+ if (AdrMode==0xff) DecideAbsolute(InCode,DispAcc,Mask,Dest);
+ else if (DispAcc==0) AdrType=ModIReg;
+ else if (DispAcc>0xffff) WrError(1320);
+ else if (DispAcc<-0x8000l) WrError(1315);
+ else
+ BEGIN
+ AdrVals[0]=Lo(DispAcc); AdrVals[1]=Hi(DispAcc);
+ AdrType=ModIndex; AdrCnt=2;
+ END
+ END
+ END
+ else
+ BEGIN
+ DispAcc=EvalIntExpression(Asc,MemInt,&OK);
+ if (OK) DecideAbsolute(InCode,DispAcc,Mask,Dest);
+ END
+
+ if ((AdrType!=ModNone) AND (((1 << AdrType) & Mask)==0))
+ BEGIN
+ WrError(1350); AdrType=ModNone; AdrCnt=0;
+ END
+END
+
+ static int DecodeCondition(char *Name)
+BEGIN
+ int z;
+
+ NLS_UpString(Name);
+ for (z=0; z<ConditionCount; z++)
+ if (strcmp(Conditions[z].Name,Name)==0) break;
+ return z;
+END
+
+ static Boolean DecodeBitAddr(char *Asc, Word *Adr, Byte *Bit, Boolean MayBeOut)
+BEGIN
+ char *p;
+ Word LAdr;
+ Byte Reg;
+ Boolean OK;
+
+ p=QuotPos(Asc,'.');
+ if (p==Nil)
+ BEGIN
+ LAdr=EvalIntExpression(Asc,UInt16,&OK) & 0x1fff;
+ if (OK)
+ BEGIN
+ if ((NOT MayBeOut) AND ((LAdr >> 12)!=Ord(ExtSFRs)))
+ BEGIN
+ WrError(1335); return False;
+ END
+ *Adr=LAdr >> 4; *Bit=LAdr & 15;
+ if (NOT MayBeOut) *Adr=Lo(*Adr);
+ return True;
+ END
+ else return False;
+ END
+ else if (p==Asc)
+ BEGIN
+ WrError(1350); return False;
+ END
+ else
+ BEGIN
+ *p='\0';
+ if (IsReg(Asc,&Reg,True)) *Adr=0xf0+Reg;
+ else
+ BEGIN
+ FirstPassUnknown=False;
+ LAdr=EvalIntExpression(Asc,UInt16,&OK); if (NOT OK) return False;
+ if (FirstPassUnknown) LAdr=0xfd00;
+ if ((LAdr&1)==1)
+ BEGIN
+ WrError(1325); return False;
+ END
+ if ((LAdr>=0xfd00) AND (LAdr<=0xfdfe)) *Adr=(LAdr-0xfd00)/2;
+ else if ((LAdr>=0xff00) AND (LAdr<=0xffde))
+ BEGIN
+ if ((ExtSFRs) AND (NOT MayBeOut))
+ BEGIN
+ WrError(1335); return False;
+ END
+ *Adr=0x80+((LAdr-0xff00)/2);
+ END
+ else if ((LAdr>=0xf100) AND (LAdr<=0xf1de))
+ BEGIN
+ if ((NOT ExtSFRs) AND (NOT MayBeOut))
+ BEGIN
+ WrError(1335); return False;
+ END
+ *Adr=0x80+((LAdr-0xf100)/2);
+ if (MayBeOut) (*Adr)+=0x100;
+ END
+ else
+ BEGIN
+ WrError(1320); return False;
+ END
+ END
+
+ *Bit=EvalIntExpression(p+1,UInt4,&OK);
+ return OK;
+ END
+END
+
+ static Word WordVal(void)
+BEGIN
+ return AdrVals[0]+(((Word)AdrVals[1]) << 8);
+END
+
+ static Boolean DecodePref(char *Asc, Byte *Erg)
+BEGIN
+ Boolean OK;
+
+ if (*Asc!='#')
+ BEGIN
+ WrError(1350); return False;
+ END
+ strcpy(Asc,Asc+1);
+ FirstPassUnknown=False;
+ *Erg=EvalIntExpression(Asc,UInt3,&OK);
+ if (FirstPassUnknown) *Erg=1;
+ if (NOT OK) return False;
+ if (*Erg<1) WrError(1315);
+ else if (*Erg>4) WrError(1320);
+ else
+ BEGIN
+ (*Erg)--; return True;
+ END
+ return False;
+END
+
+/*-------------------------------------------------------------------------*/
+
+#define ASSUME166Count 4
+static ASSUMERec ASSUME166s[ASSUME166Count]=
+ {{"DPP0", DPPAssumes+0, 0, 15, -1},
+ {"DPP1", DPPAssumes+1, 0, 15, -1},
+ {"DPP2", DPPAssumes+2, 0, 15, -1},
+ {"DPP3", DPPAssumes+3, 0, 15, -1}};
+
+ static Boolean DecodePseudo(void)
+BEGIN
+ Word Adr;
+ Byte Bit;
+
+ if (Memo("ASSUME"))
+ BEGIN
+ CodeASSUME(ASSUME166s,ASSUME166Count);
+ return True;
+ END
+
+ if (Memo("BIT"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else if (DecodeBitAddr(ArgStr[1],&Adr,&Bit,True))
+ BEGIN
+ PushLocHandle(-1);
+ EnterIntSymbol(LabPart,(Adr << 4)+Bit,SegNone,False);
+ PopLocHandle();
+ sprintf(ListLine,"=%02xH.%1x",Adr,Bit);
+ END
+ return True;
+ END
+
+ if (Memo("REG"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else AddRegDef(LabPart,ArgStr[1]);
+ return True;
+ END
+
+ return False;
+END
+
+ static Boolean BMemo(char *Name)
+BEGIN
+ int l;
+
+ if (strncmp(OpPart,Name,l=strlen(Name))!=0) return False;
+ switch (OpPart[l])
+ BEGIN
+ case '\0':
+ OpSize=1; return True;
+ case 'B':
+ if (OpPart[l+1]=='\0')
+ BEGIN
+ OpSize=0; return True;
+ END
+ else return False;
+ default:
+ return False;
+ END
+END
+
+ static void MakeCode_166(void)
+BEGIN
+ int z,Cond;
+ Word AdrWord;
+ Byte AdrBank,HReg;
+ Byte BOfs1,BOfs2;
+ Word BAdr1,BAdr2;
+ LongInt AdrLong;
+ Boolean OK;
+
+ CodeLen=0; DontPrint=False; OpSize=1;
+
+ /* zu ignorierendes */
+
+ if (Memo("")) return;
+
+ /* Pseudoanweisungen */
+
+ if (DecodePseudo()) return;
+
+ if (DecodeIntelPseudo(False)) return;
+
+ /* Pipeline-Flags weiterschalten */
+
+ SPChanged=N_SPChanged; N_SPChanged=False;
+ CPChanged=N_CPChanged; N_CPChanged=False;
+ for (z=0; z<DPPCount; z++)
+ BEGIN
+ DPPChanged[z]=N_DPPChanged[z];
+ N_DPPChanged[z]=False;
+ END
+
+ /* Praefixe herunterzaehlen */
+
+ if (ExtCounter>=0)
+ if (--ExtCounter<0)
+ BEGIN
+ MemMode=MemModeStd;
+ ExtSFRs=False;
+ END
+
+ /* ohne Argument */
+
+ for (z=0; z<FixedOrderCount; z++)
+ if (Memo(FixedOrders[z].Name))
+ BEGIN
+ if (ArgCnt!=0) WrError(1110);
+ else
+ BEGIN
+ CodeLen=2;
+ BAsmCode[0]=Lo(FixedOrders[z].Code1);
+ BAsmCode[1]=Hi(FixedOrders[z].Code1);
+ if (FixedOrders[z].Code2!=0)
+ BEGIN
+ CodeLen=4;
+ BAsmCode[2]=Lo(FixedOrders[z].Code2);
+ BAsmCode[3]=Hi(FixedOrders[z].Code2);
+ if ((strncmp(OpPart,"RET",3)==0) AND (SPChanged)) WrXError(200,RegNames[5]);
+ END
+ END
+ return;
+ END
+
+ /* Datentransfer */
+
+ if (BMemo("MOV"))
+ BEGIN
+ Cond=1-OpSize;
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg+MModMReg+MModIReg+MModPreDec+MModPostInc+MModIndex+MModAbs,False,True);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg+MModImm+MModIReg+MModPostInc+MModIndex+MModAbs,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0xf0+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModImm:
+ if (WordVal()<=15)
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0xe0+Cond;
+ BAsmCode[1]=(WordVal() << 4)+HReg;
+ END
+ else
+ BEGIN
+ CodeLen=4; BAsmCode[0]=0xe6+Cond; BAsmCode[1]=HReg+0xf0;
+ memcpy(BAsmCode+2,AdrVals,2);
+ END
+ break;
+ case ModIReg:
+ CodeLen=2; BAsmCode[0]=0xa8+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModPostInc:
+ CodeLen=2; BAsmCode[0]=0x98+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModIndex:
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xd4+(Cond << 5);
+ BAsmCode[1]=(HReg << 4)+AdrMode; memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ case ModAbs:
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xf2+Cond;
+ BAsmCode[1]=0xf0+HReg; memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ END
+ break;
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0];
+ DecodeAdr(ArgStr[2],MModImm+MModMReg+((DPPAssumes[3]==3)?MModIReg:0)+MModAbs,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModImm:
+ CodeLen=4; BAsmCode[0]=0xe6+Cond;
+ memcpy(BAsmCode+2,AdrVals,2);
+ break;
+ case ModMReg: /* BAsmCode[1] sicher absolut darstellbar, da Rn vorher */
+ /* abgefangen wird! */
+ BAsmCode[0]=0xf6+Cond;
+ AdrLong=0xfe00+(((Word)BAsmCode[1]) << 1);
+ CalcPage(&AdrLong,True);
+ BAsmCode[2]=Lo(AdrLong);
+ BAsmCode[3]=Hi(AdrLong);
+ BAsmCode[1]=AdrVals[0];
+ CodeLen=4;
+ break;
+ case ModIReg:
+ CodeLen=4; BAsmCode[0]=0x94+(Cond << 5);
+ BAsmCode[2]=BAsmCode[1] << 1;
+ BAsmCode[3]=0xfe + (BAsmCode[1] >> 7); /* ANSI :-0 */
+ BAsmCode[1]=AdrMode;
+ break;
+ case ModAbs:
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xf2+Cond;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ END
+ break;
+ case ModIReg:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg+MModIReg+MModPostInc+MModAbs,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0xb8+Cond;
+ BAsmCode[1]=HReg+(AdrMode << 4);
+ break;
+ case ModIReg:
+ CodeLen=2; BAsmCode[0]=0xc8+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModPostInc:
+ CodeLen=2; BAsmCode[0]=0xe8+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModAbs:
+ CodeLen=2+AdrCnt; BAsmCode[0]=0x84+(Cond << 5);
+ BAsmCode[1]=HReg; memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ END
+ break;
+ case ModPreDec:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0x88+Cond;
+ BAsmCode[1]=HReg+(AdrMode << 4);
+ break;
+ END
+ break;
+ case ModPostInc:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModIReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModIReg:
+ CodeLen=2; BAsmCode[0]=0xd8+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ END
+ break;
+ case ModIndex:
+ BAsmCode[1]=AdrMode; memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ DecodeAdr(ArgStr[2],MModReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ BAsmCode[0]=0xc4+(Cond << 5);
+ CodeLen=4; BAsmCode[1]+=AdrMode << 4;
+ break;
+ END
+ break;
+ case ModAbs:
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ DecodeAdr(ArgStr[2],MModIReg+MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModIReg:
+ CodeLen=4; BAsmCode[0]=0x94+(Cond << 5);
+ BAsmCode[1]=AdrMode;
+ break;
+ case ModMReg:
+ CodeLen=4; BAsmCode[0]=0xf6+Cond;
+ BAsmCode[1]=AdrVals[0];
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ if ((Memo("MOVBS")) OR (Memo("MOVBZ")))
+ BEGIN
+ Cond=Ord(Memo("MOVBS")) << 4;
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ OpSize=1;
+ DecodeAdr(ArgStr[1],MModReg+MModMReg+MModAbs,False,True);
+ OpSize=0;
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ HReg=AdrMode; DecodeAdr(ArgStr[2],MModReg+MModAbs,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0xc0+Cond;
+ BAsmCode[1]=HReg+(AdrMode << 4);
+ break;
+ case ModAbs:
+ CodeLen=4; BAsmCode[0]=0xc2+Cond;
+ BAsmCode[1]=0xf0+HReg;
+ memcpy(BAsmCode+2,AdrVals,2);
+ break;
+ END
+ break;
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0];
+ DecodeAdr(ArgStr[2],MModAbs+MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModMReg: /* BAsmCode[1] sicher absolut darstellbar, da Rn vorher */
+ /* abgefangen wird! */
+ BAsmCode[0]=0xc5+Cond;
+ AdrLong=0xfe00+(((Word)BAsmCode[1]) << 1);
+ CalcPage(&AdrLong,True);
+ BAsmCode[2]=Lo(AdrLong);
+ BAsmCode[3]=Hi(AdrLong);
+ BAsmCode[1]=AdrVals[0];
+ CodeLen=4;
+ break;
+ case ModAbs:
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xc2+Cond;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ END
+ break;
+ case ModAbs:
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ DecodeAdr(ArgStr[2],MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ CodeLen=4; BAsmCode[0]=0xc5+Cond;
+ BAsmCode[1]=AdrVals[0];
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ if ((Memo("PUSH")) OR (Memo("POP")))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModMReg,False,Memo("POP"));
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ CodeLen=2; BAsmCode[0]=0xec+(Ord(Memo("POP")) << 4);
+ BAsmCode[1]=AdrVals[0];
+ if (SPChanged) WrXError(200,RegNames[5]);
+ break;
+ END
+ END
+ return;
+ END
+
+ if (Memo("SCXT"))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModMReg,False,True);
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0];
+ DecodeAdr(ArgStr[2],MModAbs+MModImm,False,False);
+ if (AdrType!=ModNone)
+ BEGIN
+ CodeLen=4; BAsmCode[0]=0xc6+(Ord(AdrType==ModAbs) << 4);
+ memcpy(BAsmCode+2,AdrVals,2);
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ /* Arithmetik */
+
+ for (z=0; z<ALU2OrderCount; z++)
+ if (BMemo(ALU2Orders[z]))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ Cond=(1-OpSize)+(z << 4);
+ DecodeAdr(ArgStr[1],MModReg+MModMReg+MModAbs,False,True);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg+MModIReg+MModPostInc+MModAbs+MModImm,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=Cond;
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ case ModIReg:
+ if (AdrMode>3) WrError(1350);
+ else
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x08+Cond;
+ BAsmCode[1]=(HReg << 4)+8+AdrMode;
+ END
+ break;
+ case ModPostInc:
+ if (AdrMode>3) WrError(1350);
+ else
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x08+Cond;
+ BAsmCode[1]=(HReg << 4)+12+AdrMode;
+ END
+ break;
+ case ModAbs:
+ CodeLen=4; BAsmCode[0]=0x02+Cond; BAsmCode[1]=0xf0+HReg;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ case ModImm:
+ if (WordVal()<=7)
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x08+Cond;
+ BAsmCode[1]=(HReg << 4)+AdrVals[0];
+ END
+ else
+ BEGIN
+ CodeLen=4; BAsmCode[0]=0x06+Cond; BAsmCode[1]=0xf0+HReg;
+ memcpy(BAsmCode+2,AdrVals,2);
+ END
+ break;
+ END
+ break;
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0];
+ DecodeAdr(ArgStr[2],MModAbs+MModMReg+MModImm,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModAbs:
+ CodeLen=4; BAsmCode[0]=0x02+Cond;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ break;
+ case ModMReg: /* BAsmCode[1] sicher absolut darstellbar, da Rn vorher */
+ /* abgefangen wird! */
+ BAsmCode[0]=0x04+Cond;
+ AdrLong=0xfe00+(((Word)BAsmCode[1]) << 1);
+ CalcPage(&AdrLong,True);
+ BAsmCode[2]=Lo(AdrLong);
+ BAsmCode[3]=Hi(AdrLong);
+ BAsmCode[1]=AdrVals[0];
+ CodeLen=4;
+ break;
+ case ModImm:
+ CodeLen=4; BAsmCode[0]=0x06+Cond;
+ memcpy(BAsmCode+2,AdrVals,2);
+ break;
+ END
+ break;
+ case ModAbs:
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ DecodeAdr(ArgStr[2],MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ CodeLen=4; BAsmCode[0]=0x04+Cond; BAsmCode[1]=AdrVals[0];
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ if ((BMemo("CPL")) OR (BMemo("NEG")))
+ BEGIN
+ Cond=0x81+((1-OpSize) << 5);
+ if (ArgCnt!=1) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg,False,True);
+ if (AdrType==ModReg)
+ BEGIN
+ CodeLen=2; BAsmCode[0]=Cond+(Ord(BMemo("CPL")) << 4);
+ BAsmCode[1]=AdrMode << 4;
+ END
+ END
+ return;
+ END
+
+ for (z=0; z<DivOrderCount; z++)
+ if (Memo(DivOrders[z]))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg,False,False);
+ if (AdrType==ModReg)
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x4b+(z << 4);
+ BAsmCode[1]=AdrMode*0x11;
+ END
+ END
+ return;
+ END
+
+ for (z=0; z<LoopOrderCount; z++)
+ if (Memo(LoopOrders[z].Name))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg,False,True);
+ if (AdrType==ModReg)
+ BEGIN
+ BAsmCode[1]=AdrMode;
+ DecodeAdr(ArgStr[2],MModAbs+MModImm,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModAbs:
+ CodeLen=4; BAsmCode[0]=LoopOrders[z].Code+2; BAsmCode[1]+=0xf0;
+ memcpy(BAsmCode+2,AdrVals,2);
+ break;
+ case ModImm:
+ if (WordVal()<16)
+ BEGIN
+ CodeLen=2; BAsmCode[0]=LoopOrders[z].Code;
+ BAsmCode[1]+=(WordVal() << 4);
+ END
+ else
+ BEGIN
+ CodeLen=4; BAsmCode[0]=LoopOrders[z].Code+6; BAsmCode[1]+=0xf0;
+ memcpy(BAsmCode+2,AdrVals,2);
+ END
+ break;
+ END
+ END
+ END
+ return;
+ END
+
+ for (z=0; z<MulOrderCount; z++)
+ if (Memo(MulOrders[z]))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0x0b+(z << 4);
+ BAsmCode[1]=(HReg << 4)+AdrMode;
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ /* Logik */
+
+ for (z=0; z<ShiftOrderCount; z++)
+ if (Memo(ShiftOrders[z].Name))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ OpSize=1;
+ DecodeAdr(ArgStr[1],MModReg,False,True);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ HReg=AdrMode;
+ DecodeAdr(ArgStr[2],MModReg+MModImm,False,True);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ BAsmCode[0]=ShiftOrders[z].Code; BAsmCode[1]=AdrMode+(HReg << 4);
+ CodeLen=2;
+ break;
+ case ModImm:
+ if (WordVal()>15) WrError(1320);
+ else
+ BEGIN
+ BAsmCode[0]=ShiftOrders[z].Code+0x10;
+ BAsmCode[1]=(WordVal() << 4)+HReg;
+ CodeLen=2;
+ END
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ for (z=0; z<Bit2OrderCount; z++)
+ if (Memo(Bit2Orders[z].Name))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ if (DecodeBitAddr(ArgStr[1],&BAdr1,&BOfs1,False))
+ if (DecodeBitAddr(ArgStr[2],&BAdr2,&BOfs2,False))
+ BEGIN
+ CodeLen=4; BAsmCode[0]=Bit2Orders[z].Code;
+ BAsmCode[1]=BAdr2; BAsmCode[2]=BAdr1;
+ BAsmCode[3]=(BOfs2 << 4)+BOfs1;
+ END
+ return;
+ END
+
+ if ((Memo("BCLR")) OR (Memo("BSET")))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else if (DecodeBitAddr(ArgStr[1],&BAdr1,&BOfs1,False))
+ BEGIN
+ CodeLen=2; BAsmCode[0]=(BOfs1 << 4)+0x0e + Ord(Memo("BSET")); /* ANSI :-0 */
+ BAsmCode[1]=BAdr1;
+ END
+ return;
+ END
+
+ if ((Memo("BFLDH")) OR (Memo("BFLDL")))
+ BEGIN
+ if (ArgCnt!=3) WrError(1110);
+ else
+ BEGIN
+ strmaxcat(ArgStr[1],".0",255);
+ if (DecodeBitAddr(ArgStr[1],&BAdr1,&BOfs1,False))
+ BEGIN
+ OpSize=0; BAsmCode[1]=BAdr1;
+ DecodeAdr(ArgStr[2],MModImm,False,False);
+ if (AdrType==ModImm)
+ BEGIN
+ BAsmCode[2]=AdrVals[0];
+ DecodeAdr(ArgStr[3],MModImm,False,False);
+ if (AdrType==ModImm)
+ BEGIN
+ BAsmCode[3]=AdrVals[0];
+ CodeLen=4; BAsmCode[0]=0x0a;
+ if (Memo("BFLDH"))
+ BEGIN
+ BAdr1=BAsmCode[2]; BAsmCode[2]=BAsmCode[3]; BAsmCode[3]=BAdr1;
+ BAsmCode[0]+=0x10;
+ END
+ END
+ END
+ END
+ END
+ return;
+ END
+
+ /*Spruenge */
+
+ if (Memo("JMP"))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ Cond=(ArgCnt==1) ? TrueCond : DecodeCondition(ArgStr[1]);
+ if (Cond>=ConditionCount) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[ArgCnt],MModAbs+MModLAbs+MModIReg,True,False);
+ switch (AdrType)
+ BEGIN
+ case ModLAbs:
+ if (Cond!=TrueCond) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xfa; BAsmCode[1]=AdrMode;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ END
+ break;
+ case ModAbs:
+ AdrLong=WordVal()-(EProgCounter()+2);
+ if ((AdrLong<=254) AND (AdrLong>=-256) AND ((AdrLong&1)==0))
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x0d+(Conditions[Cond].Code << 4);
+ BAsmCode[1]=(AdrLong/2)&0xff;
+ END
+ else
+ BEGIN
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xea;
+ BAsmCode[1]=Conditions[Cond].Code << 4;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ END
+ break;
+ case ModIReg:
+ CodeLen=2; BAsmCode[0]=0x9c;
+ BAsmCode[1]=(Conditions[Cond].Code << 4)+AdrMode;
+ break;
+ END
+ END
+ END
+ return;
+ END
+
+ if (Memo("CALL"))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ Cond=(ArgCnt==1) ? TrueCond : DecodeCondition(ArgStr[1]);
+ if (Cond>=ConditionCount) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[ArgCnt],MModAbs+MModLAbs+MModIReg,True,False);
+ switch (AdrType)
+ BEGIN
+ case ModLAbs:
+ if (Cond!=TrueCond) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xda; BAsmCode[1]=AdrMode;
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ END
+ break;
+ case ModAbs:
+ AdrLong=WordVal()-(EProgCounter()+2);
+ if ((AdrLong<=254) AND (AdrLong>=-256) AND ((AdrLong&1)==0) AND (Cond==TrueCond))
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0xbb;
+ BAsmCode[1]=(AdrLong/2) & 0xff;
+ END
+ else
+ BEGIN
+ CodeLen=2+AdrCnt; BAsmCode[0]=0xca;
+ BAsmCode[1]=0x00+(Conditions[Cond].Code << 4);
+ memcpy(BAsmCode+2,AdrVals,AdrCnt);
+ END
+ break;
+ case ModIReg:
+ CodeLen=2; BAsmCode[0]=0xab;
+ BAsmCode[1]=(Conditions[Cond].Code << 4)+AdrMode;
+ break;
+ END
+ END
+ END
+ return;
+ END
+
+ if (Memo("JMPR"))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ Cond=(ArgCnt==1) ? TrueCond : DecodeCondition(ArgStr[1]);
+ if (Cond>=ConditionCount) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ AdrLong=EvalIntExpression(ArgStr[ArgCnt],MemInt,&OK)-(EProgCounter()+2);
+ if (OK)
+ if ((AdrLong&1)==1) WrError(1375);
+ else if ((NOT SymbolQuestionable) AND ((AdrLong>254) OR (AdrLong<-256))) WrError(1370);
+ else
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0x0d+(Conditions[Cond].Code << 4);
+ BAsmCode[1]=(AdrLong/2) & 0xff;
+ END
+ END
+ END
+ return;
+ END
+
+ if (Memo("CALLR"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else
+ BEGIN
+ AdrLong=EvalIntExpression(ArgStr[ArgCnt],MemInt,&OK)-(EProgCounter()+2);
+ if (OK)
+ if ((AdrLong&1)==1) WrError(1375);
+ else if ((NOT SymbolQuestionable) AND ((AdrLong>254) OR (AdrLong<-256))) WrError(1370);
+ else
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0xbb;
+ BAsmCode[1]=(AdrLong/2) & 0xff;
+ END
+ END
+ return;
+ END
+
+ if ((Memo("JMPA")) OR (Memo("CALLA")))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ Cond=(ArgCnt==1) ? TrueCond : DecodeCondition(ArgStr[1]);
+ if (Cond>=ConditionCount) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ AdrLong=EvalIntExpression(ArgStr[ArgCnt],MemInt,&OK);
+ if (OK)
+ if ((AdrLong >> 16)!=(EProgCounter() >> 16)) WrError(1910);
+ else
+ BEGIN
+ CodeLen=4;
+ BAsmCode[0]=(Memo("JMPA")) ? 0xea : 0xca;
+ BAsmCode[1]=0x00+(Conditions[Cond].Code << 4);
+ BAsmCode[2]=Lo(AdrLong); BAsmCode[3]=Hi(AdrLong);
+ END
+ END
+ END
+ return;
+ END
+
+ if ((Memo("JMPS")) OR (Memo("CALLS")))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ if (ArgCnt==1)
+ BEGIN
+ AdrLong=EvalIntExpression(ArgStr[1],MemInt,&OK);
+ AdrWord=AdrLong & 0xffff; AdrBank=AdrLong >> 16;
+ END
+ else
+ BEGIN
+ AdrWord=EvalIntExpression(ArgStr[2],UInt16,&OK);
+ if (OK) AdrBank=EvalIntExpression(ArgStr[1],MemInt2,&OK); else AdrBank=0;
+ END
+ if (OK)
+ BEGIN
+ CodeLen=4;
+ BAsmCode[0]=(Memo("JMPS")) ? 0xfa : 0xda;
+ BAsmCode[1]=AdrBank;
+ BAsmCode[2]=Lo(AdrWord); BAsmCode[3]=Hi(AdrWord);
+ END
+ END
+ return;
+ END
+
+ if ((Memo("JMPI")) OR (Memo("CALLI")))
+ BEGIN
+ if ((ArgCnt!=1) AND (ArgCnt!=2)) WrError(1110);
+ else
+ BEGIN
+ Cond=(ArgCnt==1) ? TrueCond : DecodeCondition(ArgStr[1]);
+ if (Cond>=ConditionCount) WrXError(1360,ArgStr[1]);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[ArgCnt],MModIReg,True,False);
+ switch (AdrType)
+ BEGIN
+ case ModIReg:
+ CodeLen=2;
+ BAsmCode[0]=(Memo("JMPI")) ? 0x9c : 0xab;
+ BAsmCode[1]=AdrMode+(Conditions[Cond].Code << 4);
+ break;
+ END
+ END
+ END
+ return;
+ END
+
+ for (z=0; z<BJmpOrderCount; z++)
+ if (Memo(BJmpOrders[z]))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else if (DecodeBitAddr(ArgStr[1],&BAdr1,&BOfs1,False))
+ BEGIN
+ AdrLong=EvalIntExpression(ArgStr[2],MemInt,&OK)-(EProgCounter()+4);
+ if (OK)
+ if ((AdrLong&1)==1) WrError(1375);
+ else if ((NOT SymbolQuestionable) AND ((AdrLong<-256) OR (AdrLong>254))) WrError(1370);
+ else
+ BEGIN
+ CodeLen=4; BAsmCode[0]=0x8a+(z << 4);
+ BAsmCode[1]=BAdr1;
+ BAsmCode[2]=(AdrLong/2) & 0xff;
+ BAsmCode[3]=BOfs1 << 4;
+ END
+ END
+ return;
+ END
+
+ if (Memo("PCALL"))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0];
+ DecodeAdr(ArgStr[2],MModAbs,True,False);
+ switch (AdrType)
+ BEGIN
+ case ModAbs:
+ CodeLen=4; BAsmCode[0]=0xe2; memcpy(BAsmCode+2,AdrVals,2);
+ break;
+ END
+ break;
+ END
+ END
+ return;
+ END
+
+ if (Memo("RETP"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else
+ BEGIN
+ DecodeAdr(ArgStr[1],MModMReg,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModMReg:
+ BAsmCode[1]=AdrVals[0]; BAsmCode[0]=0xeb; CodeLen=2;
+ if (SPChanged) WrXError(200,RegNames[5]);
+ break;
+ END
+ END
+ return;
+ END
+
+ if (Memo("TRAP"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else if (*ArgStr[1]!='#') WrError(1350);
+ else
+ BEGIN
+ BAsmCode[1]=EvalIntExpression(ArgStr[1]+1,UInt7,&OK) << 1;
+ if (OK)
+ BEGIN
+ BAsmCode[0]=0x9b; CodeLen=2;
+ END
+ END
+ return;
+ END
+
+ /* spezielle Steuerbefehle */
+
+ if (Memo("ATOMIC"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else if (MomCPU<CPU80C167) WrError(1500);
+ else if (DecodePref(ArgStr[1],&HReg))
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0xd1; BAsmCode[1]=HReg << 4;
+ END
+ return;
+ END
+
+ if (Memo("EXTR"))
+ BEGIN
+ if (ArgCnt!=1) WrError(1110);
+ else if (MomCPU<CPU80C167) WrError(1500);
+ else if (DecodePref(ArgStr[1],&HReg))
+ BEGIN
+ CodeLen=2; BAsmCode[0]=0xd1; BAsmCode[1]=0x80+(HReg << 4);
+ ExtCounter=HReg+1; ExtSFRs=True;
+ END
+ return;
+ END
+
+ if ((Memo("EXTP")) OR (Memo("EXTPR")))
+ BEGIN
+ if (ArgCnt!=2) WrError(1110);
+ else if (MomCPU<CPU80C167) WrError(1500);
+ else if (DecodePref(ArgStr[2],&HReg))
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg+MModImm,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0xdc; BAsmCode[1]=0x40+(HReg << 4)+AdrMode;
+ if (Memo("EXTPR")) BAsmCode[1]+=0x80;
+ ExtCounter=HReg+1; MemMode=MemModeZeroPage;
+ break;
+ case ModImm:
+ CodeLen=4; BAsmCode[0]=0xd7; BAsmCode[1]=0x40+(HReg << 4);
+ if (Memo("EXTPR")) BAsmCode[1]+=0x80;
+ BAsmCode[2]=WordVal() & 0xff; BAsmCode[3]=(WordVal() >> 8) & 3;
+ ExtCounter=HReg+1; MemMode=MemModeFixedPage; MemPage=WordVal() & 0x3ff;
+ break;
+ END
+ END
+ return;
+ END
+
+ if ((Memo("EXTS")) OR (Memo("EXTSR")))
+ BEGIN
+ OpSize=0;
+ if (ArgCnt!=2) WrError(1110);
+ else if (MomCPU<CPU80C167) WrError(1500);
+ else if (DecodePref(ArgStr[2],&HReg))
+ BEGIN
+ DecodeAdr(ArgStr[1],MModReg+MModImm,False,False);
+ switch (AdrType)
+ BEGIN
+ case ModReg:
+ CodeLen=2; BAsmCode[0]=0xdc; BAsmCode[1]=0x00+(HReg << 4)+AdrMode;
+ if (Memo("EXTSR")) BAsmCode[1]+=0x80;
+ ExtCounter=HReg+1; MemMode=MemModeNoCheck;
+ break;
+ case ModImm:
+ CodeLen=4; BAsmCode[0]=0xd7; BAsmCode[1]=0x00+(HReg << 4);
+ if (Memo("EXTSR")) BAsmCode[1]+=0x80;
+ BAsmCode[2]=AdrVals[0]; BAsmCode[3]=0;
+ ExtCounter=HReg+1; MemMode=MemModeFixedBank; MemPage=AdrVals[0];
+ break;
+ END
+ END
+ return;
+ END
+
+ WrXError(1200,OpPart);
+END
+
+ static void InitCode_166(void)
+BEGIN
+ int z;
+
+ SaveInitProc();
+ for (z=0; z<DPPCount; z++)
+ BEGIN
+ DPPAssumes[z]=z; N_DPPChanged[z]=False;
+ END
+ N_CPChanged=False; N_SPChanged=False;
+
+ MemMode=MemModeStd; ExtSFRs=False; ExtCounter=(-1);
+END
+
+ static Boolean IsDef_166(void)
+BEGIN
+ return (Memo("BIT")) OR (Memo("REG"));
+END
+
+ static void SwitchFrom_166(void)
+BEGIN
+ DeinitFields();
+END
+
+ static void SwitchTo_166(void)
+BEGIN
+ Byte z;
+
+ TurnWords=False; ConstMode=ConstModeIntel; SetIsOccupied=False;
+ OpSize=1;
+
+ PCSymbol="$"; HeaderID=0x4c; NOPCode=0xcc00;
+ DivideChars=","; HasAttrs=False;
+
+ ValidSegs=(1<<SegCode);
+ Grans[SegCode]=1; ListGrans[SegCode]=1; SegInits[SegCode]=0;
+
+ MakeCode=MakeCode_166; IsDef=IsDef_166;
+ SwitchFrom=SwitchFrom_166;
+
+ if (MomCPU==CPU80C166)
+ BEGIN
+ MemInt=UInt18; MemInt2=UInt2; ASSUME166s[0].Max=15;
+ SegLimits[SegCode] = 0x3ffffl;
+ END
+ else
+ BEGIN
+ MemInt=UInt24; MemInt2=UInt8; ASSUME166s[0].Max=1023;
+ SegLimits[SegCode] = 0xffffffl;
+ END
+ for (z=1; z<4; z++) ASSUME166s[z].Max=ASSUME166s[0].Max;
+
+ InitFields();
+END
+
+ void code166_init(void)
+BEGIN
+ CPU80C166=AddCPU("80C166",SwitchTo_166);
+ CPU80C167=AddCPU("80C167",SwitchTo_166);
+
+ SaveInitProc=InitPassProc; InitPassProc=InitCode_166;
+END