lkml.org 
[lkml]   [2020]   [Aug]   [12]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[RFC PATCH v1 04/19] powerpc/ptrace: Create ptrace_get_fpr() and ptrace_put_fpr()
    Date
    On the same model as ptrace_get_reg() and ptrace_put_reg(),
    create ptrace_get_fpr() and ptrace_put_fpr() to get/set
    the floating points registers.

    We move the boundary checkings in them.

    Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
    ---
    arch/powerpc/kernel/ptrace/Makefile | 1 +
    arch/powerpc/kernel/ptrace/ptrace-decl.h | 4 +++
    arch/powerpc/kernel/ptrace/ptrace-fpu.c | 40 ++++++++++++++++++++++++
    arch/powerpc/kernel/ptrace/ptrace.c | 38 +++++++---------------
    4 files changed, 56 insertions(+), 27 deletions(-)
    create mode 100644 arch/powerpc/kernel/ptrace/ptrace-fpu.c

    diff --git a/arch/powerpc/kernel/ptrace/Makefile b/arch/powerpc/kernel/ptrace/Makefile
    index c2f2402ebc8c..77abd1a5a508 100644
    --- a/arch/powerpc/kernel/ptrace/Makefile
    +++ b/arch/powerpc/kernel/ptrace/Makefile
    @@ -6,6 +6,7 @@
    CFLAGS_ptrace-view.o += -DUTS_MACHINE='"$(UTS_MACHINE)"'

    obj-y += ptrace.o ptrace-view.o
    +obj-y += ptrace-fpu.o
    obj-$(CONFIG_COMPAT) += ptrace32.o
    obj-$(CONFIG_VSX) += ptrace-vsx.o
    ifneq ($(CONFIG_VSX),y)
    diff --git a/arch/powerpc/kernel/ptrace/ptrace-decl.h b/arch/powerpc/kernel/ptrace/ptrace-decl.h
    index 2ddc68412fa8..eafe5f0f6289 100644
    --- a/arch/powerpc/kernel/ptrace/ptrace-decl.h
    +++ b/arch/powerpc/kernel/ptrace/ptrace-decl.h
    @@ -164,6 +164,10 @@ int ptrace_put_reg(struct task_struct *task, int regno, unsigned long data);

    extern const struct user_regset_view user_ppc_native_view;

    +/* ptrace-fpu */
    +int ptrace_get_fpr(struct task_struct *child, int index, unsigned long *data);
    +int ptrace_put_fpr(struct task_struct *child, int index, unsigned long data);
    +
    /* ptrace-(no)adv */
    void ppc_gethwdinfo(struct ppc_debug_info *dbginfo);
    int ptrace_get_debugreg(struct task_struct *child, unsigned long addr,
    diff --git a/arch/powerpc/kernel/ptrace/ptrace-fpu.c b/arch/powerpc/kernel/ptrace/ptrace-fpu.c
    new file mode 100644
    index 000000000000..8301cb52dd99
    --- /dev/null
    +++ b/arch/powerpc/kernel/ptrace/ptrace-fpu.c
    @@ -0,0 +1,40 @@
    +// SPDX-License-Identifier: GPL-2.0-or-later
    +
    +#include <linux/regset.h>
    +
    +#include <asm/switch_to.h>
    +
    +#include "ptrace-decl.h"
    +
    +int ptrace_get_fpr(struct task_struct *child, int index, unsigned long *data)
    +{
    + unsigned int fpidx = index - PT_FPR0;
    +
    + if (index > PT_FPSCR)
    + return -EIO;
    +
    + flush_fp_to_thread(child);
    + if (fpidx < (PT_FPSCR - PT_FPR0))
    + memcpy(data, &child->thread.TS_FPR(fpidx), sizeof(long));
    + else
    + *data = child->thread.fp_state.fpscr;
    +
    + return 0;
    +}
    +
    +int ptrace_put_fpr(struct task_struct *child, int index, unsigned long data)
    +{
    + unsigned int fpidx = index - PT_FPR0;
    +
    + if (index > PT_FPSCR)
    + return -EIO;
    +
    + flush_fp_to_thread(child);
    + if (fpidx < (PT_FPSCR - PT_FPR0))
    + memcpy(&child->thread.TS_FPR(fpidx), &data, sizeof(long));
    + else
    + child->thread.fp_state.fpscr = data;
    +
    + return 0;
    +}
    +
    diff --git a/arch/powerpc/kernel/ptrace/ptrace.c b/arch/powerpc/kernel/ptrace/ptrace.c
    index 0b4645a7a1b4..3d44b73adb83 100644
    --- a/arch/powerpc/kernel/ptrace/ptrace.c
    +++ b/arch/powerpc/kernel/ptrace/ptrace.c
    @@ -56,24 +56,17 @@ long arch_ptrace(struct task_struct *child, long request,
    ret = -EIO;
    /* convert to index and check */
    index = addr / sizeof(long);
    - if ((addr & (sizeof(long) - 1)) || (index > PT_FPSCR) || !child->thread.regs)
    + if ((addr & (sizeof(long) - 1)) || !child->thread.regs)
    break;

    CHECK_FULL_REGS(child->thread.regs);
    - if (index < PT_FPR0) {
    + if (index < PT_FPR0)
    ret = ptrace_get_reg(child, (int) index, &tmp);
    - if (ret)
    - break;
    - } else {
    - unsigned int fpidx = index - PT_FPR0;
    -
    - flush_fp_to_thread(child);
    - if (fpidx < (PT_FPSCR - PT_FPR0))
    - memcpy(&tmp, &child->thread.TS_FPR(fpidx),
    - sizeof(long));
    - else
    - tmp = child->thread.fp_state.fpscr;
    - }
    + else
    + ret = ptrace_get_fpr(child, index, &tmp);
    +
    + if (ret)
    + break;
    ret = put_user(tmp, datalp);
    break;
    }
    @@ -85,23 +78,14 @@ long arch_ptrace(struct task_struct *child, long request,
    ret = -EIO;
    /* convert to index and check */
    index = addr / sizeof(long);
    - if ((addr & (sizeof(long) - 1)) || (index > PT_FPSCR) || !child->thread.regs)
    + if ((addr & (sizeof(long) - 1)) || !child->thread.regs)
    break;

    CHECK_FULL_REGS(child->thread.regs);
    - if (index < PT_FPR0) {
    + if (index < PT_FPR0)
    ret = ptrace_put_reg(child, index, data);
    - } else {
    - unsigned int fpidx = index - PT_FPR0;
    -
    - flush_fp_to_thread(child);
    - if (fpidx < (PT_FPSCR - PT_FPR0))
    - memcpy(&child->thread.TS_FPR(fpidx), &data,
    - sizeof(long));
    - else
    - child->thread.fp_state.fpscr = data;
    - ret = 0;
    - }
    + else
    + ret = ptrace_put_fpr(child, index, data);
    break;
    }

    --
    2.25.0
    \
     
     \ /
      Last update: 2020-08-12 14:08    [W:5.162 / U:0.008 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site