Whamcloud - gitweb
LU-15220 utils: fix gcc-11 -Werror=format-truncation= error
[fs/lustre-release.git] / lustre / utils / liblustreapi.c
index 80ca61e..ca5debe 100644 (file)
@@ -776,6 +776,18 @@ retry_open:
        return fd;
 }
 
+int llapi_file_is_encrypted(int fd)
+{
+       unsigned long flags;
+       int rc;
+
+       rc = ioctl(fd, FS_IOC_GETFLAGS, &flags);
+       if (rc == -1)
+               return -errno;
+
+       return !!(flags & LUSTRE_ENCRYPT_FL);
+}
+
 int llapi_file_open_pool(const char *name, int flags, int mode,
                         unsigned long long stripe_size, int stripe_offset,
                         int stripe_count, int stripe_pattern, char *pool_name)
@@ -1806,6 +1818,11 @@ typedef int (semantic_func_t)(char *path, int p, int *d,
 
 #define OBD_NOT_FOUND           (-1)
 
+static bool lmv_is_foreign(__u32 magic)
+{
+       return magic == LMV_MAGIC_FOREIGN;
+}
+
 static void find_param_fini(struct find_param *param)
 {
        if (param->fp_migrate)
@@ -1903,6 +1920,8 @@ static int cb_get_dirstripe(char *path, int *d, struct find_param *param)
        int ret;
        bool did_nofollow = false;
 
+       if (!d || *d < 0)
+               return -ENOTDIR;
 again:
        param->fp_lmv_md->lum_stripe_count = param->fp_lmv_stripe_count;
        if (param->fp_get_default_lmv)
@@ -1945,7 +1964,7 @@ again:
                int lmv_size;
 
                /* if foreign LMV case, fake stripes number */
-               if (param->fp_lmv_md->lum_magic == LMV_MAGIC_FOREIGN) {
+               if (lmv_is_foreign(param->fp_lmv_md->lum_magic)) {
                        struct lmv_foreign_md *lfm;
 
                        lfm = (struct lmv_foreign_md *)param->fp_lmv_md;
@@ -1981,6 +2000,7 @@ again:
                }
                goto again;
        }
+
        return ret;
 }
 
@@ -3311,6 +3331,11 @@ void lmv_dump_user_lmm(struct lmv_user_md *lum, char *pool_name,
                        llapi_printf(LLAPI_MSG_NORMAL, ",bad_type");
                if (flags & LMV_HASH_FLAG_LOST_LMV)
                        llapi_printf(LLAPI_MSG_NORMAL, ",lost_lmv");
+               if (flags & LMV_HASH_FLAG_FIXED)
+                       llapi_printf(LLAPI_MSG_NORMAL, ",fixed");
+               if (flags & ~LMV_HASH_FLAG_KNOWN)
+                       llapi_printf(LLAPI_MSG_NORMAL, ",unknown_%04x",
+                                    flags & ~LMV_HASH_FLAG_KNOWN);
 
                if (verbose & VERBOSE_HASH_TYPE && !yaml)
                        separator = " ";
@@ -3645,7 +3670,7 @@ static inline void
 lov_v1v3_pool_name(struct lov_user_md *v1, char *pool_name)
 {
        if (v1->lmm_magic == LOV_USER_MAGIC_V3)
-               snprintf(pool_name, LOV_MAXPOOLNAME, "%s",
+               snprintf(pool_name, LOV_MAXPOOLNAME + 1, "%s",
                         ((struct lov_user_md_v3 *)v1)->lmm_pool_name);
        else
                pool_name[0] = '\0';
@@ -4657,7 +4682,7 @@ static int find_check_foreign(struct find_param *param)
                struct lmv_foreign_md *lfm;
 
                lfm = (void *)param->fp_lmv_md;
-               if (lfm->lfm_magic != LMV_MAGIC_FOREIGN) {
+               if (lmv_is_foreign(lfm->lfm_magic)) {
                        if (param->fp_foreign_type == LU_FOREIGN_TYPE_UNKNOWN)
                                return param->fp_exclude_foreign ? 1 : -1;
                        return -1;
@@ -4867,20 +4892,21 @@ static int fget_projid(int fd, int *projid)
  * Check that the file's permissions in *st matches the one in find_param
  */
 static int check_file_permissions(const struct find_param *param,
-                       const lstat_t *st)
+                       mode_t mode)
 {
-       const mode_t st_mode = st->st_mode & 07777;
        int decision = 0;
 
+       mode &= 07777;
+
        switch (param->fp_perm_sign) {
        case LFS_FIND_PERM_EXACT:
-               decision = (st_mode == param->fp_perm);
+               decision = (mode == param->fp_perm);
                break;
        case LFS_FIND_PERM_ALL:
-               decision = ((st_mode & param->fp_perm) == param->fp_perm);
+               decision = ((mode & param->fp_perm) == param->fp_perm);
                break;
        case LFS_FIND_PERM_ANY:
-               decision = ((st_mode & param->fp_perm) != 0);
+               decision = ((mode & param->fp_perm) != 0);
                break;
        }
 
@@ -4920,16 +4946,21 @@ static int cb_find_init(char *path, int p, int *dp,
        }
 
        /* See if we can check the file type from the dirent. */
-       if (param->fp_type != 0 && de != NULL && de->d_type != DT_UNKNOWN) {
-               checked_type = 1;
+       if (de != NULL && de->d_type != DT_UNKNOWN) {
+               if (param->fp_type != 0) {
+                       checked_type = 1;
 
-               if (DTTOIF(de->d_type) == param->fp_type) {
-                       if (param->fp_exclude_type)
-                               goto decided;
-               } else {
-                       if (!param->fp_exclude_type)
-                               goto decided;
+                       if (DTTOIF(de->d_type) == param->fp_type) {
+                               if (param->fp_exclude_type)
+                                       goto decided;
+                       } else {
+                               if (!param->fp_exclude_type)
+                                       goto decided;
+                       }
                }
+               if ((param->fp_check_mdt_count || param->fp_hash_type ||
+                    param->fp_check_hash_flag) && de->d_type != DT_DIR)
+                       goto decided;
        }
 
        ret = 0;
@@ -4952,23 +4983,66 @@ static int cb_find_init(char *path, int p, int *dp,
                decision = 0;
 
        if (decision == 0) {
-               if (d != -1 && (param->fp_check_mdt_count ||
-                   param->fp_hash_type || param->fp_check_foreign ||
-                   param->fp_check_hash_flag)) {
+               if (d != -1 &&
+                   (param->fp_check_mdt_count || param->fp_hash_type ||
+                    param->fp_check_hash_flag || param->fp_check_foreign)) {
                        param->fp_get_lmv = 1;
                        ret = cb_get_dirstripe(path, &d, param);
                        if (ret != 0) {
-                               /*
-                                * XXX this works to decide for foreign
-                                * criterion only
-                                */
-                               if (errno == ENODATA &&
-                                   param->fp_check_foreign) {
-                                       if (param->fp_exclude_foreign)
-                                               goto foreign;
-                                       goto decided;
+                               if (errno == ENODATA) {
+                                       ret = 0;
+                                       if (param->fp_check_mdt_count ||
+                                           param->fp_hash_type ||
+                                           param->fp_check_hash_flag) {
+                                               param->fp_lmv_md->lum_stripe_count = 0;
+                                               param->fp_lmv_md->lum_hash_type = 0;
+                                       }
+                                       if (param->fp_check_foreign) {
+                                               if (param->fp_exclude_foreign)
+                                                       goto print;
+                                               goto decided;
+                                       }
+                               } else {
+                                       return ret;
                                }
-                               return ret;
+                       }
+
+                       if (param->fp_check_mdt_count) {
+                               if (lmv_is_foreign(param->fp_lmv_md->lum_magic))
+                                       goto decided;
+
+                               decision = find_value_cmp(param->fp_lmv_md->lum_stripe_count,
+                                                         param->fp_mdt_count,
+                                                         param->fp_mdt_count_sign,
+                                                         param->fp_exclude_mdt_count, 1, 0);
+                               if (decision == -1)
+                                       goto decided;
+                       }
+
+                       if (param->fp_hash_type) {
+                               __u32 found;
+                               __u32 type = param->fp_lmv_md->lum_hash_type &
+                                       LMV_HASH_TYPE_MASK;
+
+                               if (lmv_is_foreign(param->fp_lmv_md->lum_magic))
+                                       goto decided;
+
+                               found = (1 << type) & param->fp_hash_type;
+                               if ((found && param->fp_exclude_hash_type) ||
+                                   (!found && !param->fp_exclude_hash_type))
+                                       goto decided;
+                       }
+
+                       if (param->fp_check_hash_flag) {
+                               __u32 flags = param->fp_lmv_md->lum_hash_type &
+                                       ~LMV_HASH_TYPE_MASK;
+
+                               if (lmv_is_foreign(param->fp_lmv_md->lum_magic))
+                                       goto decided;
+
+                               if (!(flags & param->fp_hash_inflags) ||
+                                   (flags & param->fp_hash_exflags))
+                                       goto decided;
                        }
                }
 
@@ -5033,7 +5107,18 @@ static int cb_find_init(char *path, int p, int *dp,
                }
        }
 
+       /* Check the file permissions from the stat info */
+       if (param->fp_perm_sign) {
+               decision = check_file_permissions(param, lmd->lmd_stx.stx_mode);
+               if (decision == -1)
+                       goto decided;
+       }
+
        if (param->fp_type && !checked_type) {
+               if ((param->fp_check_mdt_count || param->fp_check_hash_flag ||
+                    param->fp_hash_type) && !S_ISDIR(lmd->lmd_stx.stx_mode))
+                       goto decided;
+
                if ((lmd->lmd_stx.stx_mode & S_IFMT) == param->fp_type) {
                        if (param->fp_exclude_type)
                                goto decided;
@@ -5097,61 +5182,12 @@ static int cb_find_init(char *path, int p, int *dp,
                        goto decided;
        }
 
-       if (param->fp_check_mdt_count) {
-               if (param->fp_lmv_md->lum_magic == LMV_MAGIC_FOREIGN) {
-                       decision = -1;
-                       goto decided;
-               }
-
-               decision = find_value_cmp(
-                               param->fp_lmv_md->lum_stripe_count,
-                               param->fp_mdt_count,
-                               param->fp_mdt_count_sign,
-                               param->fp_exclude_mdt_count, 1, 0);
-               if (decision == -1)
-                       goto decided;
-       }
-
        if (param->fp_check_layout) {
                decision = find_check_layout(param);
                if (decision == -1)
                        goto decided;
        }
 
-       if (param->fp_hash_type) {
-               __u32 found;
-               __u32 type = param->fp_lmv_md->lum_hash_type &
-                            LMV_HASH_TYPE_MASK;
-
-               if (param->fp_lmv_md->lum_magic == LMV_MAGIC_FOREIGN) {
-                       decision = -1;
-                       goto decided;
-               }
-
-               found = (1 << type) & param->fp_hash_type;
-               if ((found && param->fp_exclude_hash_type) ||
-                   (!found && !param->fp_exclude_hash_type)) {
-                       decision = -1;
-                       goto decided;
-               }
-       }
-
-       if (param->fp_check_hash_flag) {
-               __u32 flags = param->fp_lmv_md->lum_hash_type &
-                             ~LMV_HASH_TYPE_MASK;
-
-               if (param->fp_lmv_md->lum_magic == LMV_MAGIC_FOREIGN) {
-                       decision = -1;
-                       goto decided;
-               }
-
-               if (!(flags & param->fp_hash_inflags) ||
-                    (flags & param->fp_hash_exflags)) {
-                       decision = -1;
-                       goto decided;
-               }
-       }
-
        /* If an OBD UUID is specified but none matches, skip this file. */
        if ((param->fp_obd_uuid && param->fp_obd_index == OBD_NOT_FOUND) ||
            (param->fp_mdt_uuid && param->fp_mdt_index == OBD_NOT_FOUND))
@@ -5300,9 +5336,6 @@ obd_matches:
              (param->fp_lazy && flags & OBD_MD_FLLAZYBLOCKS)))
                decision = 0;
 
-       if (param->fp_perm_sign)
-               decision = 0;
-
        /*
         * If file still fits the request, ask ost for updated info.
         * The regular stat is almost of the same speed as some new
@@ -5359,13 +5392,6 @@ obd_matches:
                                goto out;
                        }
                }
-
-               /* Check the file permissions from the stat info */
-               if (param->fp_perm_sign) {
-                       decision = check_file_permissions(param, &st);
-                       if (decision == -1)
-                               goto decided;
-               }
        }
 
        if (param->fp_check_size) {
@@ -5388,12 +5414,9 @@ obd_matches:
                        goto decided;
        }
 
-foreign:
-       llapi_printf(LLAPI_MSG_NORMAL, "%s", path);
-       if (param->fp_zero_end)
-               llapi_printf(LLAPI_MSG_NORMAL, "%c", '\0');
-       else
-               llapi_printf(LLAPI_MSG_NORMAL, "\n");
+print:
+       llapi_printf(LLAPI_MSG_NORMAL, "%s%c", path,
+                    param->fp_zero_end ? '\0' : '\n');
 
 decided:
        ret = 0;
@@ -5451,6 +5474,9 @@ static int cb_migrate_mdt_init(char *path, int p, int *dp,
        data.ioc_inlbuf2 = (char *)lmu;
        data.ioc_inllen2 = lmv_user_md_size(lmu->lum_stripe_count,
                                            lmu->lum_magic);
+       /* reach bottom? */
+       if (param->fp_depth == param->fp_max_depth)
+               data.ioc_type = MDS_MIGRATE_NSONLY;
        ret = llapi_ioctl_pack(&data, &rawbuf, sizeof(raw));
        if (ret != 0) {
                llapi_error(LLAPI_MSG_ERROR, ret,
@@ -5492,6 +5518,11 @@ migrate:
        }
 
 out:
+       /* Do not get down anymore? */
+       if (param->fp_depth == param->fp_max_depth)
+               ret = 1;
+       param->fp_depth++;
+
        if (dp != NULL) {
                /*
                 * If the directory is being migration, we need