mirror of
https://gitlab.com/libvirt/libvirt.git
synced 2025-01-10 23:07:44 +00:00
Allow a timezone to be specified instead of sync to host timezone
This extends the XML to allow for <clock offset='timezone' timezone='Europe/Paris'/> This is useful if the admin has not configured any timezone on the host OS, but still wants to synchronize a guest to a specific one. * src/conf/domain_conf.h, src/conf/domain_conf.c: Support extra 'timezone' attribute on clock configuration * docs/schemas/domain.rng: Add 'timezone' attribute * src/xen/xend_internal.c, src/xen/xm_internal.c: Reject configs with a configurable timezone
This commit is contained in:
parent
200c83b29d
commit
e4d7433ef0
@ -304,6 +304,16 @@
|
|||||||
<attribute name="offset">
|
<attribute name="offset">
|
||||||
<value>utc</value>
|
<value>utc</value>
|
||||||
</attribute>
|
</attribute>
|
||||||
|
<group>
|
||||||
|
<attribute name="offset">
|
||||||
|
<value>timezone</value>
|
||||||
|
</attribute>
|
||||||
|
<optional>
|
||||||
|
<attribute name="timezone">
|
||||||
|
<ref name="timeZone"/>
|
||||||
|
</attribute>
|
||||||
|
</optional>
|
||||||
|
</group>
|
||||||
<group>
|
<group>
|
||||||
<attribute name="offset">
|
<attribute name="offset">
|
||||||
<value>variable</value>
|
<value>variable</value>
|
||||||
@ -1633,4 +1643,9 @@
|
|||||||
<param name="pattern">(-|\+)?[0-9]+</param>
|
<param name="pattern">(-|\+)?[0-9]+</param>
|
||||||
</data>
|
</data>
|
||||||
</define>
|
</define>
|
||||||
|
<define name="timeZone">
|
||||||
|
<data type="string">
|
||||||
|
<param name="pattern">[a-zA-Z0-9_\.\+\-/]+</param>
|
||||||
|
</data>
|
||||||
|
</define>
|
||||||
</grammar>
|
</grammar>
|
||||||
|
@ -235,7 +235,8 @@ VIR_ENUM_IMPL(virDomainNetdevMacvtap, VIR_DOMAIN_NETDEV_MACVTAP_MODE_LAST,
|
|||||||
VIR_ENUM_IMPL(virDomainClockOffset, VIR_DOMAIN_CLOCK_OFFSET_LAST,
|
VIR_ENUM_IMPL(virDomainClockOffset, VIR_DOMAIN_CLOCK_OFFSET_LAST,
|
||||||
"utc",
|
"utc",
|
||||||
"localtime",
|
"localtime",
|
||||||
"variable");
|
"variable",
|
||||||
|
"timezone");
|
||||||
|
|
||||||
#define virDomainReportError(code, fmt...) \
|
#define virDomainReportError(code, fmt...) \
|
||||||
virReportErrorHelper(NULL, VIR_FROM_DOMAIN, code, __FILE__, \
|
virReportErrorHelper(NULL, VIR_FROM_DOMAIN, code, __FILE__, \
|
||||||
@ -657,6 +658,9 @@ void virDomainDefFree(virDomainDefPtr def)
|
|||||||
VIR_FREE(def->os.bootloader);
|
VIR_FREE(def->os.bootloader);
|
||||||
VIR_FREE(def->os.bootloaderArgs);
|
VIR_FREE(def->os.bootloaderArgs);
|
||||||
|
|
||||||
|
if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_TIMEZONE)
|
||||||
|
VIR_FREE(def->clock.data.timezone);
|
||||||
|
|
||||||
VIR_FREE(def->name);
|
VIR_FREE(def->name);
|
||||||
VIR_FREE(def->cpumask);
|
VIR_FREE(def->cpumask);
|
||||||
VIR_FREE(def->emulator);
|
VIR_FREE(def->emulator);
|
||||||
@ -3584,8 +3588,17 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps,
|
|||||||
switch (def->clock.offset) {
|
switch (def->clock.offset) {
|
||||||
case VIR_DOMAIN_CLOCK_OFFSET_VARIABLE:
|
case VIR_DOMAIN_CLOCK_OFFSET_VARIABLE:
|
||||||
if (virXPathLongLong("number(./clock/@adjustment)", ctxt,
|
if (virXPathLongLong("number(./clock/@adjustment)", ctxt,
|
||||||
&def->clock.adjustment) < 0)
|
&def->clock.data.adjustment) < 0)
|
||||||
def->clock.adjustment = 0;
|
def->clock.data.adjustment = 0;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case VIR_DOMAIN_CLOCK_OFFSET_TIMEZONE:
|
||||||
|
def->clock.data.timezone = virXPathString("string(./clock/@timezone)", ctxt);
|
||||||
|
if (!def->clock.data.timezone) {
|
||||||
|
virDomainReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||||
|
_("missing 'timezone' attribute for clock with offset='timezone'"));
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5547,7 +5560,10 @@ char *virDomainDefFormat(virDomainDefPtr def,
|
|||||||
virDomainClockOffsetTypeToString(def->clock.offset));
|
virDomainClockOffsetTypeToString(def->clock.offset));
|
||||||
switch (def->clock.offset) {
|
switch (def->clock.offset) {
|
||||||
case VIR_DOMAIN_CLOCK_OFFSET_VARIABLE:
|
case VIR_DOMAIN_CLOCK_OFFSET_VARIABLE:
|
||||||
virBufferVSprintf(&buf, " adjustment='%lld'", def->clock.adjustment);
|
virBufferVSprintf(&buf, " adjustment='%lld'", def->clock.data.adjustment);
|
||||||
|
break;
|
||||||
|
case VIR_DOMAIN_CLOCK_OFFSET_TIMEZONE:
|
||||||
|
virBufferEscapeString(&buf, " timezone='%s'", def->clock.data.timezone);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
virBufferAddLit(&buf, "/>\n");
|
virBufferAddLit(&buf, "/>\n");
|
||||||
|
@ -635,6 +635,7 @@ enum virDomainClockOffsetType {
|
|||||||
VIR_DOMAIN_CLOCK_OFFSET_UTC = 0,
|
VIR_DOMAIN_CLOCK_OFFSET_UTC = 0,
|
||||||
VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME = 1,
|
VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME = 1,
|
||||||
VIR_DOMAIN_CLOCK_OFFSET_VARIABLE = 2,
|
VIR_DOMAIN_CLOCK_OFFSET_VARIABLE = 2,
|
||||||
|
VIR_DOMAIN_CLOCK_OFFSET_TIMEZONE = 3,
|
||||||
|
|
||||||
VIR_DOMAIN_CLOCK_OFFSET_LAST,
|
VIR_DOMAIN_CLOCK_OFFSET_LAST,
|
||||||
};
|
};
|
||||||
@ -644,9 +645,15 @@ typedef virDomainClockDef *virDomainClockDefPtr;
|
|||||||
struct _virDomainClockDef {
|
struct _virDomainClockDef {
|
||||||
int offset;
|
int offset;
|
||||||
|
|
||||||
/* Adjustment in seconds, relative to UTC, when
|
union {
|
||||||
* offset == VIR_DOMAIN_CLOCK_OFFSET_VARIABLE */
|
/* Adjustment in seconds, relative to UTC, when
|
||||||
long long adjustment;
|
* offset == VIR_DOMAIN_CLOCK_OFFSET_VARIABLE */
|
||||||
|
long long adjustment;
|
||||||
|
|
||||||
|
/* Timezone name, when
|
||||||
|
* offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME */
|
||||||
|
char *timezone;
|
||||||
|
} data;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define VIR_DOMAIN_CPUMASK_LEN 1024
|
#define VIR_DOMAIN_CPUMASK_LEN 1024
|
||||||
|
@ -5846,9 +5846,15 @@ xenDaemonFormatSxpr(virConnectPtr conn,
|
|||||||
virBufferVSprintf(&buf, "(on_crash '%s')", tmp);
|
virBufferVSprintf(&buf, "(on_crash '%s')", tmp);
|
||||||
|
|
||||||
/* Set localtime here for current XenD (both PV & HVM) */
|
/* Set localtime here for current XenD (both PV & HVM) */
|
||||||
if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME)
|
if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME) {
|
||||||
|
if (def->clock.data.timezone) {
|
||||||
|
virXendError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
||||||
|
_("configurable timezones are not supported"));
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
|
|
||||||
virBufferAddLit(&buf, "(localtime 1)");
|
virBufferAddLit(&buf, "(localtime 1)");
|
||||||
else if (def->clock.offset != VIR_DOMAIN_CLOCK_OFFSET_UTC) {
|
} else if (def->clock.offset != VIR_DOMAIN_CLOCK_OFFSET_UTC) {
|
||||||
virXendError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
virXendError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
||||||
_("unsupported clock offset '%s'"),
|
_("unsupported clock offset '%s'"),
|
||||||
virDomainClockOffsetTypeToString(def->clock.offset));
|
virDomainClockOffsetTypeToString(def->clock.offset));
|
||||||
|
@ -2328,13 +2328,20 @@ virConfPtr xenXMDomainConfigFormat(virConnectPtr conn,
|
|||||||
goto no_memory;
|
goto no_memory;
|
||||||
|
|
||||||
|
|
||||||
if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME ||
|
if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME) {
|
||||||
def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_UTC) {
|
if (def->clock.data.timezone) {
|
||||||
if (xenXMConfigSetInt(conf, "localtime",
|
xenXMError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
||||||
def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_LOCALTIME ?
|
_("configurable timezones are not supported"));
|
||||||
1 : 0) < 0)
|
goto cleanup;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (xenXMConfigSetInt(conf, "localtime", 1) < 0)
|
||||||
|
goto no_memory;
|
||||||
|
} else if (def->clock.offset == VIR_DOMAIN_CLOCK_OFFSET_UTC) {
|
||||||
|
if (xenXMConfigSetInt(conf, "localtime", 0) < 0)
|
||||||
goto no_memory;
|
goto no_memory;
|
||||||
} else {
|
} else {
|
||||||
|
/* XXX We could support Xen's rtc clock offset */
|
||||||
xenXMError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
xenXMError(conn, VIR_ERR_CONFIG_UNSUPPORTED,
|
||||||
_("unsupported clock offset '%s'"),
|
_("unsupported clock offset '%s'"),
|
||||||
virDomainClockOffsetTypeToString(def->clock.offset));
|
virDomainClockOffsetTypeToString(def->clock.offset));
|
||||||
|
Loading…
Reference in New Issue
Block a user