/* Generator is (c) James Ponder, 1997-2001 http://www.squish.net/generator/ */ #include #include #include #include #include #include "generator.h" #include "tab68k.c" #define BUFLEN 1024 #define FNAME_CPUDEF "def68k.def" #define FNAME_OUTIIBS "def68k-iibs.h" #define FNAME_OUTFUNCS "def68k-funcs.h" #define FNAME_OUTPROTO "def68k-proto.h" typedef enum { bit0, bit1, bitz, bite, bitE, bitf, bitF, biti, bitn, bitN, bitc, bitv } t_bit; /* file-scope global variables */ static int total = 0; static int clocks_movetable[]; /* pre-declaration */ /* private functions for forward references */ void procline(char *line, int lineno, FILE *outiibs, FILE *outfuncs, FILE *outproto); int clocks_ea(t_datatype type); int clocks_eacalc(t_datatype type, t_size size); int clocks_6or8(t_datatype type); int clocks_typetoindex(t_datatype type); /* program entry routine */ int main(int argc, char *argv[]) { FILE *input, *outiibs, *outfuncs, *outproto; char buf[BUFLEN], *p; int lineno = 0; (void)argc; (void)argv; /* open output files and write headers */ if ((outiibs = fopen(FNAME_OUTIIBS, "w")) == NULL) { perror("fopen outiibs"); exit(1); } fprintf(outiibs, "/* automatically generated by def68k.c */\n\n"); fprintf(outiibs, "t_iib iibs[] = {\n"); fprintf(outiibs, " /* mask, bits, mnemonic, { priv, endblk, zero, "); fprintf(outiibs, "used, set },\n"); fprintf(outiibs, " size, stype, dtype, sbitpos, dbitpos, immvalue, "); fprintf(outiibs, "cc, funcnum */\n"); if ((outfuncs = fopen(FNAME_OUTFUNCS, "w")) == NULL) { perror("fopen outfuncs"); exit(1); } fprintf(outfuncs, "/* automatically generated by def68k.c */\n\n"); fprintf(outfuncs, "void (*cpu68k_funcindex[])(t_ipc *ipc) = {\n"); fprintf(outfuncs, " /* function */\n"); if ((outproto = fopen(FNAME_OUTPROTO, "w")) == NULL) { perror("fopen outproto"); exit(1); } fprintf(outproto, "/* automatically generated by def68k.c */\n\n"); /* open input file */ if ((input = fopen(FNAME_CPUDEF, "r")) == NULL) { perror("fopen input"); exit(1); } /* loop until end of file */ printf("Writing CPU definitions... "); fflush(stdout); while (!feof(input)) { /* use unix line numbering from 1 */ lineno++; /* read a line */ if (ferror(input)) { break; } if (fgets(buf, BUFLEN, input) == NULL) { break; /* huh? why does this cause fgets to say 'Unknown error'?! */ perror("fgets"); exit(1); } /* remove newline */ buf[strlen(buf)-1] = '\0'; /* remove comment */ if ((p = strchr(buf, ';')) != NULL) { *p = '\0'; } /* remove leading spaces */ p = buf; while (*p == ' ') p++; /* blank line? */ if (!*p) continue; /* process line */ procline(buf, lineno, outiibs, outfuncs, outproto); } /* close input */ if (fclose(input)) { perror("fclose input"); exit(1); } /* output footer */ fprintf(outiibs, " { 0, 0, 0, { 0, 0, 0, 0, 0 }, " "0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }\n"); fprintf(outiibs, "};\n"); fprintf(outiibs, "int iibs_num = %d;\n", total); fprintf(outfuncs, "};\n"); /* close outputs */ if (fclose(outiibs)) { perror("fclose outiibs"); exit(1); } if (fclose(outfuncs)) { perror("fclose outfuncs"); exit(1); } if (fclose(outproto)) { perror("fclose outproto"); exit(1); } printf("done.\n"); fflush(stdout); return(0); } /* process a line */ void procline(char *line, int lineno, FILE *outiibs, FILE *outfuncs, FILE *outproto) { int i; char *p; t_bit bit = bit0, lastbit = bit0; int start[16] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 }; int num[16] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 }; char mnemonic[16], *m; int setting; int clocks; /* parameters to fill in about instruction */ int mnemonic_num; uint16 mask = 0, bits = 0; /* see struct t_iib for details on */ int priv = 0, endblk = 0; /* these variables */ int imm_notzero = 0; int used = 0, set = 0; t_size isize = sz_none; int expand_s_immsize = 0, expand_s_ea_e = 0; int expand_d_ea_e = 0, expand_d_ea_f = 0; t_datatype dtype = dt_Ill; t_datatype stype = dt_Ill; int e[16] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 }; int f[16] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 }; int immvalue = 0; int sbitpos = 0, dbitpos = 0; p = line; /* bitpattern */ for (i = 15; i >= 0; i--) { while (*p == ' ') p++; switch(*p) { case '0': bit = bit0; mask |= 1<