cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

mcount.S (2641B)


      1/* SPDX-License-Identifier: GPL-2.0 */
      2/* Copyright (C) 2017 Andes Technology Corporation */
      3
      4#include <linux/init.h>
      5#include <linux/linkage.h>
      6#include <asm/asm.h>
      7#include <asm/csr.h>
      8#include <asm/unistd.h>
      9#include <asm/thread_info.h>
     10#include <asm/asm-offsets.h>
     11#include <asm-generic/export.h>
     12#include <asm/ftrace.h>
     13
     14	.text
     15
     16	.macro SAVE_ABI_STATE
     17	addi	sp, sp, -16
     18	sd	s0, 0(sp)
     19	sd	ra, 8(sp)
     20	addi	s0, sp, 16
     21	.endm
     22
     23	/*
     24	 * The call to ftrace_return_to_handler would overwrite the return
     25	 * register if a0 was not saved.
     26	 */
     27	.macro SAVE_RET_ABI_STATE
     28	addi	sp, sp, -32
     29	sd	s0, 16(sp)
     30	sd	ra, 24(sp)
     31	sd	a0, 8(sp)
     32	addi	s0, sp, 32
     33	.endm
     34
     35	.macro RESTORE_ABI_STATE
     36	ld	ra, 8(sp)
     37	ld	s0, 0(sp)
     38	addi	sp, sp, 16
     39	.endm
     40
     41	.macro RESTORE_RET_ABI_STATE
     42	ld	ra, 24(sp)
     43	ld	s0, 16(sp)
     44	ld	a0, 8(sp)
     45	addi	sp, sp, 32
     46	.endm
     47
     48ENTRY(ftrace_stub)
     49#ifdef CONFIG_DYNAMIC_FTRACE
     50       .global MCOUNT_NAME
     51       .set    MCOUNT_NAME, ftrace_stub
     52#endif
     53	ret
     54ENDPROC(ftrace_stub)
     55
     56#ifdef CONFIG_FUNCTION_GRAPH_TRACER
     57ENTRY(return_to_handler)
     58/*
     59 * On implementing the frame point test, the ideal way is to compare the
     60 * s0 (frame pointer, if enabled) on entry and the sp (stack pointer) on return.
     61 * However, the psABI of variable-length-argument functions does not allow this.
     62 *
     63 * So alternatively we check the *old* frame pointer position, that is, the
     64 * value stored in -16(s0) on entry, and the s0 on return.
     65 */
     66#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
     67	mv	t6, s0
     68#endif
     69	SAVE_RET_ABI_STATE
     70#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
     71	mv	a0, t6
     72#endif
     73	call	ftrace_return_to_handler
     74	mv	a1, a0
     75	RESTORE_RET_ABI_STATE
     76	jalr	a1
     77ENDPROC(return_to_handler)
     78#endif
     79
     80#ifndef CONFIG_DYNAMIC_FTRACE
     81ENTRY(MCOUNT_NAME)
     82	la	t4, ftrace_stub
     83#ifdef CONFIG_FUNCTION_GRAPH_TRACER
     84	la	t0, ftrace_graph_return
     85	ld	t1, 0(t0)
     86	bne	t1, t4, do_ftrace_graph_caller
     87
     88	la	t3, ftrace_graph_entry
     89	ld	t2, 0(t3)
     90	la	t6, ftrace_graph_entry_stub
     91	bne	t2, t6, do_ftrace_graph_caller
     92#endif
     93	la	t3, ftrace_trace_function
     94	ld	t5, 0(t3)
     95	bne	t5, t4, do_trace
     96	ret
     97
     98#ifdef CONFIG_FUNCTION_GRAPH_TRACER
     99/*
    100 * A pseudo representation for the function graph tracer:
    101 * prepare_to_return(&ra_to_caller_of_caller, ra_to_caller)
    102 */
    103do_ftrace_graph_caller:
    104	addi	a0, s0, -8
    105	mv	a1, ra
    106#ifdef HAVE_FUNCTION_GRAPH_FP_TEST
    107	ld	a2, -16(s0)
    108#endif
    109	SAVE_ABI_STATE
    110	call	prepare_ftrace_return
    111	RESTORE_ABI_STATE
    112	ret
    113#endif
    114
    115/*
    116 * A pseudo representation for the function tracer:
    117 * (*ftrace_trace_function)(ra_to_caller, ra_to_caller_of_caller)
    118 */
    119do_trace:
    120	ld	a1, -8(s0)
    121	mv	a0, ra
    122
    123	SAVE_ABI_STATE
    124	jalr	t5
    125	RESTORE_ABI_STATE
    126	ret
    127ENDPROC(MCOUNT_NAME)
    128#endif
    129EXPORT_SYMBOL(MCOUNT_NAME)