Skip to content

Commit

Permalink
Merge tag 'riscv-for-linus-4.16-merge_window' of git://git.kernel.org…
Browse files Browse the repository at this point in the history
…/pub/scm/linux/kernel/git/palmer/riscv-linux

Pull RISC-V updates from Palmer Dabbelt:
 "This contains the fixes we'd like to target for the 4.16 merge window.
  It's not as much as I was originally hoping to do but between glibc,
  the chip, and FOSDEM there just wasn't enough time to get everything
  put together. As such, this merge window is essentially just going to
  be small changes. This includes mostly cleanups:

   - A build fix failure to the audit test cases.

     RISC-V doesn't have renameat because the generic syscall ABI moved
     to renameat2 by the time of our port. The syscall audit test cases
     don't understand this, so I added a trivial fix. This went through
     mailing list review during the 4.15 merge window, but nobody has
     picked it up so I think it's best to just do this here.

   - The removal of our command-line argument processing code. The
     "mem_end" stuff was broken and the rest duplicated generic device
     tree code. The generic code was already being called.

   - Some unused/redundant code has been removed, including
     __ARCH_HAVE_MMU, current_pgdir, and the initialization of
     init_mm.pgd.

   - SUM is disabled upon taking a trap, which means that user memory is
     protected during traps taking inside copy_{to,from}_user().

   - The sptbr CSR has been renamed to satp in C code. We haven't
     changed the assembly code in order to maintain compatibility with
     binutils 2.29, which doesn't understand the new name.

  Additionally, we're adding some new features:

   - Basic ftrace support, thanks to Alan Kao!

   - Support for ZONE_DMA32.

     This is necessary for all the normal reasons, but also to deal with
     a deficiency in the Xilinx PCIe controller we're using on our
     FPGA-based systems. While the ZONE_DMA32 addition should be
     sufficient for most uses, it doesn't complete the fix for the
     Xilinx controller.

   - TLB shootdowns now only target the harts where they're necessary,
     instead of applying to all harts in the system.

  These patches have all been sitting on our linux-next branch for a
  while now. Due to time constraints this is all I feel comfortable
  submitting during the 4.16 merge window, hopefully we'll do better
  next time!"

[ Note to self: "harts" is RISC-V speak for "hardware threads".  I had
  to look that up.    - Linus ]

* tag 'riscv-for-linus-4.16-merge_window' of git://git.kernel.org/pub/scm/linux/kernel/git/palmer/riscv-linux:
  riscv: inline set_pgdir into its only caller
  riscv: rename sptbr to satp
  riscv: don't read back satp in paging_init
  riscv: remove the unused current_pgdir function
  riscv: add ZONE_DMA32
  RISC-V: Limit the scope of TLB shootdowns
  riscv: disable SUM in the exception handler
  riscv: remove redundant unlikely()
  riscv: remove unused __ARCH_HAVE_MMU define
  riscv/ftrace: Add basic support
  RISC-V: Remove mem_end command line processing
  RISC-V: Remove duplicate command-line parsing logic
  audit: Avoid build failures on systems without renameat
  • Loading branch information
Linus Torvalds committed Feb 7, 2018
2 parents 0bd2afc + 4889dec commit 413879a
Show file tree
Hide file tree
Showing 17 changed files with 250 additions and 76 deletions.
10 changes: 10 additions & 0 deletions arch/riscv/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ config RISCV
select GENERIC_ATOMIC64 if !64BIT || !RISCV_ISA_A
select ARCH_WANT_OPTIONAL_GPIOLIB
select HAVE_MEMBLOCK
select HAVE_MEMBLOCK_NODE_MAP
select HAVE_DMA_API_DEBUG
select HAVE_DMA_CONTIGUOUS
select HAVE_GENERIC_DMA_COHERENT
Expand All @@ -43,6 +44,10 @@ config MMU
config ARCH_PHYS_ADDR_T_64BIT
def_bool y

config ZONE_DMA32
bool
default y

config ARCH_DMA_ADDR_T_64BIT
def_bool y

Expand All @@ -55,6 +60,9 @@ config PAGE_OFFSET
config STACKTRACE_SUPPORT
def_bool y

config TRACE_IRQFLAGS_SUPPORT
def_bool y

