1 /* -*- mode: c; c-basic-offset: 8; indent-tabs-mode: nil; -*-
2 * vim:expandtab:shiftwidth=8:tabstop=8:
6 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License version 2 only,
10 * as published by the Free Software Foundation.
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License version 2 for more details (a copy is included
16 * in the LICENSE file that accompanied this code).
18 * You should have received a copy of the GNU General Public License
19 * version 2 along with this program; If not, see
20 * http://www.sun.com/software/products/lustre/docs/GPLv2.pdf
22 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
23 * CA 95054 USA or visit www.sun.com if you need additional information or
29 * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
30 * Use is subject to license terms.
33 * This file is part of Lustre, http://www.lustre.org/
34 * Lustre is a trademark of Sun Microsystems, Inc.
36 * lustre/mgs/mgs_llog.c
38 * Lustre Management Server (mgs) config llog creation
40 * Author: Nathan Rutman <nathan@clusterfs.com>
46 #define DEBUG_SUBSYSTEM S_MGS
47 #define D_MGS D_CONFIG
50 #include <linux/module.h>
51 #include <linux/pagemap.h>
57 #include <obd_class.h>
58 #include <lustre_log.h>
60 #include <libcfs/list.h>
61 #include <linux/lvfs.h>
62 #include <lustre_fsfilt.h>
63 #include <lustre_disk.h>
64 #include <lustre_param.h>
65 #include <lustre_sec.h>
66 #include "mgs_internal.h"
68 /********************** Class functions ********************/
70 /* Caller must list_del and OBD_FREE each dentry from the list */
71 int class_dentry_readdir(struct obd_device *obd, struct dentry *dir,
72 struct vfsmount *inmnt,
73 cfs_list_t *dentry_list){
74 /* see mds_cleanup_pending */
75 struct lvfs_run_ctxt saved;
77 struct dentry *dentry;
82 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
85 GOTO(out_pop, rc = PTR_ERR(dentry));
89 GOTO(out_pop, rc = PTR_ERR(mnt));
92 file = ll_dentry_open(dentry, mnt, O_RDONLY, current_cred());
94 /* dentry_open_it() drops the dentry, mnt refs */
95 GOTO(out_pop, rc = PTR_ERR(file));
97 CFS_INIT_LIST_HEAD(dentry_list);
98 rc = l_readdir(file, dentry_list);
100 /* filp_close->fput() drops the dentry, mnt refs */
103 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
107 /******************** DB functions *********************/
109 static inline int name_create(char **newname, char *prefix, char *suffix)
112 OBD_ALLOC(*newname, strlen(prefix) + strlen(suffix) + 1);
115 sprintf(*newname, "%s%s", prefix, suffix);
119 static inline void name_destroy(char **name)
122 OBD_FREE(*name, strlen(*name) + 1);
126 struct mgs_fsdb_handler_data
132 /* from the (client) config log, figure out:
133 1. which ost's/mdt's are configured (by index)
134 2. what the last config step is
135 3. COMPAT_146 lov name
136 4. COMPAT_146 mdt lov name
137 5. COMPAT_146 mdc name
138 6. COMPAT_18 osc name
140 /* It might be better to have a separate db file, instead of parsing the info
141 out of the client log. This is slow and potentially error-prone. */
142 static int mgs_fsdb_handler(struct llog_handle *llh, struct llog_rec_hdr *rec,
145 struct mgs_fsdb_handler_data *d = (struct mgs_fsdb_handler_data *) data;
146 struct fs_db *fsdb = d->fsdb;
147 int cfg_len = rec->lrh_len;
148 char *cfg_buf = (char*) (rec + 1);
149 struct lustre_cfg *lcfg;
154 if (rec->lrh_type != OBD_CFG_REC) {
155 CERROR("unhandled lrh_type: %#x\n", rec->lrh_type);
159 rc = lustre_cfg_sanity_check(cfg_buf, cfg_len);
161 CERROR("Insane cfg\n");
165 lcfg = (struct lustre_cfg *)cfg_buf;
167 CDEBUG(D_INFO, "cmd %x %s %s\n", lcfg->lcfg_command,
168 lustre_cfg_string(lcfg, 0), lustre_cfg_string(lcfg, 1));
170 /* Figure out ost indicies */
171 /* lov_modify_tgts add 0:lov1 1:ost1_UUID 2(index):0 3(gen):1 */
172 if (lcfg->lcfg_command == LCFG_LOV_ADD_OBD ||
173 lcfg->lcfg_command == LCFG_LOV_DEL_OBD) {
174 index = simple_strtoul(lustre_cfg_string(lcfg, 2),
176 CDEBUG(D_MGS, "OST index for %s is %u (%s)\n",
177 lustre_cfg_string(lcfg, 1), index,
178 lustre_cfg_string(lcfg, 2));
179 cfs_set_bit(index, fsdb->fsdb_ost_index_map);
182 /* Figure out mdt indicies */
183 /* attach 0:MDC_uml1_mdsA_MNT_client 1:mdc 2:1d834_MNT_client_03f */
184 if ((lcfg->lcfg_command == LCFG_ATTACH) &&
185 (strcmp(lustre_cfg_string(lcfg, 1), LUSTRE_MDC_NAME) == 0)) {
186 rc = server_name2index(lustre_cfg_string(lcfg, 0),
188 if (rc != LDD_F_SV_TYPE_MDT) {
189 CWARN("Unparsable MDC name %s, assuming index 0\n",
190 lustre_cfg_string(lcfg, 0));
194 CDEBUG(D_MGS, "MDT index is %u\n", index);
195 cfs_set_bit(index, fsdb->fsdb_mdt_index_map);
196 fsdb->fsdb_mdt_count ++;
200 /* figure out the old LOV name. fsdb_gen = 0 means old log */
201 /* #01 L attach 0:lov_mdsA 1:lov 2:cdbe9_lov_mdsA_dc8cf7f3bb */
202 if ((fsdb->fsdb_gen == 0) && (lcfg->lcfg_command == LCFG_ATTACH) &&
203 (strcmp(lustre_cfg_string(lcfg, 1), LUSTRE_LOV_NAME) == 0)) {
204 cfs_set_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags);
205 name_destroy(&fsdb->fsdb_clilov);
206 rc = name_create(&fsdb->fsdb_clilov,
207 lustre_cfg_string(lcfg, 0), "");
210 CDEBUG(D_MGS, "client lov name is %s\n", fsdb->fsdb_clilov);
213 /* figure out the old MDT lov name from the MDT uuid */
214 if ((fsdb->fsdb_gen == 0) && (lcfg->lcfg_command == LCFG_SETUP) &&
215 (strncmp(lustre_cfg_string(lcfg, 0), "MDC_", 4) == 0)) {
217 cfs_set_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags);
218 ptr = strstr(lustre_cfg_string(lcfg, 1), "_UUID");
220 CERROR("Can't parse MDT uuid %s\n",
221 lustre_cfg_string(lcfg, 1));
225 name_destroy(&fsdb->fsdb_mdtlov);
226 rc = name_create(&fsdb->fsdb_mdtlov,
227 "lov_", lustre_cfg_string(lcfg, 1));
230 name_destroy(&fsdb->fsdb_mdc);
231 rc = name_create(&fsdb->fsdb_mdc,
232 lustre_cfg_string(lcfg, 0), "");
235 CDEBUG(D_MGS, "MDT lov name is %s\n", fsdb->fsdb_mdtlov);
240 * compat to 1.8, check osc name used by MDT0 to OSTs, bz18548.
242 if (!cfs_test_bit(FSDB_OSCNAME18, &fsdb->fsdb_flags) &&
243 lcfg->lcfg_command == LCFG_ATTACH &&
244 strcmp(lustre_cfg_string(lcfg, 1), LUSTRE_OSC_NAME) == 0) {
245 if (OBD_OCD_VERSION_MAJOR(d->ver) == 1 &&
246 OBD_OCD_VERSION_MINOR(d->ver) <= 8) {
247 CWARN("MDT using 1.8 OSC name scheme\n");
248 cfs_set_bit(FSDB_OSCNAME18, &fsdb->fsdb_flags);
252 if (lcfg->lcfg_command == LCFG_MARKER) {
253 struct cfg_marker *marker;
254 marker = lustre_cfg_buf(lcfg, 1);
256 d->ver = marker->cm_vers;
258 /* Keep track of the latest marker step */
259 fsdb->fsdb_gen = max(fsdb->fsdb_gen, marker->cm_step);
265 /* fsdb->fsdb_sem is already held in mgs_find_or_make_fsdb*/
266 static int mgs_get_fsdb_from_llog(struct obd_device *obd, struct fs_db *fsdb)
269 struct llog_handle *loghandle;
270 struct lvfs_run_ctxt saved;
271 struct llog_ctxt *ctxt;
272 struct mgs_fsdb_handler_data d = { fsdb, 0 };
276 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
277 LASSERT(ctxt != NULL);
278 name_create(&logname, fsdb->fsdb_name, "-client");
279 cfs_down(&fsdb->fsdb_sem);
280 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
281 rc = llog_create(ctxt, &loghandle, NULL, logname);
285 rc = llog_init_handle(loghandle, LLOG_F_IS_PLAIN, NULL);
289 if (llog_get_size(loghandle) <= 1)
290 cfs_set_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags);
292 rc = llog_process(loghandle, mgs_fsdb_handler, (void *) &d, NULL);
293 CDEBUG(D_INFO, "get_db = %d\n", rc);
295 rc2 = llog_close(loghandle);
299 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
300 cfs_up(&fsdb->fsdb_sem);
301 name_destroy(&logname);
307 static void mgs_free_fsdb_srpc(struct fs_db *fsdb)
309 struct mgs_tgt_srpc_conf *tgtconf;
311 /* free target-specific rules */
312 while (fsdb->fsdb_srpc_tgt) {
313 tgtconf = fsdb->fsdb_srpc_tgt;
314 fsdb->fsdb_srpc_tgt = tgtconf->mtsc_next;
316 LASSERT(tgtconf->mtsc_tgt);
318 sptlrpc_rule_set_free(&tgtconf->mtsc_rset);
319 OBD_FREE(tgtconf->mtsc_tgt, strlen(tgtconf->mtsc_tgt) + 1);
320 OBD_FREE_PTR(tgtconf);
323 /* free general rules */
324 sptlrpc_rule_set_free(&fsdb->fsdb_srpc_gen);
327 struct fs_db *mgs_find_fsdb(struct obd_device *obd, char *fsname)
329 struct mgs_obd *mgs = &obd->u.mgs;
333 cfs_list_for_each(tmp, &mgs->mgs_fs_db_list) {
334 fsdb = cfs_list_entry(tmp, struct fs_db, fsdb_list);
335 if (strcmp(fsdb->fsdb_name, fsname) == 0)
341 /* caller must hold the mgs->mgs_fs_db_lock */
342 static struct fs_db *mgs_new_fsdb(struct obd_device *obd, char *fsname)
344 struct mgs_obd *mgs = &obd->u.mgs;
349 if (strlen(fsname) >= sizeof(fsdb->fsdb_name)) {
350 CERROR("fsname %s is too long\n", fsname);
358 strcpy(fsdb->fsdb_name, fsname);
359 cfs_sema_init(&fsdb->fsdb_sem, 1);
360 cfs_set_bit(FSDB_UDESC, &fsdb->fsdb_flags);
362 if (strcmp(fsname, MGSSELF_NAME) == 0) {
363 cfs_set_bit(FSDB_MGS_SELF, &fsdb->fsdb_flags);
365 OBD_ALLOC(fsdb->fsdb_ost_index_map, INDEX_MAP_SIZE);
366 OBD_ALLOC(fsdb->fsdb_mdt_index_map, INDEX_MAP_SIZE);
367 if (!fsdb->fsdb_ost_index_map || !fsdb->fsdb_mdt_index_map) {
368 CERROR("No memory for index maps\n");
372 rc = name_create(&fsdb->fsdb_mdtlov, fsname, "-mdtlov");
375 rc = name_create(&fsdb->fsdb_mdtlmv, fsname, "-mdtlmv");
378 rc = name_create(&fsdb->fsdb_clilov, fsname, "-clilov");
381 rc = name_create(&fsdb->fsdb_clilmv, fsname, "-clilmv");
385 /* initialise data for NID table */
386 mgs_ir_init_fs(obd, fsdb);
388 lproc_mgs_add_live(obd, fsdb);
391 cfs_list_add(&fsdb->fsdb_list, &mgs->mgs_fs_db_list);
395 if (fsdb->fsdb_ost_index_map)
396 OBD_FREE(fsdb->fsdb_ost_index_map, INDEX_MAP_SIZE);
397 if (fsdb->fsdb_mdt_index_map)
398 OBD_FREE(fsdb->fsdb_mdt_index_map, INDEX_MAP_SIZE);
399 name_destroy(&fsdb->fsdb_clilov);
400 name_destroy(&fsdb->fsdb_clilmv);
401 name_destroy(&fsdb->fsdb_mdtlov);
402 name_destroy(&fsdb->fsdb_mdtlmv);
407 static void mgs_free_fsdb(struct obd_device *obd, struct fs_db *fsdb)
409 /* wait for anyone with the sem */
410 cfs_down(&fsdb->fsdb_sem);
411 lproc_mgs_del_live(obd, fsdb);
412 cfs_list_del(&fsdb->fsdb_list);
414 /* deinitialize fsr */
415 mgs_ir_fini_fs(obd, fsdb);
417 if (fsdb->fsdb_ost_index_map)
418 OBD_FREE(fsdb->fsdb_ost_index_map, INDEX_MAP_SIZE);
419 if (fsdb->fsdb_mdt_index_map)
420 OBD_FREE(fsdb->fsdb_mdt_index_map, INDEX_MAP_SIZE);
421 name_destroy(&fsdb->fsdb_clilov);
422 name_destroy(&fsdb->fsdb_clilmv);
423 name_destroy(&fsdb->fsdb_mdtlov);
424 name_destroy(&fsdb->fsdb_mdtlmv);
425 name_destroy(&fsdb->fsdb_mdc);
426 mgs_free_fsdb_srpc(fsdb);
430 int mgs_init_fsdb_list(struct obd_device *obd)
432 struct mgs_obd *mgs = &obd->u.mgs;
433 CFS_INIT_LIST_HEAD(&mgs->mgs_fs_db_list);
437 int mgs_cleanup_fsdb_list(struct obd_device *obd)
439 struct mgs_obd *mgs = &obd->u.mgs;
441 cfs_list_t *tmp, *tmp2;
442 cfs_down(&mgs->mgs_sem);
443 cfs_list_for_each_safe(tmp, tmp2, &mgs->mgs_fs_db_list) {
444 fsdb = cfs_list_entry(tmp, struct fs_db, fsdb_list);
445 mgs_free_fsdb(obd, fsdb);
447 cfs_up(&mgs->mgs_sem);
451 int mgs_find_or_make_fsdb(struct obd_device *obd, char *name,
454 struct mgs_obd *mgs = &obd->u.mgs;
458 cfs_down(&mgs->mgs_sem);
459 fsdb = mgs_find_fsdb(obd, name);
461 cfs_up(&mgs->mgs_sem);
466 CDEBUG(D_MGS, "Creating new db\n");
467 fsdb = mgs_new_fsdb(obd, name);
468 cfs_up(&mgs->mgs_sem);
472 if (!cfs_test_bit(FSDB_MGS_SELF, &fsdb->fsdb_flags)) {
473 /* populate the db from the client llog */
474 rc = mgs_get_fsdb_from_llog(obd, fsdb);
476 CERROR("Can't get db from client log %d\n", rc);
477 mgs_free_fsdb(obd, fsdb);
482 /* populate srpc rules from params llog */
483 rc = mgs_get_fsdb_srpc_from_llog(obd, fsdb);
485 CERROR("Can't get db from params log %d\n", rc);
486 mgs_free_fsdb(obd, fsdb);
497 -1= empty client log */
498 int mgs_check_index(struct obd_device *obd, struct mgs_target_info *mti)
505 LASSERT(!(mti->mti_flags & LDD_F_NEED_INDEX));
507 rc = mgs_find_or_make_fsdb(obd, mti->mti_fsname, &fsdb);
509 CERROR("Can't get db for %s\n", mti->mti_fsname);
513 if (cfs_test_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags))
516 if (mti->mti_flags & LDD_F_SV_TYPE_OST)
517 imap = fsdb->fsdb_ost_index_map;
518 else if (mti->mti_flags & LDD_F_SV_TYPE_MDT)
519 imap = fsdb->fsdb_mdt_index_map;
523 if (cfs_test_bit(mti->mti_stripe_index, imap))
528 static __inline__ int next_index(void *index_map, int map_len)
531 for (i = 0; i < map_len * 8; i++)
532 if (!cfs_test_bit(i, index_map)) {
535 CERROR("max index %d exceeded.\n", i);
540 0 newly marked as in use
542 +EALREADY for update of an old index */
543 static int mgs_set_index(struct obd_device *obd, struct mgs_target_info *mti)
550 rc = mgs_find_or_make_fsdb(obd, mti->mti_fsname, &fsdb);
552 CERROR("Can't get db for %s\n", mti->mti_fsname);
556 if (mti->mti_flags & LDD_F_SV_TYPE_OST) {
557 imap = fsdb->fsdb_ost_index_map;
558 } else if (mti->mti_flags & LDD_F_SV_TYPE_MDT) {
559 imap = fsdb->fsdb_mdt_index_map;
560 if (fsdb->fsdb_mdt_count >= MAX_MDT_COUNT) {
561 LCONSOLE_ERROR_MSG(0x13f, "The max mdt count"
562 "is %d\n", (int)MAX_MDT_COUNT);
569 if (mti->mti_flags & LDD_F_NEED_INDEX) {
570 rc = next_index(imap, INDEX_MAP_SIZE);
573 mti->mti_stripe_index = rc;
574 if (mti->mti_flags & LDD_F_SV_TYPE_MDT)
575 fsdb->fsdb_mdt_count ++;
578 if (mti->mti_stripe_index >= INDEX_MAP_SIZE * 8) {
579 LCONSOLE_ERROR_MSG(0x13f, "Server %s requested index %d, "
580 "but the max index is %d.\n",
581 mti->mti_svname, mti->mti_stripe_index,
586 if (cfs_test_bit(mti->mti_stripe_index, imap)) {
587 if ((mti->mti_flags & LDD_F_VIRGIN) &&
588 !(mti->mti_flags & LDD_F_WRITECONF)) {
589 LCONSOLE_ERROR_MSG(0x140, "Server %s requested index "
590 "%d, but that index is already in "
591 "use. Use --writeconf to force\n",
593 mti->mti_stripe_index);
596 CDEBUG(D_MGS, "Server %s updating index %d\n",
597 mti->mti_svname, mti->mti_stripe_index);
602 cfs_set_bit(mti->mti_stripe_index, imap);
603 cfs_clear_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags);
604 server_make_name(mti->mti_flags, mti->mti_stripe_index,
605 mti->mti_fsname, mti->mti_svname);
607 CDEBUG(D_MGS, "Set index for %s to %d\n", mti->mti_svname,
608 mti->mti_stripe_index);
613 struct mgs_modify_lookup {
614 struct cfg_marker mml_marker;
618 static int mgs_modify_handler(struct llog_handle *llh, struct llog_rec_hdr *rec,
621 struct mgs_modify_lookup *mml = (struct mgs_modify_lookup *)data;
622 struct cfg_marker *marker;
623 struct lustre_cfg *lcfg = (struct lustre_cfg *)(rec + 1);
624 int cfg_len = rec->lrh_len - sizeof(struct llog_rec_hdr) -
625 sizeof(struct llog_rec_tail);
629 if (rec->lrh_type != OBD_CFG_REC) {
630 CERROR("unhandled lrh_type: %#x\n", rec->lrh_type);
634 rc = lustre_cfg_sanity_check(lcfg, cfg_len);
636 CERROR("Insane cfg\n");
640 /* We only care about markers */
641 if (lcfg->lcfg_command != LCFG_MARKER)
644 marker = lustre_cfg_buf(lcfg, 1);
645 if ((strcmp(mml->mml_marker.cm_comment, marker->cm_comment) == 0) &&
646 (strcmp(mml->mml_marker.cm_tgtname, marker->cm_tgtname) == 0) &&
647 !(marker->cm_flags & CM_SKIP)) {
648 /* Found a non-skipped marker match */
649 CDEBUG(D_MGS, "Changing rec %u marker %d %x->%x: %s %s\n",
650 rec->lrh_index, marker->cm_step,
651 marker->cm_flags, mml->mml_marker.cm_flags,
652 marker->cm_tgtname, marker->cm_comment);
653 /* Overwrite the old marker llog entry */
654 marker->cm_flags &= ~CM_EXCLUDE; /* in case we're unexcluding */
655 marker->cm_flags |= mml->mml_marker.cm_flags;
656 marker->cm_canceltime = mml->mml_marker.cm_canceltime;
657 /* Header and tail are added back to lrh_len in
658 llog_lvfs_write_rec */
659 rec->lrh_len = cfg_len;
660 rc = llog_write_rec(llh, rec, NULL, 0, (void *)lcfg,
669 /* Modify an existing config log record (for CM_SKIP or CM_EXCLUDE) */
670 static int mgs_modify(struct obd_device *obd, struct fs_db *fsdb,
671 struct mgs_target_info *mti, char *logname,
672 char *devname, char *comment, int flags)
674 struct llog_handle *loghandle;
675 struct lvfs_run_ctxt saved;
676 struct llog_ctxt *ctxt;
677 struct mgs_modify_lookup *mml;
681 CDEBUG(D_MGS, "modify %s/%s/%s fl=%x\n", logname, devname, comment,
684 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
686 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
687 LASSERT(ctxt != NULL);
688 rc = llog_create(ctxt, &loghandle, NULL, logname);
692 rc = llog_init_handle(loghandle, LLOG_F_IS_PLAIN, NULL);
696 if (llog_get_size(loghandle) <= 1)
697 GOTO(out_close, rc = 0);
701 GOTO(out_close, rc = -ENOMEM);
702 strcpy(mml->mml_marker.cm_comment, comment);
703 strcpy(mml->mml_marker.cm_tgtname, devname);
704 /* Modify mostly means cancel */
705 mml->mml_marker.cm_flags = flags;
706 mml->mml_marker.cm_canceltime = flags ? cfs_time_current_sec() : 0;
707 mml->mml_modified = 0;
708 rc = llog_process(loghandle, mgs_modify_handler, (void *)mml, NULL);
709 if (!rc && !mml->mml_modified)
714 rc2 = llog_close(loghandle);
718 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
719 if (rc && rc != -ENODEV)
720 CERROR("modify %s/%s failed %d\n",
721 mti->mti_svname, comment, rc);
726 /******************** config log recording functions *********************/
728 static int record_lcfg(struct obd_device *obd, struct llog_handle *llh,
729 struct lustre_cfg *lcfg)
731 struct lvfs_run_ctxt saved;
732 struct llog_rec_hdr rec;
738 LASSERT(llh->lgh_ctxt);
740 buflen = lustre_cfg_len(lcfg->lcfg_bufcount,
742 rec.lrh_len = llog_data_len(buflen);
743 rec.lrh_type = OBD_CFG_REC;
745 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
746 /* idx = -1 means append */
747 rc = llog_write_rec(llh, &rec, NULL, 0, (void *)lcfg, -1);
748 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
750 CERROR("failed %d\n", rc);
754 static int record_base(struct obd_device *obd, struct llog_handle *llh,
755 char *cfgname, lnet_nid_t nid, int cmd,
756 char *s1, char *s2, char *s3, char *s4)
758 struct lustre_cfg_bufs bufs;
759 struct lustre_cfg *lcfg;
762 CDEBUG(D_MGS, "lcfg %s %#x %s %s %s %s\n", cfgname,
763 cmd, s1, s2, s3, s4);
765 lustre_cfg_bufs_reset(&bufs, cfgname);
767 lustre_cfg_bufs_set_string(&bufs, 1, s1);
769 lustre_cfg_bufs_set_string(&bufs, 2, s2);
771 lustre_cfg_bufs_set_string(&bufs, 3, s3);
773 lustre_cfg_bufs_set_string(&bufs, 4, s4);
775 lcfg = lustre_cfg_new(cmd, &bufs);
778 lcfg->lcfg_nid = nid;
780 rc = record_lcfg(obd, llh, lcfg);
782 lustre_cfg_free(lcfg);
785 CERROR("error %d: lcfg %s %#x %s %s %s %s\n", rc, cfgname,
786 cmd, s1, s2, s3, s4);
792 static inline int record_add_uuid(struct obd_device *obd,
793 struct llog_handle *llh,
794 uint64_t nid, char *uuid)
796 return record_base(obd,llh,NULL,nid,LCFG_ADD_UUID,uuid,0,0,0);
800 static inline int record_add_conn(struct obd_device *obd,
801 struct llog_handle *llh,
805 return record_base(obd,llh,devname,0,LCFG_ADD_CONN,uuid,0,0,0);
808 static inline int record_attach(struct obd_device *obd, struct llog_handle *llh,
809 char *devname, char *type, char *uuid)
811 return record_base(obd,llh,devname,0,LCFG_ATTACH,type,uuid,0,0);
814 static inline int record_setup(struct obd_device *obd, struct llog_handle *llh,
816 char *s1, char *s2, char *s3, char *s4)
818 return record_base(obd,llh,devname,0,LCFG_SETUP,s1,s2,s3,s4);
821 static int record_lov_setup(struct obd_device *obd, struct llog_handle *llh,
822 char *devname, struct lov_desc *desc)
824 struct lustre_cfg_bufs bufs;
825 struct lustre_cfg *lcfg;
828 lustre_cfg_bufs_reset(&bufs, devname);
829 lustre_cfg_bufs_set(&bufs, 1, desc, sizeof(*desc));
830 lcfg = lustre_cfg_new(LCFG_SETUP, &bufs);
833 rc = record_lcfg(obd, llh, lcfg);
835 lustre_cfg_free(lcfg);
839 static int record_lmv_setup(struct obd_device *obd, struct llog_handle *llh,
840 char *devname, struct lmv_desc *desc)
842 struct lustre_cfg_bufs bufs;
843 struct lustre_cfg *lcfg;
846 lustre_cfg_bufs_reset(&bufs, devname);
847 lustre_cfg_bufs_set(&bufs, 1, desc, sizeof(*desc));
848 lcfg = lustre_cfg_new(LCFG_SETUP, &bufs);
850 rc = record_lcfg(obd, llh, lcfg);
852 lustre_cfg_free(lcfg);
856 static inline int record_mdc_add(struct obd_device *obd,
857 struct llog_handle *llh,
858 char *logname, char *mdcuuid,
859 char *mdtuuid, char *index,
862 return record_base(obd,llh,logname,0,LCFG_ADD_MDC,
863 mdtuuid,index,gen,mdcuuid);
866 static inline int record_lov_add(struct obd_device *obd,
867 struct llog_handle *llh,
868 char *lov_name, char *ost_uuid,
869 char *index, char *gen)
871 return record_base(obd,llh,lov_name,0,LCFG_LOV_ADD_OBD,
872 ost_uuid,index,gen,0);
875 static inline int record_mount_opt(struct obd_device *obd,
876 struct llog_handle *llh,
877 char *profile, char *lov_name,
880 return record_base(obd,llh,NULL,0,LCFG_MOUNTOPT,
881 profile,lov_name,mdc_name,0);
884 static int record_marker(struct obd_device *obd, struct llog_handle *llh,
885 struct fs_db *fsdb, __u32 flags,
886 char *tgtname, char *comment)
888 struct cfg_marker marker;
889 struct lustre_cfg_bufs bufs;
890 struct lustre_cfg *lcfg;
893 if (flags & CM_START)
895 marker.cm_step = fsdb->fsdb_gen;
896 marker.cm_flags = flags;
897 marker.cm_vers = LUSTRE_VERSION_CODE;
898 strncpy(marker.cm_tgtname, tgtname, sizeof(marker.cm_tgtname));
899 strncpy(marker.cm_comment, comment, sizeof(marker.cm_comment));
900 marker.cm_createtime = cfs_time_current_sec();
901 marker.cm_canceltime = 0;
902 lustre_cfg_bufs_reset(&bufs, NULL);
903 lustre_cfg_bufs_set(&bufs, 1, &marker, sizeof(marker));
904 lcfg = lustre_cfg_new(LCFG_MARKER, &bufs);
907 rc = record_lcfg(obd, llh, lcfg);
909 lustre_cfg_free(lcfg);
913 static int record_start_log(struct obd_device *obd,
914 struct llog_handle **llh, char *name)
916 static struct obd_uuid cfg_uuid = { .uuid = "config_uuid" };
917 struct lvfs_run_ctxt saved;
918 struct llog_ctxt *ctxt;
922 GOTO(out, rc = -EBUSY);
924 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
926 GOTO(out, rc = -ENODEV);
928 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
929 rc = llog_create(ctxt, llh, NULL, name);
931 llog_init_handle(*llh, LLOG_F_IS_PLAIN, &cfg_uuid);
935 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
940 CERROR("Can't start log %s: %d\n", name, rc);
945 static int record_end_log(struct obd_device *obd, struct llog_handle **llh)
947 struct lvfs_run_ctxt saved;
950 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
952 rc = llog_close(*llh);
955 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
959 static int mgs_log_is_empty(struct obd_device *obd, char *name)
961 struct lvfs_run_ctxt saved;
962 struct llog_handle *llh;
963 struct llog_ctxt *ctxt;
966 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
967 LASSERT(ctxt != NULL);
968 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
969 rc = llog_create(ctxt, &llh, NULL, name);
971 llog_init_handle(llh, LLOG_F_IS_PLAIN, NULL);
972 rc = llog_get_size(llh);
975 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
977 /* header is record 1 */
981 /******************** config "macros" *********************/
983 /* write an lcfg directly into a log (with markers) */
984 static int mgs_write_log_direct(struct obd_device *obd, struct fs_db *fsdb,
985 char *logname, struct lustre_cfg *lcfg,
986 char *devname, char *comment)
988 struct llog_handle *llh = NULL;
995 rc = record_start_log(obd, &llh, logname);
999 /* FIXME These should be a single journal transaction */
1000 rc = record_marker(obd, llh, fsdb, CM_START, devname, comment);
1002 rc = record_lcfg(obd, llh, lcfg);
1004 rc = record_marker(obd, llh, fsdb, CM_END, devname, comment);
1005 rc = record_end_log(obd, &llh);
1010 /* write the lcfg in all logs for the given fs */
1011 int mgs_write_log_direct_all(struct obd_device *obd, struct fs_db *fsdb,
1012 struct mgs_target_info *mti,
1013 struct lustre_cfg *lcfg,
1014 char *devname, char *comment)
1016 struct mgs_obd *mgs = &obd->u.mgs;
1017 cfs_list_t dentry_list;
1018 struct l_linux_dirent *dirent, *n;
1019 char *fsname = mti->mti_fsname;
1021 int rc = 0, len = strlen(fsname);
1024 /* We need to set params for any future logs
1025 as well. FIXME Append this file to every new log.
1026 Actually, we should store as params (text), not llogs. Or
1028 name_create(&logname, fsname, "-params");
1029 if (mgs_log_is_empty(obd, logname)) {
1030 struct llog_handle *llh = NULL;
1031 rc = record_start_log(obd, &llh, logname);
1032 record_end_log(obd, &llh);
1034 name_destroy(&logname);
1038 /* Find all the logs in the CONFIGS directory */
1039 rc = class_dentry_readdir(obd, mgs->mgs_configs_dir,
1040 mgs->mgs_vfsmnt, &dentry_list);
1042 CERROR("Can't read %s dir\n", MOUNT_CONFIGS_DIR);
1046 /* Could use fsdb index maps instead of directory listing */
1047 cfs_list_for_each_entry_safe(dirent, n, &dentry_list, lld_list) {
1048 cfs_list_del(&dirent->lld_list);
1049 /* don't write to sptlrpc rule log */
1050 if (strncmp(fsname, dirent->lld_name, len) == 0 &&
1051 strstr(dirent->lld_name, "-sptlrpc") == NULL) {
1052 CDEBUG(D_MGS, "Changing log %s\n", dirent->lld_name);
1053 /* Erase any old settings of this same parameter */
1054 mgs_modify(obd, fsdb, mti, dirent->lld_name, devname,
1056 /* Write the new one */
1058 rc = mgs_write_log_direct(obd, fsdb,
1063 CERROR("err %d writing log %s\n", rc,
1067 OBD_FREE(dirent, sizeof(*dirent));
1075 struct mgs_target_info *comp_tmti;
1076 struct mgs_target_info *comp_mti;
1077 struct fs_db *comp_fsdb;
1078 struct obd_device *comp_obd;
1081 static int mgs_write_log_mdc_to_mdt(struct obd_device *, struct fs_db *,
1082 struct mgs_target_info *, char *);
1083 static int mgs_write_log_osc_to_lov(struct obd_device *obd, struct fs_db *fsdb,
1084 struct mgs_target_info *mti,
1085 char *logname, char *suffix, char *lovname,
1086 enum lustre_sec_part sec_part, int flags);
1087 static void name_create_mdt_and_lov(char **logname, char **lovname,
1088 struct fs_db *fsdb, int i);
1090 static int mgs_steal_llog_handler(struct llog_handle *llh,
1091 struct llog_rec_hdr *rec,
1094 struct obd_device * obd;
1095 struct mgs_target_info *mti, *tmti;
1097 int cfg_len = rec->lrh_len;
1098 char *cfg_buf = (char*) (rec + 1);
1099 struct lustre_cfg *lcfg;
1101 struct llog_handle *mdt_llh = NULL;
1102 static int got_an_osc_or_mdc = 0;
1103 /* 0: not found any osc/mdc;
1107 static int last_step = -1;
1111 mti = ((struct temp_comp*)data)->comp_mti;
1112 tmti = ((struct temp_comp*)data)->comp_tmti;
1113 fsdb = ((struct temp_comp*)data)->comp_fsdb;
1114 obd = ((struct temp_comp*)data)->comp_obd;
1116 if (rec->lrh_type != OBD_CFG_REC) {
1117 CERROR("unhandled lrh_type: %#x\n", rec->lrh_type);
1121 rc = lustre_cfg_sanity_check(cfg_buf, cfg_len);
1123 CERROR("Insane cfg\n");
1127 lcfg = (struct lustre_cfg *)cfg_buf;
1129 if (lcfg->lcfg_command == LCFG_MARKER) {
1130 struct cfg_marker *marker;
1131 marker = lustre_cfg_buf(lcfg, 1);
1132 if (!strncmp(marker->cm_comment,"add osc",7) &&
1133 (marker->cm_flags & CM_START)){
1134 got_an_osc_or_mdc = 1;
1135 strncpy(tmti->mti_svname, marker->cm_tgtname,
1136 sizeof(tmti->mti_svname));
1137 rc = record_start_log(obd, &mdt_llh, mti->mti_svname);
1138 rc = record_marker(obd, mdt_llh, fsdb, CM_START,
1139 mti->mti_svname,"add osc(copied)");
1140 rc = record_end_log(obd, &mdt_llh);
1141 last_step = marker->cm_step;
1144 if (!strncmp(marker->cm_comment,"add osc",7) &&
1145 (marker->cm_flags & CM_END)){
1146 LASSERT(last_step == marker->cm_step);
1148 got_an_osc_or_mdc = 0;
1149 rc = record_start_log(obd, &mdt_llh, mti->mti_svname);
1150 rc = record_marker(obd, mdt_llh, fsdb, CM_END,
1151 mti->mti_svname,"add osc(copied)");
1152 rc = record_end_log(obd, &mdt_llh);
1155 if (!strncmp(marker->cm_comment,"add mdc",7) &&
1156 (marker->cm_flags & CM_START)){
1157 got_an_osc_or_mdc = 2;
1158 last_step = marker->cm_step;
1159 memcpy(tmti->mti_svname, marker->cm_tgtname,
1160 strlen(marker->cm_tgtname));
1164 if (!strncmp(marker->cm_comment,"add mdc",7) &&
1165 (marker->cm_flags & CM_END)){
1166 LASSERT(last_step == marker->cm_step);
1168 got_an_osc_or_mdc = 0;
1173 if (got_an_osc_or_mdc == 0 || last_step < 0)
1176 if (lcfg->lcfg_command == LCFG_ADD_UUID) {
1178 nodenid = lcfg->lcfg_nid;
1180 tmti->mti_nids[tmti->mti_nid_count] = nodenid;
1181 tmti->mti_nid_count++;
1186 if (lcfg->lcfg_command == LCFG_SETUP) {
1189 target = lustre_cfg_string(lcfg, 1);
1190 memcpy(tmti->mti_uuid, target, strlen(target));
1194 /* ignore client side sptlrpc_conf_log */
1195 if (lcfg->lcfg_command == LCFG_SPTLRPC_CONF)
1198 if (lcfg->lcfg_command == LCFG_ADD_MDC) {
1201 if (sscanf(lustre_cfg_buf(lcfg, 2), "%d", &index) != 1)
1204 memcpy(tmti->mti_fsname, mti->mti_fsname,
1205 strlen(mti->mti_fsname));
1206 tmti->mti_stripe_index = index;
1208 mgs_write_log_mdc_to_mdt(obd, fsdb, tmti, mti->mti_svname);
1209 memset(tmti, 0, sizeof(*tmti));
1213 if (lcfg->lcfg_command == LCFG_LOV_ADD_OBD) {
1216 char *logname, *lovname;
1218 name_create_mdt_and_lov(&logname, &lovname, fsdb,
1219 mti->mti_stripe_index);
1220 sprintf(mdt_index, "-MDT%04x", mti->mti_stripe_index);
1222 if (sscanf(lustre_cfg_buf(lcfg, 2), "%d", &index) != 1) {
1223 name_destroy(&logname);
1224 name_destroy(&lovname);
1228 tmti->mti_stripe_index = index;
1229 mgs_write_log_osc_to_lov(obd, fsdb, tmti, logname,
1232 name_destroy(&logname);
1233 name_destroy(&lovname);
1239 /* fsdb->fsdb_sem is already held in mgs_write_log_target*/
1240 /* stealed from mgs_get_fsdb_from_llog*/
1241 static int mgs_steal_llog_for_mdt_from_client(struct obd_device *obd,
1243 struct temp_comp* comp)
1245 struct llog_handle *loghandle;
1246 struct lvfs_run_ctxt saved;
1247 struct mgs_target_info *tmti;
1248 struct llog_ctxt *ctxt;
1252 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
1253 LASSERT(ctxt != NULL);
1255 OBD_ALLOC_PTR(tmti);
1259 comp->comp_tmti = tmti;
1260 comp->comp_obd = obd;
1262 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
1264 rc = llog_create(ctxt, &loghandle, NULL, client_name);
1268 rc = llog_init_handle(loghandle, LLOG_F_IS_PLAIN, NULL);
1270 GOTO(out_close, rc);
1272 rc = llog_process(loghandle, mgs_steal_llog_handler, (void *)comp, NULL);
1273 CDEBUG(D_MGS, "steal llog re = %d\n", rc);
1275 rc2 = llog_close(loghandle);
1279 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
1281 llog_ctxt_put(ctxt);
1285 /* lmv is the second thing for client logs */
1286 /* copied from mgs_write_log_lov. Please refer to that. */
1287 static int mgs_write_log_lmv(struct obd_device *obd, struct fs_db *fsdb,
1288 struct mgs_target_info *mti,
1289 char *logname, char *lmvname)
1291 struct llog_handle *llh = NULL;
1292 struct lmv_desc *lmvdesc;
1297 CDEBUG(D_MGS, "Writing lmv(%s) log for %s\n", lmvname,logname);
1299 OBD_ALLOC_PTR(lmvdesc);
1300 if (lmvdesc == NULL)
1302 lmvdesc->ld_active_tgt_count = 0;
1303 lmvdesc->ld_tgt_count = 0;
1304 sprintf((char*)lmvdesc->ld_uuid.uuid, "%s_UUID", lmvname);
1305 uuid = (char *)lmvdesc->ld_uuid.uuid;
1307 rc = record_start_log(obd, &llh, logname);
1308 rc = record_marker(obd, llh, fsdb, CM_START, lmvname, "lmv setup");
1309 rc = record_attach(obd, llh, lmvname, "lmv", uuid);
1310 rc = record_lmv_setup(obd, llh, lmvname, lmvdesc);
1311 rc = record_marker(obd, llh, fsdb, CM_END, lmvname, "lmv setup");
1312 rc = record_end_log(obd, &llh);
1314 OBD_FREE_PTR(lmvdesc);
1318 /* lov is the first thing in the mdt and client logs */
1319 static int mgs_write_log_lov(struct obd_device *obd, struct fs_db *fsdb,
1320 struct mgs_target_info *mti,
1321 char *logname, char *lovname)
1323 struct llog_handle *llh = NULL;
1324 struct lov_desc *lovdesc;
1329 CDEBUG(D_MGS, "Writing lov(%s) log for %s\n", lovname, logname);
1332 #01 L attach 0:lov_mdsA 1:lov 2:71ccb_lov_mdsA_19f961a9e1
1333 #02 L lov_setup 0:lov_mdsA 1:(struct lov_desc)
1334 uuid=lov1_UUID, stripe count=1, size=1048576, offset=0, pattern=0
1337 /* FIXME just make lov_setup accept empty desc (put uuid in buf 2) */
1338 OBD_ALLOC_PTR(lovdesc);
1339 if (lovdesc == NULL)
1341 lovdesc->ld_magic = LOV_DESC_MAGIC;
1342 lovdesc->ld_tgt_count = 0;
1343 /* Defaults. Can be changed later by lcfg config_param */
1344 lovdesc->ld_default_stripe_count = 1;
1345 lovdesc->ld_pattern = LOV_PATTERN_RAID0;
1346 lovdesc->ld_default_stripe_size = 1024 * 1024;
1347 lovdesc->ld_default_stripe_offset = -1;
1348 lovdesc->ld_qos_maxage = QOS_DEFAULT_MAXAGE;
1349 sprintf((char*)lovdesc->ld_uuid.uuid, "%s_UUID", lovname);
1350 /* can these be the same? */
1351 uuid = (char *)lovdesc->ld_uuid.uuid;
1353 /* This should always be the first entry in a log.
1354 rc = mgs_clear_log(obd, logname); */
1355 rc = record_start_log(obd, &llh, logname);
1358 /* FIXME these should be a single journal transaction */
1359 rc = record_marker(obd, llh, fsdb, CM_START, lovname, "lov setup");
1360 rc = record_attach(obd, llh, lovname, "lov", uuid);
1361 rc = record_lov_setup(obd, llh, lovname, lovdesc);
1362 rc = record_marker(obd, llh, fsdb, CM_END, lovname, "lov setup");
1363 rc = record_end_log(obd, &llh);
1367 OBD_FREE_PTR(lovdesc);
1371 /* add failnids to open log */
1372 static int mgs_write_log_failnids(struct obd_device *obd,
1373 struct mgs_target_info *mti,
1374 struct llog_handle *llh,
1377 char *failnodeuuid = NULL;
1378 char *ptr = mti->mti_params;
1383 #03 L add_uuid nid=uml1@tcp(0x20000c0a80201) nal=90 0: 1:uml1_UUID
1384 #04 L add_uuid nid=1@elan(0x1000000000001) nal=90 0: 1:uml1_UUID
1385 #05 L setup 0:OSC_uml1_ost1_mdsA 1:ost1_UUID 2:uml1_UUID
1386 #06 L add_uuid nid=uml2@tcp(0x20000c0a80202) nal=90 0: 1:uml2_UUID
1387 #0x L add_uuid nid=2@elan(0x1000000000002) nal=90 0: 1:uml2_UUID
1388 #07 L add_conn 0:OSC_uml1_ost1_mdsA 1:uml2_UUID
1391 /* Pull failnid info out of params string */
1392 while (class_find_param(ptr, PARAM_FAILNODE, &ptr) == 0) {
1393 while (class_parse_nid(ptr, &nid, &ptr) == 0) {
1394 if (failnodeuuid == NULL) {
1395 /* We don't know the failover node name,
1396 so just use the first nid as the uuid */
1397 rc = name_create(&failnodeuuid,
1398 libcfs_nid2str(nid), "");
1402 CDEBUG(D_MGS, "add nid %s for failover uuid %s, "
1403 "client %s\n", libcfs_nid2str(nid),
1404 failnodeuuid, cliname);
1405 rc = record_add_uuid(obd, llh, nid, failnodeuuid);
1408 rc = record_add_conn(obd, llh, cliname, failnodeuuid);
1409 name_destroy(&failnodeuuid);
1410 failnodeuuid = NULL;
1417 static int mgs_write_log_mdc_to_lmv(struct obd_device *obd, struct fs_db *fsdb,
1418 struct mgs_target_info *mti,
1419 char *logname, char *lmvname)
1421 struct llog_handle *llh = NULL;
1422 char *mdcname, *nodeuuid, *mdcuuid, *lmvuuid;
1427 if (mgs_log_is_empty(obd, logname)) {
1428 CERROR("log is empty! Logical error\n");
1432 CDEBUG(D_MGS, "adding mdc for %s to log %s:lmv(%s)\n",
1433 mti->mti_svname, logname, lmvname);
1435 name_create(&nodeuuid, libcfs_nid2str(mti->mti_nids[0]), "");
1436 name_create(&mdcname, mti->mti_svname, "-mdc");
1437 name_create(&mdcuuid, mdcname, "_UUID");
1438 name_create(&lmvuuid, lmvname, "_UUID");
1440 rc = record_start_log(obd, &llh, logname);
1441 rc = record_marker(obd, llh, fsdb, CM_START, mti->mti_svname,
1444 for (i = 0; i < mti->mti_nid_count; i++) {
1445 CDEBUG(D_MGS, "add nid %s for mdt\n",
1446 libcfs_nid2str(mti->mti_nids[i]));
1448 rc = record_add_uuid(obd, llh, mti->mti_nids[i], nodeuuid);
1451 rc = record_attach(obd, llh, mdcname, LUSTRE_MDC_NAME, lmvuuid);
1452 rc = record_setup(obd, llh, mdcname, mti->mti_uuid, nodeuuid, 0, 0);
1453 rc = mgs_write_log_failnids(obd, mti, llh, mdcname);
1454 snprintf(index, sizeof(index), "%d", mti->mti_stripe_index);
1455 rc = record_mdc_add(obd, llh, lmvname, mdcuuid, mti->mti_uuid,
1457 rc = record_marker(obd, llh, fsdb, CM_END, mti->mti_svname,
1459 rc = record_end_log(obd, &llh);
1461 name_destroy(&lmvuuid);
1462 name_destroy(&mdcuuid);
1463 name_destroy(&mdcname);
1464 name_destroy(&nodeuuid);
1468 /* add new mdc to already existent MDS */
1469 static int mgs_write_log_mdc_to_mdt(struct obd_device *obd, struct fs_db *fsdb,
1470 struct mgs_target_info *mti, char *logname)
1472 struct llog_handle *llh = NULL;
1473 char *nodeuuid, *mdcname, *mdcuuid, *mdtuuid;
1474 int idx = mti->mti_stripe_index;
1479 if (mgs_log_is_empty(obd, logname)) {
1480 CERROR("log is empty! Logical error\n");
1484 CDEBUG(D_MGS, "adding mdc index %d to %s\n", idx, logname);
1486 name_create(&nodeuuid, libcfs_nid2str(mti->mti_nids[0]), "");
1487 snprintf(index, sizeof(index), "-mdc%04x", idx);
1488 name_create(&mdcname, logname, index);
1489 name_create(&mdcuuid, mdcname, "_UUID");
1490 name_create(&mdtuuid, logname, "_UUID");
1492 rc = record_start_log(obd, &llh, logname);
1493 rc = record_marker(obd, llh, fsdb, CM_START, mti->mti_svname, "add mdc");
1494 for (i = 0; i < mti->mti_nid_count; i++) {
1495 CDEBUG(D_MGS, "add nid %s for mdt\n",
1496 libcfs_nid2str(mti->mti_nids[i]));
1497 rc = record_add_uuid(obd, llh, mti->mti_nids[i], nodeuuid);
1499 rc = record_attach(obd, llh, mdcname, LUSTRE_MDC_NAME, mdcuuid);
1500 rc = record_setup(obd, llh, mdcname, mti->mti_uuid, nodeuuid, 0, 0);
1501 rc = mgs_write_log_failnids(obd, mti, llh, mdcname);
1502 snprintf(index, sizeof(index), "%d", idx);
1504 rc = record_mdc_add(obd, llh, logname, mdcuuid, mti->mti_uuid,
1506 rc = record_marker(obd, llh, fsdb, CM_END, mti->mti_svname, "add mdc");
1507 rc = record_end_log(obd, &llh);
1509 name_destroy(&mdcuuid);
1510 name_destroy(&mdcname);
1511 name_destroy(&nodeuuid);
1512 name_destroy(&mdtuuid);
1516 static int mgs_write_log_mdt0(struct obd_device *obd, struct fs_db *fsdb,
1517 struct mgs_target_info *mti)
1519 char *log = mti->mti_svname;
1520 struct llog_handle *llh = NULL;
1521 char *uuid, *lovname;
1523 char *ptr = mti->mti_params;
1524 int rc = 0, failout = 0;
1527 OBD_ALLOC(uuid, sizeof(struct obd_uuid));
1531 if (class_find_param(ptr, PARAM_FAILMODE, &ptr) == 0)
1532 failout = (strncmp(ptr, "failout", 7) == 0);
1534 name_create(&lovname, log, "-mdtlov");
1535 if (mgs_log_is_empty(obd, log))
1536 rc = mgs_write_log_lov(obd, fsdb, mti, log, lovname);
1538 sprintf(uuid, "%s_UUID", log);
1539 sprintf(mdt_index, "%d", mti->mti_stripe_index);
1541 /* add MDT itself */
1542 rc = record_start_log(obd, &llh, log);
1546 /* FIXME this whole fn should be a single journal transaction */
1547 rc = record_marker(obd, llh, fsdb, CM_START, log, "add mdt");
1548 rc = record_attach(obd, llh, log, LUSTRE_MDT_NAME, uuid);
1549 rc = record_mount_opt(obd, llh, log, lovname, NULL);
1550 rc = record_setup(obd, llh, log, uuid, mdt_index, lovname,
1551 failout ? "n" : "f");
1552 rc = record_marker(obd, llh, fsdb, CM_END, log, "add mdt");
1553 rc = record_end_log(obd, &llh);
1555 name_destroy(&lovname);
1556 OBD_FREE(uuid, sizeof(struct obd_uuid));
1560 static inline void name_create_mdt(char **logname, char *fsname, int i)
1564 sprintf(mdt_index, "-MDT%04x", i);
1565 name_create(logname, fsname, mdt_index);
1568 static void name_create_mdt_and_lov(char **logname, char **lovname,
1569 struct fs_db *fsdb, int i)
1571 name_create_mdt(logname, fsdb->fsdb_name, i);
1573 if (i == 0 && cfs_test_bit(FSDB_OSCNAME18, &fsdb->fsdb_flags))
1574 name_create(lovname, fsdb->fsdb_name, "-mdtlov");
1576 name_create(lovname, *logname, "-mdtlov");
1579 static inline void name_create_mdt_osc(char **oscname, char *ostname,
1580 struct fs_db *fsdb, int i)
1584 if (i == 0 && cfs_test_bit(FSDB_OSCNAME18, &fsdb->fsdb_flags))
1585 sprintf(suffix, "-osc");
1587 sprintf(suffix, "-osc-MDT%04x", i);
1588 name_create(oscname, ostname, suffix);
1591 /* envelope method for all layers log */
1592 static int mgs_write_log_mdt(struct obd_device *obd, struct fs_db *fsdb,
1593 struct mgs_target_info *mti)
1595 struct llog_handle *llh = NULL;
1597 struct temp_comp comp = { 0 };
1601 CDEBUG(D_MGS, "writing new mdt %s\n", mti->mti_svname);
1605 if (mti->mti_flags & LDD_F_UPGRADE14) {
1606 /* We're starting with an old uuid. Assume old name for lov
1607 as well since the lov entry already exists in the log. */
1608 CDEBUG(D_MGS, "old mds uuid %s\n", mti->mti_uuid);
1609 if (strncmp(mti->mti_uuid, fsdb->fsdb_mdtlov + 4,
1610 strlen(fsdb->fsdb_mdtlov) - 4) != 0) {
1611 CERROR("old mds uuid %s doesn't match log %s (%s)\n",
1612 mti->mti_uuid, fsdb->fsdb_mdtlov,
1613 fsdb->fsdb_mdtlov + 4);
1617 /* end COMPAT_146 */
1619 if (mti->mti_uuid[0] == '\0') {
1620 /* Make up our own uuid */
1621 snprintf(mti->mti_uuid, sizeof(mti->mti_uuid),
1622 "%s_UUID", mti->mti_svname);
1626 rc = mgs_write_log_mdt0(obd, fsdb, mti);
1628 /* Append the mdt info to the client log */
1629 name_create(&cliname, mti->mti_fsname, "-client");
1631 if (mgs_log_is_empty(obd, cliname)) {
1632 /* Start client log */
1633 rc = mgs_write_log_lov(obd, fsdb, mti, cliname,
1635 rc = mgs_write_log_lmv(obd, fsdb, mti, cliname,
1640 #09 L add_uuid nid=uml1@tcp(0x20000c0a80201) 0: 1:uml1_UUID
1641 #10 L attach 0:MDC_uml1_mdsA_MNT_client 1:mdc 2:1d834_MNT_client_03f
1642 #11 L setup 0:MDC_uml1_mdsA_MNT_client 1:mdsA_UUID 2:uml1_UUID
1643 #12 L add_uuid nid=uml2@tcp(0x20000c0a80202) 0: 1:uml2_UUID
1644 #13 L add_conn 0:MDC_uml1_mdsA_MNT_client 1:uml2_UUID
1645 #14 L mount_option 0: 1:client 2:lov1 3:MDC_uml1_mdsA_MNT_client
1650 if (mti->mti_flags & LDD_F_UPGRADE14) {
1651 rc = record_start_log(obd, &llh, cliname);
1655 rc = record_marker(obd, llh, fsdb, CM_START,
1656 mti->mti_svname,"add mdc");
1658 /* Old client log already has MDC entry, but needs mount opt
1659 for new client name (lustre-client) */
1660 /* FIXME Old MDT log already has an old mount opt
1661 which we should remove (currently handled by
1662 class_del_profiles()) */
1663 rc = record_mount_opt(obd, llh, cliname, fsdb->fsdb_clilov,
1665 /* end COMPAT_146 */
1667 rc = record_marker(obd, llh, fsdb, CM_END,
1668 mti->mti_svname, "add mdc");
1672 /* copy client info about lov/lmv */
1673 comp.comp_mti = mti;
1674 comp.comp_fsdb = fsdb;
1676 rc = mgs_steal_llog_for_mdt_from_client(obd, cliname,
1679 rc = mgs_write_log_mdc_to_lmv(obd, fsdb, mti, cliname,
1682 rc = record_start_log(obd, &llh, cliname);
1686 rc = record_marker(obd, llh, fsdb, CM_START, cliname,
1688 rc = record_mount_opt(obd, llh, cliname, fsdb->fsdb_clilov,
1690 rc = record_marker(obd, llh, fsdb, CM_END, cliname,
1694 rc = record_end_log(obd, &llh);
1696 name_destroy(&cliname);
1698 // for_all_existing_mdt except current one
1699 for (i = 0; i < INDEX_MAP_SIZE * 8; i++){
1701 if (i != mti->mti_stripe_index &&
1702 cfs_test_bit(i, fsdb->fsdb_mdt_index_map)) {
1703 name_create_mdt(&mdtname, mti->mti_fsname, i);
1704 rc = mgs_write_log_mdc_to_mdt(obd, fsdb, mti, mdtname);
1705 name_destroy(&mdtname);
1712 /* Add the ost info to the client/mdt lov */
1713 static int mgs_write_log_osc_to_lov(struct obd_device *obd, struct fs_db *fsdb,
1714 struct mgs_target_info *mti,
1715 char *logname, char *suffix, char *lovname,
1716 enum lustre_sec_part sec_part, int flags)
1718 struct llog_handle *llh = NULL;
1719 char *nodeuuid, *oscname, *oscuuid, *lovuuid, *svname;
1724 CDEBUG(D_INFO, "adding osc for %s to log %s\n",
1725 mti->mti_svname, logname);
1727 if (mgs_log_is_empty(obd, logname)) {
1728 CERROR("log is empty! Logical error\n");
1732 name_create(&nodeuuid, libcfs_nid2str(mti->mti_nids[0]), "");
1733 name_create(&svname, mti->mti_svname, "-osc");
1734 name_create(&oscname, svname, suffix);
1735 name_create(&oscuuid, oscname, "_UUID");
1736 name_create(&lovuuid, lovname, "_UUID");
1739 #03 L add_uuid nid=uml1@tcp(0x20000c0a80201) 0: 1:uml1_UUID
1741 #04 L add_uuid nid=1@elan(0x1000000000001) nal=90 0: 1:uml1_UUID
1742 #04 L attach 0:OSC_uml1_ost1_MNT_client 1:osc 2:89070_lov1_a41dff51a
1743 #05 L setup 0:OSC_uml1_ost1_MNT_client 1:ost1_UUID 2:uml1_UUID
1745 #06 L add_uuid nid=uml2@tcp(0x20000c0a80202) 0: 1:uml2_UUID
1746 #07 L add_conn 0:OSC_uml1_ost1_MNT_client 1:uml2_UUID
1747 #08 L lov_modify_tgts add 0:lov1 1:ost1_UUID 2(index):0 3(gen):1
1750 rc = record_start_log(obd, &llh, logname);
1753 /* FIXME these should be a single journal transaction */
1754 rc = record_marker(obd, llh, fsdb, CM_START | flags, mti->mti_svname,
1756 for (i = 0; i < mti->mti_nid_count; i++) {
1757 CDEBUG(D_MGS, "add nid %s\n", libcfs_nid2str(mti->mti_nids[i]));
1758 rc = record_add_uuid(obd, llh, mti->mti_nids[i], nodeuuid);
1760 rc = record_attach(obd, llh, oscname, LUSTRE_OSC_NAME, lovuuid);
1761 rc = record_setup(obd, llh, oscname, mti->mti_uuid, nodeuuid, 0, 0);
1762 rc = mgs_write_log_failnids(obd, mti, llh, oscname);
1763 snprintf(index, sizeof(index), "%d", mti->mti_stripe_index);
1764 rc = record_lov_add(obd, llh, lovname, mti->mti_uuid, index, "1");
1765 rc = record_marker(obd, llh, fsdb, CM_END | flags, mti->mti_svname,
1767 rc = record_end_log(obd, &llh);
1769 name_destroy(&lovuuid);
1770 name_destroy(&oscuuid);
1771 name_destroy(&oscname);
1772 name_destroy(&svname);
1773 name_destroy(&nodeuuid);
1777 static int mgs_write_log_ost(struct obd_device *obd, struct fs_db *fsdb,
1778 struct mgs_target_info *mti)
1780 struct llog_handle *llh = NULL;
1781 char *logname, *lovname;
1782 char *ptr = mti->mti_params;
1783 int rc, flags = 0, failout = 0, i;
1786 CDEBUG(D_MGS, "writing new ost %s\n", mti->mti_svname);
1788 /* The ost startup log */
1790 /* If the ost log already exists, that means that someone reformatted
1791 the ost and it called target_add again. */
1792 if (!mgs_log_is_empty(obd, mti->mti_svname)) {
1793 LCONSOLE_ERROR_MSG(0x141, "The config log for %s already "
1794 "exists, yet the server claims it never "
1795 "registered. It may have been reformatted, "
1796 "or the index changed. writeconf the MDT to "
1797 "regenerate all logs.\n", mti->mti_svname);
1802 attach obdfilter ost1 ost1_UUID
1803 setup /dev/loop2 ldiskfs f|n errors=remount-ro,user_xattr
1805 if (class_find_param(ptr, PARAM_FAILMODE, &ptr) == 0)
1806 failout = (strncmp(ptr, "failout", 7) == 0);
1807 rc = record_start_log(obd, &llh, mti->mti_svname);
1810 /* FIXME these should be a single journal transaction */
1811 rc = record_marker(obd, llh, fsdb, CM_START, mti->mti_svname,"add ost");
1812 if (*mti->mti_uuid == '\0')
1813 snprintf(mti->mti_uuid, sizeof(mti->mti_uuid),
1814 "%s_UUID", mti->mti_svname);
1815 rc = record_attach(obd, llh, mti->mti_svname,
1816 "obdfilter"/*LUSTRE_OST_NAME*/, mti->mti_uuid);
1817 rc = record_setup(obd, llh, mti->mti_svname,
1818 "dev"/*ignored*/, "type"/*ignored*/,
1819 failout ? "n" : "f", 0/*options*/);
1820 rc = record_marker(obd, llh, fsdb, CM_END, mti->mti_svname, "add ost");
1821 rc = record_end_log(obd, &llh);
1823 /* We also have to update the other logs where this osc is part of
1826 if (cfs_test_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags)) {
1827 /* If we're upgrading, the old mdt log already has our
1828 entry. Let's do a fake one for fun. */
1829 /* Note that we can't add any new failnids, since we don't
1830 know the old osc names. */
1831 flags = CM_SKIP | CM_UPGRADE146;
1833 } else if ((mti->mti_flags & LDD_F_UPDATE) != LDD_F_UPDATE) {
1834 /* If the update flag isn't set, don't update client/mdt
1837 LCONSOLE_WARN("Client log for %s was not updated; writeconf "
1838 "the MDT first to regenerate it.\n",
1842 /* Add ost to all MDT lov defs */
1843 for (i = 0; i < INDEX_MAP_SIZE * 8; i++){
1844 if (cfs_test_bit(i, fsdb->fsdb_mdt_index_map)) {
1847 name_create_mdt_and_lov(&logname, &lovname, fsdb, i);
1848 sprintf(mdt_index, "-MDT%04x", i);
1849 mgs_write_log_osc_to_lov(obd, fsdb, mti, logname,
1851 LUSTRE_SP_MDT, flags);
1852 name_destroy(&logname);
1853 name_destroy(&lovname);
1857 /* Append ost info to the client log */
1858 name_create(&logname, mti->mti_fsname, "-client");
1859 if (mgs_log_is_empty(obd, logname)) {
1860 /* Start client log */
1861 rc = mgs_write_log_lov(obd, fsdb, mti, logname,
1863 rc = mgs_write_log_lmv(obd, fsdb, mti, logname,
1866 mgs_write_log_osc_to_lov(obd, fsdb, mti, logname, "",
1867 fsdb->fsdb_clilov, LUSTRE_SP_CLI, flags);
1868 name_destroy(&logname);
1872 static __inline__ int mgs_param_empty(char *ptr)
1876 if ((tmp = strchr(ptr, '=')) && (*(++tmp) == '\0'))
1881 static int mgs_write_log_failnid_internal(struct obd_device *obd,
1883 struct mgs_target_info *mti,
1884 char *logname, char *cliname)
1887 struct llog_handle *llh = NULL;
1889 if (mgs_param_empty(mti->mti_params)) {
1890 /* Remove _all_ failnids */
1891 rc = mgs_modify(obd, fsdb, mti, logname,
1892 mti->mti_svname, "add failnid", CM_SKIP);
1896 /* Otherwise failover nids are additive */
1897 rc = record_start_log(obd, &llh, logname);
1899 /* FIXME this should be a single journal transaction */
1900 rc = record_marker(obd, llh, fsdb, CM_START,
1901 mti->mti_svname, "add failnid");
1902 rc = mgs_write_log_failnids(obd, mti, llh, cliname);
1903 rc = record_marker(obd, llh, fsdb, CM_END,
1904 mti->mti_svname, "add failnid");
1905 rc = record_end_log(obd, &llh);
1912 /* Add additional failnids to an existing log.
1913 The mdc/osc must have been added to logs first */
1914 /* tcp nids must be in dotted-quad ascii -
1915 we can't resolve hostnames from the kernel. */
1916 static int mgs_write_log_add_failnid(struct obd_device *obd, struct fs_db *fsdb,
1917 struct mgs_target_info *mti)
1919 char *logname, *cliname;
1923 /* FIXME we currently can't erase the failnids
1924 * given when a target first registers, since they aren't part of
1925 * an "add uuid" stanza */
1927 /* Verify that we know about this target */
1928 if (mgs_log_is_empty(obd, mti->mti_svname)) {
1929 LCONSOLE_ERROR_MSG(0x142, "The target %s has not registered "
1930 "yet. It must be started before failnids "
1931 "can be added.\n", mti->mti_svname);
1935 /* Create mdc/osc client name (e.g. lustre-OST0001-osc) */
1936 if (mti->mti_flags & LDD_F_SV_TYPE_MDT) {
1937 name_create(&cliname, mti->mti_svname, "-mdc");
1938 } else if (mti->mti_flags & LDD_F_SV_TYPE_OST) {
1939 name_create(&cliname, mti->mti_svname, "-osc");
1944 /* Add failover nids to the client log */
1945 name_create(&logname, mti->mti_fsname, "-client");
1946 rc = mgs_write_log_failnid_internal(obd, fsdb, mti, logname, cliname);
1947 name_destroy(&logname);
1948 name_destroy(&cliname);
1950 if (mti->mti_flags & LDD_F_SV_TYPE_OST) {
1951 /* Add OST failover nids to the MDT logs as well */
1954 for (i = 0; i < INDEX_MAP_SIZE * 8; i++) {
1955 if (!cfs_test_bit(i, fsdb->fsdb_mdt_index_map))
1957 name_create_mdt(&logname, mti->mti_fsname, i);
1958 name_create_mdt_osc(&cliname, mti->mti_svname, fsdb, i);
1959 rc = mgs_write_log_failnid_internal(obd, fsdb, mti,
1961 name_destroy(&cliname);
1962 name_destroy(&logname);
1969 static int mgs_wlp_lcfg(struct obd_device *obd, struct fs_db *fsdb,
1970 struct mgs_target_info *mti,
1971 char *logname, struct lustre_cfg_bufs *bufs,
1972 char *tgtname, char *ptr)
1974 char comment[MTI_NAME_MAXLEN];
1976 struct lustre_cfg *lcfg;
1979 /* Erase any old settings of this same parameter */
1980 memcpy(comment, ptr, MTI_NAME_MAXLEN);
1981 comment[MTI_NAME_MAXLEN - 1] = 0;
1982 /* But don't try to match the value. */
1983 if ((tmp = strchr(comment, '=')))
1985 /* FIXME we should skip settings that are the same as old values */
1986 rc = mgs_modify(obd, fsdb, mti, logname, tgtname, comment, CM_SKIP);
1987 del = mgs_param_empty(ptr);
1989 LCONSOLE_INFO("%sing parameter %s.%s in log %s\n", del ? "Disabl" : rc ?
1990 "Sett" : "Modify", tgtname, comment, logname);
1994 lustre_cfg_bufs_reset(bufs, tgtname);
1995 lustre_cfg_bufs_set_string(bufs, 1, ptr);
1996 lcfg = lustre_cfg_new(LCFG_PARAM, bufs);
1999 rc = mgs_write_log_direct(obd, fsdb, logname, lcfg, tgtname, comment);
2000 lustre_cfg_free(lcfg);
2004 /* write global variable settings into log */
2005 static int mgs_write_log_sys(struct obd_device *obd, struct fs_db *fsdb,
2006 struct mgs_target_info *mti, char *sys, char *ptr)
2008 struct lustre_cfg_bufs bufs;
2009 struct lustre_cfg *lcfg;
2015 if (class_match_param(ptr, PARAM_TIMEOUT, &tmp) == 0)
2016 cmd = LCFG_SET_TIMEOUT;
2017 else if (class_match_param(ptr, PARAM_LDLM_TIMEOUT, &tmp) == 0)
2018 cmd = LCFG_SET_LDLM_TIMEOUT;
2019 /* Check for known params here so we can return error to lctl */
2020 else if ((class_match_param(ptr, PARAM_AT_MIN, &tmp) == 0)
2021 || (class_match_param(ptr, PARAM_AT_MAX, &tmp) == 0)
2022 || (class_match_param(ptr, PARAM_AT_EXTRA, &tmp) == 0)
2023 || (class_match_param(ptr, PARAM_AT_EARLY_MARGIN, &tmp) == 0)
2024 || (class_match_param(ptr, PARAM_AT_HISTORY, &tmp) == 0))
2029 /* separate the value */
2030 val = simple_strtoul(tmp, NULL, 0);
2032 CDEBUG(D_MGS, "global '%s' removed\n", sys);
2034 CDEBUG(D_MGS, "global '%s' val=%d\n", sys, val);
2036 lustre_cfg_bufs_reset(&bufs, NULL);
2037 lustre_cfg_bufs_set_string(&bufs, 1, sys);
2038 lcfg = lustre_cfg_new(cmd, &bufs);
2039 lcfg->lcfg_num = val;
2040 /* truncate the comment to the parameter name */
2044 /* modify all servers and clients */
2045 rc = mgs_write_log_direct_all(obd, fsdb, mti,
2046 *tmp == '\0' ? NULL : lcfg,
2047 mti->mti_fsname, sys);
2049 lustre_cfg_free(lcfg);
2053 static int mgs_srpc_set_param_disk(struct obd_device *obd,
2055 struct mgs_target_info *mti,
2058 struct llog_handle *llh = NULL;
2060 char *comment, *ptr;
2061 struct lustre_cfg_bufs bufs;
2062 struct lustre_cfg *lcfg;
2067 ptr = strchr(param, '=');
2071 OBD_ALLOC(comment, len + 1);
2072 if (comment == NULL)
2074 strncpy(comment, param, len);
2075 comment[len] = '\0';
2078 lustre_cfg_bufs_reset(&bufs, mti->mti_svname);
2079 lustre_cfg_bufs_set_string(&bufs, 1, param);
2080 lcfg = lustre_cfg_new(LCFG_SPTLRPC_CONF, &bufs);
2082 GOTO(out_comment, rc = -ENOMEM);
2084 /* construct log name */
2085 rc = name_create(&logname, mti->mti_fsname, "-sptlrpc");
2089 if (mgs_log_is_empty(obd, logname)) {
2090 rc = record_start_log(obd, &llh, logname);
2091 record_end_log(obd, &llh);
2096 /* obsolete old one */
2097 mgs_modify(obd, fsdb, mti, logname, mti->mti_svname, comment, CM_SKIP);
2099 /* write the new one */
2100 rc = mgs_write_log_direct(obd, fsdb, logname, lcfg,
2101 mti->mti_svname, comment);
2103 CERROR("err %d writing log %s\n", rc, logname);
2106 name_destroy(&logname);
2108 lustre_cfg_free(lcfg);
2110 OBD_FREE(comment, len + 1);
2114 static int mgs_srpc_set_param_udesc_mem(struct fs_db *fsdb,
2119 /* disable the adjustable udesc parameter for now, i.e. use default
2120 * setting that client always ship udesc to MDT if possible. to enable
2121 * it simply remove the following line */
2124 ptr = strchr(param, '=');
2129 if (strcmp(param, PARAM_SRPC_UDESC))
2132 if (strcmp(ptr, "yes") == 0) {
2133 cfs_set_bit(FSDB_UDESC, &fsdb->fsdb_flags);
2134 CWARN("Enable user descriptor shipping from client to MDT\n");
2135 } else if (strcmp(ptr, "no") == 0) {
2136 cfs_clear_bit(FSDB_UDESC, &fsdb->fsdb_flags);
2137 CWARN("Disable user descriptor shipping from client to MDT\n");
2145 CERROR("Invalid param: %s\n", param);
2149 static int mgs_srpc_set_param_mem(struct fs_db *fsdb,
2153 struct sptlrpc_rule rule;
2154 struct sptlrpc_rule_set *rset;
2158 if (strncmp(param, PARAM_SRPC, sizeof(PARAM_SRPC) - 1) != 0) {
2159 CERROR("Invalid sptlrpc parameter: %s\n", param);
2163 if (strncmp(param, PARAM_SRPC_UDESC,
2164 sizeof(PARAM_SRPC_UDESC) - 1) == 0) {
2165 RETURN(mgs_srpc_set_param_udesc_mem(fsdb, param));
2168 if (strncmp(param, PARAM_SRPC_FLVR, sizeof(PARAM_SRPC_FLVR) - 1) != 0) {
2169 CERROR("Invalid sptlrpc flavor parameter: %s\n", param);
2173 param += sizeof(PARAM_SRPC_FLVR) - 1;
2175 rc = sptlrpc_parse_rule(param, &rule);
2179 /* mgs rules implies must be mgc->mgs */
2180 if (cfs_test_bit(FSDB_MGS_SELF, &fsdb->fsdb_flags)) {
2181 if ((rule.sr_from != LUSTRE_SP_MGC &&
2182 rule.sr_from != LUSTRE_SP_ANY) ||
2183 (rule.sr_to != LUSTRE_SP_MGS &&
2184 rule.sr_to != LUSTRE_SP_ANY))
2188 /* preapre room for this coming rule. svcname format should be:
2189 * - fsname: general rule
2190 * - fsname-tgtname: target-specific rule
2192 if (strchr(svname, '-')) {
2193 struct mgs_tgt_srpc_conf *tgtconf;
2196 for (tgtconf = fsdb->fsdb_srpc_tgt; tgtconf != NULL;
2197 tgtconf = tgtconf->mtsc_next) {
2198 if (!strcmp(tgtconf->mtsc_tgt, svname)) {
2207 OBD_ALLOC_PTR(tgtconf);
2208 if (tgtconf == NULL)
2211 name_len = strlen(svname);
2213 OBD_ALLOC(tgtconf->mtsc_tgt, name_len + 1);
2214 if (tgtconf->mtsc_tgt == NULL) {
2215 OBD_FREE_PTR(tgtconf);
2218 memcpy(tgtconf->mtsc_tgt, svname, name_len);
2220 tgtconf->mtsc_next = fsdb->fsdb_srpc_tgt;
2221 fsdb->fsdb_srpc_tgt = tgtconf;
2224 rset = &tgtconf->mtsc_rset;
2226 rset = &fsdb->fsdb_srpc_gen;
2229 rc = sptlrpc_rule_set_merge(rset, &rule);
2234 static int mgs_srpc_set_param(struct obd_device *obd,
2236 struct mgs_target_info *mti,
2246 /* keep a copy of original param, which could be destroied
2248 copy_size = strlen(param) + 1;
2249 OBD_ALLOC(copy, copy_size);
2252 memcpy(copy, param, copy_size);
2254 rc = mgs_srpc_set_param_mem(fsdb, mti->mti_svname, param);
2258 /* previous steps guaranteed the syntax is correct */
2259 rc = mgs_srpc_set_param_disk(obd, fsdb, mti, copy);
2263 if (cfs_test_bit(FSDB_MGS_SELF, &fsdb->fsdb_flags)) {
2265 * for mgs rules, make them effective immediately.
2267 LASSERT(fsdb->fsdb_srpc_tgt == NULL);
2268 sptlrpc_target_update_exp_flavor(obd, &fsdb->fsdb_srpc_gen);
2272 OBD_FREE(copy, copy_size);
2276 struct mgs_srpc_read_data {
2277 struct fs_db *msrd_fsdb;
2281 static int mgs_srpc_read_handler(struct llog_handle *llh,
2282 struct llog_rec_hdr *rec,
2285 struct mgs_srpc_read_data *msrd = (struct mgs_srpc_read_data *) data;
2286 struct cfg_marker *marker;
2287 struct lustre_cfg *lcfg = (struct lustre_cfg *)(rec + 1);
2288 char *svname, *param;
2292 if (rec->lrh_type != OBD_CFG_REC) {
2293 CERROR("unhandled lrh_type: %#x\n", rec->lrh_type);
2297 cfg_len = rec->lrh_len - sizeof(struct llog_rec_hdr) -
2298 sizeof(struct llog_rec_tail);
2300 rc = lustre_cfg_sanity_check(lcfg, cfg_len);
2302 CERROR("Insane cfg\n");
2306 if (lcfg->lcfg_command == LCFG_MARKER) {
2307 marker = lustre_cfg_buf(lcfg, 1);
2309 if (marker->cm_flags & CM_START &&
2310 marker->cm_flags & CM_SKIP)
2311 msrd->msrd_skip = 1;
2312 if (marker->cm_flags & CM_END)
2313 msrd->msrd_skip = 0;
2318 if (msrd->msrd_skip)
2321 if (lcfg->lcfg_command != LCFG_SPTLRPC_CONF) {
2322 CERROR("invalid command (%x)\n", lcfg->lcfg_command);
2326 svname = lustre_cfg_string(lcfg, 0);
2327 if (svname == NULL) {
2328 CERROR("svname is empty\n");
2332 param = lustre_cfg_string(lcfg, 1);
2333 if (param == NULL) {
2334 CERROR("param is empty\n");
2338 rc = mgs_srpc_set_param_mem(msrd->msrd_fsdb, svname, param);
2340 CERROR("read sptlrpc record error (%d): %s\n", rc, param);
2345 int mgs_get_fsdb_srpc_from_llog(struct obd_device *obd,
2348 struct llog_handle *llh = NULL;
2349 struct lvfs_run_ctxt saved;
2350 struct llog_ctxt *ctxt;
2352 struct mgs_srpc_read_data msrd;
2356 /* construct log name */
2357 rc = name_create(&logname, fsdb->fsdb_name, "-sptlrpc");
2361 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
2362 LASSERT(ctxt != NULL);
2364 if (mgs_log_is_empty(obd, logname))
2367 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
2369 rc = llog_create(ctxt, &llh, NULL, logname);
2373 rc = llog_init_handle(llh, LLOG_F_IS_PLAIN, NULL);
2375 GOTO(out_close, rc);
2377 if (llog_get_size(llh) <= 1)
2378 GOTO(out_close, rc = 0);
2380 msrd.msrd_fsdb = fsdb;
2383 rc = llog_process(llh, mgs_srpc_read_handler, (void *) &msrd, NULL);
2388 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
2390 llog_ctxt_put(ctxt);
2391 name_destroy(&logname);
2394 CERROR("failed to read sptlrpc config database: %d\n", rc);
2398 /* Permanent settings of all parameters by writing into the appropriate
2399 * configuration logs.
2400 * A parameter with null value ("<param>='\0'") means to erase it out of
2403 static int mgs_write_log_param(struct obd_device *obd, struct fs_db *fsdb,
2404 struct mgs_target_info *mti, char *ptr)
2406 struct lustre_cfg_bufs bufs;
2409 int rc = 0, rc2 = 0;
2412 /* For various parameter settings, we have to figure out which logs
2413 care about them (e.g. both mdt and client for lov settings) */
2414 CDEBUG(D_MGS, "next param '%s'\n", ptr);
2416 /* The params are stored in MOUNT_DATA_FILE and modified via
2417 tunefs.lustre, or set using lctl conf_param */
2419 /* Processed in lustre_start_mgc */
2420 if (class_match_param(ptr, PARAM_MGSNODE, NULL) == 0)
2423 /* Processed in ost/mdt */
2424 if (class_match_param(ptr, PARAM_NETWORK, NULL) == 0)
2427 /* Processed in mgs_write_log_ost */
2428 if (class_match_param(ptr, PARAM_FAILMODE, NULL) == 0) {
2429 if (mti->mti_flags & LDD_F_PARAM) {
2430 LCONSOLE_ERROR_MSG(0x169, "%s can only be "
2431 "changed with tunefs.lustre"
2432 "and --writeconf\n", ptr);
2438 if (class_match_param(ptr, PARAM_SRPC, NULL) == 0) {
2439 rc = mgs_srpc_set_param(obd, fsdb, mti, ptr);
2443 if (class_match_param(ptr, PARAM_FAILNODE, NULL) == 0) {
2444 /* Add a failover nidlist */
2446 /* We already processed failovers params for new
2447 targets in mgs_write_log_target */
2448 if (mti->mti_flags & LDD_F_PARAM) {
2449 CDEBUG(D_MGS, "Adding failnode\n");
2450 rc = mgs_write_log_add_failnid(obd, fsdb, mti);
2455 if (class_match_param(ptr, PARAM_SYS, &tmp) == 0) {
2456 rc = mgs_write_log_sys(obd, fsdb, mti, ptr, tmp);
2460 if (class_match_param(ptr, PARAM_OSC""PARAM_ACTIVE, &tmp) == 0) {
2461 /* active=0 means off, anything else means on */
2462 int flag = (*tmp == '0') ? CM_EXCLUDE : 0;
2465 if (!(mti->mti_flags & LDD_F_SV_TYPE_OST)) {
2466 LCONSOLE_ERROR_MSG(0x144, "%s: Only OSCs can "
2467 "be (de)activated.\n",
2469 GOTO(end, rc = -EINVAL);
2471 LCONSOLE_WARN("Permanently %sactivating %s\n",
2472 flag ? "de": "re", mti->mti_svname);
2474 name_create(&logname, mti->mti_fsname, "-client");
2475 rc = mgs_modify(obd, fsdb, mti, logname,
2476 mti->mti_svname, "add osc", flag);
2477 name_destroy(&logname);
2481 /* Add to all MDT logs for CMD */
2482 for (i = 0; i < INDEX_MAP_SIZE * 8; i++) {
2483 if (!cfs_test_bit(i, fsdb->fsdb_mdt_index_map))
2485 name_create_mdt(&logname, mti->mti_fsname, i);
2486 rc = mgs_modify(obd, fsdb, mti, logname,
2487 mti->mti_svname, "add osc", flag);
2488 name_destroy(&logname);
2494 LCONSOLE_ERROR_MSG(0x145, "Couldn't find %s in"
2495 "log (%d). No permanent "
2496 "changes were made to the "
2498 mti->mti_svname, rc);
2499 if (cfs_test_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags))
2500 LCONSOLE_ERROR_MSG(0x146, "This may be"
2505 "update the logs.\n");
2508 /* Fall through to osc proc for deactivating live OSC
2509 on running MDT / clients. */
2511 /* Below here, let obd's XXX_process_config methods handle it */
2513 /* All lov. in proc */
2514 if (class_match_param(ptr, PARAM_LOV, NULL) == 0) {
2517 CDEBUG(D_MGS, "lov param %s\n", ptr);
2518 if (!(mti->mti_flags & LDD_F_SV_TYPE_MDT)) {
2519 LCONSOLE_ERROR_MSG(0x147, "LOV params must be "
2520 "set on the MDT, not %s. "
2527 if (mgs_log_is_empty(obd, mti->mti_svname))
2528 GOTO(end, rc = -ENODEV);
2530 name_create_mdt_and_lov(&logname, &mdtlovname, fsdb,
2531 mti->mti_stripe_index);
2532 rc = mgs_wlp_lcfg(obd, fsdb, mti, mti->mti_svname,
2533 &bufs, mdtlovname, ptr);
2534 name_destroy(&logname);
2535 name_destroy(&mdtlovname);
2540 name_create(&logname, mti->mti_fsname, "-client");
2541 rc = mgs_wlp_lcfg(obd, fsdb, mti, logname, &bufs,
2542 fsdb->fsdb_clilov, ptr);
2543 name_destroy(&logname);
2547 /* All osc., mdc., llite. params in proc */
2548 if ((class_match_param(ptr, PARAM_OSC, NULL) == 0) ||
2549 (class_match_param(ptr, PARAM_MDC, NULL) == 0) ||
2550 (class_match_param(ptr, PARAM_LLITE, NULL) == 0)) {
2552 if (memcmp(ptr, PARAM_LLITE, strlen(PARAM_LLITE)) == 0) {
2553 name_create(&cname, mti->mti_fsname, "-client");
2554 /* Add the client type to match the obdname in
2555 class_config_llog_handler */
2556 } else if (mti->mti_flags & LDD_F_SV_TYPE_MDT) {
2559 name_create(&cname, fsdb->fsdb_mdc, "");
2561 name_create(&cname, mti->mti_svname,
2563 } else if (mti->mti_flags & LDD_F_SV_TYPE_OST) {
2565 if (cfs_test_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags)) {
2566 LCONSOLE_ERROR_MSG(0x148, "Upgraded "
2567 "client logs for %s"
2569 "modified. Consider"
2571 "configuration with"
2574 /* We don't know the names of all the
2576 GOTO(end, rc = -EINVAL);
2578 name_create(&cname, mti->mti_svname, "-osc");
2580 GOTO(end, rc = -EINVAL);
2583 CDEBUG(D_MGS, "%.3s param %s\n", ptr, ptr + 4);
2586 name_create(&logname, mti->mti_fsname, "-client");
2587 rc = mgs_wlp_lcfg(obd, fsdb, mti, logname, &bufs,
2590 /* osc params affect the MDT as well */
2591 if (!rc && (mti->mti_flags & LDD_F_SV_TYPE_OST)) {
2594 for (i = 0; i < INDEX_MAP_SIZE * 8; i++){
2595 if (!cfs_test_bit(i, fsdb->fsdb_mdt_index_map))
2597 name_destroy(&cname);
2598 name_create_mdt_osc(&cname, mti->mti_svname,
2600 name_destroy(&logname);
2601 name_create_mdt(&logname, mti->mti_fsname, i);
2602 if (!mgs_log_is_empty(obd, logname))
2603 rc = mgs_wlp_lcfg(obd, fsdb,mti,logname,
2609 name_destroy(&logname);
2610 name_destroy(&cname);
2614 /* All mdt. params in proc */
2615 if (class_match_param(ptr, PARAM_MDT, NULL) == 0) {
2619 CDEBUG(D_MGS, "%.3s param %s\n", ptr, ptr + 4);
2620 if (strncmp(mti->mti_svname, mti->mti_fsname,
2621 MTI_NAME_MAXLEN) == 0)
2622 /* device is unspecified completely? */
2623 rc = LDD_F_SV_TYPE_MDT | LDD_F_SV_ALL;
2625 rc = server_name2index(mti->mti_svname, &idx, NULL);
2628 if ((rc & LDD_F_SV_TYPE_MDT) == 0)
2630 if (rc & LDD_F_SV_ALL) {
2631 for (i = 0; i < INDEX_MAP_SIZE * 8; i++) {
2632 if (!cfs_test_bit(i,
2633 fsdb->fsdb_mdt_index_map))
2635 name_create_mdt(&logname, mti->mti_fsname, i);
2636 rc = mgs_wlp_lcfg(obd, fsdb, mti,
2639 name_destroy(&logname);
2644 rc = mgs_wlp_lcfg(obd, fsdb, mti,
2645 mti->mti_svname, &bufs,
2646 mti->mti_svname, ptr);
2653 /* All mdd., ost. params in proc */
2654 if ((class_match_param(ptr, PARAM_MDD, NULL) == 0) ||
2655 (class_match_param(ptr, PARAM_OST, NULL) == 0)) {
2656 CDEBUG(D_MGS, "%.3s param %s\n", ptr, ptr + 4);
2657 if (mgs_log_is_empty(obd, mti->mti_svname))
2658 GOTO(end, rc = -ENODEV);
2660 rc = mgs_wlp_lcfg(obd, fsdb, mti, mti->mti_svname,
2661 &bufs, mti->mti_svname, ptr);
2665 LCONSOLE_WARN("Ignoring unrecognized param '%s'\n", ptr);
2670 CERROR("err %d on param '%s'\n", rc, ptr);
2675 /* Not implementing automatic failover nid addition at this time. */
2676 int mgs_check_failnid(struct obd_device *obd, struct mgs_target_info *mti)
2683 rc = mgs_find_or_make_fsdb(obd, fsname, &fsdb);
2687 if (mgs_log_is_empty(obd, mti->mti_svname))
2688 /* should never happen */
2691 CDEBUG(D_MGS, "Checking for new failnids for %s\n", mti->mti_svname);
2693 /* FIXME We can just check mti->params to see if we're already in
2694 the failover list. Modify mti->params for rewriting back at
2695 server_register_target(). */
2697 cfs_down(&fsdb->fsdb_sem);
2698 rc = mgs_write_log_add_failnid(obd, fsdb, mti);
2699 cfs_up(&fsdb->fsdb_sem);
2706 int mgs_write_log_target(struct obd_device *obd,
2707 struct mgs_target_info *mti,
2714 /* set/check the new target index */
2715 rc = mgs_set_index(obd, mti);
2717 CERROR("Can't get index (%d)\n", rc);
2722 if (mti->mti_flags & LDD_F_UPGRADE14) {
2723 if (rc == EALREADY) {
2724 LCONSOLE_INFO("Found index %d for %s 1.4 log, "
2725 "upgrading\n", mti->mti_stripe_index,
2728 LCONSOLE_ERROR_MSG(0x149, "Failed to find %s in the old"
2729 " client log. Apparently it is not "
2730 "part of this filesystem, or the old"
2731 " log is wrong.\nUse 'writeconf' on "
2732 "the MDT to force log regeneration."
2733 "\n", mti->mti_svname);
2734 /* Not in client log? Upgrade anyhow...*/
2735 /* Argument against upgrading: reformat MDT,
2736 upgrade OST, then OST will start but will be SKIPped
2737 in client logs. Maybe error now is better. */
2738 /* RETURN(-EINVAL); */
2740 /* end COMPAT_146 */
2742 if (rc == EALREADY) {
2743 LCONSOLE_WARN("Found index %d for %s, updating log\n",
2744 mti->mti_stripe_index, mti->mti_svname);
2745 /* We would like to mark old log sections as invalid
2746 and add new log sections in the client and mdt logs.
2747 But if we add new sections, then live clients will
2748 get repeat setup instructions for already running
2749 osc's. So don't update the client/mdt logs. */
2750 mti->mti_flags &= ~LDD_F_UPDATE;
2754 cfs_down(&fsdb->fsdb_sem);
2756 if (mti->mti_flags &
2757 (LDD_F_VIRGIN | LDD_F_UPGRADE14 | LDD_F_WRITECONF)) {
2758 /* Generate a log from scratch */
2759 if (mti->mti_flags & LDD_F_SV_TYPE_MDT) {
2760 rc = mgs_write_log_mdt(obd, fsdb, mti);
2761 } else if (mti->mti_flags & LDD_F_SV_TYPE_OST) {
2762 rc = mgs_write_log_ost(obd, fsdb, mti);
2764 CERROR("Unknown target type %#x, can't create log for "
2765 "%s\n", mti->mti_flags, mti->mti_svname);
2768 CERROR("Can't write logs for %s (%d)\n",
2769 mti->mti_svname, rc);
2773 /* Just update the params from tunefs in mgs_write_log_params */
2774 CDEBUG(D_MGS, "Update params for %s\n", mti->mti_svname);
2775 mti->mti_flags |= LDD_F_PARAM;
2778 /* allocate temporary buffer, where class_get_next_param will
2779 make copy of a current parameter */
2780 OBD_ALLOC(buf, strlen(mti->mti_params) + 1);
2782 GOTO(out_up, rc = -ENOMEM);
2783 params = mti->mti_params;
2784 while (params != NULL) {
2785 rc = class_get_next_param(¶ms, buf);
2788 /* there is no next parameter, that is
2793 CDEBUG(D_MGS, "remaining string: '%s', param: '%s'\n",
2795 rc = mgs_write_log_param(obd, fsdb, mti, buf);
2800 OBD_FREE(buf, strlen(mti->mti_params) + 1);
2803 cfs_up(&fsdb->fsdb_sem);
2808 /* verify that we can handle the old config logs */
2809 int mgs_upgrade_sv_14(struct obd_device *obd, struct mgs_target_info *mti,
2815 /* Create ost log normally, as servers register. Servers
2816 register with their old uuids (from last_rcvd), so old
2817 (MDT and client) logs should work.
2818 - new MDT won't know about old OSTs, only the ones that have
2819 registered, so we need the old MDT log to get the LOV right
2820 in order for old clients to work.
2821 - Old clients connect to the MDT, not the MGS, for their logs, and
2822 will therefore receive the old client log from the MDT /LOGS dir.
2823 - Old clients can continue to use and connect to old or new OSTs
2824 - New clients will contact the MGS for their log
2827 LCONSOLE_INFO("upgrading server %s from pre-1.6\n", mti->mti_svname);
2828 server_mti_print("upgrade", mti);
2830 if (cfs_test_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags)) {
2831 LCONSOLE_ERROR_MSG(0x14a, "The old client log %s-client is "
2832 "missing. Was tunefs.lustre successful?\n",
2837 if (fsdb->fsdb_gen == 0) {
2838 /* There were no markers in the client log, meaning we have
2839 not updated the logs for this fs */
2840 CDEBUG(D_MGS, "found old, unupdated client log\n");
2843 if (mti->mti_flags & LDD_F_SV_TYPE_MDT) {
2844 if (mgs_log_is_empty(obd, mti->mti_svname)) {
2845 LCONSOLE_ERROR_MSG(0x14b, "The old MDT log %s is "
2846 "missing. Was tunefs.lustre "
2851 /* We're starting with an old uuid. Assume old name for lov
2852 as well since the lov entry already exists in the log. */
2853 CDEBUG(D_MGS, "old mds uuid %s\n", mti->mti_uuid);
2854 if (strncmp(mti->mti_uuid, fsdb->fsdb_mdtlov + 4,
2855 strlen(fsdb->fsdb_mdtlov) - 4) != 0) {
2856 CERROR("old mds uuid %s doesn't match log %s (%s)\n",
2857 mti->mti_uuid, fsdb->fsdb_mdtlov,
2858 fsdb->fsdb_mdtlov + 4);
2863 if (!cfs_test_bit(FSDB_OLDLOG14, &fsdb->fsdb_flags)) {
2864 LCONSOLE_ERROR_MSG(0x14c, "%s-client is supposedly an old "
2865 "log, but no old LOV or MDT was found. "
2866 "Consider updating the configuration with"
2867 " --writeconf.\n", mti->mti_fsname);
2872 /* end COMPAT_146 */
2874 int mgs_erase_log(struct obd_device *obd, char *name)
2876 struct lvfs_run_ctxt saved;
2877 struct llog_ctxt *ctxt;
2878 struct llog_handle *llh;
2881 ctxt = llog_get_context(obd, LLOG_CONFIG_ORIG_CTXT);
2882 LASSERT(ctxt != NULL);
2884 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
2885 rc = llog_create(ctxt, &llh, NULL, name);
2887 llog_init_handle(llh, LLOG_F_IS_PLAIN, NULL);
2888 rc = llog_destroy(llh);
2889 llog_free_handle(llh);
2891 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
2892 llog_ctxt_put(ctxt);
2895 CERROR("failed to clear log %s: %d\n", name, rc);
2900 /* erase all logs for the given fs */
2901 int mgs_erase_logs(struct obd_device *obd, char *fsname)
2903 struct mgs_obd *mgs = &obd->u.mgs;
2905 cfs_list_t dentry_list;
2906 struct l_linux_dirent *dirent, *n;
2907 int rc, len = strlen(fsname);
2911 /* Find all the logs in the CONFIGS directory */
2912 rc = class_dentry_readdir(obd, mgs->mgs_configs_dir,
2913 mgs->mgs_vfsmnt, &dentry_list);
2915 CERROR("Can't read %s dir\n", MOUNT_CONFIGS_DIR);
2919 cfs_down(&mgs->mgs_sem);
2921 /* Delete the fs db */
2922 fsdb = mgs_find_fsdb(obd, fsname);
2924 mgs_free_fsdb(obd, fsdb);
2926 cfs_list_for_each_entry_safe(dirent, n, &dentry_list, lld_list) {
2927 cfs_list_del(&dirent->lld_list);
2928 suffix = strrchr(dirent->lld_name, '-');
2929 if (suffix != NULL) {
2930 if ((len == suffix - dirent->lld_name) &&
2931 (strncmp(fsname, dirent->lld_name, len) == 0)) {
2932 CDEBUG(D_MGS, "Removing log %s\n",
2934 mgs_erase_log(obd, dirent->lld_name);
2937 OBD_FREE(dirent, sizeof(*dirent));
2940 cfs_up(&mgs->mgs_sem);
2945 /* from llog_swab */
2946 static void print_lustre_cfg(struct lustre_cfg *lcfg)
2951 CDEBUG(D_MGS, "lustre_cfg: %p\n", lcfg);
2952 CDEBUG(D_MGS, "\tlcfg->lcfg_version: %#x\n", lcfg->lcfg_version);
2954 CDEBUG(D_MGS, "\tlcfg->lcfg_command: %#x\n", lcfg->lcfg_command);
2955 CDEBUG(D_MGS, "\tlcfg->lcfg_num: %#x\n", lcfg->lcfg_num);
2956 CDEBUG(D_MGS, "\tlcfg->lcfg_flags: %#x\n", lcfg->lcfg_flags);
2957 CDEBUG(D_MGS, "\tlcfg->lcfg_nid: %s\n", libcfs_nid2str(lcfg->lcfg_nid));
2959 CDEBUG(D_MGS, "\tlcfg->lcfg_bufcount: %d\n", lcfg->lcfg_bufcount);
2960 if (lcfg->lcfg_bufcount < LUSTRE_CFG_MAX_BUFCOUNT)
2961 for (i = 0; i < lcfg->lcfg_bufcount; i++) {
2962 CDEBUG(D_MGS, "\tlcfg->lcfg_buflens[%d]: %d %s\n",
2963 i, lcfg->lcfg_buflens[i],
2964 lustre_cfg_string(lcfg, i));
2969 /* Set a permanent (config log) param for a target or fs
2970 * \param lcfg buf0 may contain the device (testfs-MDT0000) name
2971 * buf1 contains the single parameter
2973 int mgs_setparam(struct obd_device *obd, struct lustre_cfg *lcfg, char *fsname)
2976 struct mgs_target_info *mti;
2977 char *devname, *param;
2983 print_lustre_cfg(lcfg);
2985 /* lustre, lustre-mdtlov, lustre-client, lustre-MDT0000 */
2986 devname = lustre_cfg_string(lcfg, 0);
2987 param = lustre_cfg_string(lcfg, 1);
2989 /* Assume device name embedded in param:
2990 lustre-OST0000.osc.max_dirty_mb=32 */
2991 ptr = strchr(param, '.');
2999 LCONSOLE_ERROR_MSG(0x14d, "No target specified: %s\n", param);
3003 /* Extract fsname */
3004 ptr = strrchr(devname, '-');
3005 memset(fsname, 0, MTI_NAME_MAXLEN);
3006 if (ptr && (server_name2index(ptr, &index, NULL) >= 0)) {
3007 /* param related to llite isn't allowed to set by OST or MDT */
3008 if (strncmp(param, PARAM_LLITE, sizeof(PARAM_LLITE)) == 0)
3011 strncpy(fsname, devname, ptr - devname);
3013 /* assume devname is the fsname */
3014 strncpy(fsname, devname, MTI_NAME_MAXLEN);
3016 fsname[MTI_NAME_MAXLEN - 1] = 0;
3017 CDEBUG(D_MGS, "setparam fs='%s' device='%s'\n", fsname, devname);
3019 rc = mgs_find_or_make_fsdb(obd, fsname, &fsdb);
3022 if (!cfs_test_bit(FSDB_MGS_SELF, &fsdb->fsdb_flags) &&
3023 cfs_test_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags)) {
3024 CERROR("No filesystem targets for %s. cfg_device from lctl "
3025 "is '%s'\n", fsname, devname);
3026 mgs_free_fsdb(obd, fsdb);
3030 /* Create a fake mti to hold everything */
3033 GOTO(out, rc = -ENOMEM);
3034 strncpy(mti->mti_fsname, fsname, MTI_NAME_MAXLEN);
3035 strncpy(mti->mti_svname, devname, MTI_NAME_MAXLEN);
3036 strncpy(mti->mti_params, param, sizeof(mti->mti_params));
3037 rc = server_name2index(mti->mti_svname, &mti->mti_stripe_index, &tmp);
3039 /* Not a valid server; may be only fsname */
3042 /* Strip -osc or -mdc suffix from svname */
3043 if (server_make_name(rc, mti->mti_stripe_index, mti->mti_fsname,
3045 GOTO(out, rc = -EINVAL);
3047 mti->mti_flags = rc | LDD_F_PARAM;
3049 cfs_down(&fsdb->fsdb_sem);
3050 rc = mgs_write_log_param(obd, fsdb, mti, mti->mti_params);
3051 cfs_up(&fsdb->fsdb_sem);
3054 * Revoke lock so everyone updates. Should be alright if
3055 * someone was already reading while we were updating the logs,
3056 * so we don't really need to hold the lock while we're
3059 mgs_revoke_lock(obd, fsdb, CONFIG_T_CONFIG);
3065 static int mgs_write_log_pool(struct obd_device *obd, char *logname,
3066 struct fs_db *fsdb, char *lovname,
3067 enum lcfg_command_type cmd,
3068 char *poolname, char *fsname,
3069 char *ostname, char *comment)
3071 struct llog_handle *llh = NULL;
3074 rc = record_start_log(obd, &llh, logname);
3077 rc = record_marker(obd, llh, fsdb, CM_START, lovname, comment);
3078 record_base(obd, llh, lovname, 0, cmd, poolname, fsname, ostname, 0);
3079 rc = record_marker(obd, llh, fsdb, CM_END, lovname, comment);
3080 rc = record_end_log(obd, &llh);
3085 int mgs_pool_cmd(struct obd_device *obd, enum lcfg_command_type cmd,
3086 char *fsname, char *poolname, char *ostname)
3091 char *label = NULL, *canceled_label = NULL;
3093 struct mgs_target_info *mti = NULL;
3097 rc = mgs_find_or_make_fsdb(obd, fsname, &fsdb);
3099 CERROR("Can't get db for %s\n", fsname);
3102 if (cfs_test_bit(FSDB_LOG_EMPTY, &fsdb->fsdb_flags)) {
3103 CERROR("%s is not defined\n", fsname);
3104 mgs_free_fsdb(obd, fsdb);
3108 label_sz = 10 + strlen(fsname) + strlen(poolname);
3110 /* check if ostname match fsname */
3111 if (ostname != NULL) {
3114 ptr = strrchr(ostname, '-');
3115 if ((ptr == NULL) ||
3116 (strncmp(fsname, ostname, ptr-ostname) != 0))
3118 label_sz += strlen(ostname);
3121 OBD_ALLOC(label, label_sz);
3123 GOTO(out, rc = -ENOMEM);
3126 case LCFG_POOL_NEW: {
3128 "new %s.%s", fsname, poolname);
3131 case LCFG_POOL_ADD: {
3133 "add %s.%s.%s", fsname, poolname, ostname);
3136 case LCFG_POOL_REM: {
3137 OBD_ALLOC(canceled_label, label_sz);
3138 if (canceled_label == NULL)
3139 GOTO(out, rc = -ENOMEM);
3141 "rem %s.%s.%s", fsname, poolname, ostname);
3142 sprintf(canceled_label,
3143 "add %s.%s.%s", fsname, poolname, ostname);
3146 case LCFG_POOL_DEL: {
3147 OBD_ALLOC(canceled_label, label_sz);
3148 if (canceled_label == NULL)
3149 GOTO(out, rc = -ENOMEM);
3151 "del %s.%s", fsname, poolname);
3152 sprintf(canceled_label,
3153 "new %s.%s", fsname, poolname);
3161 cfs_down(&fsdb->fsdb_sem);
3163 if (canceled_label != NULL) {
3166 GOTO(out, rc = -ENOMEM);
3169 /* write pool def to all MDT logs */
3170 for (i = 0; i < INDEX_MAP_SIZE * 8; i++) {
3171 if (cfs_test_bit(i, fsdb->fsdb_mdt_index_map)) {
3172 name_create_mdt_and_lov(&logname, &lovname, fsdb, i);
3174 if (canceled_label != NULL) {
3175 strcpy(mti->mti_svname, "lov pool");
3176 mgs_modify(obd, fsdb, mti, logname, lovname,
3177 canceled_label, CM_SKIP);
3180 mgs_write_log_pool(obd, logname, fsdb, lovname,
3181 cmd, fsname, poolname, ostname,
3183 name_destroy(&logname);
3184 name_destroy(&lovname);
3188 name_create(&logname, fsname, "-client");
3189 if (canceled_label != NULL)
3190 mgs_modify(obd, fsdb, mti, logname, fsdb->fsdb_clilov,
3191 canceled_label, CM_SKIP);
3193 mgs_write_log_pool(obd, logname, fsdb, fsdb->fsdb_clilov,
3194 cmd, fsname, poolname, ostname, label);
3195 name_destroy(&logname);
3197 cfs_up(&fsdb->fsdb_sem);
3198 /* request for update */
3199 mgs_revoke_lock(obd, fsdb, CONFIG_T_CONFIG);
3204 OBD_FREE(label, label_sz);
3206 if (canceled_label != NULL)
3207 OBD_FREE(canceled_label, label_sz);
3216 /******************** unused *********************/
3217 static int mgs_backup_llog(struct obd_device *obd, char* fsname)
3219 struct file *filp, *bak_filp;
3220 struct lvfs_run_ctxt saved;
3221 char *logname, *buf;
3222 loff_t soff = 0 , doff = 0;
3223 int count = 4096, len;
3226 OBD_ALLOC(logname, PATH_MAX);
3227 if (logname == NULL)
3230 OBD_ALLOC(buf, count);
3232 GOTO(out , rc = -ENOMEM);
3234 len = snprintf(logname, PATH_MAX, "%s/%s.bak",
3235 MOUNT_CONFIGS_DIR, fsname);
3237 if (len >= PATH_MAX - 1) {
3238 GOTO(out, -ENAMETOOLONG);
3241 push_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
3243 bak_filp = l_filp_open(logname, O_RDWR|O_CREAT|O_TRUNC, 0660);
3244 if (IS_ERR(bak_filp)) {
3245 rc = PTR_ERR(bak_filp);
3246 CERROR("backup logfile open %s: %d\n", logname, rc);
3249 sprintf(logname, "%s/%s", MOUNT_CONFIGS_DIR, fsname);
3250 filp = l_filp_open(logname, O_RDONLY, 0);
3253 CERROR("logfile open %s: %d\n", logname, rc);
3257 while ((rc = lustre_fread(filp, buf, count, &soff)) > 0) {
3258 rc = lustre_fwrite(bak_filp, buf, count, &doff);
3262 filp_close(filp, 0);
3264 filp_close(bak_filp, 0);
3266 pop_ctxt(&saved, &obd->obd_lvfs_ctxt, NULL);
3269 OBD_FREE(buf, count);
3270 OBD_FREE(logname, PATH_MAX);