diff options
Diffstat (limited to 'arch/sparc64/kernel/sys_sparc.c')
-rw-r--r-- | arch/sparc64/kernel/sys_sparc.c | 21 |
1 files changed, 21 insertions, 0 deletions
diff --git a/arch/sparc64/kernel/sys_sparc.c b/arch/sparc64/kernel/sys_sparc.c index 89ac435aacc0..a53d4abb4b49 100644 --- a/arch/sparc64/kernel/sys_sparc.c +++ b/arch/sparc64/kernel/sys_sparc.c | |||
@@ -31,6 +31,7 @@ | |||
31 | #include <asm/utrap.h> | 31 | #include <asm/utrap.h> |
32 | #include <asm/perfctr.h> | 32 | #include <asm/perfctr.h> |
33 | #include <asm/a.out.h> | 33 | #include <asm/a.out.h> |
34 | #include <asm/unistd.h> | ||
34 | 35 | ||
35 | /* #define DEBUG_UNIMP_SYSCALL */ | 36 | /* #define DEBUG_UNIMP_SYSCALL */ |
36 | 37 | ||
@@ -963,3 +964,23 @@ asmlinkage long sys_perfctr(int opcode, unsigned long arg0, unsigned long arg1, | |||
963 | }; | 964 | }; |
964 | return err; | 965 | return err; |
965 | } | 966 | } |
967 | |||
968 | /* | ||
969 | * Do a system call from kernel instead of calling sys_execve so we | ||
970 | * end up with proper pt_regs. | ||
971 | */ | ||
972 | int kernel_execve(const char *filename, char *const argv[], char *const envp[]) | ||
973 | { | ||
974 | long __res; | ||
975 | register long __g1 __asm__ ("g1") = __NR_execve; | ||
976 | register long __o0 __asm__ ("o0") = (long)(filename); | ||
977 | register long __o1 __asm__ ("o1") = (long)(argv); | ||
978 | register long __o2 __asm__ ("o2") = (long)(envp); | ||
979 | asm volatile ("t 0x6d\n\t" | ||
980 | "sub %%g0, %%o0, %0\n\t" | ||
981 | "movcc %%xcc, %%o0, %0\n\t" | ||
982 | : "=r" (__res), "=&r" (__o0) | ||
983 | : "1" (__o0), "r" (__o1), "r" (__o2), "r" (__g1) | ||
984 | : "cc"); | ||
985 | return __res; | ||
986 | } | ||