summaryrefslogtreecommitdiff
path: root/bsp/m16c62p/drivers/start_iar.asm
blob: 51dad7cd1d77c839a78ad4485065afb9d978a72d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
;-----------------------------------------------------------------------
;
; This file contains the M16C C startup routine and must usually
; be tailored to suit customer's hardware.
;
; Copyright 2002 IAR Systems. All rights reserved.
;
; $Revision: 1.16 $
;
;-----------------------------------------------------------------------

        MODULE  ?cstart

        PUBLIC  __program_start
        PUBLIC  __data16_init
        PUBLIC  __data16_zero
        PUBLIC  ?cstart_call_ctors

        EXTERN  main
        EXTERN  exit
        EXTERN  __call_ctors
        EXTERN  __low_level_init
        EXTERN  ?GENERIC_MOVE_LONG_L08
        EXTERN  RelocatableVectTbl

        ;------------------------------------------------------
        ; Useful macros
        ;------------------------------------------------------

        ; Load 24-bit constant value to (high,low)
LD24    MACRO   value,high,low
        MOV.B   #BYTE3(value),high
        MOV.W   #LWRD(value),low
        ENDM

        ; Load 32-bit constant value to (high,low)
LD32    MACRO   value,high,low
        MOV.W   #HWRD(value),high
        MOV.W   #LWRD(value),low
        ENDM

        ; Load a stack-pointer with last even address of segment
LDSTACK MACRO   segment,reg
        LDC     #sfe(segment), reg
        ENDM


        ;------------------------------------------------------
        ; __program_start - Reset vector should point to here.
        ;
        ; Calls __low_level_init to perform initialization
        ; before initializing segments and calling main.
        ; If the function returns 0 no segment initialization
        ; should take place.
        ;
        ; Link with your own version of __low_level_init to
        ; override the default action: do nothing but return 1.
        ;------------------------------------------------------

        RSEG    CSTACK
        RSEG    ISTACK
        RSEG    CSTART:CODE:NOROOT
	REQUIRE	call_main

__program_start:
        LDC     #sfe(ISTACK),   ISP                             ; Set up interrupt stack
        FCLR    U                                               ; Select interrupt stack
        LDC     #sfe(CSTACK),   SP                              ; Set up C         stack
        LDINTB  #RelocatableVectTbl                             ; Set up INTB register
        JSR.A   __low_level_init                                ; Call __low_level_init

        ;-----------------------------------------------------------
        ; Run-time test whether we should do segment initialization
        ;-----------------------------------------------------------
        TST.B   R0L,            R0L
        JNE     do_segment_init
        JMP     skip_segment_init

do_segment_init:

        ;------------------------------------------------------
        ; Perform segment initialization of DATA16 memory.
        ;------------------------------------------------------

        RSEG    DATA16_Z
        RSEG    CSTART:CODE:NOROOT

__data16_zero:
        MOV.W   #sizeof(DATA16_Z), R3
        MOV.W   #sfb(DATA16_Z),    A1
        MOV.B   #0, R0L
        SSTR.B

        RSEG    DATA16_I
        RSEG    DATA16_ID
        RSEG    CSTART:CODE:NOROOT

__data16_init:
        MOV.W   #sizeof(DATA16_ID), R3
        MOV.W   #sfb(DATA16_I),     A1
        LD24    sfb(DATA16_ID),     R1H, A0
        SMOVF.B



        RSEG    CSTART:CODE:NOROOT
skip_segment_init:
        ; Fall through to next required CSTART segment part


        ;------------------------------------------------------
        ; Call constructors
        ;------------------------------------------------------

        RSEG    DIFUNCT
        RSEG    CSTART:CODE:NOROOT

        PUBLIC  ?cstart_call_ctors
        EXTERN  __call_ctors

?cstart_call_ctors:
        PUSH.W  #HWRD(sfe(DIFUNCT))
        PUSH.W  #LWRD(sfe(DIFUNCT))
        LD32    sfb(DIFUNCT),R2,R0
        JSR.A   __call_ctors


        ; Fall through to next required CSTART segment part


        ;------------------------------------------------------
        ; Call main and exit
        ;------------------------------------------------------

        ; This segment part is marked as ROOT, since it must
        ; be preserved by the linker.
        ;
        RSEG    CSTART:CODE:NOROOT

