提交 5cc50ad7 编写于 作者: V Viktor Mihajlovski 提交者: Eric Blake

conf: Support for Block Device IO Limits

Introducing a new iolimits element allowing to override certain
properties of a guest block device like the physical and logical
block size.
This can be useful for platforms with 'non-standard' disk formats
like S390 DASD with its 4K block size.
Signed-off-by: NViktor Mihajlovski <mihajlov@linux.vnet.ibm.com>
上级 54e99644
......@@ -1264,6 +1264,7 @@
&lt;driver name='qemu' type='raw'/&gt;
&lt;source dev='/dev/sda'/&gt;
&lt;geometry cyls='16383' heads='16' secs='63' trans='lba'/&gt;
&lt;iolimits logical_block_size='512' physical_block_size='4096'/&gt;
&lt;target dev='hda' bus='ide'/&gt;
&lt;/disk&gt;
&lt;/devices&gt;
......@@ -1632,6 +1633,23 @@
BIOS-Translation-Modus (none, lba or auto)</dd>
</dl>
</dd>
<dt><code>iolimits</code></dt>
<dd>If present, the <code>iolimits</code> element allows
to override any of the block device properties listed below.
<span class="since">Since 0.10.2 (QEMU and KVM)</span>
<dl>
<dt><code>logical_block_size</code></dt>
<dd>The logical block size the disk will report to the guest
OS. For Linux this would be the value returned by the
BLKSSZGET ioctl and describes the smallest units for disk
I/O.
<dt><code>physical_block_size</code></dt>
<dd>The physical block size the disk will report to the guest
OS. For Linux this would be the value returned by the
BLKPBSZGET ioctl and describes the disk's hardware sector
size which can be relevant for the alignment of disk data.
</dl>
</dd>
</dl>
<h4><a name="elementsFilesystems">Filesystems</a></h4>
......
......@@ -886,6 +886,9 @@
<optional>
<ref name="geometry"/>
</optional>
<optional>
<ref name="diskIoLimits"/>
</optional>
</interleave>
</define>
<define name="snapshot">
......@@ -1110,6 +1113,20 @@
</optional>
</element>
</define>
<define name="diskIoLimits">
<element name="iolimits">
<optional>
<attribute name="logical_block_size">
<data type="integer"/>
</attribute>
</optional>
<optional>
<attribute name="physical_block_size">
<data type="integer"/>
</attribute>
</optional>
</element>
</define>
<!--
Disk may use a special driver for access.
-->
......
......@@ -3421,6 +3421,8 @@ virDomainDiskDefParseXML(virCapsPtr caps,
char *authUUID = NULL;
char *usageType = NULL;
char *tray = NULL;
char *logical_block_size = NULL;
char *physical_block_size = NULL;
if (VIR_ALLOC(def) < 0) {
virReportOOMError();
......@@ -3432,6 +3434,9 @@ virDomainDiskDefParseXML(virCapsPtr caps,
def->geometry.sectors = 0;
def->geometry.trans = VIR_DOMAIN_DISK_TRANS_DEFAULT;
def->iolimits.logical_block_size = 0;
def->iolimits.physical_block_size = 0;
ctxt->node = node;
type = virXMLPropString(node, "type");
......@@ -3570,6 +3575,27 @@ virDomainDiskDefParseXML(virCapsPtr caps,
goto error;
}
}
} else if (xmlStrEqual(cur->name, BAD_CAST "iolimits")) {
logical_block_size =
virXMLPropString(cur, "logical_block_size");
if (logical_block_size &&
virStrToLong_ui(logical_block_size, NULL, 0,
&def->iolimits.logical_block_size) < 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("invalid logical block size '%s'"),
logical_block_size);
goto error;
}
physical_block_size =
virXMLPropString(cur, "physical_block_size");
if (physical_block_size &&
virStrToLong_ui(physical_block_size, NULL, 0,
&def->iolimits.physical_block_size) < 0) {
virReportError(VIR_ERR_INTERNAL_ERROR,
_("invalid physical block size '%s'"),
physical_block_size);
goto error;
}
} else if (!driverName &&
xmlStrEqual(cur->name, BAD_CAST "driver")) {
driverName = virXMLPropString(cur, "name");
......@@ -4075,6 +4101,8 @@ cleanup:
VIR_FREE(serial);
virStorageEncryptionFree(encryption);
VIR_FREE(startupPolicy);
VIR_FREE(logical_block_size);
VIR_FREE(physical_block_size);
ctxt->node = save_ctxt;
return def;
......@@ -11341,6 +11369,26 @@ static void virDomainDiskGeometryDefFormat(virBufferPtr buf,
virBufferAddLit(buf, "/>\n");
}
}
static void virDomainDiskIolimitsDefFormat(virBufferPtr buf,
virDomainDiskDefPtr def)
{
if (def->iolimits.logical_block_size > 0 ||
def->iolimits.physical_block_size > 0) {
virBufferAddLit(buf," <iolimits");
if (def->iolimits.logical_block_size > 0) {
virBufferAsprintf(buf,
" logical_block_size='%u'",
def->iolimits.logical_block_size);
}
if (def->iolimits.physical_block_size > 0) {
virBufferAsprintf(buf,
" physical_block_size='%u'",
def->iolimits.physical_block_size);
}
virBufferAddLit(buf, "/>\n");
}
}
static int
virDomainDiskDefFormat(virBufferPtr buf,
......@@ -11514,6 +11562,7 @@ virDomainDiskDefFormat(virBufferPtr buf,
}
virDomainDiskGeometryDefFormat(buf, def);
virDomainDiskIolimitsDefFormat(buf, def);
/* For now, mirroring is currently output-only: we only output it
* for live domains, therefore we ignore it on input except for
......
......@@ -569,6 +569,11 @@ struct _virDomainDiskDef {
int trans;
} geometry;
struct {
unsigned int logical_block_size;
unsigned int physical_block_size;
} iolimits;
virDomainBlockIoTuneInfo blkdeviotune;
char *serial;
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册