config RWSEM_GENERIC_SPINLOCK
def_bool y

Expand Down Expand Up @@ -107,6 +115,8 @@ config ARCH_RV64I
bool "RV64I"
select CPU_SUPPORTS_64BIT_KERNEL
select 64BIT
select HAVE_FUNCTION_TRACER
select HAVE_FUNCTION_GRAPH_TRACER

endchoice

Expand Down
1 change: 0 additions & 1 deletion arch/riscv/include/asm/Kbuild
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ generic-y += errno.h
generic-y += exec.h
generic-y += fb.h
generic-y += fcntl.h
generic-y += ftrace.h
generic-y += futex.h
generic-y += hardirq.h
generic-y += hash.h
Expand Down
14 changes: 7 additions & 7 deletions arch/riscv/include/asm/csr.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,15 +40,15 @@
#define SR_SD _AC(0x8000000000000000, UL) /* FS/XS dirty */
#endif

/* SPTBR flags */
/* SATP flags */
#if __riscv_xlen == 32
#define SPTBR_PPN _AC(0x003FFFFF, UL)
#define SPTBR_MODE_32 _AC(0x80000000, UL)
#define SPTBR_MODE SPTBR_MODE_32
#define SATP_PPN _AC(0x003FFFFF, UL)
#define SATP_MODE_32 _AC(0x80000000, UL)
#define SATP_MODE SATP_MODE_32
#else
#define SPTBR_PPN _AC(0x00000FFFFFFFFFFF, UL)
#define SPTBR_MODE_39 _AC(0x8000000000000000, UL)
#define SPTBR_MODE SPTBR_MODE_39
#define SATP_PPN _AC(0x00000FFFFFFFFFFF, UL)
#define SATP_MODE_39 _AC(0x8000000000000000, UL)
#define SATP_MODE SATP_MODE_39
#endif

/* Interrupt Enable and Interrupt Pending flags */
Expand Down
10 changes: 10 additions & 0 deletions arch/riscv/include/asm/ftrace.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
/* SPDX-License-Identifier: GPL-2.0 */
/* Copyright (C) 2017 Andes Technology Corporation */

/*
* The graph frame test is not possible if CONFIG_FRAME_POINTER is not enabled.
* Check arch/riscv/kernel/mcount.S for detail.
*/
#if defined(CONFIG_FUNCTION_GRAPH_TRACER) && defined(CONFIG_FRAME_POINTER)
#define HAVE_FUNCTION_GRAPH_FP_TEST
#endif
17 changes: 6 additions & 11 deletions arch/riscv/include/asm/mmu_context.h
Original file line number Diff line number Diff line change
Expand Up @@ -39,16 +39,6 @@ static inline void destroy_context(struct mm_struct *mm)
{
}

static inline pgd_t *current_pgdir(void)
{
return pfn_to_virt(csr_read(sptbr) & SPTBR_PPN);
}

static inline void set_pgdir(pgd_t *pgd)
{
csr_write(sptbr, virt_to_pfn(pgd) | SPTBR_MODE);
}

/*
* When necessary, performs a deferred icache flush for the given MM context,
* on the local CPU. RISC-V has no direct mechanism for instruction cache
Expand Down Expand Up @@ -93,7 +83,12 @@ static inline void switch_mm(struct mm_struct *prev,
cpumask_clear_cpu(cpu, mm_cpumask(prev));
cpumask_set_cpu(cpu, mm_cpumask(next));

set_pgdir(next->pgd);
/*
* Use the old spbtr name instead of using the current satp
* name to support binutils 2.29 which doesn't know about the
* privileged ISA 1.10 yet.
*/
csr_write(sptbr, virt_to_pfn(next->pgd) | SATP_MODE);
local_flush_tlb_all();

flush_icache_deferred(next);
Expand Down
20 changes: 12 additions & 8 deletions arch/riscv/include/asm/tlbflush.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,14 @@ static inline void local_flush_tlb_page(unsigned long addr)

#define flush_tlb_all() local_flush_tlb_all()
#define flush_tlb_page(vma, addr) local_flush_tlb_page(addr)
#define flush_tlb_range(vma, start, end) local_flush_tlb_all()

