]>
Commit | Line | Data |
---|---|---|
57c9fccb | 1 | /* |
da23017d NS |
2 | * Copyright (c) 2005 Silicon Graphics, Inc. |
3 | * All Rights Reserved. | |
57c9fccb | 4 | * |
da23017d NS |
5 | * This program is free software; you can redistribute it and/or |
6 | * modify it under the terms of the GNU General Public License as | |
57c9fccb NS |
7 | * published by the Free Software Foundation. |
8 | * | |
da23017d NS |
9 | * This program is distributed in the hope that it would be useful, |
10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
12 | * GNU General Public License for more details. | |
57c9fccb | 13 | * |
da23017d NS |
14 | * You should have received a copy of the GNU General Public License |
15 | * along with this program; if not, write the Free Software Foundation, | |
16 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | |
57c9fccb NS |
17 | */ |
18 | ||
6b803e5a | 19 | #include "libxfs.h" |
57c9fccb NS |
20 | #include "command.h" |
21 | #include "attrset.h" | |
22 | #include "io.h" | |
23 | #include "output.h" | |
24 | #include "type.h" | |
25 | #include "init.h" | |
501031ab CH |
26 | #include "fprint.h" |
27 | #include "faddr.h" | |
28 | #include "field.h" | |
57c9fccb NS |
29 | #include "inode.h" |
30 | #include "malloc.h" | |
31 | ||
32 | static int attr_set_f(int argc, char **argv); | |
33 | static int attr_remove_f(int argc, char **argv); | |
34 | static void attrset_help(void); | |
35 | ||
36 | static const cmdinfo_t attr_set_cmd = | |
37 | { "attr_set", "aset", attr_set_f, 1, -1, 0, | |
9ee7055c AM |
38 | N_("[-r|-s|-p|-u] [-n] [-R|-C] [-v n] name"), |
39 | N_("set the named attribute on the current inode"), attrset_help }; | |
57c9fccb NS |
40 | static const cmdinfo_t attr_remove_cmd = |
41 | { "attr_remove", "aremove", attr_remove_f, 1, -1, 0, | |
9ee7055c AM |
42 | N_("[-r|-s|-p|-u] [-n] name"), |
43 | N_("remove the named attribute from the current inode"), attrset_help }; | |
57c9fccb NS |
44 | |
45 | static void | |
46 | attrset_help(void) | |
47 | { | |
9ee7055c | 48 | dbprintf(_( |
57c9fccb NS |
49 | "\n" |
50 | " The 'attr_set' and 'attr_remove' commands provide interfaces for debugging\n" | |
51 | " the extended attribute allocation and removal code.\n" | |
52 | " Both commands require an attribute name to be specified, and the attr_set\n" | |
53 | " command allows an optional value length (-v) to be provided as well.\n" | |
54 | " There are 4 namespace flags:\n" | |
55 | " -r -- 'root'\n" | |
56 | " -u -- 'user' (default)\n" | |
57 | " -s -- 'secure'\n" | |
58 | "\n" | |
6239071d | 59 | " For attr_set, these options further define the type of set operation:\n" |
57c9fccb NS |
60 | " -C -- 'create' - create attribute, fail if it already exists\n" |
61 | " -R -- 'replace' - replace attribute, fail if it does not exist\n" | |
6239071d | 62 | " The backward compatibility mode 'noattr2' can be emulated (-n) also.\n" |
9ee7055c | 63 | "\n")); |
57c9fccb NS |
64 | } |
65 | ||
66 | void | |
67 | attrset_init(void) | |
68 | { | |
69 | if (!expert_mode) | |
70 | return; | |
71 | ||
72 | add_command(&attr_set_cmd); | |
73 | add_command(&attr_remove_cmd); | |
74 | } | |
75 | ||
76 | static int | |
77 | attr_set_f( | |
78 | int argc, | |
79 | char **argv) | |
80 | { | |
81 | xfs_inode_t *ip = NULL; | |
82 | char *name, *value, *sp; | |
a9371e21 | 83 | int c, valuelen = 0, flags = 0; |
57c9fccb NS |
84 | |
85 | if (cur_typ == NULL) { | |
9ee7055c | 86 | dbprintf(_("no current type\n")); |
57c9fccb NS |
87 | return 0; |
88 | } | |
89 | if (cur_typ->typnm != TYP_INODE) { | |
9ee7055c | 90 | dbprintf(_("current type is not inode\n")); |
57c9fccb NS |
91 | return 0; |
92 | } | |
93 | ||
6239071d | 94 | while ((c = getopt(argc, argv, "rusCRnv:")) != EOF) { |
57c9fccb NS |
95 | switch (c) { |
96 | /* namespaces */ | |
97 | case 'r': | |
98 | flags |= LIBXFS_ATTR_ROOT; | |
99 | flags &= ~LIBXFS_ATTR_SECURE; | |
100 | break; | |
101 | case 'u': | |
102 | flags &= ~(LIBXFS_ATTR_ROOT | LIBXFS_ATTR_SECURE); | |
103 | break; | |
104 | case 's': | |
105 | flags |= LIBXFS_ATTR_SECURE; | |
106 | flags &= ~LIBXFS_ATTR_ROOT; | |
107 | break; | |
108 | ||
109 | /* modifiers */ | |
110 | case 'C': | |
111 | flags |= LIBXFS_ATTR_CREATE; | |
112 | break; | |
113 | case 'R': | |
114 | flags |= LIBXFS_ATTR_REPLACE; | |
115 | break; | |
116 | ||
6239071d NS |
117 | case 'n': |
118 | mp->m_flags |= LIBXFS_MOUNT_COMPAT_ATTR; | |
119 | break; | |
120 | ||
57c9fccb NS |
121 | /* value length */ |
122 | case 'v': | |
123 | valuelen = (int)strtol(optarg, &sp, 0); | |
124 | if (*sp != '\0' || valuelen < 0 || valuelen > 64*1024) { | |
9ee7055c | 125 | dbprintf(_("bad attr_set valuelen %s\n"), optarg); |
57c9fccb NS |
126 | return 0; |
127 | } | |
128 | break; | |
129 | ||
130 | default: | |
9ee7055c | 131 | dbprintf(_("bad option for attr_set command\n")); |
57c9fccb NS |
132 | return 0; |
133 | } | |
134 | } | |
135 | ||
136 | if (optind != argc - 1) { | |
9ee7055c | 137 | dbprintf(_("too few options for attr_set (no name given)\n")); |
57c9fccb NS |
138 | return 0; |
139 | } | |
140 | ||
141 | name = argv[optind]; | |
57c9fccb NS |
142 | |
143 | if (valuelen) { | |
144 | value = (char *)memalign(getpagesize(), valuelen); | |
145 | if (!value) { | |
9ee7055c | 146 | dbprintf(_("cannot allocate buffer (%d)\n"), valuelen); |
57c9fccb NS |
147 | goto out; |
148 | } | |
04c2e8d3 | 149 | memset(value, 'v', valuelen); |
57c9fccb NS |
150 | } else { |
151 | value = NULL; | |
152 | } | |
153 | ||
81f8132a | 154 | if (libxfs_iget(mp, NULL, iocur_top->ino, 0, &ip)) { |
57c9fccb NS |
155 | dbprintf(_("failed to iget inode %llu\n"), |
156 | (unsigned long long)iocur_top->ino); | |
157 | goto out; | |
158 | } | |
159 | ||
56b2de80 DC |
160 | if (libxfs_attr_set(ip, (unsigned char *)name, |
161 | (unsigned char *)value, valuelen, flags)) { | |
57c9fccb NS |
162 | dbprintf(_("failed to set attr %s on inode %llu\n"), |
163 | name, (unsigned long long)iocur_top->ino); | |
164 | goto out; | |
165 | } | |
166 | ||
167 | /* refresh with updated inode contents */ | |
168 | set_cur_inode(iocur_top->ino); | |
169 | ||
170 | out: | |
6239071d | 171 | mp->m_flags &= ~LIBXFS_MOUNT_COMPAT_ATTR; |
57c9fccb | 172 | if (ip) |
dd2c21d2 | 173 | IRELE(ip); |
57c9fccb NS |
174 | if (value) |
175 | free(value); | |
176 | return 0; | |
177 | } | |
178 | ||
179 | static int | |
180 | attr_remove_f( | |
181 | int argc, | |
182 | char **argv) | |
183 | { | |
184 | xfs_inode_t *ip = NULL; | |
185 | char *name; | |
a9371e21 | 186 | int c, flags = 0; |
57c9fccb NS |
187 | |
188 | if (cur_typ == NULL) { | |
9ee7055c | 189 | dbprintf(_("no current type\n")); |
57c9fccb NS |
190 | return 0; |
191 | } | |
192 | if (cur_typ->typnm != TYP_INODE) { | |
9ee7055c | 193 | dbprintf(_("current type is not inode\n")); |
57c9fccb NS |
194 | return 0; |
195 | } | |
196 | ||
6239071d | 197 | while ((c = getopt(argc, argv, "rusn")) != EOF) { |
57c9fccb NS |
198 | switch (c) { |
199 | /* namespaces */ | |
200 | case 'r': | |
201 | flags |= LIBXFS_ATTR_ROOT; | |
202 | flags &= ~LIBXFS_ATTR_SECURE; | |
203 | break; | |
204 | case 'u': | |
205 | flags &= ~(LIBXFS_ATTR_ROOT | LIBXFS_ATTR_SECURE); | |
206 | break; | |
207 | case 's': | |
208 | flags |= LIBXFS_ATTR_SECURE; | |
209 | flags &= ~LIBXFS_ATTR_ROOT; | |
210 | break; | |
211 | ||
6239071d NS |
212 | case 'n': |
213 | mp->m_flags |= LIBXFS_MOUNT_COMPAT_ATTR; | |
214 | break; | |
215 | ||
57c9fccb | 216 | default: |
9ee7055c | 217 | dbprintf(_("bad option for attr_remove command\n")); |
57c9fccb NS |
218 | return 0; |
219 | } | |
220 | } | |
221 | ||
222 | if (optind != argc - 1) { | |
9ee7055c | 223 | dbprintf(_("too few options for attr_remove (no name given)\n")); |
57c9fccb NS |
224 | return 0; |
225 | } | |
226 | ||
227 | name = argv[optind]; | |
57c9fccb | 228 | |
81f8132a | 229 | if (libxfs_iget(mp, NULL, iocur_top->ino, 0, &ip)) { |
57c9fccb NS |
230 | dbprintf(_("failed to iget inode %llu\n"), |
231 | (unsigned long long)iocur_top->ino); | |
232 | goto out; | |
233 | } | |
234 | ||
56b2de80 | 235 | if (libxfs_attr_remove(ip, (unsigned char *)name, flags)) { |
57c9fccb NS |
236 | dbprintf(_("failed to remove attr %s from inode %llu\n"), |
237 | name, (unsigned long long)iocur_top->ino); | |
238 | goto out; | |
239 | } | |
240 | ||
241 | /* refresh with updated inode contents */ | |
242 | set_cur_inode(iocur_top->ino); | |
243 | ||
244 | out: | |
6239071d | 245 | mp->m_flags &= ~LIBXFS_MOUNT_COMPAT_ATTR; |
57c9fccb | 246 | if (ip) |
dd2c21d2 | 247 | IRELE(ip); |
57c9fccb NS |
248 | return 0; |
249 | } |