Fix SAVE512/LOAD512 page-wrap losing a marker-stripped offset remainder

sv512_advance/lv512_advance hardcoded the post-wrap offset to exactly
#4000, discarding whatever the add overshot #8000 by. Invisible for
page-aligned transfers, but create_filename's ".EXT"-marker handling
(strips a leading 4-byte ".TRD"/".SCL"/etc marker some archive
downloads carry) starts thread.adress a few bytes past #4000, so the
reset silently dropped that offset on the first page wrap only,
splicing 4 stray bytes into the saved file and losing its real last 4
bytes. Fixed by subtracting #40 from H instead of resetting it (CP
doesn't touch A, so this costs zero extra bytes). Confirmed via a
direct RAM-vs-disk MD5 comparison on a 640KB, 40-page-boundary
download: byte-for-byte identical after the fix.
This commit is contained in:
2026-09-09 23:15:13 +03:00
parent c3c5c7dccc
commit 21d4c3361e
+23 -4
View File
@@ -3938,8 +3938,9 @@ lv512_advance ld hl,(lv512_off)
ld a,h ld a,h
cp #80 cp #80
jr c,lv512_nowrap jr c,lv512_nowrap
ld hl,#4000 sub #40 ; preserve the overflow remainder instead
ld a,(lv512_page) ld h,a ; of resetting to exactly #4000 -- see
ld a,(lv512_page) ; sv512_advance's own comment below
inc a inc a
ld (lv512_page),a ld (lv512_page),a
lv512_nowrap ld (lv512_off),hl lv512_nowrap ld (lv512_off),hl
@@ -3960,14 +3961,32 @@ lv512_eoc ld a,(lv512_page)
;--- sv512_advance: sv512_off += 512, wrapping to sv512_page+1 (back to ;--- sv512_advance: sv512_off += 512, wrapping to sv512_page+1 (back to
;--- slot-1 offset 0x4000, NOT 0 -- see header comment on the real ;--- slot-1 offset 0x4000, NOT 0 -- see header comment on the real
;--- 0x4000-0x7FFF convention) once it would leave the 0x4000-0x7FFF ;--- 0x4000-0x7FFF convention) once it would leave the 0x4000-0x7FFF
;--- range, i.e. reach 0x8000 (one page = exactly 32 blocks). --- ;--- range, i.e. reach 0x8000 (one page = exactly 32 blocks).
;---
;--- The wrap subtracts #40 from H (preserving whatever this add
;--- overshot #8000 by) instead of hardcoding H:=#40 -- CP doesn't
;--- touch A, so A still holds the pre-wrap H here, free to reuse.
;--- create_filename's ".EXT"-marker handling can start thread.adress
;--- (and so sv512_off, on the very first call) a few bytes PAST
;--- #4000 (skipping a leading ".TRD"/".SCL"/etc marker some servers
;--- prepend to the real payload) -- a hardcoded reset to exactly
;--- #4000 silently drops that remainder on the FIRST page wrap only
;--- (every wrap after that starts page-aligned, so the bug is
;--- invisible again), splicing 4 stray bytes from the tail of the
;--- block just written into the next one and losing the file's real
;--- last 4 bytes. Confirmed via a live memory-vs-disk diff on a real
;--- multi-page download (2026-09-09): RAM was correct throughout,
;--- only the on-disk copy had the extra bytes -- see
;--- [[project-zifi-custom-sd-driver]]. Same fix applied to
;--- lv512_advance above (LOAD512's own copy of this logic). ---
sv512_advance ld hl,(sv512_off) sv512_advance ld hl,(sv512_off)
ld de,512 ld de,512
add hl,de add hl,de
ld a,h ld a,h
cp #80 cp #80
jr c,sv512_nowrap jr c,sv512_nowrap
ld hl,#4000 sub #40
ld h,a
ld a,(sv512_page) ld a,(sv512_page)
inc a inc a
ld (sv512_page),a ld (sv512_page),a