Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 0a240339 authored by Jan Kara's avatar Jan Kara
Browse files

quota: Make VFS quotas use new interface for getting quota info



Create new internal interface for getting information about quota which
contains everything needed for both VFS quotas and XFS quotas. Make VFS
use this and hook it up to Q_GETINFO.

Reviewed-by: default avatarChristoph Hellwig <hch@lst.de>
Signed-off-by: default avatarJan Kara <jack@suse.cz>
parent 023a6007
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -789,7 +789,7 @@ static const struct quotactl_ops ext3_qctl_operations = {
	.quota_on	= ext3_quota_on,
	.quota_off	= dquot_quota_off,
	.quota_sync	= dquot_quota_sync,
	.get_info	= dquot_get_dqinfo,
	.get_state	= dquot_get_state,
	.set_info	= dquot_set_dqinfo,
	.get_dqblk	= dquot_get_dqblk,
	.set_dqblk	= dquot_set_dqblk
+1 −1
Original line number Diff line number Diff line
@@ -1076,7 +1076,7 @@ static const struct quotactl_ops ext4_qctl_operations = {
	.quota_on	= ext4_quota_on,
	.quota_off	= ext4_quota_off,
	.quota_sync	= dquot_quota_sync,
	.get_info	= dquot_get_dqinfo,
	.get_state	= dquot_get_state,
	.set_info	= dquot_set_dqinfo,
	.get_dqblk	= dquot_get_dqblk,
	.set_dqblk	= dquot_set_dqblk
+27 −14
Original line number Diff line number Diff line
@@ -2614,26 +2614,39 @@ int dquot_set_dqblk(struct super_block *sb, struct kqid qid,
EXPORT_SYMBOL(dquot_set_dqblk);

/* Generic routine for getting common part of quota file information */
int dquot_get_dqinfo(struct super_block *sb, int type, struct if_dqinfo *ii)
int dquot_get_state(struct super_block *sb, struct qc_state *state)
{
	struct mem_dqinfo *mi;
	struct qc_type_state *tstate;
	struct quota_info *dqopt = sb_dqopt(sb);
	int type;
  
	mutex_lock(&sb_dqopt(sb)->dqonoff_mutex);
	if (!sb_has_quota_active(sb, type)) {
		mutex_unlock(&sb_dqopt(sb)->dqonoff_mutex);
		return -ESRCH;
	}
	memset(state, 0, sizeof(*state));
	for (type = 0; type < MAXQUOTAS; type++) {
		if (!sb_has_quota_active(sb, type))
			continue;
		tstate = state->s_state + type;
		mi = sb_dqopt(sb)->info + type;
		tstate->flags = QCI_ACCT_ENABLED;
		spin_lock(&dq_data_lock);
	ii->dqi_bgrace = mi->dqi_bgrace;
	ii->dqi_igrace = mi->dqi_igrace;
	ii->dqi_flags = mi->dqi_flags & DQF_GETINFO_MASK;
	ii->dqi_valid = IIF_ALL;
		if (mi->dqi_flags & DQF_SYS_FILE)
			tstate->flags |= QCI_SYSFILE;
		if (mi->dqi_flags & DQF_ROOT_SQUASH)
			tstate->flags |= QCI_ROOT_SQUASH;
		if (sb_has_quota_limits_enabled(sb, type))
			tstate->flags |= QCI_LIMITS_ENFORCED;
		tstate->spc_timelimit = mi->dqi_bgrace;
		tstate->ino_timelimit = mi->dqi_igrace;
		tstate->ino = dqopt->files[type]->i_ino;
		tstate->blocks = dqopt->files[type]->i_blocks;
		tstate->nextents = 1;	/* We don't know... */
		spin_unlock(&dq_data_lock);
	}
	mutex_unlock(&sb_dqopt(sb)->dqonoff_mutex);
	return 0;
}
EXPORT_SYMBOL(dquot_get_dqinfo);
EXPORT_SYMBOL(dquot_get_state);

/* Generic routine for setting common part of quota file information */
int dquot_set_dqinfo(struct super_block *sb, int type, struct if_dqinfo *ii)
@@ -2677,7 +2690,7 @@ const struct quotactl_ops dquot_quotactl_ops = {
	.quota_on	= dquot_quota_on,
	.quota_off	= dquot_quota_off,
	.quota_sync	= dquot_quota_sync,
	.get_info	= dquot_get_dqinfo,
	.get_state	= dquot_get_state,
	.set_info	= dquot_set_dqinfo,
	.get_dqblk	= dquot_get_dqblk,
	.set_dqblk	= dquot_set_dqblk
@@ -2688,7 +2701,7 @@ const struct quotactl_ops dquot_quotactl_sysfile_ops = {
	.quota_enable	= dquot_quota_enable,
	.quota_disable	= dquot_quota_disable,
	.quota_sync	= dquot_quota_sync,
	.get_info	= dquot_get_dqinfo,
	.get_state	= dquot_get_state,
	.set_info	= dquot_set_dqinfo,
	.get_dqblk	= dquot_get_dqblk,
	.set_dqblk	= dquot_set_dqblk
+21 −4
Original line number Diff line number Diff line
@@ -118,13 +118,30 @@ static int quota_getfmt(struct super_block *sb, int type, void __user *addr)

static int quota_getinfo(struct super_block *sb, int type, void __user *addr)
{
	struct if_dqinfo info;
	struct qc_state state;
	struct qc_type_state *tstate;
	struct if_dqinfo uinfo;
	int ret;

	if (!sb->s_qcop->get_info)
	/* This checks whether qc_state has enough entries... */
	BUILD_BUG_ON(MAXQUOTAS > XQM_MAXQUOTAS);
	if (!sb->s_qcop->get_state)
		return -ENOSYS;
	ret = sb->s_qcop->get_info(sb, type, &info);
	if (!ret && copy_to_user(addr, &info, sizeof(info)))
	ret = sb->s_qcop->get_state(sb, &state);
	if (ret)
		return ret;
	tstate = state.s_state + type;
	if (!(tstate->flags & QCI_ACCT_ENABLED))
		return -ESRCH;
	memset(&uinfo, 0, sizeof(uinfo));
	uinfo.dqi_bgrace = tstate->spc_timelimit;
	uinfo.dqi_igrace = tstate->ino_timelimit;
	if (tstate->flags & QCI_SYSFILE)
		uinfo.dqi_flags |= DQF_SYS_FILE;
	if (tstate->flags & QCI_ROOT_SQUASH)
		uinfo.dqi_flags |= DQF_ROOT_SQUASH;
	uinfo.dqi_valid = IIF_ALL;
	if (!ret && copy_to_user(addr, &uinfo, sizeof(uinfo)))
		return -EFAULT;
	return ret;
}
+1 −1
Original line number Diff line number Diff line
@@ -805,7 +805,7 @@ static const struct quotactl_ops reiserfs_qctl_operations = {
	.quota_on = reiserfs_quota_on,
	.quota_off = dquot_quota_off,
	.quota_sync = dquot_quota_sync,
	.get_info = dquot_get_dqinfo,
	.get_state = dquot_get_state,
	.set_info = dquot_set_dqinfo,
	.get_dqblk = dquot_get_dqblk,
	.set_dqblk = dquot_set_dqblk,
Loading