MIPS: scall: Handle seccomp filters which redirect syscalls
[cascardo/linux.git] / arch / mips / kernel / scall64-o32.S
index 91b43ee..f4f28b1 100644 (file)
@@ -52,9 +52,6 @@ NESTED(handle_sys, PT_SIZE, sp)
        sll     a2, a2, 0
        sll     a3, a3, 0
 
-       dsll    t0, v0, 3               # offset into table
-       ld      t2, (sys32_call_table - (__NR_O32_Linux * 8))(t0)
-
        sd      a3, PT_R26(sp)          # save a3 for syscall restarting
 
        /*
@@ -88,6 +85,9 @@ loads_done:
        bnez    t0, trace_a_syscall
 
 syscall_common:
+       dsll    t0, v0, 3               # offset into table
+       ld      t2, (sys32_call_table - (__NR_O32_Linux * 8))(t0)
+
        jalr    t2                      # Do The Real Thing (TM)
 
        li      t0, -EMAXERRNO - 1      # error?
@@ -112,7 +112,6 @@ trace_a_syscall:
        sd      a6, PT_R10(sp)
        sd      a7, PT_R11(sp)          # For indirect syscalls
 
-       move    s0, t2                  # Save syscall pointer
        move    a0, sp
        /*
         * absolute syscall number is in v0 unless we called syscall(__NR_###)
@@ -133,8 +132,8 @@ trace_a_syscall:
 
        bltz    v0, 1f                  # seccomp failed? Skip syscall
 
-       move    t2, s0
        RESTORE_STATIC
+       ld      v0, PT_R2(sp)           # Restore syscall (maybe modified)
        ld      a0, PT_R4(sp)           # Restore argument registers
        ld      a1, PT_R5(sp)
        ld      a2, PT_R6(sp)
@@ -143,6 +142,11 @@ trace_a_syscall:
        ld      a5, PT_R9(sp)
        ld      a6, PT_R10(sp)
        ld      a7, PT_R11(sp)          # For indirect syscalls
+
+       dsubu   t0, v0, __NR_O32_Linux  # check (new) syscall number
+       sltiu   t0, t0, __NR_O32_Linux_syscalls + 1
+       beqz    t0, not_o32_scall
+
        j       syscall_common
 
 1:     j       syscall_exit