emu/rom/rom.68k
pjht 718f8cd276 Optimize an instruction from the ROM
The instruction to load fakestack into the SP can be removed by making use of the inital SP value in the reset vector
2022-10-25 11:43:58 -05:00

80 lines
3.2 KiB
Plaintext

.long fakestack, start
start:
move.b #0x1, d0 | Find the ROM card
bra.b find_first_card
romfindret:
move.l a0, a6 | Save the ROM card IO base in a6 for later
lea (0xF0, a6), a7 | Set up the stack at the end of the ROM's IO space RAM
bsr.b find_largest_ram | Find the largest RAM card and put the IO base in a5
move.l a0, a5
move.l d0, d7
move.b #0x4, d0 | Find a storage card and put the IO base in a4
bsr.b find_first_card
move.l a0, a4
| Transfer the bootsector load code to the ROM's
| built in RAM at the start of it's IO space
move.w #(ramcode_end - ramcode), d0 | Put the length of the ramcode in d0
move.w #ramcode, a0 | Put the address of the ramcode in a0
move.l a6, a1 | Put the start of the ROM's IO space RAM in a0
ramcode_loop:
move.b (a0)+, (a1)+ | Transfer a byte of ramcode to the ROM's IO space RAM
dbra d0, ramcode_loop | Loop back if there is more to transfer
jmp (a6) | Jump to the ramcode
stop #0x2700
ramcode:
move.b #0x0, (0xFE, a6) | Disable the ROM
move.l #0x1, (a5) | Enable the RAM at base 0x0
move.l d7, a7
| Load sector 0 to 0x0
move.l #0x0, (a4) | Set the sector number to 0
| Transfer 0x100 (256) bytes from the storage card's data register to 0x0
move.w #0x0, a1 | Load a1, the destination address register, with 0x0
move.w #0xFF, d0 | Load d0 with the sector size - 1.
sector_loop:
move.b (4, a4), (a1)+ | Transfer a byte of sector data to the destination
dbra d0, sector_loop | Loop back if there is more to transfer
jmp (0x0).W | Jump to the loaded sector
stop #0x2700
ramcode_end:
nop | Padding to make sure ramcode_end and find_first_card are different
| Finds the first card with the type in d0.b, and returns it's IO base address in a0, or 0 if not found
| Clobbers d1
find_first_card:
move.l #0xff0000, a0 | a0 holds the address of the current card
ffc_loop:
lea (0x100,a0), a0 | adda.l #$100,a0 ; Move to the next card
move.b (0xff, a0), d1 | Load the type of the card into d1
beq.b ffc_done | If the type is 0 (empty slot), we have scanned all cards, so exit the loop
cmp.b d0, d1 | If the card is the type we want, return with the address in a0
beq.b ffc_done
bra.b ffc_loop | Loop back and check the next card
ffc_done:
rts
| Finds the largest RAM card, and returns it's IO base address in a0 and size in d0, or 0 if not found
| Clobbers d1, a1
find_largest_ram:
move.l #0x0, d0 | d0 holds the size of the largest RAM card found
move.w #0x0, a0 | a0 holds the address of the largest RAM card found
move.l #0xff0000, a1 | a1 holds the address of the current card
flr_loop:
lea (0x100,a1), a1 | adda.l #$100,a0 ; Move to the next card
move.b (0xff, a1), d1 | Load the type of the card into d1
beq.b flr_done | If the type is 0 (empty slot), we have scanned all cards, so exit the loop
cmp.b #0x2, d1 | If the card isn't a RAM card, skip it
bne.b flr_loop
move.l (0x4, a1), d1 | Load the card's size into d1
cmp.l d0, d1 | If the current size is less than the largest size found, go back to the start of the loop
ble.b flr_loop
move.l d1, d0 | Store the size and address of the new largest card in d0 and a0
move.l a1, a0
bra.b flr_loop | Loop back and check the next card
flr_done:
rts
fakestack:
.long romfindret