xref: /openbmc/linux/arch/mips/kernel/scall64-o32.S (revision c819e2cf)
1/*
2 * This file is subject to the terms and conditions of the GNU General Public
3 * License.  See the file "COPYING" in the main directory of this archive
4 * for more details.
5 *
6 * Copyright (C) 1995 - 2000, 2001 by Ralf Baechle
7 * Copyright (C) 1999, 2000 Silicon Graphics, Inc.
8 * Copyright (C) 2001 MIPS Technologies, Inc.
9 * Copyright (C) 2004 Thiemo Seufer
10 *
11 * Hairy, the userspace application uses a different argument passing
12 * convention than the kernel, so we have to translate things from o32
13 * to ABI64 calling convention.	 64-bit syscalls are also processed
14 * here for now.
15 */
16#include <linux/errno.h>
17#include <asm/asm.h>
18#include <asm/asmmacro.h>
19#include <asm/irqflags.h>
20#include <asm/mipsregs.h>
21#include <asm/regdef.h>
22#include <asm/stackframe.h>
23#include <asm/thread_info.h>
24#include <asm/unistd.h>
25#include <asm/sysmips.h>
26
27	.align	5
28NESTED(handle_sys, PT_SIZE, sp)
29	.set	noat
30	SAVE_SOME
31	TRACE_IRQS_ON_RELOAD
32	STI
33	.set	at
34	ld	t1, PT_EPC(sp)		# skip syscall on return
35
36	dsubu	t0, v0, __NR_O32_Linux	# check syscall number
37	sltiu	t0, t0, __NR_O32_Linux_syscalls + 1
38	daddiu	t1, 4			# skip to next instruction
39	sd	t1, PT_EPC(sp)
40	beqz	t0, not_o32_scall
41#if 0
42 SAVE_ALL
43 move a1, v0
44 PRINT("Scall %ld\n")
45 RESTORE_ALL
46#endif
47
48	/* We don't want to stumble over broken sign extensions from
49	   userland. O32 does never use the upper half. */
50	sll	a0, a0, 0
51	sll	a1, a1, 0
52	sll	a2, a2, 0
53	sll	a3, a3, 0
54
55	dsll	t0, v0, 3		# offset into table
56	ld	t2, (sys32_call_table - (__NR_O32_Linux * 8))(t0)
57
58	sd	a3, PT_R26(sp)		# save a3 for syscall restarting
59
60	/*
61	 * More than four arguments.  Try to deal with it by copying the
62	 * stack arguments from the user stack to the kernel stack.
63	 * This Sucks (TM).
64	 *
65	 * We intentionally keep the kernel stack a little below the top of
66	 * userspace so we don't have to do a slower byte accurate check here.
67	 */
68	ld	t0, PT_R29(sp)		# get old user stack pointer
69	daddu	t1, t0, 32
70	bltz	t1, bad_stack
71
721:	lw	a4, 16(t0)		# argument #5 from usp
732:	lw	a5, 20(t0)		# argument #6 from usp
743:	lw	a6, 24(t0)		# argument #7 from usp
754:	lw	a7, 28(t0)		# argument #8 from usp (for indirect syscalls)
76
77	.section __ex_table,"a"
78	PTR	1b, bad_stack
79	PTR	2b, bad_stack
80	PTR	3b, bad_stack
81	PTR	4b, bad_stack
82	.previous
83
84	li	t1, _TIF_WORK_SYSCALL_ENTRY
85	LONG_L	t0, TI_FLAGS($28)	# syscall tracing enabled?
86	and	t0, t1, t0
87	bnez	t0, trace_a_syscall
88
89	jalr	t2			# Do The Real Thing (TM)
90
91	li	t0, -EMAXERRNO - 1	# error?
92	sltu	t0, t0, v0
93	sd	t0, PT_R7(sp)		# set error flag
94	beqz	t0, 1f
95
96	ld	t1, PT_R2(sp)		# syscall number
97	dnegu	v0			# error
98	sd	t1, PT_R0(sp)		# save it for syscall restarting
991:	sd	v0, PT_R2(sp)		# result
100
101o32_syscall_exit:
102	j	syscall_exit_partial
103
104/* ------------------------------------------------------------------------ */
105
106trace_a_syscall:
107	SAVE_STATIC
108	sd	a4, PT_R8(sp)		# Save argument registers
109	sd	a5, PT_R9(sp)
110	sd	a6, PT_R10(sp)
111	sd	a7, PT_R11(sp)		# For indirect syscalls
112
113	move	s0, t2			# Save syscall pointer
114	move	a0, sp
115	/*
116	 * absolute syscall number is in v0 unless we called syscall(__NR_###)
117	 * where the real syscall number is in a0
118	 * note: NR_syscall is the first O32 syscall but the macro is
119	 * only defined when compiling with -mabi=32 (CONFIG_32BIT)
120	 * therefore __NR_O32_Linux is used (4000)
121	 */
122	.set	push
123	.set	reorder
124	subu	t1, v0,  __NR_O32_Linux
125	move	a1, v0
126	bnez	t1, 1f /* __NR_syscall at offset 0 */
127	lw	a1, PT_R4(sp) /* Arg1 for __NR_syscall case */
128	.set	pop
129
1301:	jal	syscall_trace_enter
131
132	bltz	v0, 2f			# seccomp failed? Skip syscall
133
134	move	t0, s0
135	RESTORE_STATIC
136	ld	a0, PT_R4(sp)		# Restore argument registers
137	ld	a1, PT_R5(sp)
138	ld	a2, PT_R6(sp)
139	ld	a3, PT_R7(sp)
140	ld	a4, PT_R8(sp)
141	ld	a5, PT_R9(sp)
142	ld	a6, PT_R10(sp)
143	ld	a7, PT_R11(sp)		# For indirect syscalls
144	jalr	t0
145
146	li	t0, -EMAXERRNO - 1	# error?
147	sltu	t0, t0, v0
148	sd	t0, PT_R7(sp)		# set error flag
149	beqz	t0, 1f
150
151	ld	t1, PT_R2(sp)		# syscall number
152	dnegu	v0			# error
153	sd	t1, PT_R0(sp)		# save it for syscall restarting
1541:	sd	v0, PT_R2(sp)		# result
155
1562:	j	syscall_exit
157
158/* ------------------------------------------------------------------------ */
159
160	/*
161	 * The stackpointer for a call with more than 4 arguments is bad.
162	 */
163bad_stack:
164	li	v0, EFAULT
165	sd	v0, PT_R2(sp)
166	li	t0, 1			# set error flag
167	sd	t0, PT_R7(sp)
168	j	o32_syscall_exit
169
170not_o32_scall:
171	/*
172	 * This is not an o32 compatibility syscall, pass it on
173	 * to the 64-bit syscall handlers.
174	 */
175#ifdef CONFIG_MIPS32_N32
176	j	handle_sysn32
177#else
178	j	handle_sys64
179#endif
180	END(handle_sys)
181
182LEAF(sys32_syscall)
183	subu	t0, a0, __NR_O32_Linux	# check syscall number
184	sltiu	v0, t0, __NR_O32_Linux_syscalls + 1
185	beqz	t0, einval		# do not recurse
186	dsll	t1, t0, 3
187	beqz	v0, einval
188	ld	t2, sys32_call_table(t1)		# syscall routine
189
190	move	a0, a1			# shift argument registers
191	move	a1, a2
192	move	a2, a3
193	move	a3, a4
194	move	a4, a5
195	move	a5, a6
196	move	a6, a7
197	sd	a0, PT_R4(sp)		# ... and push back a0 - a3, some
198	sd	a1, PT_R5(sp)		# syscalls expect them there
199	sd	a2, PT_R6(sp)
200	sd	a3, PT_R7(sp)
201	sd	a3, PT_R26(sp)		# update a3 for syscall restarting
202	jr	t2
203	/* Unreached */
204
205einval: li	v0, -ENOSYS
206	jr	ra
207	END(sys32_syscall)
208
209	.align	3
210	.type	sys32_call_table,@object
211EXPORT(sys32_call_table)
212	PTR	sys32_syscall			/* 4000 */
213	PTR	sys_exit
214	PTR	__sys_fork
215	PTR	sys_read
216	PTR	sys_write
217	PTR	compat_sys_open			/* 4005 */
218	PTR	sys_close
219	PTR	sys_waitpid
220	PTR	sys_creat
221	PTR	sys_link
222	PTR	sys_unlink			/* 4010 */
223	PTR	compat_sys_execve
224	PTR	sys_chdir
225	PTR	compat_sys_time
226	PTR	sys_mknod
227	PTR	sys_chmod			/* 4015 */
228	PTR	sys_lchown
229	PTR	sys_ni_syscall
230	PTR	sys_ni_syscall			/* was sys_stat */
231	PTR	sys_lseek
232	PTR	sys_getpid			/* 4020 */
233	PTR	compat_sys_mount
234	PTR	sys_oldumount
235	PTR	sys_setuid
236	PTR	sys_getuid
237	PTR	compat_sys_stime		/* 4025 */
238	PTR	compat_sys_ptrace
239	PTR	sys_alarm
240	PTR	sys_ni_syscall			/* was sys_fstat */
241	PTR	sys_pause
242	PTR	compat_sys_utime		/* 4030 */
243	PTR	sys_ni_syscall
244	PTR	sys_ni_syscall
245	PTR	sys_access
246	PTR	sys_nice
247	PTR	sys_ni_syscall			/* 4035 */
248	PTR	sys_sync
249	PTR	sys_kill
250	PTR	sys_rename
251	PTR	sys_mkdir
252	PTR	sys_rmdir			/* 4040 */
253	PTR	sys_dup
254	PTR	sysm_pipe
255	PTR	compat_sys_times
256	PTR	sys_ni_syscall
257	PTR	sys_brk				/* 4045 */
258	PTR	sys_setgid
259	PTR	sys_getgid
260	PTR	sys_ni_syscall			/* was signal	2 */
261	PTR	sys_geteuid
262	PTR	sys_getegid			/* 4050 */
263	PTR	sys_acct
264	PTR	sys_umount
265	PTR	sys_ni_syscall
266	PTR	compat_sys_ioctl
267	PTR	compat_sys_fcntl		/* 4055 */
268	PTR	sys_ni_syscall
269	PTR	sys_setpgid
270	PTR	sys_ni_syscall
271	PTR	sys_olduname
272	PTR	sys_umask			/* 4060 */
273	PTR	sys_chroot
274	PTR	compat_sys_ustat
275	PTR	sys_dup2
276	PTR	sys_getppid
277	PTR	sys_getpgrp			/* 4065 */
278	PTR	sys_setsid
279	PTR	sys_32_sigaction
280	PTR	sys_sgetmask
281	PTR	sys_ssetmask
282	PTR	sys_setreuid			/* 4070 */
283	PTR	sys_setregid
284	PTR	sys32_sigsuspend
285	PTR	compat_sys_sigpending
286	PTR	sys_sethostname
287	PTR	compat_sys_setrlimit		/* 4075 */
288	PTR	compat_sys_getrlimit
289	PTR	compat_sys_getrusage
290	PTR	compat_sys_gettimeofday
291	PTR	compat_sys_settimeofday
292	PTR	sys_getgroups			/* 4080 */
293	PTR	sys_setgroups
294	PTR	sys_ni_syscall			/* old_select */
295	PTR	sys_symlink
296	PTR	sys_ni_syscall			/* was sys_lstat */
297	PTR	sys_readlink			/* 4085 */
298	PTR	sys_uselib
299	PTR	sys_swapon
300	PTR	sys_reboot
301	PTR	compat_sys_old_readdir
302	PTR	sys_mips_mmap			/* 4090 */
303	PTR	sys_munmap
304	PTR	compat_sys_truncate
305	PTR	compat_sys_ftruncate
306	PTR	sys_fchmod
307	PTR	sys_fchown			/* 4095 */
308	PTR	sys_getpriority
309	PTR	sys_setpriority
310	PTR	sys_ni_syscall
311	PTR	compat_sys_statfs
312	PTR	compat_sys_fstatfs		/* 4100 */
313	PTR	sys_ni_syscall			/* sys_ioperm */
314	PTR	compat_sys_socketcall
315	PTR	sys_syslog
316	PTR	compat_sys_setitimer
317	PTR	compat_sys_getitimer		/* 4105 */
318	PTR	compat_sys_newstat
319	PTR	compat_sys_newlstat
320	PTR	compat_sys_newfstat
321	PTR	sys_uname
322	PTR	sys_ni_syscall			/* sys_ioperm  *//* 4110 */
323	PTR	sys_vhangup
324	PTR	sys_ni_syscall			/* was sys_idle	 */
325	PTR	sys_ni_syscall			/* sys_vm86 */
326	PTR	compat_sys_wait4
327	PTR	sys_swapoff			/* 4115 */
328	PTR	compat_sys_sysinfo
329	PTR	compat_sys_ipc
330	PTR	sys_fsync
331	PTR	sys32_sigreturn
332	PTR	__sys_clone			/* 4120 */
333	PTR	sys_setdomainname
334	PTR	sys_newuname
335	PTR	sys_ni_syscall			/* sys_modify_ldt */
336	PTR	compat_sys_adjtimex
337	PTR	sys_mprotect			/* 4125 */
338	PTR	compat_sys_sigprocmask
339	PTR	sys_ni_syscall			/* was creat_module */
340	PTR	sys_init_module
341	PTR	sys_delete_module
342	PTR	sys_ni_syscall			/* 4130, get_kernel_syms */
343	PTR	sys_quotactl
344	PTR	sys_getpgid
345	PTR	sys_fchdir
346	PTR	sys_bdflush
347	PTR	sys_sysfs			/* 4135 */
348	PTR	sys_32_personality
349	PTR	sys_ni_syscall			/* for afs_syscall */
350	PTR	sys_setfsuid
351	PTR	sys_setfsgid
352	PTR	sys_32_llseek			/* 4140 */
353	PTR	compat_sys_getdents
354	PTR	compat_sys_select
355	PTR	sys_flock
356	PTR	sys_msync
357	PTR	compat_sys_readv		/* 4145 */
358	PTR	compat_sys_writev
359	PTR	sys_cacheflush
360	PTR	sys_cachectl
361	PTR	sys_sysmips
362	PTR	sys_ni_syscall			/* 4150 */
363	PTR	sys_getsid
364	PTR	sys_fdatasync
365	PTR	compat_sys_sysctl
366	PTR	sys_mlock
367	PTR	sys_munlock			/* 4155 */
368	PTR	sys_mlockall
369	PTR	sys_munlockall
370	PTR	sys_sched_setparam
371	PTR	sys_sched_getparam
372	PTR	sys_sched_setscheduler		/* 4160 */
373	PTR	sys_sched_getscheduler
374	PTR	sys_sched_yield
375	PTR	sys_sched_get_priority_max
376	PTR	sys_sched_get_priority_min
377	PTR	compat_sys_sched_rr_get_interval	/* 4165 */
378	PTR	compat_sys_nanosleep
379	PTR	sys_mremap
380	PTR	sys_accept
381	PTR	sys_bind
382	PTR	sys_connect			/* 4170 */
383	PTR	sys_getpeername
384	PTR	sys_getsockname
385	PTR	sys_getsockopt
386	PTR	sys_listen
387	PTR	compat_sys_recv			/* 4175 */
388	PTR	compat_sys_recvfrom
389	PTR	compat_sys_recvmsg
390	PTR	sys_send
391	PTR	compat_sys_sendmsg
392	PTR	sys_sendto			/* 4180 */
393	PTR	compat_sys_setsockopt
394	PTR	sys_shutdown
395	PTR	sys_socket
396	PTR	sys_socketpair
397	PTR	sys_setresuid			/* 4185 */
398	PTR	sys_getresuid
399	PTR	sys_ni_syscall			/* was query_module */
400	PTR	sys_poll
401	PTR	sys_ni_syscall			/* was nfsservctl */
402	PTR	sys_setresgid			/* 4190 */
403	PTR	sys_getresgid
404	PTR	sys_prctl
405	PTR	sys32_rt_sigreturn
406	PTR	compat_sys_rt_sigaction
407	PTR	compat_sys_rt_sigprocmask	/* 4195 */
408	PTR	compat_sys_rt_sigpending
409	PTR	compat_sys_rt_sigtimedwait
410	PTR	compat_sys_rt_sigqueueinfo
411	PTR	compat_sys_rt_sigsuspend
412	PTR	sys_32_pread			/* 4200 */
413	PTR	sys_32_pwrite
414	PTR	sys_chown
415	PTR	sys_getcwd
416	PTR	sys_capget
417	PTR	sys_capset			/* 4205 */
418	PTR	compat_sys_sigaltstack
419	PTR	compat_sys_sendfile
420	PTR	sys_ni_syscall
421	PTR	sys_ni_syscall
422	PTR	sys_mips_mmap2			/* 4210 */
423	PTR	sys_32_truncate64
424	PTR	sys_32_ftruncate64
425	PTR	sys_newstat
426	PTR	sys_newlstat
427	PTR	sys_newfstat			/* 4215 */
428	PTR	sys_pivot_root
429	PTR	sys_mincore
430	PTR	sys_madvise
431	PTR	sys_getdents64
432	PTR	compat_sys_fcntl64		/* 4220 */
433	PTR	sys_ni_syscall
434	PTR	sys_gettid
435	PTR	sys32_readahead
436	PTR	sys_setxattr
437	PTR	sys_lsetxattr			/* 4225 */
438	PTR	sys_fsetxattr
439	PTR	sys_getxattr
440	PTR	sys_lgetxattr
441	PTR	sys_fgetxattr
442	PTR	sys_listxattr			/* 4230 */
443	PTR	sys_llistxattr
444	PTR	sys_flistxattr
445	PTR	sys_removexattr
446	PTR	sys_lremovexattr
447	PTR	sys_fremovexattr		/* 4235 */
448	PTR	sys_tkill
449	PTR	sys_sendfile64
450	PTR	compat_sys_futex
451	PTR	compat_sys_sched_setaffinity
452	PTR	compat_sys_sched_getaffinity	/* 4240 */
453	PTR	compat_sys_io_setup
454	PTR	sys_io_destroy
455	PTR	compat_sys_io_getevents
456	PTR	compat_sys_io_submit
457	PTR	sys_io_cancel			/* 4245 */
458	PTR	sys_exit_group
459	PTR	compat_sys_lookup_dcookie
460	PTR	sys_epoll_create
461	PTR	sys_epoll_ctl
462	PTR	sys_epoll_wait			/* 4250 */
463	PTR	sys_remap_file_pages
464	PTR	sys_set_tid_address
465	PTR	sys_restart_syscall
466	PTR	sys32_fadvise64_64
467	PTR	compat_sys_statfs64		/* 4255 */
468	PTR	compat_sys_fstatfs64
469	PTR	compat_sys_timer_create
470	PTR	compat_sys_timer_settime
471	PTR	compat_sys_timer_gettime
472	PTR	sys_timer_getoverrun		/* 4260 */
473	PTR	sys_timer_delete
474	PTR	compat_sys_clock_settime
475	PTR	compat_sys_clock_gettime
476	PTR	compat_sys_clock_getres
477	PTR	compat_sys_clock_nanosleep	/* 4265 */
478	PTR	sys_tgkill
479	PTR	compat_sys_utimes
480	PTR	compat_sys_mbind
481	PTR	compat_sys_get_mempolicy
482	PTR	compat_sys_set_mempolicy	/* 4270 */
483	PTR	compat_sys_mq_open
484	PTR	sys_mq_unlink
485	PTR	compat_sys_mq_timedsend
486	PTR	compat_sys_mq_timedreceive
487	PTR	compat_sys_mq_notify		/* 4275 */
488	PTR	compat_sys_mq_getsetattr
489	PTR	sys_ni_syscall			/* sys_vserver */
490	PTR	compat_sys_waitid
491	PTR	sys_ni_syscall			/* available, was setaltroot */
492	PTR	sys_add_key			/* 4280 */
493	PTR	sys_request_key
494	PTR	sys_keyctl
495	PTR	sys_set_thread_area
496	PTR	sys_inotify_init
497	PTR	sys_inotify_add_watch		/* 4285 */
498	PTR	sys_inotify_rm_watch
499	PTR	compat_sys_migrate_pages
500	PTR	compat_sys_openat
501	PTR	sys_mkdirat
502	PTR	sys_mknodat			/* 4290 */
503	PTR	sys_fchownat
504	PTR	compat_sys_futimesat
505	PTR	sys_newfstatat
506	PTR	sys_unlinkat
507	PTR	sys_renameat			/* 4295 */
508	PTR	sys_linkat
509	PTR	sys_symlinkat
510	PTR	sys_readlinkat
511	PTR	sys_fchmodat
512	PTR	sys_faccessat			/* 4300 */
513	PTR	compat_sys_pselect6
514	PTR	compat_sys_ppoll
515	PTR	sys_unshare
516	PTR	sys_splice
517	PTR	sys32_sync_file_range		/* 4305 */
518	PTR	sys_tee
519	PTR	compat_sys_vmsplice
520	PTR	compat_sys_move_pages
521	PTR	compat_sys_set_robust_list
522	PTR	compat_sys_get_robust_list	/* 4310 */
523	PTR	compat_sys_kexec_load
524	PTR	sys_getcpu
525	PTR	compat_sys_epoll_pwait
526	PTR	sys_ioprio_set
527	PTR	sys_ioprio_get			/* 4315 */
528	PTR	compat_sys_utimensat
529	PTR	compat_sys_signalfd
530	PTR	sys_ni_syscall			/* was timerfd */
531	PTR	sys_eventfd
532	PTR	sys32_fallocate			/* 4320 */
533	PTR	sys_timerfd_create
534	PTR	compat_sys_timerfd_gettime
535	PTR	compat_sys_timerfd_settime
536	PTR	compat_sys_signalfd4
537	PTR	sys_eventfd2			/* 4325 */
538	PTR	sys_epoll_create1
539	PTR	sys_dup3
540	PTR	sys_pipe2
541	PTR	sys_inotify_init1
542	PTR	compat_sys_preadv		/* 4330 */
543	PTR	compat_sys_pwritev
544	PTR	compat_sys_rt_tgsigqueueinfo
545	PTR	sys_perf_event_open
546	PTR	sys_accept4
547	PTR	compat_sys_recvmmsg		/* 4335 */
548	PTR	sys_fanotify_init
549	PTR	compat_sys_fanotify_mark
550	PTR	sys_prlimit64
551	PTR	sys_name_to_handle_at
552	PTR	compat_sys_open_by_handle_at	/* 4340 */
553	PTR	compat_sys_clock_adjtime
554	PTR	sys_syncfs
555	PTR	compat_sys_sendmmsg
556	PTR	sys_setns
557	PTR	compat_sys_process_vm_readv	/* 4345 */
558	PTR	compat_sys_process_vm_writev
559	PTR	sys_kcmp
560	PTR	sys_finit_module
561	PTR	sys_sched_setattr
562	PTR	sys_sched_getattr		/* 4350 */
563	PTR	sys_renameat2
564	PTR	sys_seccomp
565	PTR	sys_getrandom
566	PTR	sys_memfd_create
567	PTR	sys_bpf				/* 4355 */
568	.size	sys32_call_table,.-sys32_call_table
569