Set quota on volume root directory, not _data

This will appease the higher-level quota logic. Basically, to
find a free quota ID to prevent reuse, we will iterate through
the contents of the directory and check the quota IDs of all
subdirectories, then use the first free ID found that is larger
than the base ID (the one set on the base directory). Problem:
our volumes use a two-tier directory structure, where the volume
has an outer directory (with the name of the actual volume) and
an inner directory (always named _data). We were only setting the
quota on _data, meaning the outer directory did not have an ID,
and the ID-choosing logic thus never detected that any IDs had
been allocated and always chose the same ID.

Setting the ID on the outer directory with PROJINHERIT set makes
the ID allocation logic work properly, and guarantees children
inherit the ID - so _data and all contents of the volume get the
ID as we'd expect.

No tests as we don't have a filesystem in our CI that supports
XFS quotas (setting it on / needs kernel flags added).

Fixes https://issues.redhat.com/browse/RHEL-18038

Signed-off-by: Matt Heon <mheon@redhat.com>
This commit is contained in:
Matt Heon
2024-10-22 08:19:38 -04:00
parent beb35627a3
commit 23ab7b858a

View File

@ -201,7 +201,11 @@ func (r *Runtime) newVolume(ctx context.Context, noCreatePluginVolume bool, opti
Inodes: volume.config.Inodes,
Size: volume.config.Size,
}
if err := q.SetQuota(fullVolPath, quota); err != nil {
// Must use volPathRoot not fullVolPath, as we need the
// base path for the volume - without the `_data`
// subdirectory - so the quota ID assignment logic works
// properly.
if err := q.SetQuota(volPathRoot, quota); err != nil {
return nil, fmt.Errorf("failed to set size quota size=%d inodes=%d for volume directory %q: %w", volume.config.Size, volume.config.Inodes, fullVolPath, err)
}
}