/** @} param */
+#define LUSTRE_MAXFSNAME 8
+
+/**
+ * Check whether the name is valid.
+ *
+ * \param name [in] the name to be checked
+ * \param minlen [in] the minimum length of the name
+ * \param maxlen [in] the maximum length of the name
+ *
+ * \retval 0 the name is valid
+ * \retval >0 the invalid character in the name
+ * \retval -1 the name is too short
+ * \retval -2 the name is too long
+ */
+static inline int lustre_is_name_valid(const char *name, const int minlen,
+ const int maxlen)
+{
+ const char *tmp;
+ size_t len;
+
+ len = strlen(name);
+
+ if (len < minlen)
+ return -1;
+
+ if (len > maxlen)
+ return -2;
+
+ for (tmp = name; *tmp != '\0'; ++tmp) {
+ if (isalnum(*tmp) || *tmp == '_' || *tmp == '-')
+ continue;
+ else
+ break;
+ }
+
+ return *tmp == '\0' ? 0 : *tmp;
+}
+
+/**
+ * Check whether the fsname is valid.
+ *
+ * \param fsname [in] the fsname to be checked
+ * \param minlen [in] the minimum length of the fsname
+ * \param maxlen [in] the maximum length of the fsname
+ *
+ * \retval 0 the fsname is valid
+ * \retval >0 the invalid character in the fsname
+ * \retval -1 the fsname is too short
+ * \retval -2 the fsname is too long
+ */
+static inline int lustre_is_fsname_valid(const char *fsname, const int minlen,
+ const int maxlen)
+{
+ return lustre_is_name_valid(fsname, minlen, maxlen);
+}
+
+/**
+ * Check whether the poolname is valid.
+ *
+ * \param poolname [in] the poolname to be checked
+ * \param minlen [in] the minimum length of the poolname
+ * \param maxlen [in] the maximum length of the poolname
+ *
+ * \retval 0 the poolname is valid
+ * \retval >0 the invalid character in the poolname
+ * \retval -1 the poolname is too short
+ * \retval -2 the poolname is too long
+ */
+static inline int lustre_is_poolname_valid(const char *poolname,
+ const int minlen, const int maxlen)
+{
+ return lustre_is_name_valid(poolname, minlen, maxlen);
+}
+
#endif /* _LUSTRE_PARAM_H */
}
run_test 6 "getstripe/setstripe"
+helper_test_7a()
+{
+ # Create a pool, stripe a directory and file with it
+ local pool=$1
+
+ pool_add $pool || error "pool_add failed"
+ pool_add_targets $pool 0 1 || error "pool_add_targets failed"
+
+ $SETSTRIPE -c 1 $DIR/$tdir/testfile1 --pool "$pool" || \
+ error "setstripe failed"
+ $SETSTRIPE -c 1 $DIR/$tdir/testfile2 --pool "$FSNAME.$pool" || \
+ error "setstripe failed"
+
+ mkdir $DIR/$tdir/testdir
+ $SETSTRIPE -c 1 $DIR/$tdir/testdir -p "$pool" || \
+ error "setstripe failed"
+ $SETSTRIPE -c 1 $DIR/$tdir/testdir -p "$FSNAME.$pool" || \
+ error "setstripe failed"
+
+ rm -f $DIR/$tdir/testfile1
+ rm -f $DIR/$tdir/testfile2
+ rmdir $DIR/$tdir/testdir
+
+ destroy_pool_int $FSNAME.$pool
+}
+
+test_7a()
+{
+ [ $OSTCOUNT -lt 2 ] && skip "needs >= 2 OSTs" && return
+
+ mkdir -p $DIR/$tdir
+
+ # Generate pool with random name from 1 to 15 characters
+ for i in 1 9 15 ; do
+ POOLNAME=$(cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w $i |
+ head -n 1)
+ echo set poolname to $POOLNAME
+ helper_test_7a $POOLNAME
+ done
+}
+run_test 7a "create various pool name"
+
+test_7b()
+{
+ # No fsname
+ do_facet mgs lctl pool_new qwerty
+ [ $? -ne 22 ] && error "can create a pool with no fsname"
+
+ # No pool name
+ do_facet mgs lctl pool_new $FSNAME.
+ [ $? -ne 22 ] && error "can create a pool with no name"
+
+ # Invalid character
+ do_facet mgs lctl pool_new $FSNAME.0123456789^bdef
+ [ $? -ne 22 ] && error "can create a pool with an invalid name"
+
+ # Too long
+ do_facet mgs lctl pool_new $FSNAME.0123456789abdefg
+ [ $? -ne 36 ] && error "can create a pool with a name too long"
+
+ return 0
+}
+run_test 7b "try to create pool name with invalid lengths or names"
+
+test_7c()
+{
+ [ $OSTCOUNT -lt 2 ] && skip "needs >= 2 OSTs" && return
+
+ mkdir -p $DIR/$tdir
+
+ # Create a pool with 15 letters
+ local pool=0123456789abcde
+ pool_add $pool || error "pool_add failed"
+ pool_add_targets $pool 0 1 || error "pool_add_targets failed"
+
+ # setstripe with the same pool name plus 1 letter
+ $SETSTRIPE -c 1 $DIR/$tdir/testfile1 --pool "${pool}X" && \
+ error "setstripe succedeed"
+
+ # setstripe with the same pool name minus 1 letter
+ $SETSTRIPE -c 1 $DIR/$tdir/testfile1 --pool "${pool%?}" && \
+ error "setstripe succedeed"
+
+ rm -f $DIR/$tdir/testfile1
+
+ destroy_pool_int $FSNAME.$pool
+}
+run_test 7c "create a valid pool name and setstripe with a bad one"
+
test_11() {
set_cleanup_trap
local POOL_ROOT=${POOL_ROOT:-$DIR/$tdir}
create_pool $FSNAME.$pool ||
{ error_noexit "No pool created, result code $?"; return 1; }
- [ $($LFS pool_list $FSNAME | grep -c $pool) -eq 1 ] ||
+ [ $($LFS pool_list $FSNAME | grep -c "$FSNAME.${pool}\$") -eq 1 ] ||
{ error_noexit "$pool not in lfs pool_list"; return 2; }
}
#include <libcfs/util/parser.h>
#include <lustre/lustreapi.h>
#include <lustre_ver.h>
+#include <lustre_param.h>
/* all functions */
static int lfs_setstripe(int argc, char **argv);
return CMD_HELP;
}
- if (pool_name_arg && strlen(pool_name_arg) > LOV_MAXPOOLNAME) {
- fprintf(stderr,
- "error: %s: pool name '%s' is too long (max is %d characters)\n",
- argv[0], pool_name_arg, LOV_MAXPOOLNAME);
- return CMD_HELP;
+ if (pool_name_arg != NULL) {
+ char *ptr;
+ int rc;
+
+ ptr = strchr(pool_name_arg, '.');
+ if (ptr == NULL) {
+ ptr = pool_name_arg;
+ } else {
+ if ((ptr - pool_name_arg) == 0) {
+ fprintf(stderr, "error: %s: fsname is empty "
+ "in pool name '%s'\n",
+ argv[0], pool_name_arg);
+ return CMD_HELP;
+ }
+
+ ++ptr;
+ }
+
+ rc = lustre_is_poolname_valid(ptr, 1, LOV_MAXPOOLNAME);
+ if (rc == -1) {
+ fprintf(stderr, "error: %s: poolname '%s' is "
+ "empty\n",
+ argv[0], pool_name_arg);
+ return CMD_HELP;
+ } else if (rc == -2) {
+ fprintf(stderr, "error: %s: pool name '%s' is too long "
+ "(max is %d characters)\n",
+ argv[0], pool_name_arg, LOV_MAXPOOLNAME);
+ return CMD_HELP;
+ } else if (rc > 0) {
+ fprintf(stderr, "error: %s: char '%c' not allowed in "
+ "pool name '%s'\n",
+ argv[0], rc, pool_name_arg);
+ return CMD_HELP;
+ }
}
/* get the stripe size */
sizeof(mop->mo_mkfsopts));
break;
case 'L': {
- char *tmp;
- if ((strlen(optarg) < 1) || (strlen(optarg) > 8)) {
- fprintf(stderr, "%s: filesystem name must be "
- "1-8 chars\n", progname);
- return 1;
- }
- if ((tmp = strpbrk(optarg, "/:"))) {
- fprintf(stderr, "%s: char '%c' not allowed in "
- "filesystem name\n", progname, *tmp);
- return 1;
- }
+ rc = lustre_is_fsname_valid(optarg, 1,
+ LUSTRE_MAXFSNAME);
+ if (rc < 0) {
+ fprintf(stderr, "%s: filesystem name must be "
+ "1-%d chars\n", progname,
+ LUSTRE_MAXFSNAME);
+ return 1;
+ } else if (rc > 0) {
+ fprintf(stderr, "%s: char '%c' not allowed in "
+ "filesystem name\n", progname, rc);
+ return 1;
+ }
+
strscpy(mop->mo_ldd.ldd_fsname, optarg,
sizeof(mop->mo_ldd.ldd_fsname));
fsname_option = true;
#include "obdctl.h"
#include <libcfs/util/ioctl.h>
#include <libcfs/util/parser.h>
+#include <libcfs/util/string.h>
#include <lnet/nidstr.h>
#include <lustre/lustre_idl.h>
#include <lnet/lnetctl.h>
#include <lustre/lustreapi.h>
+#include <lustre_param.h>
#define MAX_STRING_SIZE 128
#define DEVICES_LIST "/proc/fs/lustre/devices"
return 0;
}
-static int extract_fsname_poolname(char *arg, char *fsname, char *poolname)
+static int extract_fsname_poolname(const char *arg, char *fsname,
+ char *poolname)
{
- char *ptr;
- int len;
- int rc;
+ char *ptr;
+ int rc;
- strcpy(fsname, arg);
- ptr = strchr(fsname, '.');
- if (ptr == NULL) {
- fprintf(stderr, ". is missing in %s\n", fsname);
- rc = -EINVAL;
- goto err;
- }
+ strlcpy(fsname, arg, PATH_MAX + 1);
+ ptr = strchr(fsname, '.');
+ if (ptr == NULL) {
+ fprintf(stderr, ". is missing in %s\n", fsname);
+ rc = -EINVAL;
+ goto err;
+ }
- len = ptr - fsname;
- if (len == 0) {
- fprintf(stderr, "fsname is empty\n");
- rc = -EINVAL;
- goto err;
- }
+ if ((ptr - fsname) == 0) {
+ fprintf(stderr, "fsname is empty\n");
+ rc = -EINVAL;
+ goto err;
+ }
- len = strlen(ptr + 1);
- if (len == 0) {
- fprintf(stderr, "poolname is empty\n");
- rc = -EINVAL;
- goto err;
- }
- if (len > LOV_MAXPOOLNAME) {
- fprintf(stderr,
- "poolname %s is too long (length is %d max is %d)\n",
- ptr + 1, len, LOV_MAXPOOLNAME);
- rc = -ENAMETOOLONG;
- goto err;
- }
- strncpy(poolname, ptr + 1, LOV_MAXPOOLNAME);
- poolname[LOV_MAXPOOLNAME] = '\0';
- *ptr = '\0';
- return 0;
+ *ptr = '\0';
+ ++ptr;
+
+ rc = lustre_is_fsname_valid(fsname, 1, LUSTRE_MAXFSNAME);
+ if (rc < 0) {
+ fprintf(stderr, "filesystem name %s must be 1-%d chars\n",
+ fsname, LUSTRE_MAXFSNAME);
+ rc = -EINVAL;
+ goto err;
+ } else if (rc > 0) {
+ fprintf(stderr, "char '%c' not allowed in filesystem name\n",
+ rc);
+ rc = -EINVAL;
+ goto err;
+ }
+
+ rc = lustre_is_poolname_valid(ptr, 1, LOV_MAXPOOLNAME);
+ if (rc == -1) {
+ fprintf(stderr, "poolname is empty\n");
+ rc = -EINVAL;
+ goto err;
+ } else if (rc == -2) {
+ fprintf(stderr,
+ "poolname %s is too long (max is %d)\n",
+ ptr, LOV_MAXPOOLNAME);
+ rc = -ENAMETOOLONG;
+ goto err;
+ } else if (rc > 0) {
+ fprintf(stderr, "char '%c' not allowed in pool name '%s'\n",
+ rc, ptr);
+ rc = -EINVAL;
+ goto err;
+ }
+
+ strncpy(poolname, ptr, LOV_MAXPOOLNAME);
+ poolname[LOV_MAXPOOLNAME] = '\0';
+ return 0;
err:
- fprintf(stderr, "argument %s must be <fsname>.<poolname>\n", arg);
- return rc;
+ fprintf(stderr, "argument %s must be <fsname>.<poolname>\n", arg);
+ return rc;
}
int jt_pool_cmd(int argc, char **argv)