Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) /* SPDX-License-Identifier: GPL-2.0 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) #ifndef __ASM_SPARC_SYSCALL_H
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3) #define __ASM_SPARC_SYSCALL_H
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5) #include <uapi/linux/audit.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7) #include <linux/compat.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) #include <linux/sched.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) #include <asm/ptrace.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) #include <asm/thread_info.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13)  * The syscall table always contains 32 bit pointers since we know that the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14)  * address of the function to be called is (way) below 4GB.  So the "int"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15)  * type here is what we want [need] for both 32 bit and 64 bit systems.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16)  */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) extern const unsigned int sys_call_table[];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) /* The system call number is given by the user in %g1 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) static inline long syscall_get_nr(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) 				  struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) 	int syscall_p = pt_regs_is_syscall(regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) 	return (syscall_p ? regs->u_regs[UREG_G1] : -1L);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) static inline void syscall_rollback(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) 				    struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) 	/* XXX This needs some thought.  On Sparc we don't
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) 	 * XXX save away the original %o0 value somewhere.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) 	 * XXX Instead we hold it in register %l5 at the top
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 	 * XXX level trap frame and pass this down to the signal
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 	 * XXX dispatch code which is the only place that value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 	 * XXX ever was needed.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) 	 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) #ifdef CONFIG_SPARC32
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) static inline bool syscall_has_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 	return (regs->psr & PSR_C) ? true : false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) static inline void syscall_set_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 	regs->psr |= PSR_C;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) static inline void syscall_clear_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	regs->psr &= ~PSR_C;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) static inline bool syscall_has_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 	return (regs->tstate & (TSTATE_XCARRY | TSTATE_ICARRY)) ? true : false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) static inline void syscall_set_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 	regs->tstate |= (TSTATE_XCARRY | TSTATE_ICARRY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) static inline void syscall_clear_error(struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) 	regs->tstate &= ~(TSTATE_XCARRY | TSTATE_ICARRY);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) static inline long syscall_get_error(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) 				     struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) 	long val = regs->u_regs[UREG_I0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) 	return (syscall_has_error(regs) ? -val : 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) static inline long syscall_get_return_value(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) 					    struct pt_regs *regs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) 	long val = regs->u_regs[UREG_I0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) 	return val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) static inline void syscall_set_return_value(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) 					    struct pt_regs *regs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) 					    int error, long val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) 	if (error) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) 		syscall_set_error(regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) 		regs->u_regs[UREG_I0] = -error;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) 	} else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) 		syscall_clear_error(regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) 		regs->u_regs[UREG_I0] = val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) static inline void syscall_get_arguments(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) 					 struct pt_regs *regs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) 					 unsigned long *args)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) 	int zero_extend = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) 	unsigned int j;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 	unsigned int n = 6;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) #ifdef CONFIG_SPARC64
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) 	if (test_tsk_thread_flag(task, TIF_32BIT))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 		zero_extend = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 	for (j = 0; j < n; j++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 		unsigned long val = regs->u_regs[UREG_I0 + j];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) 		if (zero_extend)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 			args[j] = (u32) val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 		else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 			args[j] = val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 	}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) static inline void syscall_set_arguments(struct task_struct *task,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) 					 struct pt_regs *regs,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 					 const unsigned long *args)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) 	unsigned int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 	for (i = 0; i < 6; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) 		regs->u_regs[UREG_I0 + i] = args[i];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) static inline int syscall_get_arch(struct task_struct *task)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) #if defined(CONFIG_SPARC64) && defined(CONFIG_COMPAT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) 	return test_tsk_thread_flag(task, TIF_32BIT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 		? AUDIT_ARCH_SPARC : AUDIT_ARCH_SPARC64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) #elif defined(CONFIG_SPARC64)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 	return AUDIT_ARCH_SPARC64;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 	return AUDIT_ARCH_SPARC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) #endif /* __ASM_SPARC_SYSCALL_H */