1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2 * vim:expandtab:shiftwidth=8:tabstop=8:
4 * Copyright (C) 2001-2003 Cluster File Systems, Inc.
6 * This file is part of Lustre, http://www.sf.net/projects/lustre/
8 * Lustre is free software; you can redistribute it and/or
9 * modify it under the terms of version 2 of the GNU General Public
10 * License as published by the Free Software Foundation.
12 * Lustre is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with Lustre; if not, write to the Free Software
19 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 #define DEBUG_SUBSYSTEM S_CMOBD
24 #include <linux/config.h>
25 #include <linux/module.h>
26 #include <linux/kernel.h>
27 #include <linux/obd_class.h>
28 #include <linux/lustre_net.h>
29 #include <linux/lustre_mds.h>
30 #include <linux/lustre_smfs.h>
32 #include "cm_internal.h"
34 /* converts mds_rec_setattr to struct iattr. */
35 static inline void cmobd_rec2iattr(struct mds_rec_setattr *rec,
38 iattr->ia_uid = rec->sa_uid;
39 iattr->ia_gid = rec->sa_gid;
40 iattr->ia_mode = rec->sa_mode;
41 iattr->ia_size = rec->sa_size;
42 iattr->ia_valid = rec->sa_valid;
43 LTIME_S(iattr->ia_atime) = rec->sa_atime;
44 LTIME_S(iattr->ia_mtime) = rec->sa_mtime;
45 LTIME_S(iattr->ia_ctime) = rec->sa_ctime;
46 iattr->ia_attr_flags = rec->sa_attr_flags;
50 cmobd_prepare_mdc_data(struct mdc_op_data *data, struct lustre_id *id1,
51 struct lustre_id *id2, const char *name,
52 int namelen, __u32 mode)
57 memset(data, 0, sizeof(*data));
63 memset(&data->id2, 0, sizeof(data->id2));
67 data->namelen = namelen;
68 data->create_mode = mode;
69 data->mod_time = LTIME_S(CURRENT_TIME);
72 /* If mdc_setattr() is called with an 'iattr', then it is a normal RPC that
73 * should take the normal semaphore and go to the normal portal.
75 * If it is called with iattr->ia_valid & ATTR_FROM_OPEN, then it is a magic
76 * open-path setattr that should take the setattr semaphore and go to the
78 static int cmobd_reint_setattr(struct obd_device *obd, void *record)
80 struct cm_obd *cmobd = &obd->u.cm;
81 struct ptlrpc_request *req = NULL;
82 struct mds_kml_pack_info *mkpi;
83 struct mds_rec_setattr *rec;
84 struct mdc_op_data *op_data;
85 struct lustre_msg *msg;
92 mkpi = (struct mds_kml_pack_info *)record;
93 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
95 rec = lustre_msg_buf(msg, 0, 0);
99 /* converting setattr rec to struct iattr. */
100 cmobd_rec2iattr(rec, &iattr);
102 /* FIXME-UMKA: here should be handling of setattr() from open. Bug
103 * #249. Will be fixed later. */
105 /* converting localstore cookie to remote lustre_id. */
106 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->sa_id,
107 &rec->sa_id, sizeof(rec->sa_id));
109 CERROR("Can't read master MDS store cookie "
110 "from local inode EA, err = %d.\n", rc);
114 OBD_ALLOC(op_data, sizeof(*op_data));
117 cmobd_prepare_mdc_data(op_data, &rec->sa_id, NULL,
120 /* handling possible EAs. */
121 ea1 = lustre_msg_buf(msg, 1, 0);
122 ea1len = ea1 ? msg->buflens[1] : 0;
124 ea2 = lustre_msg_buf(msg, 2, 0);
125 ea2len = ea2 ? msg->buflens[2] : 0;
127 rc = md_setattr(cmobd->master_exp, op_data, &iattr,
128 ea1, ea1len, ea2, ea2len, &req);
129 OBD_FREE(op_data, sizeof(*op_data));
132 ptlrpc_req_finished(req);
136 static int cmobd_reint_create(struct obd_device *obd, void *record)
138 struct cm_obd *cmobd = &obd->u.cm;
139 struct ptlrpc_request *req = NULL;
140 struct mds_kml_pack_info *mkpi;
141 int rc = 0, namelen, datalen, alloc = 0;
142 struct mds_rec_create *rec;
143 struct mdc_op_data *op_data;
144 struct lustre_msg *msg;
145 struct mds_body *body;
146 struct lustre_id lid;
150 mkpi = (struct mds_kml_pack_info *)record;
151 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
153 rec = lustre_msg_buf(msg, 0, 0);
157 lid = rec->cr_replayid;
159 /* converting local inode store cookie to remote lustre_id. */
160 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->cr_id,
161 &rec->cr_id, sizeof(rec->cr_id));
163 CERROR("Can't read master MDS store cookie "
164 "from local inode EA, err = %d.\n", rc);
168 /* getting name to be created and its length */
169 name = lustre_msg_string(msg, 1, 0);
170 namelen = name ? msg->buflens[1] - 1 : 0;
172 /* getting misc data (symlink) and its length */
173 data = (char *)lustre_msg_buf(msg, 2, 0);
174 datalen = data ? msg->buflens[2] : 0;
176 OBD_ALLOC(op_data, sizeof(*op_data));
178 GOTO(exit, rc = -ENOMEM);
180 /* zeroing @rec->cr_replayid out in request, as master MDS should create
181 * own inode (with own store cookie). */
182 memset(&rec->cr_replayid, 0, sizeof(rec->cr_replayid));
184 /* prepare mdc request data. */
185 cmobd_prepare_mdc_data(op_data, &rec->cr_id, &rec->cr_replayid,
186 name, namelen, rec->cr_mode);
188 /* requesting to master to create object with passed attributes. */
189 rc = md_create(cmobd->master_exp, op_data, data, datalen,
190 rec->cr_mode, current->fsuid, current->fsgid,
192 OBD_FREE(op_data, sizeof(*op_data));
195 /* here we save store cookie from master MDS to local
197 body = lustre_msg_buf(req->rq_repmsg, 0, sizeof(*body));
199 rc = mds_update_mid(cmobd->cache_exp->exp_obd, &lid,
200 &body->id1, sizeof(body->id1));
204 ptlrpc_req_finished(req);
207 OBD_FREE(data, datalen);
212 static int cmobd_reint_unlink(struct obd_device *obd, void *record)
214 struct cm_obd *cmobd = &obd->u.cm;
215 struct ptlrpc_request *req = NULL;
216 struct mds_kml_pack_info *mkpi;
217 struct mdc_op_data *op_data;
218 struct mds_rec_unlink *rec;
219 struct lustre_msg *msg;
224 mkpi = (struct mds_kml_pack_info *)record;
225 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
227 rec = lustre_msg_buf(msg, 0, 0);
231 /* converting local store cookie to remote lustre_id. */
232 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->ul_id1,
233 &rec->ul_id1, sizeof(rec->ul_id1));
235 CERROR("Can't read master MDS store cookie "
236 "from local inode EA, err = %d.\n", rc);
240 /* getting name to be created and its length */
241 name = lustre_msg_string(msg, 1, 0);
242 namelen = name ? msg->buflens[1] - 1 : 0;
244 OBD_ALLOC(op_data, sizeof(*op_data));
248 /* prepare mdc request data. */
249 cmobd_prepare_mdc_data(op_data, &rec->ul_id1, NULL,
250 name, namelen, rec->ul_mode);
252 rc = md_unlink(cmobd->master_exp, op_data, &req);
253 OBD_FREE(op_data, sizeof(*op_data));
256 ptlrpc_req_finished(req);
260 static int cmobd_reint_link(struct obd_device *obd, void *record)
262 struct cm_obd *cmobd = &obd->u.cm;
263 struct ptlrpc_request *req = NULL;
264 struct mds_kml_pack_info *mkpi;
265 struct mdc_op_data *op_data;
266 struct mds_rec_link *rec;
267 struct lustre_msg *msg;
272 mkpi = (struct mds_kml_pack_info *)record;
273 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
275 rec = lustre_msg_buf(msg, 0, 0);
279 /* converting local store cookie for both ids to remote lustre_id. */
280 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->lk_id1,
281 &rec->lk_id1, sizeof(rec->lk_id1));
283 CERROR("Can't read master MDS store cookie "
284 "from local inode EA, err = %d.\n", rc);
288 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->lk_id2,
289 &rec->lk_id2, sizeof(rec->lk_id2));
291 CERROR("Can't read master MDS store cookie "
292 "from local inode EA, err = %d.\n", rc);
296 /* getting name to be created and its length */
297 name = lustre_msg_string(msg, 1, 0);
298 namelen = name ? msg->buflens[1] - 1: 0;
300 OBD_ALLOC(op_data, sizeof(*op_data));
304 /* prepare mdc request data. */
305 cmobd_prepare_mdc_data(op_data, &rec->lk_id1, &rec->lk_id2,
308 rc = md_link(cmobd->master_exp, op_data, &req);
309 OBD_FREE(op_data, sizeof(*op_data));
312 ptlrpc_req_finished(req);
316 static int cmobd_reint_rename(struct obd_device *obd, void *record)
318 struct cm_obd *cmobd = &obd->u.cm;
319 struct ptlrpc_request *req = NULL;
320 struct mds_kml_pack_info *mkpi;
321 struct mdc_op_data *op_data;
322 struct mds_rec_rename *rec;
323 int rc = 0, oldlen, newlen;
324 struct lustre_msg *msg;
328 mkpi = (struct mds_kml_pack_info *)record;
329 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
331 rec = lustre_msg_buf(msg, 0, 0);
335 /* converting local store cookie for both ids to remote lustre_id. */
336 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->rn_id1,
337 &rec->rn_id1, sizeof(rec->rn_id1));
339 CERROR("Can't read master MDS store cookie "
340 "from local inode EA, err = %d.\n", rc);
344 rc = mds_read_mid(cmobd->cache_exp->exp_obd, &rec->rn_id2,
345 &rec->rn_id2, sizeof(rec->rn_id2));
347 CERROR("Can't read master MDS store cookie "
348 "from local inode EA, err = %d.\n", rc);
352 /* getting old name and its length */
353 old = lustre_msg_string(msg, 1, 0);
354 oldlen = old ? msg->buflens[1] - 1 : 0;
356 /* getting new len and its length */
357 new = lustre_msg_string(msg, 2, 0);
358 newlen = new ? msg->buflens[2] - 1: 0;
360 OBD_ALLOC(op_data, sizeof(*op_data));
364 /* prepare mdc request data. */
365 cmobd_prepare_mdc_data(op_data, &rec->rn_id1, &rec->rn_id1,
368 rc = md_rename(cmobd->master_exp, op_data, old, oldlen,
370 OBD_FREE(op_data, sizeof(*op_data));
373 ptlrpc_req_finished(req);
377 typedef int (*cmobd_reint_rec_func_t)(struct obd_device *, void *);
379 static cmobd_reint_rec_func_t mds_reint_handler[REINT_MAX + 1] = {
380 [REINT_SETATTR] cmobd_reint_setattr,
381 [REINT_CREATE] cmobd_reint_create,
382 [REINT_LINK] cmobd_reint_link,
383 [REINT_UNLINK] cmobd_reint_unlink,
384 [REINT_RENAME] cmobd_reint_rename,
387 int cmobd_reint_mds(struct obd_device *obd, void *record, int dummy)
389 struct mds_kml_pack_info *mkpi;
390 struct lustre_msg *msg;
393 mkpi = (struct mds_kml_pack_info *)record;
394 msg = (struct lustre_msg *)(record + sizeof(*mkpi));
396 opcode = *(__u32 *)lustre_msg_buf(msg, 0, 0);
398 if (opcode > REINT_MAX || opcode <= 0) {
399 CERROR("Invalid mds reint opcode %u\n",
404 return mds_reint_handler[opcode](obd, record);