Jump to content
IGNORED

Flashjazzcat's Blog - The Last Word Development Blog: Part 2


RSS Bot

Recommended Posts

It's been a fraught week of hardware problems, but in between all that I've managed a few hours' coding. Moving The Last Word's code under the banked text buffer has proved more difficult than I thought: a program which was designed to access linear memory in an ad hoc fashion needs a lot of careful reorganisation to ensure target code never gets switched out at the wrong time.

 

In prior versions of LW, the page at $7F00 has held pointers and tables pertaining to the text in the memory between $4000-$7EFF (although the "main" bank can extend down to $3000 in some versions). In fact, $7F00 in every text bank contains $DB (the internal representation of the EOL character), which acts as an "end of text" marker (the screen redraw checks for $7F00 every time it hits an EOL character. There's only one EOL at this address, so it signifies the end of text. The EOL character is also stored at the cursor location, although it's never displayed because it's also a marker, which tells the screen redraw routine to skip the empty space which is always immediately in front of the insertion point). Keeping the tables at the top of the bank is convenient when accessing the banked memory directly, but when using an indirect system, it makes things complicated. I've decided for this reason to simply copy the data table into main ram when swapping banks in and out, so the editing routines can perform direct reads and writes. When a different bank gets swapped in, I'll just copy the table back to the last page of the current RAM bank first.

 

So now that the program is almost fully operational with the text bank sitting "underneath" the program code, how can we break the pesky 16K text size limit? Well, anyone familiar with FMS or RAMdisk programming will be familar with what I have in mind. The existing system for storing a byte at the insertion point is:

 

 

sta_pos_y pha lda textbankmask sta portb pla sta (pos),y pha lda banktab sta portb pla rts

 

Since we've already incurred the overhead of calling a subroutine instead of doing a direct store, I intend to take advantage of the abstract data addressing by allowing POS to range across a 32K space instead of a 16K space, while masking the pointer and transparently switching in the appropriate bank. POS might as well be stored as $4000-$BFFF or $0000-$7FFF - it doesn't really matter since the pointer will need to be "trimmed" to point to $4000-7FFF only 50% of whichever way we do it.

 

If we adopt $4000-$BFFF as values for POS, then our storage routine needs to be amended as follows: we need to check for bit 7 being set in the MSB of the address pointer (POS). If it is, then we reverse bits 7 and 6 (EOR $C0) of the MSB, and switch in the "next" bank along: effectively the second half of the 32K space. Doing this quickly enough is the most difficult challenge, especially bearing in mind there are occasions when we'll want to copy or move data between one extended bank and another.

 

A verbose example of how we might code this up is as follows:

 

sta_pos_y pha ; save byte to store lda textbankmask ; assume first bank bit pos+1 ; test high bits of MSB bpl select_bank lda pos+1 eor #$C0 ; shift down by $4000 sta pos+1 lda textbankmask+1 ; select next bankselect_bank sta portb pla ; get byte back sta (pos),y pha lda banktab sta portb pla

 

This example is flawed in as much as it corrupts POS (which needs to be left intact), so we need yet more code. There's also redundancy in so much as the banking mask is loaded twice when the pointer refers to the higher bank. However, once this routine is optimized, it's the way I intend to go about things. Better suggestions are welcomed!

 

http://www.atariage.com/forums/index.php?app=blog&blogid=281&showentry=6820

Link to comment
Share on other sites

Guest
This topic is now closed to further replies.
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...