static inline void flush_tlb_range(struct vm_area_struct *vma,
unsigned long start, unsigned long end)
{
local_flush_tlb_all();
}

#define flush_tlb_mm(mm) flush_tlb_all()

#else /* CONFIG_SMP */

Expand All @@ -45,16 +52,13 @@ static inline void local_flush_tlb_page(unsigned long addr)
#define flush_tlb_all() sbi_remote_sfence_vma(0, 0, -1)
#define flush_tlb_page(vma, addr) flush_tlb_range(vma, addr, 0)
#define flush_tlb_range(vma, start, end) \
sbi_remote_sfence_vma(0, start, (end) - (start))
sbi_remote_sfence_vma(mm_cpumask((vma)->vm_mm)->bits, \
start, (end) - (start))
#define flush_tlb_mm(mm) \
sbi_remote_sfence_vma(mm_cpumask(mm)->bits, 0, -1)

#endif /* CONFIG_SMP */

/* Flush the TLB entries of the specified mm context */
static inline void flush_tlb_mm(struct mm_struct *mm)
{
flush_tlb_all();
}

/* Flush a range of kernel pages */
static inline void flush_tlb_kernel_range(unsigned long start,
unsigned long end)
Expand Down
1 change: 0 additions & 1 deletion arch/riscv/include/asm/unistd.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@
* GNU General Public License for more details.
*/

#define __ARCH_HAVE_MMU
#define __ARCH_WANT_SYS_CLONE
#include <uapi/asm/unistd.h>
#include <uapi/asm/syscalls.h>
7 changes: 7 additions & 0 deletions arch/riscv/kernel/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@
# Makefile for the RISC-V Linux kernel
#

ifdef CONFIG_FTRACE
CFLAGS_REMOVE_ftrace.o = -pg
CFLAGS_REMOVE_setup.o = -pg
endif

extra-y += head.o
extra-y += vmlinux.lds

Expand Down Expand Up @@ -29,5 +34,7 @@ CFLAGS_setup.o := -mcmodel=medany
obj-$(CONFIG_SMP) += smpboot.o
obj-$(CONFIG_SMP) += smp.o
obj-$(CONFIG_MODULES) += module.o
obj-$(CONFIG_FUNCTION_TRACER) += mcount.o
obj-$(CONFIG_FUNCTION_GRAPH_TRACER) += ftrace.o

clean:
9 changes: 6 additions & 3 deletions arch/riscv/kernel/entry.S
Original file line number Diff line number Diff line change
Expand Up @@ -78,10 +78,13 @@ _save_context:
REG_S x31, PT_T6(sp)

/*
* Disable FPU to detect illegal usage of
* floating point in kernel space
* Disable user-mode memory access as it should only be set in the
* actual user copy routines.
*
* Disable the FPU to detect illegal usage of floating point in kernel
* space.
*/
li t0, SR_FS
li t0, SR_SUM | SR_FS

REG_L s0, TASK_TI_USER_SP(tp)
csrrc s1, sstatus, t0
Expand Down
41 changes: 41 additions & 0 deletions arch/riscv/kernel/ftrace.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2013 Linaro Limited
* Author: AKASHI Takahiro <takahiro.akashi@linaro.org>
* Copyright (C) 2017 Andes Technology Corporation
*/

#include <linux/ftrace.h>

/*
* Most of this file is copied from arm64.
*/
void prepare_ftrace_return(unsigned long *parent, unsigned long self_addr,
unsigned long frame_pointer)
{
unsigned long return_hooker = (unsigned long)&return_to_handler;
unsigned long old;
struct ftrace_graph_ent trace;
int err;

if (unlikely(atomic_read(&current->tracing_graph_pause)))
return;

/*
* We don't suffer access faults, so no extra fault-recovery assembly
* is needed here.
*/
old = *parent;

trace.func = self_addr;
trace.depth = current->curr_ret_stack + 1;

if (!ftrace_graph_entry(&trace))
return;

err = ftrace_push_return_trace(old, self_addr, &trace.depth,
frame_pointer, NULL);
if (err == -EBUSY)
return;
*parent = return_hooker;
}
6 changes: 3 additions & 3 deletions arch/riscv/kernel/head.S
Original file line number Diff line number Diff line change
Expand Up @@ -74,15 +74,15 @@ relocate:
sub a1, a1, a0
add ra, ra, a1

