xref: /kvm-unit-tests/s390x/spec_ex-sie.c (revision 49934b5af0f0fb01130d42b2a21b8ea9fc631843)
1 // SPDX-License-Identifier: GPL-2.0-only
2 /*
3  * Copyright IBM Corp. 2021
4  *
5  * Specification exception interception test.
6  * Checks that specification exception interceptions occur as expected when
7  * specification exception interpretation is off/on.
8  */
9 #include <libcflat.h>
10 #include <sclp.h>
11 #include <asm/page.h>
12 #include <asm/arch_def.h>
13 #include <alloc_page.h>
14 #include <vm.h>
15 #include <sie.h>
16 #include <snippet.h>
17 
18 static struct vm vm;
19 extern const char SNIPPET_NAME_START(c, spec_ex)[];
20 extern const char SNIPPET_NAME_END(c, spec_ex)[];
21 
22 static void setup_guest(void)
23 {
24 	char *guest;
25 	int binary_size = SNIPPET_LEN(c, spec_ex);
26 
27 	setup_vm();
28 	guest = alloc_pages(8);
29 	memcpy(guest, SNIPPET_NAME_START(c, spec_ex), binary_size);
30 	sie_guest_create(&vm, (uint64_t) guest, HPAGE_SIZE);
31 }
32 
33 static void reset_guest(void)
34 {
35 	vm.sblk->gpsw = snippet_psw;
36 	vm.sblk->icptcode = 0;
37 }
38 
39 static void test_spec_ex_sie(void)
40 {
41 	setup_guest();
42 
43 	report_prefix_push("SIE spec ex interpretation");
44 	report_prefix_push("off");
45 	reset_guest();
46 	sie(&vm);
47 	/* interpretation off -> initial exception must cause interception */
48 	report(vm.sblk->icptcode == ICPT_PROGI
49 	       && vm.sblk->iprcc == PGM_INT_CODE_SPECIFICATION
50 	       && vm.sblk->gpsw.addr != 0xdeadbeee,
51 	       "Received specification exception intercept for initial exception");
52 	report_prefix_pop();
53 
54 	report_prefix_push("on");
55 	vm.sblk->ecb |= ECB_SPECI;
56 	reset_guest();
57 	sie(&vm);
58 	/* interpretation on -> configuration dependent if initial exception causes
59 	 * interception, but invalid new program PSW must
60 	 */
61 	report(vm.sblk->icptcode == ICPT_PROGI
62 	       && vm.sblk->iprcc == PGM_INT_CODE_SPECIFICATION,
63 	       "Received specification exception intercept");
64 	if (vm.sblk->gpsw.addr == 0xdeadbeee)
65 		report_info("Interpreted initial exception, intercepted invalid program new PSW exception");
66 	else
67 		report_info("Did not interpret initial exception");
68 	report_prefix_pop();
69 	report_prefix_pop();
70 }
71 
72 int main(int argc, char **argv)
73 {
74 	if (!sclp_facilities.has_sief2) {
75 		report_skip("SIEF2 facility unavailable");
76 		goto out;
77 	}
78 
79 	test_spec_ex_sie();
80 out:
81 	return report_summary();
82 }
83