1 /*
2 * Copyright (c) 2017 FUJITSU LIMITED. All rights reserved.
3 * Author: Xiao Yang <yangx.jy@cn.fujitsu.com>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
13 * the GNU General Public License for more details.
14 */
15
16 /*
17 * Test for EFAULT when rlim points outside the accessible address space.
18 */
19
20 #define _GNU_SOURCE
21 #include <errno.h>
22 #include <sys/resource.h>
23 #include <sys/time.h>
24 #include <sys/wait.h>
25 #include <stdlib.h>
26
27 #include "tst_test.h"
28
29 static void *bad_addr;
30
verify_setrlimit(void)31 static void verify_setrlimit(void)
32 {
33 int status;
34 pid_t pid;
35
36 pid = SAFE_FORK();
37 if (!pid) {
38 TEST(setrlimit(RLIMIT_NOFILE, bad_addr));
39 if (TST_RET != -1) {
40 tst_res(TFAIL, "setrlimit() succeeded unexpectedly");
41 exit(0);
42 }
43
44 /* Usually, setrlimit() should return EFAULT */
45 if (TST_ERR == EFAULT) {
46 tst_res(TPASS | TTERRNO,
47 "setrlimit() failed as expected");
48 } else {
49 tst_res(TFAIL | TTERRNO,
50 "setrlimit() should fail with EFAULT, got");
51 }
52
53 exit(0);
54 }
55
56 SAFE_WAITPID(pid, &status, 0);
57
58 /* If glibc has to convert between 32bit and 64bit struct rlimit
59 * in some cases, it is possible to get SegFault.
60 */
61 if (WIFSIGNALED(status) && WTERMSIG(status) == SIGSEGV) {
62 tst_res(TPASS, "setrlimit() caused SIGSEGV");
63 return;
64 }
65
66 if (WIFEXITED(status) && WEXITSTATUS(status) == 0)
67 return;
68
69 tst_res(TBROK, "child %s", tst_strstatus(status));
70 }
71
setup(void)72 static void setup(void)
73 {
74 bad_addr = tst_get_bad_addr(NULL);
75 }
76
77 static struct tst_test test = {
78 .test_all = verify_setrlimit,
79 .forks_child = 1,
80 .setup = setup,
81 };
82