in scsi.c [1469:1521]
static int vhost_scsi_setup_vq_cmds(struct vhost_virtqueue *vq, int max_cmds)
{
struct vhost_scsi_virtqueue *svq = container_of(vq,
struct vhost_scsi_virtqueue, vq);
struct vhost_scsi_cmd *tv_cmd;
unsigned int i;
if (svq->scsi_cmds)
return 0;
if (sbitmap_init_node(&svq->scsi_tags, max_cmds, -1, GFP_KERNEL,
NUMA_NO_NODE, false, true))
return -ENOMEM;
svq->max_cmds = max_cmds;
svq->scsi_cmds = kcalloc(max_cmds, sizeof(*tv_cmd), GFP_KERNEL);
if (!svq->scsi_cmds) {
sbitmap_free(&svq->scsi_tags);
return -ENOMEM;
}
for (i = 0; i < max_cmds; i++) {
tv_cmd = &svq->scsi_cmds[i];
tv_cmd->tvc_sgl = kcalloc(VHOST_SCSI_PREALLOC_SGLS,
sizeof(struct scatterlist),
GFP_KERNEL);
if (!tv_cmd->tvc_sgl) {
pr_err("Unable to allocate tv_cmd->tvc_sgl\n");
goto out;
}
tv_cmd->tvc_upages = kcalloc(VHOST_SCSI_PREALLOC_UPAGES,
sizeof(struct page *),
GFP_KERNEL);
if (!tv_cmd->tvc_upages) {
pr_err("Unable to allocate tv_cmd->tvc_upages\n");
goto out;
}
tv_cmd->tvc_prot_sgl = kcalloc(VHOST_SCSI_PREALLOC_PROT_SGLS,
sizeof(struct scatterlist),
GFP_KERNEL);
if (!tv_cmd->tvc_prot_sgl) {
pr_err("Unable to allocate tv_cmd->tvc_prot_sgl\n");
goto out;
}
}
return 0;
out:
vhost_scsi_destroy_vq_cmds(vq);
return -ENOMEM;
}