1
0
mirror of https://github.com/fadden/6502bench.git synced 2024-12-02 13:51:36 +00:00
Commit Graph

115 Commits

Author SHA1 Message Date
Andy McFadden
0ac0686c7a ORG rework, part 9
Modified "jump to" code to understand address range start/end lines.
If there are multiple starts or ends at the same offset, we jump to
the first one in the set, which is suboptimal but simpler to do.
Simplified the API, embedding GoToMode in the Location object (which
is where it really needs to be, to make fwd/back work right).

Updated HTML export to grey out addresses in NON_ADDR sections.

Changed default pseudo-op strings for address regions to ".addrs" and
".adrend", after trying a bunch of things that were worse.  Added
definitions for region-end pseudo-ops to Merlin32 and cc65 for display
on screen.

Added regression test 20260 for address region pre-labels.

Fixed handling of leading underscores in platform/project symbols.
These need to be escaped in 64tass output.  Updated regression test
20170-external-symbols to check it.
2021-10-07 12:39:30 -07:00
Andy McFadden
e8608770b9 ORG rework, part 7
Implemented "is relative" flag.  This only affects source code
generation, replacing ".arstart <addr>" with ".arstart *+<value>".
Only output by 64tass and ACME generators.

Added a bold-text summary to radio buttons in address region edit
dialog.  This makes it much easier to see what you're doing.  Added
a warning to the label edit dialog when a label is being placed in
a non-addressable region.

Modified double-click behavior for .arstart/.arend to jump to the
other end when the opcode is clicked on.  This matches the behavior
of instructions with address operands.

Reordered Actions menu, putting "edit operand" at the top.

Fixed AddressMap entry collision testing.
Fixed PRG issue with multiple address regions at offset +000002.

Added regression tests.  Most of the complicated stuff with regions
is tested by unit tests inside AddressMap, but we still need to
exercise nested region code generation.
2021-10-02 15:43:41 -07:00
Andy McFadden
5f472b60cf ORG rework, part 3
Split ".org" into ".arstart" and ".arend" (address range start/end).
Address range ends are now shown in the code list view, and the
pseudo-op can be edited in app settings.  Address range starts are
now shown after notes and long comments, rather than before, which
brings the on-screen display in sync with generated code.

Reworked the address range editor UI to include the new features.
The implementation is fully broken.

More changes to the AddressMap API, putting the resolved region length
into a separate ActualLength field.  Added FindRegion().  Renamed
some things.

Code generation changed slightly: the blank line before a region-end
line now comes after it, and ACME's "} ;!pseudopc" is now just "}".
This required minor updates to some of the regression test results.
2021-09-22 15:28:11 -07:00
Andy McFadden
39b7b20144 ORG rework, part 1
This is the first step toward changing the address region map from a
linear list to a hierarchy.  See issue #107 for the plan.

The AddressMap class has been rewritten to support the new approach.
The rest of the project has been updated to conform to the new API,
but feature-wise is unchanged.  While the map class supports
nested regions with explicit lengths, the rest of the application
still assumes a series of non-overlapping regions with "floating"
lengths.

The Set Address dialog is currently non-functional.

All of the output for cc65 changed because generation of segment
comments has been removed.  Some of the output for ACME changed as
well, because we no longer follow "* = addr" with a redundant
pseudopc statement.  ACME and 65tass have similar approaches to
placing things in memory, and so now have similar implementations.
2021-09-16 17:02:19 -07:00
Andy McFadden
bdad8501f0 Minor fix for Merlin32
The test for '{' needed more parenthesis.
2021-08-23 17:22:56 -07:00
Andy McFadden
635084db9d Fix DCI string edge case
If a DCI string ended with a string delimiter or non-ASCII character
(e.g. a PETSCII char with no ASCII equivalent), the code generator
output the last byte as a hex value.  This caused an error because it
was outputting the raw hex value, with the high bit already set, which
the assembler did not expect.

This change corrects the behavior for code generation and on-screen
display, and adds a few samples to the regression test suite.