call_main:
        MOV.W   #0, R0  ; Call main with argc = 0
        JSR.A   main
        JMP.A   exit    ; Argument to exit is return value of main

        ;------------------------------------------------------
        ; Fixed interrupt table.
        ;
        ; We install all fixed interrupts in a segment called
        ; INTVEC1. All fixed interrupts have a hard coded name.
        ; Write an interrupt handler in C using this name, with
        ; no vector specification, and it will replace the
        ; default handler.
        ;------------------------------------------------------

        EXTERN  __undefined_instruction_handler
        EXTERN  __overflow_handler
        EXTERN  __break_instruction_handler
        EXTERN  __address_match_handler
        EXTERN  __single_step_handler
        EXTERN  __watchdog_timer_handler
        EXTERN  __DBC_handler
        EXTERN  __NMI_handler

        ; Labels for the ID Code Check Function.
        ; (To be initialized in the linker file)
        EXTERN  _ID_CODE_1
        EXTERN  _ID_CODE_2
        EXTERN  _ID_CODE_3
        EXTERN  _ID_CODE_4
        EXTERN  _ID_CODE_5
        EXTERN  _ID_CODE_6
        EXTERN  _ID_CODE_7
        EXTERN  _OFS_VALUE

	PUBLIC ??intvec_start

        COMMON INTVEC1:NOROOT
??intvec_start:
        DC24    __undefined_instruction_handler
        DC8     _ID_CODE_1
        DC24    __overflow_handler
        DC8     _ID_CODE_2
        DC24    __break_instruction_handler
        DC8     0
        DC24    __address_match_handler
        DC8     _ID_CODE_3
        DC24    __single_step_handler
        DC8     _ID_CODE_4
        DC24    __watchdog_timer_handler
        DC8     _ID_CODE_5
        DC24    __DBC_handler
        DC8     _ID_CODE_6
        DC24    __NMI_handler
        DC8     _ID_CODE_7
        DC24    __program_start              ; Reset vector
        DC8     _OFS_VALUE                                 

        ENDMOD


        ;------------------------------------------------------
        ; Default handlers for fixed interrupts
        ;------------------------------------------------------

        MODULE  __undefined_instruction
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __undefined_instruction_handler
        RSEG    CSTART:CODE:NOROOT(1)
__undefined_instruction_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __overflow
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __overflow_handler
        RSEG    CSTART:CODE:NOROOT(1)
__overflow_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __break_instruction
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __break_instruction_handler
        RSEG    CSTART:CODE:NOROOT(1)
__break_instruction_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __address_match
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __address_match_handler
        RSEG    CSTART:CODE:NOROOT(1)
__address_match_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __single_step
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __single_step_handler
        RSEG    CSTART:CODE:NOROOT(1)
__single_step_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __watchdog_timer
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __watchdog_timer_handler
        RSEG    CSTART:CODE:NOROOT(1)
__watchdog_timer_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __DBC
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __DBC_handler
        RSEG    CSTART:CODE:NOROOT(1)
__DBC_handler:
        ; Fall through to ??reit
        ENDMOD

        MODULE  __NMI
        EXTERN  ??reit
        REQUIRE ??reit
        PUBLIC  __NMI_handler
        RSEG    CSTART:CODE:NOROOT(1)
__NMI_handler:
        ; Fall through to ??reit
        ENDMOD

        ;------------------------------------------------------
        ; Return from interrupt
        ;------------------------------------------------------
        MODULE    __reit
        PUBLIC  ??reit
        RSEG    CSTART:CODE:NOROOT(1)
	EXTERN ??intvec_start
	REQUIRE ??intvec_start
??reit:
        REIT

        ENDMOD


        ;------------------------------------------------------
        ; FUNCTION: __low_level_init
        ;
        ; You can replace this routine by linking with your
        ; own version.
        ;
        ; The default action is to do nothing and return 1.
        ;------------------------------------------------------

        MODULE  __low_level_init
        PUBLIC  __low_level_init
        RSEG    CSTART:CODE:NOROOT

__low_level_init:
        MOV.B   #1,R0L
        RTS

        ENDMOD


        ;------------------------------------------------------
        ;  __overflow - This variable is used by the intrinsic
        ;               functions __RMPA_W_overflow and
        ;               __RMPA_B_overflow.
        ;------------------------------------------------------

        MODULE  __overflow
        PUBLIC  __overflow
        EXTERN  __data13_zero

        RSEG    DATA13_Z:NEAR:NOROOT

__overflow:
        DC8     0
        REQUIRE __data13_zero

        END