drivers/vdpa/mlx5/core/mr.c

Source file repositories/reference/linux-study-clean/drivers/vdpa/mlx5/core/mr.c

File Facts

System
Linux kernel
Corpus path
drivers/vdpa/mlx5/core/mr.c
Extension
.c
Size
21924 bytes
Lines
920
Domain
Driver Families
Bucket
drivers/vdpa
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct mlx5_create_mkey_mem {
	u8 out[MLX5_ST_SZ_BYTES(create_mkey_out)];
	u8 in[MLX5_ST_SZ_BYTES(create_mkey_in)];
	__be64 mtt[];
};

struct mlx5_destroy_mkey_mem {
	u8 out[MLX5_ST_SZ_BYTES(destroy_mkey_out)];
	u8 in[MLX5_ST_SZ_BYTES(destroy_mkey_in)];
};

static void fill_create_direct_mr(struct mlx5_vdpa_dev *mvdev,
				  struct mlx5_vdpa_direct_mr *mr,
				  struct mlx5_create_mkey_mem *mem)
{
	void *in = &mem->in;
	void *mkc;

	MLX5_SET(create_mkey_in, in, uid, mvdev->res.uid);
	mkc = MLX5_ADDR_OF(create_mkey_in, in, memory_key_mkey_entry);
	MLX5_SET(mkc, mkc, lw, !!(mr->perm & VHOST_MAP_WO));
	MLX5_SET(mkc, mkc, lr, !!(mr->perm & VHOST_MAP_RO));
	mlx5_set_access_mode(mkc, MLX5_MKC_ACCESS_MODE_MTT);
	MLX5_SET(mkc, mkc, qpn, 0xffffff);
	MLX5_SET(mkc, mkc, pd, mvdev->res.pdn);
	MLX5_SET64(mkc, mkc, start_addr, mr->offset);
	MLX5_SET64(mkc, mkc, len, mr->end - mr->start);
	MLX5_SET(mkc, mkc, log_page_size, mr->log_size);
	MLX5_SET(mkc, mkc, translations_octword_size,
		 get_octo_len(mr->end - mr->start, mr->log_size));
	MLX5_SET(create_mkey_in, in, translations_octword_actual_size,
		 get_octo_len(mr->end - mr->start, mr->log_size));
	populate_mtts(mr, MLX5_ADDR_OF(create_mkey_in, in, klm_pas_mtt));

	MLX5_SET(create_mkey_in, in, opcode, MLX5_CMD_OP_CREATE_MKEY);
	MLX5_SET(create_mkey_in, in, uid, mvdev->res.uid);
}

static void create_direct_mr_end(struct mlx5_vdpa_dev *mvdev,
				 struct mlx5_vdpa_direct_mr *mr,
				 struct mlx5_create_mkey_mem *mem)
{
	u32 mkey_index = MLX5_GET(create_mkey_out, mem->out, mkey_index);

	mr->mr = mlx5_idx_to_mkey(mkey_index);
}

static void fill_destroy_direct_mr(struct mlx5_vdpa_dev *mvdev,
				   struct mlx5_vdpa_direct_mr *mr,
				   struct mlx5_destroy_mkey_mem *mem)
{
	void *in = &mem->in;

	MLX5_SET(destroy_mkey_in, in, uid, mvdev->res.uid);
	MLX5_SET(destroy_mkey_in, in, opcode, MLX5_CMD_OP_DESTROY_MKEY);
	MLX5_SET(destroy_mkey_in, in, mkey_index, mlx5_mkey_to_idx(mr->mr));
}

static void destroy_direct_mr(struct mlx5_vdpa_dev *mvdev, struct mlx5_vdpa_direct_mr *mr)
{
	if (!mr->mr)
		return;

	mlx5_vdpa_destroy_mkey(mvdev, mr->mr);
}

static u64 map_start(struct vhost_iotlb_map *map, struct mlx5_vdpa_direct_mr *mr)
{
	return max_t(u64, map->start, mr->start);
}

static u64 map_end(struct vhost_iotlb_map *map, struct mlx5_vdpa_direct_mr *mr)
{
	return min_t(u64, map->last + 1, mr->end);
}

static u64 maplen(struct vhost_iotlb_map *map, struct mlx5_vdpa_direct_mr *mr)
{
	return map_end(map, mr) - map_start(map, mr);
}

#define MLX5_VDPA_INVALID_START_ADDR ((u64)-1)
#define MLX5_VDPA_INVALID_LEN ((u64)-1)

static u64 indir_start_addr(struct mlx5_vdpa_mr *mkey)
{
	struct mlx5_vdpa_direct_mr *s;

	s = list_first_entry_or_null(&mkey->head, struct mlx5_vdpa_direct_mr, list);
	if (!s)

Annotation

Implementation Notes