(see issue #102)
2021-08-10 14:08:39 -07:00
Andy McFadden
3a02132694 Update 64tass code gen
64tass v1.55.2176 added a missing undocumented op, so we can remove
the workaround unless we're configured for an older version.
2021-08-09 14:26:25 -07:00
Andy McFadden
478afa542e Fix 64tass code gen corner case
On the 65816, if you say "JSR foo" from bank $12, but "foo" is an
address in bank 0, most assemblers will conclude that you're forming
a 16-bit argument with a 16-bit address and assemble happily.  64tass
halts with an error.  Up until v1.55 or so, you could fake it out
by supplying a large offset.

This no longer works.  The preferred way to say "no really I mean to
do this" is to append ",k" to the operand.  We now do that as needed.

I didn't want to define a new ExpressionMode for 64tass just to
support an operand modifier that should probably never actually get
generated (you can't call across banks with JSR!), so this is
implemented with a quirk and an op flag.

64tass v1.56.2625 is now the default.

(issue #104)
2021-08-09 14:11:15 -07:00
Andy McFadden
3368182e14 Allow single-character DCI strings
The DCI string format uses character values where the high bit of the
last byte differs from the rest of the string.  Usually all the high
bits are clear except on the last byte, but SourceGen generally allows
either polarity.

This gets a little uncertain with single-character strings, because
SourceGen can't auto-detect DCI very effectively.  A series of bytes
with the high bit set could be a single high-ASCII string or a series
of single-byte DCI strings.

The motivation for allowing them is C64 PETSCII.  While ASCII allows
"high ASCII" as an escape hatch, PETSCII doesn't have that option, so
there's no way to mark the data as a character or a string.  We still
want to do a bit of screening, but if the user specifies a non-ASCII
character set and the selected bytes have their high bits set, we
want to just treat the whole set as 1-byte DCI.

Some minor adjustments were needed for a couple of validity checks
that expected longer strings.

This adds some short DCI strings in different character sets to the
char-encoding regression tests.

(for issue #102)
2021-08-08 15:38:39 -07:00
Andy McFadden
8db554c1cd Fix 64tass output for non-loadable files
64tass wants to place its output into a 64KB region of memory,
starting at the address "*" is set to, and continuing without
wrapping around the end of the bank.  Some files aren't meant to be
handled that way, so we need to generate the output differently.

If the file's output fits nicely, it's considered "loadable", and
is generated in the usual way.  If it doesn't, it's treated as
"streamable", and the initial "* = addr" directive is omitted
(leaving "*" at zero), and we go straight to ".logical" directives.

65816 code with an initial address outside bank 0 is treated as
"streamable" whether or not the contents fit nicely in the designated
64K area.  This caused a minor change to a few of the 65816 tests.

A new test, 20240-large-overlay, exercises "streamable" by creating
a file with eight overlapping 8KB segments that load at $8000.
While the file as a whole fits in 64KB, it wouldn't if loaded at
the desired start address.

Also, updated the regression test harness to report assembler
failure independently of overall test failure.  This makes it easier
to confirm that (say) ACME v0.96.4 still works with the code we
generate, even though it doesn't match the expected output (which
was generated for v0.97).

(problem was raised in issue #98)
2021-08-01 17:21:20 -07:00
Andy McFadden
752fa06ef5 Tweak backslash escaping
The initial implementation was testing the byte value rather than
the converted value, so backslashes were getting through in high
ASCII strings.  PETSCII and C64 screen codes don't really have a
backslash so it's not really an issue there.

The new implementation handles high ASCII correctly.  The various
201n0-char-encoding-x regression tests have been updated to verify
this.
2021-07-31 20:22:21 -07:00
Andy McFadden
8c053c29f2 Update ACME generator for v0.97
Two things changed: (1) string literals can now hold backslash
escapes like "\n"; (2) MVN/MVP operands can now be prefixed with '#'.
The former was a breaking change because any string with "\" must
be changed to "\\".  This is now handled by the string operand
formatter.

Also, improved test harness output.  Show the assembler versions at
the end, and include assembler failure messages in the collected
output.
2021-07-31 14:42:36 -07:00
Andy McFadden
c16e646701 Add a line to 20052-branches-and-banks
Throw a non-bank-zero JSR <hexaddr> into the mix.
2021-07-31 13:51:35 -07:00
Andy McFadden
bc7a225080 Expand 20152-local-variables test
Added a compiled C implementation of strlen().  The most interesting
part about this is that it references a 16-bit value via direct-page
address $ff, which means you'd want a local variable with
address=$ff and width=2.  The current UI prevents this.
2021-07-20 11:28:26 -07:00
Andy McFadden
9321f15052 Minor fix for 24-bit MULTI_MASK
The test for max allowed value was assuming 16-bit addresses.

We had no tests for 24-bit values, so this adds a 65816-specific
version of 20170-external-symbols.
2020-11-03 11:47:53 -08:00
Andy McFadden
345dff7765 Clone 20152-local-variables
Generate a 6502 test from the 65816 version by substituting the
16-bit instructions with 8-bit no-ops.  There's a lot of project
edits and weird stuff in the test, so this was much easier than
starting over.

The 65816 variant is largely unchanged, though it could now be
stripped down to the stack-offset instructions.
2020-10-19 17:14:56 -07:00
Andy McFadden
84e3dd3df2 Add 20100-label-dp test
The 20102-label-dp test is "allops-common-65816" with direct-page
labels.  20100-label-dp is the same thing, but with the 6502 version
instead.
2020-10-19 16:02:28 -07:00
Andy McFadden
b7d3e3cfdf Refactor 2006x-target-adjustment
Split into 6502/65816 portions.  The 6502 version is the original
with a few in-place substitutions (e.g. JMP for BRL).  The 65816
version is only needed to exercise special handling of PEA/PER.
2020-10-19 15:46:05 -07:00
Andy McFadden
8109396c48 Rework 201XX-char-encoding-X tests
We have a single character-encoding test that is cloned 3x so we can
exercise the different values for the project's default character
set.  It was a 65816 test because it tested 16-bit immediate char
operands, but that's a very small part of it.

The 65816-specific portion is now 20122-char-encoding.  The rest is
now 201{2,3,4}0-char-encoding-X.
2020-10-19 15:01:02 -07:00
Andy McFadden
17dc908420 Refactor tests 1002x and 1003x
Tests 10022-embedded-instructions and 10032-flags-and-branches were
a mix of 6502 and 65816 code.  The 6502 code has been separated into
its own file, so that the tests can be run on 8-bit-only assemblers.
2020-10-18 20:30:42 -07:00
Andy McFadden
e9fbc6c96c Change Merlin 32 output suffix
We append an assembler identifier to generated code.  For Merlin 32,
this was "_Merlin32".  All of the other assemblers use a lower-case
string, which makes Merlin look a little weird, so it has been
changed to "_merlin32".

Windows filesystems are generally case-insensitive, so this won't
likely affect anything.
2020-10-18 15:47:11 -07:00
Andy McFadden
2afb280472 Rename test 10042
The 10042-data-recognition test has no 65816-specific content, so it
should be named 10040-data-recognition.

Also, remove header comment from 20102-label-dp.
2020-10-18 09:16:50 -07:00
Andy McFadden
99cd0d3ac1 Improve handling of C64 PRG header
C64 PRG files are pretty common.  Their salient feature is that they
start with a 16-bit value that is used as the load address.  The
value is commonly generated by the assembler itself, rather than
explicitly added to the source file.

Not all assemblers know what a PRG file is, and some of them handle
it in ways that are difficult to guarantee in SourceGen.  ACME adds
the 16-bit header when the output file name ends in ".prg", cc65
uses a modified config file, 64tass uses a different command-line
option, and Merlin 32 has no idea what they are.

This change adds PRG file detection and handling to the 64tass code
generator.  Doing so required making a few changes to the gen/asm
interfaces, because we now need to have the generator pass additional
flags to the assembler, and sometimes we need code generation to
start somewhere other than offset zero.  Overall the changes were
pretty minor.

The 20042-address-changes test needed a 6502-only variant.  A new test
(20040-address-changes) has been added and given a PRG header.  As
part of this change the 65816 variant was changed to use addresses
in bank 2, which uncovered a code generation bug that this change
also fixes.

The 64tass --long-address flag doesn't appear to be necessary for
files <= 65536 bytes long, so we no longer emit it for those.

(issue #90)
2020-10-17 16:45:13 -07:00
Andy McFadden
728966f8d2 Add W65C02S support, part 4 (of 4)
Added 20233-rockwell unit test to exercise the new opcodes.  Nothing
too fancy.

Fixed branch offset computation.

(issue #87)
2020-10-11 18:43:00 -07:00
Andy McFadden
34ba47e71d Add W65C02S support, part 3
Modified the asm source generators and on-screen display to show the
DP arg for BBR/BBS as hex.  The instructions are otherwise treated
as relative branches, e.g. the DP arg doesn't get factored into the
cross-reference table.

ACME/cc65 put the bit number in the mnemonic, 64tass wants it to be
in the first argument, and Merlin32 wants nothing to do with any of
this because it's incompatible with the 65816.

Added an "all ops" test for W65C02.
2020-10-11 14:35:17 -07:00
Andy McFadden
ba35f88d02 Mark flags as indeterminate for inline BRK
We weren't altering the status flags after a BRK because of the
assumption that a BRK was a crash.  For an inline BRK, such as a SOS
call, execution continues.  We need to mark NVZC indeterminate or
we may incorrectly handle conditional branches that follow.

The BRK instruction now uses the same flag updater as JSR, since it's
effectively a subroutine call to unknown code.  If execution doesn't
continue across the BRK then the flags don't matter.

Updated 20182-extension-scripts to exercise this.
2020-08-22 08:56:38 -07:00
Andy McFadden
c63035fb55 Update expected results for 10032-flags-and-branches
The "smart PLP" behavior change in 2a65457e altered the analysis.
2020-07-30 16:57:33 -07:00
Andy McFadden
b7d771a3b2 Fix expected values for 20212-reloc-data
Somehow these weren't part of commit 689204.
2020-07-22 17:25:55 -07:00
Andy McFadden
288a857e47 Change PLP handling
The "smart" PLP handler tries to recover the flags from an earlier
PHP.  The non-smart version just marks all the flags as indeterminate.
This doesn't work well on the 65816 in native mode, because having
the M/X flags in an indeterminate state is rarely what you want.

Code rarely uses PLP to reset the flags to a specific state, preferring
explicit SEP/REP.  The analyzer is more likely to get the correct
answer by simply leaving the flags in their prior state.

A test case has been added to 20052-branches-and-banks, which now has
"smart PLP" disabled.
2020-07-20 11:54:00 -07:00
Andy McFadden
cc6ebaffc5 Update relocation data handling
When we have relocation data available, the code currently skips the
process of matching an address with a label for a PEA instruction when
the instruction in question doesn't have reloc data.  This does a
great job of separating code that pushes parts of addresses from code
that pushes constants.

This change expands the behavior to exclude instructions with 16-bit
address operands that use the Data Bank Register, e.g. "LDA abs"
and "LDA abs,X".  This is particularly useful for code that accesses
structured data using the operand as the structure offset, e.g.
"LDX addr" / "LDA $0000,X"

The 20212-reloc-data test has been updated to check the behavior.
2020-07-10 17:41:38 -07:00
Andy McFadden
da38bc0db8 Data Bank Register management, part 6 (of 6)
Add 20222-data-bank to regression test suite.  This exercises handling
of 16-bit operands with inter- and intra-bank references, and tests the
smartness in "smart PLB".

Also, update a couple of older tests that broke because the DBR is no
longer always the same as the PBR.  This just required adding "B=K"
in a few places to restore the original output.
2020-07-10 15:53:43 -07:00
Andy McFadden
6ce2cc0b58 Fix label-trampling bug in reloc data handler
If code accesses the high/low parts of a 32-bit address value with
no label, it auto-generates labels for addr+2 and addr.  The reloc
handler was replacing the unformatted bytes with a single multi-byte
format, hiding the label at addr+2.

The easy fix is to have the reloc data handler skip the entry.  This
is less useful than other approaches, but much simpler.

Added a test to 20212-reloc-data.
2020-07-10 13:56:07 -07:00
Andy McFadden
4e70edc90c Add 20212-reloc-data test
This test exercises the relocation data feature.  The test file is
generated from a multi-segment OMF file that was hex-edited to have
specific attributes (see 20212-reloc-data-lnk.S for instructions).
The test also serves as a way to exercise the OMF converter.

Also, implement the Bank Relative flag.
2020-07-05 17:17:44 -07:00
Andy McFadden
8d291ba21e Fix bank for AbsInd and AbsIndLong addressing
The Absolute Indirect and Absolute Indirect Long addressing modes
(e.g. "JMP (addr)" and "JMP [addr]") are 16-bit values in bank 0.
The code analyzer was placing them in the program bank, which
meant the wrong symbol was being used.

Also, tweak some docs.
2020-07-04 15:03:23 -07:00
Andy McFadden
6d7fdff6b5 Fix 65816 code generation issues
Code generated for 64tass was incorrect for JSR/JMP to a location
outside the file bounds.  A test added to 20052-branches-and-banks
revealed an issue with cc65 generation as well.
2020-07-03 14:02:38 -07:00
Andy McFadden
4d06bb24eb Improve Common expression generation
Removed unnecessary parenthesis from Common-style expressions, which
are used by 64tass and ACME.
2020-07-02 13:00:02 -07:00
Andy McFadden
7d1d7f9c56 Operand for ".enc" should be in double quotes
The 64tass assembler was generating a warning.
2020-07-02 08:14:42 -07:00
Andy McFadden
fdd2bcf847 Fix some 65816 code generation issues
Two basic problems:

(1) cc65, being a one-pass assembler, can't tell if a forward-referenced
label is 16-bit or 24-bit.  If the operand is potentially ambiguous,
such as "LDA label", we need to add an operand width disambiguator.
(The existing tests managed to only do backward references.)

(2) 64tass wants the labels on JMP/JSR absolute operands to have 24-bit
values that match the current program bank.  This is the opposite of
cc65, which requires 16-bit values.  We need to distinguish PBR vs.
DBR instructions (i.e. "LDA abs" vs. "JMP abs") and handle them
differently when formatting for "Common".

Merlin32 doesn't care, and ACME doesn't work at all, so neither of
those needed updating.

The 20052-branches-and-banks test was expanded to cover the problematic
cases.
2020-07-01 17:59:12 -07:00
Andy McFadden
b43fd07688 Split 2002x-operand-formats test
My original goal was to add a sign-extended decimal format, but that
turned out to be awkward.  It works for data items and instructions
with immediate operands (e.g. "LDA #-1"), but is either wrong or
useless for address operands, since most assemblers treat integers
as 32-bit values.  (LDA -1 is not LDA $FFFF, it's LDA $FFFFFFFF,
which is not useful unless your asm is doing an implicit mod.)

There's also a bit of variability in how assemblers treat negative
values, so I'm shelving the idea for now.  I'm keeping the updated
tests, which are now split into 6502 / 65816 parts.

Also, updated the formatter to output all decimal values as unsigned.
Most assemblers were fine with negative values, but 64tass .dword
insists on positive.  Rather than make the opcode conditional on the
value's range, we now just always output unsigned decimal, which
all current assemblers accept.
2020-06-08 17:47:26 -07:00
Andy McFadden
3637bb964d Regression test rework, part 4
Split 2005x-branches-and-banks into two parts, one that stays within
the 64K bounds of the 6502, one that puts code in a separate bank.
2020-06-06 17:30:50 -07:00
Andy McFadden
d0d387b973 Regression test rework, part 3
Add a 6502-only version of the 20032-labels-and-symbols test.  The
65816 version could get away with just the 65816-specific stuff, but
there's no real need to modify it.  (The next time I update it I may
remove the duplicate label since that requires hand-editing.)
2020-06-06 17:06:31 -07:00
Andy McFadden
225ab9e132 Regression test rework, part 2
Renamed the remaining tests.  Only edits were to the project files
that referenced .sym65/.cs.
2020-06-06 15:36:08 -07:00
Andy McFadden
3ff0fbae34 Regression test rework, part 1
The regression tests were written with the assumption that all cross
assemblers would support 6502, 65C02, and 65816 code.  There are a
few that support 65816 partially (e.g. ACME) or not at all.  To best
support these, we need to split some of the tests into pieces, so
that important 6502 tests aren't skipped simply because parts of the
test also exercise 65816 code.

The first step is to change the regression test naming scheme.  The
old system used 1xxx for tests without project files, and 2xxx for
tests with project files.  The new system uses 1xxxN / 2xxxN, where
N indicates the CPU type: 0 for 6502, 1 for 65C02, and 2 for 65816.
For the 1xxxN tests the new value determines which CPU is used,
which allows us to move the "allops" 6502/65C02 tests into the
no-project category.  For 2xxxN it just allows the 6502 and 65816
versions to have the same base name and number.

This change updates the first batch of tests.  It involves minor
changes to the test harness and a whole bunch of renaming.
2020-06-06 14:47:19 -07:00
Andy McFadden
4981c3cdbb Fix ACME code gen "overflow"
ACME has a "real" PC and a "pseudo" PC.  The "real" PC determines the
initial position in a 64KB buffer used to hold assembler output.  If
the amount of code generated runs off the end, the assembler fails
with "produced too much code".

The source code generator in SourceGen was outputting a "real" PC
for the first address range and "psuedo" PCs for any address ranges
that followed.  This produced nice results for code with a single
range, but caused problems for multi-range sources if the initial
range was high in memory and a later range was lower in memory.
While the assembler isn't actually generating more than 64KB of code,
ACME's buffer management was detecting an overflow.

Now, if a source file has multiple address ranges, we set the "real"
PC to $0000 and use a "pseudo" PC for all ranges.  Output for projects
with a single address range is unmodified.
2020-05-14 16:37:33 -07:00
Andy McFadden
63d7a48705 Fix bug in inline JSR/JSL no-continue handling
JSR/JSL calls with inline data have the option of reporting that
they don't continue, which causes the code analyzer to treat them
as JMPs instead.  There was a bug that was causing the no-continue
flag to be lost in certain circumstances.

The code now explicitly records the plugin's response in an Anattrib
flag.  Test 2022-extension-scripts has been updated with a test case
that exercises this situation.
2020-05-08 17:41:26 -07:00
Andy McFadden
facaa721de Fix AND/ORA imm flag updater
The code was making an unwarranted assumption about how the flags
were being set.  For example, ORA #$00 can't know if the previous
contents of the accumulator were nonzero, only that the instruction
hasn't made them nonzero, but instead of marking the Z-flag
"indeterminate" it was leaving the flag in its previous state.  This
produces incorrect results if the previous instruction didn't set
its flags from the accumulator contents, e.g. it was an LDX.

Test 1003-flags-and-branches has been updated to test these states.
2020-05-01 17:29:22 -07:00
Andy McFadden
59b7ec0dea Recognize that LSR always clears the 'N' flag
The instruction shifts 0 into the high bit, so the result is never
negative.  Added a test case to 1003-flags-and-branches.
2020-04-23 17:23:12 -07:00
Andy McFadden
547cbb7811 Work around Merlin assembler bug
The assembler can't handle "DFB '{'" or "DFB '}'", so just output
those as hex.

Tests added to 2006-operand-formats.
2020-03-18 17:45:06 -07:00
Andy McFadden
0bbb307d4e Correct handling of no-op .ORG statements
These were being overlooked because they didn't actually cause
anything to happen (a no-op .ORG sets the address to what it would
already have been).  The assembly source generator works in a way
that causes them to be skipped, so everybody was happy.

This seemed like the sort of thing that was likely to cause problems
down the road, however, so we now split regions correctly when a
no-op .ORG is encountered.  This affects the uncategorized data
analyzer and selection grouping.

This changed the behavior of the 2004-numeric-types test, which was
visibly weird in the UI but generated correct output.

Added the 2024-ui-edge-cases test to provide a place to exercise
edge cases when testing the UI by hand.  It has some value for the
automated regression test, so it's included there.

Also, changed the AddressMapEntry objects to be immutable.  This
is handy when passing lists of them around.
2020-02-28 14:49:18 -08:00
Andy McFadden
5b75ae35fc Fix ANDImm flag updater
For nonzero values we were leaving Z=prev, which is wrong when Z=0
because the AND result might be zero.  Now if Z=1 we leave it alone,
but if Z=0 we now set it to Z=?.

Test 1003-flags-and-branches was testing for the (incorrect)
behavior, so we're now running into a BRK.  This is fine.
2020-02-01 16:41:44 -08:00