};
struct lustre_cfg {
- __u32 lcfg_version;
- __u32 lcfg_command;
+ __u32 lcfg_version;
+ __u32 lcfg_command;
- __u32 lcfg_num;
- __u32 lcfg_flags;
- __u64 lcfg_nid;
- __u32 lcfg_nal; /* not used any more */
+ __u32 lcfg_num;
+ __u32 lcfg_flags;
+ __u64 lcfg_nid;
+ __u32 lcfg_nal; /* not used any more */
- __u32 lcfg_bufcount;
- __u32 lcfg_buflens[0];
+ __u32 lcfg_bufcount;
+ __u32 lcfg_buflens[0];
};
enum cfg_record_type {
static inline char *lustre_cfg_string(struct lustre_cfg *lcfg, int index)
{
- char *s;
-
- if (!lcfg->lcfg_buflens[index])
- return NULL;
-
- s = lustre_cfg_buf(lcfg, index);
- if (!s)
- return NULL;
-
- /* make sure it's NULL terminated, even if this kills a char
- * of data. Try to use the padding first though.
- */
- if (s[lcfg->lcfg_buflens[index] - 1] != '\0') {
- int last = min((int)lcfg->lcfg_buflens[index],
- cfs_size_round(lcfg->lcfg_buflens[index]) - 1);
- char lost = s[last];
- s[last] = '\0';
- if (lost != '\0') {
- CWARN("Truncated buf %d to '%s' (lost '%c'...)\n",
- index, s, lost);
- }
- }
- return s;
+ char *s;
+
+ if (lcfg->lcfg_buflens[index] == 0)
+ return NULL;
+
+ s = lustre_cfg_buf(lcfg, index);
+ if (s == NULL)
+ return NULL;
+
+ /*
+ * make sure it's NULL terminated, even if this kills a char
+ * of data. Try to use the padding first though.
+ */
+ if (s[lcfg->lcfg_buflens[index] - 1] != '\0') {
+ int last = min((int)lcfg->lcfg_buflens[index],
+ cfs_size_round(lcfg->lcfg_buflens[index]) - 1);
+ char lost = s[last];
+ s[last] = '\0';
+ if (lost != '\0') {
+ CWARN("Truncated buf %d to '%s' (lost '%c'...)\n",
+ index, s, lost);
+ }
+ }
+ return s;
}
static inline int lustre_cfg_len(__u32 bufcount, __u32 *buflens)
if (lcfg->lcfg_version != LUSTRE_CFG_VERSION)
RETURN(-EINVAL);
-
+
if (lcfg->lcfg_bufcount >= LUSTRE_CFG_MAX_BUFCOUNT)
RETURN(-EINVAL);
return (rc);
}
+/* For interoperability between 1.8 and 2.0. */
+#define CFG_GROUP_UPCALL "mdt.group_upcall"
+#define CFG_QUOTA_TYPE_OLD "mdt.quota_type"
+#define CFG_QUOTA_TYPE_NEW "mdd.quota_type"
+#define CFG_ROOT_SQUASH_OLD "mdt.rootsquash"
+#define CFG_ROOT_SQUASH_NEW "mdt.root_squash"
+#define CFG_NOSQUASH_NID_OLD "mdt.nosquash_nid"
+#define CFG_NOSQUASH_NID_NEW "mdt.nosquash_nids"
+
/* used by MGS to process specific configurations */
static int mdt_process_config(const struct lu_env *env,
struct lu_device *d, struct lustre_cfg *cfg)
int rc = 0;
ENTRY;
- switch (cfg->lcfg_command) {
- case LCFG_PARAM: {
- struct lprocfs_static_vars lvars;
- struct obd_device *obd = d->ld_obd;
-
- /*
- * For interoperability between 1.8 and 2.0,
- */
- {
- /* Skip old "mdt.group_upcall" param. */
- char *param = lustre_cfg_string(cfg, 1);
- if (param && !strncmp("mdt.group_upcall", param, 16)) {
- CWARN("For 1.8 interoperability, skip this"
- " mdt.group_upcall. It is obsolete\n");
- break;
- }
- /* Rename old "mdt.quota_type" to "mdd.quota_type. */
- if (param && !strncmp("mdt.quota_type", param, 14)) {
- CWARN("Found old param mdt.quota_type, changed"
- " it to mdd.quota_type.\n");
- param[2] = 'd';
- }
- }
-
- lprocfs_mdt_init_vars(&lvars);
- rc = class_process_proc_param(PARAM_MDT, lvars.obd_vars,
- cfg, obd);
- if (rc > 0 || rc == -ENOSYS)
- /* we don't understand; pass it on */
- rc = next->ld_ops->ldo_process_config(env, next, cfg);
- break;
- }
+ switch (cfg->lcfg_command) {
+ case LCFG_PARAM: {
+ struct lprocfs_static_vars lvars;
+ struct obd_device *obd = d->ld_obd;
+
+ /* For interoperability between 1.8 and 2.0. */
+ struct lustre_cfg *old_cfg = NULL;
+ char *param = NULL;
+ char *new_name = NULL;
+
+ param = lustre_cfg_string(cfg, 1);
+ if (param == NULL) {
+ CERROR("param is empty\n");
+ rc = -EINVAL;
+ break;
+ }
+
+ /* Skip old "mdt.group_upcall" param. */
+ if (strncmp(param, CFG_GROUP_UPCALL,
+ strlen(CFG_GROUP_UPCALL)) == 0) {
+ CWARN("For 1.8 interoperability, skip this %s."
+ " It is obsolete.\n", CFG_GROUP_UPCALL);
+ break;
+ }
+
+ /* Rename old "mdt.quota_type" to "mdd.quota_type". */
+ if (strncmp(param, CFG_QUOTA_TYPE_OLD,
+ strlen(CFG_QUOTA_TYPE_OLD)) == 0) {
+ CWARN("Found old param %s, changed it to %s.\n",
+ CFG_QUOTA_TYPE_OLD, CFG_QUOTA_TYPE_NEW);
+ new_name = CFG_QUOTA_TYPE_NEW;
+
+ } else if (strncmp(param, CFG_ROOT_SQUASH_OLD,
+ strlen(CFG_ROOT_SQUASH_OLD)) == 0) {
+ /* Rename old "mdt.rootsquash" to "mdt.root_squash". */
+ CWARN("Found old param %s, changed it to %s.\n",
+ CFG_ROOT_SQUASH_OLD, CFG_ROOT_SQUASH_NEW);
+ new_name = CFG_ROOT_SQUASH_NEW;
+
+ } else if (strncmp(param, CFG_NOSQUASH_NID_OLD,
+ strlen(CFG_NOSQUASH_NID_OLD)) == 0 &&
+ param[strlen(CFG_NOSQUASH_NID_OLD)] != 's') {
+ /*
+ * Rename old "mdt.nosquash_nid" to
+ * "mdt.nosquash_nids".
+ */
+ CWARN("Found old param %s, changed it to %s.\n",
+ CFG_NOSQUASH_NID_OLD, CFG_NOSQUASH_NID_NEW);
+ new_name = CFG_NOSQUASH_NID_NEW;
+ }
+
+ if (new_name != NULL) {
+ old_cfg = cfg;
+ cfg = lustre_cfg_rename(old_cfg, new_name);
+ if (IS_ERR(cfg)) {
+ rc = PTR_ERR(cfg);
+ break;
+ }
+ }
+
+ lprocfs_mdt_init_vars(&lvars);
+ rc = class_process_proc_param(PARAM_MDT, lvars.obd_vars,
+ cfg, obd);
+ if (rc > 0 || rc == -ENOSYS)
+ /* we don't understand; pass it on */
+ rc = next->ld_ops->ldo_process_config(env, next, cfg);
+
+ if (old_cfg != NULL)
+ lustre_cfg_free(cfg);
+
+ break;
+ }
case LCFG_ADD_MDC:
/*
* Add mdc hook to get first MDT uuid and connect it to
}
EXPORT_SYMBOL(lustre_register_client_process_config);
+/**
+ * Rename the proc parameter in \a cfg with a new name \a new_name.
+ *
+ * \param cfg config structure which contains the proc parameter
+ * \param new_name new name of the proc parameter
+ *
+ * \retval valid-pointer pointer to the newly-allocated config structure
+ * which contains the renamed proc parameter
+ * \retval ERR_PTR(-EINVAL) if \a cfg or \a new_name is NULL, or \a cfg does
+ * not contain a proc parameter
+ * \retval ERR_PTR(-ENOMEM) if memory allocation failure occurs
+ */
+struct lustre_cfg *lustre_cfg_rename(struct lustre_cfg *cfg,
+ const char *new_name)
+{
+ struct lustre_cfg_bufs *bufs = NULL;
+ struct lustre_cfg *new_cfg = NULL;
+ char *param = NULL;
+ char *new_param = NULL;
+ char *value = NULL;
+ int name_len = 0;
+ int new_len = 0;
+ ENTRY;
+
+ if (cfg == NULL || new_name == NULL)
+ RETURN(ERR_PTR(-EINVAL));
+
+ param = lustre_cfg_string(cfg, 1);
+ if (param == NULL)
+ RETURN(ERR_PTR(-EINVAL));
+
+ value = strchr(param, '=');
+ if (value == NULL)
+ name_len = strlen(param);
+ else
+ name_len = value - param;
+
+ new_len = LUSTRE_CFG_BUFLEN(cfg, 1) + strlen(new_name) - name_len;
+
+ OBD_ALLOC(new_param, new_len);
+ if (new_param == NULL)
+ RETURN(ERR_PTR(-ENOMEM));
+
+ strcpy(new_param, new_name);
+ if (value != NULL)
+ strcat(new_param, value);
+
+ OBD_ALLOC_PTR(bufs);
+ if (bufs == NULL) {
+ OBD_FREE(new_param, new_len);
+ RETURN(ERR_PTR(-ENOMEM));
+ }
+
+ lustre_cfg_bufs_reset(bufs, NULL);
+ lustre_cfg_bufs_init(bufs, cfg);
+ lustre_cfg_bufs_set_string(bufs, 1, new_param);
+
+ new_cfg = lustre_cfg_new(cfg->lcfg_command, bufs);
+
+ OBD_FREE(new_param, new_len);
+ OBD_FREE_PTR(bufs);
+ if (new_cfg == NULL)
+ RETURN(ERR_PTR(-ENOMEM));
+
+ new_cfg->lcfg_num = cfg->lcfg_num;
+ new_cfg->lcfg_flags = cfg->lcfg_flags;
+ new_cfg->lcfg_nid = cfg->lcfg_nid;
+ new_cfg->lcfg_nal = cfg->lcfg_nal;
+
+ RETURN(new_cfg);
+}
+EXPORT_SYMBOL(lustre_cfg_rename);
+
/** Process configuration commands given in lustre_cfg form.
* These may come from direct calls (e.g. class_manual_cleanup)
* or processing the config llog, or ioctl from lctl.