diff --git a/xa/src/xat.c b/xa/src/xat.c index 681570c..7ec226c 100644 --- a/xa/src/xat.c +++ b/xa/src/xat.c @@ -704,8 +704,14 @@ fprintf(stderr, "E_NODEF pass1 xat.c\n"); } else sy=4+nk; /* absolute or zero page */ - /* length counter set to maximum length + 1 */ - bl=Maxbyt+1; + /* length counter set to maximum length + 1 */ + if (w65816 || (t[l-1]=='@' || t[l-1] == '!')) { + /* for 65816 allow addressing modes up to 4 byte overall length */ + bl=Maxbyt+1; + } else { + /* for other modes only check for addressing modes up to 3 byte overall length */ + bl=Maxbyt; + } /* find best fit for length of this operand */ while(--bl) @@ -1375,9 +1381,19 @@ fprintf(stderr, "Kdsb E_DSB %i\n", j); } } } - - bl=Maxbyt+1; + /* set bl to maximum overall length +1 as while() below starts with decrementing it */ + if (w65816 || (t[*ll-1]=='@' || t[*ll-1] == '!')) { + /* for 65816 allow addressing modes up to 4 byte overall length */ + bl=Maxbyt+1; + } else { + /* for other modes only check for addressing modes up to 3 byte overall length */ + bl=Maxbyt; + } + +#ifdef DEBUG_AM + printf("--- trying to find am using: (max+1) bl=%d, sy=%d\n", bl, sy); +#endif while(--bl) { if((am=at[sy][bl-1])>=0) @@ -1415,8 +1431,8 @@ fprintf(stderr, "Kdsb E_DSB %i\n", j); { #ifdef DEBUG_AM fprintf(stderr, -"b4: pc= %d, am = %d and vv[0] = %d, optimize = %d, bitmask = %d\n", - pc[segment], am, vv[0], fl, (vv[0]&0xffff00)); +"b4: pc= %d, am = %d and vv[0] = %d, optimize = %d, bitmask = %u, er=%d\n", + pc[segment], am, vv[0], fl, (vv[0]&0xffff00), er); #endif /* terrible KLUDGE!!!! OH NOES!!!1! @@ -1455,15 +1471,21 @@ fprintf(stderr, else { bl=le[am]; + if ((am != 11 && am != 16) && (vv[0] > 255 || vv[0] < -256) && bl == 2) { + er = E_OVERFLOW; + } else + if ((am != 11 && am != 16) && (vv[0] > 65535 || vv[0] < -65536) && (bl == 2 || bl == 3)) { + er = E_OVERFLOW; + } else if( ((ct[n][am]&0x400) && memode) || ((ct[n][am]&0x800) && xmode)) { bl++; - } + } *ll=bl; } #ifdef DEBUG_AM -fprintf(stderr, "byte length is now %d\n", bl); +fprintf(stderr, "byte length is now %d, am=%d, er=%d\n", bl, am, er); #endif if(!er) diff --git a/xa/tests/neg_offset/Makefile b/xa/tests/neg_offset/Makefile index 86ae8c3..7c4bc33 100644 --- a/xa/tests/neg_offset/Makefile +++ b/xa/tests/neg_offset/Makefile @@ -1,12 +1,33 @@ -default: test1 test2 +default: test1 test2 test3 test4 test5 test6 test7 test8 test1: ../../xa -R -LLIB6502 test1.s -o test1.o - ../hextool -cmp=ok < test1.o + ../hextool -cmp=ok1 < test1.o test2: ../../xa -R -LLIB6502 test2.s -o test2.o - ../hextool -cmp=ok < test2.o + ../hextool -cmp=ok2 < test2.o + +test3: + ../../xa -R -LLIB6502 test3.s -o test3.o + ../hextool -cmp=ok3 < test3.o + +test4: + ../../xa -R -LLIB6502 test4.s -o test4.o + ../hextool -cmp=ok4 < test4.o + +test5: + ../../xa -R -LLIB6502 test5.s -o test5.o + ../hextool -cmp=ok5 < test5.o + +test6: + ../../xa -R -LLIB6502 test6.s -o test6.o || exit 0 && exit 1 + +test7: + ../../xa -R -LLIB6502 test7.s -o test7.o || exit 0 && exit 1 + +test8: + ../../xa -R -LLIB6502 test8.s -o test8.o || exit 0 && exit 1 clean: rm -f *.o diff --git a/xa/tests/neg_offset/a.o65 b/xa/tests/neg_offset/a.o65 new file mode 100644 index 0000000..0bea5d1 Binary files /dev/null and b/xa/tests/neg_offset/a.o65 differ diff --git a/xa/tests/neg_offset/ok1 b/xa/tests/neg_offset/ok1 new file mode 100644 index 0000000..9f821a0 Binary files /dev/null and b/xa/tests/neg_offset/ok1 differ diff --git a/xa/tests/neg_offset/ok2 b/xa/tests/neg_offset/ok2 new file mode 100644 index 0000000..9f821a0 Binary files /dev/null and b/xa/tests/neg_offset/ok2 differ diff --git a/xa/tests/neg_offset/ok3 b/xa/tests/neg_offset/ok3 new file mode 100644 index 0000000..3663025 Binary files /dev/null and b/xa/tests/neg_offset/ok3 differ diff --git a/xa/tests/neg_offset/ok4 b/xa/tests/neg_offset/ok4 new file mode 100644 index 0000000..40a1a4a Binary files /dev/null and b/xa/tests/neg_offset/ok4 differ diff --git a/xa/tests/neg_offset/ok5 b/xa/tests/neg_offset/ok5 new file mode 100644 index 0000000..0bea5d1 Binary files /dev/null and b/xa/tests/neg_offset/ok5 differ diff --git a/xa/tests/neg_offset/test3.s b/xa/tests/neg_offset/test3.s new file mode 100644 index 0000000..29a90cd --- /dev/null +++ b/xa/tests/neg_offset/test3.s @@ -0,0 +1,6 @@ + + .text + + jsr LIB6502-255 + + diff --git a/xa/tests/neg_offset/test4.s b/xa/tests/neg_offset/test4.s new file mode 100644 index 0000000..1358dfb --- /dev/null +++ b/xa/tests/neg_offset/test4.s @@ -0,0 +1,6 @@ + + .text + + jsr LIB6502+256 + + diff --git a/xa/tests/neg_offset/test5.s b/xa/tests/neg_offset/test5.s new file mode 100644 index 0000000..41d582a --- /dev/null +++ b/xa/tests/neg_offset/test5.s @@ -0,0 +1,6 @@ + + .text + + jsr LIB6502-256 + + diff --git a/xa/tests/neg_offset/test6.s b/xa/tests/neg_offset/test6.s new file mode 100644 index 0000000..aa2b73f --- /dev/null +++ b/xa/tests/neg_offset/test6.s @@ -0,0 +1,6 @@ + + .text + + jsr LIB6502-65537 + + diff --git a/xa/tests/neg_offset/test7.s b/xa/tests/neg_offset/test7.s new file mode 100644 index 0000000..b3ea18e --- /dev/null +++ b/xa/tests/neg_offset/test7.s @@ -0,0 +1,6 @@ + + .text + + jsr 65536 + + diff --git a/xa/tests/neg_offset/test8.s b/xa/tests/neg_offset/test8.s new file mode 100644 index 0000000..4571b2a --- /dev/null +++ b/xa/tests/neg_offset/test8.s @@ -0,0 +1,6 @@ + + .text + + jsr LIB6502+65536 + +