]> git.sur5r.net Git - cc65/blob - libsrc/c128/crt0.s
Removed the jump to RESTOR on exit for all the CBM platforms.
[cc65] / libsrc / c128 / crt0.s
1 ;
2 ; Startup code for cc65 (C128 version)
3 ;
4
5         .export         _exit
6         .export         __STARTUP__ : absolute = 1      ; Mark as startup
7         .import         callirq, initlib, donelib
8         .import         zerobss
9         .import         push0, callmain
10         .import         RESTOR, BSOUT, CLRCH
11         .import         __INTERRUPTOR_COUNT__
12         .import         __RAM_START__, __RAM_SIZE__, __STACKSIZE__
13
14         .include        "zeropage.inc"
15         .include        "c128.inc"
16
17
18 ; ------------------------------------------------------------------------
19 ; Constants
20
21 IRQInd          = $2FD  ; JMP $0000 - used as indirect IRQ vector
22
23 ; ------------------------------------------------------------------------
24 ; Startup code
25
26 .segment        "STARTUP"
27
28 Start:
29
30 ; Switch to the second charset
31
32         lda     #14
33         jsr     BSOUT
34
35 ; Before doing anything else, we have to setup our banking configuration.
36 ; Otherwise just the lowest 16K are actually RAM. Writing through the ROM
37 ; to the underlying RAM works, but it is bad style.
38
39         lda     MMU_CR          ; Get current memory configuration...
40         pha                     ; ...and save it for later
41         lda     #MMU_CFG_CC65   ; Bank0 with kernal ROM
42         sta     MMU_CR
43
44 ; Save the zero page locations we need
45
46         ldx     #zpspace-1
47 L1:     lda     sp,x
48         sta     zpsave,x
49         dex
50         bpl     L1
51
52 ; Clear the BSS data
53
54         jsr     zerobss
55
56 ; Save system stuff and setup the stack
57
58         pla                     ; Get MMU setting
59         sta     mmusave
60
61         tsx
62         stx     spsave          ; Save the system stack pointer
63
64         lda     #<(__RAM_START__ + __RAM_SIZE__ + __STACKSIZE__)
65         sta     sp
66         lda     #>(__RAM_START__ + __RAM_SIZE__ + __STACKSIZE__)
67         sta     sp+1            ; Set argument stack ptr
68
69 ; If we have IRQ functions, chain our stub into the IRQ vector
70
71         lda     #<__INTERRUPTOR_COUNT__
72         beq     NoIRQ1
73         lda     IRQVec
74         ldx     IRQVec+1
75         sta     IRQInd+1
76         stx     IRQInd+2
77         lda     #<IRQStub
78         ldx     #>IRQStub
79         sei
80         sta     IRQVec
81         stx     IRQVec+1
82         cli
83
84 ; Call module constructors
85
86 NoIRQ1: jsr     initlib
87
88 ; Set the bank for the file name to our execution bank. We must do this,
89 ; *after* calling constructors, because some of them may depend on the
90 ; original value of this register.
91
92         lda     #0
93         sta     FNAM_BANK
94
95 ; Push arguments and call main()
96
97         jsr     callmain
98
99 ; Back from main (this is also the _exit entry). Run module destructors
100
101 _exit:  jsr     donelib
102
103 ; Reset the IRQ vector if we chained it.
104
105         pha                             ; Save the return code on stack
106         lda     #<__INTERRUPTOR_COUNT__
107         beq     NoIRQ2
108         lda     IRQInd+1
109         ldx     IRQInd+2
110         sei
111         sta     IRQVec
112         stx     IRQVec+1
113         cli
114
115 ; Copy back the zero page stuff
116
117 NoIRQ2: ldx     #zpspace-1
118 L2:     lda     zpsave,x
119         sta     sp,x
120         dex
121         bpl     L2
122
123 ; Place the program return code into ST
124
125         pla
126         sta     ST
127
128 ; Reset the stack and the memory configuration
129
130         ldx     spsave
131         txs
132         ldx     mmusave
133         stx     MMU_CR
134
135 ; Done, return to BASIC
136
137         rts
138
139 ; ------------------------------------------------------------------------
140 ; The C128 has ROM parallel to the RAM starting from $4000. The startup code
141 ; above will change this setting so that we have RAM from $0000-$BFFF. This
142 ; works quite well with the exception of interrupts: The interrupt handler
143 ; is in ROM, and the ROM switches back to the ROM configuration, which means
144 ; that parts of our program may not be accessible. To solve this, we place
145 ; the following code into a special segment called "LOWCODE" which will be
146 ; placed just above the startup code, so it goes into a RAM area that is
147 ; not banked.
148
149 .segment        "LOWCODE"
150
151 IRQStub:
152         cld                             ; Just to be sure
153         lda     MMU_CR                  ; Get old register value
154         pha                             ; And save on stack
155         lda     #MMU_CFG_CC65           ; Bank 0 with kernal ROM
156         sta     MMU_CR
157         jsr     callirq                 ; Call the functions
158         pla                             ; Get old register value
159         sta     MMU_CR
160         jmp     IRQInd                  ; Jump to the saved IRQ vector
161
162
163 ; ------------------------------------------------------------------------
164 ; Data
165
166 .segment        "ZPSAVE"
167
168 zpsave: .res    zpspace
169
170 .bss
171 spsave: .res    1
172 mmusave:.res    1
173
174
175