1 /*
2 * Copyright (c) 2016 Fujitsu Ltd.
3 * Author: Jinbao Huang <huangjb.jy@cn.fujitsu.com>
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of version 2 of the GNU General Public License as
7 * published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope that it would be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12 *
13 * You should have received a copy of the GNU General Public License
14 * alone with this program.
15 *
16 */
17
18 /*
19 * Test Name: lgetxattr02
20 *
21 * Description:
22 * 1) lgetxattr(2) fails if the named attribute does not exist.
23 * 2) lgetxattr(2) fails if the size of the value buffer is too small
24 * to hold the result.
25 * 3) lgetxattr(2) fails when attemptes to read from a invalid address.
26 *
27 * Expected Result:
28 * 1) lgetxattr(2) should return -1 and set errno to ENODATA.
29 * 2) lgetxattr(2) should return -1 and set errno to ERANGE.
30 * 3) lgetxattr(2) should return -1 and set errno to EFAULT.
31 */
32
33 #include "config.h"
34 #include <errno.h>
35 #include <sys/types.h>
36 #include <string.h>
37
38 #ifdef HAVE_SYS_XATTR_H
39 # include <sys/xattr.h>
40 #endif
41
42 #include "tst_test.h"
43
44 #ifdef HAVE_SYS_XATTR_H
45
46 #define SECURITY_KEY "security.ltptest"
47 #define VALUE "this is a test value"
48
49 static struct test_case {
50 const char *path;
51 size_t size;
52 int exp_err;
53 } tcase[] = {
54 {"testfile", sizeof(VALUE), ENODATA},
55 {"symlink", 1, ERANGE},
56 {(char *)-1, sizeof(VALUE), EFAULT}
57 };
58
verify_lgetxattr(unsigned int n)59 static void verify_lgetxattr(unsigned int n)
60 {
61 struct test_case *tc = tcase + n;
62 char buf[tc->size];
63
64 TEST(lgetxattr(tc->path, SECURITY_KEY, buf, sizeof(buf)));
65 if (TST_RET != -1) {
66 tst_res(TFAIL, "lgetxattr() succeeded unexpectedly");
67 return;
68 }
69
70 if (TST_ERR != tc->exp_err) {
71 tst_res(TFAIL | TTERRNO, "lgetxattr() failed unexpectedlly, "
72 "expected %s", tst_strerrno(tc->exp_err));
73 } else {
74 tst_res(TPASS | TTERRNO, "lgetxattr() failed as expected");
75 }
76 }
77
setup(void)78 static void setup(void)
79 {
80 int res;
81
82 SAFE_TOUCH("testfile", 0644, NULL);
83 SAFE_SYMLINK("testfile", "symlink");
84
85 res = lsetxattr("symlink", SECURITY_KEY, VALUE, strlen(VALUE), XATTR_CREATE);
86 if (res == -1) {
87 if (errno == ENOTSUP) {
88 tst_brk(TCONF, "no xattr support in fs or "
89 "mounted without user_xattr option");
90 } else {
91 tst_brk(TBROK | TERRNO, "lsetxattr(%s) failed",
92 SECURITY_KEY);
93 }
94 }
95 }
96
97 static struct tst_test test = {
98 .needs_tmpdir = 1,
99 .needs_root = 1,
100 .test = verify_lgetxattr,
101 .tcnt = ARRAY_SIZE(tcase),
102 .setup = setup
103 };
104
105 #else /* HAVE_SYS_XATTR_H */
106 TST_TEST_TCONF("<sys/xattr.h> does not exist.");
107 #endif
108