home *** CD-ROM | disk | FTP | other *** search
- #include <stdio.h>
- #include "defs.h"
- #include "externs.h"
-
- /* class 1 machine operations processor - 1 byte, no operand field */
-
- class1(int *ip)
- {
- check_eol(ip);
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- println();
- }
- loccnt++;
- }
-
- /* class 2 machine operations processor - 2 byte, relative addressing */
-
- class2(int *ip)
- {
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- while (isspace(prlnbuf[++(*ip)]));
- if (evaluate(ip, ';')) {
- value -= ((loccnt + 2) + (page << 13));
- if (value >= -128 && value < 128) {
- loadv(loccnt + 1, value, 1);
- println();
- } else
- error("Invalid branch address!");
- }
- }
- loccnt += 2;
- }
-
- /* class 3 machine operations processor - 2 byte, inherent addressing */
-
- class3(int *ip)
- {
- check_eol(ip);
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt+1, optype, 1);
- println();
- }
- loccnt += 2;
- }
-
- /* class 4 machine operations processor - various addressing modes */
-
- class4(int *ip)
- {
- char c;
- int code;
- int flag;
- int i;
- int temp;
-
- while (isspace(c = prlnbuf[++(*ip)]));
- switch(c) {
- case '\0':
- case ';':
- error("Operand field missing!");
- return;
- case 'A':
- case 'a':
- if ((c = prlnbuf[*ip + 1]) == ' ' || c == 0 || c == '\t') {
- flag = ACC;
- break;
- }
- default:
- switch(c = prlnbuf[*ip]) {
- case '#':
- flag = IMM;
- ++(*ip);
- break;
- case '<':
- flag = ZP | ZP_X | ZP_Y;
- ++(*ip);
- break;
- case '[':
- flag = ABS_IND | ABS_IND_X | ZP_IND | ZP_IND_X | ZP_IND_Y;
- ++(*ip);
- break;
- default:
- flag = ABS | ABS_X | ABS_Y;
- }
- if (!evaluate(ip, 0))
- return;
-
- /* -- range checking. */
-
- if (flag & (ZP | ZP_X | ZP_Y | ZP_IND | ZP_IND_X | ZP_IND_Y) & opflg) {
- if ((value & 0xFFFFFF00) && ((value & 0xFFFFFF00) != 0x2000)) {
- error("Zero page index out of range!");
- return;
- }
- } else if (flag & (IMM) & opflg) {
- if ((value > 0xFF) && (value < 0xFFFFFF00)) {
- error("Immediate value out of range!");
- return;
- }
- } else if (flag & (ABS | ABS_X | ABS_Y | ABS_IND | ABS_IND_X) & opflg) {
- if (value & 0xFFFF0000) {
- error("Address out of range!");
- return;
- }
- }
- code = 0;
- while (c = prlnbuf[(*ip)++]) {
- if (c == ';')
- break;
- if (!isspace(c))
- code *= 8;
- switch(c) {
- case ']': /* ] = 4 */
- ++code;
- case ',': /* , = 3 */
- ++code;
- case 'X': /* X = 2 */
- case 'x':
- ++code;
- case 'Y': /* Y = 1 */
- case 'y':
- ++code;
- case ' ':
- case '\t':
- break;
- default:
- flag = 0;
- }
- }
- switch(code) {
- case 0: /* no termination characters */
- flag &= (ABS | ZP | IMM);
- break;
- case 4: /* termination = ] */
- flag &= (ZP_IND | ABS_IND);
- break;
- case 25: /* termination = ,Y */
- flag &= (ABS_Y | ZP_Y);
- break;
- case 26: /* termination = ,X */
- flag &= (ABS_X | ZP_X);
- break;
- case 212: /* termination = ,X] */
- flag &= (ZP_IND_X | ABS_IND_X);
- break;
- case 281: /* termination = ],Y */
- flag &= ZP_IND_Y;
- break;
- default:
- flag = 0;
- }
- }
- opflg &= flag;
-
- i = 0;
- temp = opflg;
- while (temp >>= 1)
- i++;
- opval += opvaltab[optype][i];
-
- switch(opflg) {
- case ACC: /* single byte - class 4 */
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- println();
- }
- loccnt++;
- return;
- case IMM: /* double byte - class 4 */
- case ZP:
- case ZP_X:
- case ZP_Y:
- case ZP_IND:
- case ZP_IND_X:
- case ZP_IND_Y:
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt+1, value & 0xFF, 1);
- println();
- }
- loccnt += 2;
- return;
- case ABS: /* triple byte - class 4 */
- case ABS_X:
- case ABS_Y:
- case ABS_IND:
- case ABS_IND_X:
- if (pass == LAST_PASS) {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt+1, value, 1);
- loadv(loccnt+2, value >> 8, 2);
- println();
- }
- loccnt += 3;
- return;
- default:
- error("Invalid addressing mode!");
- return;
- }
- }
-
- /* class 5 machine operations processor - 3 bytes, zp/relative addressing */
-
- class5(int *ip)
- {
- char c;
- int zp;
-
- while (isspace(c = prlnbuf[(*ip)++]));
- if (c != '<') {
- error("Invalid addressing mode!");
- return;
- }
- if (!evaluate(ip, ','))
- return;
- zp = value;
- if (!evaluate(ip, ';'))
- return;
- if (pass == LAST_PASS) {
- if ((zp & 0xFFFFFF00) && ((zp & 0xFFFFFF00) != 0x2000))
- error("Zero page index out of range!");
- else {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt + 1, zp & 0xFF, 1);
- value -= ((loccnt + 3) + (page << 13));
- if (value >= -128 && value < 128) {
- loadv(loccnt + 2, value, 2);
- println();
- } else
- error("Invalid branch address!");
- }
- }
- loccnt += 3;
- }
-
- /* class 6 machine operations processor - 7 bytes, src/dest/length */
-
- class6(int *ip)
- {
- char c;
- int i, j, temp[3];
-
- for (i = 0; i < 3; i++) {
- if (!evaluate(ip, 0))
- return;
- temp[i] = value;
- if (i == 2)
- check_eol(ip);
- else {
- if (prlnbuf[(*ip)++] != ',') {
- error("Syntax error!");
- return;
- }
- }
- }
- if (pass == LAST_PASS) {
- for (i = 0; i < 3; i++) {
- if (temp[i] & 0xFFFF0000) {
- error("Number out of range!");
- loccnt += 7;
- return;
- }
- }
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt + 1, temp[0] & 0xFF, 1);
- loadv(loccnt + 2, (temp[0] & 0xFF00) >> 8, 2);
- println(); clearln();
- loadlc(loccnt + 3, 0);
- loadv(loccnt + 3, temp[1] & 0xFF, 0);
- loadv(loccnt + 4, (temp[1] & 0xFF00) >> 8, 1);
- loadv(loccnt + 5, temp[2] & 0xFF, 2);
- println(); clearln();
- loadlc(loccnt + 6, 0);
- loadv(loccnt + 6, (temp[2] & 0xFF00) >> 8, 0);
- println();
- }
- loccnt += 7;
- }
-
- /* class 7 machine operations processor - TST instruction */
-
- class7(int *ip)
- {
- char c;
- int code, imm;
-
- while (isspace(c = prlnbuf[(*ip)++]));
- if (c != '#') {
- error("Invalid addressing mode!");
- return;
- }
- if (!evaluate(ip, ','))
- return;
- imm = value;
- if (prlnbuf[*ip] != '<')
- opval = 0x93;
- else {
- (*ip)++;
- opval = 0x83;
- }
- if (!evaluate(ip, 0))
- return;
- code = 0;
- while (c = prlnbuf[(*ip)++]) {
- if (c == ';')
- break;
- if (!isspace(c))
- code *= 4;
- switch(c) {
- case ',': /* , = 2 */
- code++;
- case 'X': /* X = 1 */
- case 'x':
- code++;
- break;
- case ' ':
- case '\t':
- break;
- }
- }
- switch (code) {
- case 0:
- break;
- case 9:
- opval += 0x20;
- break;
- default:
- error("Syntax error!");
- return;
- }
- switch (opval & 0x93) {
- case 0x83:
- if (pass == LAST_PASS) {
- if ((value & 0xFFFFFF00) && ((value & 0xFFFFFF00) != 0x2000))
- error("Zero page index out of range!");
- else if (imm & 0xFFFFFF00)
- error("Immediate value out of range!");
- else {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt + 1, imm, 1);
- loadv(loccnt + 2, value & 0xFF, 2);
- println();
- }
- }
- loccnt += 3;
- break;
- case 0x93:
- if (pass == LAST_PASS) {
- if (value & 0xFFFF0000)
- error("Address out of range!");
- else if (imm & 0xFFFFFF00)
- error("Immediate value out of range!");
- else {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt + 1, imm, 1);
- loadv(loccnt + 2, value & 0xFF, 2);
- println(); clearln();
- loadlc(loccnt + 3, 0);
- loadv(loccnt + 3, (value & 0xFF00) >> 8, 0);
- println();
- }
- }
- loccnt += 4;
- break;
- }
- }
-
- /* class 8 machine operations processor - TAM/TMA instruction */
-
- class8(int *ip)
- {
- char c;
-
- while (isspace(c = prlnbuf[(*ip)++]));
- if (c != '#') {
- error("Invalid addressing mode!");
- return;
- }
- if (!evaluate(ip, ';'))
- return;
- if (pass == LAST_PASS) {
- if (value & 0xFFFFFFF8)
- error("Page index out of range!");
- else {
- loadlc(loccnt, 0);
- loadv(loccnt, opval, 0);
- loadv(loccnt + 1, (1 << value), 1);
- println();
- }
- }
- loccnt += 2;
- }
-
-