File Index
Files and directories
Sign in
FILE

vstate_prctl.c

File preview with syntax highlighting.

linux-6.19.14/tools/testing/selftests/riscv/vector/vstate_prctl.c C
  1// SPDX-License-Identifier: GPL-2.0-only
  2#include <sys/prctl.h>
  3#include <unistd.h>
  4#include <errno.h>
  5#include <sys/wait.h>
  6#include <sys/types.h>
  7#include <stdlib.h>
  8
  9#include "kselftest_harness.h"
 10#include "v_helpers.h"
 11
 12#define NEXT_PROGRAM "./vstate_exec_nolibc"
 13
 14int test_and_compare_child(long provided, long expected, int inherit, int xtheadvector)
 15{
 16	int rc;
 17
 18	rc = prctl(PR_RISCV_V_SET_CONTROL, provided);
 19	if (rc != 0) {
 20		printf("prctl with provided arg %lx failed with code %d\n",
 21		       provided, rc);
 22		return -1;
 23	}
 24	rc = launch_test(NEXT_PROGRAM, inherit, xtheadvector);
 25	if (rc != expected) {
 26		printf("Test failed, check %d != %ld\n", rc, expected);
 27		return -2;
 28	}
 29	return 0;
 30}
 31
 32#define PR_RISCV_V_VSTATE_CTRL_CUR_SHIFT 0
 33#define PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT 2
 34
 35TEST(get_control_no_v)
 36{
 37	long rc;
 38
 39	if (is_vector_supported() || is_xtheadvector_supported())
 40		SKIP(return, "Test expects vector to be not supported");
 41
 42	rc = prctl(PR_RISCV_V_GET_CONTROL);
 43	EXPECT_EQ(-1, rc)
 44	TH_LOG("GET_CONTROL should fail on kernel/hw without ZVE32X");
 45	EXPECT_EQ(EINVAL, errno)
 46	TH_LOG("GET_CONTROL should fail on kernel/hw without ZVE32X");
 47}
 48
 49TEST(set_control_no_v)
 50{
 51	long rc;
 52
 53	if (is_vector_supported() || is_xtheadvector_supported())
 54		SKIP(return, "Test expects vector to be not supported");
 55
 56	rc = prctl(PR_RISCV_V_SET_CONTROL, PR_RISCV_V_VSTATE_CTRL_ON);
 57	EXPECT_EQ(-1, rc)
 58	TH_LOG("SET_CONTROL should fail on kernel/hw without ZVE32X");
 59	EXPECT_EQ(EINVAL, errno)
 60	TH_LOG("SET_CONTROL should fail on kernel/hw without ZVE32X");
 61}
 62
 63TEST(vstate_on_current)
 64{
 65	long flag;
 66	long rc;
 67
 68	if (!is_vector_supported() && !is_xtheadvector_supported())
 69		SKIP(return, "Vector not supported");
 70
 71	flag = PR_RISCV_V_VSTATE_CTRL_ON;
 72	rc = prctl(PR_RISCV_V_SET_CONTROL, flag);
 73	EXPECT_EQ(0, rc) TH_LOG("Enabling V for current should always succeed");
 74}
 75
 76TEST(vstate_off_eperm)
 77{
 78	long flag;
 79	long rc;
 80
 81	if (!is_vector_supported() && !is_xtheadvector_supported())
 82		SKIP(return, "Vector not supported");
 83
 84	flag = PR_RISCV_V_VSTATE_CTRL_OFF;
 85	rc = prctl(PR_RISCV_V_SET_CONTROL, flag);
 86	EXPECT_EQ(EPERM, errno)
 87	TH_LOG("Disabling V in current thread with V enabled must fail with EPERM(%d)", errno);
 88	EXPECT_EQ(-1, rc)
 89	TH_LOG("Disabling V in current thread with V enabled must fail with EPERM(%d)", errno);
 90}
 91
 92TEST(vstate_on_no_nesting)
 93{
 94	long flag;
 95	int xtheadvector = 0;
 96
 97	if (!is_vector_supported()) {
 98		if (is_xtheadvector_supported())
 99			xtheadvector = 1;
100		else
101			SKIP(return, "Vector not supported");
102	}
103
104	/* Turn on next's vector explicitly and test */
105	flag = PR_RISCV_V_VSTATE_CTRL_ON << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
106
107	EXPECT_EQ(0, test_and_compare_child(flag, PR_RISCV_V_VSTATE_CTRL_ON, 0, xtheadvector));
108}
109
110TEST(vstate_off_nesting)
111{
112	long flag;
113	int xtheadvector = 0;
114
115	if (!is_vector_supported()) {
116		if (is_xtheadvector_supported())
117			xtheadvector = 1;
118		else
119			SKIP(return, "Vector not supported");
120	}
121
122	/* Turn off next's vector explicitly and test */
123	flag = PR_RISCV_V_VSTATE_CTRL_OFF << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
124
125	EXPECT_EQ(0, test_and_compare_child(flag, PR_RISCV_V_VSTATE_CTRL_OFF, 1, xtheadvector));
126}
127
128TEST(vstate_on_inherit_no_nesting)
129{
130	long flag, expected;
131	int xtheadvector = 0;
132
133	if (!is_vector_supported()) {
134		if (is_xtheadvector_supported())
135			xtheadvector = 1;
136		else
137			SKIP(return, "Vector not supported");
138	}
139
140	/* Turn on next's vector explicitly and test no inherit */
141	flag = PR_RISCV_V_VSTATE_CTRL_ON << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
142	flag |= PR_RISCV_V_VSTATE_CTRL_INHERIT;
143	expected = flag | PR_RISCV_V_VSTATE_CTRL_ON;
144
145	EXPECT_EQ(0, test_and_compare_child(flag, expected, 0, xtheadvector));
146}
147
148TEST(vstate_on_inherit)
149{
150	long flag, expected;
151	int xtheadvector = 0;
152
153	if (!is_vector_supported()) {
154		if (is_xtheadvector_supported())
155			xtheadvector = 1;
156		else
157			SKIP(return, "Vector not supported");
158	}
159
160	/* Turn on next's vector explicitly and test inherit */
161	flag = PR_RISCV_V_VSTATE_CTRL_ON << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
162	flag |= PR_RISCV_V_VSTATE_CTRL_INHERIT;
163	expected = flag | PR_RISCV_V_VSTATE_CTRL_ON;
164
165	EXPECT_EQ(0, test_and_compare_child(flag, expected, 1, xtheadvector));
166}
167
168TEST(vstate_off_inherit_no_nesting)
169{
170	long flag, expected;
171	int xtheadvector = 0;
172
173	if (!is_vector_supported()) {
174		if (is_xtheadvector_supported())
175			xtheadvector = 1;
176		else
177			SKIP(return, "Vector not supported");
178	}
179	/* Turn off next's vector explicitly and test no inherit */
180	flag = PR_RISCV_V_VSTATE_CTRL_OFF << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
181	flag |= PR_RISCV_V_VSTATE_CTRL_INHERIT;
182	expected = flag | PR_RISCV_V_VSTATE_CTRL_OFF;
183
184	EXPECT_EQ(0, test_and_compare_child(flag, expected, 0, xtheadvector));
185}
186
187TEST(vstate_off_inherit)
188{
189	long flag, expected;
190	int xtheadvector = 0;
191
192	if (!is_vector_supported()) {
193		if (is_xtheadvector_supported())
194			xtheadvector = 1;
195		else
196			SKIP(return, "Vector not supported");
197	}
198
199	/* Turn off next's vector explicitly and test inherit */
200	flag = PR_RISCV_V_VSTATE_CTRL_OFF << PR_RISCV_V_VSTATE_CTRL_NEXT_SHIFT;
201	flag |= PR_RISCV_V_VSTATE_CTRL_INHERIT;
202	expected = flag | PR_RISCV_V_VSTATE_CTRL_OFF;
203
204	EXPECT_EQ(0, test_and_compare_child(flag, expected, 1, xtheadvector));
205}
206
207/* arguments should fail with EINVAL */
208TEST(inval_set_control_1)
209{
210	int rc;
211
212	if (!is_vector_supported() && !is_xtheadvector_supported())
213		SKIP(return, "Vector not supported");
214
215	rc = prctl(PR_RISCV_V_SET_CONTROL, 0xff0);
216	EXPECT_EQ(-1, rc);
217	EXPECT_EQ(EINVAL, errno);
218}
219
220/* arguments should fail with EINVAL */
221TEST(inval_set_control_2)
222{
223	int rc;
224
225	if (!is_vector_supported() && !is_xtheadvector_supported())
226		SKIP(return, "Vector not supported");
227
228	rc = prctl(PR_RISCV_V_SET_CONTROL, 0x3);
229	EXPECT_EQ(-1, rc);
230	EXPECT_EQ(EINVAL, errno);
231}
232
233/* arguments should fail with EINVAL */
234TEST(inval_set_control_3)
235{
236	int rc;
237
238	if (!is_vector_supported() && !is_xtheadvector_supported())
239		SKIP(return, "Vector not supported");
240
241	rc = prctl(PR_RISCV_V_SET_CONTROL, 0xc);
242	EXPECT_EQ(-1, rc);
243	EXPECT_EQ(EINVAL, errno);
244}
245
246TEST_HARNESS_MAIN
~/ Read-only file preview.