drivers/infiniband/hw/usnic/usnic_ib_verbs.c

Source file repositories/reference/linux-study-clean/drivers/infiniband/hw/usnic/usnic_ib_verbs.c

File Facts

System
Linux kernel
Corpus path
drivers/infiniband/hw/usnic/usnic_ib_verbs.c
Extension
.c
Size
18889 bytes
Lines
709
Domain
Driver Families
Bucket
drivers/infiniband
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

if (!usnic_vnic_check_room(vnic, res_spec)) {
				usnic_dbg("Found used vnic %s from %s\n",
						dev_name(&us_ibdev->ib_dev.dev),
						pci_name(usnic_vnic_get_pdev(
									vnic)));
				ret = usnic_ib_qp_grp_create(qp_grp,
							     us_ibdev->ufdev,
							     vf, pd, res_spec,
							     trans_spec);

				mutex_unlock(&vf->lock);
				goto qp_grp_check;
			}
			mutex_unlock(&vf->lock);

		}
		usnic_uiom_free_dev_list(dev_list);
		dev_list = NULL;
	}

	/* Try to find resources on an unused vf */
	list_for_each_entry(vf, &us_ibdev->vf_dev_list, link) {
		mutex_lock(&vf->lock);
		vnic = vf->vnic;
		if (vf->qp_grp_ref_cnt == 0 &&
		    usnic_vnic_check_room(vnic, res_spec) == 0) {
			ret = usnic_ib_qp_grp_create(qp_grp, us_ibdev->ufdev,
						     vf, pd, res_spec,
						     trans_spec);

			mutex_unlock(&vf->lock);
			goto qp_grp_check;
		}
		mutex_unlock(&vf->lock);
	}

	usnic_info("No free qp grp found on %s\n",
		   dev_name(&us_ibdev->ib_dev.dev));
	return -ENOMEM;

qp_grp_check:
	if (ret) {
		usnic_err("Failed to allocate qp_grp\n");
		if (usnic_ib_share_vf)
			usnic_uiom_free_dev_list(dev_list);
	}
	return ret;
}

static void qp_grp_destroy(struct usnic_ib_qp_grp *qp_grp)
{
	struct usnic_ib_vf *vf = qp_grp->vf;

	WARN_ON(qp_grp->state != IB_QPS_RESET);

	mutex_lock(&vf->lock);
	usnic_ib_qp_grp_destroy(qp_grp);
	mutex_unlock(&vf->lock);
}

static int create_qp_validate_user_data(struct usnic_ib_create_qp_cmd cmd)
{
	if (cmd.spec.trans_type <= USNIC_TRANSPORT_UNKNOWN ||
			cmd.spec.trans_type >= USNIC_TRANSPORT_MAX)
		return -EINVAL;

	return 0;
}

/* Start of ib callback functions */

enum rdma_link_layer usnic_ib_port_link_layer(struct ib_device *device,
					      u32 port_num)
{
	return IB_LINK_LAYER_ETHERNET;
}

int usnic_ib_query_device(struct ib_device *ibdev,
			  struct ib_device_attr *props,
			  struct ib_udata *uhw)
{
	struct usnic_ib_dev *us_ibdev = to_usdev(ibdev);
	union ib_gid gid;
	struct ethtool_drvinfo info;
	int qp_per_vf;
	int err;

	usnic_dbg("\n");
	err = ib_is_udata_in_empty(uhw);
	if (err)

Annotation

Implementation Notes