nodedev: Dump max vports and vports in use for HBA's XML

This enrichs HBA's xml by dumping the number of max vports and
vports in use. Format is like:

  <capability type='vport_ops'>
    <max_vports>164</max_vports>
    <vports>5</vports>
  </capability>

* docs/formatnode.html.in: (Document the new XML)
* docs/schemas/nodedev.rng: (Add the schema)
* src/conf/node_device_conf.h: (New member for data.scsi_host)
* src/node_device/node_device_linux_sysfs.c: (Collect the value of
  max_vports and vports)
This commit is contained in:
Osier Yang 2013-01-08 01:05:32 +08:00
parent 4360a09844
commit 448be8f706
5 changed files with 66 additions and 8 deletions

View File

@ -136,9 +136,13 @@
<dd>The SCSI host number.</dd>
<dt><code>capability</code></dt>
<dd>Current capabilities include "vports_ops" (indicates
vport operations are supported) and "fc_host", the later
implies following sub-elements: <code>wwnn</code>,
<code>wwpn</code>, <code>fabric_wwn</code>.
vport operations are supported) and "fc_host". "vport_ops"
could contain two optional sub-elements: <code>vports</code>,
and <code>max_vports</code>. <code>vports</code> shows the
number of vport in use. <code>max_vports</code> shows the
maximum vports the HBA supports. "fc_host" implies following
sub-elements: <code>wwnn</code>, <code>wwpn</code>, and
<code>fabric_wwn</code>.
</dd>
</dl>
</dd>

View File

@ -268,6 +268,12 @@
<attribute name='type'>
<value>vports_ops</value>
</attribute>
<element name='max_vports'>
<ref name='unsignedInt'/>
</element>
<element name='vports'>
<ref name='unsignedInt'/>
</element>
</define>
<define name='capscsihost'>

View File

@ -391,7 +391,12 @@ char *virNodeDeviceDefFormat(const virNodeDeviceDefPtr def)
virBufferAddLit(&buf, " </capability>\n");
}
if (data->scsi_host.flags & VIR_NODE_DEV_CAP_FLAG_HBA_VPORT_OPS) {
virBufferAddLit(&buf, " <capability type='vport_ops' />\n");
virBufferAddLit(&buf, " <capability type='vport_ops'>\n");
virBufferAsprintf(&buf, " <max_vports>%d</max_vports>\n",
data->scsi_host.max_vports);
virBufferAsprintf(&buf, " <vports>%d</vports>\n",
data->scsi_host.vports);
virBufferAddLit(&buf, " </capability>\n");
}
break;

View File

@ -138,6 +138,8 @@ struct _virNodeDevCapsDef {
char *wwpn;
char *fabric_wwn;
unsigned int flags;
int max_vports;
int vports;
} scsi_host;
struct {
char *name;

View File

@ -40,6 +40,8 @@
int
detect_scsi_host_caps_linux(union _virNodeDevCapData *d)
{
char *max_vports = NULL;
char *vports = NULL;
int ret = -1;
VIR_DEBUG("Checking if host%d is an FC HBA", d->scsi_host.host);
@ -50,7 +52,7 @@ detect_scsi_host_caps_linux(union _virNodeDevCapData *d)
if (virReadFCHost(NULL,
d->scsi_host.host,
"port_name",
&d->scsi_host.wwpn) == -1) {
&d->scsi_host.wwpn) < 0) {
VIR_ERROR(_("Failed to read WWPN for host%d"), d->scsi_host.host);
goto cleanup;
}
@ -58,7 +60,7 @@ detect_scsi_host_caps_linux(union _virNodeDevCapData *d)
if (virReadFCHost(NULL,
d->scsi_host.host,
"node_name",
&d->scsi_host.wwnn) == -1) {
&d->scsi_host.wwnn) < 0) {
VIR_ERROR(_("Failed to read WWNN for host%d"), d->scsi_host.host);
goto cleanup;
}
@ -66,23 +68,62 @@ detect_scsi_host_caps_linux(union _virNodeDevCapData *d)
if (virReadFCHost(NULL,
d->scsi_host.host,
"fabric_name",
&d->scsi_host.fabric_wwn) == -1) {
&d->scsi_host.fabric_wwn) < 0) {
VIR_ERROR(_("Failed to read fabric WWN for host%d"),
d->scsi_host.host);
goto cleanup;
}
}
if (virIsCapableVport(NULL, d->scsi_host.host) == 0)
if (virIsCapableVport(NULL, d->scsi_host.host) == 0) {
d->scsi_host.flags |= VIR_NODE_DEV_CAP_FLAG_HBA_VPORT_OPS;
if (virReadFCHost(NULL,
d->scsi_host.max_vports,
"max_npiv_vports",
&max_vports) < 0) {
VIR_ERROR(_("Failed to read max_npiv_vports for host%d"),
d->scsi_host.host);
goto cleanup;
}
if (virReadFCHost(NULL,
d->scsi_host.max_vports,
"npiv_vports_inuse",
&vports) < 0) {
VIR_ERROR(_("Failed to read npiv_vports_inuse for host%d"),
d->scsi_host.host);
goto cleanup;
}
if (virStrToLong_i(max_vports, NULL, 10,
&d->scsi_host.max_vports) < 0) {
VIR_ERROR(_("Failed to parse value of max_npiv_vports '%s'"),
max_vports);
goto cleanup;
}
if (virStrToLong_i(vports, NULL, 10,
&d->scsi_host.vports) < 0) {
VIR_ERROR(_("Failed to parse value of npiv_vports_inuse '%s'"),
vports);
goto cleanup;
}
}
ret = 0;
cleanup:
if (ret < 0) {
/* Clear the two flags in case of producing confusing XML output */
d->scsi_host.flags &= ~(VIR_NODE_DEV_CAP_FLAG_HBA_FC_HOST |
VIR_NODE_DEV_CAP_FLAG_HBA_VPORT_OPS);
VIR_FREE(d->scsi_host.wwnn);
VIR_FREE(d->scsi_host.wwpn);
VIR_FREE(d->scsi_host.fabric_wwn);
}
VIR_FREE(max_vports);
VIR_FREE(vports);
return ret;
}