^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * vfsv0 quota IO operations on file
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) #include <linux/errno.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/fs.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/mount.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/dqblk_v2.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/quotaops.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <asm/byteorder.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include "quota_tree.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include "quotaio_v2.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) MODULE_AUTHOR("Jan Kara");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) MODULE_DESCRIPTION("Quota format v2 support");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) static void v2r0_mem2diskdqb(void *dp, struct dquot *dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) static void v2r0_disk2memdqb(struct dquot *dquot, void *dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) static int v2r0_is_id(void *dp, struct dquot *dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) static void v2r1_mem2diskdqb(void *dp, struct dquot *dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) static void v2r1_disk2memdqb(struct dquot *dquot, void *dp);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) static int v2r1_is_id(void *dp, struct dquot *dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) static const struct qtree_fmt_operations v2r0_qtree_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) .mem2disk_dqblk = v2r0_mem2diskdqb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) .disk2mem_dqblk = v2r0_disk2memdqb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) .is_id = v2r0_is_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) static const struct qtree_fmt_operations v2r1_qtree_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) .mem2disk_dqblk = v2r1_mem2diskdqb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) .disk2mem_dqblk = v2r1_disk2memdqb,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) .is_id = v2r1_is_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) #define QUOTABLOCK_BITS 10
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) #define QUOTABLOCK_SIZE (1 << QUOTABLOCK_BITS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) static inline qsize_t v2_stoqb(qsize_t space)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) return (space + QUOTABLOCK_SIZE - 1) >> QUOTABLOCK_BITS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) static inline qsize_t v2_qbtos(qsize_t blocks)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) return blocks << QUOTABLOCK_BITS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) static int v2_read_header(struct super_block *sb, int type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) struct v2_disk_dqheader *dqhead)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) ssize_t size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) size = sb->s_op->quota_read(sb, type, (char *)dqhead,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) sizeof(struct v2_disk_dqheader), 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) if (size != sizeof(struct v2_disk_dqheader)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) quota_error(sb, "Failed header read: expected=%zd got=%zd",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) sizeof(struct v2_disk_dqheader), size);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) if (size < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) return size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) return -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) /* Check whether given file is really vfsv0 quotafile */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) static int v2_check_quota_file(struct super_block *sb, int type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) struct v2_disk_dqheader dqhead;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) static const uint quota_magics[] = V2_INITQMAGICS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) static const uint quota_versions[] = V2_INITQVERSIONS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) if (v2_read_header(sb, type, &dqhead))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) if (le32_to_cpu(dqhead.dqh_magic) != quota_magics[type] ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) le32_to_cpu(dqhead.dqh_version) > quota_versions[type])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) return 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) /* Read information header from quota file */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) static int v2_read_file_info(struct super_block *sb, int type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) struct v2_disk_dqinfo dinfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) struct v2_disk_dqheader dqhead;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) struct quota_info *dqopt = sb_dqopt(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) struct mem_dqinfo *info = &dqopt->info[type];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) struct qtree_mem_dqinfo *qinfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) ssize_t size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) unsigned int version;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) down_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) ret = v2_read_header(sb, type, &dqhead);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) if (ret < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) version = le32_to_cpu(dqhead.dqh_version);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) if ((info->dqi_fmt_id == QFMT_VFS_V0 && version != 0) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) (info->dqi_fmt_id == QFMT_VFS_V1 && version != 1)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) ret = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) size = sb->s_op->quota_read(sb, type, (char *)&dinfo,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) sizeof(struct v2_disk_dqinfo), V2_DQINFOOFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) if (size != sizeof(struct v2_disk_dqinfo)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) quota_error(sb, "Can't read info structure");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) if (size < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) ret = size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) ret = -EIO;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) info->dqi_priv = kmalloc(sizeof(struct qtree_mem_dqinfo), GFP_NOFS);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) if (!info->dqi_priv) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) ret = -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) qinfo = info->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) if (version == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) /* limits are stored as unsigned 32-bit data */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) info->dqi_max_spc_limit = 0xffffffffLL << QUOTABLOCK_BITS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) info->dqi_max_ino_limit = 0xffffffff;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) * Used space is stored as unsigned 64-bit value in bytes but
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) * quota core supports only signed 64-bit values so use that
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) * as a limit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) info->dqi_max_spc_limit = 0x7fffffffffffffffLL; /* 2^63-1 */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) info->dqi_max_ino_limit = 0x7fffffffffffffffLL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) info->dqi_bgrace = le32_to_cpu(dinfo.dqi_bgrace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) info->dqi_igrace = le32_to_cpu(dinfo.dqi_igrace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) /* No flags currently supported */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) info->dqi_flags = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) qinfo->dqi_sb = sb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) qinfo->dqi_type = type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) qinfo->dqi_blocks = le32_to_cpu(dinfo.dqi_blocks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) qinfo->dqi_free_blk = le32_to_cpu(dinfo.dqi_free_blk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) qinfo->dqi_free_entry = le32_to_cpu(dinfo.dqi_free_entry);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) qinfo->dqi_blocksize_bits = V2_DQBLKSIZE_BITS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) qinfo->dqi_usable_bs = 1 << V2_DQBLKSIZE_BITS;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) qinfo->dqi_qtree_depth = qtree_depth(qinfo);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) if (version == 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) qinfo->dqi_entry_size = sizeof(struct v2r0_disk_dqblk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) qinfo->dqi_ops = &v2r0_qtree_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) qinfo->dqi_entry_size = sizeof(struct v2r1_disk_dqblk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) qinfo->dqi_ops = &v2r1_qtree_ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) ret = -EUCLEAN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) /* Some sanity checks of the read headers... */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) if ((loff_t)qinfo->dqi_blocks << qinfo->dqi_blocksize_bits >
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) i_size_read(sb_dqopt(sb)->files[type])) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) quota_error(sb, "Number of blocks too big for quota file size (%llu > %llu).",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) (loff_t)qinfo->dqi_blocks << qinfo->dqi_blocksize_bits,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) i_size_read(sb_dqopt(sb)->files[type]));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) if (qinfo->dqi_free_blk >= qinfo->dqi_blocks) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) quota_error(sb, "Free block number too big (%u >= %u).",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) qinfo->dqi_free_blk, qinfo->dqi_blocks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) if (qinfo->dqi_free_entry >= qinfo->dqi_blocks) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) quota_error(sb, "Block with free entry too big (%u >= %u).",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) qinfo->dqi_free_entry, qinfo->dqi_blocks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) goto out_free;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) ret = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) out_free:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) kfree(info->dqi_priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) info->dqi_priv = NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) up_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) /* Write information header to quota file */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) static int v2_write_file_info(struct super_block *sb, int type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) struct v2_disk_dqinfo dinfo;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) struct quota_info *dqopt = sb_dqopt(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) struct mem_dqinfo *info = &dqopt->info[type];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) struct qtree_mem_dqinfo *qinfo = info->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) ssize_t size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) down_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) spin_lock(&dq_data_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) info->dqi_flags &= ~DQF_INFO_DIRTY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) dinfo.dqi_bgrace = cpu_to_le32(info->dqi_bgrace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) dinfo.dqi_igrace = cpu_to_le32(info->dqi_igrace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) /* No flags currently supported */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) dinfo.dqi_flags = cpu_to_le32(0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) spin_unlock(&dq_data_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) dinfo.dqi_blocks = cpu_to_le32(qinfo->dqi_blocks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) dinfo.dqi_free_blk = cpu_to_le32(qinfo->dqi_free_blk);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) dinfo.dqi_free_entry = cpu_to_le32(qinfo->dqi_free_entry);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) size = sb->s_op->quota_write(sb, type, (char *)&dinfo,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) sizeof(struct v2_disk_dqinfo), V2_DQINFOOFF);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) up_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) if (size != sizeof(struct v2_disk_dqinfo)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) quota_error(sb, "Can't write info structure");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) return -1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) static void v2r0_disk2memdqb(struct dquot *dquot, void *dp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) struct v2r0_disk_dqblk *d = dp, empty;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) struct mem_dqblk *m = &dquot->dq_dqb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) m->dqb_ihardlimit = le32_to_cpu(d->dqb_ihardlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) m->dqb_isoftlimit = le32_to_cpu(d->dqb_isoftlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) m->dqb_curinodes = le32_to_cpu(d->dqb_curinodes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) m->dqb_itime = le64_to_cpu(d->dqb_itime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) m->dqb_bhardlimit = v2_qbtos(le32_to_cpu(d->dqb_bhardlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) m->dqb_bsoftlimit = v2_qbtos(le32_to_cpu(d->dqb_bsoftlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) m->dqb_curspace = le64_to_cpu(d->dqb_curspace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) m->dqb_btime = le64_to_cpu(d->dqb_btime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) /* We need to escape back all-zero structure */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) memset(&empty, 0, sizeof(struct v2r0_disk_dqblk));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) empty.dqb_itime = cpu_to_le64(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) if (!memcmp(&empty, dp, sizeof(struct v2r0_disk_dqblk)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) m->dqb_itime = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) static void v2r0_mem2diskdqb(void *dp, struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) struct v2r0_disk_dqblk *d = dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) struct mem_dqblk *m = &dquot->dq_dqb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) struct qtree_mem_dqinfo *info =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) d->dqb_ihardlimit = cpu_to_le32(m->dqb_ihardlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) d->dqb_isoftlimit = cpu_to_le32(m->dqb_isoftlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) d->dqb_curinodes = cpu_to_le32(m->dqb_curinodes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) d->dqb_itime = cpu_to_le64(m->dqb_itime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) d->dqb_bhardlimit = cpu_to_le32(v2_stoqb(m->dqb_bhardlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) d->dqb_bsoftlimit = cpu_to_le32(v2_stoqb(m->dqb_bsoftlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) d->dqb_curspace = cpu_to_le64(m->dqb_curspace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) d->dqb_btime = cpu_to_le64(m->dqb_btime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) d->dqb_id = cpu_to_le32(from_kqid(&init_user_ns, dquot->dq_id));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) if (qtree_entry_unused(info, dp))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) d->dqb_itime = cpu_to_le64(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) static int v2r0_is_id(void *dp, struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) struct v2r0_disk_dqblk *d = dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) struct qtree_mem_dqinfo *info =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) if (qtree_entry_unused(info, dp))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) return qid_eq(make_kqid(&init_user_ns, dquot->dq_id.type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) le32_to_cpu(d->dqb_id)),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) dquot->dq_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) static void v2r1_disk2memdqb(struct dquot *dquot, void *dp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) struct v2r1_disk_dqblk *d = dp, empty;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) struct mem_dqblk *m = &dquot->dq_dqb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) m->dqb_ihardlimit = le64_to_cpu(d->dqb_ihardlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) m->dqb_isoftlimit = le64_to_cpu(d->dqb_isoftlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) m->dqb_curinodes = le64_to_cpu(d->dqb_curinodes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) m->dqb_itime = le64_to_cpu(d->dqb_itime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) m->dqb_bhardlimit = v2_qbtos(le64_to_cpu(d->dqb_bhardlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) m->dqb_bsoftlimit = v2_qbtos(le64_to_cpu(d->dqb_bsoftlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) m->dqb_curspace = le64_to_cpu(d->dqb_curspace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) m->dqb_btime = le64_to_cpu(d->dqb_btime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) /* We need to escape back all-zero structure */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) memset(&empty, 0, sizeof(struct v2r1_disk_dqblk));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) empty.dqb_itime = cpu_to_le64(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) if (!memcmp(&empty, dp, sizeof(struct v2r1_disk_dqblk)))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) m->dqb_itime = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) static void v2r1_mem2diskdqb(void *dp, struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) struct v2r1_disk_dqblk *d = dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) struct mem_dqblk *m = &dquot->dq_dqb;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) struct qtree_mem_dqinfo *info =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) d->dqb_ihardlimit = cpu_to_le64(m->dqb_ihardlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) d->dqb_isoftlimit = cpu_to_le64(m->dqb_isoftlimit);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) d->dqb_curinodes = cpu_to_le64(m->dqb_curinodes);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) d->dqb_itime = cpu_to_le64(m->dqb_itime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) d->dqb_bhardlimit = cpu_to_le64(v2_stoqb(m->dqb_bhardlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) d->dqb_bsoftlimit = cpu_to_le64(v2_stoqb(m->dqb_bsoftlimit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) d->dqb_curspace = cpu_to_le64(m->dqb_curspace);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) d->dqb_btime = cpu_to_le64(m->dqb_btime);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) d->dqb_id = cpu_to_le32(from_kqid(&init_user_ns, dquot->dq_id));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) d->dqb_pad = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) if (qtree_entry_unused(info, dp))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) d->dqb_itime = cpu_to_le64(1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) static int v2r1_is_id(void *dp, struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) struct v2r1_disk_dqblk *d = dp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) struct qtree_mem_dqinfo *info =
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) if (qtree_entry_unused(info, dp))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) return qid_eq(make_kqid(&init_user_ns, dquot->dq_id.type,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) le32_to_cpu(d->dqb_id)),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) dquot->dq_id);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) static int v2_read_dquot(struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) struct quota_info *dqopt = sb_dqopt(dquot->dq_sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) down_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) ret = qtree_read_dquot(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) up_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) static int v2_write_dquot(struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) struct quota_info *dqopt = sb_dqopt(dquot->dq_sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) bool alloc = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) * If space for dquot is already allocated, we don't need any
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) * protection as we'll only overwrite the place of dquot. We are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) * still protected by concurrent writes of the same dquot by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) * dquot->dq_lock.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) if (!dquot->dq_off) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) alloc = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) down_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) down_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) ret = qtree_write_dquot(
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) if (alloc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) up_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) up_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) static int v2_release_dquot(struct dquot *dquot)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) struct quota_info *dqopt = sb_dqopt(dquot->dq_sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) down_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) ret = qtree_release_dquot(sb_dqinfo(dquot->dq_sb, dquot->dq_id.type)->dqi_priv, dquot);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) up_write(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) static int v2_free_file_info(struct super_block *sb, int type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) kfree(sb_dqinfo(sb, type)->dqi_priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) static int v2_get_next_id(struct super_block *sb, struct kqid *qid)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) struct quota_info *dqopt = sb_dqopt(sb);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) down_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) ret = qtree_get_next_id(sb_dqinfo(sb, qid->type)->dqi_priv, qid);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) up_read(&dqopt->dqio_sem);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) static const struct quota_format_ops v2_format_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) .check_quota_file = v2_check_quota_file,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) .read_file_info = v2_read_file_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) .write_file_info = v2_write_file_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) .free_file_info = v2_free_file_info,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) .read_dqblk = v2_read_dquot,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) .commit_dqblk = v2_write_dquot,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) .release_dqblk = v2_release_dquot,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) .get_next_id = v2_get_next_id,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) static struct quota_format_type v2r0_quota_format = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) .qf_fmt_id = QFMT_VFS_V0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) .qf_ops = &v2_format_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) .qf_owner = THIS_MODULE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) static struct quota_format_type v2r1_quota_format = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) .qf_fmt_id = QFMT_VFS_V1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) .qf_ops = &v2_format_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) .qf_owner = THIS_MODULE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) static int __init init_v2_quota_format(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) ret = register_quota_format(&v2r0_quota_format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) return register_quota_format(&v2r1_quota_format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) static void __exit exit_v2_quota_format(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) unregister_quota_format(&v2r0_quota_format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) unregister_quota_format(&v2r1_quota_format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) module_init(init_v2_quota_format);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) module_exit(exit_v2_quota_format);