"usb",
"net",
"scsi_host",
+ "scsi_target",
"scsi",
"storage")
}
break;
+
+ case VIR_NODE_DEV_CAP_SCSI_TARGET:
+ virBufferVSprintf(&buf, " <target>%s</target>\n",
+ data->scsi_target.name);
+ break;
+
case VIR_NODE_DEV_CAP_SCSI:
virBufferVSprintf(&buf, " <host>%d</host>\n", data->scsi.host);
virBufferVSprintf(&buf, " <bus>%d</bus>\n", data->scsi.bus);
return ret;
}
+
+static int
+virNodeDevCapScsiTargetParseXML(virConnectPtr conn,
+ xmlXPathContextPtr ctxt,
+ virNodeDeviceDefPtr def,
+ xmlNodePtr node,
+ union _virNodeDevCapData *data)
+{
+ xmlNodePtr orignode;
+ int ret = -1;
+
+ orignode = ctxt->node;
+ ctxt->node = node;
+
+ data->scsi_target.name = virXPathString(conn, "string(./name[1])", ctxt);
+ if (!data->scsi_target.name) {
+ virNodeDeviceReportError(conn, VIR_ERR_INTERNAL_ERROR,
+ _("no target name supplied for '%s'"),
+ def->name);
+ goto out;
+ }
+
+ ret = 0;
+
+out:
+ ctxt->node = orignode;
+ return ret;
+}
+
+
static int
virNodeDevCapScsiHostParseXML(virConnectPtr conn,
xmlXPathContextPtr ctxt,
case VIR_NODE_DEV_CAP_SCSI_HOST:
ret = virNodeDevCapScsiHostParseXML(conn, ctxt, def, node, &caps->data, create);
break;
+ case VIR_NODE_DEV_CAP_SCSI_TARGET:
+ ret = virNodeDevCapScsiTargetParseXML(conn, ctxt, def, node, &caps->data);
+ break;
case VIR_NODE_DEV_CAP_SCSI:
ret = virNodeDevCapScsiParseXML(conn, ctxt, def, node, &caps->data);
break;
VIR_FREE(data->scsi_host.wwnn);
VIR_FREE(data->scsi_host.wwpn);
break;
+ case VIR_NODE_DEV_CAP_SCSI_TARGET:
+ VIR_FREE(data->scsi_target.name);
+ break;
case VIR_NODE_DEV_CAP_SCSI:
VIR_FREE(data->scsi.type);
break;
VIR_NODE_DEV_CAP_USB_INTERFACE, /* USB interface */
VIR_NODE_DEV_CAP_NET, /* Network device */
VIR_NODE_DEV_CAP_SCSI_HOST, /* SCSI Host Bus Adapter */
+ VIR_NODE_DEV_CAP_SCSI_TARGET, /* SCSI Target */
VIR_NODE_DEV_CAP_SCSI, /* SCSI device */
VIR_NODE_DEV_CAP_STORAGE, /* Storage device */
VIR_NODE_DEV_CAP_LAST
char *wwpn;
unsigned flags;
} scsi_host;
+ struct {
+ char *name;
+ } scsi_target;
struct {
unsigned host;
unsigned bus;
}
+static int udevProcessSCSITarget(struct udev_device *device ATTRIBUTE_UNUSED,
+ virNodeDeviceDefPtr def)
+{
+ int ret = -1;
+ const char *sysname = NULL;
+ union _virNodeDevCapData *data = &def->caps->data;
+
+ sysname = udev_device_get_sysname(device);
+
+ data->scsi_target.name = strdup(sysname);
+ if (data->scsi_target.name == NULL) {
+ virReportOOMError(NULL);
+ goto out;
+ }
+
+ if (udevGenerateDeviceName(device, def, NULL) != 0) {
+ goto out;
+ }
+
+ ret = 0;
+
+out:
+ return ret;
+}
+
+
static int udevGetSCSIType(unsigned int type, char **typestring)
{
int ret = 0;
goto out;
}
+ if (devtype != NULL && STREQ(devtype, "scsi_target")) {
+ *type = VIR_NODE_DEV_CAP_SCSI_TARGET;
+ goto out;
+ }
+
if (devtype != NULL && STREQ(devtype, "scsi_device")) {
*type = VIR_NODE_DEV_CAP_SCSI;
goto out;
case VIR_NODE_DEV_CAP_SCSI_HOST:
ret = udevProcessSCSIHost(device, def);
break;
+ case VIR_NODE_DEV_CAP_SCSI_TARGET:
+ ret = udevProcessSCSITarget(device, def);
+ break;
case VIR_NODE_DEV_CAP_SCSI:
ret = udevProcessSCSIDevice(device, def);
break;