1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34#define DEBUG_SUBSYSTEM S_MDC
35#include <lustre_net.h>
36#include <uapi/linux/lustre/lustre_idl.h>
37#include "mdc_internal.h"
38
39static void set_mrc_cr_flags(struct mdt_rec_create *mrc, u64 flags)
40{
41 mrc->cr_flags_l = (u32)(flags & 0xFFFFFFFFUll);
42 mrc->cr_flags_h = (u32)(flags >> 32);
43}
44
45static void __mdc_pack_body(struct mdt_body *b, __u32 suppgid)
46{
47 b->mbo_suppgid = suppgid;
48 b->mbo_uid = from_kuid(&init_user_ns, current_uid());
49 b->mbo_gid = from_kgid(&init_user_ns, current_gid());
50 b->mbo_fsuid = from_kuid(&init_user_ns, current_fsuid());
51 b->mbo_fsgid = from_kgid(&init_user_ns, current_fsgid());
52 b->mbo_capability = cfs_curproc_cap_pack();
53}
54
55void mdc_swap_layouts_pack(struct ptlrpc_request *req,
56 struct md_op_data *op_data)
57{
58 struct mdt_body *b = req_capsule_client_get(&req->rq_pill,
59 &RMF_MDT_BODY);
60
61 __mdc_pack_body(b, op_data->op_suppgids[0]);
62 b->mbo_fid1 = op_data->op_fid1;
63 b->mbo_fid2 = op_data->op_fid2;
64 b->mbo_valid |= OBD_MD_FLID;
65}
66
67void mdc_pack_body(struct ptlrpc_request *req, const struct lu_fid *fid,
68 __u64 valid, size_t ea_size, __u32 suppgid, u32 flags)
69{
70 struct mdt_body *b = req_capsule_client_get(&req->rq_pill,
71 &RMF_MDT_BODY);
72 b->mbo_valid = valid;
73 b->mbo_eadatasize = ea_size;
74 b->mbo_flags = flags;
75 __mdc_pack_body(b, suppgid);
76 if (fid) {
77 b->mbo_fid1 = *fid;
78 b->mbo_valid |= OBD_MD_FLID;
79 }
80}
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95static void mdc_pack_name(struct ptlrpc_request *req,
96 const struct req_msg_field *field,
97 const char *name, size_t name_len)
98{
99 size_t buf_size;
100 size_t cpy_len;
101 char *buf;
102
103 buf = req_capsule_client_get(&req->rq_pill, field);
104 buf_size = req_capsule_get_size(&req->rq_pill, field, RCL_CLIENT);
105
106 LASSERT(name && name_len && buf && buf_size == name_len + 1);
107
108 cpy_len = strlcpy(buf, name, buf_size);
109
110 LASSERT(cpy_len == name_len && lu_name_is_valid_2(buf, cpy_len));
111}
112
113void mdc_readdir_pack(struct ptlrpc_request *req, __u64 pgoff, size_t size,
114 const struct lu_fid *fid)
115{
116 struct mdt_body *b = req_capsule_client_get(&req->rq_pill,
117 &RMF_MDT_BODY);
118 b->mbo_fid1 = *fid;
119 b->mbo_valid |= OBD_MD_FLID;
120 b->mbo_size = pgoff;
121 b->mbo_nlink = size;
122 __mdc_pack_body(b, -1);
123 b->mbo_mode = LUDA_FID | LUDA_TYPE;
124}
125
126
127void mdc_create_pack(struct ptlrpc_request *req, struct md_op_data *op_data,
128 const void *data, size_t datalen, umode_t mode,
129 uid_t uid, gid_t gid, cfs_cap_t cap_effective, __u64 rdev)
130{
131 struct mdt_rec_create *rec;
132 char *tmp;
133 __u64 flags;
134
135 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) != sizeof(struct mdt_rec_create));
136 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
137
138 rec->cr_opcode = REINT_CREATE;
139 rec->cr_fsuid = uid;
140 rec->cr_fsgid = gid;
141 rec->cr_cap = cap_effective;
142 rec->cr_fid1 = op_data->op_fid1;
143 rec->cr_fid2 = op_data->op_fid2;
144 rec->cr_mode = mode;
145 rec->cr_rdev = rdev;
146 rec->cr_time = op_data->op_mod_time;
147 rec->cr_suppgid1 = op_data->op_suppgids[0];
148 rec->cr_suppgid2 = op_data->op_suppgids[1];
149 flags = 0;
150 if (op_data->op_bias & MDS_CREATE_VOLATILE)
151 flags |= MDS_OPEN_VOLATILE;
152 set_mrc_cr_flags(rec, flags);
153 rec->cr_bias = op_data->op_bias;
154 rec->cr_umask = current_umask();
155
156 mdc_pack_name(req, &RMF_NAME, op_data->op_name, op_data->op_namelen);
157 if (data) {
158 tmp = req_capsule_client_get(&req->rq_pill, &RMF_EADATA);
159 memcpy(tmp, data, datalen);
160 }
161}
162
163static inline __u64 mds_pack_open_flags(__u64 flags)
164{
165 __u64 cr_flags = (flags & (FMODE_READ | FMODE_WRITE |
166 MDS_OPEN_FL_INTERNAL));
167 if (flags & O_CREAT)
168 cr_flags |= MDS_OPEN_CREAT;
169 if (flags & O_EXCL)
170 cr_flags |= MDS_OPEN_EXCL;
171 if (flags & O_TRUNC)
172 cr_flags |= MDS_OPEN_TRUNC;
173 if (flags & O_APPEND)
174 cr_flags |= MDS_OPEN_APPEND;
175 if (flags & O_SYNC)
176 cr_flags |= MDS_OPEN_SYNC;
177 if (flags & O_DIRECTORY)
178 cr_flags |= MDS_OPEN_DIRECTORY;
179 if (flags & __FMODE_EXEC)
180 cr_flags |= MDS_FMODE_EXEC;
181 if (cl_is_lov_delay_create(flags))
182 cr_flags |= MDS_OPEN_DELAY_CREATE;
183
184 if (flags & O_NONBLOCK)
185 cr_flags |= MDS_OPEN_NORESTORE;
186
187 return cr_flags;
188}
189
190
191void mdc_open_pack(struct ptlrpc_request *req, struct md_op_data *op_data,
192 umode_t mode, __u64 rdev, __u64 flags, const void *lmm,
193 size_t lmmlen)
194{
195 struct mdt_rec_create *rec;
196 char *tmp;
197 __u64 cr_flags;
198
199 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) != sizeof(struct mdt_rec_create));
200 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
201
202
203 rec->cr_opcode = REINT_OPEN;
204 rec->cr_fsuid = from_kuid(&init_user_ns, current_fsuid());
205 rec->cr_fsgid = from_kgid(&init_user_ns, current_fsgid());
206 rec->cr_cap = cfs_curproc_cap_pack();
207 rec->cr_fid1 = op_data->op_fid1;
208 rec->cr_fid2 = op_data->op_fid2;
209
210 rec->cr_mode = mode;
211 cr_flags = mds_pack_open_flags(flags);
212 rec->cr_rdev = rdev;
213 rec->cr_time = op_data->op_mod_time;
214 rec->cr_suppgid1 = op_data->op_suppgids[0];
215 rec->cr_suppgid2 = op_data->op_suppgids[1];
216 rec->cr_bias = op_data->op_bias;
217 rec->cr_umask = current_umask();
218 rec->cr_old_handle = op_data->op_handle;
219
220 if (op_data->op_name) {
221 mdc_pack_name(req, &RMF_NAME, op_data->op_name,
222 op_data->op_namelen);
223
224 if (op_data->op_bias & MDS_CREATE_VOLATILE)
225 cr_flags |= MDS_OPEN_VOLATILE;
226 }
227
228 if (lmm) {
229 cr_flags |= MDS_OPEN_HAS_EA;
230 tmp = req_capsule_client_get(&req->rq_pill, &RMF_EADATA);
231 memcpy(tmp, lmm, lmmlen);
232 }
233 set_mrc_cr_flags(rec, cr_flags);
234}
235
236static inline __u64 attr_pack(unsigned int ia_valid)
237{
238 __u64 sa_valid = 0;
239
240 if (ia_valid & ATTR_MODE)
241 sa_valid |= MDS_ATTR_MODE;
242 if (ia_valid & ATTR_UID)
243 sa_valid |= MDS_ATTR_UID;
244 if (ia_valid & ATTR_GID)
245 sa_valid |= MDS_ATTR_GID;
246 if (ia_valid & ATTR_SIZE)
247 sa_valid |= MDS_ATTR_SIZE;
248 if (ia_valid & ATTR_ATIME)
249 sa_valid |= MDS_ATTR_ATIME;
250 if (ia_valid & ATTR_MTIME)
251 sa_valid |= MDS_ATTR_MTIME;
252 if (ia_valid & ATTR_CTIME)
253 sa_valid |= MDS_ATTR_CTIME;
254 if (ia_valid & ATTR_ATIME_SET)
255 sa_valid |= MDS_ATTR_ATIME_SET;
256 if (ia_valid & ATTR_MTIME_SET)
257 sa_valid |= MDS_ATTR_MTIME_SET;
258 if (ia_valid & ATTR_FORCE)
259 sa_valid |= MDS_ATTR_FORCE;
260 if (ia_valid & ATTR_ATTR_FLAG)
261 sa_valid |= MDS_ATTR_ATTR_FLAG;
262 if (ia_valid & ATTR_KILL_SUID)
263 sa_valid |= MDS_ATTR_KILL_SUID;
264 if (ia_valid & ATTR_KILL_SGID)
265 sa_valid |= MDS_ATTR_KILL_SGID;
266 if (ia_valid & ATTR_CTIME_SET)
267 sa_valid |= MDS_ATTR_CTIME_SET;
268 if (ia_valid & ATTR_OPEN)
269 sa_valid |= MDS_ATTR_FROM_OPEN;
270 if (ia_valid & ATTR_BLOCKS)
271 sa_valid |= MDS_ATTR_BLOCKS;
272 if (ia_valid & MDS_OPEN_OWNEROVERRIDE)
273
274 sa_valid |= MDS_OPEN_OWNEROVERRIDE;
275 return sa_valid;
276}
277
278static void mdc_setattr_pack_rec(struct mdt_rec_setattr *rec,
279 struct md_op_data *op_data)
280{
281 rec->sa_opcode = REINT_SETATTR;
282 rec->sa_fsuid = from_kuid(&init_user_ns, current_fsuid());
283 rec->sa_fsgid = from_kgid(&init_user_ns, current_fsgid());
284 rec->sa_cap = cfs_curproc_cap_pack();
285 rec->sa_suppgid = -1;
286
287 rec->sa_fid = op_data->op_fid1;
288 rec->sa_valid = attr_pack(op_data->op_attr.ia_valid);
289 rec->sa_mode = op_data->op_attr.ia_mode;
290 rec->sa_uid = from_kuid(&init_user_ns, op_data->op_attr.ia_uid);
291 rec->sa_gid = from_kgid(&init_user_ns, op_data->op_attr.ia_gid);
292 rec->sa_size = op_data->op_attr.ia_size;
293 rec->sa_blocks = op_data->op_attr_blocks;
294 rec->sa_atime = LTIME_S(op_data->op_attr.ia_atime);
295 rec->sa_mtime = LTIME_S(op_data->op_attr.ia_mtime);
296 rec->sa_ctime = LTIME_S(op_data->op_attr.ia_ctime);
297 rec->sa_attr_flags = op_data->op_attr_flags;
298 if ((op_data->op_attr.ia_valid & ATTR_GID) &&
299 in_group_p(op_data->op_attr.ia_gid))
300 rec->sa_suppgid =
301 from_kgid(&init_user_ns, op_data->op_attr.ia_gid);
302 else
303 rec->sa_suppgid = op_data->op_suppgids[0];
304
305 rec->sa_bias = op_data->op_bias;
306}
307
308static void mdc_ioepoch_pack(struct mdt_ioepoch *epoch,
309 struct md_op_data *op_data)
310{
311 epoch->mio_handle = op_data->op_handle;
312 epoch->mio_unused1 = 0;
313 epoch->mio_unused2 = 0;
314 epoch->mio_padding = 0;
315}
316
317void mdc_setattr_pack(struct ptlrpc_request *req, struct md_op_data *op_data,
318 void *ea, size_t ealen)
319{
320 struct mdt_rec_setattr *rec;
321 struct lov_user_md *lum = NULL;
322
323 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) !=
324 sizeof(struct mdt_rec_setattr));
325 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
326 mdc_setattr_pack_rec(rec, op_data);
327
328 if (ealen == 0)
329 return;
330
331 lum = req_capsule_client_get(&req->rq_pill, &RMF_EADATA);
332 if (!ea) {
333 lum->lmm_magic = cpu_to_le32(LOV_USER_MAGIC_V1);
334 lum->lmm_stripe_size = 0;
335 lum->lmm_stripe_count = 0;
336 lum->lmm_stripe_offset = (typeof(lum->lmm_stripe_offset))(-1);
337 } else {
338 memcpy(lum, ea, ealen);
339 }
340}
341
342void mdc_unlink_pack(struct ptlrpc_request *req, struct md_op_data *op_data)
343{
344 struct mdt_rec_unlink *rec;
345
346 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) != sizeof(struct mdt_rec_unlink));
347 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
348
349 rec->ul_opcode = op_data->op_cli_flags & CLI_RM_ENTRY ?
350 REINT_RMENTRY : REINT_UNLINK;
351 rec->ul_fsuid = op_data->op_fsuid;
352 rec->ul_fsgid = op_data->op_fsgid;
353 rec->ul_cap = op_data->op_cap;
354 rec->ul_mode = op_data->op_mode;
355 rec->ul_suppgid1 = op_data->op_suppgids[0];
356 rec->ul_suppgid2 = -1;
357 rec->ul_fid1 = op_data->op_fid1;
358 rec->ul_fid2 = op_data->op_fid2;
359 rec->ul_time = op_data->op_mod_time;
360 rec->ul_bias = op_data->op_bias;
361
362 mdc_pack_name(req, &RMF_NAME, op_data->op_name, op_data->op_namelen);
363}
364
365void mdc_link_pack(struct ptlrpc_request *req, struct md_op_data *op_data)
366{
367 struct mdt_rec_link *rec;
368
369 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) != sizeof(struct mdt_rec_link));
370 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
371
372 rec->lk_opcode = REINT_LINK;
373 rec->lk_fsuid = op_data->op_fsuid;
374 rec->lk_fsgid = op_data->op_fsgid;
375 rec->lk_cap = op_data->op_cap;
376 rec->lk_suppgid1 = op_data->op_suppgids[0];
377 rec->lk_suppgid2 = op_data->op_suppgids[1];
378 rec->lk_fid1 = op_data->op_fid1;
379 rec->lk_fid2 = op_data->op_fid2;
380 rec->lk_time = op_data->op_mod_time;
381 rec->lk_bias = op_data->op_bias;
382
383 mdc_pack_name(req, &RMF_NAME, op_data->op_name, op_data->op_namelen);
384}
385
386static void mdc_intent_close_pack(struct ptlrpc_request *req,
387 struct md_op_data *op_data)
388{
389 enum mds_op_bias bias = op_data->op_bias;
390 struct close_data *data;
391 struct ldlm_lock *lock;
392
393 if (!(bias & (MDS_HSM_RELEASE | MDS_CLOSE_LAYOUT_SWAP |
394 MDS_RENAME_MIGRATE)))
395 return;
396
397 data = req_capsule_client_get(&req->rq_pill, &RMF_CLOSE_DATA);
398 LASSERT(data);
399
400 lock = ldlm_handle2lock(&op_data->op_lease_handle);
401 if (lock) {
402 data->cd_handle = lock->l_remote_handle;
403 LDLM_LOCK_PUT(lock);
404 }
405 ldlm_cli_cancel(&op_data->op_lease_handle, LCF_LOCAL);
406
407 data->cd_data_version = op_data->op_data_version;
408 data->cd_fid = op_data->op_fid2;
409}
410
411void mdc_rename_pack(struct ptlrpc_request *req, struct md_op_data *op_data,
412 const char *old, size_t oldlen,
413 const char *new, size_t newlen)
414{
415 struct mdt_rec_rename *rec;
416
417 BUILD_BUG_ON(sizeof(struct mdt_rec_reint) != sizeof(struct mdt_rec_rename));
418 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
419
420
421 rec->rn_opcode = op_data->op_cli_flags & CLI_MIGRATE ?
422 REINT_MIGRATE : REINT_RENAME;
423 rec->rn_opcode = REINT_RENAME;
424 rec->rn_fsuid = op_data->op_fsuid;
425 rec->rn_fsgid = op_data->op_fsgid;
426 rec->rn_cap = op_data->op_cap;
427 rec->rn_suppgid1 = op_data->op_suppgids[0];
428 rec->rn_suppgid2 = op_data->op_suppgids[1];
429 rec->rn_fid1 = op_data->op_fid1;
430 rec->rn_fid2 = op_data->op_fid2;
431 rec->rn_time = op_data->op_mod_time;
432 rec->rn_mode = op_data->op_mode;
433 rec->rn_bias = op_data->op_bias;
434
435 mdc_pack_name(req, &RMF_NAME, old, oldlen);
436
437 if (new)
438 mdc_pack_name(req, &RMF_SYMTGT, new, newlen);
439
440 if (op_data->op_cli_flags & CLI_MIGRATE &&
441 op_data->op_bias & MDS_RENAME_MIGRATE) {
442 struct mdt_ioepoch *epoch;
443
444 mdc_intent_close_pack(req, op_data);
445 epoch = req_capsule_client_get(&req->rq_pill, &RMF_MDT_EPOCH);
446 mdc_ioepoch_pack(epoch, op_data);
447 }
448}
449
450void mdc_getattr_pack(struct ptlrpc_request *req, __u64 valid, u32 flags,
451 struct md_op_data *op_data, size_t ea_size)
452{
453 struct mdt_body *b = req_capsule_client_get(&req->rq_pill,
454 &RMF_MDT_BODY);
455
456 b->mbo_valid = valid;
457 if (op_data->op_bias & MDS_CHECK_SPLIT)
458 b->mbo_valid |= OBD_MD_FLCKSPLIT;
459 if (op_data->op_bias & MDS_CROSS_REF)
460 b->mbo_valid |= OBD_MD_FLCROSSREF;
461 b->mbo_eadatasize = ea_size;
462 b->mbo_flags = flags;
463 __mdc_pack_body(b, op_data->op_suppgids[0]);
464
465 b->mbo_fid1 = op_data->op_fid1;
466 b->mbo_fid2 = op_data->op_fid2;
467 b->mbo_valid |= OBD_MD_FLID;
468
469 if (op_data->op_name)
470 mdc_pack_name(req, &RMF_NAME, op_data->op_name,
471 op_data->op_namelen);
472}
473
474void mdc_close_pack(struct ptlrpc_request *req, struct md_op_data *op_data)
475{
476 struct mdt_ioepoch *epoch;
477 struct mdt_rec_setattr *rec;
478
479 epoch = req_capsule_client_get(&req->rq_pill, &RMF_MDT_EPOCH);
480 rec = req_capsule_client_get(&req->rq_pill, &RMF_REC_REINT);
481
482 mdc_setattr_pack_rec(rec, op_data);
483
484
485
486
487
488
489
490
491
492 if (rec->sa_atime == 0)
493 rec->sa_valid &= ~MDS_ATTR_ATIME;
494
495 mdc_ioepoch_pack(epoch, op_data);
496 mdc_intent_close_pack(req, op_data);
497}
498