crt0.s (5701B)
1 .include "global.s" 2 3 .title "Runtime" 4 .module Runtime 5 .area _HEADER (ABS) 6 7 .globl _set_default_palette 8 9 .org 0x00 ; Reset 00h 10 di ; disable interrupt 11 im 1 ; interrupt mode 1 (this won't change) 12 jp .init 13 14; .org 0x08 ; --profile handler 15 16 .org 0x10 ; RST 0x10: VDP_WRITE_CMD 17 18_WRITE_VDP_CMD:: 19 VDP_WRITE_CMD h, l 20 ret 21 22; .org 0x18 ; unusable 23 24 .org 0x20 ; RST 0x20: VDP_WRITE_DATA 25 26_WRITE_VDP_DATA:: 27 VDP_WRITE_DATA h, l 28 ret 29 30; .org 0x28 ; unusable 31 32 .org 0x30 ; RST 0x30: call HL 33.call_hl:: 34 jp (HL) 35 36 .org 0x38 ; handle IRQ 37 jp _INT_ISR 38 39 .org 0x66 ; handle NMI 40 jp _NMI_ISR 41 42 .org 0x80 43 44.init:: 45 ld sp, #.STACK ; set stack pointer at end of RAM 46 47 ld a, (#.BIOS) 48 push af 49 50 xor a 51 ld bc, #l__DATA 52 ld hl, #s__DATA 53 call .memset_simple ; initialize veriables in RAM with zero 54 55 pop af 56 ld (#__BIOS), a ; save BIOS value 57 58 ld hl, #_shadow_OAM 59 ld de, #(_shadow_OAM + 1) 60 ld bc, #64 61 ld (hl), #0xc0 62 ldir 63 ld (hl), #0 64 ld bc, #(128 - 1) 65 ldir 66 67 ld hl,#0x0000 ; initialize mappers 68 ld (#.RAM_CONTROL),hl ; [.RAM_CONTROL]=$00, [.MAP_FRAME0]=$00 69 ld hl,#0x0201 70 ld (#.MAP_FRAME1),hl ; [.MAP_FRAME1]=$01, [.MAP_FRAME2]=$02 71 72 ;; Initialise global variables 73 call .gsinit 74 75 ;; Initialize VDP 76 ld c, #.VDP_CMD 77 ld b, #(.shadow_VDP_end - .shadow_VDP) 78 ld hl,#(.shadow_VDP_end - 1) 791$: 80 outd 81 82 ld a, b 83 or #.VDP_REG_MASK 84 out (c), a 85 86 ld a, b 87 or a 88 jr nz, 1$ 89 90 ;; detect PAL/NTSC 91 in a, (.GG_STATE) 92 and #.GGSTATE_NNTS 93 jr nz, 2$ 94 ld a, #.SYSTEM_NTSC 95 jr 3$ 962$: 97 ld a, #.SYSTEM_PAL 983$: 99 ld (#__SYSTEM), a 100 101 call .clear_VRAM 102 103 call _set_default_palette 104 105 VDP_CANCEL_INT 106 107 ei ; re-enable interrupts before going to main() 108 call _main 10910$: 110 halt 111 jr 10$ 112 113 ;; Ordering of segments for the linker. 114 .area _HOME 115 .area _BASE 116 .area _CODE 117 .area _CODE_0 118 .area _LIT 119 .area _INITIALIZER 120 .area _GSINIT 121 .area _GSFINAL 122 123 .area _DATA 124 .area _INITIALIZED 125 .area _BSEG 126 .area _BSS 127 .area _HEAP 128 .area _HEAP_END 129 130 .area _CODE 131 .area _GSINIT 132.gsinit:: 133 ;; initialize static storage variables 134 ld bc, #l__INITIALIZER 135 ld hl, #s__INITIALIZER 136 ld de, #s__INITIALIZED 137 call .memcpy_simple 138 139 .area _GSFINAL 140 ret 141 142 .area _HOME 143 144.clear_VRAM: 145 ld a, #<.VDP_VRAM 146 out (#.VDP_CMD), a 147 ld a, #>.VDP_VRAM 148 out (#.VDP_CMD), a 149 xor a 150 ld bc, #0x4101 151 jr 6$ 1525$: 153 out (.VDP_DATA), a 1546$: 155 dec c 156 jr nz, 5$ 157 dec b 158 jr nz, 5$ 159 ret 160 161 ;; fills memory at HL of length BC with A, clobbers DE 162.memset_simple:: 163 ld e, a 164 ld a, c 165 or b 166 ret z 167 ld (hl), e 168 dec bc 169 ld d, h 170 ld e, l 171 inc de 172 173 ;; copies BC bytes from HL into DE 174.memcpy_simple:: 175 ld a, c 176 or b 177 ret z 178 ldir 179 ret 180 181 ;; Wait for VBL interrupt to be finished 182.wait_vbl_done:: 183_wait_vbl_done:: 184 ld a, (_shadow_VDP_R1) 185 and #.R1_DISP_ON 186 ret z 187 188 xor a 189 ld (.vbl_done), a 1901$: 191 halt 192 ld a, (.vbl_done) 193 or a 194 jr z, 1$ 195 ret 196 197 .area _DATA 198 199.start_crt_globals: 200__BIOS:: 201 .ds 0x01 ; GB type (GB, PGB, CGB) 202__SYSTEM:: 203 .ds 0x01 ; PAL/NTSC 204.end_crt_globals: 205 206 .area _INITIALIZED 207.shadow_VDP: 208_shadow_VDP_R0:: 209 .ds 0x01 210_shadow_VDP_R1:: 211 .ds 0x01 212_shadow_VDP_R2:: 213 .ds 0x01 214_shadow_VDP_R3:: 215 .ds 0x01 216_shadow_VDP_R4:: 217 .ds 0x01 218_shadow_VDP_R5:: 219 .ds 0x01 220_shadow_VDP_R6:: 221 .ds 0x01 222_shadow_VDP_R7:: 223_shadow_VDP_RBORDER:: 224 .ds 0x01 225_shadow_VDP_R8:: 226_shadow_VDP_RSCX:: 227 .ds 0x01 228_shadow_VDP_R9:: 229_shadow_VDP_RSCY:: 230 .ds 0x01 231_shadow_VDP_R10:: 232 .ds 0x01 233.shadow_VDP_end:: 234 235.sys_time:: 236_sys_time:: 237 .ds 0x02 238.vbl_done:: 239 .ds 0x01 240_VDP_ATTR_SHIFT:: 241.vdp_shift:: 242 .ds 0x01 243__shadow_OAM_base:: 244 .ds 0x01 245__shadow_OAM_OFF:: 246 .ds 0x01 247.mode:: 248 .ds 0x01 ; Current mode 249 250 .area _INITIALIZER 251 252 .db .R0_DEFAULT 253 .db #(.R1_DEFAULT | .R1_DISP_ON | .R1_IE) ; VBLANK 254 .db .R2_MAP_0x3800 255 .db 0xFF 256 .db 0xFF 257 .db .R5_SAT_0x3F00 258 .db .R6_DATA_0x2000 259 .db #(0 | .R7_COLOR_MASK) 260 .db 0 ; SCX 261 .db 0 ; SCY 262 .db .R10_INT_OFF 263 .dw 0x0000 ; .sys_time 264 .db 0 ; .vbl_done 265 .db 0 ; _VDP_ATTR_SHIFT 266 .db #>_shadow_OAM ; __shadow_OAM_base 267 .db 0 ; __shadow_OAM_OFF 268 .db .T_MODE_INOUT ; .mode