;; This program will dump the CPC+ System cartridge.
;;
;; This program will save 8 files.
;; CARTROM1.BIN, CARTROM2.BIN, CARTROM3.BIN, CARTROM4.BIN,
;; CARTROM5.BIN, CARTROM6.BIN, CARTROM7.BIN and CARTROM8.BIN
;; 
;; Each file will be 16K. The total data will be 128K.
;; 
;; The files should be joined together into a single binary file to
;; create the complete ROM image. Join the files in numeric order:
;; e.g. CARTROM1.BIN+CARTROM2.BIN+CARTROM3.BIN+...+CARTROM8.BIN
;; 
;; This final binary file can be converted to a .CPR cartridge file for use
;; with emulators using the BUILDCPR utility.
;;
;; Kev Thacker, 1997-2002
;; 
;; This source is released under the GNU public license.

;; firmware function to enable upper rom (rom will be readable in range &c000-&ffff)
.kl_u_rom_enable	equ &b900
;; firmware function to disable upper rom (rom data can't be read)
.kl_u_rom_disable equ &b903

;; firmware function to open a file for output
.cas_out_open	equ &bc8c
;; firmware function to write a block of data to a file
.cas_out_direct	equ &bc98
;; firmware function to close a file opened for output
.cas_out_close	equ &bc8f


;; NOTE: ROM Data from &4000-&7FFF. Program code starts at &8000.
;; Upper ROM can be read in range &c000-&ffff (when activated).
;; Firmware area between &A600 (approximatly; depends on ROMs connected) to &bfff.
;; Lower firmware area between &0000-&0040. 

org &8000
nolist

.save_cart
;; There are 8 x 16K blocks in the system cartridge.
ld b,8

;; ROM's with ID's of 128-255 will select a 16K block in the cartridge ROM
;; if a cartridge is less than 512K, then more than one ID will select the same
;; 16K block of the cartridge ROM. e.g. if the cartridge is 128K, then selections
;; 128 and 136 will select the same 16K block.

ld e,&80

.save_loop
push bc

;;----------------------------------------------------------------
;; disable interrupts - will stop firmware from enabling any roms
di

;;----------------------------------------------------------------
;; STAGE 1: Select the rom
ld c,e
ld b,&df
out (c),c

;;----------------------------------------------------------------
;; STAGE 2: enable rom (rom data now readable in range &c000-&ffff

;; enable upper rom
call kl_u_rom_enable

;;----------------------------------------------------------------
;; STAGE 3: copy rom data to ram

;; copy rom data to ram
;; (the firmware will enable the DOS rom in the range &c000-&ffff to write
;; the file; therefore we can't keep the rom enabled while reading/writing to
;; disc)
ld hl,&c000
ld de,&4000
ld bc,&4000
ldir

;; disable upper rom
call kl_u_rom_disable

;; save rom data
call save_file

inc de
pop bc
djnz save_loop
ret


;;----------------------------------------------------------

.save_file
push hl
push de

ld hl,end_filename-1		;; update digit in filename
inc (hl)

ld b,end_filename-filename	;; B = length of filename
ld hl,filename			;; HL = address of filename
ld de,two_k_buffer		;; DE = address of 2k buffer (not used
					;; with cas_out_direct)

call cas_out_open			;; firmware function: open output file
pop de
pop hl
					;; HL = start address
					;; DE = length
					;; BC = execution address
ld bc,0
ld a,2				;; binary file
call cas_out_direct		;; firmware function: write a entire block

call cas_out_close		;; firmware function: close output file
ret

;; the initial filename, this is updated for 
;; each file saved
.filename
defb "CARTROM0"
.end_filename

.two_k_buffer equ $+1