Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
awilliam
GitHub Repository: awilliam/linux-vfio
Path: blob/master/arch/h8300/kernel/entry.S
10817 views
1
/* -*- mode: asm -*-
2
*
3
* linux/arch/h8300/platform/h8300h/entry.S
4
*
5
* Yoshinori Sato <[email protected]>
6
* David McCullough <[email protected]>
7
*
8
*/
9
10
/*
11
* entry.S
12
* include exception/interrupt gateway
13
* system call entry
14
*/
15
16
#include <linux/sys.h>
17
#include <asm/unistd.h>
18
#include <asm/setup.h>
19
#include <asm/segment.h>
20
#include <asm/linkage.h>
21
#include <asm/asm-offsets.h>
22
#include <asm/thread_info.h>
23
#include <asm/errno.h>
24
25
#if defined(CONFIG_CPU_H8300H)
26
#define USERRET 8
27
INTERRUPTS = 64
28
.h8300h
29
.macro SHLL2 reg
30
shll.l \reg
31
shll.l \reg
32
.endm
33
.macro SHLR2 reg
34
shlr.l \reg
35
shlr.l \reg
36
.endm
37
.macro SAVEREGS
38
mov.l er0,@-sp
39
mov.l er1,@-sp
40
mov.l er2,@-sp
41
mov.l er3,@-sp
42
.endm
43
.macro RESTOREREGS
44
mov.l @sp+,er3
45
mov.l @sp+,er2
46
.endm
47
.macro SAVEEXR
48
.endm
49
.macro RESTOREEXR
50
.endm
51
#endif
52
#if defined(CONFIG_CPU_H8S)
53
#define USERRET 10
54
#define USEREXR 8
55
INTERRUPTS = 128
56
.h8300s
57
.macro SHLL2 reg
58
shll.l #2,\reg
59
.endm
60
.macro SHLR2 reg
61
shlr.l #2,\reg
62
.endm
63
.macro SAVEREGS
64
stm.l er0-er3,@-sp
65
.endm
66
.macro RESTOREREGS
67
ldm.l @sp+,er2-er3
68
.endm
69
.macro SAVEEXR
70
mov.w @(USEREXR:16,er0),r1
71
mov.w r1,@(LEXR-LER3:16,sp) /* copy EXR */
72
.endm
73
.macro RESTOREEXR
74
mov.w @(LEXR-LER1:16,sp),r1 /* restore EXR */
75
mov.b r1l,r1h
76
mov.w r1,@(USEREXR:16,er0)
77
.endm
78
#endif
79
80
81
/* CPU context save/restore macros. */
82
83
.macro SAVE_ALL
84
mov.l er0,@-sp
85
stc ccr,r0l /* check kernel mode */
86
btst #4,r0l
87
bne 5f
88
89
/* user mode */
90
mov.l sp,@SYMBOL_NAME(sw_usp)
91
mov.l @sp,er0 /* restore saved er0 */
92
orc #0x10,ccr /* switch kernel stack */
93
mov.l @SYMBOL_NAME(sw_ksp),sp
94
sub.l #(LRET-LORIG),sp /* allocate LORIG - LRET */
95
SAVEREGS
96
mov.l @SYMBOL_NAME(sw_usp),er0
97
mov.l @(USERRET:16,er0),er1 /* copy the RET addr */
98
mov.l er1,@(LRET-LER3:16,sp)
99
SAVEEXR
100
101
mov.l @(LORIG-LER3:16,sp),er0
102
mov.l er0,@(LER0-LER3:16,sp) /* copy ER0 */
103
mov.w e1,r1 /* e1 highbyte = ccr */
104
and #0xef,r1h /* mask mode? flag */
105
bra 6f
106
5:
107
/* kernel mode */
108
mov.l @sp,er0 /* restore saved er0 */
109
subs #2,sp /* set dummy ccr */
110
SAVEREGS
111
mov.w @(LRET-LER3:16,sp),r1 /* copy old ccr */
112
6:
113
mov.b r1h,r1l
114
mov.b #0,r1h
115
mov.w r1,@(LCCR-LER3:16,sp) /* set ccr */
116
mov.l er6,@-sp /* syscall arg #6 */
117
mov.l er5,@-sp /* syscall arg #5 */
118
mov.l er4,@-sp /* syscall arg #4 */
119
.endm /* r1 = ccr */
120
121
.macro RESTORE_ALL
122
mov.l @sp+,er4
123
mov.l @sp+,er5
124
mov.l @sp+,er6
125
RESTOREREGS
126
mov.w @(LCCR-LER1:16,sp),r0 /* check kernel mode */
127
btst #4,r0l
128
bne 7f
129
130
orc #0x80,ccr
131
mov.l @SYMBOL_NAME(sw_usp),er0
132
mov.l @(LER0-LER1:16,sp),er1 /* restore ER0 */
133
mov.l er1,@er0
134
RESTOREEXR
135
mov.w @(LCCR-LER1:16,sp),r1 /* restore the RET addr */
136
mov.b r1l,r1h
137
mov.b @(LRET+1-LER1:16,sp),r1l
138
mov.w r1,e1
139
mov.w @(LRET+2-LER1:16,sp),r1
140
mov.l er1,@(USERRET:16,er0)
141
142
mov.l @sp+,er1
143
add.l #(LRET-LER1),sp /* remove LORIG - LRET */
144
mov.l sp,@SYMBOL_NAME(sw_ksp)
145
andc #0xef,ccr /* switch to user mode */
146
mov.l er0,sp
147
bra 8f
148
7:
149
mov.l @sp+,er1
150
adds #4,sp
151
adds #2,sp
152
8:
153
mov.l @sp+,er0
154
adds #4,sp /* remove the sw created LVEC */
155
rte
156
.endm
157
158
.globl SYMBOL_NAME(system_call)
159
.globl SYMBOL_NAME(ret_from_exception)
160
.globl SYMBOL_NAME(ret_from_fork)
161
.globl SYMBOL_NAME(ret_from_interrupt)
162
.globl SYMBOL_NAME(interrupt_redirect_table)
163
.globl SYMBOL_NAME(sw_ksp),SYMBOL_NAME(sw_usp)
164
.globl SYMBOL_NAME(resume)
165
.globl SYMBOL_NAME(interrupt_entry)
166
.globl SYMBOL_NAME(trace_break)
167
168
#if defined(CONFIG_ROMKERNEL)
169
.section .int_redirect,"ax"
170
SYMBOL_NAME_LABEL(interrupt_redirect_table)
171
#if defined(CONFIG_CPU_H8300H)
172
.rept 7
173
.long 0
174
.endr
175
#endif
176
#if defined(CONFIG_CPU_H8S)
177
.rept 5
178
.long 0
179
.endr
180
jmp @SYMBOL_NAME(trace_break)
181
.long 0
182
#endif
183
184
jsr @SYMBOL_NAME(interrupt_entry) /* NMI */
185
jmp @SYMBOL_NAME(system_call) /* TRAPA #0 (System call) */
186
.long 0
187
.long 0
188
jmp @SYMBOL_NAME(trace_break) /* TRAPA #3 (breakpoint) */
189
.rept INTERRUPTS-12
190
jsr @SYMBOL_NAME(interrupt_entry)
191
.endr
192
#endif
193
#if defined(CONFIG_RAMKERNEL)
194
.globl SYMBOL_NAME(interrupt_redirect_table)
195
.section .bss
196
SYMBOL_NAME_LABEL(interrupt_redirect_table)
197
.space 4
198
#endif
199
200
.section .text
201
.align 2
202
SYMBOL_NAME_LABEL(interrupt_entry)
203
SAVE_ALL
204
mov.l sp,er0
205
add.l #LVEC,er0
206
btst #4,r1l
207
bne 1f
208
/* user LVEC */
209
mov.l @SYMBOL_NAME(sw_usp),er0
210
adds #4,er0
211
1:
212
mov.l @er0,er0 /* LVEC address */
213
#if defined(CONFIG_ROMKERNEL)
214
sub.l #SYMBOL_NAME(interrupt_redirect_table),er0
215
#endif
216
#if defined(CONFIG_RAMKERNEL)
217
mov.l @SYMBOL_NAME(interrupt_redirect_table),er1
218
sub.l er1,er0
219
#endif
220
SHLR2 er0
221
dec.l #1,er0
222
mov.l sp,er1
223
subs #4,er1 /* adjust ret_pc */
224
jsr @SYMBOL_NAME(do_IRQ)
225
jmp @SYMBOL_NAME(ret_from_interrupt)
226
227
SYMBOL_NAME_LABEL(system_call)
228
subs #4,sp /* dummy LVEC */
229
SAVE_ALL
230
andc #0x7f,ccr
231
mov.l er0,er4
232
233
/* save top of frame */
234
mov.l sp,er0
235
jsr @SYMBOL_NAME(set_esp0)
236
mov.l sp,er2
237
and.w #0xe000,r2
238
mov.b @((TI_FLAGS+3-(TIF_SYSCALL_TRACE >> 3)):16,er2),r2l
239
btst #(TIF_SYSCALL_TRACE & 7),r2l
240
beq 1f
241
jsr @SYMBOL_NAME(do_syscall_trace)
242
1:
243
cmp.l #NR_syscalls,er4
244
bcc badsys
245
SHLL2 er4
246
mov.l #SYMBOL_NAME(sys_call_table),er0
247
add.l er4,er0
248
mov.l @er0,er4
249
beq SYMBOL_NAME(ret_from_exception):16
250
mov.l @(LER1:16,sp),er0
251
mov.l @(LER2:16,sp),er1
252
mov.l @(LER3:16,sp),er2
253
jsr @er4
254
mov.l er0,@(LER0:16,sp) /* save the return value */
255
mov.l sp,er2
256
and.w #0xe000,r2
257
mov.b @((TI_FLAGS+3-(TIF_SYSCALL_TRACE >> 3)):16,er2),r2l
258
btst #(TIF_SYSCALL_TRACE & 7),r2l
259
beq 2f
260
jsr @SYMBOL_NAME(do_syscall_trace)
261
2:
262
#if defined(CONFIG_SYSCALL_PRINT)
263
jsr @SYMBOL_NAME(syscall_print)
264
#endif
265
orc #0x80,ccr
266
bra resume_userspace
267
268
badsys:
269
mov.l #-ENOSYS,er0
270
mov.l er0,@(LER0:16,sp)
271
bra resume_userspace
272
273
#if !defined(CONFIG_PREEMPT)
274
#define resume_kernel restore_all
275
#endif
276
277
SYMBOL_NAME_LABEL(ret_from_exception)
278
#if defined(CONFIG_PREEMPT)
279
orc #0x80,ccr
280
#endif
281
SYMBOL_NAME_LABEL(ret_from_interrupt)
282
mov.b @(LCCR+1:16,sp),r0l
283
btst #4,r0l
284
bne resume_kernel:8 /* return from kernel */
285
resume_userspace:
286
andc #0x7f,ccr
287
mov.l sp,er4
288
and.w #0xe000,r4 /* er4 <- current thread info */
289
mov.l @(TI_FLAGS:16,er4),er1
290
and.l #_TIF_WORK_MASK,er1
291
beq restore_all:8
292
work_pending:
293
btst #TIF_NEED_RESCHED,r1l
294
bne work_resched:8
295
/* work notifysig */
296
mov.l sp,er0
297
subs #4,er0 /* er0: pt_regs */
298
jsr @SYMBOL_NAME(do_notify_resume)
299
bra restore_all:8
300
work_resched:
301
mov.l sp,er0
302
jsr @SYMBOL_NAME(set_esp0)
303
jsr @SYMBOL_NAME(schedule)
304
bra resume_userspace:8
305
restore_all:
306
RESTORE_ALL /* Does RTE */
307
308
#if defined(CONFIG_PREEMPT)
309
resume_kernel:
310
mov.l @(TI_PRE_COUNT:16,er4),er0
311
bne restore_all:8
312
need_resched:
313
mov.l @(TI_FLAGS:16,er4),er0
314
btst #TIF_NEED_RESCHED,r0l
315
beq restore_all:8
316
mov.b @(LCCR+1:16,sp),r0l /* Interrupt Enabled? */
317
bmi restore_all:8
318
mov.l #PREEMPT_ACTIVE,er0
319
mov.l er0,@(TI_PRE_COUNT:16,er4)
320
andc #0x7f,ccr
321
mov.l sp,er0
322
jsr @SYMBOL_NAME(set_esp0)
323
jsr @SYMBOL_NAME(schedule)
324
orc #0x80,ccr
325
bra need_resched:8
326
#endif
327
328
SYMBOL_NAME_LABEL(ret_from_fork)
329
mov.l er2,er0
330
jsr @SYMBOL_NAME(schedule_tail)
331
jmp @SYMBOL_NAME(ret_from_exception)
332
333
SYMBOL_NAME_LABEL(resume)
334
/*
335
* Beware - when entering resume, offset of tss is in d1,
336
* prev (the current task) is in a0, next (the new task)
337
* is in a1 and d2.b is non-zero if the mm structure is
338
* shared between the tasks, so don't change these
339
* registers until their contents are no longer needed.
340
*/
341
342
/* save sr */
343
sub.w r3,r3
344
stc ccr,r3l
345
mov.w r3,@(THREAD_CCR+2:16,er0)
346
347
/* disable interrupts */
348
orc #0x80,ccr
349
mov.l @SYMBOL_NAME(sw_usp),er3
350
mov.l er3,@(THREAD_USP:16,er0)
351
mov.l sp,@(THREAD_KSP:16,er0)
352
353
/* Skip address space switching if they are the same. */
354
/* FIXME: what did we hack out of here, this does nothing! */
355
356
mov.l @(THREAD_USP:16,er1),er0
357
mov.l er0,@SYMBOL_NAME(sw_usp)
358
mov.l @(THREAD_KSP:16,er1),sp
359
360
/* restore status register */
361
mov.w @(THREAD_CCR+2:16,er1),r3
362
363
ldc r3l,ccr
364
rts
365
366
SYMBOL_NAME_LABEL(trace_break)
367
subs #4,sp
368
SAVE_ALL
369
sub.l er1,er1
370
dec.l #1,er1
371
mov.l er1,@(LORIG,sp)
372
mov.l sp,er0
373
jsr @SYMBOL_NAME(set_esp0)
374
mov.l @SYMBOL_NAME(sw_usp),er0
375
mov.l @er0,er1
376
mov.w @(-2:16,er1),r2
377
cmp.w #0x5730,r2
378
beq 1f
379
subs #2,er1
380
mov.l er1,@er0
381
1:
382
and.w #0xff,e1
383
mov.l er1,er0
384
jsr @SYMBOL_NAME(trace_trap)
385
jmp @SYMBOL_NAME(ret_from_exception)
386
387
.section .bss
388
SYMBOL_NAME_LABEL(sw_ksp)
389
.space 4
390
SYMBOL_NAME_LABEL(sw_usp)
391
.space 4
392
393
.end
394
395