1 |
|
#define MICRODISC_LOADER |
2 |
#include "disk_info.h" |
#include "disk_info.h" |
3 |
|
|
|
|
|
4 |
#define COLOR(color) pha:lda #16+(color&7):sta $bb80+40*27:pla |
#define COLOR(color) pha:lda #16+(color&7):sta $bb80+40*27:pla |
5 |
#define STOP(color) pha:lda #16+(color&7):sta $bb80+40*27:jmp *:pla |
#define STOP(color) pha:lda #16+(color&7):sta $bb80+40*27:jmp *:pla |
6 |
|
|
13 |
current_track .dsb 1 ; Index of the track being loaded |
current_track .dsb 1 ; Index of the track being loaded |
14 |
current_sector .dsb 1 ; Index of the sector being loaded |
current_sector .dsb 1 ; Index of the sector being loaded |
15 |
current_side .dsb 1 ; Has the bit 4 set to 0 or 1 to be used as a mask on the Microdisc control register (other bits have to be set to zero) |
current_side .dsb 1 ; Has the bit 4 set to 0 or 1 to be used as a mask on the Microdisc control register (other bits have to be set to zero) |
16 |
|
irq_save_a .dsb 1 ; To preserve the accumulator value in the IRQ code |
17 |
|
|
18 |
|
; Unpack test |
19 |
|
ptr_source .dsb 2 ; Packed source data adress |
20 |
|
ptr_destination .dsb 2 ; Destination adress where we depack |
21 |
|
ptr_destination_end .dsb 2 ; Point on the end of the depacked stuff |
22 |
|
ptr_source_back .dsb 2 ; Temporary used to hold a pointer on depacked stuff |
23 |
|
offset .dsb 2 |
24 |
|
mask_value .dsb 1 |
25 |
|
nb_dst .dsb 1 |
26 |
|
|
27 |
.text |
.text |
28 |
|
|
29 |
; FFF0 |
*=location_loader |
30 |
; FFF1 |
|
|
; FFF2 |
|
|
; FFF3 |
|
|
; FFF4 |
|
|
; FFF5 |
|
|
; FFF6 |
|
|
; FFF7 |
|
|
; FFF8 |
|
|
; FFF9 - Test Overlay |
|
|
; |
|
|
; FFFA - NMI Vector (Usually points to $0247) |
|
|
; FFFB |
|
|
; |
|
|
; FFFC - RESET Vector (Usually points to $F88F) |
|
|
; FFFD |
|
31 |
; |
; |
32 |
; FFFE - IRQ Vector (Normally points to $0244) |
; This is called from the bootsectors with the X register containing the fdc offset; |
33 |
; FFFF |
; +$00 = Microdisc |
34 |
|
; +$e4 = Jasmin |
35 |
; |
; |
36 |
*=location_loader |
Initialize |
37 |
|
jmp StartUp |
38 |
|
|
39 |
|
#define LOADER |
40 |
|
|
41 |
Initialize |
; This file is generated by the floppy builder |
42 |
jsr SetUpIrqHandlers |
#include "floppy_description.h" |
|
jsr SoftHiresWithCopyCharset |
|
|
|
|
|
; Load the picture |
|
|
ldx #0 |
|
|
jsr LoadData |
|
|
;STOP(1) |
|
|
jsr ExecuteData |
|
|
|
|
|
|
|
|
; Load the rasters crap |
|
|
;STOP(1) |
|
|
;ldx #1 |
|
|
;jsr LoadData |
|
|
;jsr SoftHires ; Delete the screen |
|
|
;STOP(2) |
|
|
;jsr ExecuteData |
|
|
|
|
|
; Load the demo |
|
|
jsr SoftHires ; Delete the screen |
|
|
;STOP(1) |
|
|
ldx #2 |
|
|
jsr LoadData |
|
|
;STOP(2) |
|
|
jsr ExecuteData |
|
|
|
|
|
; |
|
|
; End of demo - Just stay there doing nothing |
|
|
; |
|
|
sei |
|
|
.( |
|
|
loop |
|
|
jmp loop |
|
|
.) |
|
|
|
|
|
|
|
|
ClearZeroPage |
|
|
.( |
|
|
lda #0 |
|
|
tax |
|
|
loop |
|
|
sta $00,x |
|
|
dex |
|
|
bne loop |
|
|
rts |
|
|
.) |
|
43 |
|
|
44 |
|
; Some local variables we need |
45 |
SetUpIrqHandlers |
fdc_register_offset .dsb 1 |
|
sei |
|
46 |
|
|
47 |
; Set-up a safe irq that does nothing - Good to avoid crashes |
StartUp |
48 |
lda #<IrqDoNothing |
stx fdc_register_offset ; Store the FDC offset value |
|
sta $fffa |
|
|
sta $fffc |
|
|
lda #>IrqDoNothing |
|
|
sta $fffb |
|
|
sta $fffd |
|
|
|
|
|
ldy #<IrqHandler |
|
|
lda #>IrqHandler |
|
|
sty $fffe |
|
|
sta $ffff |
|
|
|
|
|
; Make sure the microdisc IRQ is disabled |
|
|
jsr WaitCompletion |
|
|
|
|
|
lda #%10000100 ; Disable the FDC (Eprom select + FDC Interrupt request) |
|
|
sta MICRODISC |
|
|
|
|
|
rts |
|
49 |
|
|
50 |
|
; Load the slideshow |
51 |
SaveA .byt 0 |
ldx #LOADER_INTRO_PART |
52 |
|
jsr LoadAndRun |
53 |
|
|
54 |
|
ldx #LOADER_MAIN_PART |
55 |
|
jsr LoadAndRun |
56 |
|
|
57 |
|
LoadAndRun |
58 |
|
jsr LoadData |
59 |
|
|
60 |
|
; Give control to the application and hope it knows what to do |
61 |
|
__auto_execute_address |
62 |
|
jmp $a000 |
63 |
|
|
64 |
|
|
65 |
IrqHandler |
IrqHandler |
66 |
sta SaveA |
sta irq_save_a |
67 |
pla |
pla |
68 |
|
pha |
69 |
and #%00010000 ; Check the saved B flag to detect a BRK |
and #%00010000 ; Check the saved B flag to detect a BRK |
70 |
bne from_brk |
bne from_brk |
71 |
|
|
72 |
from_irq |
from_irq |
73 |
lda SaveA |
#ifdef LOADER_SHOW_DEBUGINFO |
74 |
pha |
lda $bfdf |
75 |
|
eor #1 |
76 |
|
ora #16 |
77 |
|
sta $bfdf |
78 |
|
#endif |
79 |
|
lda irq_save_a |
80 |
|
bit $304 |
81 |
IrqDoNothing |
IrqDoNothing |
82 |
rti |
rti |
83 |
|
|
89 |
nop |
nop |
90 |
lda #16+2 |
lda #16+2 |
91 |
sta $bb80+40*27 |
sta $bb80+40*27 |
92 |
jmp from_brk |
bne from_brk |
93 |
|
|
94 |
|
|
95 |
|
|
|
HexData .byt "0123456789ABCDEF" |
|
|
|
|
96 |
|
|
97 |
; X=File index |
; X=File index |
98 |
|
; A=Low |
99 |
|
; Y=High |
100 |
|
SetLoadAddress |
101 |
|
sta FileLoadAdressLow,x |
102 |
|
tya |
103 |
|
sta FileLoadAdressHigh,x |
104 |
|
rts |
105 |
|
|
106 |
|
|
107 |
|
; X=File index |
108 |
LoadData |
LoadData |
109 |
|
;STOP(2) |
110 |
|
|
111 |
|
; We have to start somewhere no matter what, compressed or not |
112 |
|
jsr StartReadOperation |
113 |
|
|
114 |
|
; Now at this stage we have to check if the data is compressed or not |
115 |
|
lda FileStoredSizeLow,x |
116 |
|
cmp FileSizeLow,x |
117 |
|
bne LoadCompressedData |
118 |
|
|
119 |
|
lda FileStoredSizeHigh,x |
120 |
|
cmp FileSizeHigh,x |
121 |
|
bne LoadCompressedData |
122 |
|
|
123 |
|
LoadUncompressedData |
124 |
|
|
125 |
|
; |
126 |
|
; Loop to read all the sectors |
127 |
|
; |
128 |
|
read_sectors_loop |
129 |
|
jsr ReadNextSector |
130 |
|
|
131 |
|
; Try to let time to an IRQ to play, and during that time copy the sector to the final location |
132 |
|
cli |
133 |
|
|
134 |
|
ldy #0 |
135 |
|
loop_copy |
136 |
|
lda $200,y ; Load the byte from page 2 |
137 |
|
__auto_write_address |
138 |
|
sta $c000,y ; Store it to the final location |
139 |
|
iny |
140 |
|
bne loop_copy |
141 |
|
|
142 |
|
nop |
143 |
|
nop |
144 |
sei |
sei |
145 |
|
|
146 |
|
; Next sector |
147 |
|
inc __auto_write_address+2 |
148 |
|
dec sectors_to_go |
149 |
|
bne read_sectors_loop |
150 |
|
|
151 |
|
; Data successfully loaded (we hope), so we restore the interrupts |
152 |
|
cli |
153 |
|
rts |
154 |
|
|
155 |
|
|
156 |
|
LoadCompressedData |
157 |
|
clc |
158 |
|
lda FileLoadAdressLow,x |
159 |
|
sta ptr_destination+0 |
160 |
|
adc FileSizeLow,x |
161 |
|
sta ptr_destination_end+0 |
162 |
|
|
163 |
|
lda FileLoadAdressHigh,x |
164 |
|
sta ptr_destination+1 |
165 |
|
adc FileSizeHigh,x |
166 |
|
sta ptr_destination_end+1 |
167 |
|
|
168 |
|
;STOP(2) |
169 |
|
|
170 |
|
jsr UnpackData |
171 |
|
cli |
172 |
|
rts |
173 |
|
|
174 |
|
|
175 |
|
StartReadOperation |
176 |
|
sei |
177 |
|
|
178 |
|
ldy fdc_register_offset |
179 |
|
|
180 |
|
; Make sure the microdisc IRQ is disabled |
181 |
|
jsr WaitCompletion |
182 |
|
|
183 |
|
lda #%10000100 ; Disable the FDC (Eprom select + FDC Interrupt request) |
184 |
|
sta FDC_flags,y |
185 |
|
|
186 |
|
;jsr WaitCompletion |
187 |
|
|
188 |
|
; |
189 |
|
; Setup, we use the table to find out where the file is located on the floppy, |
190 |
|
; where to write it in memory, and how large it is. |
191 |
|
; |
192 |
lda FileLoadAdressHigh,x |
lda FileLoadAdressHigh,x |
193 |
sta __auto_execute_address+2 |
sta __auto_execute_address+2 |
194 |
sta __auto_write_address+2 |
sta __auto_write_address+2 |
195 |
|
|
|
|
|
196 |
lda FileLoadAdressLow,x |
lda FileLoadAdressLow,x |
197 |
sta __auto_execute_address+1 |
sta __auto_execute_address+1 |
198 |
sta __auto_write_address+1 |
sta __auto_write_address+1 |
199 |
|
|
200 |
|
; Starting track |
201 |
; Start on side 0 |
ldy #%00000000 ; Side 0 |
202 |
lda #0 |
lda FileStartTrack,x ; If the track id is larger than 128, it means it is on the other side of the floppy |
203 |
sta current_side |
bpl first_side |
204 |
|
; The file starts on the second side |
205 |
; Starting track |
ldy #FDC_Flag_DiscSide ; Side 1 |
206 |
lda FileStartTrack,x |
and #%01111111 ; Mask out the extra bit |
207 |
sta current_track |
first_side |
208 |
|
sty current_side |
|
; If >128 it means it is on the other side |
|
|
sec |
|
|
sbc #128 |
|
|
bmi same_side |
|
209 |
sta current_track |
sta current_track |
210 |
|
|
211 |
lda #%00010000 |
ldy fdc_register_offset |
|
sta current_side |
|
|
same_side |
|
212 |
|
|
213 |
; First sector |
; First sector |
214 |
lda FileStartSector,x |
lda FileStartSector,x |
215 |
sta current_sector |
sta current_sector |
216 |
|
|
217 |
|
; FileSizeLow/FileSizeHigh |
218 |
; Number of sectors to load |
; Number of sectors to load |
219 |
lda FileSectorCount,x |
.( |
220 |
|
lda FileStoredSizeHigh,x |
221 |
sta sectors_to_go |
sta sectors_to_go |
222 |
|
lda FileStoredSizeLow,x |
223 |
; Loop to read all the sectors |
beq skip |
224 |
read_sectors_loop |
inc sectors_to_go |
225 |
|
skip |
226 |
|
.) |
227 |
|
rts |
228 |
|
|
229 |
|
|
230 |
|
ReadNextSector |
231 |
|
cli |
232 |
|
|
233 |
|
ldy fdc_register_offset |
234 |
|
|
235 |
; Check if we have reached the end of the track |
; Check if we have reached the end of the track |
236 |
lda current_sector |
lda current_sector |
237 |
|
cmp #FLOPPY_SECTOR_PER_TRACK+1 |
|
cmp #17+1 |
|
238 |
bne same_track |
bne same_track |
239 |
|
|
240 |
; Next track |
; Next track |
241 |
inc current_track |
inc current_track |
242 |
|
lda current_track |
243 |
|
cmp #FLOPPY_TRACK_NUMBER |
244 |
|
bne stay_on_same_side |
245 |
|
|
246 |
|
; Reset to the first track on the other side |
247 |
|
lda #0 |
248 |
|
sta current_track |
249 |
|
|
250 |
|
sei |
251 |
|
|
252 |
|
lda #FDC_Flag_DiscSide |
253 |
|
sta current_side |
254 |
|
stay_on_same_side |
255 |
|
|
256 |
|
|
257 |
; Reset the sector position |
; Reset the sector position |
258 |
lda #1 |
lda #1 |
259 |
sta current_sector |
sta current_sector |
260 |
same_track |
same_track |
261 |
|
|
262 |
|
#ifdef LOADER_SHOW_DEBUGINFO |
263 |
; Display debug info |
; Display debug info |
264 |
;jsr DisplayPosition |
cli |
265 |
|
jsr DisplayPosition |
266 |
|
sei |
267 |
|
#else |
268 |
|
cli |
269 |
|
jsr WaitCommand |
270 |
|
sei |
271 |
|
#endif |
272 |
|
|
273 |
lda current_sector |
lda current_sector |
274 |
sta FDC_sector_register |
sta FDC_sector_register,y |
275 |
inc current_sector |
inc current_sector |
276 |
|
|
277 |
; Check if the drive is on the correct track |
; Check if the drive is on the correct track |
278 |
lda current_track |
lda current_track |
279 |
cmp FDC_track_register |
cmp FDC_track_register,y |
280 |
beq stay_on_the_track |
beq stay_on_the_track |
281 |
|
|
282 |
; Set the new track |
; Set the new track |
283 |
sta FDC_data |
sta FDC_data,y |
284 |
|
|
285 |
lda #CMD_Seek |
lda #CMD_Seek |
286 |
sta FDC_command_register |
sta FDC_command_register,y |
287 |
jsr WaitCompletion |
jsr WaitCompletion |
288 |
|
|
289 |
|
stay_on_the_track |
290 |
lda #%10000100 ; on force les le Microdisk en side0, drive A ... Set le bit de données !!! |
lda #%10000100 ; on force les le Microdisk en side0, drive A ... Set le bit de données !!! |
291 |
ora current_side |
ora current_side |
292 |
sta MICRODISC |
sta FDC_flags,y |
293 |
|
|
|
stay_on_the_track |
|
294 |
lda #CMD_ReadSector |
lda #CMD_ReadSector |
295 |
sta FDC_command_register |
sta FDC_command_register,y |
|
|
|
296 |
|
|
297 |
ldy #wait_status_floppy |
;cli |
298 |
waitcommand |
jsr WaitCommand |
299 |
nop |
;sei |
|
nop |
|
|
dey |
|
|
bne waitcommand |
|
300 |
|
|
301 |
; |
; |
302 |
; Read the sector data |
; Read the sector data |
303 |
; |
; |
304 |
ldy #0 |
ldx #0 |
305 |
microdisc_read_data |
microdisc_read_data |
306 |
lda $0318 |
lda $0318 |
307 |
bmi microdisc_read_data |
bmi microdisc_read_data |
308 |
|
|
309 |
lda $313 |
lda FDC_data,y |
310 |
__auto_write_address |
sta $200,x ; Store the byte in page 2 |
311 |
sta $c000,y |
inx |
|
iny |
|
312 |
|
|
313 |
bne microdisc_read_data |
bne microdisc_read_data |
314 |
|
|
315 |
lda FDC_status_register |
lda FDC_status_register,y |
316 |
and #$1C |
and #$1C |
317 |
|
|
318 |
; Next sector |
jsr WaitCompletion |
319 |
inc __auto_write_address+2 |
cli |
|
dec sectors_to_go |
|
|
bne read_sectors_loop |
|
|
|
|
|
; Data successfully loaded (we hope) |
|
320 |
rts |
rts |
321 |
|
|
322 |
ExecuteData |
WaitCommand |
323 |
jsr SetUpIrqHandlers |
ldx #wait_status_floppy |
324 |
jsr ClearZeroPage |
waitcommand |
325 |
__auto_execute_address |
nop |
326 |
jsr $a000 |
nop |
327 |
jsr SetUpIrqHandlers |
dex |
328 |
|
bne waitcommand |
329 |
rts |
rts |
330 |
|
|
331 |
|
WaitCompletion |
332 |
|
txa |
333 |
|
pha |
334 |
|
|
335 |
|
php |
336 |
|
sei |
337 |
|
nop |
338 |
|
nop |
339 |
|
nop |
340 |
|
|
341 |
WaitCompletion |
ldx #4 |
|
ldy #4 |
|
342 |
r_wait_completion |
r_wait_completion |
343 |
dey |
dex |
344 |
bne r_wait_completion |
bne r_wait_completion |
345 |
|
plp |
346 |
|
|
347 |
r2_wait_completion |
r2_wait_completion |
348 |
lda FDC_status_register |
lda FDC_status_register,y |
349 |
lsr |
lsr |
350 |
bcs r2_wait_completion |
bcs r2_wait_completion |
351 |
asl |
|
352 |
|
;asl |
353 |
|
pla |
354 |
|
tax |
355 |
rts |
rts |
356 |
|
|
357 |
|
#ifdef LOADER_SHOW_DEBUGINFO |
358 |
|
HexData .byt "0123456789ABCDEF" |
359 |
|
|
360 |
DisplayPosition |
DisplayPosition |
361 |
.( |
.( |
362 |
lda current_side |
lda current_side |
407 |
;jsr WaitLoop |
;jsr WaitLoop |
408 |
rts |
rts |
409 |
.) |
.) |
410 |
|
#endif |
|
|
|
|
WaitLoop |
|
|
jsr WaitLoop2 |
|
|
jsr WaitLoop2 |
|
|
jsr WaitLoop2 |
|
|
jsr WaitLoop2 |
|
|
rts |
|
|
|
|
|
WaitLoop2 |
|
|
jsr WaitLoop3 |
|
|
jsr WaitLoop3 |
|
|
jsr WaitLoop3 |
|
|
jsr WaitLoop3 |
|
|
rts |
|
|
|
|
|
WaitLoop3 |
|
|
jsr WaitLoop4 |
|
|
jsr WaitLoop4 |
|
|
jsr WaitLoop4 |
|
|
jsr WaitLoop4 |
|
|
rts |
|
411 |
|
|
412 |
WaitLoop4 |
|
413 |
.( |
GetNextByte |
414 |
ldx #0 |
php |
415 |
loop |
lda __fetchByte+1 |
416 |
|
bne __fetchByte |
417 |
nop |
nop |
418 |
nop |
nop |
419 |
nop |
nop |
420 |
dex |
nop |
421 |
bne loop |
sei |
422 |
rts |
jsr ReadNextSector |
423 |
.) |
nop |
424 |
|
nop |
425 |
|
nop |
426 |
SoftHiresWithCopyCharset |
nop |
427 |
LDY #$00 ;COPY CHARSET |
cli |
428 |
HM_03 |
ldx #0 |
429 |
LDA $B500,Y |
ldy #0 |
430 |
STA $9900,Y |
__fetchByte |
431 |
LDA $B600,Y |
lda $200 |
432 |
STA $9A00,Y |
inc __fetchByte+1 |
433 |
LDA $B700,Y |
plp |
434 |
STA $9B00,Y |
rts |
|
LDA $B900,Y |
|
|
STA $9D00,Y |
|
|
LDA $BA00,Y |
|
|
STA $9E00,Y |
|
|
LDA $BB00,Y |
|
|
STA $9F00,Y |
|
|
DEY |
|
|
BNE HM_03 |
|
|
SoftHires |
|
|
LDA #$A0 ;CLEAR DOWN ALL MEMORY AREA WITH ZERO |
|
|
STA $01 |
|
|
LDA #$00 |
|
|
STA $00 |
|
|
LDX #$20 |
|
|
HM_01 STA ($00),Y |
|
|
INY |
|
|
BNE HM_01 |
|
|
INC $01 |
|
|
DEX |
|
|
BNE HM_01 |
|
|
LDA #30 ;WRITE HIRES SWITCH |
|
|
STA $BF40 |
|
|
LDA #$A0 ;CLEAR HIRES WITH #$40 |
|
|
STA $01 |
|
|
LDX #$20 |
|
|
LDX #64 |
|
|
HM_04 |
|
|
LDY #124 |
|
|
HM_05 |
|
|
LDA #$40 |
|
|
STA ($00),Y |
|
|
DEY |
|
|
BPL HM_05 |
|
|
LDA $00 |
|
|
ADC #125 |
|
|
STA $00 |
|
|
BCC HM_02 |
|
|
INC $01 |
|
|
HM_02 DEX |
|
|
BNE HM_04 |
|
|
RTS |
|
435 |
|
|
436 |
|
|
437 |
|
|
438 |
|
; void file_unpack(void *ptr_dst,void *ptr_src) |
439 |
|
|
440 |
|
; Need to be called with valid values in: |
441 |
|
; ptr_destination |
442 |
|
; ptr_source |
443 |
|
; ptr_destination_end (Destination + size) |
444 |
|
UnpackData |
445 |
|
;jmp UnpackData |
446 |
|
.( |
447 |
|
cli |
448 |
|
|
449 |
|
; Initialise variables |
450 |
|
; We try to keep "y" null during all the code, |
451 |
|
; so the block copy routine has to be sure that |
452 |
|
; y is null on exit |
453 |
|
ldy #0 |
454 |
|
sty __fetchByte+1 |
455 |
|
lda #1 |
456 |
|
sta mask_value |
457 |
|
|
458 |
|
unpack_loop |
459 |
|
; Handle bit mask |
460 |
|
lsr mask_value |
461 |
|
bne end_reload_mask |
462 |
|
|
463 |
|
jsr GetNextByte ; Read from source stream |
464 |
|
|
465 |
|
ror |
466 |
|
sta mask_value |
467 |
|
end_reload_mask |
468 |
|
bcc back_copy |
469 |
|
|
470 |
|
write_byte |
471 |
|
; Copy one byte from the source stream |
472 |
|
jsr GetNextByte ; Read from source stream |
473 |
|
sta (ptr_destination),y |
474 |
|
|
475 |
|
lda #1 |
476 |
|
sta nb_dst |
477 |
|
|
478 |
|
|
479 |
|
|
480 |
|
_UnpackEndLoop |
481 |
|
;// We increase the current destination pointer, |
482 |
|
;// by a given value, white checking if we reach |
483 |
|
;// the end of the buffer. |
484 |
|
clc |
485 |
|
lda ptr_destination |
486 |
|
adc nb_dst |
487 |
|
sta ptr_destination |
488 |
|
|
489 |
|
.( |
490 |
|
bcc skip |
491 |
|
inc ptr_destination+1 |
492 |
|
skip |
493 |
|
.) |
494 |
|
cmp ptr_destination_end |
495 |
|
lda ptr_destination+1 |
496 |
|
sbc ptr_destination_end+1 |
497 |
|
bcc unpack_loop |
498 |
|
rts |
499 |
|
|
500 |
|
|
501 |
#include<loader.cod> |
back_copy |
502 |
|
;BreakPoint jmp BreakPoint |
503 |
|
; Copy a number of bytes from the already unpacked stream |
504 |
|
; Here we know that y is null. So no need for clearing it. |
505 |
|
; Just be sure it's still null at the end. |
506 |
|
; At this point, the source pointer points to a two byte value that actually contains a 4 bits counter, and a 12 bit offset to point back into the depacked stream. |
507 |
|
; The counter is in the 4 high order bits. |
508 |
|
;clc <== No need, since we access this routie from a BCC |
509 |
|
jsr GetNextByte ; Read from source stream |
510 |
|
adc #1 |
511 |
|
sta offset |
512 |
|
jsr GetNextByte ; Read from source stream |
513 |
|
tax |
514 |
|
and #$0f |
515 |
|
adc #0 |
516 |
|
sta offset+1 |
517 |
|
|
518 |
|
txa |
519 |
|
lsr |
520 |
|
lsr |
521 |
|
lsr |
522 |
|
lsr |
523 |
|
clc |
524 |
|
adc #3 |
525 |
|
sta nb_dst |
526 |
|
|
527 |
|
sec |
528 |
|
lda ptr_destination |
529 |
|
sbc offset |
530 |
|
sta ptr_source_back |
531 |
|
lda ptr_destination+1 |
532 |
|
sbc offset+1 |
533 |
|
sta ptr_source_back+1 |
534 |
|
|
535 |
|
; Beware, in that loop, the direction is important |
536 |
|
; since RLE like depacking is done by recopying the |
537 |
|
; very same byte just copied... Do not make it a |
538 |
|
; reverse loop to achieve some speed gain... |
539 |
|
.( |
540 |
|
copy_loop |
541 |
|
lda (ptr_source_back),y ; Read from already unpacked stream |
542 |
|
sta (ptr_destination),y ; Write to destination buffer |
543 |
|
iny |
544 |
|
cpy nb_dst |
545 |
|
bne copy_loop |
546 |
|
.) |
547 |
|
ldy #0 |
548 |
|
beq _UnpackEndLoop |
549 |
|
rts |
550 |
|
.) |
551 |
|
|
552 |
|
_EndLoaderCode |
553 |
|
|
554 |
|
; |
555 |
|
; This is free memory that can be used, when it reaches zero then the loader start address should be changed |
556 |
|
; |
557 |
|
|
558 |
|
.dsb $FFF4 - _EndLoaderCode |
559 |
|
|
560 |
|
_Vectors |
561 |
|
|
562 |
|
#if ( _Vectors <> $FFF4 ) |
563 |
|
#error - Vector address is incorrect, loader will crash |
564 |
|
#else |
565 |
|
|
566 |
|
; |
567 |
|
; Here are the functions that the user can call from his own application |
568 |
|
; |
569 |
|
_ApiSetLoadAddress .byt $4c,<SetLoadAddress,>SetLoadAddress ; $FFF4 |
570 |
|
_ApiSetLoadData .byt $4c,<LoadData,>LoadData ; $FFF7 |
571 |
|
|
572 |
|
; |
573 |
|
; These three HAVE to be at these precise adresses, they map to hardware registers |
574 |
|
; |
575 |
|
_VectorNMI .word IrqDoNothing ; FFFA-FFFB - NMI Vector (Usually points to $0247) |
576 |
|
_VectorReset .word IrqDoNothing ; FFFC-FFFD - RESET Vector (Usually points to $F88F) |
577 |
|
_VectorIRQ .word IrqHandler ; FFFE-FFFF - IRQ Vector (Normally points to $0244) |
578 |
|
|
579 |
|
#echo Remaining space in the loader code: |
580 |
|
#print (_Vectors - _EndLoaderCode) |
581 |
|
|
582 |
|
#endif |
583 |
|
|
584 |
|
; End of the loader - Nothing should come after because it's out of the addressable memory range :) |
585 |
|
|