mirror of
https://github.com/a2-4am/4live.git
synced 2024-06-17 21:29:37 +00:00
Merge pull request #18 from peterferrie/master
correct page display, limit to 99 pages
This commit is contained in:
commit
43bfa0a80d
337
src/4live.a
337
src/4live.a
|
@ -72,19 +72,22 @@
|
||||||
POSRDWRRANGE = 4
|
POSRDWRRANGE = 4
|
||||||
WIDTH = 40
|
WIDTH = 40
|
||||||
HEIGHT = 24
|
HEIGHT = 24
|
||||||
LDRBASE = $2E0
|
LDRBASE = $2E9
|
||||||
INSTALLBUFFER = $23C ; yes, the overlay overwrites the loader...
|
INSTALLBUFFER = $23B ; yes, the overlay overwrites the loader...
|
||||||
; see also "warning!" below
|
; see also "warning!" below
|
||||||
SWAPBUFFER = $900 ; (LoadSaveEnd - LoadSaveStart) size
|
SWAPBUFFER = $900 ; (LoadSaveEnd - LoadSaveStart) size
|
||||||
; needed by DiversiDOS, must be page-aligned
|
; needed by Diversi-DOS, must be page-aligned
|
||||||
; region is preserved across calls
|
; region is preserved across calls
|
||||||
|
; do not set below $900 if *size* of buffer is not page-aligned
|
||||||
|
SWAPSIZEALIGNED = 0 ; set to 1 if (LoadSaveEnd - LoadSaveStart) size is page-aligned
|
||||||
|
; an aligned size reduces code size by a bit but increases memory usage by a lot
|
||||||
|
|
||||||
*=LDRBASE-4
|
*=LDRBASE-4
|
||||||
LdrHeader
|
LdrHeader
|
||||||
!word LDRBASE, LdrEnd - LdrStart
|
!word LDRBASE, LdrEnd - LdrStart
|
||||||
|
|
||||||
;loader loads to pages 2-3, loads discardable install code also to pages 2-3
|
;loader loads to pages 2-3, loads discardable install code also to pages 2-3
|
||||||
;and carries proxy routines including file manager and banked RAM exchange for DiversiDOS
|
;and carries proxy routines including file manager and banked RAM exchange for Diversi-DOS
|
||||||
|
|
||||||
LdrStart
|
LdrStart
|
||||||
;set filename pointer in MLI request packet
|
;set filename pointer in MLI request packet
|
||||||
|
@ -228,22 +231,14 @@ BankInRAM1
|
||||||
bit LCBANK1
|
bit LCBANK1
|
||||||
rts
|
rts
|
||||||
|
|
||||||
;write size must be one less than required value because of course it must
|
;read file content into memory
|
||||||
|
;with swapping of the memory contents in Diversi-DOS,
|
||||||
WriteFile
|
;in order to preserve the original memory region
|
||||||
lda ReadWriteCmd
|
|
||||||
lsr ;read has bit 0 set, write does not
|
|
||||||
bcs ReadFile
|
|
||||||
|
|
||||||
;;we are not now writing any page-aligned sizes
|
|
||||||
;; lda WriteSize
|
|
||||||
;; bne +
|
|
||||||
;; dec WriteSize + 1
|
|
||||||
;;+
|
|
||||||
dec WriteSize
|
|
||||||
|
|
||||||
ReadFile
|
ReadFile
|
||||||
jsr ExchangeBanked1
|
jsr ExchangeBanked1
|
||||||
|
ReadFileNoXchg
|
||||||
|
WriteFile
|
||||||
jsr DOSMLI
|
jsr DOSMLI
|
||||||
!byte ReadMLI_e - ReadMLI_b
|
!byte ReadMLI_e - ReadMLI_b
|
||||||
ReadMLI_b
|
ReadMLI_b
|
||||||
|
@ -262,16 +257,16 @@ WriteSize
|
||||||
|
|
||||||
ReadBuffer
|
ReadBuffer
|
||||||
WriteBuffer
|
WriteBuffer
|
||||||
!word LoadSaveStart ;buffer, self-modified in DiversiDOS
|
!word LoadSaveStart ;buffer, self-modified in Diversi-DOS
|
||||||
ReadMLI_e
|
ReadMLI_e
|
||||||
;fall through to ExchangeBanked1
|
;fall through to ExchangeBanked1
|
||||||
|
|
||||||
;swap banked dynamic region with spare region also in banked memory
|
;swap banked memory region with main memory region
|
||||||
;call again to restore the banked dynamic region
|
;call again to restore the main memory region
|
||||||
;sorry, I couldn't find a simpler way...
|
;sorry, I couldn't find a simpler way...
|
||||||
|
|
||||||
ExchangeBanked1
|
ExchangeBanked1
|
||||||
rts ;self-modified to CLC in DiversiDOS environment
|
rts ;self-modified to CLC in Diversi-DOS environment
|
||||||
|
|
||||||
;fill banked dynamic region with spaces
|
;fill banked dynamic region with spaces
|
||||||
|
|
||||||
|
@ -284,6 +279,8 @@ ClearVirtualBuffer ;called with carry set
|
||||||
sta OPSRC1L
|
sta OPSRC1L
|
||||||
lda #<LastLine
|
lda #<LastLine
|
||||||
|
|
||||||
|
;can also swap banked dynamic region with spare region also in banked memory
|
||||||
|
|
||||||
ExchangeBankedSet ;called with A=buffer offset, carry clear
|
ExchangeBankedSet ;called with A=buffer offset, carry clear
|
||||||
sta OPDST1L
|
sta OPDST1L
|
||||||
|
|
||||||
|
@ -306,32 +303,35 @@ ExchangeBankedPatch
|
||||||
bpl -
|
bpl -
|
||||||
rts
|
rts
|
||||||
LdrEnd
|
LdrEnd
|
||||||
!if (LdrEnd > $3D0) {
|
!ifdef PASS2 {
|
||||||
!error "page 3 swap-code too large, ", LdrEnd - $3D0, " bytes too many"
|
!if (LdrEnd > $3D0) {
|
||||||
} else {
|
!error "LDRBASE too high, change to ", LdrStart + $3D0 - LdrEnd
|
||||||
!if (LdrEnd < $3D0) {
|
} else {
|
||||||
!error "LDRBASE too low, change to ", LdrStart + $3D0 - LdrEnd
|
!if (LdrEnd < $3D0) {
|
||||||
|
!error "LDRBASE too low, change to ", LdrStart + $3D0 - LdrEnd
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
;install routine is an overlay that is loaded by loader routine above
|
;install routine is an overlay that is loaded by loader routine above
|
||||||
;loads editor code and data file into banked RAM either directly for DOS 3.3
|
;loads editor code and data file into banked RAM either directly for DOS 3.3
|
||||||
;or via RAM exchange for DiversiDOS
|
;or via RAM exchange for Diversi-DOS
|
||||||
|
|
||||||
!pseudopc INSTALLBUFFER {
|
!pseudopc INSTALLBUFFER {
|
||||||
InstallStart
|
InstallStart
|
||||||
;check for DiversiDOS
|
;check for Diversi-DOS
|
||||||
|
|
||||||
pla
|
pla
|
||||||
eor #$BF
|
eor #$BF
|
||||||
|
pha
|
||||||
bne + ;regular DOS
|
bne + ;regular DOS
|
||||||
sta ReadBuffer
|
sta ReadBuffer
|
||||||
lda #>SWAPBUFFER
|
lda #>SWAPBUFFER
|
||||||
sta ReadBuffer + 1
|
sta ReadBuffer + 1
|
||||||
sta InstallReadBuffer + 1
|
sta InstallReadBuffer + 1
|
||||||
lda #$18 ;CLC
|
lda #$18 ;CLC
|
||||||
sta ExchangeBanked1
|
|
||||||
sta ExchangeBanked2
|
sta ExchangeBanked2
|
||||||
|
sta ExchangeBanked1
|
||||||
+
|
+
|
||||||
;enable reading directly into banked RAM
|
;enable reading directly into banked RAM
|
||||||
|
|
||||||
|
@ -340,7 +340,11 @@ InstallStart
|
||||||
;read second overlay to banked RAM
|
;read second overlay to banked RAM
|
||||||
|
|
||||||
jsr ReadEditor
|
jsr ReadEditor
|
||||||
|
pla
|
||||||
|
bne +
|
||||||
|
lda #$90
|
||||||
|
sta PatchDiversi
|
||||||
|
+
|
||||||
;open source file and read header if available
|
;open source file and read header if available
|
||||||
|
|
||||||
jsr LoadSaveHeader
|
jsr LoadSaveHeader
|
||||||
|
@ -354,6 +358,7 @@ InstallStart
|
||||||
;set to true if no data file found (carry is set)
|
;set to true if no data file found (carry is set)
|
||||||
|
|
||||||
rol ClearOnFirstKeypress + 1
|
rol ClearOnFirstKeypress + 1
|
||||||
|
rol PreventAddPage + 1 ;tri-state flag because Diversi-DOS
|
||||||
|
|
||||||
jsr SetTextCoords1
|
jsr SetTextCoords1
|
||||||
|
|
||||||
|
@ -371,7 +376,7 @@ InstallStart
|
||||||
beq +
|
beq +
|
||||||
lda #INVSPACE
|
lda #INVSPACE
|
||||||
sta CharDel + 1
|
sta CharDel + 1
|
||||||
lda #("z" + 1)
|
lda #$DF
|
||||||
sta CharMap1 + 1
|
sta CharMap1 + 1
|
||||||
sta CharMap2 + 1
|
sta CharMap2 + 1
|
||||||
+
|
+
|
||||||
|
@ -379,26 +384,23 @@ InstallStart
|
||||||
|
|
||||||
ldy #0
|
ldy #0
|
||||||
beq ++
|
beq ++
|
||||||
CharMap1
|
- cmp #$E0
|
||||||
cmp #0 ;self-modified in Apple II+ environment
|
|
||||||
bcs +
|
|
||||||
cmp #"a"
|
|
||||||
bcc +
|
bcc +
|
||||||
and #$DF
|
CharMap1
|
||||||
|
and #$FF ;self-modified in Apple II+ environment
|
||||||
+ jsr COUT
|
+ jsr COUT
|
||||||
++ iny
|
++ iny
|
||||||
lda _WelcomeMessage-1,y
|
lda _WelcomeMessage-1,y
|
||||||
bne CharMap1
|
bne -
|
||||||
;;warning! takes advantage of the fact that the hook is at $300!
|
lda #<GlobalKeyboardHook
|
||||||
;;but this cannot be detected as assemble time because of the forward reference
|
|
||||||
;; !if <GlobalKeyboardHook {
|
|
||||||
;; lda #<GlobalKeyboardHook
|
|
||||||
;; }
|
|
||||||
sta KSWL
|
sta KSWL
|
||||||
lda #>GlobalKeyboardHook
|
lda #>GlobalKeyboardHook
|
||||||
sta KSWH
|
sta KSWH
|
||||||
jmp WARMDOS ;DOS will reconnect the vector itself
|
jmp WARMDOS ;DOS will reconnect the vector itself
|
||||||
|
|
||||||
|
;read the main code into banked RAM
|
||||||
|
;uses the memory swapping technique in Diversi-DOS
|
||||||
|
|
||||||
ReadEditor
|
ReadEditor
|
||||||
jsr ExchangeBanked2
|
jsr ExchangeBanked2
|
||||||
lda #$20 ;JSR
|
lda #$20 ;JSR
|
||||||
|
@ -416,10 +418,10 @@ InstallReadMLI_b
|
||||||
InstallReadBuffer
|
InstallReadBuffer
|
||||||
!word $D000 ;buffer
|
!word $D000 ;buffer
|
||||||
InstallReadMLI_e
|
InstallReadMLI_e
|
||||||
;fall through to ExchangeBanked2
|
;fall through to restore buffer
|
||||||
|
|
||||||
ExchangeBanked2
|
ExchangeBanked2
|
||||||
rts ;self-modified to CLC (for compatibility) in DiversiDOS environment
|
rts ;self-modified to CLC (for compatibility) in Diversi-DOS environment
|
||||||
lda #>($D000 - <(BankedCopyStart - BankedCopyEnd))
|
lda #>($D000 - <(BankedCopyStart - BankedCopyEnd))
|
||||||
sta OPDST1H
|
sta OPDST1H
|
||||||
ldx #>(BankedCopyEnd - BankedCopyStart)
|
ldx #>(BankedCopyEnd - BankedCopyStart)
|
||||||
|
@ -454,11 +456,15 @@ GetKey
|
||||||
jsr RDCHAR ;returns non-zero
|
jsr RDCHAR ;returns non-zero
|
||||||
bne GetKey ;always
|
bne GetKey ;always
|
||||||
InstallEnd
|
InstallEnd
|
||||||
!if (InstallEnd > JmpInstall) {
|
!ifdef PASS2 {
|
||||||
!error "page 2 swap-code too large, ", InstallEnd - JmpInstall, " bytes too many"
|
!if (LdrEnd = $3D0) {
|
||||||
} else {
|
!if (InstallEnd > JmpInstall) {
|
||||||
!if (InstallEnd < JmpInstall) {
|
!error "INSTALLBUFFER too large, change to ", InstallStart + JmpInstall - InstallEnd
|
||||||
!error "INSTALLBUFFER too low, change to ", InstallStart + JmpInstall - InstallEnd
|
} else {
|
||||||
|
!if (InstallEnd < JmpInstall) {
|
||||||
|
!error "INSTALLBUFFER too low, change to ", InstallStart + JmpInstall - InstallEnd
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -476,11 +482,12 @@ RunFromBankedRAM
|
||||||
|
|
||||||
;first, scroll the edit buffer onto the screen
|
;first, scroll the edit buffer onto the screen
|
||||||
;(this also swaps the current screen contents out so we can restore it later)
|
;(this also swaps the current screen contents out so we can restore it later)
|
||||||
|
|
||||||
jsr ScrollEditBufferIn ;returns Y=FF
|
jsr ScrollEditBufferIn ;returns Y=FF
|
||||||
|
|
||||||
;do the thing
|
;do the thing
|
||||||
|
|
||||||
iny
|
iny ;Y=0
|
||||||
sty WriteIfDirty2 + 1 ;0=false, non-0=true
|
sty WriteIfDirty2 + 1 ;0=false, non-0=true
|
||||||
|
|
||||||
;do the thing
|
;do the thing
|
||||||
|
@ -519,12 +526,13 @@ ScrollEditBufferIn
|
||||||
|
|
||||||
ldy #(WIDTH - 1)
|
ldy #(WIDTH - 1)
|
||||||
- lda (OPDST1L), y
|
- lda (OPDST1L), y
|
||||||
jsr CharMap2
|
jsr MapCase
|
||||||
sta $0400, y
|
sta $0400, y
|
||||||
dey
|
dey
|
||||||
bpl -
|
bpl -
|
||||||
|
|
||||||
;animation delay
|
;animation delay
|
||||||
|
|
||||||
jsr Delay
|
jsr Delay
|
||||||
|
|
||||||
lda #-WIDTH
|
lda #-WIDTH
|
||||||
|
@ -553,7 +561,7 @@ HexToDec ;called with X=hex value to print
|
||||||
ldx #0
|
ldx #0
|
||||||
- cmp #$0A
|
- cmp #$0A
|
||||||
bcc +
|
bcc +
|
||||||
sbc #9
|
sbc #$0A
|
||||||
inx
|
inx
|
||||||
bne -
|
bne -
|
||||||
+ jsr AToScr
|
+ jsr AToScr
|
||||||
|
@ -565,12 +573,11 @@ AToScr ;called with A=dec value to print
|
||||||
dey
|
dey
|
||||||
rts
|
rts
|
||||||
|
|
||||||
CharMap2
|
MapCase
|
||||||
cmp #0 ;self-modified in Apple II+ environment
|
cmp #$E0
|
||||||
bcs +
|
|
||||||
cmp #"a"
|
|
||||||
bcc +
|
bcc +
|
||||||
and #$DF
|
CharMap2
|
||||||
|
and #$FF ;self-modified in Apple II+ environment
|
||||||
+ rts
|
+ rts
|
||||||
|
|
||||||
ScrollEditBufferOut
|
ScrollEditBufferOut
|
||||||
|
@ -598,6 +605,7 @@ ScrollEditBufferOut
|
||||||
bpl -
|
bpl -
|
||||||
|
|
||||||
;animation delay
|
;animation delay
|
||||||
|
|
||||||
jsr Delay ;returns A=0
|
jsr Delay ;returns A=0
|
||||||
|
|
||||||
tay
|
tay
|
||||||
|
@ -682,6 +690,8 @@ CopyRow
|
||||||
Delay
|
Delay
|
||||||
lda #1
|
lda #1
|
||||||
|
|
||||||
|
;straight from ROM
|
||||||
|
|
||||||
MyWAIT
|
MyWAIT
|
||||||
sec
|
sec
|
||||||
-- pha
|
-- pha
|
||||||
|
@ -695,6 +705,8 @@ MyWAIT
|
||||||
MyKEYIN
|
MyKEYIN
|
||||||
ldx MyCH + 1
|
ldx MyCH + 1
|
||||||
|
|
||||||
|
;fetch the character at the current cursor position
|
||||||
|
|
||||||
ScreenBuff2
|
ScreenBuff2
|
||||||
lda $34f3, x ;self-modified
|
lda $34f3, x ;self-modified
|
||||||
sta ToggleChar + 1
|
sta ToggleChar + 1
|
||||||
|
@ -760,17 +772,21 @@ EditorMode
|
||||||
+ cpx #(IgnoreDirty - KeyTable_b)
|
+ cpx #(IgnoreDirty - KeyTable_b)
|
||||||
;save result in carry
|
;save result in carry
|
||||||
|
|
||||||
|
;the first keypress that clears the screen is also a trigger that the first page is dirty
|
||||||
|
;we require this trigger to allow us to work around a bug in Diversi-DOS
|
||||||
|
|
||||||
ClearOnFirstKeypress
|
ClearOnFirstKeypress
|
||||||
ldy #0 ;self-modified
|
ldy #0 ;self-modified
|
||||||
beq +
|
beq +
|
||||||
dec ClearOnFirstKeypress + 1
|
dec ClearOnFirstKeypress + 1
|
||||||
php ;save carry (don't care about the rest)
|
php ;save carry (don't care about the rest)
|
||||||
pha
|
pha
|
||||||
jsr ClearScreen
|
jsr ClearScreen ;returns Y=FF
|
||||||
|
sty PreventAddPage + 1 ;trigger first write
|
||||||
pla
|
pla
|
||||||
plp ;restore carry
|
plp ;restore carry
|
||||||
+ bcc DispatchCommand
|
+ bcc DispatchCommand
|
||||||
sta WriteIfDirty2 + 1
|
sta WriteIfDirty2 + 1 ;remember if page was modified in the general case
|
||||||
|
|
||||||
DispatchCommand
|
DispatchCommand
|
||||||
jsr $34f3 ;self-modified, currently both bytes
|
jsr $34f3 ;self-modified, currently both bytes
|
||||||
|
@ -805,16 +821,16 @@ ScreenBuff4
|
||||||
ldx #0
|
ldx #0
|
||||||
MyCV
|
MyCV
|
||||||
ldy #"Q" ;self-modified
|
ldy #"Q" ;self-modified
|
||||||
iny
|
iny ;move to next line on horizontal typed wraparound
|
||||||
cpy #(HEIGHT - 1)
|
cpy #(HEIGHT - 1)
|
||||||
bne MyBASCALC
|
bne MyBASCALC
|
||||||
dey
|
ldy #0 ;move to top left on vertical typed wraparound
|
||||||
bne MyBASCALC ;always
|
beq MyBASCALC ;always
|
||||||
|
|
||||||
HandleKeyLineLeft
|
HandleKeyLineLeft
|
||||||
dec MyCH + 1
|
dec MyCH + 1
|
||||||
bpl DispatchReturn
|
bpl DispatchReturn
|
||||||
lda #(WIDTH - 1)
|
lda #(WIDTH - 1) ;wrap to same line on horizontal arrow wraparound
|
||||||
|
|
||||||
SetColumn
|
SetColumn
|
||||||
sta MyCH + 1
|
sta MyCH + 1
|
||||||
|
@ -825,7 +841,7 @@ HandleKeyLineRight
|
||||||
lda MyCH + 1
|
lda MyCH + 1
|
||||||
eor #WIDTH ;zero on match
|
eor #WIDTH ;zero on match
|
||||||
bne DispatchReturn
|
bne DispatchReturn
|
||||||
beq SetColumn ;always
|
beq SetColumn ;always, wrap to same line on horizontal arrow wraparound
|
||||||
|
|
||||||
HandleKeyLineUp
|
HandleKeyLineUp
|
||||||
ldy MyCV + 1
|
ldy MyCV + 1
|
||||||
|
@ -859,7 +875,7 @@ HandleKeyClearScreen
|
||||||
|
|
||||||
HandleKeyReturn
|
HandleKeyReturn
|
||||||
lda #0
|
lda #0
|
||||||
sta MyCH + 1
|
sta MyCH + 1 ;move to left of next line on return
|
||||||
;fall through
|
;fall through
|
||||||
|
|
||||||
HandleKeyLineDown
|
HandleKeyLineDown
|
||||||
|
@ -886,7 +902,7 @@ HandleKeyImportScreen ;called with carry set
|
||||||
ldx #(HEIGHT - 2)
|
ldx #(HEIGHT - 2)
|
||||||
-- jsr SetTextCalc
|
-- jsr SetTextCalc
|
||||||
ldy #(WIDTH - 1)
|
ldy #(WIDTH - 1)
|
||||||
lda #$A0
|
lda #SPACE
|
||||||
- bcc + ;ClearScreen path
|
- bcc + ;ClearScreen path
|
||||||
lda (OPSRC1L), y
|
lda (OPSRC1L), y
|
||||||
+ sta (OPSRC2L), y
|
+ sta (OPSRC2L), y
|
||||||
|
@ -910,6 +926,28 @@ PageReturn
|
||||||
;then select that page
|
;then select that page
|
||||||
|
|
||||||
HandleKeyAddPage
|
HandleKeyAddPage
|
||||||
|
PreventAddPage
|
||||||
|
lda #0 ;self-modified
|
||||||
|
beq + ;page 1 exists already, go directly to add
|
||||||
|
bpl PageReturn ;page 1 doesn't exist and nothing to write
|
||||||
|
|
||||||
|
;Diversi-DOS (not DOS 3.3) has a critical bug when writing to a newly-created file
|
||||||
|
;if the first write occurs beyond the first sector, then no preceding entries are created in the TS list!
|
||||||
|
;instead, it leaves the entries blank, causing read errors when attempting to read earlier content
|
||||||
|
;the disk space is also not reclaimed when deleting the file because the TS list looks empty
|
||||||
|
;to work around this, we detect when we are writing to the file for the first time,
|
||||||
|
;and just force the write to occur before the page is added
|
||||||
|
|
||||||
|
jsr WriteIfDirty2 ;page 1 is ready to write for the first time
|
||||||
|
|
||||||
|
;the problem is that the wrong screen was active at the time that we wrote the initial content
|
||||||
|
;so we have to perform a second write after the screen is scrolled properly
|
||||||
|
;performance is bad, but fortunately it's a one-time thing
|
||||||
|
|
||||||
|
inc WriteIfDirty2 + 1 ;force it to write again
|
||||||
|
+ lda Pages + 1
|
||||||
|
cmp #(99 - 1) ;maximum 99 pages
|
||||||
|
beq PageReturn
|
||||||
jsr ExchangeVirtualBuffer
|
jsr ExchangeVirtualBuffer
|
||||||
sec
|
sec
|
||||||
jsr ClearVirtualBuffer
|
jsr ClearVirtualBuffer
|
||||||
|
@ -972,8 +1010,14 @@ HandleKeyPrevPage
|
||||||
;update header to specify new page count and current page
|
;update header to specify new page count and current page
|
||||||
|
|
||||||
+++ jsr LoadSaveHeader
|
+++ jsr LoadSaveHeader
|
||||||
jsr CloseFile ;work around DiversiDOS bug
|
|
||||||
jsr OpenDataFile ;by close and reopen to flush the write
|
;Diversi-DOS has a critical bug when reading from a just-written sector
|
||||||
|
;IT RETURNS THE ORIGINAL DATA UNLESS YOU CLOSE THE FILE AND RE-OPEN IT
|
||||||
|
;so that's what we do
|
||||||
|
|
||||||
|
jsr CloseFile
|
||||||
|
jsr OpenDataFile
|
||||||
|
|
||||||
dec ReadWriteCmd ;lda #CMDREAD / sta ReadWriteCmd
|
dec ReadWriteCmd ;lda #CMDREAD / sta ReadWriteCmd
|
||||||
lda ReadBuffer
|
lda ReadBuffer
|
||||||
pha
|
pha
|
||||||
|
@ -1013,6 +1057,8 @@ HandleKeyPrevPage
|
||||||
tax
|
tax
|
||||||
jsr SetTextCoords2
|
jsr SetTextCoords2
|
||||||
|
|
||||||
|
;fall through to restore buffer
|
||||||
|
|
||||||
;copy virtual buffer to another virtual buffer
|
;copy virtual buffer to another virtual buffer
|
||||||
;hack existing buffer copy to redirect target,
|
;hack existing buffer copy to redirect target,
|
||||||
;since it copies exactly the size that we want
|
;since it copies exactly the size that we want
|
||||||
|
@ -1020,7 +1066,7 @@ HandleKeyPrevPage
|
||||||
ExchangeVirtualBuffer
|
ExchangeVirtualBuffer
|
||||||
lda #>(TEMPBUFFER - <(LoadSaveStart - LastLine))
|
lda #>(TEMPBUFFER - <(LoadSaveStart - LastLine))
|
||||||
sta ExchangeBankedPatch + 1
|
sta ExchangeBankedPatch + 1
|
||||||
clc ;enable full path even if not DiversiDOS
|
clc ;enable full path even if not Diversi-DOS
|
||||||
jsr ExchangeBanked1 + 1
|
jsr ExchangeBanked1 + 1
|
||||||
lda #>(SWAPBUFFER - <(LoadSaveStart - LastLine))
|
lda #>(SWAPBUFFER - <(LoadSaveStart - LastLine))
|
||||||
sta ExchangeBankedPatch + 1
|
sta ExchangeBankedPatch + 1
|
||||||
|
@ -1032,6 +1078,8 @@ SetPrevPage
|
||||||
lda Pages + 1
|
lda Pages + 1
|
||||||
rts
|
rts
|
||||||
|
|
||||||
|
;turn everything to inverse or normal
|
||||||
|
|
||||||
HandleKeyHighlight
|
HandleKeyHighlight
|
||||||
ldx MyCV + 1
|
ldx MyCV + 1
|
||||||
jsr SetTextCalc
|
jsr SetTextCalc
|
||||||
|
@ -1057,7 +1105,7 @@ HandleKeyHighlight
|
||||||
|
|
||||||
;control range to normal range
|
;control range to normal range
|
||||||
|
|
||||||
cmp #$A0
|
cmp #SPACE
|
||||||
bcs +
|
bcs +
|
||||||
ora #$40
|
ora #$40
|
||||||
|
|
||||||
|
@ -1227,7 +1275,7 @@ SeekReadWrite ;also writes, called with X=page to read
|
||||||
sta SaveCH
|
sta SaveCH
|
||||||
lda MyCV + 1
|
lda MyCV + 1
|
||||||
sta SaveCV
|
sta SaveCV
|
||||||
jsr WriteFile ;also ReadFile
|
jsr WriteFileBuff ;also used by ReadFile
|
||||||
|
|
||||||
CloseFile
|
CloseFile
|
||||||
jsr DOSMLI
|
jsr DOSMLI
|
||||||
|
@ -1240,6 +1288,7 @@ OpenReturn
|
||||||
rts
|
rts
|
||||||
|
|
||||||
;open the file, load/save the page count and current page
|
;open the file, load/save the page count and current page
|
||||||
|
;leaves the file open for additional accesses
|
||||||
|
|
||||||
LoadSaveHeader
|
LoadSaveHeader
|
||||||
jsr OpenDataFile
|
jsr OpenDataFile
|
||||||
|
@ -1254,8 +1303,124 @@ LoadSaveHeader
|
||||||
sta SaveCH
|
sta SaveCH
|
||||||
lda CurPage + 1
|
lda CurPage + 1
|
||||||
sta SaveCV
|
sta SaveCV
|
||||||
|
|
||||||
|
WriteFileBuff
|
||||||
|
lda ReadWriteCmd
|
||||||
|
lsr ;read has bit 0 set, write does not
|
||||||
|
bcs JumpFileIO
|
||||||
|
|
||||||
|
PatchDiversi
|
||||||
|
bcs InitDiversiWrite ;self-modified to BCC if Diversi-DOS
|
||||||
|
|
||||||
|
;write size must be one less than required value because of course it must
|
||||||
|
|
||||||
|
AdjustWriteSize
|
||||||
|
lda WriteSize
|
||||||
|
bne +
|
||||||
|
dec WriteSize + 1
|
||||||
|
+ dec WriteSize
|
||||||
|
|
||||||
|
JumpFileIO
|
||||||
jmp WriteFile ;also ReadFile
|
jmp WriteFile ;also ReadFile
|
||||||
|
|
||||||
|
;Diversi-DOS (not DOS 3.3) has a critical bug when writing within a sector
|
||||||
|
;the bug is that it does not read the original sector and then replace the data before writing
|
||||||
|
;instead, it uses the last-read sector to supply the content to replace!
|
||||||
|
;to work around this, we detect when we are writing within a sector
|
||||||
|
;that can be either the write offset is non-zero, and/or the low size is non-zero
|
||||||
|
;in either case, we perform as expected: read the original sector, replace the content, write the sector
|
||||||
|
|
||||||
|
InitDiversiWrite
|
||||||
|
jsr ExchangeSectorBuffer
|
||||||
|
lda WriteSize
|
||||||
|
sta WriteSizeLow + 1
|
||||||
|
lda WriteSize + 1
|
||||||
|
sta WriteSizeHigh + 1
|
||||||
|
lda WriteOffset
|
||||||
|
sta DiversiWriteBuffer + 1
|
||||||
|
!if (SWAPSIZEALIGNED = 0) {
|
||||||
|
dec WriteBuffer + 1
|
||||||
|
}
|
||||||
|
lda #<LoadSaveStart
|
||||||
|
sta DiversiReadBuffer + 1
|
||||||
|
lda #>LoadSaveStart
|
||||||
|
sta DiversiReadBuffer + 2
|
||||||
|
|
||||||
|
;disable swapping temporarily
|
||||||
|
|
||||||
|
lda #$60 ;RTS
|
||||||
|
sta ExchangeBanked1
|
||||||
|
|
||||||
|
;read the existing sector
|
||||||
|
|
||||||
|
FixDiversiWrite
|
||||||
|
ldx #0
|
||||||
|
stx ReadSize
|
||||||
|
stx ReadOffset
|
||||||
|
inx
|
||||||
|
stx ReadSize + 1
|
||||||
|
dec ReadWriteCmd ;lda #CMDREAD / sta ReadWriteCmd
|
||||||
|
jsr ReadFileNoXchg
|
||||||
|
inc ReadWriteCmd ;lda #CMDWRITE / sta ReadWriteCmd
|
||||||
|
|
||||||
|
;replace existing content
|
||||||
|
;slow copy operation, but it works
|
||||||
|
|
||||||
|
DiversiReadBuffer
|
||||||
|
lda $34f3 ;self-modified
|
||||||
|
inc DiversiReadBuffer + 1
|
||||||
|
bne DiversiWriteBuffer
|
||||||
|
inc DiversiReadBuffer + 2
|
||||||
|
|
||||||
|
DiversiWriteBuffer
|
||||||
|
sta (SWAPBUFFER - <(LoadSaveStart - LastLine)) and $FF00
|
||||||
|
;low byte is self-modified
|
||||||
|
ldx WriteSizeLow + 1
|
||||||
|
bne +
|
||||||
|
dec WriteSizeHigh + 1
|
||||||
|
+ dex
|
||||||
|
stx WriteSizeLow + 1
|
||||||
|
txa
|
||||||
|
ora WriteSizeHigh + 1
|
||||||
|
beq +
|
||||||
|
inc DiversiWriteBuffer + 1
|
||||||
|
bne DiversiReadBuffer
|
||||||
|
|
||||||
|
;reaching this path means that we copy an entire sector on next pass
|
||||||
|
;but it happens only twice currently, which seems to be acceptable
|
||||||
|
;and it reduces the complexity of the code
|
||||||
|
+
|
||||||
|
;write new sector
|
||||||
|
|
||||||
|
jsr AdjustWriteSize
|
||||||
|
inc WriteOffset + 1
|
||||||
|
|
||||||
|
WriteSizeLow
|
||||||
|
lda #"Q" ;self-modified
|
||||||
|
|
||||||
|
WriteSizeHigh
|
||||||
|
ora #"Q" ;self-modified
|
||||||
|
bne FixDiversiWrite
|
||||||
|
|
||||||
|
;re-enable swapping
|
||||||
|
|
||||||
|
!if (SWAPSIZEALIGNED = 0) {
|
||||||
|
inc WriteBuffer + 1
|
||||||
|
}
|
||||||
|
lda #$18 ;CLC
|
||||||
|
sta ExchangeBanked1
|
||||||
|
|
||||||
|
;fall through to restore buffer
|
||||||
|
|
||||||
|
ExchangeSectorBuffer
|
||||||
|
lda #>SECTORBUFFER
|
||||||
|
sta OPDST1H
|
||||||
|
lda #0
|
||||||
|
tax
|
||||||
|
tay
|
||||||
|
sta OPSRC1L
|
||||||
|
jmp ExchangeBankedSet
|
||||||
|
|
||||||
TextCalcHi
|
TextCalcHi
|
||||||
!byte $04, $04, $05, $05, $06, $06, $07, $07
|
!byte $04, $04, $05, $05, $06, $06, $07, $07
|
||||||
!byte $04, $04, $05, $05, $06, $06, $07, $07
|
!byte $04, $04, $05, $05, $06, $06, $07, $07
|
||||||
|
@ -1334,33 +1499,41 @@ SaveCV
|
||||||
;is the design flaw in the scrolling or the reading? you decide.
|
;is the design flaw in the scrolling or the reading? you decide.
|
||||||
|
|
||||||
FirstLine ;lines are stored sequentially, not like text page in memory
|
FirstLine ;lines are stored sequentially, not like text page in memory
|
||||||
!fill WIDTH, $A0
|
!fill WIDTH, SPACE
|
||||||
|
|
||||||
SecondLine
|
SecondLine
|
||||||
!if >SecondLine != >LoadSaveStart {
|
!if (>SecondLine != >LoadSaveStart) {
|
||||||
!error "first two lines of text buffer must not cross a page"
|
!error "first two lines of text buffer must not cross a page"
|
||||||
}
|
}
|
||||||
!fill WIDTH * 7, $A0
|
!fill WIDTH * 7, SPACE
|
||||||
!text " 4LIVE by 4am && qkumba "
|
!text " 4LIVE by 4am && qkumba "
|
||||||
!fill WIDTH, $A0
|
!fill WIDTH, SPACE
|
||||||
!text " Revision 03 / Serial number 161123 "
|
!text " Revision 03 / Serial number 161123 "
|
||||||
!fill WIDTH * 2, $A0
|
!fill WIDTH * 2, SPACE
|
||||||
!text " https://github.com/a2-4am/4live "
|
!text " https://github.com/a2-4am/4live "
|
||||||
!fill WIDTH * 9, $A0
|
!fill WIDTH * 9, SPACE
|
||||||
|
|
||||||
LoadSaveEnd
|
LoadSaveEnd
|
||||||
!fill (WIDTH - 5), $20
|
!fill (WIDTH - 5), $20
|
||||||
!text "4LIVE"
|
!text "4LIVE"
|
||||||
|
|
||||||
LastLine
|
LastLine
|
||||||
!fill WIDTH, $A0
|
!fill WIDTH, SPACE
|
||||||
|
|
||||||
TEMPBUFFER=(*+255) and not 255
|
TEMPBUFFER=(*+255) and not 255
|
||||||
!if (TEMPBUFFER>$DC00) {
|
!ifdef PASS2 {
|
||||||
!error "banked code is too large, ends at ", *, ", ", *-$DC00, " bytes too many"
|
!if (TEMPBUFFER > $DB00) {
|
||||||
|
!error "banked code is too large, ends at ", *, ", ", *-$DB00, " bytes too many"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
!if VERBOSE=1 {
|
SECTORBUFFER=TEMPBUFFER+$400
|
||||||
!warn "banked code end=", *, ", data end=", TEMPBUFFER+$3FF, ", bytes free=", $DC00-*
|
!ifdef PASS2 {
|
||||||
|
!if (VERBOSE = 1) {
|
||||||
|
!warn "banked code end=", *, ", data end=", SECTORBUFFER+$FF, ", bytes free=", $DB00-*
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
;define pass-dependent label to reduce output noise
|
||||||
|
!set PASS2 = 1
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
BankedCopyEnd
|
BankedCopyEnd
|
||||||
|
|
Loading…
Reference in New Issue
Block a user