xref: /openbmc/linux/arch/riscv/include/asm/bug.h (revision 69505e3d)
150acfb2bSThomas Gleixner /* SPDX-License-Identifier: GPL-2.0-only */
276d2a049SPalmer Dabbelt /*
376d2a049SPalmer Dabbelt  * Copyright (C) 2012 Regents of the University of California
476d2a049SPalmer Dabbelt  */
576d2a049SPalmer Dabbelt 
676d2a049SPalmer Dabbelt #ifndef _ASM_RISCV_BUG_H
776d2a049SPalmer Dabbelt #define _ASM_RISCV_BUG_H
876d2a049SPalmer Dabbelt 
976d2a049SPalmer Dabbelt #include <linux/compiler.h>
1076d2a049SPalmer Dabbelt #include <linux/const.h>
1176d2a049SPalmer Dabbelt #include <linux/types.h>
1276d2a049SPalmer Dabbelt 
1376d2a049SPalmer Dabbelt #include <asm/asm.h>
1476d2a049SPalmer Dabbelt 
15ee72e0e7SVincent Chen #define __INSN_LENGTH_MASK  _UL(0x3)
16ee72e0e7SVincent Chen #define __INSN_LENGTH_32    _UL(0x3)
17ee72e0e7SVincent Chen #define __COMPRESSED_INSN_MASK	_UL(0xffff)
18ee72e0e7SVincent Chen 
19ee72e0e7SVincent Chen #define __BUG_INSN_32	_UL(0x00100073) /* ebreak */
20ee72e0e7SVincent Chen #define __BUG_INSN_16	_UL(0x9002) /* c.ebreak */
2176d2a049SPalmer Dabbelt 
22b42d763aSZong Li #define GET_INSN_LENGTH(insn)						\
23b42d763aSZong Li ({									\
24b42d763aSZong Li 	unsigned long __len;						\
25b42d763aSZong Li 	__len = ((insn & __INSN_LENGTH_MASK) == __INSN_LENGTH_32) ?	\
26b42d763aSZong Li 		4UL : 2UL;						\
27b42d763aSZong Li 	__len;								\
28b42d763aSZong Li })
29b42d763aSZong Li 
3076d2a049SPalmer Dabbelt typedef u32 bug_insn_t;
3176d2a049SPalmer Dabbelt 
3276d2a049SPalmer Dabbelt #ifdef CONFIG_GENERIC_BUG_RELATIVE_POINTERS
33*69505e3dSJosh Poimboeuf #define __BUG_ENTRY_ADDR	RISCV_INT " 1b - ."
34*69505e3dSJosh Poimboeuf #define __BUG_ENTRY_FILE	RISCV_INT " %0 - ."
3576d2a049SPalmer Dabbelt #else
3676d2a049SPalmer Dabbelt #define __BUG_ENTRY_ADDR	RISCV_PTR " 1b"
3776d2a049SPalmer Dabbelt #define __BUG_ENTRY_FILE	RISCV_PTR " %0"
3876d2a049SPalmer Dabbelt #endif
3976d2a049SPalmer Dabbelt 
4076d2a049SPalmer Dabbelt #ifdef CONFIG_DEBUG_BUGVERBOSE
4176d2a049SPalmer Dabbelt #define __BUG_ENTRY			\
4276d2a049SPalmer Dabbelt 	__BUG_ENTRY_ADDR "\n\t"		\
4376d2a049SPalmer Dabbelt 	__BUG_ENTRY_FILE "\n\t"		\
44d18ebc27SVincent Chen 	RISCV_SHORT " %1\n\t"		\
45d18ebc27SVincent Chen 	RISCV_SHORT " %2"
4676d2a049SPalmer Dabbelt #else
4776d2a049SPalmer Dabbelt #define __BUG_ENTRY			\
48d18ebc27SVincent Chen 	__BUG_ENTRY_ADDR "\n\t"		\
49d18ebc27SVincent Chen 	RISCV_SHORT " %2"
5076d2a049SPalmer Dabbelt #endif
5176d2a049SPalmer Dabbelt 
52a6d9e267SChristoph Hellwig #ifdef CONFIG_GENERIC_BUG
53d18ebc27SVincent Chen #define __BUG_FLAGS(flags)					\
5476d2a049SPalmer Dabbelt do {								\
5576d2a049SPalmer Dabbelt 	__asm__ __volatile__ (					\
5676d2a049SPalmer Dabbelt 		"1:\n\t"					\
5776d2a049SPalmer Dabbelt 			"ebreak\n"				\
58d18ebc27SVincent Chen 			".pushsection __bug_table,\"aw\"\n\t"	\
5976d2a049SPalmer Dabbelt 		"2:\n\t"					\
6076d2a049SPalmer Dabbelt 			__BUG_ENTRY "\n\t"			\
61d18ebc27SVincent Chen 			".org 2b + %3\n\t"                      \
6276d2a049SPalmer Dabbelt 			".popsection"				\
6376d2a049SPalmer Dabbelt 		:						\
6476d2a049SPalmer Dabbelt 		: "i" (__FILE__), "i" (__LINE__),		\
65d18ebc27SVincent Chen 		  "i" (flags),					\
6676d2a049SPalmer Dabbelt 		  "i" (sizeof(struct bug_entry)));              \
6776d2a049SPalmer Dabbelt } while (0)
6876d2a049SPalmer Dabbelt #else /* CONFIG_GENERIC_BUG */
69d18ebc27SVincent Chen #define __BUG_FLAGS(flags) do {					\
7076d2a049SPalmer Dabbelt 	__asm__ __volatile__ ("ebreak\n");			\
7176d2a049SPalmer Dabbelt } while (0)
7276d2a049SPalmer Dabbelt #endif /* CONFIG_GENERIC_BUG */
7376d2a049SPalmer Dabbelt 
74d18ebc27SVincent Chen #define BUG() do {						\
75d18ebc27SVincent Chen 	__BUG_FLAGS(0);						\
76d18ebc27SVincent Chen 	unreachable();						\
77d18ebc27SVincent Chen } while (0)
78d18ebc27SVincent Chen 
79d18ebc27SVincent Chen #define __WARN_FLAGS(flags) __BUG_FLAGS(BUGFLAG_WARNING|(flags))
80d18ebc27SVincent Chen 
8176d2a049SPalmer Dabbelt #define HAVE_ARCH_BUG
8276d2a049SPalmer Dabbelt 
8376d2a049SPalmer Dabbelt #include <asm-generic/bug.h>
8476d2a049SPalmer Dabbelt 
8576d2a049SPalmer Dabbelt struct pt_regs;
8676d2a049SPalmer Dabbelt struct task_struct;
8776d2a049SPalmer Dabbelt 
88091b9450SKefeng Wang void __show_regs(struct pt_regs *regs);
89a6d9e267SChristoph Hellwig void die(struct pt_regs *regs, const char *str);
90a6d9e267SChristoph Hellwig void do_trap(struct pt_regs *regs, int signo, int code, unsigned long addr);
9176d2a049SPalmer Dabbelt 
9276d2a049SPalmer Dabbelt #endif /* _ASM_RISCV_BUG_H */
93