/* Point stvec to virtual address of intruction after sptbr write */
/* Point stvec to virtual address of intruction after satp write */
la a0, 1f
add a0, a0, a1
csrw stvec, a0

/* Compute sptbr for kernel page tables, but don't load it yet */
/* Compute satp for kernel page tables, but don't load it yet */
la a2, swapper_pg_dir
srl a2, a2, PAGE_SHIFT
li a1, SPTBR_MODE
li a1, SATP_MODE
or a2, a2, a1

/*
Expand Down
126 changes: 126 additions & 0 deletions arch/riscv/kernel/mcount.S
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
/* SPDX-License-Identifier: GPL-2.0 */
/* Copyright (C) 2017 Andes Technology Corporation */

#include <linux/init.h>
#include <linux/linkage.h>
#include <asm/asm.h>
#include <asm/csr.h>
#include <asm/unistd.h>
#include <asm/thread_info.h>
#include <asm/asm-offsets.h>
#include <asm-generic/export.h>
#include <asm/ftrace.h>

.text

.macro SAVE_ABI_STATE
addi sp, sp, -16
sd s0, 0(sp)
sd ra, 8(sp)
addi s0, sp, 16
.endm

/*
* The call to ftrace_return_to_handler would overwrite the return
* register if a0 was not saved.
*/
.macro SAVE_RET_ABI_STATE
addi sp, sp, -32
sd s0, 16(sp)
sd ra, 24(sp)
sd a0, 8(sp)
addi s0, sp, 32
.endm

.macro STORE_ABI_STATE
ld ra, 8(sp)
ld s0, 0(sp)
addi sp, sp, 16
.endm

.macro STORE_RET_ABI_STATE
ld ra, 24(sp)
ld s0, 16(sp)
ld a0, 8(sp)
addi sp, sp, 32
.endm

ENTRY(ftrace_stub)
ret
ENDPROC(ftrace_stub)

#ifdef CONFIG_FUNCTION_GRAPH_TRACER
ENTRY(return_to_handler)
/*
* On implementing the frame point test, the ideal way is to compare the
* s0 (frame pointer, if enabled) on entry and the sp (stack pointer) on return.
* However, the psABI of variable-length-argument functions does not allow this.
*
* So alternatively we check the *old* frame pointer position, that is, the
* value stored in -16(s0) on entry, and the s0 on return.
*/
#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
mv t6, s0
#endif
SAVE_RET_ABI_STATE
#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
mv a0, t6
#endif
la t0, ftrace_return_to_handler
jalr t0
mv a1, a0
STORE_RET_ABI_STATE
jalr a1
ENDPROC(return_to_handler)
EXPORT_SYMBOL(return_to_handler)
#endif

ENTRY(_mcount)
la t4, ftrace_stub
#ifdef CONFIG_FUNCTION_GRAPH_TRACER
la t0, ftrace_graph_return
ld t1, 0(t0)
bne t1, t4, do_ftrace_graph_caller

la t3, ftrace_graph_entry
ld t2, 0(t3)
la t6, ftrace_graph_entry_stub
bne t2, t6, do_ftrace_graph_caller
#endif
la t3, ftrace_trace_function
ld t5, 0(t3)
bne t5, t4, do_trace
ret

#ifdef CONFIG_FUNCTION_GRAPH_TRACER
/*
* A pseudo representation for the function graph tracer:
* prepare_to_return(&ra_to_caller_of_caller, ra_to_caller)
*/
do_ftrace_graph_caller:
addi a0, s0, -8
mv a1, ra
#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
ld a2, -16(s0)
#endif
SAVE_ABI_STATE
la t0, prepare_ftrace_return
jalr t0
STORE_ABI_STATE
ret
#endif

/*
* A pseudo representation for the function tracer:
* (*ftrace_trace_function)(ra_to_caller, ra_to_caller_of_caller)
*/
do_trace:
ld a1, -8(s0)
mv a0, ra

SAVE_ABI_STATE
jalr t5
STORE_ABI_STATE
ret
ENDPROC(_mcount)
EXPORT_SYMBOL(_mcount)
Loading

0 comments on commit 413879a

Please sign in to comment.