xref: /kvm-unit-tests/s390x/cpu.S (revision bb4c17e3783ce4578065f8ea55b6227dc0f53ad8)
1/* SPDX-License-Identifier: GPL-2.0-only */
2/*
3 * s390x assembly library
4 *
5 * Copyright (c) 2019 IBM Corp.
6 *
7 * Authors:
8 *    Janosch Frank <frankja@linux.ibm.com>
9 */
10#include <asm/asm-offsets.h>
11#include <asm/sigp.h>
12
13#include "macros.S"
14
15/*
16 * load_reset calling convention:
17 * %r2 subcode (0 or 1)
18 */
19.globl diag308_load_reset
20diag308_load_reset:
21	SAVE_REGS_STACK
22	/* Backup current PSW mask, as we have to restore it on success */
23	epsw	%r0, %r1
24	st	%r0, GEN_LC_SW_INT_PSW
25	st	%r1, GEN_LC_SW_INT_PSW + 4
26	/* Load reset psw mask (short psw, 64 bit) */
27	lg	%r0, reset_psw
28	/* Load the success label address */
29	larl    %r1, 0f
30	/* Or it to the mask */
31	ogr	%r0, %r1
32	/* Store it at the reset PSW location (real 0x0) */
33	stg	%r0, 0
34	stg     %r15, GEN_LC_SW_INT_GRS + 15 * 8
35	/* Do the reset */
36	diag    %r0,%r2,0x308
37	/* Failure path */
38	xgr	%r2, %r2
39	br	%r14
40	/* Success path */
41	/* load a cr0 that has the AFP control bit which enables all FPRs */
420:	larl	%r1, initial_cr0
43	lctlg	%c0, %c0, 0(%r1)
44	lg      %r15, GEN_LC_SW_INT_GRS + 15 * 8
45	RESTORE_REGS_STACK
46	lhi	%r2, 1
47	larl	%r0, 1f
48	stg	%r0, GEN_LC_SW_INT_PSW + 8
49	lpswe	GEN_LC_SW_INT_PSW
501:	br	%r14
51
52/* Sets up general registers and cr0 when a new cpu is brought online. */
53.globl smp_cpu_setup_state
54smp_cpu_setup_state:
55	xgr	%r1, %r1
56	lmg     %r0, %r15, GEN_LC_SW_INT_GRS
57	lctlg   %c0, %c0, GEN_LC_SW_INT_CRS
58	/* We should only go once through cpu setup and not for every restart */
59	stg	%r14, GEN_LC_RESTART_NEW_PSW + 8
60	larl	%r14, 0f
61	lpswe	GEN_LC_SW_INT_PSW
62	/* If the function returns, just loop here */
630:	j	0
64
65/*
66 * sie64a calling convention:
67 * %r2 pointer to sie control block
68 * %r3 guest register save area
69 */
70.globl sie64a
71sie64a:
72	# Save host grs, fprs, fpc
73	stmg	%r0,%r14,SIE_SAVEAREA_HOST_GRS(%r3)	# save kernel registers
74	.irp i, 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
75	std	\i, \i * 8  + SIE_SAVEAREA_HOST_FPRS(%r3)
76	.endr
77	stfpc	SIE_SAVEAREA_HOST_FPC(%r3)
78
79	stctg	%c1, %c1, SIE_SAVEAREA_HOST_ASCE(%r3)
80	lctlg	%c1, %c1, SIE_SAVEAREA_GUEST_ASCE(%r3)
81
82	# Store scb and save_area pointer into stack frame
83	stg	%r2,__SF_SIE_CONTROL(%r15)	# save control block pointer
84	stg	%r3,__SF_SIE_SAVEAREA(%r15)	# save guest register save area
85.globl sie_entry_gregs
86sie_entry_gregs:
87	# Load guest's gprs, fprs and fpc
88	.irp i, 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
89	ld	\i, \i * 8 + SIE_SAVEAREA_GUEST_FPRS(%r3)
90	.endr
91	lfpc	SIE_SAVEAREA_GUEST_FPC(%r3)
92	lmg	%r0,%r13,SIE_SAVEAREA_GUEST_GRS(%r3)
93
94	# Move scb ptr into r14 for the sie instruction
95	lg	%r14,__SF_SIE_CONTROL(%r15)
96
97.globl sie_entry
98sie_entry:
99	sie	0(%r14)
100	nopr	7
101	nopr	7
102	nopr	7
103
104.globl sie_exit
105sie_exit:
106	# Load guest register save area
107	lg	%r14,__SF_SIE_SAVEAREA(%r15)
108
109	# Restore the host asce
110	lctlg	%c1, %c1, SIE_SAVEAREA_HOST_ASCE(%r14)
111
112	# Store guest's gprs, fprs and fpc
113	stmg	%r0,%r13,SIE_SAVEAREA_GUEST_GRS(%r14)	# save guest gprs 0-13
114	.irp i, 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
115	std	\i, \i * 8  + SIE_SAVEAREA_GUEST_FPRS(%r14)
116	.endr
117	stfpc	SIE_SAVEAREA_GUEST_FPC(%r14)
118
119	# Restore host's gprs, fprs and fpc
120	.irp i, 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
121	ld	\i, \i * 8 + SIE_SAVEAREA_HOST_FPRS(%r14)
122	.endr
123	lfpc	SIE_SAVEAREA_HOST_FPC(%r14)
124	lmg	%r0,%r14,SIE_SAVEAREA_HOST_GRS(%r14)	# restore kernel registers
125.globl sie_exit_gregs
126sie_exit_gregs:
127	br	%r14
128
129	.align	8
130reset_psw:
131	.quad	0x0008000180000000
132