162306a36Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-or-later */
262306a36Sopenharmony_ci#ifndef _ASM_POWERPC_EXCEPTION_H
362306a36Sopenharmony_ci#define _ASM_POWERPC_EXCEPTION_H
462306a36Sopenharmony_ci/*
562306a36Sopenharmony_ci * Extracted from head_64.S
662306a36Sopenharmony_ci *
762306a36Sopenharmony_ci *  PowerPC version
862306a36Sopenharmony_ci *    Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org)
962306a36Sopenharmony_ci *
1062306a36Sopenharmony_ci *  Rewritten by Cort Dougan (cort@cs.nmt.edu) for PReP
1162306a36Sopenharmony_ci *    Copyright (C) 1996 Cort Dougan <cort@cs.nmt.edu>
1262306a36Sopenharmony_ci *  Adapted for Power Macintosh by Paul Mackerras.
1362306a36Sopenharmony_ci *  Low-level exception handlers and MMU support
1462306a36Sopenharmony_ci *  rewritten by Paul Mackerras.
1562306a36Sopenharmony_ci *    Copyright (C) 1996 Paul Mackerras.
1662306a36Sopenharmony_ci *
1762306a36Sopenharmony_ci *  Adapted for 64bit PowerPC by Dave Engebretsen, Peter Bergner, and
1862306a36Sopenharmony_ci *    Mike Corrigan {engebret|bergner|mikejc}@us.ibm.com
1962306a36Sopenharmony_ci *
2062306a36Sopenharmony_ci *  This file contains the low-level support and setup for the
2162306a36Sopenharmony_ci *  PowerPC-64 platform, including trap and interrupt dispatch.
2262306a36Sopenharmony_ci */
2362306a36Sopenharmony_ci/*
2462306a36Sopenharmony_ci * The following macros define the code that appears as
2562306a36Sopenharmony_ci * the prologue to each of the exception handlers.  They
2662306a36Sopenharmony_ci * are split into two parts to allow a single kernel binary
2762306a36Sopenharmony_ci * to be used for pSeries and iSeries.
2862306a36Sopenharmony_ci *
2962306a36Sopenharmony_ci * We make as much of the exception code common between native
3062306a36Sopenharmony_ci * exception handlers (including pSeries LPAR) and iSeries LPAR
3162306a36Sopenharmony_ci * implementations as possible.
3262306a36Sopenharmony_ci */
3362306a36Sopenharmony_ci#include <asm/feature-fixups.h>
3462306a36Sopenharmony_ci
3562306a36Sopenharmony_ci/* PACA save area size in u64 units (exgen, exmc, etc) */
3662306a36Sopenharmony_ci#define EX_SIZE		10
3762306a36Sopenharmony_ci
3862306a36Sopenharmony_ci/* PACA save area offsets */
3962306a36Sopenharmony_ci#define EX_R9		0
4062306a36Sopenharmony_ci#define EX_R10		8
4162306a36Sopenharmony_ci#define EX_R11		16
4262306a36Sopenharmony_ci#define EX_R12		24
4362306a36Sopenharmony_ci#define EX_R13		32
4462306a36Sopenharmony_ci#define EX_DAR		40
4562306a36Sopenharmony_ci#define EX_DSISR	48
4662306a36Sopenharmony_ci#define EX_CCR		52
4762306a36Sopenharmony_ci#define EX_CFAR		56
4862306a36Sopenharmony_ci#define EX_PPR		64
4962306a36Sopenharmony_ci#define EX_CTR		72
5062306a36Sopenharmony_ci
5162306a36Sopenharmony_ci/*
5262306a36Sopenharmony_ci * maximum recursive depth of MCE exceptions
5362306a36Sopenharmony_ci */
5462306a36Sopenharmony_ci#define MAX_MCE_DEPTH	4
5562306a36Sopenharmony_ci
5662306a36Sopenharmony_ci#ifdef __ASSEMBLY__
5762306a36Sopenharmony_ci
5862306a36Sopenharmony_ci#define STF_ENTRY_BARRIER_SLOT						\
5962306a36Sopenharmony_ci	STF_ENTRY_BARRIER_FIXUP_SECTION;				\
6062306a36Sopenharmony_ci	nop;								\
6162306a36Sopenharmony_ci	nop;								\
6262306a36Sopenharmony_ci	nop
6362306a36Sopenharmony_ci
6462306a36Sopenharmony_ci#define STF_EXIT_BARRIER_SLOT						\
6562306a36Sopenharmony_ci	STF_EXIT_BARRIER_FIXUP_SECTION;					\
6662306a36Sopenharmony_ci	nop;								\
6762306a36Sopenharmony_ci	nop;								\
6862306a36Sopenharmony_ci	nop;								\
6962306a36Sopenharmony_ci	nop;								\
7062306a36Sopenharmony_ci	nop;								\
7162306a36Sopenharmony_ci	nop
7262306a36Sopenharmony_ci
7362306a36Sopenharmony_ci#define ENTRY_FLUSH_SLOT						\
7462306a36Sopenharmony_ci	ENTRY_FLUSH_FIXUP_SECTION;					\
7562306a36Sopenharmony_ci	nop;								\
7662306a36Sopenharmony_ci	nop;								\
7762306a36Sopenharmony_ci	nop;
7862306a36Sopenharmony_ci
7962306a36Sopenharmony_ci#define SCV_ENTRY_FLUSH_SLOT						\
8062306a36Sopenharmony_ci	SCV_ENTRY_FLUSH_FIXUP_SECTION;					\
8162306a36Sopenharmony_ci	nop;								\
8262306a36Sopenharmony_ci	nop;								\
8362306a36Sopenharmony_ci	nop;
8462306a36Sopenharmony_ci
8562306a36Sopenharmony_ci/*
8662306a36Sopenharmony_ci * r10 must be free to use, r13 must be paca
8762306a36Sopenharmony_ci */
8862306a36Sopenharmony_ci#define INTERRUPT_TO_KERNEL						\
8962306a36Sopenharmony_ci	STF_ENTRY_BARRIER_SLOT;						\
9062306a36Sopenharmony_ci	ENTRY_FLUSH_SLOT
9162306a36Sopenharmony_ci
9262306a36Sopenharmony_ci/*
9362306a36Sopenharmony_ci * r10, ctr must be free to use, r13 must be paca
9462306a36Sopenharmony_ci */
9562306a36Sopenharmony_ci#define SCV_INTERRUPT_TO_KERNEL						\
9662306a36Sopenharmony_ci	STF_ENTRY_BARRIER_SLOT;						\
9762306a36Sopenharmony_ci	SCV_ENTRY_FLUSH_SLOT
9862306a36Sopenharmony_ci
9962306a36Sopenharmony_ci/*
10062306a36Sopenharmony_ci * Macros for annotating the expected destination of (h)rfid
10162306a36Sopenharmony_ci *
10262306a36Sopenharmony_ci * The nop instructions allow us to insert one or more instructions to flush the
10362306a36Sopenharmony_ci * L1-D cache when returning to userspace or a guest.
10462306a36Sopenharmony_ci *
10562306a36Sopenharmony_ci * powerpc relies on return from interrupt/syscall being context synchronising
10662306a36Sopenharmony_ci * (which hrfid, rfid, and rfscv are) to support ARCH_HAS_MEMBARRIER_SYNC_CORE
10762306a36Sopenharmony_ci * without additional synchronisation instructions.
10862306a36Sopenharmony_ci *
10962306a36Sopenharmony_ci * soft-masked interrupt replay does not include a context-synchronising rfid,
11062306a36Sopenharmony_ci * but those always return to kernel, the sync is only required when returning
11162306a36Sopenharmony_ci * to user.
11262306a36Sopenharmony_ci */
11362306a36Sopenharmony_ci#define RFI_FLUSH_SLOT							\
11462306a36Sopenharmony_ci	RFI_FLUSH_FIXUP_SECTION;					\
11562306a36Sopenharmony_ci	nop;								\
11662306a36Sopenharmony_ci	nop;								\
11762306a36Sopenharmony_ci	nop
11862306a36Sopenharmony_ci
11962306a36Sopenharmony_ci#define RFI_TO_KERNEL							\
12062306a36Sopenharmony_ci	rfid
12162306a36Sopenharmony_ci
12262306a36Sopenharmony_ci#define RFI_TO_USER							\
12362306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
12462306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
12562306a36Sopenharmony_ci	rfid;								\
12662306a36Sopenharmony_ci	b	rfi_flush_fallback
12762306a36Sopenharmony_ci
12862306a36Sopenharmony_ci#define RFI_TO_USER_OR_KERNEL						\
12962306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
13062306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
13162306a36Sopenharmony_ci	rfid;								\
13262306a36Sopenharmony_ci	b	rfi_flush_fallback
13362306a36Sopenharmony_ci
13462306a36Sopenharmony_ci#define RFI_TO_GUEST							\
13562306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
13662306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
13762306a36Sopenharmony_ci	rfid;								\
13862306a36Sopenharmony_ci	b	rfi_flush_fallback
13962306a36Sopenharmony_ci
14062306a36Sopenharmony_ci#define HRFI_TO_KERNEL							\
14162306a36Sopenharmony_ci	hrfid
14262306a36Sopenharmony_ci
14362306a36Sopenharmony_ci#define HRFI_TO_USER							\
14462306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
14562306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
14662306a36Sopenharmony_ci	hrfid;								\
14762306a36Sopenharmony_ci	b	hrfi_flush_fallback
14862306a36Sopenharmony_ci
14962306a36Sopenharmony_ci#define HRFI_TO_USER_OR_KERNEL						\
15062306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
15162306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
15262306a36Sopenharmony_ci	hrfid;								\
15362306a36Sopenharmony_ci	b	hrfi_flush_fallback
15462306a36Sopenharmony_ci
15562306a36Sopenharmony_ci#define HRFI_TO_GUEST							\
15662306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
15762306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
15862306a36Sopenharmony_ci	hrfid;								\
15962306a36Sopenharmony_ci	b	hrfi_flush_fallback
16062306a36Sopenharmony_ci
16162306a36Sopenharmony_ci#define HRFI_TO_UNKNOWN							\
16262306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
16362306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
16462306a36Sopenharmony_ci	hrfid;								\
16562306a36Sopenharmony_ci	b	hrfi_flush_fallback
16662306a36Sopenharmony_ci
16762306a36Sopenharmony_ci#define RFSCV_TO_USER							\
16862306a36Sopenharmony_ci	STF_EXIT_BARRIER_SLOT;						\
16962306a36Sopenharmony_ci	RFI_FLUSH_SLOT;							\
17062306a36Sopenharmony_ci	RFSCV;								\
17162306a36Sopenharmony_ci	b	rfscv_flush_fallback
17262306a36Sopenharmony_ci
17362306a36Sopenharmony_ci#else /* __ASSEMBLY__ */
17462306a36Sopenharmony_ci/* Prototype for function defined in exceptions-64s.S */
17562306a36Sopenharmony_civoid do_uaccess_flush(void);
17662306a36Sopenharmony_ci#endif /* __ASSEMBLY__ */
17762306a36Sopenharmony_ci
17862306a36Sopenharmony_ci#endif	/* _ASM_POWERPC_EXCEPTION_H */
179