vfio/mlx5: Allow loading of larger images than 512 MB
Allow loading of larger images than 512 MB by dropping the arbitrary hard-coded value that we have today and move to use the max device loading value which is for now 4GB. As part of that we move to use the GFP_KERNEL_ACCOUNT option upon allocating the persistent data of mlx5 and rely on the cgroup to provide the memory limit for the given user. The GFP_KERNEL_ACCOUNT option lets the memory allocator know that this is untrusted allocation triggered from userspace and should be a subject of kmem accounting, and as such it is controlled by the cgroup mechanism. Signed-off-by: Yishai Hadas <yishaih@nvidia.com> Reviewed-by: Jason Gunthorpe <jgg@nvidia.com> Link: https://lore.kernel.org/r/20230108154427.32609-3-yishaih@nvidia.com Signed-off-by: Alex Williamson <alex.williamson@redhat.com>
This commit is contained in:
parent
c9c4c070e0
commit
83ff6095ec
@ -373,7 +373,7 @@ mlx5vf_alloc_data_buffer(struct mlx5_vf_migration_file *migf,
|
||||
struct mlx5_vhca_data_buffer *buf;
|
||||
int ret;
|
||||
|
||||
buf = kzalloc(sizeof(*buf), GFP_KERNEL);
|
||||
buf = kzalloc(sizeof(*buf), GFP_KERNEL_ACCOUNT);
|
||||
if (!buf)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
@ -1032,7 +1032,7 @@ mlx5vf_create_rc_qp(struct mlx5_core_dev *mdev,
|
||||
void *in;
|
||||
int err;
|
||||
|
||||
qp = kzalloc(sizeof(*qp), GFP_KERNEL);
|
||||
qp = kzalloc(sizeof(*qp), GFP_KERNEL_ACCOUNT);
|
||||
if (!qp)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
@ -1213,12 +1213,13 @@ static int alloc_recv_pages(struct mlx5_vhca_recv_buf *recv_buf,
|
||||
int i;
|
||||
|
||||
recv_buf->page_list = kvcalloc(npages, sizeof(*recv_buf->page_list),
|
||||
GFP_KERNEL);
|
||||
GFP_KERNEL_ACCOUNT);
|
||||
if (!recv_buf->page_list)
|
||||
return -ENOMEM;
|
||||
|
||||
for (;;) {
|
||||
filled = alloc_pages_bulk_array(GFP_KERNEL, npages - done,
|
||||
filled = alloc_pages_bulk_array(GFP_KERNEL_ACCOUNT,
|
||||
npages - done,
|
||||
recv_buf->page_list + done);
|
||||
if (!filled)
|
||||
goto err;
|
||||
@ -1248,7 +1249,7 @@ static int register_dma_recv_pages(struct mlx5_core_dev *mdev,
|
||||
|
||||
recv_buf->dma_addrs = kvcalloc(recv_buf->npages,
|
||||
sizeof(*recv_buf->dma_addrs),
|
||||
GFP_KERNEL);
|
||||
GFP_KERNEL_ACCOUNT);
|
||||
if (!recv_buf->dma_addrs)
|
||||
return -ENOMEM;
|
||||
|
||||
|
@ -21,8 +21,8 @@
|
||||
|
||||
#include "cmd.h"
|
||||
|
||||
/* Arbitrary to prevent userspace from consuming endless memory */
|
||||
#define MAX_MIGRATION_SIZE (512*1024*1024)
|
||||
/* Device specification max LOAD size */
|
||||
#define MAX_LOAD_SIZE (BIT_ULL(__mlx5_bit_sz(load_vhca_state_in, size)) - 1)
|
||||
|
||||
static struct mlx5vf_pci_core_device *mlx5vf_drvdata(struct pci_dev *pdev)
|
||||
{
|
||||
@ -73,12 +73,13 @@ int mlx5vf_add_migration_pages(struct mlx5_vhca_data_buffer *buf,
|
||||
int ret;
|
||||
|
||||
to_fill = min_t(unsigned int, npages, PAGE_SIZE / sizeof(*page_list));
|
||||
page_list = kvzalloc(to_fill * sizeof(*page_list), GFP_KERNEL);
|
||||
page_list = kvzalloc(to_fill * sizeof(*page_list), GFP_KERNEL_ACCOUNT);
|
||||
if (!page_list)
|
||||
return -ENOMEM;
|
||||
|
||||
do {
|
||||
filled = alloc_pages_bulk_array(GFP_KERNEL, to_fill, page_list);
|
||||
filled = alloc_pages_bulk_array(GFP_KERNEL_ACCOUNT, to_fill,
|
||||
page_list);
|
||||
if (!filled) {
|
||||
ret = -ENOMEM;
|
||||
goto err;
|
||||
@ -87,7 +88,7 @@ int mlx5vf_add_migration_pages(struct mlx5_vhca_data_buffer *buf,
|
||||
ret = sg_alloc_append_table_from_pages(
|
||||
&buf->table, page_list, filled, 0,
|
||||
filled << PAGE_SHIFT, UINT_MAX, SG_MAX_SINGLE_ALLOC,
|
||||
GFP_KERNEL);
|
||||
GFP_KERNEL_ACCOUNT);
|
||||
|
||||
if (ret)
|
||||
goto err;
|
||||
@ -467,7 +468,7 @@ mlx5vf_pci_save_device_data(struct mlx5vf_pci_core_device *mvdev, bool track)
|
||||
size_t length;
|
||||
int ret;
|
||||
|
||||
migf = kzalloc(sizeof(*migf), GFP_KERNEL);
|
||||
migf = kzalloc(sizeof(*migf), GFP_KERNEL_ACCOUNT);
|
||||
if (!migf)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
@ -564,7 +565,7 @@ mlx5vf_resume_read_image_no_header(struct mlx5_vhca_data_buffer *vhca_buf,
|
||||
{
|
||||
int ret;
|
||||
|
||||
if (requested_length > MAX_MIGRATION_SIZE)
|
||||
if (requested_length > MAX_LOAD_SIZE)
|
||||
return -ENOMEM;
|
||||
|
||||
if (vhca_buf->allocated_length < requested_length) {
|
||||
@ -648,7 +649,7 @@ mlx5vf_resume_read_header(struct mlx5_vf_migration_file *migf,
|
||||
u64 flags;
|
||||
|
||||
vhca_buf->header_image_size = le64_to_cpup((__le64 *)to_buff);
|
||||
if (vhca_buf->header_image_size > MAX_MIGRATION_SIZE) {
|
||||
if (vhca_buf->header_image_size > MAX_LOAD_SIZE) {
|
||||
ret = -ENOMEM;
|
||||
goto end;
|
||||
}
|
||||
@ -781,7 +782,7 @@ mlx5vf_pci_resume_device_data(struct mlx5vf_pci_core_device *mvdev)
|
||||
struct mlx5_vhca_data_buffer *buf;
|
||||
int ret;
|
||||
|
||||
migf = kzalloc(sizeof(*migf), GFP_KERNEL);
|
||||
migf = kzalloc(sizeof(*migf), GFP_KERNEL_ACCOUNT);
|
||||
if (!migf)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user