Compare commits
340 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 44dd796f94 | |||
| a72fbea0f8 | |||
| 61b23fb997 | |||
| 7536fa7aac | |||
| 4b1ddcd058 | |||
| 440decb498 | |||
| 9d7f31c7fb | |||
| 6aafc18452 | |||
| 7d77bf76aa | |||
| 7f0f1b831e | |||
| d964be0097 | |||
| a2479f539e | |||
| c2c89ec6a3 | |||
| d61e2404ba | |||
| a2be167dfe | |||
| 15ca09e1da | |||
| 2cc07e6366 | |||
| 4dd4fe78a4 | |||
| 0bc22fb6f7 | |||
| 76097a6961 | |||
| 98cbf39fd3 | |||
| d670e246d0 | |||
| 50e7b9a91d | |||
| 5cbc0451ce | |||
| b420054636 | |||
| 143fedee46 | |||
| 88887cac0f | |||
| 579afc99f2 | |||
| 7f5808b9d0 | |||
| 4df5f77071 | |||
| 1bdd527daf | |||
| e5fa1c00d2 | |||
| 18f7b8c79c | |||
| 782468f8e9 | |||
| 202e7d9569 | |||
| 0676a07265 | |||
| f57ce74947 | |||
| 851cfde15b | |||
| 06123137eb | |||
| 6ccf3cb58c | |||
| 030ddaa4ef | |||
| a8886736c4 | |||
| 4fd635e537 | |||
| 6210c457fc | |||
| 82926cfdf0 | |||
| e7a3ca6f6b | |||
| 1ae6f647b7 | |||
| 48941c011f | |||
| a3c4cc6f3d | |||
| 90fbcbd48f | |||
| 6efd96d995 | |||
| 21316e7a45 | |||
| 8adbb7a402 | |||
| 3f19d41908 | |||
| 34da93e0c9 | |||
| 208f506190 | |||
| 0ca715cad9 | |||
| 0f5d8c1c22 | |||
| a56bcbd063 | |||
| 89c3fa751c | |||
| 051644ffcb | |||
| 2a9c282548 | |||
| 2ae80af461 | |||
| 7335ede0e1 | |||
| 6c92ba3805 | |||
| 446f680673 | |||
| 3f56aa2870 | |||
| 3cec91694f | |||
| cb0cfa566f | |||
| a27acebf66 | |||
| 99d3a0ca1a | |||
| 9c962ebc4f | |||
| 99cbbf6606 | |||
| b73e509648 | |||
| b23ff9c0f7 | |||
| 20f9ed9c4c | |||
| 04cb28c315 | |||
| a74ea318d1 | |||
| 98ed6b4e36 | |||
| 2c49d1fd11 | |||
| 6e7bca6631 | |||
| 2fe145bb02 | |||
| 10b7d235e3 | |||
| 232e2e7de2 | |||
| fb1e4b061e | |||
| 0b1a013081 | |||
| a972457f43 | |||
| 67cfa34a05 | |||
| fc2ebb7646 | |||
| e92b461b4f | |||
| b1ac7b5791 | |||
| 88424efe85 | |||
| 4e2aab98a2 | |||
| f4bc1a2fe2 | |||
| a4bf2768b8 | |||
| 47cd44e9da | |||
| 731c6b90ff | |||
| 47ca46905d | |||
| 860ffc5b13 | |||
| 611b2ee520 | |||
| edcb926f9d | |||
| caebff8304 | |||
| 8fa41135ca | |||
| 0debbff964 | |||
| d6cc78be66 | |||
| 8d9645735e | |||
| 4c65f08330 | |||
| 2427f8f078 | |||
| d168e4f934 | |||
| 4dd365589f | |||
| 50e253df29 | |||
| cb71801a2b | |||
| 4a9c74e91d | |||
| 281508ec99 | |||
| feb92626e1 | |||
| 93cadb0880 | |||
| dd6b57aa60 | |||
| b8cb754e9d | |||
| dbe61507bd | |||
| ce7b23d9d0 | |||
| 8ded6ff93e | |||
| 1ef96f3488 | |||
| ee3bf37900 | |||
| 7452a06938 | |||
| fe8f9ed9c4 | |||
| 1b64f74c82 | |||
| c81949046d | |||
| 19dcb913e6 | |||
| e4b5ba1a9d | |||
| 5f1a422d83 | |||
| c5b0b3ef9d | |||
| c0a04cb876 | |||
| 3cc7cdf12f | |||
| 6b531d9967 | |||
| 4d05ac021c | |||
| d29aa84b17 | |||
| a075adc818 | |||
| 4d0e63f99c | |||
| 9e11936ec5 | |||
| a4075ec632 | |||
| dadb59c95f | |||
| e73cc6a9d8 | |||
| 10cd84e37f | |||
| e63e2040cd | |||
| 91063332d7 | |||
| 503330ba5d | |||
| 0a64085f47 | |||
| 1073e2447a | |||
| 5b1a906ace | |||
| aff97e0146 | |||
| a4b41a378b | |||
| 3ec523d168 | |||
| 622cf0d642 | |||
| a540751e83 | |||
| 11b596669a | |||
| fefbae879b | |||
| 695b281409 | |||
| 9f9eae34c1 | |||
| ae37ed3500 | |||
| f7f509999b | |||
| 419bcc4b2f | |||
| 7b59d4f7eb | |||
| 03326e9c04 | |||
| f40b464d1e | |||
| 810ca6c207 | |||
| 8df3aef6aa | |||
| 0223d5a656 | |||
| aad810a204 | |||
| 1b8b7567b1 | |||
| 442040caac | |||
| 65efaafca2 | |||
| e87c8ab0c7 | |||
| be6bda45b4 | |||
| 8c9e40d383 | |||
| 0f6f9b973a | |||
| 3db6039b2b | |||
| 4051217c8b | |||
| c5c28baba1 | |||
| 43618df1d4 | |||
| a2951dccb5 | |||
| b884323c03 | |||
| adeaf839fd | |||
| 40d99010e1 | |||
| 11755d8663 | |||
| 2daa92daf9 | |||
| db2858c661 | |||
| 53adb9aaba | |||
| 168df8b606 | |||
| f9085f2538 | |||
| b159bbdc98 | |||
| a5af3cf105 | |||
| 27ca069db7 | |||
| 000a3274d2 | |||
| 19c7799c31 | |||
| 198ff818c6 | |||
| e80c83ad06 | |||
| 660e0112c6 | |||
| 45c1cabef6 | |||
| 56be2c5e38 | |||
| 4aa9c4f1a3 | |||
| 7be420ad22 | |||
| 40b00623a4 | |||
| ce09ec66c7 | |||
| 97d7c80e2e | |||
| b856ae03bf | |||
| 803b3b891a | |||
| 350081d1a9 | |||
| 1b71b68bb9 | |||
| 4084288dd5 | |||
| d1cd1b7ceb | |||
| 5ed69704b9 | |||
| be6e136cb1 | |||
| d3109abfa4 | |||
| f5ff4a2393 | |||
| 8cc50838dc | |||
| 2c2e71c0ce | |||
| 96b1b18b42 | |||
| f7763bfd17 | |||
| 404e58cb18 | |||
| cd3767e3b9 | |||
| f1867a5ecc | |||
| b5548f62cb | |||
| 52f3bedee7 | |||
| f87237919c | |||
| e8969fb913 | |||
| 74d46bc7dd | |||
| 4b6ea94306 | |||
| 963754bc8c | |||
| 7b5483236c | |||
| 438006407c | |||
| 76c8282ee2 | |||
| f463598b24 | |||
| f4e752a385 | |||
| c37cb21dea | |||
| e0bfc1f8aa | |||
| 544ad4a787 | |||
| 8f163760ed | |||
| 565427cf89 | |||
| e10da2f6d4 | |||
| aa386576d5 | |||
| c73c129b48 | |||
| afe729ac3c | |||
| b6038bae4f | |||
| e6d9787587 | |||
| 44699dc495 | |||
| 991d719dde | |||
| 96a520b555 | |||
| e31df5e9de | |||
| 6763b267b9 | |||
| 24e91208a4 | |||
| 15dec999e7 | |||
| d6b0635d3d | |||
| 336a93264e | |||
| 6398d1cff5 | |||
| 6926ed26ea | |||
| 6253f97a2d | |||
| 37ddbd0eac | |||
| 95fe7c8df2 | |||
| 79ae809020 | |||
| f19e302ba9 | |||
| e9c1d3f4b0 | |||
| 0f577d932b | |||
| 21a02c2e90 | |||
| 4e460d5f09 | |||
| f9de2f6bc6 | |||
| 2daa1b7814 | |||
| f99eeb8567 | |||
| 7069f75cb8 | |||
| 2cac7dac46 | |||
| 913c3c6554 | |||
| a5a4c0c89b | |||
| 8c8aca2fab | |||
| daf8e124ca | |||
| 38c4b724fe | |||
| 4d00487275 | |||
| a6831c26c1 | |||
| c363c7ebdb | |||
| 18ee6daf8a | |||
| 459eb426c3 | |||
| a0d670d2bf | |||
| d7b41212c1 | |||
| 2e1539eba4 | |||
| ee9521d87c | |||
| 8d8fc08bac | |||
| e79d304c79 | |||
| db03f03fd9 | |||
| 957403ebec | |||
| 6c32e1aaeb | |||
| 362e335c0b | |||
| ed6c49f874 | |||
| 47fcec5405 | |||
| d7239a45b6 | |||
| f13fb18c58 | |||
| d29644418d | |||
| ed9e426b26 | |||
| 659febf9ff | |||
| fca1fccfad | |||
| f713d63bab | |||
| 5a45e466cf | |||
| 742b24eb23 | |||
| 03369d2383 | |||
| 2605d662e0 | |||
| e8394ab5b5 | |||
| 8ad156a5c2 | |||
| f2d6fb6239 | |||
| e3a592c38d | |||
| 7e99819dda | |||
| a160d7f98d | |||
| 36cab842e8 | |||
| 7b7b86e327 | |||
| f4bfe638b6 | |||
| 0e9d242f05 | |||
| e24467a8c2 | |||
| b39c370a76 | |||
| 62e4e7cde2 | |||
| f822179f97 | |||
| 47e7e1e548 | |||
| e73b75314b | |||
| 8193a55b4a | |||
| 6036708fa2 | |||
| 4717aa0b6d | |||
| 97ae25ea7d | |||
| 6470ed033b | |||
| b550f9c1d5 | |||
| ee0273ffc3 | |||
| 50fce74b00 | |||
| e29f71d1c9 | |||
| 427ed20801 | |||
| d23e6c285b | |||
| 2c139b45d8 | |||
| 762435e3b7 | |||
| 6383d6b056 | |||
| 3712441ea6 | |||
| 9d0bc882fa | |||
| 90dddf3d3d | |||
| 86abd54d02 | |||
| 4ab5ad5425 | |||
| f9c1b758c3 | |||
| 38cf1bd5ba | |||
| aeda455930 |
-13
@@ -1,13 +0,0 @@
|
||||
.build*.log
|
||||
*.rpm
|
||||
i686
|
||||
x86_64
|
||||
libvirt-*.tar.gz
|
||||
libvirt-0.6.0.tar.gz
|
||||
libvirt-0.6.1.tar.gz
|
||||
libvirt-0.6.2.tar.gz
|
||||
libvirt-0.6.3.tar.gz
|
||||
libvirt-0.6.4.tar.gz
|
||||
libvirt-0.6.5.tar.gz
|
||||
libvirt-0.7.0.tar.gz
|
||||
libvirt-0.7.1.tar.gz
|
||||
@@ -0,0 +1,5 @@
|
||||
.build*.log
|
||||
*.rpm
|
||||
i686
|
||||
x86_64
|
||||
libvirt-*.tar.xz
|
||||
@@ -0,0 +1,31 @@
|
||||
From: Erik Skultety <eskultet@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:09 +0200
|
||||
Subject: [PATCH] src: security: Replace bitwise OR with logical OR
|
||||
|
||||
Typo introduced by commit d73f3f58360.
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1738483
|
||||
|
||||
Signed-off-by: Erik Skultety <eskultet@redhat.com>
|
||||
(cherry picked from commit 5801ef06ec29fdbac6718e455015450f7c243c1b)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740024
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_util.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/security/security_util.c b/src/security/security_util.c
|
||||
index ad265b0bc5..9d3f483f6b 100644
|
||||
--- a/src/security/security_util.c
|
||||
+++ b/src/security/security_util.c
|
||||
@@ -268,7 +268,7 @@ virSecurityMoveRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) attr_value = NULL;
|
||||
|
||||
- if (!(ref_name = virSecurityGetRefCountAttrName(name)) |
|
||||
+ if (!(ref_name = virSecurityGetRefCountAttrName(name)) ||
|
||||
!(attr_name = virSecurityGetAttrName(name)))
|
||||
return -1;
|
||||
|
||||
@@ -0,0 +1,176 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:10 +0200
|
||||
Subject: [PATCH] security_util: Use more VIR_AUTOFREE()
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit 8ced0909e5a0c41a44c2110d7060f6518b65f0db)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740024
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_util.c | 78 +++++++++++++++---------------------
|
||||
1 file changed, 32 insertions(+), 46 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_util.c b/src/security/security_util.c
|
||||
index 9d3f483f6b..04347f51e5 100644
|
||||
--- a/src/security/security_util.c
|
||||
+++ b/src/security/security_util.c
|
||||
@@ -113,34 +113,32 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
const char *path,
|
||||
char **label)
|
||||
{
|
||||
- char *ref_name = NULL;
|
||||
- char *attr_name = NULL;
|
||||
- char *value = NULL;
|
||||
+ VIR_AUTOFREE(char *) ref_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
- int ret = -1;
|
||||
|
||||
*label = NULL;
|
||||
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileGetXAttrQuiet(path, ref_name, &value) < 0) {
|
||||
- if (errno == ENOSYS || errno == ENODATA || errno == ENOTSUP) {
|
||||
- ret = -2;
|
||||
- } else {
|
||||
- virReportSystemError(errno,
|
||||
- _("Unable to get XATTR %s on %s"),
|
||||
- ref_name,
|
||||
- path);
|
||||
- }
|
||||
- goto cleanup;
|
||||
+ if (errno == ENOSYS || errno == ENODATA || errno == ENOTSUP)
|
||||
+ return -2;
|
||||
+
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Unable to get XATTR %s on %s"),
|
||||
+ ref_name,
|
||||
+ path);
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
if (virStrToLong_ui(value, NULL, 10, &refcount) < 0) {
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
_("malformed refcount %s on %s"),
|
||||
value, path);
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
VIR_FREE(value);
|
||||
@@ -149,30 +147,25 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
|
||||
if (refcount > 0) {
|
||||
if (virAsprintf(&value, "%u", refcount) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileSetXAttr(path, ref_name, value) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
} else {
|
||||
if (virFileRemoveXAttr(path, ref_name) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (!(attr_name = virSecurityGetAttrName(name)))
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileGetXAttr(path, attr_name, label) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileRemoveXAttr(path, attr_name) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
- ret = 0;
|
||||
- cleanup:
|
||||
- VIR_FREE(value);
|
||||
- VIR_FREE(attr_name);
|
||||
- VIR_FREE(ref_name);
|
||||
- return ret;
|
||||
+ return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -201,25 +194,23 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
const char *path,
|
||||
const char *label)
|
||||
{
|
||||
- char *ref_name = NULL;
|
||||
- char *attr_name = NULL;
|
||||
- char *value = NULL;
|
||||
+ VIR_AUTOFREE(char *) ref_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
- int ret = -1;
|
||||
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileGetXAttrQuiet(path, ref_name, &value) < 0) {
|
||||
if (errno == ENOSYS || errno == ENOTSUP) {
|
||||
- ret = -2;
|
||||
- goto cleanup;
|
||||
+ return -2;
|
||||
} else if (errno != ENODATA) {
|
||||
virReportSystemError(errno,
|
||||
_("Unable to get XATTR %s on %s"),
|
||||
ref_name,
|
||||
path);
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -228,7 +219,7 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
_("malformed refcount %s on %s"),
|
||||
value, path);
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
VIR_FREE(value);
|
||||
@@ -237,24 +228,19 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
|
||||
if (refcount == 1) {
|
||||
if (!(attr_name = virSecurityGetAttrName(name)))
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileSetXAttr(path, attr_name, label) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
if (virAsprintf(&value, "%u", refcount) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
if (virFileSetXAttr(path, ref_name, value) < 0)
|
||||
- goto cleanup;
|
||||
+ return -1;
|
||||
|
||||
- ret = refcount;
|
||||
- cleanup:
|
||||
- VIR_FREE(value);
|
||||
- VIR_FREE(attr_name);
|
||||
- VIR_FREE(ref_name);
|
||||
- return ret;
|
||||
+ return refcount;
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:11 +0200
|
||||
Subject: [PATCH] security_util: Document virSecurityMoveRememberedLabel
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit 359c7c1e94e0c54bf7e7a5a8365f066904b4387b)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740024
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_util.c | 13 +++++++++++++
|
||||
1 file changed, 13 insertions(+)
|
||||
|
||||
diff --git a/src/security/security_util.c b/src/security/security_util.c
|
||||
index 04347f51e5..365b2dd2d6 100644
|
||||
--- a/src/security/security_util.c
|
||||
+++ b/src/security/security_util.c
|
||||
@@ -244,6 +244,19 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
}
|
||||
|
||||
|
||||
+/**
|
||||
+ * virSecurityMoveRememberedLabel:
|
||||
+ * @name: security driver name
|
||||
+ * @src: source file
|
||||
+ * @dst: destination file
|
||||
+ *
|
||||
+ * For given security driver @name, move all XATTRs related to seclabel
|
||||
+ * remembering from @src to @dst. However, if @dst is NULL, then XATTRs
|
||||
+ * are just removed from @src.
|
||||
+ *
|
||||
+ * Returns: 0 on success,
|
||||
+ * -1 otherwise.
|
||||
+ */
|
||||
int
|
||||
virSecurityMoveRememberedLabel(const char *name,
|
||||
const char *src,
|
||||
@@ -0,0 +1,164 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:12 +0200
|
||||
Subject: [PATCH] security: Don't increase XATTRs refcounter on failure
|
||||
|
||||
If user has two domains, each have the same disk (configured for
|
||||
RW) but each runs with different seclabel then we deny start of
|
||||
the second domain because in order to do that we would need to
|
||||
relabel the disk but that would cut the first domain off. Even if
|
||||
we did not do that, qemu would fail to start because it would be
|
||||
unable to lock the disk image for the second time. So far, this
|
||||
behaviour is expected. But what is not expected is that we
|
||||
increase the refcounter in XATTRs and leave it like that.
|
||||
|
||||
What happens is that when the second domain starts,
|
||||
virSecuritySetRememberedLabel() is called, and since there are
|
||||
XATTRs from the first domain it increments the refcounter and
|
||||
returns it (refcounter == 2 at this point). Then callers
|
||||
(virSecurityDACSetOwnership() and
|
||||
virSecuritySELinuxSetFileconHelper()) realize that refcounter is
|
||||
greater than 1 and desired seclabel doesn't match the one the
|
||||
disk image already has and an error is produced. But the
|
||||
refcounter is never decremented.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740024
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit 6a2806fd549c0bfdcb3eb83f130ee99ea8d213e1)
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_dac.c | 41 ++++++++++++++++++---------------
|
||||
src/security/security_selinux.c | 18 ++++++++++-----
|
||||
2 files changed, 34 insertions(+), 25 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_dac.c b/src/security/security_dac.c
|
||||
index 137daf5d28..4b4afef18a 100644
|
||||
--- a/src/security/security_dac.c
|
||||
+++ b/src/security/security_dac.c
|
||||
@@ -751,6 +751,7 @@ virSecurityDACSetOwnership(virSecurityManagerPtr mgr,
|
||||
bool remember)
|
||||
{
|
||||
virSecurityDACDataPtr priv = virSecurityManagerGetPrivateData(mgr);
|
||||
+ virErrorPtr origerr;
|
||||
struct stat sb;
|
||||
int refcount;
|
||||
int rc;
|
||||
@@ -784,12 +785,13 @@ virSecurityDACSetOwnership(virSecurityManagerPtr mgr,
|
||||
* is @refcount domains using the @path. Do not
|
||||
* change the label (as it would almost certainly
|
||||
* cause the other domains to lose access to the
|
||||
- * @path). */
|
||||
+ * @path). However, the refcounter was incremented in
|
||||
+ * XATTRs so decrease it. */
|
||||
if (sb.st_uid != uid || sb.st_gid != gid) {
|
||||
virReportError(VIR_ERR_OPERATION_INVALID,
|
||||
_("Setting different DAC user or group on %s "
|
||||
"which is already in use"), path);
|
||||
- return -1;
|
||||
+ goto error;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -797,25 +799,26 @@ virSecurityDACSetOwnership(virSecurityManagerPtr mgr,
|
||||
VIR_INFO("Setting DAC user and group on '%s' to '%ld:%ld'",
|
||||
NULLSTR(src ? src->path : path), (long)uid, (long)gid);
|
||||
|
||||
- if (virSecurityDACSetOwnershipInternal(priv, src, path, uid, gid) < 0) {
|
||||
- virErrorPtr origerr;
|
||||
-
|
||||
- virErrorPreserveLast(&origerr);
|
||||
- /* Try to restore the label. This is done so that XATTRs
|
||||
- * are left in the same state as when the control entered
|
||||
- * this function. However, if our attempt fails, there's
|
||||
- * not much we can do. XATTRs refcounting is fubar'ed and
|
||||
- * the only option we have is warn users. */
|
||||
- if (virSecurityDACRestoreFileLabelInternal(mgr, src, path, remember) < 0)
|
||||
- VIR_WARN("Unable to restore label on '%s'. "
|
||||
- "XATTRs might have been left in inconsistent state.",
|
||||
- NULLSTR(src ? src->path : path));
|
||||
-
|
||||
- virErrorRestore(&origerr);
|
||||
- return -1;
|
||||
- }
|
||||
+ if (virSecurityDACSetOwnershipInternal(priv, src, path, uid, gid) < 0)
|
||||
+ goto error;
|
||||
|
||||
return 0;
|
||||
+
|
||||
+ error:
|
||||
+ virErrorPreserveLast(&origerr);
|
||||
+ /* Try to restore the label. This is done so that XATTRs
|
||||
+ * are left in the same state as when the control entered
|
||||
+ * this function. However, if our attempt fails, there's
|
||||
+ * not much we can do. XATTRs refcounting is fubar'ed and
|
||||
+ * the only option we have is warn users. */
|
||||
+ if (virSecurityDACRestoreFileLabelInternal(mgr, src, path, remember) < 0)
|
||||
+ VIR_WARN("Unable to restore label on '%s'. "
|
||||
+ "XATTRs might have been left in inconsistent state.",
|
||||
+ NULLSTR(src ? src->path : path));
|
||||
+
|
||||
+ virErrorRestore(&origerr);
|
||||
+
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index ea20373a90..9857223bbf 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -1334,6 +1334,7 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
security_context_t econ = NULL;
|
||||
int refcount;
|
||||
int rc;
|
||||
+ bool rollback = false;
|
||||
int ret = -1;
|
||||
|
||||
if ((rc = virSecuritySELinuxTransactionAppend(path, tcon,
|
||||
@@ -1353,6 +1354,8 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
|
||||
if (econ) {
|
||||
refcount = virSecuritySELinuxRememberLabel(path, econ);
|
||||
+ if (refcount > 0)
|
||||
+ rollback = true;
|
||||
if (refcount == -2) {
|
||||
/* Not supported. Don't error though. */
|
||||
} else if (refcount < 0) {
|
||||
@@ -1362,7 +1365,8 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
* is @refcount domains using the @path. Do not
|
||||
* change the label (as it would almost certainly
|
||||
* cause the other domains to lose access to the
|
||||
- * @path). */
|
||||
+ * @path). However, the refcounter was
|
||||
+ * incremented in XATTRs so decrease it. */
|
||||
if (STRNEQ(econ, tcon)) {
|
||||
virReportError(VIR_ERR_OPERATION_INVALID,
|
||||
_("Setting different SELinux label on %s "
|
||||
@@ -1373,7 +1377,12 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
}
|
||||
}
|
||||
|
||||
- if (virSecuritySELinuxSetFileconImpl(path, tcon, optional, privileged) < 0) {
|
||||
+ if (virSecuritySELinuxSetFileconImpl(path, tcon, optional, privileged) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ ret = 0;
|
||||
+ cleanup:
|
||||
+ if (ret < 0 && rollback) {
|
||||
virErrorPtr origerr;
|
||||
|
||||
virErrorPreserveLast(&origerr);
|
||||
@@ -1388,11 +1397,8 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
path);
|
||||
|
||||
virErrorRestore(&origerr);
|
||||
- goto cleanup;
|
||||
- }
|
||||
|
||||
- ret = 0;
|
||||
- cleanup:
|
||||
+ }
|
||||
freecon(econ);
|
||||
return ret;
|
||||
}
|
||||
@@ -0,0 +1,183 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:13 +0200
|
||||
Subject: [PATCH] util: Introduce virhostuptime
|
||||
|
||||
This module contains function to get host boot time.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit 8b802f13cb47817706cba101f5d52e2c8957698d)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741140
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
configure.ac | 1 +
|
||||
src/libvirt_private.syms | 4 ++
|
||||
src/util/Makefile.inc.am | 2 +
|
||||
src/util/virhostuptime.c | 81 ++++++++++++++++++++++++++++++++++++++++
|
||||
src/util/virhostuptime.h | 27 ++++++++++++++
|
||||
5 files changed, 115 insertions(+)
|
||||
create mode 100644 src/util/virhostuptime.c
|
||||
create mode 100644 src/util/virhostuptime.h
|
||||
|
||||
diff --git a/configure.ac b/configure.ac
|
||||
index d18d427695..771dd961a5 100644
|
||||
--- a/configure.ac
|
||||
+++ b/configure.ac
|
||||
@@ -337,6 +337,7 @@ AC_CHECK_FUNCS_ONCE([\
|
||||
getpwuid_r \
|
||||
getrlimit \
|
||||
getuid \
|
||||
+ getutxid \
|
||||
if_indextoname \
|
||||
mmap \
|
||||
newlocale \
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index c323f679b3..9fd778272f 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -2135,6 +2135,10 @@ virHostMemGetStats;
|
||||
virHostMemSetParameters;
|
||||
|
||||
|
||||
+# util/virhostuptime.h
|
||||
+virHostGetBootTime;
|
||||
+
|
||||
+
|
||||
# util/viridentity.h
|
||||
virIdentityGetAttr;
|
||||
virIdentityGetCurrent;
|
||||
diff --git a/src/util/Makefile.inc.am b/src/util/Makefile.inc.am
|
||||
index a47f333a98..46866cf213 100644
|
||||
--- a/src/util/Makefile.inc.am
|
||||
+++ b/src/util/Makefile.inc.am
|
||||
@@ -91,6 +91,8 @@ UTIL_SOURCES = \
|
||||
util/virhostdev.h \
|
||||
util/virhostmem.c \
|
||||
util/virhostmem.h \
|
||||
+ util/virhostuptime.c \
|
||||
+ util/virhostuptime.h \
|
||||
util/viridentity.c \
|
||||
util/viridentity.h \
|
||||
util/virinitctl.c \
|
||||
diff --git a/src/util/virhostuptime.c b/src/util/virhostuptime.c
|
||||
new file mode 100644
|
||||
index 0000000000..62b781acd5
|
||||
--- /dev/null
|
||||
+++ b/src/util/virhostuptime.c
|
||||
@@ -0,0 +1,81 @@
|
||||
+/*
|
||||
+ * virhostuptime.c: helper APIs for host uptime
|
||||
+ *
|
||||
+ * Copyright (C) 2019 Red Hat, Inc.
|
||||
+ *
|
||||
+ * This library is free software; you can redistribute it and/or
|
||||
+ * modify it under the terms of the GNU Lesser General Public
|
||||
+ * License as published by the Free Software Foundation; either
|
||||
+ * version 2.1 of the License, or (at your option) any later version.
|
||||
+ *
|
||||
+ * This library is distributed in the hope that it will be useful,
|
||||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
+ * Lesser General Public License for more details.
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU Lesser General Public
|
||||
+ * License along with this library. If not, see
|
||||
+ * <http://www.gnu.org/licenses/>.
|
||||
+ */
|
||||
+
|
||||
+#include <config.h>
|
||||
+
|
||||
+#ifdef HAVE_GETUTXID
|
||||
+# include <utmpx.h>
|
||||
+#endif
|
||||
+
|
||||
+#include "virhostuptime.h"
|
||||
+#include "virthread.h"
|
||||
+
|
||||
+static unsigned long long bootTime;
|
||||
+static int bootTimeErrno;
|
||||
+static virOnceControl virHostGetBootTimeOnce = VIR_ONCE_CONTROL_INITIALIZER;
|
||||
+
|
||||
+#ifdef HAVE_GETUTXID
|
||||
+static void
|
||||
+virHostGetBootTimeOnceInit(void)
|
||||
+{
|
||||
+ struct utmpx id = {.ut_type = BOOT_TIME};
|
||||
+ struct utmpx *res = NULL;
|
||||
+
|
||||
+ if (!(res = getutxid(&id))) {
|
||||
+ bootTimeErrno = errno;
|
||||
+ } else {
|
||||
+ bootTime = res->ut_tv.tv_sec;
|
||||
+ }
|
||||
+
|
||||
+ endutxent();
|
||||
+}
|
||||
+
|
||||
+#else /* !HAVE_GETUTXID */
|
||||
+
|
||||
+static void
|
||||
+virHostGetBootTimeOnceInit(void)
|
||||
+{
|
||||
+ bootTimeErrno = ENOSYS;
|
||||
+}
|
||||
+#endif /* HAVE_GETUTXID */
|
||||
+
|
||||
+/**
|
||||
+ * virHostGetBootTime:
|
||||
+ * @when: UNIX timestamp of boot time
|
||||
+ *
|
||||
+ * Get a UNIX timestamp of host boot time and store it at @when.
|
||||
+ *
|
||||
+ * Return: 0 on success,
|
||||
+ * -1 otherwise.
|
||||
+ */
|
||||
+int
|
||||
+virHostGetBootTime(unsigned long long *when)
|
||||
+{
|
||||
+ if (virOnce(&virHostGetBootTimeOnce, virHostGetBootTimeOnceInit) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (bootTimeErrno) {
|
||||
+ errno = bootTimeErrno;
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ *when = bootTime;
|
||||
+ return 0;
|
||||
+}
|
||||
diff --git a/src/util/virhostuptime.h b/src/util/virhostuptime.h
|
||||
new file mode 100644
|
||||
index 0000000000..03c1517a64
|
||||
--- /dev/null
|
||||
+++ b/src/util/virhostuptime.h
|
||||
@@ -0,0 +1,27 @@
|
||||
+/*
|
||||
+ * virhostuptime.h: helper APIs for host uptime
|
||||
+ *
|
||||
+ * Copyright (C) 2019 Red Hat, Inc.
|
||||
+ *
|
||||
+ * This library is free software; you can redistribute it and/or
|
||||
+ * modify it under the terms of the GNU Lesser General Public
|
||||
+ * License as published by the Free Software Foundation; either
|
||||
+ * version 2.1 of the License, or (at your option) any later version.
|
||||
+ *
|
||||
+ * This library is distributed in the hope that it will be useful,
|
||||
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
+ * Lesser General Public License for more details.
|
||||
+ *
|
||||
+ * You should have received a copy of the GNU Lesser General Public
|
||||
+ * License along with this library. If not, see
|
||||
+ * <http://www.gnu.org/licenses/>.
|
||||
+ */
|
||||
+
|
||||
+#pragma once
|
||||
+
|
||||
+#include "internal.h"
|
||||
+
|
||||
+int
|
||||
+virHostGetBootTime(unsigned long long *when)
|
||||
+ ATTRIBUTE_NOINLINE;
|
||||
@@ -0,0 +1,344 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:14 +0200
|
||||
Subject: [PATCH] security_util: Remove stale XATTRs
|
||||
|
||||
It may happen that we leave some XATTRs behind. For instance, on
|
||||
a sudden power loss, the host just shuts down without calling
|
||||
restore on domain paths. This creates a problem, because when the
|
||||
host starts up again, the XATTRs are there but they don't reflect
|
||||
the true state and this may result in libvirt denying start of a
|
||||
domain.
|
||||
|
||||
To solve this, save a unique timestamp (host boot time) among
|
||||
with our XATTRs.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741140
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit 7cfb7aab573a031880a1f4fd20747843fea109ba)
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_util.c | 194 +++++++++++++++++++++++++++++++-
|
||||
tests/qemusecuritymock.c | 12 ++
|
||||
tools/libvirt_recover_xattrs.sh | 2 +-
|
||||
3 files changed, 206 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_util.c b/src/security/security_util.c
|
||||
index 365b2dd2d6..31f41cedfd 100644
|
||||
--- a/src/security/security_util.c
|
||||
+++ b/src/security/security_util.c
|
||||
@@ -22,11 +22,16 @@
|
||||
#include "virfile.h"
|
||||
#include "virstring.h"
|
||||
#include "virerror.h"
|
||||
+#include "virlog.h"
|
||||
+#include "viruuid.h"
|
||||
+#include "virhostuptime.h"
|
||||
|
||||
#include "security_util.h"
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_SECURITY
|
||||
|
||||
+VIR_LOG_INIT("security.security_util");
|
||||
+
|
||||
/* There are four namespaces available on Linux (xattr(7)):
|
||||
*
|
||||
* user - can be modified by anybody,
|
||||
@@ -83,6 +88,153 @@ virSecurityGetRefCountAttrName(const char *name ATTRIBUTE_UNUSED)
|
||||
}
|
||||
|
||||
|
||||
+#ifdef XATTR_NAMESPACE
|
||||
+static char *
|
||||
+virSecurityGetTimestampAttrName(const char *name)
|
||||
+{
|
||||
+ char *ret = NULL;
|
||||
+ ignore_value(virAsprintf(&ret, XATTR_NAMESPACE ".libvirt.security.timestamp_%s", name));
|
||||
+ return ret;
|
||||
+}
|
||||
+#else /* !XATTR_NAMESPACE */
|
||||
+static char *
|
||||
+virSecurityGetTimestampAttrName(const char *name ATTRIBUTE_UNUSED)
|
||||
+{
|
||||
+ errno = ENOSYS;
|
||||
+ virReportSystemError(errno, "%s",
|
||||
+ _("Extended attributes are not supported on this system"));
|
||||
+ return NULL;
|
||||
+}
|
||||
+#endif /* !XATTR_NAMESPACE */
|
||||
+
|
||||
+
|
||||
+static char *
|
||||
+virSecurityGetTimestamp(void)
|
||||
+{
|
||||
+ unsigned long long boottime = 0;
|
||||
+ char *ret = NULL;
|
||||
+
|
||||
+ if (virHostGetBootTime(&boottime) < 0) {
|
||||
+ virReportSystemError(errno, "%s",
|
||||
+ _("Unable to get host boot time"));
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ ignore_value(virAsprintf(&ret, "%llu", boottime));
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+/**
|
||||
+ * virSecurityValidateTimestamp:
|
||||
+ * @name: security driver name
|
||||
+ * @path: file name
|
||||
+ *
|
||||
+ * Check if remembered label on @path for security driver @name
|
||||
+ * is valid, i.e. the label has been set since the last boot. If
|
||||
+ * the label was set in previous runs, all XATTRs related to
|
||||
+ * @name are removed so that clean slate is restored.
|
||||
+ *
|
||||
+ * This is done having extra attribute timestamp_$SECDRIVER which
|
||||
+ * contains the host boot time. Its value is then compared to
|
||||
+ * actual host boot time. If these two values don't match then
|
||||
+ * XATTRs are considered as stale and thus invalid.
|
||||
+ *
|
||||
+ * In ideal world, where there network file systems have XATTRs
|
||||
+ * using plain host boot time is not enough as it may lead to a
|
||||
+ * situation where a freshly started host sees XATTRs, sees the
|
||||
+ * timestamp put there by some longer running host and considers
|
||||
+ * the XATTRs invalid. Well, there is not an easy way out. We
|
||||
+ * would need to somehow check if the longer running host is
|
||||
+ * still there and uses the @path (how?).
|
||||
+ * Fortunately, there is only one network file system which
|
||||
+ * supports XATTRs currently (GlusterFS via FUSE) and it is used
|
||||
+ * so rarely that it's almost a corner case.
|
||||
+ * The worst thing that happens there is that we remove XATTRs
|
||||
+ * and thus return @path to the default label for $SECDRIVER.
|
||||
+ *
|
||||
+ * Returns: 0 if remembered label is valid,
|
||||
+ * 1 if remembered label was not valid,
|
||||
+ * -2 if underlying file system doesn't support XATTRs,
|
||||
+ * -1 otherwise.
|
||||
+ */
|
||||
+static int
|
||||
+virSecurityValidateTimestamp(const char *name,
|
||||
+ const char *path)
|
||||
+{
|
||||
+ VIR_AUTOFREE(char *) expected_timestamp = NULL;
|
||||
+ VIR_AUTOFREE(char *) timestamp_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) value = NULL;
|
||||
+
|
||||
+ if (!(expected_timestamp = virSecurityGetTimestamp()) ||
|
||||
+ !(timestamp_name = virSecurityGetTimestampAttrName(name)))
|
||||
+ return -1;
|
||||
+
|
||||
+ errno = 0;
|
||||
+ if (virFileGetXAttrQuiet(path, timestamp_name, &value) < 0) {
|
||||
+ if (errno == ENOSYS || errno == ENOTSUP) {
|
||||
+ return -2;
|
||||
+ } else if (errno != ENODATA) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Unable to get XATTR %s on %s"),
|
||||
+ timestamp_name,
|
||||
+ path);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ /* Timestamp is missing. We could continue and claim a valid timestamp.
|
||||
+ * But then we would never remove stale XATTRs. Therefore, claim it
|
||||
+ * invalid and have the code below remove all XATTRs. This of course
|
||||
+ * means that we will not restore the original owner, but the plus side
|
||||
+ * is that we reset refcounter which will represent the true state.
|
||||
+ */
|
||||
+ }
|
||||
+
|
||||
+ if (STREQ_NULLABLE(value, expected_timestamp)) {
|
||||
+ VIR_DEBUG("XATTRs on %s secdriver=%s are valid", path, name);
|
||||
+ return 0;
|
||||
+ }
|
||||
+
|
||||
+ VIR_WARN("Invalid XATTR timestamp detected on %s secdriver=%s", path, name);
|
||||
+
|
||||
+ if (virSecurityMoveRememberedLabel(name, path, NULL) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 1;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+virSecurityAddTimestamp(const char *name,
|
||||
+ const char *path)
|
||||
+{
|
||||
+ VIR_AUTOFREE(char *) timestamp_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) timestamp_value = NULL;
|
||||
+
|
||||
+ if (!(timestamp_value = virSecurityGetTimestamp()) ||
|
||||
+ !(timestamp_name = virSecurityGetTimestampAttrName(name)))
|
||||
+ return -1;
|
||||
+
|
||||
+ return virFileSetXAttr(path, timestamp_name, timestamp_value);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+virSecurityRemoveTimestamp(const char *name,
|
||||
+ const char *path)
|
||||
+{
|
||||
+ VIR_AUTOFREE(char *) timestamp_name = NULL;
|
||||
+
|
||||
+ if (!(timestamp_name = virSecurityGetTimestampAttrName(name)))
|
||||
+ return -1;
|
||||
+
|
||||
+ if (virFileRemoveXAttr(path, timestamp_name) < 0 && errno != ENOENT)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+
|
||||
/**
|
||||
* virSecurityGetRememberedLabel:
|
||||
* @name: security driver name
|
||||
@@ -117,9 +269,13 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
+ int rc;
|
||||
|
||||
*label = NULL;
|
||||
|
||||
+ if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
+ return rc;
|
||||
+
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
return -1;
|
||||
|
||||
@@ -163,6 +319,9 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
|
||||
if (virFileRemoveXAttr(path, attr_name) < 0)
|
||||
return -1;
|
||||
+
|
||||
+ if (virSecurityRemoveTimestamp(name, path) < 0)
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -198,6 +357,10 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
+ int rc;
|
||||
+
|
||||
+ if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
+ return rc;
|
||||
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
return -1;
|
||||
@@ -232,6 +395,9 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
|
||||
if (virFileSetXAttr(path, attr_name, label) < 0)
|
||||
return -1;
|
||||
+
|
||||
+ if (virSecurityAddTimestamp(name, path) < 0)
|
||||
+ return -1;
|
||||
}
|
||||
|
||||
if (virAsprintf(&value, "%u", refcount) < 0)
|
||||
@@ -266,9 +432,12 @@ virSecurityMoveRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) ref_value = NULL;
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) attr_value = NULL;
|
||||
+ VIR_AUTOFREE(char *) timestamp_name = NULL;
|
||||
+ VIR_AUTOFREE(char *) timestamp_value = NULL;
|
||||
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)) ||
|
||||
- !(attr_name = virSecurityGetAttrName(name)))
|
||||
+ !(attr_name = virSecurityGetAttrName(name)) ||
|
||||
+ !(timestamp_name = virSecurityGetTimestampAttrName(name)))
|
||||
return -1;
|
||||
|
||||
if (virFileGetXAttrQuiet(src, ref_name, &ref_value) < 0) {
|
||||
@@ -293,6 +462,17 @@ virSecurityMoveRememberedLabel(const char *name,
|
||||
}
|
||||
}
|
||||
|
||||
+ if (virFileGetXAttrQuiet(src, timestamp_name, ×tamp_value) < 0) {
|
||||
+ if (errno == ENOSYS || errno == ENOTSUP) {
|
||||
+ return -2;
|
||||
+ } else if (errno != ENODATA) {
|
||||
+ virReportSystemError(errno,
|
||||
+ _("Unable to get XATTR %s on %s"),
|
||||
+ attr_name, src);
|
||||
+ return -1;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
if (ref_value &&
|
||||
virFileRemoveXAttr(src, ref_name) < 0) {
|
||||
return -1;
|
||||
@@ -303,6 +483,11 @@ virSecurityMoveRememberedLabel(const char *name,
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ if (timestamp_value &&
|
||||
+ virFileRemoveXAttr(src, timestamp_name) < 0) {
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
if (dst) {
|
||||
if (ref_value &&
|
||||
virFileSetXAttr(dst, ref_name, ref_value) < 0) {
|
||||
@@ -314,6 +499,13 @@ virSecurityMoveRememberedLabel(const char *name,
|
||||
ignore_value(virFileRemoveXAttr(dst, ref_name));
|
||||
return -1;
|
||||
}
|
||||
+
|
||||
+ if (timestamp_value &&
|
||||
+ virFileSetXAttr(dst, timestamp_name, timestamp_value) < 0) {
|
||||
+ ignore_value(virFileRemoveXAttr(dst, ref_name));
|
||||
+ ignore_value(virFileRemoveXAttr(dst, attr_name));
|
||||
+ return -1;
|
||||
+ }
|
||||
}
|
||||
|
||||
return 0;
|
||||
diff --git a/tests/qemusecuritymock.c b/tests/qemusecuritymock.c
|
||||
index a15eef29c9..373d64305a 100644
|
||||
--- a/tests/qemusecuritymock.c
|
||||
+++ b/tests/qemusecuritymock.c
|
||||
@@ -32,6 +32,7 @@
|
||||
#include "viralloc.h"
|
||||
#include "qemusecuritytest.h"
|
||||
#include "security/security_manager.h"
|
||||
+#include "virhostuptime.h"
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_NONE
|
||||
|
||||
@@ -488,3 +489,14 @@ virProcessRunInFork(virProcessForkCallback cb,
|
||||
{
|
||||
return cb(-1, opaque);
|
||||
}
|
||||
+
|
||||
+
|
||||
+/* We don't really need to mock this function. The qemusecuritytest doesn't
|
||||
+ * care about the actual value. However, travis runs build and tests in a
|
||||
+ * container where utmp is missing and thus this function fails. */
|
||||
+int
|
||||
+virHostGetBootTime(unsigned long long *when)
|
||||
+{
|
||||
+ *when = 1234567890;
|
||||
+ return 0;
|
||||
+}
|
||||
diff --git a/tools/libvirt_recover_xattrs.sh b/tools/libvirt_recover_xattrs.sh
|
||||
index 58f02f8dfb..3907413c63 100755
|
||||
--- a/tools/libvirt_recover_xattrs.sh
|
||||
+++ b/tools/libvirt_recover_xattrs.sh
|
||||
@@ -74,7 +74,7 @@ fi
|
||||
declare -a XATTRS
|
||||
for i in "dac" "selinux"; do
|
||||
for p in ${LIBVIRT_XATTR_PREFIXES[@]}; do
|
||||
- XATTRS+=("$p.$i" "$p.ref_$i")
|
||||
+ XATTRS+=("$p.$i" "$p.ref_$i" "$p.timestamp_$i")
|
||||
done
|
||||
done
|
||||
|
||||
@@ -0,0 +1,96 @@
|
||||
From: Nikolay Shirokovskiy <nshirokovskiy@virtuozzo.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:15 +0200
|
||||
Subject: [PATCH] security_util: verify xattrs only if ref is present
|
||||
|
||||
After 7cfb7aab573 commit starting a domain pullutes logs with
|
||||
warnings like [1]. The reason is resource files do not
|
||||
have timestamp before starting a domain and after destroying
|
||||
domain the timestamp is cleared. Let's check the timestamp
|
||||
only if attribute with refcounter is found.
|
||||
|
||||
[1] warning : virSecurityValidateTimestamp:198 : Invalid XATTR timestamp detected on \
|
||||
/some/path secdriver=dac
|
||||
|
||||
Signed-off-by: Nikolay Shirokovskiy <nshirokovskiy@virtuozzo.com>
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit 7c40211a5a0fd15f5885e38dc571e81b9a3fd699)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741140
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_util.c | 36 ++++++++++++++++++++++++++++--------
|
||||
1 file changed, 28 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_util.c b/src/security/security_util.c
|
||||
index 31f41cedfd..865b3ec905 100644
|
||||
--- a/src/security/security_util.c
|
||||
+++ b/src/security/security_util.c
|
||||
@@ -269,13 +269,9 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
- int rc;
|
||||
|
||||
*label = NULL;
|
||||
|
||||
- if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
- return rc;
|
||||
-
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
return -1;
|
||||
|
||||
@@ -290,6 +286,20 @@ virSecurityGetRememberedLabel(const char *name,
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ if (value) {
|
||||
+ int rc;
|
||||
+
|
||||
+ /* Do this after we've tried to get refcounter to ensure underlying FS
|
||||
+ * supports XATTRs and @path has refcounter attribute set, because
|
||||
+ * validator might throws a warning. */
|
||||
+ if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
+ return rc;
|
||||
+
|
||||
+ /* Invalid label is like a non-existent one */
|
||||
+ if (rc == 1)
|
||||
+ return -2;
|
||||
+ }
|
||||
+
|
||||
if (virStrToLong_ui(value, NULL, 10, &refcount) < 0) {
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
_("malformed refcount %s on %s"),
|
||||
@@ -357,10 +367,6 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
VIR_AUTOFREE(char *) attr_name = NULL;
|
||||
VIR_AUTOFREE(char *) value = NULL;
|
||||
unsigned int refcount = 0;
|
||||
- int rc;
|
||||
-
|
||||
- if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
- return rc;
|
||||
|
||||
if (!(ref_name = virSecurityGetRefCountAttrName(name)))
|
||||
return -1;
|
||||
@@ -377,6 +383,20 @@ virSecuritySetRememberedLabel(const char *name,
|
||||
}
|
||||
}
|
||||
|
||||
+ if (value) {
|
||||
+ int rc;
|
||||
+
|
||||
+ /* Do this after we've tried to get refcounter to ensure underlying FS
|
||||
+ * supports XATTRs and @path has refcounter attribute set, because
|
||||
+ * validator might throws a warning. */
|
||||
+ if ((rc = virSecurityValidateTimestamp(name, path)) < 0)
|
||||
+ return rc;
|
||||
+
|
||||
+ /* Invalid label is like a non-existent one */
|
||||
+ if (rc == 1)
|
||||
+ VIR_FREE(value);
|
||||
+ }
|
||||
+
|
||||
if (value &&
|
||||
virStrToLong_ui(value, NULL, 10, &refcount) < 0) {
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
@@ -0,0 +1,97 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:16 +0200
|
||||
Subject: [PATCH] virSecuritySELinuxSetFileconImpl: Drop @optional argument
|
||||
|
||||
The only thing that the @optional argument does is that it makes
|
||||
the function return 1 instead of 0 if setting SELinux context
|
||||
failed in a non-critical fashion. Drop the argument then and
|
||||
return 1 in that case. This enables caller to learn if SELinux
|
||||
context was set or not.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit 34712a5e3b313fb9ca2223c54ea46f626429a6c4)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740506
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_selinux.c | 35 +++++++++++++++++++++++----------
|
||||
1 file changed, 25 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index 9857223bbf..766f334faf 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -1257,12 +1257,27 @@ virSecuritySELinuxGetProcessLabel(virSecurityManagerPtr mgr ATTRIBUTE_UNUSED,
|
||||
return 0;
|
||||
}
|
||||
|
||||
-/* Attempt to change the label of PATH to TCON. If OPTIONAL is true,
|
||||
- * return 1 if labelling was not possible. Otherwise, require a label
|
||||
- * change, and return 0 for success, -1 for failure. */
|
||||
+/**
|
||||
+ * virSecuritySELinuxSetFileconImpl:
|
||||
+ * @path: path to the file to set context on
|
||||
+ * @tcon: target context to set
|
||||
+ * @privileged: whether running as privileged user
|
||||
+ *
|
||||
+ * Set @tcon SELinux context on @path. If unable to do so, check SELinux
|
||||
+ * configuration and produce sensible error message suggesting solution.
|
||||
+ * It may happen that setting context fails but hypervisor will be able to
|
||||
+ * open the @path successfully. This is because some file systems don't
|
||||
+ * support SELinux, are RO, or the @path had the correct context from the
|
||||
+ * start. If that is the case, a positive one is returned.
|
||||
+ *
|
||||
+ * Returns: 0 if context was set successfully
|
||||
+ * 1 if setting the context failed in a non-critical fashion
|
||||
+ * -1 in case of error
|
||||
+ */
|
||||
static int
|
||||
-virSecuritySELinuxSetFileconImpl(const char *path, const char *tcon,
|
||||
- bool optional, bool privileged)
|
||||
+virSecuritySELinuxSetFileconImpl(const char *path,
|
||||
+ const char *tcon,
|
||||
+ bool privileged)
|
||||
{
|
||||
security_context_t econ;
|
||||
|
||||
@@ -1278,7 +1293,7 @@ virSecuritySELinuxSetFileconImpl(const char *path, const char *tcon,
|
||||
if (STREQ(tcon, econ)) {
|
||||
freecon(econ);
|
||||
/* It's alright, there's nothing to change anyway. */
|
||||
- return optional ? 1 : 0;
|
||||
+ return 1;
|
||||
}
|
||||
freecon(econ);
|
||||
}
|
||||
@@ -1315,9 +1330,9 @@ virSecuritySELinuxSetFileconImpl(const char *path, const char *tcon,
|
||||
VIR_INFO("Setting security context '%s' on '%s' not supported",
|
||||
tcon, path);
|
||||
}
|
||||
- if (optional)
|
||||
- return 1;
|
||||
}
|
||||
+
|
||||
+ return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -1377,7 +1392,7 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
}
|
||||
}
|
||||
|
||||
- if (virSecuritySELinuxSetFileconImpl(path, tcon, optional, privileged) < 0)
|
||||
+ if (virSecuritySELinuxSetFileconImpl(path, tcon, privileged) < 0)
|
||||
goto cleanup;
|
||||
|
||||
ret = 0;
|
||||
@@ -1542,7 +1557,7 @@ virSecuritySELinuxRestoreFileLabel(virSecurityManagerPtr mgr,
|
||||
}
|
||||
}
|
||||
|
||||
- if (virSecuritySELinuxSetFileconImpl(newpath, fcon, false, privileged) < 0)
|
||||
+ if (virSecuritySELinuxSetFileconImpl(newpath, fcon, privileged) < 0)
|
||||
goto cleanup;
|
||||
|
||||
ret = 0;
|
||||
@@ -0,0 +1,106 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:17 +0200
|
||||
Subject: [PATCH] security_selinux: Drop virSecuritySELinuxSetFileconOptional()
|
||||
|
||||
There is no real difference between
|
||||
virSecuritySELinuxSetFilecon() and
|
||||
virSecuritySELinuxSetFileconOptional(). Drop the latter in favour
|
||||
of the former.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit 079c1d6a291869ab4ee5d7f70bfd9a0f716c508e)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740506
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_selinux.c | 53 ++++++++++++++-------------------
|
||||
1 file changed, 22 insertions(+), 31 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index 766f334faf..87e1ba202d 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -1419,15 +1419,6 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
}
|
||||
|
||||
|
||||
-static int
|
||||
-virSecuritySELinuxSetFileconOptional(virSecurityManagerPtr mgr,
|
||||
- const char *path,
|
||||
- const char *tcon,
|
||||
- bool remember)
|
||||
-{
|
||||
- return virSecuritySELinuxSetFileconHelper(mgr, path, tcon, true, remember);
|
||||
-}
|
||||
-
|
||||
static int
|
||||
virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
const char *path,
|
||||
@@ -1884,28 +1875,28 @@ virSecuritySELinuxSetImageLabelInternal(virSecurityManagerPtr mgr,
|
||||
parent_seclabel->label, remember);
|
||||
} else if (!parent || parent == src) {
|
||||
if (src->shared) {
|
||||
- ret = virSecuritySELinuxSetFileconOptional(mgr,
|
||||
- src->path,
|
||||
- data->file_context,
|
||||
- remember);
|
||||
+ ret = virSecuritySELinuxSetFilecon(mgr,
|
||||
+ src->path,
|
||||
+ data->file_context,
|
||||
+ remember);
|
||||
} else if (src->readonly) {
|
||||
- ret = virSecuritySELinuxSetFileconOptional(mgr,
|
||||
- src->path,
|
||||
- data->content_context,
|
||||
- remember);
|
||||
+ ret = virSecuritySELinuxSetFilecon(mgr,
|
||||
+ src->path,
|
||||
+ data->content_context,
|
||||
+ remember);
|
||||
} else if (secdef->imagelabel) {
|
||||
- ret = virSecuritySELinuxSetFileconOptional(mgr,
|
||||
- src->path,
|
||||
- secdef->imagelabel,
|
||||
- remember);
|
||||
+ ret = virSecuritySELinuxSetFilecon(mgr,
|
||||
+ src->path,
|
||||
+ secdef->imagelabel,
|
||||
+ remember);
|
||||
} else {
|
||||
ret = 0;
|
||||
}
|
||||
} else {
|
||||
- ret = virSecuritySELinuxSetFileconOptional(mgr,
|
||||
- src->path,
|
||||
- data->content_context,
|
||||
- remember);
|
||||
+ ret = virSecuritySELinuxSetFilecon(mgr,
|
||||
+ src->path,
|
||||
+ data->content_context,
|
||||
+ remember);
|
||||
}
|
||||
|
||||
if (ret == 1 && !disk_seclabel) {
|
||||
@@ -2045,14 +2036,14 @@ virSecuritySELinuxSetSCSILabel(virSCSIDevicePtr dev,
|
||||
return 0;
|
||||
|
||||
if (virSCSIDeviceGetShareable(dev))
|
||||
- return virSecuritySELinuxSetFileconOptional(mgr, file,
|
||||
- data->file_context, true);
|
||||
+ return virSecuritySELinuxSetFilecon(mgr, file,
|
||||
+ data->file_context, true);
|
||||
else if (virSCSIDeviceGetReadonly(dev))
|
||||
- return virSecuritySELinuxSetFileconOptional(mgr, file,
|
||||
- data->content_context, true);
|
||||
+ return virSecuritySELinuxSetFilecon(mgr, file,
|
||||
+ data->content_context, true);
|
||||
else
|
||||
- return virSecuritySELinuxSetFileconOptional(mgr, file,
|
||||
- secdef->imagelabel, true);
|
||||
+ return virSecuritySELinuxSetFilecon(mgr, file,
|
||||
+ secdef->imagelabel, true);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -0,0 +1,126 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:18 +0200
|
||||
Subject: [PATCH] security_selinux: Drop @optional from
|
||||
_virSecuritySELinuxContextItem
|
||||
|
||||
Now, that we don't need to remember if setting context is
|
||||
'optional' (the argument only made
|
||||
virSecuritySELinuxSetFileconImpl() return a different success
|
||||
code), we can drop it from the _virSecuritySELinuxContextItem
|
||||
structure as we don't need to remember it in transactions.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit b71d54f44707e80aae6fd01a766bb254882f5163)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740506
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_selinux.c | 16 ++++------------
|
||||
1 file changed, 4 insertions(+), 12 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index 87e1ba202d..e5b55fccb4 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -81,7 +81,6 @@ typedef virSecuritySELinuxContextItem *virSecuritySELinuxContextItemPtr;
|
||||
struct _virSecuritySELinuxContextItem {
|
||||
char *path;
|
||||
char *tcon;
|
||||
- bool optional;
|
||||
bool remember; /* Whether owner remembering should be done for @path/@src */
|
||||
bool restore; /* Whether current operation is 'set' or 'restore' */
|
||||
};
|
||||
@@ -122,7 +121,6 @@ static int
|
||||
virSecuritySELinuxContextListAppend(virSecuritySELinuxContextListPtr list,
|
||||
const char *path,
|
||||
const char *tcon,
|
||||
- bool optional,
|
||||
bool remember,
|
||||
bool restore)
|
||||
{
|
||||
@@ -135,7 +133,6 @@ virSecuritySELinuxContextListAppend(virSecuritySELinuxContextListPtr list,
|
||||
if (VIR_STRDUP(item->path, path) < 0 || VIR_STRDUP(item->tcon, tcon) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- item->optional = optional;
|
||||
item->remember = remember;
|
||||
item->restore = restore;
|
||||
|
||||
@@ -170,7 +167,6 @@ virSecuritySELinuxContextListFree(void *opaque)
|
||||
* virSecuritySELinuxTransactionAppend:
|
||||
* @path: Path to chown
|
||||
* @tcon: target context
|
||||
- * @optional: true if setting @tcon is optional
|
||||
* @remember: if the original owner should be recorded/recalled
|
||||
* @restore: if current operation is set or restore
|
||||
*
|
||||
@@ -187,7 +183,6 @@ virSecuritySELinuxContextListFree(void *opaque)
|
||||
static int
|
||||
virSecuritySELinuxTransactionAppend(const char *path,
|
||||
const char *tcon,
|
||||
- bool optional,
|
||||
bool remember,
|
||||
bool restore)
|
||||
{
|
||||
@@ -198,7 +193,7 @@ virSecuritySELinuxTransactionAppend(const char *path,
|
||||
return 0;
|
||||
|
||||
if (virSecuritySELinuxContextListAppend(list, path, tcon,
|
||||
- optional, remember, restore) < 0)
|
||||
+ remember, restore) < 0)
|
||||
return -1;
|
||||
|
||||
return 1;
|
||||
@@ -234,7 +229,6 @@ virSecuritySELinuxRecallLabel(const char *path,
|
||||
static int virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
const char *path,
|
||||
const char *tcon,
|
||||
- bool optional,
|
||||
bool remember);
|
||||
|
||||
|
||||
@@ -290,7 +284,6 @@ virSecuritySELinuxTransactionRun(pid_t pid ATTRIBUTE_UNUSED,
|
||||
rv = virSecuritySELinuxSetFileconHelper(list->manager,
|
||||
item->path,
|
||||
item->tcon,
|
||||
- item->optional,
|
||||
remember);
|
||||
} else {
|
||||
rv = virSecuritySELinuxRestoreFileLabel(list->manager,
|
||||
@@ -1342,7 +1335,6 @@ static int
|
||||
virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
const char *path,
|
||||
const char *tcon,
|
||||
- bool optional,
|
||||
bool remember)
|
||||
{
|
||||
bool privileged = virSecurityManagerGetPrivileged(mgr);
|
||||
@@ -1353,7 +1345,7 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
int ret = -1;
|
||||
|
||||
if ((rc = virSecuritySELinuxTransactionAppend(path, tcon,
|
||||
- optional, remember, false)) < 0)
|
||||
+ remember, false)) < 0)
|
||||
return -1;
|
||||
else if (rc > 0)
|
||||
return 0;
|
||||
@@ -1425,7 +1417,7 @@ virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
const char *tcon,
|
||||
bool remember)
|
||||
{
|
||||
- return virSecuritySELinuxSetFileconHelper(mgr, path, tcon, false, remember);
|
||||
+ return virSecuritySELinuxSetFileconHelper(mgr, path, tcon, remember);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -1512,7 +1504,7 @@ virSecuritySELinuxRestoreFileLabel(virSecurityManagerPtr mgr,
|
||||
}
|
||||
|
||||
if ((rc = virSecuritySELinuxTransactionAppend(path, NULL,
|
||||
- false, recall, true)) < 0) {
|
||||
+ recall, true)) < 0) {
|
||||
goto cleanup;
|
||||
} else if (rc > 0) {
|
||||
ret = 0;
|
||||
@@ -0,0 +1,83 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:19 +0200
|
||||
Subject: [PATCH] security_selinux: Drop virSecuritySELinuxSetFileconHelper
|
||||
|
||||
This function is no longer needed because after previous commits
|
||||
it's just an alias to virSecuritySELinuxSetFilecon.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit eaa2a064fa9a7cf6220349ac8706a22593cbf607)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740506
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_selinux.c | 33 ++++++++++++---------------------
|
||||
1 file changed, 12 insertions(+), 21 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index e5b55fccb4..1df04d7358 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -226,10 +226,10 @@ virSecuritySELinuxRecallLabel(const char *path,
|
||||
}
|
||||
|
||||
|
||||
-static int virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
- const char *path,
|
||||
- const char *tcon,
|
||||
- bool remember);
|
||||
+static int virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
+ const char *path,
|
||||
+ const char *tcon,
|
||||
+ bool remember);
|
||||
|
||||
|
||||
static int virSecuritySELinuxRestoreFileLabel(virSecurityManagerPtr mgr,
|
||||
@@ -281,10 +281,10 @@ virSecuritySELinuxTransactionRun(pid_t pid ATTRIBUTE_UNUSED,
|
||||
const bool remember = item->remember && list->lock;
|
||||
|
||||
if (!item->restore) {
|
||||
- rv = virSecuritySELinuxSetFileconHelper(list->manager,
|
||||
- item->path,
|
||||
- item->tcon,
|
||||
- remember);
|
||||
+ rv = virSecuritySELinuxSetFilecon(list->manager,
|
||||
+ item->path,
|
||||
+ item->tcon,
|
||||
+ remember);
|
||||
} else {
|
||||
rv = virSecuritySELinuxRestoreFileLabel(list->manager,
|
||||
item->path,
|
||||
@@ -1332,10 +1332,10 @@ virSecuritySELinuxSetFileconImpl(const char *path,
|
||||
|
||||
|
||||
static int
|
||||
-virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
- const char *path,
|
||||
- const char *tcon,
|
||||
- bool remember)
|
||||
+virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
+ const char *path,
|
||||
+ const char *tcon,
|
||||
+ bool remember)
|
||||
{
|
||||
bool privileged = virSecurityManagerGetPrivileged(mgr);
|
||||
security_context_t econ = NULL;
|
||||
@@ -1411,15 +1411,6 @@ virSecuritySELinuxSetFileconHelper(virSecurityManagerPtr mgr,
|
||||
}
|
||||
|
||||
|
||||
-static int
|
||||
-virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
- const char *path,
|
||||
- const char *tcon,
|
||||
- bool remember)
|
||||
-{
|
||||
- return virSecuritySELinuxSetFileconHelper(mgr, path, tcon, remember);
|
||||
-}
|
||||
-
|
||||
static int
|
||||
virSecuritySELinuxFSetFilecon(int fd, char *tcon)
|
||||
{
|
||||
@@ -0,0 +1,49 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:20 +0200
|
||||
Subject: [PATCH] security_selinux: Play nicely with network FS that only
|
||||
emulates SELinux
|
||||
|
||||
There are some network file systems that do support XATTRs (e.g.
|
||||
gluster via FUSE). And they appear to support SELinux too.
|
||||
However, not really. Problem is, that it is impossible to change
|
||||
SELinux label of a file stored there, and yet we claim success
|
||||
(rightfully - hypervisor succeeds in opening the file). But this
|
||||
creates a problem for us - from XATTR bookkeeping POV, we haven't
|
||||
changed the label and thus if we remembered any label, we must
|
||||
roll back and remove it.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1740506
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Martin Kletzander <mkletzan@redhat.com>
|
||||
(cherry picked from commit 8fe953805a535097cf3b819b3b68fbfb166efed4)
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/security/security_selinux.c | 10 ++++++++--
|
||||
1 file changed, 8 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/security/security_selinux.c b/src/security/security_selinux.c
|
||||
index 1df04d7358..39d616ba44 100644
|
||||
--- a/src/security/security_selinux.c
|
||||
+++ b/src/security/security_selinux.c
|
||||
@@ -1384,12 +1384,18 @@ virSecuritySELinuxSetFilecon(virSecurityManagerPtr mgr,
|
||||
}
|
||||
}
|
||||
|
||||
- if (virSecuritySELinuxSetFileconImpl(path, tcon, privileged) < 0)
|
||||
+ rc = virSecuritySELinuxSetFileconImpl(path, tcon, privileged);
|
||||
+ if (rc < 0)
|
||||
goto cleanup;
|
||||
|
||||
+ /* Do not try restoring the label if it was not changed
|
||||
+ * (setting it failed in a non-critical fashion) */
|
||||
+ if (rc == 0)
|
||||
+ rollback = false;
|
||||
+
|
||||
ret = 0;
|
||||
cleanup:
|
||||
- if (ret < 0 && rollback) {
|
||||
+ if (rollback) {
|
||||
virErrorPtr origerr;
|
||||
|
||||
virErrorPreserveLast(&origerr);
|
||||
@@ -0,0 +1,42 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:21 +0200
|
||||
Subject: [PATCH] qemu_blockjob: Print image path on failed security metadata
|
||||
move too
|
||||
|
||||
When a block job is completed, the security image metadata are
|
||||
moved to the new image. If this fails an warning is printed, but
|
||||
the message contains only domain name and lacks image paths. Put
|
||||
them both into the warning message.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
ACKed-by: Peter Krempa <pkrempa@redhat.com>
|
||||
(cherry picked from commit 7f99d8a739c01a280ca0c173ecd6051a92f0c897)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741456
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/qemu/qemu_blockjob.c | 10 ++++++++--
|
||||
1 file changed, 8 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu/qemu_blockjob.c b/src/qemu/qemu_blockjob.c
|
||||
index a5b558b9ab..b3c0f784cd 100644
|
||||
--- a/src/qemu/qemu_blockjob.c
|
||||
+++ b/src/qemu/qemu_blockjob.c
|
||||
@@ -584,8 +584,14 @@ qemuBlockJobEventProcessLegacyCompleted(virQEMUDriverPtr driver,
|
||||
virDomainLockImageDetach(driver->lockManager, vm, disk->src);
|
||||
|
||||
/* Move secret driver metadata */
|
||||
- if (qemuSecurityMoveImageMetadata(driver, vm, disk->src, disk->mirror) < 0)
|
||||
- VIR_WARN("Unable to move disk metadata on vm %s", vm->def->name);
|
||||
+ if (qemuSecurityMoveImageMetadata(driver, vm, disk->src, disk->mirror) < 0) {
|
||||
+ VIR_WARN("Unable to move disk metadata on "
|
||||
+ "vm %s from %s to %s (disk target %s)",
|
||||
+ vm->def->name,
|
||||
+ NULLSTR(disk->src->path),
|
||||
+ NULLSTR(disk->mirror->path),
|
||||
+ disk->dst);
|
||||
+ }
|
||||
|
||||
virObjectUnref(disk->src);
|
||||
disk->src = disk->mirror;
|
||||
@@ -0,0 +1,79 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 2 Sep 2019 13:25:22 +0200
|
||||
Subject: [PATCH] qemu_blockjob: Remove secdriver metadata more frequently
|
||||
|
||||
If a block job reaches failed/cancelled state, or is completed
|
||||
without pivot then we must remove security driver metadata
|
||||
associated to the backing chain so that we don't leave any
|
||||
metadata behind.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741456
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
ACKed-by: Peter Krempa <pkrempa@redhat.com>
|
||||
(cherry picked from commit 16fb3c8b83fb39f9931e942f7d1738ffe024d234)
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
|
||||
Conflicts:
|
||||
- src/qemu/qemu_blockjob.c:
|
||||
qemuBlockJobProcessEventFailedActiveCommit() doesn't exist as
|
||||
v5.7.0-rc2~2 isn't backported (blockdev is not going to be
|
||||
enabled with RHEL-AV-8.1.0).
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
---
|
||||
src/qemu/qemu_blockjob.c | 32 ++++++++++++++++++++++++++++++++
|
||||
1 file changed, 32 insertions(+)
|
||||
|
||||
diff --git a/src/qemu/qemu_blockjob.c b/src/qemu/qemu_blockjob.c
|
||||
index b3c0f784cd..beda9bd64e 100644
|
||||
--- a/src/qemu/qemu_blockjob.c
|
||||
+++ b/src/qemu/qemu_blockjob.c
|
||||
@@ -597,7 +597,23 @@ qemuBlockJobEventProcessLegacyCompleted(virQEMUDriverPtr driver,
|
||||
disk->src = disk->mirror;
|
||||
} else {
|
||||
if (disk->mirror) {
|
||||
+ virStorageSourcePtr n;
|
||||
+
|
||||
virDomainLockImageDetach(driver->lockManager, vm, disk->mirror);
|
||||
+
|
||||
+ /* Ideally, we would restore seclabels on the backing chain here
|
||||
+ * but we don't know if somebody else is not using parts of it.
|
||||
+ * Remove security driver metadata so that they are not leaked. */
|
||||
+ for (n = disk->mirror; virStorageSourceIsBacking(n); n = n->backingStore) {
|
||||
+ if (qemuSecurityMoveImageMetadata(driver, vm, n, NULL) < 0) {
|
||||
+ VIR_WARN("Unable to remove disk metadata on "
|
||||
+ "vm %s from %s (disk target %s)",
|
||||
+ vm->def->name,
|
||||
+ NULLSTR(disk->src->path),
|
||||
+ disk->dst);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
virObjectUnref(disk->mirror);
|
||||
}
|
||||
}
|
||||
@@ -666,7 +682,23 @@ qemuBlockJobEventProcessLegacy(virQEMUDriverPtr driver,
|
||||
case VIR_DOMAIN_BLOCK_JOB_FAILED:
|
||||
case VIR_DOMAIN_BLOCK_JOB_CANCELED:
|
||||
if (disk->mirror) {
|
||||
+ virStorageSourcePtr n;
|
||||
+
|
||||
virDomainLockImageDetach(driver->lockManager, vm, disk->mirror);
|
||||
+
|
||||
+ /* Ideally, we would restore seclabels on the backing chain here
|
||||
+ * but we don't know if somebody else is not using parts of it.
|
||||
+ * Remove security driver metadata so that they are not leaked. */
|
||||
+ for (n = disk->mirror; virStorageSourceIsBacking(n); n = n->backingStore) {
|
||||
+ if (qemuSecurityMoveImageMetadata(driver, vm, n, NULL) < 0) {
|
||||
+ VIR_WARN("Unable to remove disk metadata on "
|
||||
+ "vm %s from %s (disk target %s)",
|
||||
+ vm->def->name,
|
||||
+ NULLSTR(disk->src->path),
|
||||
+ disk->dst);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
virObjectUnref(disk->mirror);
|
||||
disk->mirror = NULL;
|
||||
}
|
||||
@@ -0,0 +1,192 @@
|
||||
From: =?UTF-8?q?J=C3=A1n=20Tomko?= <jtomko@redhat.com>
|
||||
Date: Fri, 9 Aug 2019 10:48:35 +0200
|
||||
Subject: [PATCH] Revert "tpm: Check TPM XML device configuration changes after
|
||||
edit"
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Redefining a domain via virDomainDefineXML should not give different results
|
||||
based on an already existing definition.
|
||||
|
||||
Also, there's a crasher somewhere in the code:
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1739338
|
||||
|
||||
This reverts commit 94b3aa55f83ada33a9fdda66068d58ef1a56c0a5
|
||||
|
||||
Signed-off-by: Ján Tomko <jtomko@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit d8326cb8826170019c74018511d76c58665ab282)
|
||||
---
|
||||
src/conf/domain_conf.c | 56 ---------------------------------------
|
||||
src/conf/domain_conf.h | 3 ---
|
||||
src/libvirt_private.syms | 1 -
|
||||
src/qemu/qemu_driver.c | 28 --------------------
|
||||
src/qemu/qemu_extdevice.c | 2 +-
|
||||
src/qemu/qemu_extdevice.h | 3 ---
|
||||
6 files changed, 1 insertion(+), 92 deletions(-)
|
||||
|
||||
diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
|
||||
index 441eb1a5a2..ac0561ddc5 100644
|
||||
--- a/src/conf/domain_conf.c
|
||||
+++ b/src/conf/domain_conf.c
|
||||
@@ -31436,59 +31436,3 @@ virDomainGraphicsNeedsAutoRenderNode(const virDomainGraphicsDef *graphics)
|
||||
|
||||
return true;
|
||||
}
|
||||
-
|
||||
-
|
||||
-static int
|
||||
-virDomainCheckTPMChanges(virDomainDefPtr def,
|
||||
- virDomainDefPtr newDef)
|
||||
-{
|
||||
- bool oldEnc, newEnc;
|
||||
-
|
||||
- if (!def->tpm)
|
||||
- return 0;
|
||||
-
|
||||
- switch (def->tpm->type) {
|
||||
- case VIR_DOMAIN_TPM_TYPE_EMULATOR:
|
||||
- if (virFileExists(def->tpm->data.emulator.storagepath)) {
|
||||
- /* VM has been started */
|
||||
- /* Once a VM was started with an encrypted state we allow
|
||||
- * less configuration changes.
|
||||
- */
|
||||
- oldEnc = def->tpm->data.emulator.hassecretuuid;
|
||||
- if (oldEnc && def->tpm->type != newDef->tpm->type) {
|
||||
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
- _("Changing the type of TPM is not allowed"));
|
||||
- return -1;
|
||||
- }
|
||||
- if (oldEnc && !newDef->tpm) {
|
||||
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
- _("Removing an encrypted TPM is not allowed"));
|
||||
- return -1;
|
||||
- }
|
||||
- newEnc = newDef->tpm->data.emulator.hassecretuuid;
|
||||
- if (oldEnc != newEnc) {
|
||||
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED, "%s",
|
||||
- _("TPM state encryption cannot be changed "
|
||||
- "once VM was started"));
|
||||
- return -1;
|
||||
- }
|
||||
- }
|
||||
- break;
|
||||
- case VIR_DOMAIN_TPM_TYPE_PASSTHROUGH:
|
||||
- case VIR_DOMAIN_TPM_TYPE_LAST:
|
||||
- break;
|
||||
- }
|
||||
-
|
||||
- return 0;
|
||||
-}
|
||||
-
|
||||
-
|
||||
-int
|
||||
-virDomainCheckDeviceChanges(virDomainDefPtr def,
|
||||
- virDomainDefPtr newDef)
|
||||
-{
|
||||
- if (!def || !newDef)
|
||||
- return 0;
|
||||
-
|
||||
- return virDomainCheckTPMChanges(def, newDef);
|
||||
-}
|
||||
diff --git a/src/conf/domain_conf.h b/src/conf/domain_conf.h
|
||||
index 8a4425df64..d5190a20db 100644
|
||||
--- a/src/conf/domain_conf.h
|
||||
+++ b/src/conf/domain_conf.h
|
||||
@@ -3638,6 +3638,3 @@ virDomainGraphicsGetRenderNode(const virDomainGraphicsDef *graphics);
|
||||
|
||||
bool
|
||||
virDomainGraphicsNeedsAutoRenderNode(const virDomainGraphicsDef *graphics);
|
||||
-
|
||||
-int
|
||||
-virDomainCheckDeviceChanges(virDomainDefPtr def, virDomainDefPtr newDef);
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index 9fd778272f..bbc5144aa2 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -216,7 +216,6 @@ virDomainBootTypeFromString;
|
||||
virDomainBootTypeToString;
|
||||
virDomainCapabilitiesPolicyTypeToString;
|
||||
virDomainCapsFeatureTypeToString;
|
||||
-virDomainCheckDeviceChanges;
|
||||
virDomainChrConsoleTargetTypeFromString;
|
||||
virDomainChrConsoleTargetTypeToString;
|
||||
virDomainChrDefForeach;
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 4ca3eb7bde..1ba6def419 100644
|
||||
--- a/src/qemu/qemu_driver.c
|
||||
+++ b/src/qemu/qemu_driver.c
|
||||
@@ -53,7 +53,6 @@
|
||||
#include "qemu_migration_params.h"
|
||||
#include "qemu_blockjob.h"
|
||||
#include "qemu_security.h"
|
||||
-#include "qemu_extdevice.h"
|
||||
|
||||
#include "virerror.h"
|
||||
#include "virlog.h"
|
||||
@@ -7760,30 +7759,6 @@ qemuDomainCreate(virDomainPtr dom)
|
||||
return qemuDomainCreateWithFlags(dom, 0);
|
||||
}
|
||||
|
||||
-static int
|
||||
-qemuDomainCheckDeviceChanges(virQEMUDriverPtr driver,
|
||||
- virDomainDefPtr def)
|
||||
-{
|
||||
- virDomainObjPtr vm;
|
||||
- int ret;
|
||||
-
|
||||
- vm = virDomainObjListFindByUUID(driver->domains, def->uuid);
|
||||
- if (!vm)
|
||||
- return 0;
|
||||
-
|
||||
- if (qemuExtDevicesInitPaths(driver, vm->def) < 0) {
|
||||
- ret = -1;
|
||||
- goto cleanup;
|
||||
- }
|
||||
-
|
||||
- ret = virDomainCheckDeviceChanges(vm->def, def);
|
||||
-
|
||||
- cleanup:
|
||||
- virDomainObjEndAPI(&vm);
|
||||
-
|
||||
- return ret;
|
||||
-}
|
||||
-
|
||||
static virDomainPtr
|
||||
qemuDomainDefineXMLFlags(virConnectPtr conn,
|
||||
const char *xml,
|
||||
@@ -7820,9 +7795,6 @@ qemuDomainDefineXMLFlags(virConnectPtr conn,
|
||||
if (virDomainDefineXMLFlagsEnsureACL(conn, def) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- if (qemuDomainCheckDeviceChanges(driver, def) < 0)
|
||||
- goto cleanup;
|
||||
-
|
||||
if (!(vm = virDomainObjListAdd(driver->domains, def,
|
||||
driver->xmlopt,
|
||||
0, &oldDef)))
|
||||
diff --git a/src/qemu/qemu_extdevice.c b/src/qemu/qemu_extdevice.c
|
||||
index af52466421..dc032aa60c 100644
|
||||
--- a/src/qemu/qemu_extdevice.c
|
||||
+++ b/src/qemu/qemu_extdevice.c
|
||||
@@ -79,7 +79,7 @@ qemuExtDeviceLogCommand(qemuDomainLogContextPtr logCtxt,
|
||||
* stored and we can remove directories and files in case of domain XML
|
||||
* changes.
|
||||
*/
|
||||
-int
|
||||
+static int
|
||||
qemuExtDevicesInitPaths(virQEMUDriverPtr driver,
|
||||
virDomainDefPtr def)
|
||||
{
|
||||
diff --git a/src/qemu/qemu_extdevice.h b/src/qemu/qemu_extdevice.h
|
||||
index 5a53c79f38..039b3e60dd 100644
|
||||
--- a/src/qemu/qemu_extdevice.h
|
||||
+++ b/src/qemu/qemu_extdevice.h
|
||||
@@ -54,6 +54,3 @@ bool qemuExtDevicesHasDevice(virDomainDefPtr def);
|
||||
int qemuExtDevicesSetupCgroup(virQEMUDriverPtr driver,
|
||||
virDomainDefPtr def,
|
||||
virCgroupPtr cgroup);
|
||||
-
|
||||
-int qemuExtDevicesInitPaths(virQEMUDriverPtr driver,
|
||||
- virDomainDefPtr def);
|
||||
@@ -0,0 +1,59 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Thu, 15 Aug 2019 21:52:28 -0400
|
||||
Subject: [PATCH] network: fix crash during cleanup from failure to allocate
|
||||
port
|
||||
|
||||
During networkPortCreateXML, if networkAllocatePort() failed,
|
||||
networkReleasePort() would be called, which would (in the case of
|
||||
network pools of macvtap passthrough devices) attempt to find the
|
||||
allocated device by comparing port->plug.direct.linkdev to each device
|
||||
in the pool. Since port->plug.direct.linkdev was still NULL, the
|
||||
attempted strcmp would result in a SEGV.
|
||||
|
||||
Calling networkReleasePort() during error cleanup is something that
|
||||
should only be done if networkAllocatePort() has already succeeded. It
|
||||
turns out there is one other possible error exit from
|
||||
networkPortCreateXML() that happens after networkAllocatePort() has
|
||||
succeeded, so the code to call networkReleasePort() was just moved
|
||||
down to there.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/1741390
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit dac697e8d7d6d9a607e61caeeec06b259edf513f)
|
||||
---
|
||||
src/network/bridge_driver.c | 12 ++++++------
|
||||
1 file changed, 6 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index 41fa89a4af..bc0f781c56 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -5592,20 +5592,20 @@ networkPortCreateXML(virNetworkPtr net,
|
||||
rc = networkNotifyPort(obj, portdef);
|
||||
else
|
||||
rc = networkAllocatePort(obj, portdef);
|
||||
- if (rc < 0) {
|
||||
+ if (rc < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (virNetworkObjAddPort(obj, portdef, driver->stateDir) < 0) {
|
||||
virErrorPtr saved;
|
||||
+
|
||||
saved = virSaveLastError();
|
||||
ignore_value(networkReleasePort(obj, portdef));
|
||||
+ virNetworkPortDefFree(portdef);
|
||||
virSetError(saved);
|
||||
virFreeError(saved);
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if (virNetworkObjAddPort(obj, portdef, driver->stateDir) < 0) {
|
||||
- virNetworkPortDefFree(portdef);
|
||||
- goto cleanup;
|
||||
- }
|
||||
-
|
||||
ret = virGetNetworkPort(net, portdef->uuid);
|
||||
cleanup:
|
||||
virNetworkObjEndAPI(&obj);
|
||||
@@ -0,0 +1,57 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Thu, 15 Aug 2019 22:28:27 -0400
|
||||
Subject: [PATCH] network: replace virSaveLastError() with
|
||||
virErrorPreserveLast()
|
||||
|
||||
virErrorPreserveLast()/virErrorRestore() (added in commit 8333e7455
|
||||
back in 2017), do a better better job of saving and restoring the last
|
||||
libvirt error than virSaveLastError()/virErrorRestore() (they're
|
||||
simpler, and they also save/restore the system errno).
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit 39de732aa728ae9b8a9414ad08b8d0ee7ed02732)
|
||||
---
|
||||
src/network/bridge_driver.c | 17 ++++++++---------
|
||||
1 file changed, 8 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index bc0f781c56..c7e5151d09 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -2987,13 +2987,12 @@ networkStartNetwork(virNetworkDriverStatePtr driver,
|
||||
|
||||
cleanup:
|
||||
if (ret < 0) {
|
||||
+ virErrorPtr save_err;
|
||||
+
|
||||
+ virErrorPreserveLast(&save_err);
|
||||
virNetworkObjUnsetDefTransient(obj);
|
||||
- virErrorPtr save_err = virSaveLastError();
|
||||
- int save_errno = errno;
|
||||
networkShutdownNetwork(driver, obj);
|
||||
- virSetError(save_err);
|
||||
- virFreeError(save_err);
|
||||
- errno = save_errno;
|
||||
+ virErrorRestore(&save_err);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
@@ -5596,13 +5595,13 @@ networkPortCreateXML(virNetworkPtr net,
|
||||
goto cleanup;
|
||||
|
||||
if (virNetworkObjAddPort(obj, portdef, driver->stateDir) < 0) {
|
||||
- virErrorPtr saved;
|
||||
+ virErrorPtr save_err;
|
||||
|
||||
- saved = virSaveLastError();
|
||||
+ virErrorPreserveLast(&save_err);
|
||||
ignore_value(networkReleasePort(obj, portdef));
|
||||
virNetworkPortDefFree(portdef);
|
||||
- virSetError(saved);
|
||||
- virFreeError(saved);
|
||||
+ virErrorRestore(&save_err);
|
||||
+
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Thu, 15 Aug 2019 16:34:21 -0400
|
||||
Subject: [PATCH] access: fix incorrect addition to virAccessPermNetwork
|
||||
|
||||
Commit e69444e17 (first appeared in libvirt-5.5.0) added the new value
|
||||
"VIR_ACCESS_PERM_NETWORK_SEARCH_PORTS" to the virAccessPerNetwork
|
||||
enum, and also the string "search_ports" to the VIR_ENUM_IMPL() macro
|
||||
for that enum. Unfortunately, the enum value was added in the middle
|
||||
of the list, while the string was added to the end of the
|
||||
VIR_ENUM_IMPL().
|
||||
|
||||
This patch corrects that error by moving the new value to the end of
|
||||
the enum definition, so that the order matches that of the string
|
||||
list.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/1741428
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit 8d6eaf5e099dab8400aa76bcc9a0ac74ff6f46e1)
|
||||
---
|
||||
src/access/viraccessperm.h | 12 ++++++------
|
||||
1 file changed, 6 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/src/access/viraccessperm.h b/src/access/viraccessperm.h
|
||||
index a42512d5e0..7480ee8c2f 100644
|
||||
--- a/src/access/viraccessperm.h
|
||||
+++ b/src/access/viraccessperm.h
|
||||
@@ -410,18 +410,18 @@ typedef enum {
|
||||
*/
|
||||
VIR_ACCESS_PERM_NETWORK_START,
|
||||
|
||||
- /**
|
||||
- * @desc: List network ports
|
||||
- * @message: Listing network ports requires authorization
|
||||
- */
|
||||
- VIR_ACCESS_PERM_NETWORK_SEARCH_PORTS,
|
||||
-
|
||||
/**
|
||||
* @desc: Stop network
|
||||
* @message: Stopping network requires authorization
|
||||
*/
|
||||
VIR_ACCESS_PERM_NETWORK_STOP,
|
||||
|
||||
+ /**
|
||||
+ * @desc: List network ports
|
||||
+ * @message: Listing network ports requires authorization
|
||||
+ */
|
||||
+ VIR_ACCESS_PERM_NETWORK_SEARCH_PORTS,
|
||||
+
|
||||
VIR_ACCESS_PERM_NETWORK_LAST
|
||||
} virAccessPermNetwork;
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
|
||||
Date: Thu, 8 Aug 2019 13:42:24 +0100
|
||||
Subject: [PATCH] network: fix ability to use openvswitch with vlans
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Use the correct enum constant when validating vlan usage.
|
||||
This fixes a merge error in
|
||||
|
||||
commit 6cb0ec48bd95c95489a987e05a88e8bcf1f9109c
|
||||
Author: Daniel P. Berrangé <berrange@redhat.com>
|
||||
Date: Mon Sep 3 17:34:22 2018 +0100
|
||||
|
||||
network: convert networkAllocateActualDevice to virNetworkPortDef
|
||||
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit 93c1d5fe7bb7a62ef884eb41b505b2809d1704b6)
|
||||
---
|
||||
src/network/bridge_driver.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index c7e5151d09..acaeb5c9a2 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -4813,7 +4813,7 @@ networkAllocatePort(virNetworkObjPtr obj,
|
||||
if (!(port->plugtype == VIR_NETWORK_PORT_PLUG_TYPE_HOSTDEV_PCI ||
|
||||
(port->plugtype == VIR_NETWORK_PORT_PLUG_TYPE_DIRECT &&
|
||||
port->plug.direct.mode == VIR_NETDEV_MACVLAN_MODE_PASSTHRU) ||
|
||||
- (port->plugtype == VIR_DOMAIN_NET_TYPE_BRIDGE &&
|
||||
+ (port->plugtype == VIR_NETWORK_PORT_PLUG_TYPE_BRIDGE &&
|
||||
port->virtPortProfile &&
|
||||
port->virtPortProfile->virtPortType == VIR_NETDEV_VPORT_PROFILE_OPENVSWITCH))) {
|
||||
virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
|
||||
@@ -0,0 +1,127 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Sun, 11 Aug 2019 16:21:42 -0400
|
||||
Subject: [PATCH] util: allow tap-based guest interfaces to have MAC address
|
||||
prefix 0xFE
|
||||
|
||||
Back in July 2010, commit 6ea90b84 (meant to resolve
|
||||
https://bugzilla.redhat.com/571991 ) added code to set the MAC address
|
||||
of any tap device to the associated guest interface's MAC, but with
|
||||
the first byte replaced with 0xFE. This was done in order to assure
|
||||
that
|
||||
|
||||
1) the tap MAC and guest interface MAC were different (otherwise L2
|
||||
forwarding through the tap would not work, and the kernel would
|
||||
repeatedly issue a warning stating as much).
|
||||
|
||||
2) any bridge device that had one of these taps attached would *not*
|
||||
take on the MAC of the tap (leading to network instability as
|
||||
guests started and stopped)
|
||||
|
||||
A couple years later, https://bugzilla.redhat.com/798467 was filed,
|
||||
complaining that a user could configure a tap-based guest interface to
|
||||
have a MAC address that itself had a first byte of 0xFE, silently
|
||||
(other than the kernel warning messages) resulting in a non-working
|
||||
configuration. This was fixed by commit 5d571045, which logged an
|
||||
error and failed the guest start / interface attach if the MAC's first
|
||||
byte was 0xFE.
|
||||
|
||||
Although this restriction only reduces the potential pool of MAC
|
||||
addresses from 2^46 (last two bits of byte 1 must be set to 10) by
|
||||
2^32 (still 4 orders of magnitude larger than the entire IPv4 address
|
||||
space), it also means that management software that autogenerates MAC
|
||||
addresses must have special code to avoid an 0xFE prefix. Now after 7
|
||||
years, someone has noticed this restriction and requested that we
|
||||
remove it.
|
||||
|
||||
So instead of failing when 0xFE is found as the first byte, this patch
|
||||
removes the restriction by just replacing the first byte in the tap
|
||||
device MAC with 0xFA if the first byte in the guest interface is
|
||||
0xFE. 0xFA is the next-highest value that still has 10 as the lowest
|
||||
two bits, and still
|
||||
|
||||
2) meets the requirement of "tap MAC must be different from guest
|
||||
interface MAC", and
|
||||
|
||||
3) is high enough that there should never be an issue of the attached
|
||||
bridge device taking on the MAC of the tap.
|
||||
|
||||
The result is that *any* MAC can be chosen by management software
|
||||
(although it would still not work correctly if a multicast MAC (lowest
|
||||
bit of first byte set to 1) was chosen), but that's a different
|
||||
issue).
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com
|
||||
(cherry picked from commit a60ee914009aa7f1a27fc0563337ded08b09247f)
|
||||
---
|
||||
src/qemu/qemu_interface.c | 11 ++++++++++-
|
||||
src/util/virnetdevtap.c | 26 ++++++++++++--------------
|
||||
2 files changed, 22 insertions(+), 15 deletions(-)
|
||||
|
||||
diff --git a/src/qemu/qemu_interface.c b/src/qemu/qemu_interface.c
|
||||
index c8effa68f4..72ed51cb1f 100644
|
||||
--- a/src/qemu/qemu_interface.c
|
||||
+++ b/src/qemu/qemu_interface.c
|
||||
@@ -444,8 +444,17 @@ qemuInterfaceEthernetConnect(virDomainDefPtr def,
|
||||
}
|
||||
|
||||
virDomainAuditNetDevice(def, net, tunpath, true);
|
||||
+
|
||||
+ /* The tap device's MAC address cannot match the MAC address
|
||||
+ * used by the guest. This results in "received packet on
|
||||
+ * vnetX with own address as source address" error logs from
|
||||
+ * the kernel.
|
||||
+ */
|
||||
virMacAddrSet(&tapmac, &net->mac);
|
||||
- tapmac.addr[0] = 0xFE;
|
||||
+ if (tapmac.addr[0] == 0xFE)
|
||||
+ tapmac.addr[0] = 0xFA;
|
||||
+ else
|
||||
+ tapmac.addr[0] = 0xFE;
|
||||
|
||||
if (virNetDevSetMAC(net->ifname, &tapmac) < 0)
|
||||
goto cleanup;
|
||||
diff --git a/src/util/virnetdevtap.c b/src/util/virnetdevtap.c
|
||||
index b65c26bee1..4548b51b5b 100644
|
||||
--- a/src/util/virnetdevtap.c
|
||||
+++ b/src/util/virnetdevtap.c
|
||||
@@ -668,7 +668,6 @@ int virNetDevTapCreateInBridgePort(const char *brname,
|
||||
unsigned int flags)
|
||||
{
|
||||
virMacAddr tapmac;
|
||||
- char macaddrstr[VIR_MAC_STRING_BUFLEN];
|
||||
size_t i;
|
||||
|
||||
if (virNetDevTapCreate(ifname, tunpath, tapfd, tapfdSize, flags) < 0)
|
||||
@@ -682,19 +681,18 @@ int virNetDevTapCreateInBridgePort(const char *brname,
|
||||
*/
|
||||
virMacAddrSet(&tapmac, macaddr);
|
||||
if (!(flags & VIR_NETDEV_TAP_CREATE_USE_MAC_FOR_BRIDGE)) {
|
||||
- if (macaddr->addr[0] == 0xFE) {
|
||||
- /* For normal use, the tap device's MAC address cannot
|
||||
- * match the MAC address used by the guest. This results
|
||||
- * in "received packet on vnetX with own address as source
|
||||
- * address" error logs from the kernel.
|
||||
- */
|
||||
- virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
|
||||
- _("Unable to use MAC address starting with "
|
||||
- "reserved value 0xFE - '%s' - "),
|
||||
- virMacAddrFormat(macaddr, macaddrstr));
|
||||
- goto error;
|
||||
- }
|
||||
- tapmac.addr[0] = 0xFE; /* Discourage bridge from using TAP dev MAC */
|
||||
+ /* The tap device's MAC address cannot match the MAC address
|
||||
+ * used by the guest. This results in "received packet on
|
||||
+ * vnetX with own address as source address" error logs from
|
||||
+ * the kernel. Making the tap address as high as possible
|
||||
+ * discourages the bridge from using this tap's MAC as its own
|
||||
+ * (a Linux host bridge will take on the lowest numbered MAC
|
||||
+ * of all devices attached to it).
|
||||
+ */
|
||||
+ if (tapmac.addr[0] == 0xFE)
|
||||
+ tapmac.addr[0] = 0xFA;
|
||||
+ else
|
||||
+ tapmac.addr[0] = 0xFE;
|
||||
}
|
||||
|
||||
if (virNetDevSetMAC(*ifname, &tapmac) < 0)
|
||||
@@ -0,0 +1,39 @@
|
||||
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
|
||||
Date: Thu, 22 Aug 2019 14:48:46 +0100
|
||||
Subject: [PATCH] remote: use Wants instead of Requires for libvirtd sockets
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
To facilitate upgrades from earlier versions of libvirt which did not
|
||||
use socket activation for libvirtd, we want to allow the libvirtd socket
|
||||
units to be disabled (masked). This can only be supported if we use the
|
||||
weaker Wants statement instead of Requires.
|
||||
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit ec7e31ed32065837e201cd3d8a3fb882e43b7fdb)
|
||||
---
|
||||
src/remote/libvirtd.service.in | 9 ++++++---
|
||||
1 file changed, 6 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/src/remote/libvirtd.service.in b/src/remote/libvirtd.service.in
|
||||
index 3ddf0e229b..914bcbd5c4 100644
|
||||
--- a/src/remote/libvirtd.service.in
|
||||
+++ b/src/remote/libvirtd.service.in
|
||||
@@ -2,9 +2,12 @@
|
||||
Description=Virtualization daemon
|
||||
Requires=virtlogd.socket
|
||||
Requires=virtlockd.socket
|
||||
-Requires=libvirtd.socket
|
||||
-Requires=libvirtd-ro.socket
|
||||
-Requires=libvirtd-admin.socket
|
||||
+# Use Wants instead of Requires so that users
|
||||
+# can disable these three .socket units to revert
|
||||
+# to a traditional non-activation deployment setup
|
||||
+Wants=libvirtd.socket
|
||||
+Wants=libvirtd-ro.socket
|
||||
+Wants=libvirtd-admin.socket
|
||||
Wants=systemd-machined.service
|
||||
Before=libvirt-guests.service
|
||||
After=network.target
|
||||
@@ -0,0 +1,67 @@
|
||||
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
|
||||
Date: Thu, 29 Aug 2019 12:04:42 +0100
|
||||
Subject: [PATCH] remote: move timeout arg into sysconf file
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
We need to give users the ability to customize the length of the
|
||||
shutdown timeout, or even disable timeouts entirely. Thus we must move
|
||||
the timeout arg into the sysconf file, instead of the service unit.
|
||||
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit 581767a98ab5f674ac335d6c270efa8576bfdfbf)
|
||||
|
||||
Conflicts:
|
||||
src/remote/libvirtd.service.in - due to not having
|
||||
5b816e16968ba02def56f067774ecd9a8c8d44d7 in rhel8
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741403
|
||||
Message-Id: <20190829110444.12163-3-berrange@redhat.com>
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Cole Robinson <crobinso@redhat.com>
|
||||
---
|
||||
src/remote/libvirtd.service.in | 6 +-----
|
||||
src/remote/libvirtd.sysconf | 12 +++++++++---
|
||||
2 files changed, 10 insertions(+), 8 deletions(-)
|
||||
|
||||
diff --git a/src/remote/libvirtd.service.in b/src/remote/libvirtd.service.in
|
||||
index 914bcbd5c4..d5d98f0c12 100644
|
||||
--- a/src/remote/libvirtd.service.in
|
||||
+++ b/src/remote/libvirtd.service.in
|
||||
@@ -24,11 +24,7 @@ Documentation=https://libvirt.org
|
||||
[Service]
|
||||
Type=notify
|
||||
EnvironmentFile=-/etc/sysconfig/libvirtd
|
||||
-# libvirtd.service is set to run on boot so that autostart of
|
||||
-# VMs can be performed. We don't want it to stick around if
|
||||
-# unused though, so we set a timeout. The socket activation
|
||||
-# then ensures it gets started again if anything needs it
|
||||
-ExecStart=@sbindir@/libvirtd --timeout 120 $LIBVIRTD_ARGS
|
||||
+ExecStart=@sbindir@/libvirtd $LIBVIRTD_ARGS
|
||||
ExecReload=/bin/kill -HUP $MAINPID
|
||||
KillMode=process
|
||||
Restart=on-failure
|
||||
diff --git a/src/remote/libvirtd.sysconf b/src/remote/libvirtd.sysconf
|
||||
index 5969518bf2..ee9db22bab 100644
|
||||
--- a/src/remote/libvirtd.sysconf
|
||||
+++ b/src/remote/libvirtd.sysconf
|
||||
@@ -1,8 +1,14 @@
|
||||
# Customizations for the libvirtd.service systemd unit
|
||||
|
||||
-# Listen for TCP/IP connections. This is not required if using systemd
|
||||
-# socket activation.
|
||||
-# NB. must setup TLS/SSL keys prior to using this
|
||||
+# Default behaviour is for libvirtd.service to start on boot
|
||||
+# so that VM autostart can be performed. We then want it to
|
||||
+# shutdown again if nothing was started and rely on systemd
|
||||
+# socket activation to start it again when some client app
|
||||
+# connects.
|
||||
+LIBVIRTD_ARGS="--timeout 120"
|
||||
+
|
||||
+# If systemd socket activation is disabled, then the following
|
||||
+# can be used to listen on TCP/TLS sockets
|
||||
#LIBVIRTD_ARGS="--listen"
|
||||
|
||||
# Override Kerberos service keytab for SASL/GSSAPI
|
||||
@@ -0,0 +1,99 @@
|
||||
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
|
||||
Date: Thu, 29 Aug 2019 12:04:43 +0100
|
||||
Subject: [PATCH] remote: forbid the --listen arg when systemd socket
|
||||
activation
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
When using systemd socket activation the --listen arg has no
|
||||
effect. This is confusing to users upgrading from previous versions of
|
||||
libvirt as their config is silently ignored. Turn use of --listen into a
|
||||
fatal error when sockets are passed from systemd.
|
||||
|
||||
This helps the admin discover the change in behaviour and thus decide
|
||||
whether to stick with socket activation or revert to previous behaviour.
|
||||
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit 3a6a725b8f575890ee6c151ad1f46ea0ceea1f3b)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741403
|
||||
Message-Id: <20190829110444.12163-4-berrange@redhat.com>
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Cole Robinson <crobinso@redhat.com>
|
||||
---
|
||||
src/remote/libvirtd.pod | 33 ++++++++++++++++++++++++++++++++-
|
||||
src/remote/remote_daemon.c | 8 ++++++++
|
||||
2 files changed, 40 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/remote/libvirtd.pod b/src/remote/libvirtd.pod
|
||||
index 4721e0f4ec..fa30d6a37a 100644
|
||||
--- a/src/remote/libvirtd.pod
|
||||
+++ b/src/remote/libvirtd.pod
|
||||
@@ -30,6 +30,35 @@ and will be picked up automatically if their XML configuration has been
|
||||
defined. Any guests whose XML configuration has not been defined will be lost
|
||||
from the configuration.
|
||||
|
||||
+=head1 SYSTEM SOCKET ACTIVATION
|
||||
+
|
||||
+The B<libvirtd> daemon is capable of starting in two modes.
|
||||
+
|
||||
+In the traditional mode, it will create and listen on UNIX sockets itself.
|
||||
+If the B<--listen> parameter is given, it will also listen on TCP/IP socket(s),
|
||||
+according to the B<listen_tcp> and B<listen_tls> options in
|
||||
+B</etc/libvirt/libvirtd.conf>
|
||||
+
|
||||
+In socket activation mode, it will rely on systemd to create and listen
|
||||
+on the UNIX, and optionally TCP/IP, sockets and pass them as pre-opened
|
||||
+file descriptors. In this mode, it is not permitted to pass the B<--listen>
|
||||
+parameter, and most of the socket related config options in
|
||||
+B</etc/libvirt/libvirtd.conf> will no longer have any effect. To enable
|
||||
+TCP or TLS sockets use either
|
||||
+
|
||||
+B<$ systemctl start libvirtd-tls.socket>
|
||||
+
|
||||
+Or
|
||||
+
|
||||
+B<$ systemctl start libvirtd-tcp.socket>
|
||||
+
|
||||
+Socket activation mode is generally the default when running on a host
|
||||
+OS that uses systemd. To revert to the traditional mode, all the socket
|
||||
+unit files must be masked:
|
||||
+
|
||||
+B<$ systemctl mask libvirtd.socket libvirtd-ro.socket \
|
||||
+ libvirtd-admin.socket libvirtd-tls.socket libvirtd-tcp.socket>
|
||||
+
|
||||
=head1 OPTIONS
|
||||
|
||||
=over
|
||||
@@ -48,7 +77,9 @@ Use this configuration file, overriding the default value.
|
||||
|
||||
=item B<-l, --listen>
|
||||
|
||||
-Listen for TCP/IP connections.
|
||||
+Listen for TCP/IP connections. This should not be set if using systemd
|
||||
+socket activation. Instead activate the libvirtd-tls.socket or
|
||||
+libvirtd-tcp.socket unit files.
|
||||
|
||||
=item B<-p, --pid-file> I<FILE>
|
||||
|
||||
diff --git a/src/remote/remote_daemon.c b/src/remote/remote_daemon.c
|
||||
index d887b7abfb..b7ee1cf49b 100644
|
||||
--- a/src/remote/remote_daemon.c
|
||||
+++ b/src/remote/remote_daemon.c
|
||||
@@ -391,6 +391,14 @@ daemonSetupNetworking(virNetServerPtr srv,
|
||||
if (virSystemdGetActivation(actmap, ARRAY_CARDINALITY(actmap), &act) < 0)
|
||||
return -1;
|
||||
|
||||
+#ifdef WITH_IP
|
||||
+ if (act && ipsock) {
|
||||
+ VIR_ERROR(_("--listen parameter not permitted with systemd activation "
|
||||
+ "sockets, see 'man libvirtd' for further guidance"));
|
||||
+ return -1;
|
||||
+ }
|
||||
+#endif /* ! WITH_IP */
|
||||
+
|
||||
if (config->unix_sock_group) {
|
||||
if (virGetGroupID(config->unix_sock_group, &unix_sock_gid) < 0)
|
||||
return ret;
|
||||
@@ -0,0 +1,86 @@
|
||||
From: =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= <berrange@redhat.com>
|
||||
Date: Thu, 29 Aug 2019 12:04:44 +0100
|
||||
Subject: [PATCH] rpm: don't enable socket activation in upgrade if --listen
|
||||
present
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Currently during RPM upgrade we restart libvirtd and unconditionally
|
||||
enable use of systemd socket activation for the UNIX sockets.
|
||||
|
||||
If the user had previously given the --listen arg to libvirtd though,
|
||||
this will no longer be honoured if socket activation is used.
|
||||
|
||||
We could start libvirtd-tcp.socket or libvirtd-tls.socket for this,
|
||||
but mgmt tools like puppet/ansible might not be expecting this.
|
||||
So for now we silently disable socket activation if we see --listen
|
||||
was previously set on the host.
|
||||
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit 66d04312d03c24c62bcf3b1dc2706f8775d4e2d3)
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1741403
|
||||
Message-Id: <20190829110444.12163-5-berrange@redhat.com>
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
Signed-off-by: Cole Robinson <crobinso@redhat.com>
|
||||
---
|
||||
libvirt.spec.in | 44 +++++++++++++++++++++++++++++++-------------
|
||||
1 file changed, 31 insertions(+), 13 deletions(-)
|
||||
|
||||
diff --git a/libvirt.spec.in b/libvirt.spec.in
|
||||
index 045c0fed1a..58f7cae092 100644
|
||||
--- a/libvirt.spec.in
|
||||
+++ b/libvirt.spec.in
|
||||
@@ -1378,19 +1378,37 @@ fi
|
||||
|
||||
%posttrans daemon
|
||||
if [ -f %{_localstatedir}/lib/rpm-state/libvirt/restart ]; then
|
||||
- # Old libvirtd owns the sockets and will delete them on
|
||||
- # shutdown. Can't use a try-restart as libvirtd will simply
|
||||
- # own the sockets again when it comes back up. Thus we must
|
||||
- # do this particular ordering
|
||||
- /bin/systemctl is-active libvirtd.service 1>/dev/null 2>&1
|
||||
- if test $? = 0 ; then
|
||||
- /bin/systemctl stop libvirtd.service >/dev/null 2>&1 || :
|
||||
-
|
||||
- /bin/systemctl try-restart libvirtd.socket >/dev/null 2>&1 || :
|
||||
- /bin/systemctl try-restart libvirtd-ro.socket >/dev/null 2>&1 || :
|
||||
- /bin/systemctl try-restart libvirtd-admin.socket >/dev/null 2>&1 || :
|
||||
-
|
||||
- /bin/systemctl start libvirtd.service >/dev/null 2>&1 || :
|
||||
+ # See if user has previously modified their install to
|
||||
+ # tell libvirtd to use --listen
|
||||
+ grep -E '^LIBVIRTD_ARGS=.*--listen' /etc/sysconfig/libvirtd 1>/dev/null 2>&1
|
||||
+ if test $? = 0
|
||||
+ then
|
||||
+ # Then lets keep honouring --listen and *not* use
|
||||
+ # systemd socket activation, because switching things
|
||||
+ # might confuse mgmt tool like puppet/ansible that
|
||||
+ # expect the old style libvirtd
|
||||
+ /bin/systemctl mask libvirtd.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl mask libvirtd-ro.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl mask libvirtd-admin.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl mask libvirtd-tls.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl mask libvirtd-tcp.socket >/dev/null 2>&1 || :
|
||||
+ else
|
||||
+ # Old libvirtd owns the sockets and will delete them on
|
||||
+ # shutdown. Can't use a try-restart as libvirtd will simply
|
||||
+ # own the sockets again when it comes back up. Thus we must
|
||||
+ # do this particular ordering, so that we get libvirtd
|
||||
+ # running with socket activation in use
|
||||
+ /bin/systemctl is-active libvirtd.service 1>/dev/null 2>&1
|
||||
+ if test $? = 0
|
||||
+ then
|
||||
+ /bin/systemctl stop libvirtd.service >/dev/null 2>&1 || :
|
||||
+
|
||||
+ /bin/systemctl try-restart libvirtd.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl try-restart libvirtd-ro.socket >/dev/null 2>&1 || :
|
||||
+ /bin/systemctl try-restart libvirtd-admin.socket >/dev/null 2>&1 || :
|
||||
+
|
||||
+ /bin/systemctl start libvirtd.service >/dev/null 2>&1 || :
|
||||
+ fi
|
||||
fi
|
||||
fi
|
||||
rm -rf %{_localstatedir}/lib/rpm-state/libvirt || :
|
||||
@@ -0,0 +1,27 @@
|
||||
From: Michael Chapman <mike@very.puzzling.org>
|
||||
Date: Tue, 17 Sep 2019 17:03:57 +1000
|
||||
Subject: [PATCH] remote: fix registration of TLS socket
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
Signed-off-by: Michael Chapman <mike@very.puzzling.org>
|
||||
(cherry picked from commit 522b3d2b24d0f7ac78dad442c990d4e34db0eaf2)
|
||||
---
|
||||
src/remote/remote_daemon.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/remote/remote_daemon.c b/src/remote/remote_daemon.c
|
||||
index b7ee1cf49b..6b5a6c1523 100644
|
||||
--- a/src/remote/remote_daemon.c
|
||||
+++ b/src/remote/remote_daemon.c
|
||||
@@ -473,7 +473,7 @@ daemonSetupNetworking(virNetServerPtr srv,
|
||||
config->max_client_requests) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- if (((ipsock && config->listen_tls) || (act && virSystemdActivationHasName(act, "ip-tls")))) {
|
||||
+ if (((ipsock && config->listen_tls) || (act && virSystemdActivationHasName(act, "libvirtd-tls.socket")))) {
|
||||
virNetTLSContextPtr ctxt = NULL;
|
||||
|
||||
if (config->ca_file ||
|
||||
@@ -0,0 +1,34 @@
|
||||
From: Pavel Hrdina <phrdina@redhat.com>
|
||||
Date: Thu, 5 Sep 2019 11:22:11 +0200
|
||||
Subject: [PATCH] vircgroupv2: fix setting cpu.max period
|
||||
|
||||
When we set cpu.max period we need to parse the cpu.max file first as
|
||||
it contains both quota and period values separated by space. When only
|
||||
a single number is written to that file it will set quota. However,
|
||||
in order to change period we need to write both values.
|
||||
|
||||
The code was prepared for that but mistakenly used new line to end the
|
||||
string with the first value.
|
||||
|
||||
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1749227
|
||||
|
||||
Signed-off-by: Pavel Hrdina <phrdina@redhat.com>
|
||||
Reviewed-by: Erik Skultety <eskultet@redhat.com>
|
||||
(cherry picked from commit 0bd4ad193d8ba7f0104f4739f19f2731e7cf9f56)
|
||||
---
|
||||
src/util/vircgroupv2.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/util/vircgroupv2.c b/src/util/vircgroupv2.c
|
||||
index e36c36685b..d8abe18943 100644
|
||||
--- a/src/util/vircgroupv2.c
|
||||
+++ b/src/util/vircgroupv2.c
|
||||
@@ -1507,7 +1507,7 @@ virCgroupV2SetCpuCfsPeriod(virCgroupPtr group,
|
||||
_("Invalid 'cpu.max' data."));
|
||||
return -1;
|
||||
}
|
||||
- *tmp = '\n';
|
||||
+ *tmp = '\0';
|
||||
|
||||
if (virAsprintf(&value, "%s %llu", str, cfs_period) < 0)
|
||||
return -1;
|
||||
@@ -0,0 +1,55 @@
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Thu, 26 Sep 2019 15:00:55 -0400
|
||||
Subject: [PATCH] vircgroupv2: Fix VM startup when legacy cgroups are defined
|
||||
|
||||
On Fedora 31, starting a 'mock' build alters /proc/$pid/cgroup,
|
||||
probably due to usage of systemd-nspawn.
|
||||
|
||||
Before:
|
||||
$ cat /proc/self/cgroup
|
||||
0::/user.slice/user-1000.slice/...
|
||||
|
||||
After:
|
||||
$ cat /proc/self/cgroup
|
||||
1:name=systemd:/
|
||||
0::/user.slice/user-1000.slice/...
|
||||
|
||||
The cgroupv2 code mishandles that first line in the second case, which
|
||||
causes VM startup to fail with: Unable to read from
|
||||
'/sys/fs/cgroup/machine/cgroup.controllers': No such file or directory
|
||||
|
||||
The kernel docs[1] say that the cgroupv2 path will always start with
|
||||
'0::', which in the code here controllers="". Only set the v2 placement
|
||||
path when we see that cgroup file entry.
|
||||
|
||||
[1] https://www.kernel.org/doc/html/v5.3/admin-guide/cgroup-v2.html#processes
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1751120
|
||||
|
||||
Signed-off-by: Cole Robinson <crobinso@redhat.com>
|
||||
---
|
||||
src/util/vircgroupv2.c | 6 +++++-
|
||||
1 file changed, 5 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/util/vircgroupv2.c b/src/util/vircgroupv2.c
|
||||
index d8abe18943..acd48d1259 100644
|
||||
--- a/src/util/vircgroupv2.c
|
||||
+++ b/src/util/vircgroupv2.c
|
||||
@@ -194,12 +194,16 @@ virCgroupV2DetectMounts(virCgroupPtr group,
|
||||
static int
|
||||
virCgroupV2DetectPlacement(virCgroupPtr group,
|
||||
const char *path,
|
||||
- const char *controllers ATTRIBUTE_UNUSED,
|
||||
+ const char *controllers,
|
||||
const char *selfpath)
|
||||
{
|
||||
if (group->unified.placement)
|
||||
return 0;
|
||||
|
||||
+ /* controllers="" indicates the cgroupv2 controller path */
|
||||
+ if (STRNEQ_NULLABLE(controllers, ""))
|
||||
+ return 0;
|
||||
+
|
||||
/*
|
||||
* selfpath == "/" + path="" -> "/"
|
||||
* selfpath == "/libvirt.service" + path == "" -> "/libvirt.service"
|
||||
@@ -0,0 +1,72 @@
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Thu, 26 Sep 2019 15:25:52 -0400
|
||||
Subject: [PATCH] vircgroup: Add some VIR_DEBUG statements
|
||||
|
||||
These helped with debugging
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1612383
|
||||
|
||||
Signed-off-by: Cole Robinson <crobinso@redhat.com>
|
||||
---
|
||||
src/util/vircgroup.c | 3 ++-
|
||||
src/util/vircgroupv2.c | 9 +++++++++
|
||||
2 files changed, 11 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/util/vircgroup.c b/src/util/vircgroup.c
|
||||
index 825f62a97b..4f9d80666d 100644
|
||||
--- a/src/util/vircgroup.c
|
||||
+++ b/src/util/vircgroup.c
|
||||
@@ -1157,7 +1157,8 @@ virCgroupNewMachineSystemd(const char *name,
|
||||
virCgroupFree(&init);
|
||||
|
||||
if (!path || STREQ(path, "/") || path[0] != '/') {
|
||||
- VIR_DEBUG("Systemd didn't setup its controller");
|
||||
+ VIR_DEBUG("Systemd didn't setup its controller, path=%s",
|
||||
+ NULLSTR(path));
|
||||
return -2;
|
||||
}
|
||||
|
||||
diff --git a/src/util/vircgroupv2.c b/src/util/vircgroupv2.c
|
||||
index acd48d1259..c536be0cd9 100644
|
||||
--- a/src/util/vircgroupv2.c
|
||||
+++ b/src/util/vircgroupv2.c
|
||||
@@ -155,10 +155,14 @@ virCgroupV2CopyPlacement(virCgroupPtr group,
|
||||
const char *path,
|
||||
virCgroupPtr parent)
|
||||
{
|
||||
+ VIR_DEBUG("group=%p path=%s parent=%p", group, path, parent);
|
||||
+
|
||||
if (path[0] == '/') {
|
||||
if (VIR_STRDUP(group->unified.placement, path) < 0)
|
||||
return -1;
|
||||
} else {
|
||||
+ VIR_DEBUG("parent->unified.placement=%s", parent->unified.placement);
|
||||
+
|
||||
/*
|
||||
* parent == "/" + path="" => "/"
|
||||
* parent == "/libvirt.service" + path == "" => "/libvirt.service"
|
||||
@@ -172,6 +176,7 @@ virCgroupV2CopyPlacement(virCgroupPtr group,
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ VIR_DEBUG("set group->unified.placement=%s", group->unified.placement);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -200,6 +205,9 @@ virCgroupV2DetectPlacement(virCgroupPtr group,
|
||||
if (group->unified.placement)
|
||||
return 0;
|
||||
|
||||
+ VIR_DEBUG("group=%p path=%s controllers=%s selfpath=%s",
|
||||
+ group, path, controllers, selfpath);
|
||||
+
|
||||
/* controllers="" indicates the cgroupv2 controller path */
|
||||
if (STRNEQ_NULLABLE(controllers, ""))
|
||||
return 0;
|
||||
@@ -216,6 +224,7 @@ virCgroupV2DetectPlacement(virCgroupPtr group,
|
||||
path) < 0)
|
||||
return -1;
|
||||
|
||||
+ VIR_DEBUG("set group->unified.placement=%s", group->unified.placement);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Fri, 4 Oct 2019 16:33:37 +0200
|
||||
Subject: [PATCH] qemu_driver: Fix comment of qemuStateCleanup()
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
The comment says that the function kills domains and networks.
|
||||
This is obviously not the case.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit e0b90162c94c45a9b0cf197e45b71f26036725d8)
|
||||
---
|
||||
src/qemu/qemu_driver.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 1ba6def419..69416d6d1a 100644
|
||||
--- a/src/qemu/qemu_driver.c
|
||||
+++ b/src/qemu/qemu_driver.c
|
||||
@@ -1190,7 +1190,7 @@ qemuStateStop(void)
|
||||
/**
|
||||
* qemuStateCleanup:
|
||||
*
|
||||
- * Shutdown the QEMU daemon, it will stop all active domains and networks
|
||||
+ * Release resources allocated by QEMU driver (no domain is shut off though)
|
||||
*/
|
||||
static int
|
||||
qemuStateCleanup(void)
|
||||
@@ -0,0 +1,123 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Fri, 4 Oct 2019 16:57:04 +0200
|
||||
Subject: [PATCH] driver: Introduce virDriverShouldAutostart()
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Some of objects we manage can be autostarted on libvirtd startup
|
||||
(e.g. domains, network, storage pools). The idea was that when
|
||||
the host is started up these objects are started too without need
|
||||
of user intervention. However, with the latest daemon split and
|
||||
switch to socket activated, short lived daemons (we put --timeout
|
||||
120 onto each daemon's command line) this doesn't do what we want
|
||||
it to. The problem is not new though, we already had the session
|
||||
daemon come and go and we circumvented this problem by
|
||||
documenting it (see v4.10.0-92-g61b4e8aaf1). But now that we meet
|
||||
the same problem at all fronts it's time to deal with it.
|
||||
|
||||
The solution implemented in this commit is to have a file (one
|
||||
per each driver) that:
|
||||
|
||||
1) if doesn't exist, is created and autostart is allowed for
|
||||
given driver,
|
||||
|
||||
2) if it does exist, then autostart is suppressed for given
|
||||
driver.
|
||||
|
||||
All the files live in a location that doesn't survive host
|
||||
reboots (/var/run/ for instance) and thus the file is
|
||||
automatically not there on fresh host boot.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit ee16a195d97315ba3610b3640d347d3f4a358b55)
|
||||
---
|
||||
src/driver.c | 39 +++++++++++++++++++++++++++++++++++++++
|
||||
src/driver.h | 3 +++
|
||||
src/libvirt_private.syms | 1 +
|
||||
3 files changed, 43 insertions(+)
|
||||
|
||||
diff --git a/src/driver.c b/src/driver.c
|
||||
index 5e8f68f6df..471053686f 100644
|
||||
--- a/src/driver.c
|
||||
+++ b/src/driver.c
|
||||
@@ -29,6 +29,7 @@
|
||||
#include "virfile.h"
|
||||
#include "virlog.h"
|
||||
#include "virmodule.h"
|
||||
+#include "virstring.h"
|
||||
#include "virthread.h"
|
||||
#include "configmake.h"
|
||||
|
||||
@@ -69,6 +70,44 @@ virDriverLoadModule(const char *name,
|
||||
|
||||
/* XXX unload modules, but we can't until we can unregister libvirt drivers */
|
||||
|
||||
+/**
|
||||
+ * virDriverShouldAutostart:
|
||||
+ * @dir: driver's run state directory (usually /var/run/libvirt/$driver)
|
||||
+ * @autostart: whether driver should initiate autostart
|
||||
+ *
|
||||
+ * Automatic starting of libvirt's objects (e.g. domains, networks, storage
|
||||
+ * pools, etc.) doesn't play nice with using '--timeout' on daemon's command
|
||||
+ * line because the objects are attempted to autostart on every start of
|
||||
+ * corresponding driver/daemon. To resolve this problem, a file is created in
|
||||
+ * driver's private directory (which doesn't survive host's reboot) and thus
|
||||
+ * autostart is attempted only once.
|
||||
+ */
|
||||
+int
|
||||
+virDriverShouldAutostart(const char *dir,
|
||||
+ bool *autostart)
|
||||
+{
|
||||
+ VIR_AUTOFREE(char *) path = NULL;
|
||||
+
|
||||
+ *autostart = false;
|
||||
+
|
||||
+ if (virAsprintf(&path, "%s/autostarted", dir) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (virFileExists(path)) {
|
||||
+ VIR_DEBUG("Autostart file %s exists, skipping autostart", path);
|
||||
+ return 0;
|
||||
+ }
|
||||
+
|
||||
+ VIR_DEBUG("Autostart file %s does not exist, do autostart", path);
|
||||
+ *autostart = true;
|
||||
+
|
||||
+ if (virFileTouch(path, 0600) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+
|
||||
virThreadLocal connectInterface;
|
||||
virThreadLocal connectNetwork;
|
||||
virThreadLocal connectNWFilter;
|
||||
diff --git a/src/driver.h b/src/driver.h
|
||||
index 898fb96df4..c52284498e 100644
|
||||
--- a/src/driver.h
|
||||
+++ b/src/driver.h
|
||||
@@ -112,6 +112,9 @@ int virDriverLoadModule(const char *name,
|
||||
const char *regfunc,
|
||||
bool required);
|
||||
|
||||
+int virDriverShouldAutostart(const char *name,
|
||||
+ bool *autostart);
|
||||
+
|
||||
virConnectPtr virGetConnectInterface(void);
|
||||
virConnectPtr virGetConnectNetwork(void);
|
||||
virConnectPtr virGetConnectNWFilter(void);
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index bbc5144aa2..c1c3974133 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -1337,6 +1337,7 @@ virStreamClass;
|
||||
|
||||
|
||||
# driver.h
|
||||
+virDriverShouldAutostart;
|
||||
virGetConnectInterface;
|
||||
virGetConnectNetwork;
|
||||
virGetConnectNodeDev;
|
||||
@@ -0,0 +1,187 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Sat, 5 Oct 2019 09:15:24 +0200
|
||||
Subject: [PATCH] lib: autostart objects exactly once
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1755303
|
||||
|
||||
With the recent work in daemon split and socket activation
|
||||
daemons can come and go. They can and will be started many times
|
||||
during a session which results in objects being autostarted
|
||||
multiple times. This is not optimal. Use
|
||||
virDriverShouldAutostart() to determine if autostart should be
|
||||
done or not.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit bab464f8ea54d177e163f32c7c3476220694665c)
|
||||
---
|
||||
src/bhyve/bhyve_driver.c | 8 +++++++-
|
||||
src/libxl/libxl_driver.c | 10 ++++++++--
|
||||
src/lxc/lxc_driver.c | 7 ++++++-
|
||||
src/network/bridge_driver.c | 12 +++++++++---
|
||||
src/qemu/qemu_driver.c | 7 ++++++-
|
||||
src/storage/storage_driver.c | 7 ++++++-
|
||||
6 files changed, 42 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/src/bhyve/bhyve_driver.c b/src/bhyve/bhyve_driver.c
|
||||
index 5387ac5570..12788155a8 100644
|
||||
--- a/src/bhyve/bhyve_driver.c
|
||||
+++ b/src/bhyve/bhyve_driver.c
|
||||
@@ -1218,6 +1218,8 @@ bhyveStateInitialize(bool privileged,
|
||||
virStateInhibitCallback callback ATTRIBUTE_UNUSED,
|
||||
void *opaque ATTRIBUTE_UNUSED)
|
||||
{
|
||||
+ bool autostart = true;
|
||||
+
|
||||
if (!privileged) {
|
||||
VIR_INFO("Not running privileged, disabling driver");
|
||||
return 0;
|
||||
@@ -1301,7 +1303,11 @@ bhyveStateInitialize(bool privileged,
|
||||
|
||||
virBhyveProcessReconnectAll(bhyve_driver);
|
||||
|
||||
- bhyveAutostartDomains(bhyve_driver);
|
||||
+ if (virDriverShouldAutostart(BHYVE_STATE_DIR, &autostart) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (autostart)
|
||||
+ bhyveAutostartDomains(bhyve_driver);
|
||||
|
||||
return 0;
|
||||
|
||||
diff --git a/src/libxl/libxl_driver.c b/src/libxl/libxl_driver.c
|
||||
index 492028c487..c1c94767c3 100644
|
||||
--- a/src/libxl/libxl_driver.c
|
||||
+++ b/src/libxl/libxl_driver.c
|
||||
@@ -655,6 +655,7 @@ libxlStateInitialize(bool privileged,
|
||||
libxlDriverConfigPtr cfg;
|
||||
char *driverConf = NULL;
|
||||
char ebuf[1024];
|
||||
+ bool autostart = true;
|
||||
|
||||
if (!libxlDriverShouldLoad(privileged))
|
||||
return 0;
|
||||
@@ -800,8 +801,13 @@ libxlStateInitialize(bool privileged,
|
||||
NULL, NULL) < 0)
|
||||
goto error;
|
||||
|
||||
- virDomainObjListForEach(libxl_driver->domains, libxlAutostartDomain,
|
||||
- libxl_driver);
|
||||
+ if (virDriverShouldAutostart(cfg->stateDir, &autostart) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (autostart) {
|
||||
+ virDomainObjListForEach(libxl_driver->domains, libxlAutostartDomain,
|
||||
+ libxl_driver);
|
||||
+ }
|
||||
|
||||
virDomainObjListForEach(libxl_driver->domains, libxlDomainManagedSaveLoad,
|
||||
libxl_driver);
|
||||
diff --git a/src/lxc/lxc_driver.c b/src/lxc/lxc_driver.c
|
||||
index d0b6703101..24e6773f09 100644
|
||||
--- a/src/lxc/lxc_driver.c
|
||||
+++ b/src/lxc/lxc_driver.c
|
||||
@@ -1541,6 +1541,7 @@ static int lxcStateInitialize(bool privileged,
|
||||
{
|
||||
virCapsPtr caps = NULL;
|
||||
virLXCDriverConfigPtr cfg = NULL;
|
||||
+ bool autostart = true;
|
||||
|
||||
/* Check that the user is root, silently disable if not */
|
||||
if (!privileged) {
|
||||
@@ -1630,7 +1631,11 @@ static int lxcStateInitialize(bool privileged,
|
||||
NULL, NULL) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- virLXCProcessAutostartAll(lxc_driver);
|
||||
+ if (virDriverShouldAutostart(cfg->stateDir, &autostart) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ if (autostart)
|
||||
+ virLXCProcessAutostartAll(lxc_driver);
|
||||
|
||||
virObjectUnref(caps);
|
||||
return 0;
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index acaeb5c9a2..b830cdba42 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -716,6 +716,7 @@ networkStateInitialize(bool privileged,
|
||||
int ret = -1;
|
||||
char *configdir = NULL;
|
||||
char *rundir = NULL;
|
||||
+ bool autostart = true;
|
||||
#ifdef WITH_FIREWALLD
|
||||
DBusConnection *sysbus = NULL;
|
||||
#endif
|
||||
@@ -816,9 +817,14 @@ networkStateInitialize(bool privileged,
|
||||
networkReloadFirewallRules(network_driver, true);
|
||||
networkRefreshDaemons(network_driver);
|
||||
|
||||
- virNetworkObjListForEach(network_driver->networks,
|
||||
- networkAutostartConfig,
|
||||
- network_driver);
|
||||
+ if (virDriverShouldAutostart(network_driver->stateDir, &autostart) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (autostart) {
|
||||
+ virNetworkObjListForEach(network_driver->networks,
|
||||
+ networkAutostartConfig,
|
||||
+ network_driver);
|
||||
+ }
|
||||
|
||||
network_driver->networkEventState = virObjectEventStateNew();
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 69416d6d1a..5dd2616c7b 100644
|
||||
--- a/src/qemu/qemu_driver.c
|
||||
+++ b/src/qemu/qemu_driver.c
|
||||
@@ -726,6 +726,7 @@ qemuStateInitialize(bool privileged,
|
||||
gid_t run_gid = -1;
|
||||
char *hugepagePath = NULL;
|
||||
char *memoryBackingPath = NULL;
|
||||
+ bool autostart = true;
|
||||
size_t i;
|
||||
|
||||
if (VIR_ALLOC(qemu_driver) < 0)
|
||||
@@ -1071,7 +1072,11 @@ qemuStateInitialize(bool privileged,
|
||||
|
||||
qemuProcessReconnectAll(qemu_driver);
|
||||
|
||||
- qemuAutostartDomains(qemu_driver);
|
||||
+ if (virDriverShouldAutostart(cfg->stateDir, &autostart) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (autostart)
|
||||
+ qemuAutostartDomains(qemu_driver);
|
||||
|
||||
return 0;
|
||||
|
||||
diff --git a/src/storage/storage_driver.c b/src/storage/storage_driver.c
|
||||
index 03ac6a6845..05192027d6 100644
|
||||
--- a/src/storage/storage_driver.c
|
||||
+++ b/src/storage/storage_driver.c
|
||||
@@ -253,6 +253,7 @@ storageStateInitialize(bool privileged,
|
||||
{
|
||||
VIR_AUTOFREE(char *) configdir = NULL;
|
||||
VIR_AUTOFREE(char *) rundir = NULL;
|
||||
+ bool autostart = true;
|
||||
|
||||
if (VIR_ALLOC(driver) < 0)
|
||||
return -1;
|
||||
@@ -314,7 +315,11 @@ storageStateInitialize(bool privileged,
|
||||
|
||||
storagePoolUpdateAllState();
|
||||
|
||||
- storageDriverAutostart();
|
||||
+ if (virDriverShouldAutostart(driver->stateDir, &autostart) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (autostart)
|
||||
+ storageDriverAutostart();
|
||||
|
||||
driver->storageEventState = virObjectEventStateNew();
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Sat, 5 Oct 2019 09:22:15 +0200
|
||||
Subject: [PATCH] Revert "src: Document autostart for session demon"
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
This reverts commit 61b4e8aaf1bce07f282c152de556c3d6aa8d65be.
|
||||
|
||||
After previous commits this is no longer needed.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit 897d8b34c8577d6e663b7b9bdb17ea4f5f1b83b9)
|
||||
---
|
||||
src/libvirt-domain.c | 5 -----
|
||||
1 file changed, 5 deletions(-)
|
||||
|
||||
diff --git a/src/libvirt-domain.c b/src/libvirt-domain.c
|
||||
index 2fe9bb8e91..d01fef358f 100644
|
||||
--- a/src/libvirt-domain.c
|
||||
+++ b/src/libvirt-domain.c
|
||||
@@ -6693,11 +6693,6 @@ virDomainCreateWithFiles(virDomainPtr domain, unsigned int nfiles,
|
||||
* configured to be automatically started when the host
|
||||
* machine boots.
|
||||
*
|
||||
- * Please note that this might result in unexpected behaviour if
|
||||
- * used for some session URIs. Since the session daemon is started
|
||||
- * with --timeout it comes and goes and as it does so it
|
||||
- * autostarts domains which might have been shut off recently.
|
||||
- *
|
||||
* Returns -1 in case of error, 0 in case of success
|
||||
*/
|
||||
int
|
||||
@@ -0,0 +1,39 @@
|
||||
From: Laine Stump <laine@laine.org>
|
||||
Date: Wed, 16 Oct 2019 14:06:54 -0400
|
||||
Subject: [PATCH] util: allow sending mac addr to virNetNewLink without ifindex
|
||||
|
||||
Although until now, any use of the extra_args argument (a pointer to a
|
||||
struct containing extra attributes to add the the RTM_NEWLINK message)
|
||||
would always have the ifindex and mac set, so the code could assume it
|
||||
was safe to add both to the message if extra_args != NULL. There is
|
||||
now a use for setting a MAC address in the RTM_NEWLINK without setting
|
||||
the ifindex, so we should check each of these separately.
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit b596d6c106cd87d6d452c5dd4ad923a034544fbf)
|
||||
---
|
||||
src/util/virnetlink.c | 9 +++++++--
|
||||
1 file changed, 7 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/util/virnetlink.c b/src/util/virnetlink.c
|
||||
index 7b3c6bf05f..394495ee2b 100644
|
||||
--- a/src/util/virnetlink.c
|
||||
+++ b/src/util/virnetlink.c
|
||||
@@ -548,9 +548,14 @@ virNetlinkNewLink(const char *ifname,
|
||||
NETLINK_MSG_NEST_END(nl_msg, linkinfo);
|
||||
|
||||
if (extra_args) {
|
||||
- NETLINK_MSG_PUT(nl_msg, IFLA_LINK,
|
||||
+ if (extra_args->ifindex) {
|
||||
+ NETLINK_MSG_PUT(nl_msg, IFLA_LINK,
|
||||
sizeof(uint32_t), extra_args->ifindex);
|
||||
- NETLINK_MSG_PUT(nl_msg, IFLA_ADDRESS, VIR_MAC_BUFLEN, extra_args->mac);
|
||||
+ }
|
||||
+ if (extra_args->mac) {
|
||||
+ NETLINK_MSG_PUT(nl_msg, IFLA_ADDRESS,
|
||||
+ VIR_MAC_BUFLEN, extra_args->mac);
|
||||
+ }
|
||||
}
|
||||
|
||||
if (virNetlinkCommand(nl_msg, &resp, &buflen, 0, 0, NETLINK_ROUTE, 0) < 0)
|
||||
@@ -0,0 +1,213 @@
|
||||
From: Laine Stump <laine@laine.org>
|
||||
Date: Thu, 17 Oct 2019 21:12:30 -0400
|
||||
Subject: [PATCH] util: set bridge device MAC address explicitly during
|
||||
virNetDevBridgeCreate
|
||||
|
||||
When libvirt first implemented a stable and configurable MAC address
|
||||
for the bridges created for libvirt virtual networks (commit
|
||||
5754dbd56d, in libvirt v0.8.8) most distro stable releases didn't
|
||||
support explicitly setting the MAC address of a bridge; the bridge
|
||||
just always assumed the lowest numbered MAC of all attached
|
||||
interfaces. Because of this, we stabilized the bridge MAC address by
|
||||
creating a "dummy" tap interface with a MAC address guaranteed to be
|
||||
lower than any of the guest tap devices' MACs (which all started with
|
||||
0xFE, so it's not difficult to do) and attached it to the bridge -
|
||||
this was the inception of the "virbr0-nic" device that has confused so
|
||||
many people over the years.
|
||||
|
||||
Even though the linux kernel had recently gained support for
|
||||
explicitly setting a bridge MAC, we deemed it unnecessary to set the
|
||||
MAC that way, because the other (indirect) method worked everywhere.
|
||||
|
||||
But recently there have been reports that the bridge MAC address was
|
||||
not following the setting in the network config, and mismatched the
|
||||
MAC of the dummy tap device (which was still correct). It turns out
|
||||
that this is due to a change in systemd-242 that persists whatever MAC
|
||||
address is set for a bridge when it's initially started. According to
|
||||
the systemd NEWS file entry for version 242
|
||||
(https://github.com/systemd/systemd/blob/master/NEWS):
|
||||
|
||||
"if a bridge interface is created without any slaves, and gains
|
||||
a slave later, then now the bridge does not inherit slave's MAC."
|
||||
|
||||
This change was the result of:
|
||||
|
||||
https://github.com/systemd/systemd/issues/3374
|
||||
|
||||
(apparently if there is no MAC saved for a bridge by the name of a
|
||||
bridge being created, the random MAC generated during creation is
|
||||
saved, and then that same MAC is used to explicitly set the MAC each
|
||||
time it is created). Once a bridge has an explicitly set MAC, the "use
|
||||
the lowest numbered MAC of attached devices" rule is ignored, so our
|
||||
dummy tap device is like the goggles - it does nothing! (well, almost).
|
||||
|
||||
We could whine about changes in default behavior, etc. etc., but
|
||||
because the change was in response to actual user problems, that seems
|
||||
likely a fruitless task. Fortunately, time has marched on, and even
|
||||
distro releases that are old enough that they are no longer supported
|
||||
by upstream libvirt (e.g. RHEL6) have support for explicitly setting a
|
||||
bridge device MAC address, either during creation or with a separate
|
||||
ioctl after creation, so we can now do that.
|
||||
|
||||
To enable explicitly setting the mac during bridge creation, we add a
|
||||
mac arg to virNetDevBridgeCreate(). In the case of platforms where
|
||||
the bridge is created with a netlink RTM_NEWLINK message, we just add
|
||||
that mac to the message. For platforms that still use an ioctl (either
|
||||
SIOCBRADDBR or SIOCIFCREATE2), we make a separate call to
|
||||
virNetDevSetMAC() after creating the bridge.
|
||||
|
||||
(NB: I was unable to test the calling of virNetDevSetMAC() from the
|
||||
SIOCIFCREATE2 (BSD) version of virNetDevBridgeCreate(); even though I
|
||||
managed to get a FreeBSD system setup and libvirt built there, when I
|
||||
tried to start the default network the SIOCIFCREATE2 ioctl itself
|
||||
failed, so it never even got to the virNetDevSetMAC(). That leaves the
|
||||
FreeBSD implementation untested.)
|
||||
|
||||
This makes the dummy tap pointless for purposes of setting the MAC
|
||||
address, but it is still useful for IPv6 DAD initialization (which
|
||||
apparently requires at least one interface to be attached to the
|
||||
bridge and online), as well as for setting an initial MTU for the
|
||||
bridge, so it hasn't been removed.
|
||||
|
||||
(NB: we can safely *always* call virNetDevBridgeCreate() with
|
||||
&def->mac from the network driver because, in spite of the existence
|
||||
of a "mac_specified" bool in the config suggesting that it may not
|
||||
always be present, in reality a mac address will always be added to
|
||||
any network that doesn't have one - this is guaranteed in all cases by
|
||||
commit a47ae7c004)
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1760851
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
(cherry picked from commit 13ec827052fcd79a4350f499aab5f4aa20ea83fa)
|
||||
---
|
||||
src/network/bridge_driver.c | 2 +-
|
||||
src/util/virnetdevbridge.c | 44 ++++++++++++++++++++++++++++++-------
|
||||
src/util/virnetdevbridge.h | 3 ++-
|
||||
3 files changed, 39 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index b830cdba42..d5c544f556 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -2510,7 +2510,7 @@ networkStartNetworkVirtual(virNetworkDriverStatePtr driver,
|
||||
def->name);
|
||||
return -1;
|
||||
}
|
||||
- if (virNetDevBridgeCreate(def->bridge) < 0)
|
||||
+ if (virNetDevBridgeCreate(def->bridge, &def->mac) < 0)
|
||||
return -1;
|
||||
|
||||
if (def->mac_specified) {
|
||||
diff --git a/src/util/virnetdevbridge.c b/src/util/virnetdevbridge.c
|
||||
index 4f21a82fb7..368ce912d1 100644
|
||||
--- a/src/util/virnetdevbridge.c
|
||||
+++ b/src/util/virnetdevbridge.c
|
||||
@@ -379,7 +379,8 @@ virNetDevBridgePortSetUnicastFlood(const char *brname ATTRIBUTE_UNUSED,
|
||||
*/
|
||||
#if defined(HAVE_STRUCT_IFREQ) && defined(SIOCBRADDBR)
|
||||
static int
|
||||
-virNetDevBridgeCreateWithIoctl(const char *brname)
|
||||
+virNetDevBridgeCreateWithIoctl(const char *brname,
|
||||
+ const virMacAddr *mac)
|
||||
{
|
||||
VIR_AUTOCLOSE fd = -1;
|
||||
|
||||
@@ -392,22 +393,36 @@ virNetDevBridgeCreateWithIoctl(const char *brname)
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ if (virNetDevSetMAC(brname, mac) < 0) {
|
||||
+ virErrorPtr savederr;
|
||||
+
|
||||
+ virErrorPreserveLast(&savederr);
|
||||
+ ignore_value(ioctl(fd, SIOCBRDELBR, brname));
|
||||
+ virErrorRestore(&savederr);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(__linux__) && defined(HAVE_LIBNL)
|
||||
int
|
||||
-virNetDevBridgeCreate(const char *brname)
|
||||
+virNetDevBridgeCreate(const char *brname,
|
||||
+ const virMacAddr *mac)
|
||||
{
|
||||
/* use a netlink RTM_NEWLINK message to create the bridge */
|
||||
int error = 0;
|
||||
+ virNetlinkNewLinkData data = {
|
||||
+ .mac = mac,
|
||||
+ };
|
||||
+
|
||||
|
||||
- if (virNetlinkNewLink(brname, "bridge", NULL, &error) < 0) {
|
||||
+ if (virNetlinkNewLink(brname, "bridge", &data, &error) < 0) {
|
||||
# if defined(HAVE_STRUCT_IFREQ) && defined(SIOCBRADDBR)
|
||||
if (error == -EOPNOTSUPP) {
|
||||
/* fallback to ioctl if netlink doesn't support creating bridges */
|
||||
- return virNetDevBridgeCreateWithIoctl(brname);
|
||||
+ return virNetDevBridgeCreateWithIoctl(brname, mac);
|
||||
}
|
||||
# endif
|
||||
if (error < 0)
|
||||
@@ -423,15 +438,17 @@ virNetDevBridgeCreate(const char *brname)
|
||||
|
||||
#elif defined(HAVE_STRUCT_IFREQ) && defined(SIOCBRADDBR)
|
||||
int
|
||||
-virNetDevBridgeCreate(const char *brname)
|
||||
+virNetDevBridgeCreate(const char *brname,
|
||||
+ const virMacAddr *mac)
|
||||
{
|
||||
- return virNetDevBridgeCreateWithIoctl(brname);
|
||||
+ return virNetDevBridgeCreateWithIoctl(brname, mac);
|
||||
}
|
||||
|
||||
|
||||
#elif defined(HAVE_STRUCT_IFREQ) && defined(SIOCIFCREATE2)
|
||||
int
|
||||
-virNetDevBridgeCreate(const char *brname)
|
||||
+virNetDevBridgeCreate(const char *brname,
|
||||
+ const virMacAddr *mac)
|
||||
{
|
||||
struct ifreq ifr;
|
||||
VIR_AUTOCLOSE s = -1;
|
||||
@@ -448,10 +465,21 @@ virNetDevBridgeCreate(const char *brname)
|
||||
if (virNetDevSetName(ifr.ifr_name, brname) == -1)
|
||||
return -1;
|
||||
|
||||
+ if (virNetDevSetMAC(brname, mac) < 0) {
|
||||
+ virErrorPtr savederr;
|
||||
+
|
||||
+ virErrorPreserveLast(&savederr);
|
||||
+ ignore_value(virNetDevBridgeDelete(brname));
|
||||
+ virErrorRestore(&savederr);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
-int virNetDevBridgeCreate(const char *brname)
|
||||
+int
|
||||
+virNetDevBridgeCreate(const char *brname,
|
||||
+ const virMacAddr *mac G_GNUC_UNUSED)
|
||||
{
|
||||
virReportSystemError(ENOSYS,
|
||||
_("Unable to create bridge %s"), brname);
|
||||
diff --git a/src/util/virnetdevbridge.h b/src/util/virnetdevbridge.h
|
||||
index 8df5e51c2e..2a2bde8d0e 100644
|
||||
--- a/src/util/virnetdevbridge.h
|
||||
+++ b/src/util/virnetdevbridge.h
|
||||
@@ -21,7 +21,8 @@
|
||||
#include "internal.h"
|
||||
#include "virmacaddr.h"
|
||||
|
||||
-int virNetDevBridgeCreate(const char *brname)
|
||||
+int virNetDevBridgeCreate(const char *brname,
|
||||
+ const virMacAddr *mac)
|
||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_RETURN_CHECK;
|
||||
int virNetDevBridgeDelete(const char *brname)
|
||||
ATTRIBUTE_NONNULL(1) ATTRIBUTE_RETURN_CHECK;
|
||||
@@ -0,0 +1,122 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Mon, 14 Oct 2019 16:37:03 +0200
|
||||
Subject: [PATCH] virhostuptime: Add linux stub for musl
|
||||
|
||||
When we want to know the boot timestamp of the host, we can call
|
||||
virHostGetBootTime(). Under the hood, it uses getutxid() which is
|
||||
defined by POSIX and properly check for in configure. However,
|
||||
musl took a path where it declares the function but instead of
|
||||
providing any useful implementation it returns NULL meaning "no
|
||||
record found". If that's the case, use our second best option -
|
||||
/proc/uptime and a bit of maths.
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1760885
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Cole Robinson <crobinso@redhat.com>
|
||||
(cherry picked from commit 070d6969fe912b8f2e9aadee88c6bdda00a65f4f)
|
||||
Signed-off-by: rpm-build <rpm-build>
|
||||
|
||||
Conflicts:
|
||||
po/POTFILES.in
|
||||
---
|
||||
src/util/virhostuptime.c | 62 ++++++++++++++++++++++++++++++++++++++--
|
||||
1 file changed, 59 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/src/util/virhostuptime.c b/src/util/virhostuptime.c
|
||||
index 62b781acd5..a203961996 100644
|
||||
--- a/src/util/virhostuptime.c
|
||||
+++ b/src/util/virhostuptime.c
|
||||
@@ -25,16 +25,68 @@
|
||||
#endif
|
||||
|
||||
#include "virhostuptime.h"
|
||||
+#include "viralloc.h"
|
||||
+#include "virfile.h"
|
||||
+#include "virlog.h"
|
||||
+#include "virstring.h"
|
||||
+#include "virtime.h"
|
||||
#include "virthread.h"
|
||||
|
||||
+#define VIR_FROM_THIS VIR_FROM_NONE
|
||||
+
|
||||
+VIR_LOG_INIT("util.virhostuptime");
|
||||
+
|
||||
static unsigned long long bootTime;
|
||||
static int bootTimeErrno;
|
||||
static virOnceControl virHostGetBootTimeOnce = VIR_ONCE_CONTROL_INITIALIZER;
|
||||
|
||||
-#ifdef HAVE_GETUTXID
|
||||
+#if defined(__linux__)
|
||||
+# define UPTIME_FILE "/proc/uptime"
|
||||
+static int
|
||||
+virHostGetBootTimeProcfs(unsigned long long *btime)
|
||||
+{
|
||||
+ unsigned long long now;
|
||||
+ double up;
|
||||
+ VIR_AUTOFREE(char *) buf = NULL;
|
||||
+ char *tmp;
|
||||
+
|
||||
+ if (virTimeMillisNow(&now) < 0)
|
||||
+ return -errno;
|
||||
+
|
||||
+ /* 1KiB limit is more than enough. */
|
||||
+ if (virFileReadAll(UPTIME_FILE, 1024, &buf) < 0)
|
||||
+ return -errno;
|
||||
+
|
||||
+ /* buf contains two doubles now:
|
||||
+ * $uptime $idle_time
|
||||
+ * We're interested only in the first one */
|
||||
+ if (!(tmp = strchr(buf, ' '))) {
|
||||
+ virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("uptime file has unexpected format '%s'"),
|
||||
+ buf);
|
||||
+ return -EINVAL;
|
||||
+ }
|
||||
+
|
||||
+ *tmp = '\0';
|
||||
+
|
||||
+ if (virStrToDouble(buf, NULL, &up) < 0) {
|
||||
+ virReportError(VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Unable to parse uptime value '%s'"),
|
||||
+ buf);
|
||||
+ return -EINVAL;
|
||||
+ }
|
||||
+
|
||||
+ *btime = now / 1000 - up + 0.5;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+#endif /* defined(__linux__) */
|
||||
+
|
||||
+#if defined(HAVE_GETUTXID) || defined(__linux__)
|
||||
static void
|
||||
virHostGetBootTimeOnceInit(void)
|
||||
{
|
||||
+# ifdef HAVE_GETUTXID
|
||||
struct utmpx id = {.ut_type = BOOT_TIME};
|
||||
struct utmpx *res = NULL;
|
||||
|
||||
@@ -45,16 +97,20 @@ virHostGetBootTimeOnceInit(void)
|
||||
}
|
||||
|
||||
endutxent();
|
||||
+# endif /* HAVE_GETUTXID */
|
||||
+
|
||||
+ if (bootTimeErrno != 0 || bootTime == 0)
|
||||
+ bootTimeErrno = -virHostGetBootTimeProcfs(&bootTime);
|
||||
}
|
||||
|
||||
-#else /* !HAVE_GETUTXID */
|
||||
+#else /* !defined(HAVE_GETUTXID) && !defined(__linux__) */
|
||||
|
||||
static void
|
||||
virHostGetBootTimeOnceInit(void)
|
||||
{
|
||||
bootTimeErrno = ENOSYS;
|
||||
}
|
||||
-#endif /* HAVE_GETUTXID */
|
||||
+#endif /* !defined(HAVE_GETUTXID) && !defined(__linux__) */
|
||||
|
||||
/**
|
||||
* virHostGetBootTime:
|
||||
@@ -0,0 +1,31 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Thu, 14 Nov 2019 16:42:51 +0100
|
||||
Subject: [PATCH] virhostuptime: Wrap virHostGetBootTimeProcfs() call in an
|
||||
ifdef
|
||||
|
||||
The virHostGetBootTimeProcfs() function is defined only for Linux
|
||||
and therefore it's only call should also be done if we're on
|
||||
Linux.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit 1b0de07f41bbe0d23ab96b604428ae55fd22aec0)
|
||||
Signed-off-by: rpm-build <rpm-build>
|
||||
---
|
||||
src/util/virhostuptime.c | 2 ++
|
||||
1 file changed, 2 insertions(+)
|
||||
|
||||
diff --git a/src/util/virhostuptime.c b/src/util/virhostuptime.c
|
||||
index a203961996..94004d05db 100644
|
||||
--- a/src/util/virhostuptime.c
|
||||
+++ b/src/util/virhostuptime.c
|
||||
@@ -99,8 +99,10 @@ virHostGetBootTimeOnceInit(void)
|
||||
endutxent();
|
||||
# endif /* HAVE_GETUTXID */
|
||||
|
||||
+# ifdef __linux__
|
||||
if (bootTimeErrno != 0 || bootTime == 0)
|
||||
bootTimeErrno = -virHostGetBootTimeProcfs(&bootTime);
|
||||
+# endif /* __linux__ */
|
||||
}
|
||||
|
||||
#else /* !defined(HAVE_GETUTXID) && !defined(__linux__) */
|
||||
@@ -0,0 +1,71 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Thu, 19 Dec 2019 10:11:04 +0100
|
||||
Subject: [PATCH] virhostuptime: Introduce virHostBootTimeInit()
|
||||
|
||||
The idea is to offer callers an init function that they can call
|
||||
independently to ensure that the global variables get
|
||||
initialized.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Cole Robinson <crobinso@redhat.com>
|
||||
(cherry picked from commit 9d69bc19b94544b06838b2e2895826991d107178)
|
||||
Signed-off-by: rpm-build <rpm-build>
|
||||
|
||||
Conflicts:
|
||||
src/util/virhostuptime.h
|
||||
---
|
||||
src/libvirt_private.syms | 1 +
|
||||
src/util/virhostuptime.c | 12 +++++++++++-
|
||||
src/util/virhostuptime.h | 3 +++
|
||||
3 files changed, 15 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms
|
||||
index c1c3974133..fbd1c25597 100644
|
||||
--- a/src/libvirt_private.syms
|
||||
+++ b/src/libvirt_private.syms
|
||||
@@ -2136,6 +2136,7 @@ virHostMemSetParameters;
|
||||
|
||||
|
||||
# util/virhostuptime.h
|
||||
+virHostBootTimeInit;
|
||||
virHostGetBootTime;
|
||||
|
||||
|
||||
diff --git a/src/util/virhostuptime.c b/src/util/virhostuptime.c
|
||||
index 94004d05db..d82e268264 100644
|
||||
--- a/src/util/virhostuptime.c
|
||||
+++ b/src/util/virhostuptime.c
|
||||
@@ -126,7 +126,7 @@ virHostGetBootTimeOnceInit(void)
|
||||
int
|
||||
virHostGetBootTime(unsigned long long *when)
|
||||
{
|
||||
- if (virOnce(&virHostGetBootTimeOnce, virHostGetBootTimeOnceInit) < 0)
|
||||
+ if (virHostBootTimeInit() < 0)
|
||||
return -1;
|
||||
|
||||
if (bootTimeErrno) {
|
||||
@@ -137,3 +137,13 @@ virHostGetBootTime(unsigned long long *when)
|
||||
*when = bootTime;
|
||||
return 0;
|
||||
}
|
||||
+
|
||||
+
|
||||
+int
|
||||
+virHostBootTimeInit(void)
|
||||
+{
|
||||
+ if (virOnce(&virHostGetBootTimeOnce, virHostGetBootTimeOnceInit) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
diff --git a/src/util/virhostuptime.h b/src/util/virhostuptime.h
|
||||
index 03c1517a64..0886b03767 100644
|
||||
--- a/src/util/virhostuptime.h
|
||||
+++ b/src/util/virhostuptime.h
|
||||
@@ -25,3 +25,6 @@
|
||||
int
|
||||
virHostGetBootTime(unsigned long long *when)
|
||||
ATTRIBUTE_NOINLINE;
|
||||
+
|
||||
+int
|
||||
+virHostBootTimeInit(void);
|
||||
@@ -0,0 +1,54 @@
|
||||
From: Michal Privoznik <mprivozn@redhat.com>
|
||||
Date: Tue, 17 Dec 2019 14:08:42 +0100
|
||||
Subject: [PATCH] remote_daemon: Initialize host boot time global variable
|
||||
|
||||
This is not strictly needed, but it makes sure we initialize the
|
||||
@bootTime global variable. Thing is, in order to validate XATTRs
|
||||
and prune those set in some previous runs of the host, a
|
||||
timestamp is recorded in XATTRs. The host boot time was unique
|
||||
enough so it was chosen as the timestamp value. And to avoid
|
||||
querying and parsing /proc/uptime every time, the query function
|
||||
does that only once and stores the boot time in a global
|
||||
variable. However, the only time the query function is called is
|
||||
in a child process that does lock files and changes seclabels. So
|
||||
effectively, we are doing exactly what we wanted to prevent from
|
||||
happening.
|
||||
|
||||
The fix is simple, call the virHostBootTimeInit() function which
|
||||
sets the global variable.
|
||||
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Cole Robinson <crobinso@redhat.com>
|
||||
(cherry picked from commit 35d603d5ae0abe91b8b48203c5b7051b1800682b)
|
||||
Signed-off-by: rpm-build <rpm-build>
|
||||
---
|
||||
src/remote/remote_daemon.c | 9 +++++++++
|
||||
1 file changed, 9 insertions(+)
|
||||
|
||||
diff --git a/src/remote/remote_daemon.c b/src/remote/remote_daemon.c
|
||||
index 6b5a6c1523..43f9527405 100644
|
||||
--- a/src/remote/remote_daemon.c
|
||||
+++ b/src/remote/remote_daemon.c
|
||||
@@ -57,6 +57,7 @@
|
||||
#include "virgettext.h"
|
||||
#include "util/virnetdevopenvswitch.h"
|
||||
#include "virsystemd.h"
|
||||
+#include "virhostuptime.h"
|
||||
|
||||
#include "driver.h"
|
||||
|
||||
@@ -1088,6 +1089,14 @@ int main(int argc, char **argv) {
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
+ /* Let's try to initialize global variable that holds the host's boot time. */
|
||||
+ if (virHostBootTimeInit() < 0) {
|
||||
+ /* This is acceptable failure. Maybe we won't need the boot time
|
||||
+ * anyway, and if we do, then virHostGetBootTime() returns an
|
||||
+ * appropriate error. */
|
||||
+ VIR_DEBUG("Ignoring failed boot time init");
|
||||
+ }
|
||||
+
|
||||
daemonSetupNetDevOpenvswitch(config);
|
||||
|
||||
if (daemonSetupAccessManager(config) < 0) {
|
||||
@@ -0,0 +1,55 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Thu, 7 May 2020 22:32:59 -0400
|
||||
Subject: [PATCH] network: make it safe to call networkSetupPrivateChains()
|
||||
multiple times
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
networkSetupPrivateChains() is currently called only once per run of
|
||||
libvirtd, so it can assume that errInitV4 and errInitV6 are empty/null
|
||||
when it is called. In preparation for potentially calling this
|
||||
function multiple times during one run, this patch moves the reset of
|
||||
errInitV[46] to the top of the function, to assure no memory is
|
||||
leaked.
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit de110f110fb917a31b9f33ad8e4b3c1d3284766a)
|
||||
---
|
||||
src/network/bridge_driver_linux.c | 8 ++++----
|
||||
1 file changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver_linux.c b/src/network/bridge_driver_linux.c
|
||||
index 35459c10d1..f4e4e2df76 100644
|
||||
--- a/src/network/bridge_driver_linux.c
|
||||
+++ b/src/network/bridge_driver_linux.c
|
||||
@@ -48,6 +48,10 @@ static void networkSetupPrivateChains(void)
|
||||
VIR_DEBUG("Setting up global firewall chains");
|
||||
|
||||
createdChains = false;
|
||||
+ virFreeError(errInitV4);
|
||||
+ errInitV4 = NULL;
|
||||
+ virFreeError(errInitV6);
|
||||
+ errInitV6 = NULL;
|
||||
|
||||
rc = iptablesSetupPrivateChains(VIR_FIREWALL_LAYER_IPV4);
|
||||
if (rc < 0) {
|
||||
@@ -56,8 +60,6 @@ static void networkSetupPrivateChains(void)
|
||||
errInitV4 = virSaveLastError();
|
||||
virResetLastError();
|
||||
} else {
|
||||
- virFreeError(errInitV4);
|
||||
- errInitV4 = NULL;
|
||||
if (rc) {
|
||||
VIR_DEBUG("Created global IPv4 chains");
|
||||
createdChains = true;
|
||||
@@ -73,8 +75,6 @@ static void networkSetupPrivateChains(void)
|
||||
errInitV6 = virSaveLastError();
|
||||
virResetLastError();
|
||||
} else {
|
||||
- virFreeError(errInitV6);
|
||||
- errInitV6 = NULL;
|
||||
if (rc) {
|
||||
VIR_DEBUG("Created global IPv6 chains");
|
||||
createdChains = true;
|
||||
@@ -0,0 +1,265 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Thu, 7 May 2020 21:54:39 -0400
|
||||
Subject: [PATCH] network: force re-creation of iptables private chains on
|
||||
firewalld restart
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
When firewalld is stopped, it removes *all* iptables rules and chains,
|
||||
including those added by libvirt. Since restarting firewalld means
|
||||
stopping and then starting it, any time it is restarted, libvirt needs
|
||||
to recreate all the private iptables chains it uses, along with all
|
||||
the rules it adds.
|
||||
|
||||
We already have code in place to call networkReloadFirewallRules() any
|
||||
time we're notified of a firewalld start, and
|
||||
networkReloadFirewallRules() will call
|
||||
networkPreReloadFirewallRules(), which calls
|
||||
networkSetupPrivateChains(); unfortunately that last call is called
|
||||
using virOnce(), meaning that it will only be called the first time
|
||||
through networkPreReloadFirewallRules() after libvirtd starts - so of
|
||||
course when firewalld is later restarted, the call to
|
||||
networkSetupPrivateChains() is skipped.
|
||||
|
||||
The neat and tidy way to fix this would be if there was a standard way
|
||||
to reset a pthread_once_t object so that the next time virOnce was
|
||||
called, it would think the function hadn't been called, and call it
|
||||
again. Unfortunately, there isn't any official way of doing that (we
|
||||
*could* just fill it with 0 and hope for the best, but that doesn't
|
||||
seem very safe.
|
||||
|
||||
So instead, this patch just adds a static variable called
|
||||
chainInitDone, which is set to true after networkSetupPrivateChains()
|
||||
is called for the first time, and then during calls to
|
||||
networkPreReloadFirewallRules(), if chainInitDone is set, we call
|
||||
networkSetupPrivateChains() directly instead of via virOnce().
|
||||
|
||||
It may seem unsafe to directly call a function that is meant to be
|
||||
called only once, but I think in this case we're safe - there's
|
||||
nothing in the function that is inherently "once only" - it doesn't
|
||||
initialize anything that can't safely be re-initialized (as long as
|
||||
two threads don't try to do it at the same time), and it only happens
|
||||
when responding to a dbus message that firewalld has been started (and
|
||||
I don't think it's possible for us to be processing two of those at
|
||||
once), and even then only if the initial call to the function has
|
||||
already been completed (so we're safe if we receive a firewalld
|
||||
restart call at a time when we haven't yet called it, or even if
|
||||
another thread is already in the process of executing it. The only
|
||||
problematic bit I can think of is if another thread is in the process
|
||||
of adding an iptable rule at the time we're executing this function,
|
||||
but 1) none of those threads will be trying to add chains, and 2) if
|
||||
there was a concurrency problem with other threads adding iptables
|
||||
rules while firewalld was being restarted, it would still be a problem
|
||||
even without this change.
|
||||
|
||||
This is yet another patch that fixes an occurrence of this error:
|
||||
|
||||
COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --insert LIBVIRT_INP --in-interface virbr0 --protocol tcp --destination-port 67 --jump ACCEPT' failed: iptables: No chain/target/match by that name.
|
||||
|
||||
In particular, this resolves: https://bugzilla.redhat.com/1813830
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
|
||||
(cherry picked from commit f5418b427e7d2f26803880309478de9103680826)
|
||||
---
|
||||
src/network/bridge_driver.c | 16 ++++---
|
||||
src/network/bridge_driver_linux.c | 69 ++++++++++++++++++----------
|
||||
src/network/bridge_driver_nop.c | 3 +-
|
||||
src/network/bridge_driver_platform.h | 2 +-
|
||||
4 files changed, 58 insertions(+), 32 deletions(-)
|
||||
|
||||
diff --git a/src/network/bridge_driver.c b/src/network/bridge_driver.c
|
||||
index d5c544f556..981b4e4578 100644
|
||||
--- a/src/network/bridge_driver.c
|
||||
+++ b/src/network/bridge_driver.c
|
||||
@@ -289,7 +289,9 @@ static int
|
||||
networkShutdownNetworkExternal(virNetworkObjPtr obj);
|
||||
|
||||
static void
|
||||
-networkReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup);
|
||||
+networkReloadFirewallRules(virNetworkDriverStatePtr driver,
|
||||
+ bool startup,
|
||||
+ bool force);
|
||||
|
||||
static void
|
||||
networkRefreshDaemons(virNetworkDriverStatePtr driver);
|
||||
@@ -695,7 +697,7 @@ firewalld_dbus_filter_bridge(DBusConnection *connection ATTRIBUTE_UNUSED,
|
||||
|
||||
if (reload) {
|
||||
VIR_DEBUG("Reload in bridge_driver because of firewalld.");
|
||||
- networkReloadFirewallRules(driver, false);
|
||||
+ networkReloadFirewallRules(driver, false, true);
|
||||
}
|
||||
|
||||
return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
|
||||
@@ -814,7 +816,7 @@ networkStateInitialize(bool privileged,
|
||||
virNetworkObjListPrune(network_driver->networks,
|
||||
VIR_CONNECT_LIST_NETWORKS_INACTIVE |
|
||||
VIR_CONNECT_LIST_NETWORKS_TRANSIENT);
|
||||
- networkReloadFirewallRules(network_driver, true);
|
||||
+ networkReloadFirewallRules(network_driver, true, false);
|
||||
networkRefreshDaemons(network_driver);
|
||||
|
||||
if (virDriverShouldAutostart(network_driver->stateDir, &autostart) < 0)
|
||||
@@ -884,7 +886,7 @@ networkStateReload(void)
|
||||
network_driver->networkConfigDir,
|
||||
network_driver->networkAutostartDir,
|
||||
network_driver->xmlopt);
|
||||
- networkReloadFirewallRules(network_driver, false);
|
||||
+ networkReloadFirewallRules(network_driver, false, false);
|
||||
networkRefreshDaemons(network_driver);
|
||||
virNetworkObjListForEach(network_driver->networks,
|
||||
networkAutostartConfig,
|
||||
@@ -2267,14 +2269,16 @@ networkReloadFirewallRulesHelper(virNetworkObjPtr obj,
|
||||
|
||||
|
||||
static void
|
||||
-networkReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup)
|
||||
+networkReloadFirewallRules(virNetworkDriverStatePtr driver,
|
||||
+ bool startup,
|
||||
+ bool force)
|
||||
{
|
||||
VIR_INFO("Reloading iptables rules");
|
||||
/* Ideally we'd not even register the driver when unprivilegd
|
||||
* but until we untangle the virt driver that's not viable */
|
||||
if (!driver->privileged)
|
||||
return;
|
||||
- networkPreReloadFirewallRules(driver, startup);
|
||||
+ networkPreReloadFirewallRules(driver, startup, force);
|
||||
virNetworkObjListForEach(driver->networks,
|
||||
networkReloadFirewallRulesHelper,
|
||||
NULL);
|
||||
diff --git a/src/network/bridge_driver_linux.c b/src/network/bridge_driver_linux.c
|
||||
index f4e4e2df76..f65928e556 100644
|
||||
--- a/src/network/bridge_driver_linux.c
|
||||
+++ b/src/network/bridge_driver_linux.c
|
||||
@@ -36,11 +36,14 @@ VIR_LOG_INIT("network.bridge_driver_linux");
|
||||
#define PROC_NET_ROUTE "/proc/net/route"
|
||||
|
||||
static virOnceControl createdOnce;
|
||||
-static bool createdChains;
|
||||
+static bool chainInitDone; /* true iff networkSetupPrivateChains was ever called */
|
||||
+static bool createdChains; /* true iff networkSetupPrivateChains created chains during most recent call */
|
||||
static virErrorPtr errInitV4;
|
||||
static virErrorPtr errInitV6;
|
||||
|
||||
-/* Only call via virOnce */
|
||||
+/* Usually only called via virOnce, but can also be called directly in
|
||||
+ * response to firewalld reload (if chainInitDone == true)
|
||||
+ */
|
||||
static void networkSetupPrivateChains(void)
|
||||
{
|
||||
int rc;
|
||||
@@ -82,6 +85,8 @@ static void networkSetupPrivateChains(void)
|
||||
VIR_DEBUG("Global IPv6 chains already exist");
|
||||
}
|
||||
}
|
||||
+
|
||||
+ chainInitDone = true;
|
||||
}
|
||||
|
||||
|
||||
@@ -111,7 +116,10 @@ networkHasRunningNetworks(virNetworkDriverStatePtr driver)
|
||||
}
|
||||
|
||||
|
||||
-void networkPreReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup)
|
||||
+void
|
||||
+networkPreReloadFirewallRules(virNetworkDriverStatePtr driver,
|
||||
+ bool startup,
|
||||
+ bool force)
|
||||
{
|
||||
/*
|
||||
* If there are any running networks, we need to
|
||||
@@ -130,29 +138,42 @@ void networkPreReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup
|
||||
* of starting the network though as that makes them
|
||||
* more likely to be seen by a human
|
||||
*/
|
||||
- if (!networkHasRunningNetworks(driver)) {
|
||||
- VIR_DEBUG("Delayed global rule setup as no networks are running");
|
||||
- return;
|
||||
- }
|
||||
+ if (chainInitDone && force) {
|
||||
+ /* The Private chains have already been initialized once
|
||||
+ * during this run of libvirtd, so 1) we can't do it again via
|
||||
+ * virOnce(), and 2) we need to re-add the private chains even
|
||||
+ * if there are currently no running networks, because the
|
||||
+ * next time a network is started, libvirt will expect that
|
||||
+ * the chains have already been added. So we call directly
|
||||
+ * instead of via virOnce().
|
||||
+ */
|
||||
+ networkSetupPrivateChains();
|
||||
|
||||
- ignore_value(virOnce(&createdOnce, networkSetupPrivateChains));
|
||||
+ } else {
|
||||
+ if (!networkHasRunningNetworks(driver)) {
|
||||
+ VIR_DEBUG("Delayed global rule setup as no networks are running");
|
||||
+ return;
|
||||
+ }
|
||||
|
||||
- /*
|
||||
- * If this is initial startup, and we just created the
|
||||
- * top level private chains we either
|
||||
- *
|
||||
- * - upgraded from old libvirt
|
||||
- * - freshly booted from clean state
|
||||
- *
|
||||
- * In the first case we must delete the old rules from
|
||||
- * the built-in chains, instead of our new private chains.
|
||||
- * In the second case it doesn't matter, since no existing
|
||||
- * rules will be present. Thus we can safely just tell it
|
||||
- * to always delete from the builin chain
|
||||
- */
|
||||
- if (startup && createdChains) {
|
||||
- VIR_DEBUG("Requesting cleanup of legacy firewall rules");
|
||||
- iptablesSetDeletePrivate(false);
|
||||
+ ignore_value(virOnce(&createdOnce, networkSetupPrivateChains));
|
||||
+
|
||||
+ /*
|
||||
+ * If this is initial startup, and we just created the
|
||||
+ * top level private chains we either
|
||||
+ *
|
||||
+ * - upgraded from old libvirt
|
||||
+ * - freshly booted from clean state
|
||||
+ *
|
||||
+ * In the first case we must delete the old rules from
|
||||
+ * the built-in chains, instead of our new private chains.
|
||||
+ * In the second case it doesn't matter, since no existing
|
||||
+ * rules will be present. Thus we can safely just tell it
|
||||
+ * to always delete from the builin chain
|
||||
+ */
|
||||
+ if (startup && createdChains) {
|
||||
+ VIR_DEBUG("Requesting cleanup of legacy firewall rules");
|
||||
+ iptablesSetDeletePrivate(false);
|
||||
+ }
|
||||
}
|
||||
}
|
||||
|
||||
diff --git a/src/network/bridge_driver_nop.c b/src/network/bridge_driver_nop.c
|
||||
index ec7b1ed8b7..74a9b87158 100644
|
||||
--- a/src/network/bridge_driver_nop.c
|
||||
+++ b/src/network/bridge_driver_nop.c
|
||||
@@ -20,7 +20,8 @@
|
||||
#include <config.h>
|
||||
|
||||
void networkPreReloadFirewallRules(virNetworkDriverStatePtr driver ATTRIBUTE_UNUSED,
|
||||
- bool startup ATTRIBUTE_UNUSED)
|
||||
+ bool startup ATTRIBUTE_UNUSED,
|
||||
+ bool force ATTRIBUTE_UNUSED)
|
||||
{
|
||||
}
|
||||
|
||||
diff --git a/src/network/bridge_driver_platform.h b/src/network/bridge_driver_platform.h
|
||||
index 169417a6c0..48ab52c160 100644
|
||||
--- a/src/network/bridge_driver_platform.h
|
||||
+++ b/src/network/bridge_driver_platform.h
|
||||
@@ -62,7 +62,7 @@ struct _virNetworkDriverState {
|
||||
typedef struct _virNetworkDriverState virNetworkDriverState;
|
||||
typedef virNetworkDriverState *virNetworkDriverStatePtr;
|
||||
|
||||
-void networkPreReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup);
|
||||
+void networkPreReloadFirewallRules(virNetworkDriverStatePtr driver, bool startup, bool force);
|
||||
void networkPostReloadFirewallRules(bool startup);
|
||||
|
||||
int networkCheckRouteCollision(virNetworkDefPtr def);
|
||||
@@ -0,0 +1,85 @@
|
||||
From: Laine Stump <laine@redhat.com>
|
||||
Date: Fri, 1 May 2020 00:05:50 -0400
|
||||
Subject: [PATCH] systemd: start libvirtd after firewalld/iptables services
|
||||
|
||||
When a system has enabled the iptables/ip6tables services rather than
|
||||
firewalld, there is no explicit ordering of the start of those
|
||||
services vs. libvirtd. This creates a problem when libvirtd.service is
|
||||
started before ip[6]tables, as the latter, when it finally is started,
|
||||
will remove all of the iptables rules that had previously been added
|
||||
by libvirt, including the custom chains where libvirt's rules are
|
||||
kept. This results in an error message similar to the following when a
|
||||
user subsequently tries to start a new libvirt network:
|
||||
|
||||
"Error while activating network: Call to virNetworkCreate failed:
|
||||
internal error: Failed to apply firewall rules
|
||||
/usr/sbin/ip6tables -w --table filter --insert LIBVIRT_FWO \
|
||||
--in-interface virbr2 --jump REJECT:
|
||||
ip6tables: No chain/target/match by that name."
|
||||
|
||||
(Prior to logging this error, it also would have caused failure to
|
||||
forward (or block) traffic in some cases, e.g. for guests on a NATed
|
||||
network, since libvirt's rules to forward/block had all been deleted
|
||||
and libvirt didn't know about it, so it couldn't fix the problem)
|
||||
|
||||
When this happens, the problem can be remedied by simply restarting
|
||||
libvirtd.service (which has the side-effect of reloading all
|
||||
libvirt-generated firewall rules)
|
||||
|
||||
Instead, we can just explicitly stating in the libvirtd.service file
|
||||
that libvirtd.service should start after ip6tables.service and
|
||||
ip6tables.service, eliminating the race condition that leads to the
|
||||
error.
|
||||
|
||||
There is also nothing (that I can see) in the systemd .service files
|
||||
to guarantee that firewalld.service will be started (if enabled) prior
|
||||
to libvirtd.service. The same error scenario given above would occur
|
||||
if libvirtd.service started before firewalld.service. Even before
|
||||
that, though libvirtd would have detected that firewalld.service was
|
||||
disabled, and then turn off all firewalld support. So, for example,
|
||||
firewalld's libvirt zone wouldn't be used, and most likely traffic
|
||||
from guests would therefore be blocked (all with no external
|
||||
indication of the source of the problem other than a debug-level log
|
||||
when libvirtd was started saying that firewalld wasn't in use); also
|
||||
libvirtd wouldn't notice when firewalld reloaded its rules (which also
|
||||
simultaneously deletes all of libvirt's rules).
|
||||
|
||||
I'm not aware of any reports that have been traced back to
|
||||
libvirtd.service starting before firewalld.service, but have seen that
|
||||
error reported multiple times, and also don't see an existing
|
||||
dependency that would guarantee firewalld.service starts before
|
||||
libvirtd.service, so it's possible it's been happening and we just
|
||||
haven't gotten to the bottom of it.
|
||||
|
||||
This patch adds an After= line to the libvirtd.service file for each
|
||||
of iptables.service, ip6tables.service, and firewalld.servicee, which
|
||||
should guarantee that libvirtd.service isn't started until systemd has
|
||||
started whichever of the others is enabled.
|
||||
|
||||
This race was diagnosed, and patch proposed, by Jason Montleon in
|
||||
https://bugzilla.redhat.com/1723698 . At the time (April 2019) danpb
|
||||
agreed with him that this change to libvirtd.service was a reasonable
|
||||
thing to do, but I guess everyone thought someone else was going to
|
||||
post a patch, so in the end nobody did.
|
||||
|
||||
Signed-off-by: Laine Stump <laine@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit 0756415f147dda15a417bd79eef9a62027d176e6)
|
||||
---
|
||||
src/remote/libvirtd.service.in | 3 +++
|
||||
1 file changed, 3 insertions(+)
|
||||
|
||||
diff --git a/src/remote/libvirtd.service.in b/src/remote/libvirtd.service.in
|
||||
index d5d98f0c12..ada5be62e6 100644
|
||||
--- a/src/remote/libvirtd.service.in
|
||||
+++ b/src/remote/libvirtd.service.in
|
||||
@@ -11,6 +11,9 @@ Wants=libvirtd-admin.socket
|
||||
Wants=systemd-machined.service
|
||||
Before=libvirt-guests.service
|
||||
After=network.target
|
||||
+After=firewalld.service
|
||||
+After=iptables.service
|
||||
+After=ip6tables.service
|
||||
After=dbus.service
|
||||
After=iscsid.service
|
||||
After=apparmor.service
|
||||
@@ -0,0 +1,41 @@
|
||||
From: Peter Krempa <pkrempa@redhat.com>
|
||||
Date: Wed, 19 Feb 2020 08:40:59 +0100
|
||||
Subject: [PATCH] qemuDomainGetStatsIOThread: Don't leak array with 0 iothreads
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
qemuMonitorGetIOThreads returns a NULL-terminated list even when 0
|
||||
iothreads are present. The caller didn't perform cleanup if there were 0
|
||||
iothreads leaking the array.
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1804548
|
||||
|
||||
Fixes: d1eac92784573559b6fd56836e33b215c89308e3
|
||||
Reported-by: Jing Yan <jiyan@redhat.com>
|
||||
Signed-off-by: Peter Krempa <pkrempa@redhat.com>
|
||||
Reviewed-by: Ján Tomko <jtomko@redhat.com>
|
||||
(cherry picked from commit 9bf9e0ae6af38c806f4672ca7b12a6b38d5a9581)
|
||||
---
|
||||
src/qemu/qemu_driver.c | 8 ++++++--
|
||||
1 file changed, 6 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 5dd2616c7b..331e53b971 100644
|
||||
--- a/src/qemu/qemu_driver.c
|
||||
+++ b/src/qemu/qemu_driver.c
|
||||
@@ -21632,8 +21632,12 @@ qemuDomainGetStatsIOThread(virQEMUDriverPtr driver,
|
||||
if ((niothreads = qemuDomainGetIOThreadsMon(driver, dom, &iothreads)) < 0)
|
||||
return -1;
|
||||
|
||||
- if (niothreads == 0)
|
||||
- return 0;
|
||||
+ /* qemuDomainGetIOThreadsMon returns a NULL-terminated list, so we must free
|
||||
+ * it even if it returns 0 */
|
||||
+ if (niothreads == 0) {
|
||||
+ ret = 0;
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
|
||||
QEMU_ADD_COUNT_PARAM(record, maxparams, "iothread", niothreads);
|
||||
|
||||
@@ -0,0 +1,47 @@
|
||||
From: Yi Li <yili@winhong.com>
|
||||
Date: Sat, 21 Dec 2019 08:33:33 +0800
|
||||
Subject: [PATCH] storage: Fix daemon crash on lookup storagepool by targetpath
|
||||
|
||||
Causing a crash when storagePoolLookupByTargetPath beacuse of
|
||||
Some types of storage pool have no target elements.
|
||||
Use STREQ_NULLABLE instead of STREQ
|
||||
Avoids segfaults when using NULL arguments.
|
||||
|
||||
Core was generated by `/usr/sbin/libvirtd'.
|
||||
Program terminated with signal 11, Segmentation fault.
|
||||
(gdb) bt
|
||||
0 0x0000ffff9e951388 in strcmp () from /lib64/libc.so.6
|
||||
1 0x0000ffff92103e9c in storagePoolLookupByTargetPathCallback (
|
||||
obj=0xffff7009aab0, opaque=0xffff801058b0) at storage/storage_driver.c:1649
|
||||
2 0x0000ffff9f2c52a4 in virStoragePoolObjListSearchCb (
|
||||
payload=0xffff801058b0, name=<optimized out>, opaque=<optimized out>)
|
||||
at conf/virstorageobj.c:476
|
||||
3 0x0000ffff9f1f2f7c in virHashSearch (ctable=0xffff800f4f60,
|
||||
iter=iter@entry=0xffff9f2c5278 <virStoragePoolObjListSearchCb>,
|
||||
data=data@entry=0xffff95af7488, name=name@entry=0x0) at util/virhash.c:696
|
||||
4 0x0000ffff9f2c64f0 in virStoragePoolObjListSearch (pools=0xffff800f2ce0,
|
||||
searcher=searcher@entry=0xffff92103e68 <storagePoolLookupByTargetPathCallback>,
|
||||
opaque=<optimized out>) at conf/virstorageobj.c:505
|
||||
5 0x0000ffff92101f54 in storagePoolLookupByTargetPath (conn=0xffff5c0009f0,
|
||||
path=0xffff7009a850 "/vms/images") at storage/storage_driver.c:1672
|
||||
|
||||
Reviewed-by: Cole Robinson <crobinso@redhat.com>
|
||||
Signed-off-by: Yi Li <yili@winhong.com>
|
||||
(cherry picked from commit dfff16a7c261f8d28e3abe60a47165f845fa952f)
|
||||
---
|
||||
src/storage/storage_driver.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/src/storage/storage_driver.c b/src/storage/storage_driver.c
|
||||
index 05192027d6..d878b0be92 100644
|
||||
--- a/src/storage/storage_driver.c
|
||||
+++ b/src/storage/storage_driver.c
|
||||
@@ -1675,7 +1675,7 @@ storagePoolLookupByTargetPathCallback(virStoragePoolObjPtr obj,
|
||||
return false;
|
||||
|
||||
def = virStoragePoolObjGetDef(obj);
|
||||
- return STREQ(path, def->target.path);
|
||||
+ return STREQ_NULLABLE(path, def->target.path);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,168 @@
|
||||
From: Jonathon Jongsma <jjongsma@redhat.com>
|
||||
Date: Thu, 5 Dec 2019 10:08:52 -0600
|
||||
Subject: [PATCH] qemu: don't hold both jobs for suspend
|
||||
|
||||
We have to assume that the guest agent may be malicious so we don't want
|
||||
to allow any agent queries to block any other libvirt API. By holding a
|
||||
monitor job while we're querying the agent, we open ourselves up to a
|
||||
DoS.
|
||||
|
||||
So split the function up a bit to only hold the monitor job while
|
||||
querying qemu for whether the domain supports suspend. Then acquire only
|
||||
an agent job while issuing the agent suspend command.
|
||||
|
||||
Signed-off-by: Jonathon Jongsma <jjongsma@redhat.com>
|
||||
Signed-off-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
Reviewed-by: Michal Privoznik <mprivozn@redhat.com>
|
||||
(cherry picked from commit a663a860819287e041c3de672aad1d8543098ecc)
|
||||
---
|
||||
src/qemu/qemu_driver.c | 94 ++++++++++++++++++++++++++----------------
|
||||
1 file changed, 59 insertions(+), 35 deletions(-)
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 331e53b971..96c0b3505a 100644
|
||||
--- a/src/qemu/qemu_driver.c
|
||||
+++ b/src/qemu/qemu_driver.c
|
||||
@@ -19867,6 +19867,59 @@ qemuDomainProbeQMPCurrentMachine(virQEMUDriverPtr driver,
|
||||
}
|
||||
|
||||
|
||||
+/* returns -1 on error, or if query is not supported, 0 if query was successful */
|
||||
+static int
|
||||
+qemuDomainQueryWakeupSuspendSupport(virQEMUDriverPtr driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ bool *wakeupSupported)
|
||||
+{
|
||||
+ qemuDomainObjPrivatePtr priv = vm->privateData;
|
||||
+ int ret = -1;
|
||||
+
|
||||
+ if (!virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_QUERY_CURRENT_MACHINE))
|
||||
+ return -1;
|
||||
+
|
||||
+ if (qemuDomainObjBeginJob(driver, vm, QEMU_JOB_MODIFY) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if ((ret = virDomainObjCheckActive(vm)) < 0)
|
||||
+ goto endjob;
|
||||
+
|
||||
+ ret = qemuDomainProbeQMPCurrentMachine(driver, vm, wakeupSupported);
|
||||
+
|
||||
+ endjob:
|
||||
+ qemuDomainObjEndJob(driver, vm);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+qemuDomainPMSuspendAgent(virQEMUDriverPtr driver,
|
||||
+ virDomainObjPtr vm,
|
||||
+ unsigned int target)
|
||||
+{
|
||||
+ qemuAgentPtr agent;
|
||||
+ int ret = -1;
|
||||
+
|
||||
+ if (qemuDomainObjBeginAgentJob(driver, vm, QEMU_AGENT_JOB_MODIFY) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if ((ret = virDomainObjCheckActive(vm)) < 0)
|
||||
+ goto endjob;
|
||||
+
|
||||
+ if (!qemuDomainAgentAvailable(vm, true))
|
||||
+ goto endjob;
|
||||
+
|
||||
+ agent = qemuDomainObjEnterAgent(vm);
|
||||
+ ret = qemuAgentSuspend(agent, target);
|
||||
+ qemuDomainObjExitAgent(vm, agent);
|
||||
+
|
||||
+ endjob:
|
||||
+ qemuDomainObjEndAgentJob(vm);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+
|
||||
static int
|
||||
qemuDomainPMSuspendForDuration(virDomainPtr dom,
|
||||
unsigned int target,
|
||||
@@ -19874,11 +19927,9 @@ qemuDomainPMSuspendForDuration(virDomainPtr dom,
|
||||
unsigned int flags)
|
||||
{
|
||||
virQEMUDriverPtr driver = dom->conn->privateData;
|
||||
- qemuDomainObjPrivatePtr priv;
|
||||
virDomainObjPtr vm;
|
||||
- qemuAgentPtr agent;
|
||||
- qemuDomainJob job = QEMU_JOB_NONE;
|
||||
int ret = -1;
|
||||
+ bool wakeupSupported;
|
||||
|
||||
virCheckFlags(0, -1);
|
||||
|
||||
@@ -19903,17 +19954,6 @@ qemuDomainPMSuspendForDuration(virDomainPtr dom,
|
||||
if (virDomainPMSuspendForDurationEnsureACL(dom->conn, vm->def) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- priv = vm->privateData;
|
||||
-
|
||||
- if (virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_QUERY_CURRENT_MACHINE))
|
||||
- job = QEMU_JOB_MODIFY;
|
||||
-
|
||||
- if (qemuDomainObjBeginJobWithAgent(driver, vm, job, QEMU_AGENT_JOB_MODIFY) < 0)
|
||||
- goto cleanup;
|
||||
-
|
||||
- if (virDomainObjCheckActive(vm) < 0)
|
||||
- goto endjob;
|
||||
-
|
||||
/*
|
||||
* The case we want to handle here is when QEMU has the API (i.e.
|
||||
* QEMU_CAPS_QUERY_CURRENT_MACHINE is set). Otherwise, do not interfere
|
||||
@@ -19921,16 +19961,11 @@ qemuDomainPMSuspendForDuration(virDomainPtr dom,
|
||||
* that don't know about this cap, will keep their old behavior of
|
||||
* suspending 'in the dark'.
|
||||
*/
|
||||
- if (virQEMUCapsGet(priv->qemuCaps, QEMU_CAPS_QUERY_CURRENT_MACHINE)) {
|
||||
- bool wakeupSupported;
|
||||
-
|
||||
- if (qemuDomainProbeQMPCurrentMachine(driver, vm, &wakeupSupported) < 0)
|
||||
- goto endjob;
|
||||
-
|
||||
+ if (qemuDomainQueryWakeupSuspendSupport(driver, vm, &wakeupSupported) == 0) {
|
||||
if (!wakeupSupported) {
|
||||
virReportError(VIR_ERR_OPERATION_UNSUPPORTED, "%s",
|
||||
_("Domain does not have suspend support"));
|
||||
- goto endjob;
|
||||
+ goto cleanup;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19940,29 +19975,18 @@ qemuDomainPMSuspendForDuration(virDomainPtr dom,
|
||||
target == VIR_NODE_SUSPEND_TARGET_HYBRID)) {
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||
_("S3 state is disabled for this domain"));
|
||||
- goto endjob;
|
||||
+ goto cleanup;
|
||||
}
|
||||
|
||||
if (vm->def->pm.s4 == VIR_TRISTATE_BOOL_NO &&
|
||||
target == VIR_NODE_SUSPEND_TARGET_DISK) {
|
||||
virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
|
||||
_("S4 state is disabled for this domain"));
|
||||
- goto endjob;
|
||||
+ goto cleanup;
|
||||
}
|
||||
}
|
||||
|
||||
- if (!qemuDomainAgentAvailable(vm, true))
|
||||
- goto endjob;
|
||||
-
|
||||
- agent = qemuDomainObjEnterAgent(vm);
|
||||
- ret = qemuAgentSuspend(agent, target);
|
||||
- qemuDomainObjExitAgent(vm, agent);
|
||||
-
|
||||
- endjob:
|
||||
- if (job)
|
||||
- qemuDomainObjEndJobWithAgent(driver, vm);
|
||||
- else
|
||||
- qemuDomainObjEndAgentJob(vm);
|
||||
+ ret = qemuDomainPMSuspendAgent(driver, vm, target);
|
||||
|
||||
cleanup:
|
||||
virDomainObjEndAPI(&vm);
|
||||
@@ -1,21 +0,0 @@
|
||||
# Makefile for source rpm: libvirt
|
||||
# $Id$
|
||||
NAME := libvirt
|
||||
SPECFILE = $(firstword $(wildcard *.spec))
|
||||
|
||||
define find-makefile-common
|
||||
for d in common ../common ../../common ; do if [ -f $$d/Makefile.common ] ; then if [ -f $$d/CVS/Root -a -w $$d/Makefile.common ] ; then cd $$d ; cvs -Q update ; fi ; echo "$$d/Makefile.common" ; break ; fi ; done
|
||||
endef
|
||||
|
||||
MAKEFILE_COMMON := $(shell $(find-makefile-common))
|
||||
|
||||
ifeq ($(MAKEFILE_COMMON),)
|
||||
# attempt a checkout
|
||||
define checkout-makefile-common
|
||||
test -f CVS/Root && { cvs -Q -d $$(cat CVS/Root) checkout common && echo "common/Makefile.common" ; } || { echo "ERROR: I can't figure out how to checkout the 'common' module." ; exit -1 ; } >&2
|
||||
endef
|
||||
|
||||
MAKEFILE_COMMON := $(shell $(checkout-makefile-common))
|
||||
endif
|
||||
|
||||
include $(MAKEFILE_COMMON)
|
||||
@@ -1,122 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd.init.in audio/qemud/libvirtd.init.in
|
||||
--- libvirt-0.7.1/qemud/libvirtd.init.in 2009-07-22 09:37:32.000000000 -0400
|
||||
+++ audio/qemud/libvirtd.init.in 2010-05-26 12:05:50.584822000 -0400
|
||||
@@ -47,6 +47,9 @@ KRB5_KTNAME=/etc/libvirt/krb5.tab
|
||||
|
||||
test -f @sysconfdir@/sysconfig/libvirtd && . @sysconfdir@/sysconfig/libvirtd
|
||||
|
||||
+export QEMU_AUDIO_DRV
|
||||
+export SDL_AUDIODRIVER
|
||||
+
|
||||
LIBVIRTD_CONFIG_ARGS=
|
||||
if [ -n "$LIBVIRTD_CONFIG" ]
|
||||
then
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd_qemu.aug audio/qemud/libvirtd_qemu.aug
|
||||
--- libvirt-0.7.1/qemud/libvirtd_qemu.aug 2009-09-08 10:16:02.000000000 -0400
|
||||
+++ audio/qemud/libvirtd_qemu.aug 2010-05-26 12:07:24.169216000 -0400
|
||||
@@ -36,6 +36,7 @@ module Libvirtd_qemu =
|
||||
| str_array_entry "cgroup_device_acl"
|
||||
| str_entry "save_image_format"
|
||||
| str_entry "hugetlbfs_mount"
|
||||
+ | bool_entry "vnc_allow_host_audio"
|
||||
|
||||
(* Each enty in the config is one of the following three ... *)
|
||||
let entry = vnc_entry
|
||||
diff -rup libvirt-0.7.1/qemud/libvirtd.sysconf audio/qemud/libvirtd.sysconf
|
||||
--- libvirt-0.7.1/qemud/libvirtd.sysconf 2010-05-26 12:04:08.379130000 -0400
|
||||
+++ audio/qemud/libvirtd.sysconf 2010-05-26 12:10:28.263486000 -0400
|
||||
@@ -11,7 +11,8 @@
|
||||
# Override the QEMU/SDL default audio driver probing when
|
||||
# starting virtual machines using SDL graphics
|
||||
#
|
||||
-# NB these have no effect for VMs using VNC
|
||||
+# NB these have no effect for VMs using VNC, unless vnc_allow_host_audio
|
||||
+# is enabled in /etc/libvirt/qemu.conf
|
||||
#QEMU_AUDIO_DRV=sdl
|
||||
#
|
||||
#SDL_AUDIODRIVER=pulse
|
||||
diff -rup libvirt-0.7.1/qemud/test_libvirtd_qemu.aug audio/qemud/test_libvirtd_qemu.aug
|
||||
--- libvirt-0.7.1/qemud/test_libvirtd_qemu.aug 2009-09-08 10:16:02.000000000 -0400
|
||||
+++ audio/qemud/test_libvirtd_qemu.aug 2010-05-26 12:11:19.540907000 -0400
|
||||
@@ -92,6 +92,8 @@ cgroup_device_acl = [ \"/dev/null\", \"/
|
||||
|
||||
save_image_format = \"gzip\"
|
||||
|
||||
+vnc_allow_host_audio = 1
|
||||
+
|
||||
hugetlbfs_mount = \"/dev/hugepages\"
|
||||
"
|
||||
|
||||
@@ -195,4 +197,6 @@ hugetlbfs_mount = \"/dev/hugepages\"
|
||||
{ "#empty" }
|
||||
{ "save_image_format" = "gzip" }
|
||||
{ "#empty" }
|
||||
-{ "hugetlbfs_mount" = "/dev/hugepages" }
|
||||
\ No newline at end of file
|
||||
+{ "hugetlbfs_mount" = "/dev/hugepages" }
|
||||
+{ "#empty" }
|
||||
+{ "vnc_allow_host_audio" = "1" }
|
||||
diff -rup libvirt-0.7.1/src/qemu.conf audio/src/qemu.conf
|
||||
--- libvirt-0.7.1/src/qemu.conf 2009-09-10 05:15:56.000000000 -0400
|
||||
+++ audio/src/qemu.conf 2010-05-26 12:08:12.419811000 -0400
|
||||
@@ -152,3 +152,13 @@
|
||||
# in a location of $MOUNTPOINT/libvirt/qemu
|
||||
|
||||
# hugetlbfs_mount = "/dev/hugepages"
|
||||
+#
|
||||
+
|
||||
+# QEMU implements an extension for providing audio over a VNC connection,
|
||||
+# though if your VNC client does not support it, your only chance for getting
|
||||
+# sound output is through regular audio backends. By default, libvirt will
|
||||
+# disable all QEMU sound backends if using VNC, since they can cause
|
||||
+# permissions issues. Enabling this option will make libvirtd honor the
|
||||
+# QEMU_AUDIO_DRV environment variable when using VNC.
|
||||
+#
|
||||
+# vnc_allow_host_audio = 0
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.c audio/src/qemu_conf.c
|
||||
--- libvirt-0.7.1/src/qemu_conf.c 2010-05-26 12:04:08.578062000 -0400
|
||||
+++ audio/src/qemu_conf.c 2010-05-26 12:09:31.174206000 -0400
|
||||
@@ -318,6 +318,10 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
}
|
||||
}
|
||||
|
||||
+ p = virConfGetValue (conf, "vnc_allow_host_audio");
|
||||
+ CHECK_TYPE ("vnc_allow_host_audio", VIR_CONF_LONG);
|
||||
+ if (p) driver->vncAllowHostAudio = p->l;
|
||||
+
|
||||
virConfFree (conf);
|
||||
return 0;
|
||||
}
|
||||
@@ -2113,12 +2117,15 @@ int qemudBuildCommandLine(virConnectPtr
|
||||
ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap);
|
||||
}
|
||||
|
||||
- /* QEMU implements a VNC extension for providing audio, so we
|
||||
- * set the audio backend to none, to prevent it opening the
|
||||
- * host OS audio devices since that causes security issues
|
||||
- * and is non-sensical when using VNC.
|
||||
+ /* Unless user requested it, set the audio backend to none, to
|
||||
+ * prevent it opening the host OS audio devices, since that causes
|
||||
+ * security issues and might not work when using VNC.
|
||||
*/
|
||||
- ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
+ if (driver->vncAllowHostAudio) {
|
||||
+ ADD_ENV_COPY("QEMU_AUDIO_DRV");
|
||||
+ } else {
|
||||
+ ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
+ }
|
||||
} else if ((def->ngraphics == 1) &&
|
||||
def->graphics[0]->type == VIR_DOMAIN_GRAPHICS_TYPE_SDL) {
|
||||
char *xauth = NULL;
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.h audio/src/qemu_conf.h
|
||||
--- libvirt-0.7.1/src/qemu_conf.h 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ audio/src/qemu_conf.h 2010-05-26 12:10:07.196992000 -0400
|
||||
@@ -110,6 +110,8 @@ struct qemud_driver {
|
||||
char *hugetlbfs_mount;
|
||||
char *hugepage_path;
|
||||
|
||||
+ unsigned int vncAllowHostAudio : 1;
|
||||
+
|
||||
virCapsPtr caps;
|
||||
|
||||
/* An array of callbacks */
|
||||
@@ -1,99 +0,0 @@
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-17 11:30:54.501983000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-17 11:20:13.032900000 -0400
|
||||
@@ -69,7 +69,7 @@
|
||||
#include "hostusb.h"
|
||||
#include "security.h"
|
||||
#include "cgroup.h"
|
||||
-
|
||||
+#include "storage_file.h"
|
||||
|
||||
#define VIR_FROM_THIS VIR_FROM_QEMU
|
||||
|
||||
@@ -1895,6 +1895,7 @@ static int qemuDomainSetDeviceOwnership(
|
||||
{
|
||||
uid_t uid;
|
||||
gid_t gid;
|
||||
+ const char *path;
|
||||
|
||||
if (!driver->privileged)
|
||||
return 0;
|
||||
@@ -1912,6 +1913,35 @@ static int qemuDomainSetDeviceOwnership(
|
||||
(def->data.disk->readonly || def->data.disk->shared))
|
||||
return 0;
|
||||
|
||||
+ if (!def->data.disk->src)
|
||||
+ return 0;
|
||||
+
|
||||
+ path = def->data.disk->src;
|
||||
+ do {
|
||||
+ virStorageFileMetadata meta;
|
||||
+ int ret;
|
||||
+
|
||||
+ memset(&meta, 0, sizeof(meta));
|
||||
+
|
||||
+ ret = virStorageFileGetMetadata(conn, path, &meta);
|
||||
+
|
||||
+ if (path != def->data.disk->src)
|
||||
+ VIR_FREE(path);
|
||||
+ path = NULL;
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (meta.backingStore != NULL &&
|
||||
+ qemuDomainSetFileOwnership(conn,
|
||||
+ meta.backingStore, uid, gid) < 0) {
|
||||
+ VIR_FREE(meta.backingStore);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ path = meta.backingStore;
|
||||
+ } while (path != NULL);
|
||||
+
|
||||
return qemuDomainSetFileOwnership(conn, def->data.disk->src, uid, gid);
|
||||
|
||||
case VIR_DOMAIN_DEVICE_HOSTDEV:
|
||||
@@ -1929,6 +1959,7 @@ static int qemuDomainSetAllDeviceOwnersh
|
||||
int i;
|
||||
uid_t uid;
|
||||
gid_t gid;
|
||||
+ const char *path;
|
||||
|
||||
if (!driver->privileged)
|
||||
return 0;
|
||||
@@ -1949,6 +1980,35 @@ static int qemuDomainSetAllDeviceOwnersh
|
||||
(def->disks[i]->readonly || def->disks[i]->shared))
|
||||
continue;
|
||||
|
||||
+ if (!def->disks[i]->src)
|
||||
+ continue;
|
||||
+
|
||||
+ path = def->disks[i]->src;
|
||||
+ do {
|
||||
+ virStorageFileMetadata meta;
|
||||
+ int ret;
|
||||
+
|
||||
+ memset(&meta, 0, sizeof(meta));
|
||||
+
|
||||
+ ret = virStorageFileGetMetadata(conn, path, &meta);
|
||||
+
|
||||
+ if (path != def->disks[i]->src)
|
||||
+ VIR_FREE(path);
|
||||
+ path = NULL;
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (meta.backingStore != NULL &&
|
||||
+ qemuDomainSetFileOwnership(conn,
|
||||
+ meta.backingStore, uid, gid) < 0) {
|
||||
+ VIR_FREE(meta.backingStore);
|
||||
+ return -1;
|
||||
+ }
|
||||
+
|
||||
+ path = meta.backingStore;
|
||||
+ } while (path != NULL);
|
||||
+
|
||||
if (qemuDomainSetFileOwnership(conn, def->disks[i]->src, uid, gid) < 0)
|
||||
return -1;
|
||||
}
|
||||
@@ -1,82 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/qemu.conf new/src/qemu.conf
|
||||
--- libvirt-0.7.1/src/qemu.conf 2010-06-03 15:01:14.288848000 -0400
|
||||
+++ new/src/qemu.conf 2010-06-03 15:04:05.062031000 -0400
|
||||
@@ -162,3 +162,12 @@
|
||||
# QEMU_AUDIO_DRV environment variable when using VNC.
|
||||
#
|
||||
# vnc_allow_host_audio = 0
|
||||
+
|
||||
+# If clear_emulator_capabilities is enabled, libvirt will drop all
|
||||
+# privileged capabilities of the QEmu/KVM emulator. This is enabled by
|
||||
+# default.
|
||||
+#
|
||||
+# Warning: Disabling this option means that a compromised guest can
|
||||
+# exploit the privileges and possibly do damage to the host.
|
||||
+#
|
||||
+# clear_emulator_capabilities = 1
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.c new/src/qemu_conf.c
|
||||
--- libvirt-0.7.1/src/qemu_conf.c 2010-06-03 15:01:14.302852000 -0400
|
||||
+++ new/src/qemu_conf.c 2010-06-03 15:05:09.755183000 -0400
|
||||
@@ -98,7 +98,9 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
char *group;
|
||||
int i;
|
||||
|
||||
- /* Setup 2 critical defaults */
|
||||
+ /* Setup critical defaults */
|
||||
+ driver->clearEmulatorCapabilities = 1;
|
||||
+
|
||||
if (!(driver->vncListen = strdup("127.0.0.1"))) {
|
||||
virReportOOMError(NULL);
|
||||
return -1;
|
||||
@@ -322,6 +324,10 @@ int qemudLoadDriverConfig(struct qemud_d
|
||||
CHECK_TYPE ("vnc_allow_host_audio", VIR_CONF_LONG);
|
||||
if (p) driver->vncAllowHostAudio = p->l;
|
||||
|
||||
+ p = virConfGetValue (conf, "clear_emulator_capabilities");
|
||||
+ CHECK_TYPE ("clear_emulator_capabilities", VIR_CONF_LONG);
|
||||
+ if (p) driver->clearEmulatorCapabilities = p->l;
|
||||
+
|
||||
virConfFree (conf);
|
||||
return 0;
|
||||
}
|
||||
diff -rup libvirt-0.7.1/src/qemu_conf.h new/src/qemu_conf.h
|
||||
--- libvirt-0.7.1/src/qemu_conf.h 2010-06-03 15:01:14.306860000 -0400
|
||||
+++ new/src/qemu_conf.h 2010-06-03 15:05:27.968796000 -0400
|
||||
@@ -111,6 +111,7 @@ struct qemud_driver {
|
||||
char *hugepage_path;
|
||||
|
||||
unsigned int vncAllowHostAudio : 1;
|
||||
+ unsigned int clearEmulatorCapabilities : 1;
|
||||
|
||||
virCapsPtr caps;
|
||||
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 15:01:14.413848000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 15:06:08.186798000 -0400
|
||||
@@ -2063,7 +2063,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
int stdin_fd) {
|
||||
const char **argv = NULL, **tmp;
|
||||
const char **progenv = NULL;
|
||||
- int i, ret;
|
||||
+ int i, ret, runflags;
|
||||
struct stat sb;
|
||||
int *tapfds = NULL;
|
||||
int ntapfds = 0;
|
||||
@@ -2205,9 +2205,16 @@ static int qemudStartVMDaemon(virConnect
|
||||
for (i = 0 ; i < ntapfds ; i++)
|
||||
FD_SET(tapfds[i], &keepfd);
|
||||
|
||||
+ VIR_DEBUG("Clear emulator capabilities: %d",
|
||||
+ driver->clearEmulatorCapabilities);
|
||||
+ runflags = VIR_EXEC_NONBLOCK;
|
||||
+ if (driver->clearEmulatorCapabilities) {
|
||||
+ runflags |= VIR_EXEC_CLEAR_CAPS;
|
||||
+ }
|
||||
+
|
||||
ret = virExecDaemonize(conn, argv, progenv, &keepfd, &child,
|
||||
stdin_fd, &logfile, &logfile,
|
||||
- VIR_EXEC_NONBLOCK | VIR_EXEC_CLEAR_CAPS,
|
||||
+ runflags,
|
||||
qemudSecurityHook, &hookData,
|
||||
pidfile);
|
||||
VIR_FREE(pidfile);
|
||||
@@ -1,12 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 13:51:14.398483000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 13:56:05.667092000 -0400
|
||||
@@ -5988,7 +5988,7 @@ static int qemudDomainAttachDevice(virDo
|
||||
virDomainDiskDeviceTypeToString(dev->data.disk->device));
|
||||
/* Fallthrough */
|
||||
}
|
||||
- if (ret != 0) {
|
||||
+ if (ret != 0 && cgroup) {
|
||||
virCgroupDenyDevicePath(cgroup,
|
||||
dev->data.disk->src);
|
||||
}
|
||||
@@ -1,267 +0,0 @@
|
||||
commit bc0010b3d149df00406b82c37eb59874d8525af4
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Wed Nov 11 12:07:00 2009 +0000
|
||||
|
||||
Fix save and restore with non-privileged guests and SELinux
|
||||
|
||||
When running qemu:///system instance, libvirtd runs as root,
|
||||
but QEMU may optionally be configured to run non-root. When
|
||||
then saving a guest to a state file, the file is initially
|
||||
created as root, and thus QEMU cannot write to it. It is also
|
||||
missing labelling required to allow access via SELinux.
|
||||
|
||||
* src/qemu_driver.c: Set ownership on save image before
|
||||
running migrate command in virDomainSave impl. Call out to
|
||||
security driver to set save image labelling
|
||||
* src/security.h: Add driver APIs for setting
|
||||
and restoring saved state file labelling
|
||||
* src/security_selinux.c: Implement saved state file
|
||||
labelling for SELinux
|
||||
|
||||
diff --git a/src/security.h b/src/security.h
|
||||
index fde2978..5514962 100644
|
||||
--- a/src/security.h
|
||||
+++ b/src/security.h
|
||||
@@ -42,6 +42,11 @@ typedef int (*virSecurityDomainRestoreHostdevLabel) (virConnectPtr conn,
|
||||
typedef int (*virSecurityDomainSetHostdevLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
virDomainHostdevDefPtr dev);
|
||||
+typedef int (*virSecurityDomainSetSavedStateLabel) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile);
|
||||
+typedef int (*virSecurityDomainRestoreSavedStateLabel) (virConnectPtr conn,
|
||||
+ const char *savefile);
|
||||
typedef int (*virSecurityDomainGenLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr sec);
|
||||
typedef int (*virSecurityDomainReserveLabel) (virConnectPtr conn,
|
||||
@@ -71,6 +76,8 @@ struct _virSecurityDriver {
|
||||
virSecurityDomainRestoreLabel domainRestoreSecurityLabel;
|
||||
virSecurityDomainRestoreHostdevLabel domainRestoreSecurityHostdevLabel;
|
||||
virSecurityDomainSetHostdevLabel domainSetSecurityHostdevLabel;
|
||||
+ virSecurityDomainSetSavedStateLabel domainSetSavedStateLabel;
|
||||
+ virSecurityDomainRestoreSavedStateLabel domainRestoreSavedStateLabel;
|
||||
|
||||
/*
|
||||
* This is internally managed driver state and should only be accessed
|
||||
diff --git a/src/security_selinux.c b/src/security_selinux.c
|
||||
index 0e31077..bd838e6 100644
|
||||
--- a/src/security_selinux.c
|
||||
+++ b/src/security_selinux.c
|
||||
@@ -523,6 +523,7 @@ done:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+
|
||||
static int
|
||||
SELinuxRestoreSecurityPCILabel(virConnectPtr conn,
|
||||
pciDevice *dev ATTRIBUTE_UNUSED,
|
||||
@@ -623,6 +624,26 @@ SELinuxRestoreSecurityLabel(virConnectPtr conn,
|
||||
return rc;
|
||||
}
|
||||
|
||||
+
|
||||
+static int
|
||||
+SELinuxSetSavedStateLabel(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ const virSecurityLabelDefPtr secdef = &vm->def->seclabel;
|
||||
+
|
||||
+ return SELinuxSetFilecon(conn, savefile, secdef->imagelabel);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
+SELinuxRestoreSavedStateLabel(virConnectPtr conn,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ return SELinuxRestoreSecurityFileLabel(conn, savefile);
|
||||
+}
|
||||
+
|
||||
+
|
||||
static int
|
||||
SELinuxSecurityVerify(virConnectPtr conn, virDomainDefPtr def)
|
||||
{
|
||||
@@ -692,4 +713,6 @@ virSecurityDriver virSELinuxSecurityDriver = {
|
||||
.domainSetSecurityLabel = SELinuxSetSecurityLabel,
|
||||
.domainSetSecurityHostdevLabel = SELinuxSetSecurityHostdevLabel,
|
||||
.domainRestoreSecurityHostdevLabel = SELinuxRestoreSecurityHostdevLabel,
|
||||
+ .domainSetSavedStateLabel = SELinuxSetSavedStateLabel,
|
||||
+ .domainRestoreSavedStateLabel = SELinuxRestoreSavedStateLabel,
|
||||
};
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 16:28:38.243890000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 16:36:28.035091000 -0400
|
||||
@@ -3907,6 +3907,20 @@ static int qemudDomainSave(virDomainPtr
|
||||
}
|
||||
fd = -1;
|
||||
|
||||
+ if (driver->privileged &&
|
||||
+ chown(path, driver->user, driver->group) < 0) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ _("unable to set ownership of '%s' to user %d:%d"),
|
||||
+ path, driver->user, driver->group);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabel &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabel(dom->conn, vm, path) == -1)
|
||||
+ goto cleanup;
|
||||
+
|
||||
+
|
||||
/* Migrate to file */
|
||||
safe_path = qemudEscapeShellArg(path);
|
||||
if (!safe_path) {
|
||||
@@ -3956,6 +3970,20 @@ static int qemudDomainSave(virDomainPtr
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
+ if (driver->privileged &&
|
||||
+ chown(path, 0, 0) < 0) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ _("unable to set ownership of '%s' to user %d:%d"),
|
||||
+ path, 0, 0);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, path) == -1)
|
||||
+ VIR_WARN("failed to restore save state label on %s", path);
|
||||
+
|
||||
+
|
||||
/* Shut it down */
|
||||
qemudShutdownVMDaemon(dom->conn, driver, vm);
|
||||
event = virDomainEventNewFromObj(vm,
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-18 11:45:29.903145000 -0400
|
||||
@@ -4028,7 +4028,7 @@ static int qemudDomainSave(virDomainPtr
|
||||
|
||||
if (driver->securityDriver &&
|
||||
driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
- driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, path) == -1)
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(dom->conn, vm, path) == -1)
|
||||
VIR_WARN("failed to restore save state label on %s", path);
|
||||
|
||||
|
||||
@@ -4616,6 +4616,11 @@ static int qemudDomainRestore(virConnect
|
||||
}
|
||||
def = NULL;
|
||||
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabelRO &&
|
||||
+ driver->securityDriver->domainSetSavedStateLabelRO(conn, vm, path) == -1)
|
||||
+ goto cleanup;
|
||||
+
|
||||
if (header.version == 2) {
|
||||
const char *intermediate_argv[3] = { NULL, "-dc", NULL };
|
||||
const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
@@ -4651,11 +4656,6 @@ static int qemudDomainRestore(virConnect
|
||||
close(fd);
|
||||
fd = -1;
|
||||
if (ret < 0) {
|
||||
- if (!vm->persistent) {
|
||||
- virDomainRemoveInactive(&driver->domains,
|
||||
- vm);
|
||||
- vm = NULL;
|
||||
- }
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
@@ -4677,6 +4677,19 @@ static int qemudDomainRestore(virConnect
|
||||
ret = 0;
|
||||
|
||||
cleanup:
|
||||
+ if (ret < 0) {
|
||||
+ if (!vm->persistent) {
|
||||
+ virDomainRemoveInactive(&driver->domains,
|
||||
+ vm);
|
||||
+ vm = NULL;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (driver->securityDriver &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel &&
|
||||
+ driver->securityDriver->domainRestoreSavedStateLabel(conn, vm, path) == -1)
|
||||
+ VIR_WARN("Unable to restore labelling on %s", path);
|
||||
+
|
||||
virDomainDefFree(def);
|
||||
VIR_FREE(xml);
|
||||
if (fd != -1)
|
||||
diff -rup libvirt-0.7.1/src/security.h new/src/security.h
|
||||
--- libvirt-0.7.1/src/security.h 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/security.h 2010-05-18 11:41:27.703746000 -0400
|
||||
@@ -44,7 +44,11 @@ typedef int (*virSecurityDomainSetHostde
|
||||
typedef int (*virSecurityDomainSetSavedStateLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
const char *savefile);
|
||||
+typedef int (*virSecurityDomainSetSavedStateLabelRO) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
+ const char *savefile);
|
||||
typedef int (*virSecurityDomainRestoreSavedStateLabel) (virConnectPtr conn,
|
||||
+ virDomainObjPtr vm,
|
||||
const char *savefile);
|
||||
typedef int (*virSecurityDomainGenLabel) (virConnectPtr conn,
|
||||
virDomainObjPtr sec);
|
||||
@@ -76,6 +80,7 @@ struct _virSecurityDriver {
|
||||
virSecurityDomainRestoreHostdevLabel domainRestoreSecurityHostdevLabel;
|
||||
virSecurityDomainSetHostdevLabel domainSetSecurityHostdevLabel;
|
||||
virSecurityDomainSetSavedStateLabel domainSetSavedStateLabel;
|
||||
+ virSecurityDomainSetSavedStateLabelRO domainSetSavedStateLabelRO;
|
||||
virSecurityDomainRestoreSavedStateLabel domainRestoreSavedStateLabel;
|
||||
|
||||
/*
|
||||
diff -rup libvirt-0.7.1/src/security_selinux.c new/src/security_selinux.c
|
||||
--- libvirt-0.7.1/src/security_selinux.c 2010-05-17 17:55:34.000000000 -0400
|
||||
+++ new/src/security_selinux.c 2010-05-18 11:49:24.542106000 -0400
|
||||
@@ -364,12 +364,20 @@ SELinuxRestoreSecurityFileLabel(virConne
|
||||
goto err;
|
||||
}
|
||||
|
||||
- if (stat(newpath, &buf) != 0)
|
||||
+ if (stat(newpath, &buf) != 0) {
|
||||
+ virReportSystemError(conn, err,
|
||||
+ _("cannot stat %s"), newpath);
|
||||
goto err;
|
||||
+ }
|
||||
|
||||
- if (matchpathcon(newpath, buf.st_mode, &fcon) == 0) {
|
||||
- rc = SELinuxSetFilecon(conn, newpath, fcon);
|
||||
+ if (matchpathcon(newpath, buf.st_mode, &fcon) != 0) {
|
||||
+ virReportSystemError(conn, err,
|
||||
+ _("failed to determine default context for %s"), newpath);
|
||||
+ goto err;
|
||||
}
|
||||
+
|
||||
+ rc = SELinuxSetFilecon(conn, newpath, fcon);
|
||||
+
|
||||
err:
|
||||
VIR_FREE(fcon);
|
||||
VIR_FREE(newpath);
|
||||
@@ -632,7 +640,17 @@ SELinuxSetSavedStateLabel(virConnectPtr
|
||||
|
||||
|
||||
static int
|
||||
+SELinuxSetSavedStateLabelRO(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm ATTRIBUTE_UNUSED,
|
||||
+ const char *savefile)
|
||||
+{
|
||||
+ return SELinuxSetFilecon(conn, savefile, default_content_context);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int
|
||||
SELinuxRestoreSavedStateLabel(virConnectPtr conn,
|
||||
+ virDomainObjPtr vm ATTRIBUTE_UNUSED,
|
||||
const char *savefile)
|
||||
{
|
||||
return SELinuxRestoreSecurityFileLabel(conn, savefile);
|
||||
@@ -709,5 +727,6 @@ virSecurityDriver virSELinuxSecurityDriv
|
||||
.domainSetSecurityHostdevLabel = SELinuxSetSecurityHostdevLabel,
|
||||
.domainRestoreSecurityHostdevLabel = SELinuxRestoreSecurityHostdevLabel,
|
||||
.domainSetSavedStateLabel = SELinuxSetSavedStateLabel,
|
||||
+ .domainSetSavedStateLabelRO = SELinuxSetSavedStateLabelRO,
|
||||
.domainRestoreSavedStateLabel = SELinuxRestoreSavedStateLabel,
|
||||
};
|
||||
@@ -1,22 +0,0 @@
|
||||
commit 823a684f8d0495bd5e7b413e1a81fd5a600abef7
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Thu Feb 11 14:39:13 2010 +0000
|
||||
|
||||
Fix USB device path formatting mixup
|
||||
|
||||
* src/util/hostusb.c: The device path for a USB device wants the
|
||||
bus/device IDs in decimal not octal
|
||||
|
||||
diff --git a/src/util/hostusb.c b/src/util/hostusb.c
|
||||
index 3cce66b..bf96539 100644
|
||||
--- a/src/hostusb.c
|
||||
+++ b/src/hostusb.c
|
||||
@@ -184,7 +184,7 @@ usbGetDevice(unsigned bus,
|
||||
snprintf(dev->name, sizeof(dev->name), "%.3o:%.3o",
|
||||
dev->bus, dev->dev);
|
||||
snprintf(dev->path, sizeof(dev->path),
|
||||
- USB_DEVFS "%03o/%03o", dev->bus, dev->dev);
|
||||
+ USB_DEVFS "%03d/%03d", dev->bus, dev->dev);
|
||||
|
||||
/* XXX fixme. this should be product/vendor */
|
||||
snprintf(dev->id, sizeof(dev->id), "%d %d", dev->bus, dev->dev);
|
||||
@@ -1,13 +0,0 @@
|
||||
Only in new: qemu_driver.c
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-06-03 13:51:14.392459000 -0400
|
||||
+++ new/src/hostusb.c 2010-06-03 14:49:11.763379000 -0400
|
||||
@@ -123,7 +123,7 @@ static int usbFindBusByVendor(virConnect
|
||||
char *tmpstr = de->d_name;
|
||||
unsigned found_bus, found_addr;
|
||||
|
||||
- if (STREQ(de->d_name, "usb"))
|
||||
+ if (STRPREFIX(de->d_name, "usb"))
|
||||
tmpstr += 3;
|
||||
|
||||
if (virStrToLong_ui(tmpstr, &ignore, 10, &found_bus) < 0) {
|
||||
@@ -1,496 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-05-17 16:53:48.740748000 -0400
|
||||
+++ new/src/hostusb.c 2010-05-17 16:57:19.294731000 -0400
|
||||
@@ -37,9 +37,10 @@
|
||||
#include "util.h"
|
||||
#include "virterror_internal.h"
|
||||
|
||||
+#define USB_SYSFS "/sys/bus/usb"
|
||||
#define USB_DEVFS "/dev/bus/usb/"
|
||||
-#define USB_ID_LEN 10 /* "XXXX XXXX" */
|
||||
-#define USB_ADDR_LEN 8 /* "XXX:XXX" */
|
||||
+#define USB_ID_LEN 10 /* "1234 5678" */
|
||||
+#define USB_ADDR_LEN 8 /* "123:456" */
|
||||
|
||||
struct _usbDevice {
|
||||
unsigned bus;
|
||||
@@ -57,6 +58,101 @@ struct _usbDevice {
|
||||
virReportErrorHelper(conn, VIR_FROM_NONE, code, __FILE__, \
|
||||
__FUNCTION__, __LINE__, fmt)
|
||||
|
||||
+static int usbSysReadFile(virConnectPtr conn,
|
||||
+ const char *f_name, const char *d_name,
|
||||
+ int base, unsigned *value)
|
||||
+{
|
||||
+ int ret = -1, tmp;
|
||||
+ char *buf = NULL;
|
||||
+ char *filename = NULL;
|
||||
+ char *ignore = NULL;
|
||||
+
|
||||
+ tmp = virAsprintf(&filename, USB_SYSFS "/devices/%s/%s", d_name, f_name);
|
||||
+ if (tmp < 0) {
|
||||
+ virReportOOMError(conn);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (virFileReadAll(filename, 1024, &buf) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (virStrToLong_ui(buf, &ignore, base, value) < 0) {
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Could not parse usb file %s"), filename);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ ret = 0;
|
||||
+error:
|
||||
+ VIR_FREE(filename);
|
||||
+ VIR_FREE(buf);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+static int usbFindBusByVendor(virConnectPtr conn,
|
||||
+ unsigned vendor, unsigned product,
|
||||
+ unsigned *bus, unsigned *devno)
|
||||
+{
|
||||
+ DIR *dir = NULL;
|
||||
+ int ret = -1, found = 0;
|
||||
+ char *ignore = NULL;
|
||||
+ struct dirent *de;
|
||||
+
|
||||
+ dir = opendir(USB_SYSFS "/devices");
|
||||
+ if (!dir) {
|
||||
+ virReportSystemError(conn, errno,
|
||||
+ _("Could not open directory %s"),
|
||||
+ USB_SYSFS "/devices");
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ while ((de = readdir(dir))) {
|
||||
+ unsigned found_prod, found_vend;
|
||||
+ if (de->d_name[0] == '.' || strchr(de->d_name, ':'))
|
||||
+ continue;
|
||||
+
|
||||
+ if (usbSysReadFile(conn, "idVendor", de->d_name,
|
||||
+ 16, &found_vend) < 0)
|
||||
+ goto error;
|
||||
+ if (usbSysReadFile(conn, "idProduct", de->d_name,
|
||||
+ 16, &found_prod) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ if (found_prod == product && found_vend == vendor) {
|
||||
+ /* Lookup bus.addr info */
|
||||
+ char *tmpstr = de->d_name;
|
||||
+ unsigned found_bus, found_addr;
|
||||
+
|
||||
+ if (STREQ(de->d_name, "usb"))
|
||||
+ tmpstr += 3;
|
||||
+
|
||||
+ if (virStrToLong_ui(tmpstr, &ignore, 10, &found_bus) < 0) {
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Failed to parse dir name '%s'"),
|
||||
+ de->d_name);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ if (usbSysReadFile(conn, "devnum", de->d_name,
|
||||
+ 10, &found_addr) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ *bus = found_bus;
|
||||
+ *devno = found_addr;
|
||||
+ found = 1;
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ if (!found)
|
||||
+ usbReportError(conn, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Did not find USB device %x:%x"), vendor, product);
|
||||
+ else
|
||||
+ ret = 0;
|
||||
+
|
||||
+error:
|
||||
+ return ret;
|
||||
+}
|
||||
|
||||
usbDevice *
|
||||
usbGetDevice(virConnectPtr conn,
|
||||
@@ -86,6 +182,21 @@ usbGetDevice(virConnectPtr conn,
|
||||
return dev;
|
||||
}
|
||||
|
||||
+
|
||||
+usbDevice *
|
||||
+usbFindDevice(unsigned vendor,
|
||||
+ unsigned product)
|
||||
+{
|
||||
+ unsigned bus = 0, devno = 0;
|
||||
+
|
||||
+ if (usbFindBusByVendor(vendor, product, &bus, &devno) < 0) {
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ return usbGetDevice(bus, devno);
|
||||
+}
|
||||
+
|
||||
+
|
||||
void
|
||||
usbFreeDevice(virConnectPtr conn ATTRIBUTE_UNUSED, usbDevice *dev)
|
||||
{
|
||||
@@ -93,6 +204,18 @@ usbFreeDevice(virConnectPtr conn ATTRIBU
|
||||
VIR_FREE(dev);
|
||||
}
|
||||
|
||||
+unsigned usbDeviceGetBus(usbDevice *dev)
|
||||
+{
|
||||
+ return dev->bus;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+unsigned usbDeviceGetDevno(usbDevice *dev)
|
||||
+{
|
||||
+ return dev->dev;
|
||||
+}
|
||||
+
|
||||
+
|
||||
|
||||
int usbDeviceFileIterate(virConnectPtr conn,
|
||||
usbDevice *dev,
|
||||
diff -rup libvirt-0.7.1/src/hostusb.h new/src/hostusb.h
|
||||
--- libvirt-0.7.1/src/hostusb.h 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ new/src/hostusb.h 2010-05-17 16:58:06.553924000 -0400
|
||||
@@ -27,11 +27,16 @@
|
||||
|
||||
typedef struct _usbDevice usbDevice;
|
||||
|
||||
-usbDevice *usbGetDevice (virConnectPtr conn,
|
||||
- unsigned bus,
|
||||
- unsigned devno);
|
||||
-void usbFreeDevice (virConnectPtr conn,
|
||||
- usbDevice *dev);
|
||||
+usbDevice *usbGetDevice(virConnectPtr conn,
|
||||
+ unsigned bus,
|
||||
+ unsigned devno);
|
||||
+usbDevice *usbFindDevice(virConnectPtr conn,
|
||||
+ unsigned vendor,
|
||||
+ unsigned product);
|
||||
+void usbFreeDevice (virConnectPtr conn, usbDevice *dev);
|
||||
+
|
||||
+unsigned usbDeviceGetBus(usbDevice *dev);
|
||||
+unsigned usbDeviceGetDevno(usbDevice *dev);
|
||||
|
||||
/*
|
||||
* Callback that will be invoked once for each file
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms new/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-05-17 16:53:48.401831000 -0400
|
||||
+++ new/src/libvirt_private.syms 2010-05-17 16:55:03.001748000 -0400
|
||||
@@ -441,7 +441,10 @@ virFileMatchesNameSuffix;
|
||||
|
||||
# usb.h
|
||||
usbGetDevice;
|
||||
+usbFindDevice;
|
||||
usbFreeDevice;
|
||||
+usbDeviceGetBus;
|
||||
+usbDeviceGetDevno;
|
||||
usbDeviceFileIterate;
|
||||
|
||||
# uuid.h
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 16:53:48.785743000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 17:06:40.575145000 -0400
|
||||
@@ -1493,16 +1493,13 @@ qemuUpdateActivePciHostdevs(struct qemud
|
||||
}
|
||||
|
||||
static int
|
||||
-qemuPrepareHostDevices(virConnectPtr conn,
|
||||
- struct qemud_driver *driver,
|
||||
- virDomainDefPtr def)
|
||||
+qemuPrepareHostPCIDevices(virConnectPtr conn,
|
||||
+ struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
{
|
||||
pciDeviceList *pcidevs;
|
||||
int i;
|
||||
|
||||
- if (!def->nhostdevs)
|
||||
- return 0;
|
||||
-
|
||||
if (!(pcidevs = qemuGetPciHostDeviceList(conn, def)))
|
||||
return -1;
|
||||
|
||||
@@ -1792,14 +1789,11 @@ static int qemuDomainSetHostdevUSBOwners
|
||||
struct qemuFileOwner owner = { uid, gid };
|
||||
int ret = -1;
|
||||
|
||||
- /* XXX what todo for USB devs assigned based on product/vendor ? Doom :-( */
|
||||
- if (!def->source.subsys.u.usb.bus ||
|
||||
- !def->source.subsys.u.usb.device)
|
||||
- return 0;
|
||||
-
|
||||
usbDevice *dev = usbGetDevice(conn,
|
||||
def->source.subsys.u.usb.bus,
|
||||
- def->source.subsys.u.usb.device);
|
||||
+ def->source.subsys.u.usb.device,
|
||||
+ def->source.subsys.u.usb.vendor,
|
||||
+ def->source.subsys.u.usb.product);
|
||||
|
||||
if (!dev)
|
||||
goto cleanup;
|
||||
@@ -2065,13 +2059,17 @@ static int qemudStartVMDaemon(virConnect
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ DEBUG0("Preparing host devices");
|
||||
+ if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
+ goto cleanup;
|
||||
+
|
||||
/* If you are using a SecurityDriver with dynamic labelling,
|
||||
then generate a security label for isolation */
|
||||
if (vm->def->seclabel.type == VIR_DOMAIN_SECLABEL_DYNAMIC &&
|
||||
driver->securityDriver &&
|
||||
driver->securityDriver->domainGenSecurityLabel &&
|
||||
driver->securityDriver->domainGenSecurityLabel(conn, vm) < 0)
|
||||
- return -1;
|
||||
+ return cleanup;
|
||||
|
||||
/* Ensure no historical cgroup for this VM is lieing around bogus settings */
|
||||
qemuRemoveCgroup(conn, driver, vm);
|
||||
@@ -2119,9 +2117,6 @@ static int qemudStartVMDaemon(virConnect
|
||||
if (qemuSetupCgroup(conn, driver, vm) < 0)
|
||||
goto cleanup;
|
||||
|
||||
- if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
- goto cleanup;
|
||||
-
|
||||
if (VIR_ALLOC(vm->monitor_chr) < 0) {
|
||||
virReportOOMError(conn);
|
||||
goto cleanup;
|
||||
@@ -2348,6 +2343,56 @@ retry:
|
||||
}
|
||||
|
||||
|
||||
+
|
||||
+static int
|
||||
+qemuPrepareHostUSBDevices(struct qemud_driver *driver ATTRIBUTE_UNUSED,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ int i;
|
||||
+ for (i = 0 ; i < def->nhostdevs ; i++) {
|
||||
+ virDomainHostdevDefPtr hostdev = def->hostdevs[i];
|
||||
+
|
||||
+ if (hostdev->mode != VIR_DOMAIN_HOSTDEV_MODE_SUBSYS)
|
||||
+ continue;
|
||||
+ if (hostdev->source.subsys.type != VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB)
|
||||
+ continue;
|
||||
+
|
||||
+ /* Resolve a vendor/product to bus/device */
|
||||
+ if (hostdev->source.subsys.u.usb.vendor) {
|
||||
+ usbDevice *usb
|
||||
+ = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ hostdev->source.subsys.u.usb.product);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ return -1;
|
||||
+
|
||||
+ hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
+ hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
+
|
||||
+ usbFreeDevice(usb);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int
|
||||
+qemuPrepareHostDevices(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def)
|
||||
+{
|
||||
+ if (!def->nhostdevs)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (qemuPrepareHostPCIDevices(driver, def) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ if (qemuPrepareHostUSBDevices(driver, def) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+
|
||||
static void
|
||||
qemudDispatchVMEvent(int watch, int fd, int events, void *opaque) {
|
||||
struct qemud_driver *driver = opaque;
|
||||
@@ -6294,6 +6339,23 @@ static int qemudDomainDetachHostDevice(v
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ /* Resolve USB product/vendor to bus/device */
|
||||
+ if (hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB &&
|
||||
+ hostdev->source.subsys.u.usb.vendor) {
|
||||
+ usbDevice *usb
|
||||
+ = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ hostdev->source.subsys.u.usb.product);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ return -1;
|
||||
+
|
||||
+ hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
+ hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
+
|
||||
+ usbFreeDevice(usb);
|
||||
+ }
|
||||
+
|
||||
+
|
||||
if (driver->securityDriver &&
|
||||
driver->securityDriver->domainSetSecurityHostdevLabel(conn, vm, dev->data.hostdev) < 0)
|
||||
VIR_WARN0("Failed to restore device labelling");
|
||||
diff -rup libvirt-0.7.1/src/security_selinux.c new/src/security_selinux.c
|
||||
--- libvirt-0.7.1/src/security_selinux.c 2010-05-17 16:53:48.775745000 -0400
|
||||
+++ new/src/security_selinux.c 2010-05-17 16:58:47.442604000 -0400
|
||||
@@ -482,20 +482,15 @@ SELinuxSetSecurityHostdevLabel(virConnec
|
||||
|
||||
switch (dev->source.subsys.type) {
|
||||
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB: {
|
||||
- if (dev->source.subsys.u.usb.bus && dev->source.subsys.u.usb.device) {
|
||||
- usbDevice *usb = usbGetDevice(conn,
|
||||
- dev->source.subsys.u.usb.bus,
|
||||
- dev->source.subsys.u.usb.device);
|
||||
-
|
||||
- if (!usb)
|
||||
- goto done;
|
||||
-
|
||||
- ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
- usbFreeDevice(conn, usb);
|
||||
- } else {
|
||||
- /* XXX deal with product/vendor better */
|
||||
- ret = 0;
|
||||
- }
|
||||
+ usbDevice *usb = usbGetDevice(conn,
|
||||
+ dev->source.subsys.u.usb.bus,
|
||||
+ dev->source.subsys.u.usb.device);
|
||||
+
|
||||
+ if (!usb)
|
||||
+ goto done;
|
||||
+
|
||||
+ ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
+ usbFreeDevice(conn, usb);
|
||||
break;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/hostusb.c new/src/hostusb.c
|
||||
--- libvirt-0.7.1/src/hostusb.c 2010-05-17 17:09:02.573638000 -0400
|
||||
+++ new/src/hostusb.c 2010-05-17 17:29:49.133509000 -0400
|
||||
@@ -184,16 +184,17 @@ usbGetDevice(virConnectPtr conn,
|
||||
|
||||
|
||||
usbDevice *
|
||||
-usbFindDevice(unsigned vendor,
|
||||
+usbFindDevice(virConnectPtr conn,
|
||||
+ unsigned vendor,
|
||||
unsigned product)
|
||||
{
|
||||
unsigned bus = 0, devno = 0;
|
||||
|
||||
- if (usbFindBusByVendor(vendor, product, &bus, &devno) < 0) {
|
||||
+ if (usbFindBusByVendor(conn, vendor, product, &bus, &devno) < 0) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- return usbGetDevice(bus, devno);
|
||||
+ return usbGetDevice(conn, bus, devno);
|
||||
}
|
||||
|
||||
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-05-17 17:09:02.602638000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-05-17 17:36:10.066214000 -0400
|
||||
@@ -1791,9 +1791,7 @@ static int qemuDomainSetHostdevUSBOwners
|
||||
|
||||
usbDevice *dev = usbGetDevice(conn,
|
||||
def->source.subsys.u.usb.bus,
|
||||
- def->source.subsys.u.usb.device,
|
||||
- def->source.subsys.u.usb.vendor,
|
||||
- def->source.subsys.u.usb.product);
|
||||
+ def->source.subsys.u.usb.device);
|
||||
|
||||
if (!dev)
|
||||
goto cleanup;
|
||||
@@ -2026,6 +2024,10 @@ qemuPrepareMonitorChr(virConnectPtr conn
|
||||
return 0;
|
||||
}
|
||||
|
||||
+static int
|
||||
+qemuPrepareHostDevices(struct qemud_driver *driver,
|
||||
+ virDomainDefPtr def);
|
||||
+
|
||||
static int qemudStartVMDaemon(virConnectPtr conn,
|
||||
struct qemud_driver *driver,
|
||||
virDomainObjPtr vm,
|
||||
@@ -2060,7 +2062,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
}
|
||||
|
||||
DEBUG0("Preparing host devices");
|
||||
- if (qemuPrepareHostDevices(conn, driver, vm->def) < 0)
|
||||
+ if (qemuPrepareHostDevices(driver, vm->def) < 0)
|
||||
goto cleanup;
|
||||
|
||||
/* If you are using a SecurityDriver with dynamic labelling,
|
||||
@@ -2069,7 +2071,7 @@ static int qemudStartVMDaemon(virConnect
|
||||
driver->securityDriver &&
|
||||
driver->securityDriver->domainGenSecurityLabel &&
|
||||
driver->securityDriver->domainGenSecurityLabel(conn, vm) < 0)
|
||||
- return cleanup;
|
||||
+ goto cleanup;
|
||||
|
||||
/* Ensure no historical cgroup for this VM is lieing around bogus settings */
|
||||
qemuRemoveCgroup(conn, driver, vm);
|
||||
@@ -2360,7 +2362,8 @@ qemuPrepareHostUSBDevices(struct qemud_d
|
||||
/* Resolve a vendor/product to bus/device */
|
||||
if (hostdev->source.subsys.u.usb.vendor) {
|
||||
usbDevice *usb
|
||||
- = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ = usbFindDevice(NULL,
|
||||
+ hostdev->source.subsys.u.usb.vendor,
|
||||
hostdev->source.subsys.u.usb.product);
|
||||
|
||||
if (!usb)
|
||||
@@ -2369,7 +2372,7 @@ qemuPrepareHostUSBDevices(struct qemud_d
|
||||
hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
|
||||
- usbFreeDevice(usb);
|
||||
+ usbFreeDevice(NULL, usb);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2383,7 +2386,7 @@ qemuPrepareHostDevices(struct qemud_driv
|
||||
if (!def->nhostdevs)
|
||||
return 0;
|
||||
|
||||
- if (qemuPrepareHostPCIDevices(driver, def) < 0)
|
||||
+ if (qemuPrepareHostPCIDevices(NULL, driver, def) < 0)
|
||||
return -1;
|
||||
|
||||
if (qemuPrepareHostUSBDevices(driver, def) < 0)
|
||||
@@ -6343,7 +6346,8 @@ static int qemudDomainDetachHostDevice(v
|
||||
if (hostdev->source.subsys.type == VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_USB &&
|
||||
hostdev->source.subsys.u.usb.vendor) {
|
||||
usbDevice *usb
|
||||
- = usbFindDevice(hostdev->source.subsys.u.usb.vendor,
|
||||
+ = usbFindDevice(NULL,
|
||||
+ hostdev->source.subsys.u.usb.vendor,
|
||||
hostdev->source.subsys.u.usb.product);
|
||||
|
||||
if (!usb)
|
||||
@@ -6352,7 +6356,7 @@ static int qemudDomainDetachHostDevice(v
|
||||
hostdev->source.subsys.u.usb.bus = usbDeviceGetBus(usb);
|
||||
hostdev->source.subsys.u.usb.device = usbDeviceGetDevno(usb);
|
||||
|
||||
- usbFreeDevice(usb);
|
||||
+ usbFreeDevice(NULL, usb);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,686 +0,0 @@
|
||||
commit 33a198c1f6a4a1bc7f34d50a31032e03bec10fee
|
||||
Author: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Fri Jul 17 20:20:08 2009 +0100
|
||||
|
||||
Initialize gcrypt threading
|
||||
|
||||
GNUTLS uses gcrypt for its crypto functions. gcrypt requires
|
||||
that the app/library initializes threading before using it.
|
||||
We don't want to force apps using libvirt to know about
|
||||
gcrypt, so we make virInitialize init threading on their
|
||||
behalf. This location also ensures libvirtd has initialized
|
||||
it correctly. This initialization is required even if libvirt
|
||||
itself were only using one thread, since another non-libvirt
|
||||
library (eg GTK-VNC) could also be using gcrypt from another
|
||||
thread
|
||||
|
||||
* src/libvirt.c: Register thread functions for gcrypt
|
||||
* configure.in: Add -lgcrypt to linker flags
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 103b331..cad33c2 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -22,6 +22,7 @@
|
||||
#include <sys/wait.h>
|
||||
#endif
|
||||
#include <time.h>
|
||||
+#include <gcrypt.h>
|
||||
|
||||
#include <libxml/parser.h>
|
||||
#include <libxml/xpath.h>
|
||||
@@ -251,6 +252,55 @@ winsock_init (void)
|
||||
}
|
||||
#endif
|
||||
|
||||
+static int virTLSMutexInit (void **priv)
|
||||
+{ \
|
||||
+ virMutexPtr lock = NULL;
|
||||
+
|
||||
+ if (VIR_ALLOC(lock) < 0)
|
||||
+ return ENOMEM;
|
||||
+
|
||||
+ if (virMutexInit(lock) < 0) {
|
||||
+ VIR_FREE(lock);
|
||||
+ return errno;
|
||||
+ }
|
||||
+
|
||||
+ *priv = lock;
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexDestroy(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexDestroy(lock);
|
||||
+ VIR_FREE(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexLock(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexLock(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int virTLSMutexUnlock(void **priv)
|
||||
+{
|
||||
+ virMutexPtr lock = *priv;
|
||||
+ virMutexUnlock(lock);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static struct gcry_thread_cbs virTLSThreadImpl = {
|
||||
+ (GCRY_THREAD_OPTION_PTHREAD | (GCRY_THREAD_OPTION_VERSION << 8)),
|
||||
+ NULL,
|
||||
+ virTLSMutexInit,
|
||||
+ virTLSMutexDestroy,
|
||||
+ virTLSMutexLock,
|
||||
+ virTLSMutexUnlock,
|
||||
+ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
|
||||
+};
|
||||
+
|
||||
+
|
||||
/**
|
||||
* virInitialize:
|
||||
*
|
||||
@@ -273,6 +323,9 @@ virInitialize(void)
|
||||
virRandomInitialize(time(NULL) ^ getpid()))
|
||||
return -1;
|
||||
|
||||
+ gcry_control(GCRYCTL_SET_THREAD_CBS, &virTLSThreadImpl);
|
||||
+ gcry_check_version(NULL);
|
||||
+
|
||||
virLogSetFromEnv();
|
||||
|
||||
DEBUG0("register drivers");
|
||||
commit 1c5c63338c90f6e82731f6871901dc72732033ef
|
||||
Author: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Fri Dec 18 12:02:07 2009 +0100
|
||||
|
||||
Fix compilation with gcrypt < 1.4.2
|
||||
|
||||
Commit 33a198c1f6a4a1bc7f34d50a31032e03bec10fee increased the gcrypt
|
||||
version requirement to 1.4.2 because the GCRY_THREAD_OPTION_VERSION
|
||||
define was added in this version.
|
||||
|
||||
The configure script doesn't check for the gcrypt version. To support
|
||||
gcrypt versions < 1.4.2 change the virTLSThreadImpl initialization
|
||||
to use GCRY_THREAD_OPTION_VERSION only if it's defined.
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 5167bc2..16c851f 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -291,7 +291,12 @@ static int virTLSMutexUnlock(void **priv)
|
||||
}
|
||||
|
||||
static struct gcry_thread_cbs virTLSThreadImpl = {
|
||||
+ /* GCRY_THREAD_OPTION_VERSION was added in gcrypt 1.4.2 */
|
||||
+#ifdef GCRY_THREAD_OPTION_VERSION
|
||||
(GCRY_THREAD_OPTION_PTHREAD | (GCRY_THREAD_OPTION_VERSION << 8)),
|
||||
+#else
|
||||
+ GCRY_THREAD_OPTION_PTHREAD,
|
||||
+#endif
|
||||
NULL,
|
||||
virTLSMutexInit,
|
||||
virTLSMutexDestroy,
|
||||
diff -rup libvirt-0.7.1/aclocal.m4 gcrypt-new/aclocal.m4
|
||||
--- libvirt-0.7.1/aclocal.m4 2009-09-15 08:35:04.000000000 -0400
|
||||
+++ gcrypt-new/aclocal.m4 2010-05-17 17:52:13.765215000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# generated automatically by aclocal 1.11 -*- Autoconf -*-
|
||||
+# generated automatically by aclocal 1.11.1 -*- Autoconf -*-
|
||||
|
||||
# Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
|
||||
# 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc.
|
||||
@@ -190,7 +190,7 @@ AC_DEFUN([AM_AUTOMAKE_VERSION],
|
||||
[am__api_version='1.11'
|
||||
dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
|
||||
dnl require some minimum version. Point them to the right macro.
|
||||
-m4_if([$1], [1.11], [],
|
||||
+m4_if([$1], [1.11.1], [],
|
||||
[AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
|
||||
])
|
||||
|
||||
@@ -206,7 +206,7 @@ m4_define([_AM_AUTOCONF_VERSION], [])
|
||||
# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
|
||||
# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
|
||||
AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
|
||||
-[AM_AUTOMAKE_VERSION([1.11])dnl
|
||||
+[AM_AUTOMAKE_VERSION([1.11.1])dnl
|
||||
m4_ifndef([AC_AUTOCONF_VERSION],
|
||||
[m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
|
||||
_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
|
||||
diff -rup libvirt-0.7.1/configure gcrypt-new/configure
|
||||
--- libvirt-0.7.1/configure 2009-09-15 08:35:09.000000000 -0400
|
||||
+++ gcrypt-new/configure 2010-05-17 17:52:18.706838000 -0400
|
||||
@@ -43324,7 +43324,7 @@ fi
|
||||
$as_echo "$as_me: error: You must install the GnuTLS library in order to compile and run libvirt" >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
|
||||
- GNUTLS_LIBS=$LIBS
|
||||
+ GNUTLS_LIBS="$LIBS -lgcrypt"
|
||||
LIBS="$old_libs"
|
||||
fi
|
||||
|
||||
diff -rup libvirt-0.7.1/docs/devhelp/Makefile.in gcrypt-new/docs/devhelp/Makefile.in
|
||||
--- libvirt-0.7.1/docs/devhelp/Makefile.in 2009-09-15 08:35:13.000000000 -0400
|
||||
+++ gcrypt-new/docs/devhelp/Makefile.in 2010-05-17 17:52:23.305455000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/docs/examples/Makefile.in gcrypt-new/docs/examples/Makefile.in
|
||||
--- libvirt-0.7.1/docs/examples/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/examples/Makefile.in 2010-05-17 17:52:23.492454000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -999,7 +999,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1024,7 +1024,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/docs/examples/python/Makefile.in gcrypt-new/docs/examples/python/Makefile.in
|
||||
--- libvirt-0.7.1/docs/examples/python/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/examples/python/Makefile.in 2010-05-17 17:52:23.650454000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/docs/Makefile.in gcrypt-new/docs/Makefile.in
|
||||
--- libvirt-0.7.1/docs/Makefile.in 2009-09-15 08:35:13.000000000 -0400
|
||||
+++ gcrypt-new/docs/Makefile.in 2010-05-17 17:52:23.143456000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -966,7 +966,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -991,7 +991,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/docs/schemas/Makefile.in gcrypt-new/docs/schemas/Makefile.in
|
||||
--- libvirt-0.7.1/docs/schemas/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/docs/schemas/Makefile.in 2010-05-17 17:52:23.807456000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/examples/domain-events/events-c/Makefile.in gcrypt-new/examples/domain-events/events-c/Makefile.in
|
||||
--- libvirt-0.7.1/examples/domain-events/events-c/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/examples/domain-events/events-c/Makefile.in 2010-05-17 17:52:23.983380000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/examples/hellolibvirt/Makefile.in gcrypt-new/examples/hellolibvirt/Makefile.in
|
||||
--- libvirt-0.7.1/examples/hellolibvirt/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/examples/hellolibvirt/Makefile.in 2010-05-17 17:52:24.166378000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/gnulib/lib/Makefile.in gcrypt-new/gnulib/lib/Makefile.in
|
||||
--- libvirt-0.7.1/gnulib/lib/Makefile.in 2009-09-15 08:35:14.000000000 -0400
|
||||
+++ gcrypt-new/gnulib/lib/Makefile.in 2010-05-17 17:52:24.409381000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1128,7 +1128,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1153,7 +1153,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/gnulib/tests/Makefile.in gcrypt-new/gnulib/tests/Makefile.in
|
||||
--- libvirt-0.7.1/gnulib/tests/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/gnulib/tests/Makefile.in 2010-05-17 17:52:24.719382000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1501,7 +1501,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1526,7 +1526,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/include/libvirt/Makefile.in gcrypt-new/include/libvirt/Makefile.in
|
||||
--- libvirt-0.7.1/include/libvirt/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/include/libvirt/Makefile.in 2010-05-17 17:52:25.069302000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/include/Makefile.in gcrypt-new/include/Makefile.in
|
||||
--- libvirt-0.7.1/include/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/include/Makefile.in 2010-05-17 17:52:24.902313000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -896,7 +896,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -921,7 +921,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/Makefile.in gcrypt-new/Makefile.in
|
||||
--- libvirt-0.7.1/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/Makefile.in 2010-05-17 17:52:28.423082000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1060,7 +1060,7 @@ uninstall-pkgconfigDATA:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1085,7 +1085,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1265,7 +1265,8 @@ distdir: $(DISTFILES)
|
||||
top_distdir="$(top_distdir)" distdir="$(distdir)" \
|
||||
dist-hook
|
||||
-test -n "$(am__skip_mode_fix)" \
|
||||
- || find "$(distdir)" -type d ! -perm -777 -exec chmod a+rwx {} \; -o \
|
||||
+ || find "$(distdir)" -type d ! -perm -755 \
|
||||
+ -exec chmod u+rwx,go+rx {} \; -o \
|
||||
! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \
|
||||
! -type d ! -perm -400 -exec chmod a+r {} \; -o \
|
||||
! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \
|
||||
@@ -1309,17 +1310,17 @@ dist dist-all: distdir
|
||||
distcheck: dist
|
||||
case '$(DIST_ARCHIVES)' in \
|
||||
*.tar.gz*) \
|
||||
- GZIP=$(GZIP_ENV) gunzip -c $(distdir).tar.gz | $(am__untar) ;;\
|
||||
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
|
||||
*.tar.bz2*) \
|
||||
- bunzip2 -c $(distdir).tar.bz2 | $(am__untar) ;;\
|
||||
+ bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
|
||||
*.tar.lzma*) \
|
||||
- unlzma -c $(distdir).tar.lzma | $(am__untar) ;;\
|
||||
+ lzma -dc $(distdir).tar.lzma | $(am__untar) ;;\
|
||||
*.tar.xz*) \
|
||||
xz -dc $(distdir).tar.xz | $(am__untar) ;;\
|
||||
*.tar.Z*) \
|
||||
uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
|
||||
*.shar.gz*) \
|
||||
- GZIP=$(GZIP_ENV) gunzip -c $(distdir).shar.gz | unshar ;;\
|
||||
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\
|
||||
*.zip*) \
|
||||
unzip $(distdir).zip ;;\
|
||||
esac
|
||||
diff -rup libvirt-0.7.1/proxy/Makefile.in gcrypt-new/proxy/Makefile.in
|
||||
--- libvirt-0.7.1/proxy/Makefile.in 2009-09-15 08:35:15.000000000 -0400
|
||||
+++ gcrypt-new/proxy/Makefile.in 2010-05-17 17:52:25.334306000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/python/Makefile.in gcrypt-new/python/Makefile.in
|
||||
--- libvirt-0.7.1/python/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/python/Makefile.in 2010-05-17 17:52:25.538302000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1090,7 +1090,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1115,7 +1115,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/python/tests/Makefile.in gcrypt-new/python/tests/Makefile.in
|
||||
--- libvirt-0.7.1/python/tests/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/python/tests/Makefile.in 2010-05-17 17:52:25.702304000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/qemud/Makefile.in gcrypt-new/qemud/Makefile.in
|
||||
--- libvirt-0.7.1/qemud/Makefile.in 2009-09-15 08:35:16.000000000 -0400
|
||||
+++ gcrypt-new/qemud/Makefile.in 2010-05-17 17:52:25.997229000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1522,7 +1522,7 @@ remote_protocol.c: remote_protocol.h
|
||||
@WITH_LIBVIRTD_TRUE@ test -e $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml || \
|
||||
@WITH_LIBVIRTD_TRUE@ ln -s ../default.xml \
|
||||
@WITH_LIBVIRTD_TRUE@ $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
-@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/run/libvirt
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/lib/libvirt
|
||||
|
||||
@@ -1530,7 +1530,7 @@ remote_protocol.c: remote_protocol.h
|
||||
@WITH_LIBVIRTD_TRUE@ rm -f $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
@WITH_LIBVIRTD_TRUE@ rm -f $(DESTDIR)$(sysconfdir)/$(default_xml_dest)
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart || :
|
||||
-@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/log/libvirt/qemu || :
|
||||
+@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/log/libvirt || :
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/run/libvirt || :
|
||||
@WITH_LIBVIRTD_TRUE@ rmdir $(DESTDIR)$(localstatedir)/lib/libvirt || :
|
||||
|
||||
@@ -1577,6 +1577,8 @@ remote_protocol.c: remote_protocol.h
|
||||
|
||||
@WITH_LIBVIRTD_TRUE@install-logrotate: libvirtd.logrotate
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu/
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/lxc/
|
||||
+@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/uml/
|
||||
@WITH_LIBVIRTD_TRUE@ mkdir -p $(DESTDIR)$(sysconfdir)/logrotate.d/
|
||||
@WITH_LIBVIRTD_TRUE@ $(INSTALL_DATA) $< $(DESTDIR)$(sysconfdir)/logrotate.d/libvirtd
|
||||
|
||||
diff -rup libvirt-0.7.1/src/Makefile.in gcrypt-new/src/Makefile.in
|
||||
--- libvirt-0.7.1/src/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/src/Makefile.in 2010-05-17 17:52:26.929151000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -598,9 +598,9 @@ am__objects_45 = libvirt_util_la-bridge.
|
||||
libvirt_util_la-pci.lo libvirt_util_la-hostusb.lo \
|
||||
libvirt_util_la-qparams.lo \
|
||||
libvirt_util_la-storage_encryption_conf.lo \
|
||||
- libvirt_util_la-threads.lo libvirt_util_la-uuid.lo \
|
||||
- libvirt_util_la-util.lo libvirt_util_la-virterror.lo \
|
||||
- libvirt_util_la-xml.lo
|
||||
+ libvirt_util_la-storage_file.lo libvirt_util_la-threads.lo \
|
||||
+ libvirt_util_la-uuid.lo libvirt_util_la-util.lo \
|
||||
+ libvirt_util_la-virterror.lo libvirt_util_la-xml.lo
|
||||
am_libvirt_util_la_OBJECTS = $(am__objects_45)
|
||||
libvirt_util_la_OBJECTS = $(am_libvirt_util_la_OBJECTS)
|
||||
libvirt_util_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \
|
||||
@@ -617,11 +617,11 @@ am__libvirt_lxc_SOURCES_DIST = lxc_conf.
|
||||
event.h hash.c hash.h iptables.c iptables.h logging.c \
|
||||
logging.h memory.c memory.h pci.c pci.h hostusb.c hostusb.h \
|
||||
qparams.c qparams.h storage_encryption_conf.h \
|
||||
- storage_encryption_conf.c threads.c threads.h \
|
||||
- threads-pthread.h threads-win32.h uuid.c uuid.h util.c util.h \
|
||||
- virterror.c virterror_internal.h xml.c xml.h capabilities.c \
|
||||
- capabilities.h domain_conf.c domain_conf.h nodeinfo.h \
|
||||
- nodeinfo.c
|
||||
+ storage_encryption_conf.c storage_file.c storage_file.h \
|
||||
+ threads.c threads.h threads-pthread.h threads-win32.h uuid.c \
|
||||
+ uuid.h util.c util.h virterror.c virterror_internal.h xml.c \
|
||||
+ xml.h capabilities.c capabilities.h domain_conf.c \
|
||||
+ domain_conf.h nodeinfo.h nodeinfo.c
|
||||
am__objects_46 = libvirt_lxc-lxc_conf.$(OBJEXT) \
|
||||
libvirt_lxc-lxc_container.$(OBJEXT) \
|
||||
libvirt_lxc-lxc_controller.$(OBJEXT) \
|
||||
@@ -633,6 +633,7 @@ am__objects_47 = libvirt_lxc-bridge.$(OB
|
||||
libvirt_lxc-memory.$(OBJEXT) libvirt_lxc-pci.$(OBJEXT) \
|
||||
libvirt_lxc-hostusb.$(OBJEXT) libvirt_lxc-qparams.$(OBJEXT) \
|
||||
libvirt_lxc-storage_encryption_conf.$(OBJEXT) \
|
||||
+ libvirt_lxc-storage_file.$(OBJEXT) \
|
||||
libvirt_lxc-threads.$(OBJEXT) libvirt_lxc-uuid.$(OBJEXT) \
|
||||
libvirt_lxc-util.$(OBJEXT) libvirt_lxc-virterror.$(OBJEXT) \
|
||||
libvirt_lxc-xml.$(OBJEXT)
|
||||
@@ -1485,6 +1486,7 @@ UTIL_SOURCES = \
|
||||
hostusb.c hostusb.h \
|
||||
qparams.c qparams.h \
|
||||
storage_encryption_conf.h storage_encryption_conf.c \
|
||||
+ storage_file.c storage_file.h \
|
||||
threads.c threads.h \
|
||||
threads-pthread.h \
|
||||
threads-win32.h \
|
||||
@@ -2151,6 +2153,7 @@ distclean-compile:
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-pci.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-qparams.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-storage_encryption_conf.Po@am__quote@
|
||||
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-storage_file.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-threads.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-util.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_lxc-uuid.Po@am__quote@
|
||||
@@ -2170,6 +2173,7 @@ distclean-compile:
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-pci.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-qparams.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-storage_encryption_conf.Plo@am__quote@
|
||||
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-storage_file.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-threads.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-util.Plo@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libvirt_util_la-uuid.Plo@am__quote@
|
||||
@@ -2753,6 +2757,14 @@ libvirt_util_la-storage_encryption_conf.
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -c -o libvirt_util_la-storage_encryption_conf.lo `test -f 'storage_encryption_conf.c' || echo '$(srcdir)/'`storage_encryption_conf.c
|
||||
|
||||
+libvirt_util_la-storage_file.lo: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -MT libvirt_util_la-storage_file.lo -MD -MP -MF $(DEPDIR)/libvirt_util_la-storage_file.Tpo -c -o libvirt_util_la-storage_file.lo `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_util_la-storage_file.Tpo $(DEPDIR)/libvirt_util_la-storage_file.Plo
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_util_la-storage_file.lo' libtool=yes @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -c -o libvirt_util_la-storage_file.lo `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+
|
||||
libvirt_util_la-threads.lo: threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_util_la_CFLAGS) $(CFLAGS) -MT libvirt_util_la-threads.lo -MD -MP -MF $(DEPDIR)/libvirt_util_la-threads.Tpo -c -o libvirt_util_la-threads.lo `test -f 'threads.c' || echo '$(srcdir)/'`threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_util_la-threads.Tpo $(DEPDIR)/libvirt_util_la-threads.Plo
|
||||
@@ -3065,6 +3077,22 @@ libvirt_lxc-storage_encryption_conf.obj:
|
||||
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_encryption_conf.obj `if test -f 'storage_encryption_conf.c'; then $(CYGPATH_W) 'storage_encryption_conf.c'; else $(CYGPATH_W) '$(srcdir)/storage_encryption_conf.c'; fi`
|
||||
|
||||
+libvirt_lxc-storage_file.o: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-storage_file.o -MD -MP -MF $(DEPDIR)/libvirt_lxc-storage_file.Tpo -c -o libvirt_lxc-storage_file.o `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-storage_file.Tpo $(DEPDIR)/libvirt_lxc-storage_file.Po
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_lxc-storage_file.o' libtool=no @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_file.o `test -f 'storage_file.c' || echo '$(srcdir)/'`storage_file.c
|
||||
+
|
||||
+libvirt_lxc-storage_file.obj: storage_file.c
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-storage_file.obj -MD -MP -MF $(DEPDIR)/libvirt_lxc-storage_file.Tpo -c -o libvirt_lxc-storage_file.obj `if test -f 'storage_file.c'; then $(CYGPATH_W) 'storage_file.c'; else $(CYGPATH_W) '$(srcdir)/storage_file.c'; fi`
|
||||
+@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-storage_file.Tpo $(DEPDIR)/libvirt_lxc-storage_file.Po
|
||||
+@am__fastdepCC_FALSE@ $(AM_V_CC) @AM_BACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='storage_file.c' object='libvirt_lxc-storage_file.obj' libtool=no @AMDEPBACKSLASH@
|
||||
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
|
||||
+@am__fastdepCC_FALSE@ $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -c -o libvirt_lxc-storage_file.obj `if test -f 'storage_file.c'; then $(CYGPATH_W) 'storage_file.c'; else $(CYGPATH_W) '$(srcdir)/storage_file.c'; fi`
|
||||
+
|
||||
libvirt_lxc-threads.o: threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libvirt_lxc_CFLAGS) $(CFLAGS) -MT libvirt_lxc-threads.o -MD -MP -MF $(DEPDIR)/libvirt_lxc-threads.Tpo -c -o libvirt_lxc-threads.o `test -f 'threads.c' || echo '$(srcdir)/'`threads.c
|
||||
@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/libvirt_lxc-threads.Tpo $(DEPDIR)/libvirt_lxc-threads.Po
|
||||
diff -rup libvirt-0.7.1/tests/confdata/Makefile.in gcrypt-new/tests/confdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/confdata/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/confdata/Makefile.in 2010-05-17 17:52:27.383154000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/Makefile.in gcrypt-new/tests/Makefile.in
|
||||
--- libvirt-0.7.1/tests/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/Makefile.in 2010-05-17 17:52:27.223153000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1401,7 +1401,7 @@ clean-libtool:
|
||||
# (which will cause the Makefiles to be regenerated when you run `make');
|
||||
# (2) otherwise, pass the desired values on the `make' command line.
|
||||
$(RECURSIVE_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
@@ -1426,7 +1426,7 @@ $(RECURSIVE_TARGETS):
|
||||
fi; test -z "$$fail"
|
||||
|
||||
$(RECURSIVE_CLEAN_TARGETS):
|
||||
- @failcom='exit 1'; \
|
||||
+ @fail= failcom='exit 1'; \
|
||||
for f in x $$MAKEFLAGS; do \
|
||||
case $$f in \
|
||||
*=* | --[!k]*);; \
|
||||
diff -rup libvirt-0.7.1/tests/sexpr2xmldata/Makefile.in gcrypt-new/tests/sexpr2xmldata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/sexpr2xmldata/Makefile.in 2009-09-15 08:35:17.000000000 -0400
|
||||
+++ gcrypt-new/tests/sexpr2xmldata/Makefile.in 2010-05-17 17:52:27.543159000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xencapsdata/Makefile.in gcrypt-new/tests/xencapsdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xencapsdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xencapsdata/Makefile.in 2010-05-17 17:52:27.704150000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xmconfigdata/Makefile.in gcrypt-new/tests/xmconfigdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xmconfigdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xmconfigdata/Makefile.in 2010-05-17 17:52:27.872118000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tests/xml2sexprdata/Makefile.in gcrypt-new/tests/xml2sexprdata/Makefile.in
|
||||
--- libvirt-0.7.1/tests/xml2sexprdata/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tests/xml2sexprdata/Makefile.in 2010-05-17 17:52:28.046074000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
diff -rup libvirt-0.7.1/tools/Makefile.in gcrypt-new/tools/Makefile.in
|
||||
--- libvirt-0.7.1/tools/Makefile.in 2009-09-15 08:35:18.000000000 -0400
|
||||
+++ gcrypt-new/tools/Makefile.in 2010-05-17 17:52:28.213075000 -0400
|
||||
@@ -1,4 +1,4 @@
|
||||
-# Makefile.in generated by automake 1.11 from Makefile.am.
|
||||
+# Makefile.in generated by automake 1.11.1 from Makefile.am.
|
||||
# @configure_input@
|
||||
|
||||
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
|
||||
@@ -1,13 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/lxc_driver.c new/src/lxc_driver.c
|
||||
--- libvirt-0.7.1/src/lxc_driver.c 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ new/src/lxc_driver.c 2010-06-03 15:03:11.524069000 -0400
|
||||
@@ -96,7 +96,8 @@ static virDrvOpenStatus lxcOpen(virConne
|
||||
return VIR_DRV_OPEN_DECLINED;
|
||||
|
||||
/* If path isn't '/' then they typoed, tell them correct path */
|
||||
- if (STRNEQ(conn->uri->path, "/")) {
|
||||
+ if (conn->uri->path != NULL &&
|
||||
+ STRNEQ(conn->uri->path, "/")) {
|
||||
lxcError(conn, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
_("unexpected LXC URI path '%s', try lxc:///"),
|
||||
conn->uri->path);
|
||||
@@ -1,65 +0,0 @@
|
||||
commit e5f31f461f63bbad211e84b810d6ba43a705f9dd
|
||||
Author: Justin Clift <justin@salasaga.org>
|
||||
Date: Sun May 30 13:28:42 2010 +1000
|
||||
|
||||
Trivial virsh.pod additions --all for "list" command and similar
|
||||
|
||||
This is just a trivial patch to virsh.pod (from git master). It adds the
|
||||
following pieces to the virsh man page:
|
||||
|
||||
+ Shows the --inactive and --all optional parameters for the list
|
||||
command.
|
||||
|
||||
Closes Bugzilla #575512, reported by Renich Bon Ciric
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=575512
|
||||
|
||||
+ Corrects the existing description of the list command, to now say
|
||||
that only running domains are listed if no domains are specified.
|
||||
|
||||
The man page up until this point has said all domains are listed if
|
||||
no domains are specified, which is incorrect.
|
||||
|
||||
+ Adds the "shut off" state to the list of states for the list
|
||||
command.
|
||||
|
||||
+ Adds a missing =back around line 755, that pod2man was complaining
|
||||
was missing.
|
||||
|
||||
diff --git a/tools/virsh.pod b/tools/virsh.pod
|
||||
index cf7585d..495bb46 100644
|
||||
--- a/docs/virsh.pod
|
||||
+++ b/docs/virsh.pod
|
||||
@@ -156,10 +156,10 @@ description see:
|
||||
L<http://libvirt.org/formatcaps.html>
|
||||
The XML also show the NUMA topology information if available.
|
||||
|
||||
-=item B<list>
|
||||
+=item B<list> optional I<--inactive> I<--all>
|
||||
|
||||
Prints information about one or more domains. If no domains are
|
||||
-specified it prints out information about all domains.
|
||||
+specified it prints out information about running domains.
|
||||
|
||||
An example format for the list is as follows:
|
||||
|
||||
@@ -177,7 +177,7 @@ State is the run state (see below).
|
||||
|
||||
B<STATES>
|
||||
|
||||
-The State field lists 6 states for a domain, and which ones the
|
||||
+The State field lists 7 states for a domain, and which ones the
|
||||
current domain is in.
|
||||
|
||||
=over 4
|
||||
@@ -205,6 +205,11 @@ The domain is in the process of shutting down, i.e. the guest operating system
|
||||
has been notified and should be in the process of stopping its operations
|
||||
gracefully.
|
||||
|
||||
+=item B<shut off>
|
||||
+
|
||||
+The domain is not running. Usually this indicates the domain has been
|
||||
+shut down completely, or has not been started.
|
||||
+
|
||||
=item B<crashed>
|
||||
|
||||
The domain has crashed, which is always a violent ending. Usually
|
||||
@@ -1,401 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/libvirt.c new/src/libvirt.c
|
||||
--- libvirt-0.7.1/src/libvirt.c 2010-06-03 15:30:32.615164000 -0400
|
||||
+++ new/src/libvirt.c 2010-06-03 15:33:22.863409000 -0400
|
||||
@@ -3054,6 +3054,7 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
char *cookie = NULL;
|
||||
char *dom_xml = NULL;
|
||||
int cookielen = 0, ret;
|
||||
+ virErrorPtr orig_err = NULL;
|
||||
|
||||
/* Prepare the migration.
|
||||
*
|
||||
@@ -3102,6 +3103,10 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
ret = domain->conn->driver->domainMigratePerform
|
||||
(domain, cookie, cookielen, uri, flags, dname, bandwidth);
|
||||
|
||||
+ /* Perform failed. Make sure Finish doesn't overwrite the error */
|
||||
+ if (ret < 0)
|
||||
+ orig_err = virSaveLastError();
|
||||
+
|
||||
/* In version 2 of the migration protocol, we pass the
|
||||
* status code from the sender to the destination host,
|
||||
* so it can do any cleanup if the migration failed.
|
||||
@@ -3111,6 +3116,10 @@ virDomainMigrateVersion2 (virDomainPtr d
|
||||
(dconn, dname, cookie, cookielen, uri, flags, ret);
|
||||
|
||||
done:
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
VIR_FREE (uri_out);
|
||||
VIR_FREE (cookie);
|
||||
return ddomain;
|
||||
@@ -3222,7 +3231,7 @@ virDomainMigrate (virDomainPtr domain,
|
||||
|
||||
error:
|
||||
/* Copy to connection error object for back compatability */
|
||||
- virSetConnError(domain->conn);
|
||||
+ virDispatchError(domain->conn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -3269,8 +3278,7 @@ virDomainMigratePrepare (virConnectPtr d
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3318,8 +3326,7 @@ virDomainMigratePerform (virDomainPtr do
|
||||
virLibDomainError (domain, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(domain->conn);
|
||||
+ virDispatchError(domain->conn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3364,8 +3371,7 @@ virDomainMigrateFinish (virConnectPtr dc
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -3416,8 +3422,7 @@ virDomainMigratePrepare2 (virConnectPtr
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -3464,8 +3469,7 @@ virDomainMigrateFinish2 (virConnectPtr d
|
||||
virLibConnError (dconn, VIR_ERR_NO_SUPPORT, __FUNCTION__);
|
||||
|
||||
error:
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(dconn);
|
||||
+ virDispatchError(dconn);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms new/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-06-03 15:30:33.051186000 -0400
|
||||
+++ new/src/libvirt_private.syms 2010-06-03 15:33:22.869400000 -0400
|
||||
@@ -461,6 +461,7 @@ virRaiseErrorFull;
|
||||
virReportSystemErrorFull;
|
||||
virReportOOMErrorFull;
|
||||
virStrerror;
|
||||
+virSetError;
|
||||
|
||||
|
||||
# xml.h
|
||||
diff -rup libvirt-0.7.1/src/qemu_driver.c new/src/qemu_driver.c
|
||||
--- libvirt-0.7.1/src/qemu_driver.c 2010-06-03 15:30:33.111159000 -0400
|
||||
+++ new/src/qemu_driver.c 2010-06-03 15:35:22.809404000 -0400
|
||||
@@ -2297,12 +2297,17 @@ static void qemudShutdownVMDaemon(virCon
|
||||
virDomainObjPtr vm) {
|
||||
int ret;
|
||||
int retries = 0;
|
||||
+ virErrorPtr orig_err;
|
||||
|
||||
if (!virDomainIsActive(vm))
|
||||
return;
|
||||
|
||||
VIR_DEBUG(_("Shutting down VM '%s'\n"), vm->def->name);
|
||||
|
||||
+ /* This method is routinely used in clean up paths. Disable error
|
||||
+ * reporting so we don't squash a legit error. */
|
||||
+ orig_err = virSaveLastError();
|
||||
+
|
||||
if (virKillProcess(vm->pid, 0) == 0 &&
|
||||
virKillProcess(vm->pid, SIGTERM) < 0)
|
||||
virReportSystemError(conn, errno,
|
||||
@@ -2377,6 +2382,11 @@ retry:
|
||||
vm->def->id = -1;
|
||||
vm->newDef = NULL;
|
||||
}
|
||||
+
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
}
|
||||
|
||||
|
||||
@@ -7497,6 +7507,10 @@ qemudDomainMigrateFinish2 (virConnectPtr
|
||||
virDomainObjPtr vm;
|
||||
virDomainPtr dom = NULL;
|
||||
virDomainEventPtr event = NULL;
|
||||
+ virErrorPtr orig_err;
|
||||
+
|
||||
+ /* Migration failed. Save the current error so nothing squashes it */
|
||||
+ orig_err = virSaveLastError();
|
||||
|
||||
qemuDriverLock(driver);
|
||||
vm = virDomainFindByName(&driver->domains, dname);
|
||||
@@ -7540,6 +7554,10 @@ qemudDomainMigrateFinish2 (virConnectPtr
|
||||
}
|
||||
|
||||
cleanup:
|
||||
+ if (orig_err) {
|
||||
+ virSetError(orig_err);
|
||||
+ virFreeError(orig_err);
|
||||
+ }
|
||||
if (vm)
|
||||
virDomainObjUnlock(vm);
|
||||
if (event)
|
||||
diff -rup libvirt-0.7.1/src/util.c new/src/util.c
|
||||
--- libvirt-0.7.1/src/util.c 2010-06-03 15:30:33.064159000 -0400
|
||||
+++ new/src/util.c 2010-06-03 15:33:22.881417000 -0400
|
||||
@@ -1764,31 +1764,82 @@ int virDiskNameToIndex(const char *name)
|
||||
#define AI_CANONIDN 0
|
||||
#endif
|
||||
|
||||
-char *virGetHostname(void)
|
||||
+/* Who knew getting a hostname could be so delicate. In Linux (and Unices
|
||||
+ * in general), many things depend on "hostname" returning a value that will
|
||||
+ * resolve one way or another. In the modern world where networks frequently
|
||||
+ * come and go this is often being hard-coded to resolve to "localhost". If
|
||||
+ * it *doesn't* resolve to localhost, then we would prefer to have the FQDN.
|
||||
+ * That leads us to 3 possibilities:
|
||||
+ *
|
||||
+ * 1) gethostname() returns an FQDN (not localhost) - we return the string
|
||||
+ * as-is, it's all of the information we want
|
||||
+ * 2) gethostname() returns "localhost" - we return localhost; doing further
|
||||
+ * work to try to resolve it is pointless
|
||||
+ * 3) gethostname() returns a shortened hostname - in this case, we want to
|
||||
+ * try to resolve this to a fully-qualified name. Therefore we pass it
|
||||
+ * to getaddrinfo(). There are two possible responses:
|
||||
+ * a) getaddrinfo() resolves to a FQDN - return the FQDN
|
||||
+ * b) getaddrinfo() resolves to localhost - in this case, the data we got
|
||||
+ * from gethostname() is actually more useful than what we got from
|
||||
+ * getaddrinfo(). Return the value from gethostname() and hope for
|
||||
+ * the best.
|
||||
+ */
|
||||
+char *virGetHostname()
|
||||
{
|
||||
int r;
|
||||
char hostname[HOST_NAME_MAX+1], *result;
|
||||
struct addrinfo hints, *info;
|
||||
|
||||
r = gethostname (hostname, sizeof(hostname));
|
||||
- if (r == -1)
|
||||
+ if (r == -1) {
|
||||
+ virReportSystemError(NULL, errno,
|
||||
+ "%s", _("failed to determine host name"));
|
||||
return NULL;
|
||||
+ }
|
||||
NUL_TERMINATE(hostname);
|
||||
|
||||
+ if (STRPREFIX(hostname, "localhost") || strchr(hostname, '.')) {
|
||||
+ /* in this case, gethostname returned localhost (meaning we can't
|
||||
+ * do any further canonicalization), or it returned an FQDN (and
|
||||
+ * we don't need to do any further canonicalization). Return the
|
||||
+ * string as-is; it's up to callers to check whether "localhost"
|
||||
+ * is allowed.
|
||||
+ */
|
||||
+ result = strdup(hostname);
|
||||
+ goto check_and_return;
|
||||
+ }
|
||||
+
|
||||
+ /* otherwise, it's a shortened, non-localhost, hostname. Attempt to
|
||||
+ * canonicalize the hostname by running it through getaddrinfo
|
||||
+ */
|
||||
+
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
hints.ai_flags = AI_CANONNAME|AI_CANONIDN;
|
||||
hints.ai_family = AF_UNSPEC;
|
||||
r = getaddrinfo(hostname, NULL, &hints, &info);
|
||||
- if (r != 0)
|
||||
- return NULL;
|
||||
- if (info->ai_canonname == NULL) {
|
||||
- freeaddrinfo(info);
|
||||
+ if (r != 0) {
|
||||
+ ReportError(NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("getaddrinfo failed for '%s': %s"),
|
||||
+ hostname, gai_strerror(r));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- /* Caller frees this string. */
|
||||
- result = strdup (info->ai_canonname);
|
||||
+ if (info->ai_canonname == NULL ||
|
||||
+ STRPREFIX(info->ai_canonname, "localhost"))
|
||||
+ /* in this case, we tried to canonicalize and we ended up back with
|
||||
+ * localhost. Ignore the canonicalized name and just return the
|
||||
+ * original hostname
|
||||
+ */
|
||||
+ result = strdup(hostname);
|
||||
+ else
|
||||
+ /* Caller frees this string. */
|
||||
+ result = strdup (info->ai_canonname);
|
||||
+
|
||||
freeaddrinfo(info);
|
||||
+
|
||||
+check_and_return:
|
||||
+ if (result == NULL)
|
||||
+ virReportOOMError(NULL);
|
||||
return result;
|
||||
}
|
||||
|
||||
diff -rup libvirt-0.7.1/src/virterror.c new/src/virterror.c
|
||||
--- libvirt-0.7.1/src/virterror.c 2009-09-14 06:12:53.000000000 -0400
|
||||
+++ new/src/virterror.c 2010-06-03 15:33:22.886409000 -0400
|
||||
@@ -287,6 +287,28 @@ virGetLastError(void)
|
||||
}
|
||||
|
||||
/**
|
||||
+ * virSetError:
|
||||
+ *
|
||||
+ * Set the current error from a previously saved error object
|
||||
+ *
|
||||
+ * Can be used to re-set an old error, which may have been squashed by
|
||||
+ * other functions (like cleanup routines).
|
||||
+ *
|
||||
+ * Returns 0 on success, 1 on failure
|
||||
+ */
|
||||
+int
|
||||
+virSetError(virErrorPtr newerr)
|
||||
+{
|
||||
+ virErrorPtr err;
|
||||
+ err = virGetLastError();
|
||||
+ if (!err)
|
||||
+ return -1;
|
||||
+
|
||||
+ virResetError(err);
|
||||
+ return virCopyError(newerr, err);
|
||||
+}
|
||||
+
|
||||
+/**
|
||||
* virCopyLastError:
|
||||
* @to: target to receive the copy
|
||||
*
|
||||
@@ -596,6 +618,52 @@ virSetConnError(virConnectPtr conn)
|
||||
}
|
||||
}
|
||||
|
||||
+/**
|
||||
+ * virDispatchError:
|
||||
+ * @conn: pointer to the hypervisor connection
|
||||
+ *
|
||||
+ * Internal helper to do final stage of error
|
||||
+ * reporting in public APIs.
|
||||
+ *
|
||||
+ * - Copy the global error to per-connection error if needed
|
||||
+ * - Set a generic error message if none is already set
|
||||
+ * - Invoke the error callback functions
|
||||
+ */
|
||||
+void
|
||||
+virDispatchError(virConnectPtr conn)
|
||||
+{
|
||||
+ virErrorPtr err = virLastErrorObject();
|
||||
+ virErrorFunc handler = virErrorHandler;
|
||||
+ void *userData = virUserData;
|
||||
+
|
||||
+ /* Should never happen, but doesn't hurt to check */
|
||||
+ if (!err)
|
||||
+ return;
|
||||
+
|
||||
+ /* Set a generic error message if none is already set */
|
||||
+ if (err->code == VIR_ERR_OK)
|
||||
+ virErrorGenericFailure(err);
|
||||
+
|
||||
+ /* Copy the global error to per-connection error if needed */
|
||||
+ if (conn) {
|
||||
+ virMutexLock(&conn->lock);
|
||||
+ virCopyError(err, &conn->err);
|
||||
+
|
||||
+ if (conn->handler != NULL) {
|
||||
+ handler = conn->handler;
|
||||
+ userData = conn->userData;
|
||||
+ }
|
||||
+ virMutexUnlock(&conn->lock);
|
||||
+ }
|
||||
+
|
||||
+ /* Invoke the error callback functions */
|
||||
+ if (handler != NULL) {
|
||||
+ (handler)(userData, err);
|
||||
+ } else {
|
||||
+ virDefaultErrorFunc(err);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
|
||||
|
||||
/**
|
||||
@@ -634,8 +702,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
virErrorPtr to;
|
||||
- void *userData = virUserData;
|
||||
- virErrorFunc handler = virErrorHandler;
|
||||
char *str;
|
||||
|
||||
/*
|
||||
@@ -653,18 +719,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
return;
|
||||
|
||||
/*
|
||||
- * try to find the best place to save and report the error
|
||||
- */
|
||||
- if (conn != NULL) {
|
||||
- virMutexLock(&conn->lock);
|
||||
- if (conn->handler != NULL) {
|
||||
- handler = conn->handler;
|
||||
- userData = conn->userData;
|
||||
- }
|
||||
- virMutexUnlock(&conn->lock);
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
* formats the message
|
||||
*/
|
||||
if (fmt == NULL) {
|
||||
@@ -683,7 +737,6 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
/*
|
||||
* Save the information about the error
|
||||
*/
|
||||
- virResetError(to);
|
||||
/*
|
||||
* Delibrately not setting conn, dom & net fields since
|
||||
* they're utterly unsafe
|
||||
@@ -701,14 +754,7 @@ virRaiseErrorFull(virConnectPtr conn,
|
||||
to->int1 = int1;
|
||||
to->int2 = int2;
|
||||
|
||||
- /*
|
||||
- * now, report it
|
||||
- */
|
||||
- if (handler != NULL) {
|
||||
- handler(userData, to);
|
||||
- } else {
|
||||
- virDefaultErrorFunc(to);
|
||||
- }
|
||||
+ virDispatchError(conn);
|
||||
}
|
||||
|
||||
/**
|
||||
diff -rup libvirt-0.7.1/src/virterror_internal.h new/src/virterror_internal.h
|
||||
--- libvirt-0.7.1/src/virterror_internal.h 2009-07-23 12:33:02.000000000 -0400
|
||||
+++ new/src/virterror_internal.h 2010-06-03 15:33:22.890402000 -0400
|
||||
@@ -89,6 +89,8 @@ void virReportOOMErrorFull(virConnectPtr
|
||||
|
||||
void virSetGlobalError(void);
|
||||
void virSetConnError(virConnectPtr conn);
|
||||
+int virSetError(virErrorPtr newerr);
|
||||
+void virDispatchError(virConnectPtr conn);
|
||||
const char *virStrerror(int theerrno, char *errBuf, size_t errBufLen);
|
||||
|
||||
#endif
|
||||
@@ -1,126 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/network_driver.c new/src/network_driver.c
|
||||
--- libvirt-0.7.1/src/network_driver.c 2009-09-15 03:49:04.000000000 -0400
|
||||
+++ new/src/network_driver.c 2010-06-15 13:33:01.900912000 -0400
|
||||
@@ -43,6 +43,8 @@
|
||||
#include <stdio.h>
|
||||
#include <sys/wait.h>
|
||||
#include <sys/ioctl.h>
|
||||
+#include <netinet/in.h>
|
||||
+#include <arpa/inet.h>
|
||||
|
||||
#include "virterror_internal.h"
|
||||
#include "datatypes.h"
|
||||
@@ -843,6 +845,102 @@ cleanup:
|
||||
return ret;
|
||||
}
|
||||
|
||||
+#define PROC_NET_ROUTE "/proc/net/route"
|
||||
+
|
||||
+static int networkCheckRouteCollision(virNetworkObjPtr network)
|
||||
+{
|
||||
+ int ret = -1, len;
|
||||
+ char *cur, *buf = NULL;
|
||||
+ enum {MAX_ROUTE_SIZE = 1024*64};
|
||||
+ struct in_addr inaddress, innetmask;
|
||||
+ unsigned int net_dest;
|
||||
+
|
||||
+ if (!network->def->ipAddress || !network->def->netmask)
|
||||
+ return 0;
|
||||
+
|
||||
+ if (inet_pton(AF_INET, network->def->ipAddress, &inaddress) <= 0) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("cannot parse IP address '%s'"),
|
||||
+ network->def->ipAddress);
|
||||
+ goto error;
|
||||
+ }
|
||||
+ if (inet_pton(AF_INET, network->def->netmask, &innetmask) <= 0) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("cannot parse netmask '%s'"),
|
||||
+ network->def->netmask);
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ net_dest = (inaddress.s_addr & innetmask.s_addr);
|
||||
+
|
||||
+ /* Read whole routing table into memory */
|
||||
+ if ((len = virFileReadAll(PROC_NET_ROUTE, MAX_ROUTE_SIZE, &buf)) < 0)
|
||||
+ goto error;
|
||||
+
|
||||
+ /* Dropping the last character shouldn't hurt */
|
||||
+ if (len > 0)
|
||||
+ buf[len-1] = '\0';
|
||||
+
|
||||
+ VIR_DEBUG("%s output:\n%s", PROC_NET_ROUTE, buf);
|
||||
+
|
||||
+ if (!STRPREFIX (buf, "Iface"))
|
||||
+ goto out;
|
||||
+
|
||||
+ /* First line is just headings, skip it */
|
||||
+ cur = strchr(buf, '\n');
|
||||
+ if (cur)
|
||||
+ cur++;
|
||||
+
|
||||
+ while (cur) {
|
||||
+ char iface[17], dest[128], mask[128];
|
||||
+ unsigned int addr_val, mask_val;
|
||||
+ int num;
|
||||
+
|
||||
+ /* NUL-terminate the line, so sscanf doesn't go beyond a newline. */
|
||||
+ char *nl = strchr(cur, '\n');
|
||||
+ if (nl) {
|
||||
+ *nl++ = '\0';
|
||||
+ }
|
||||
+
|
||||
+ num = sscanf(cur, "%16s %127s %*s %*s %*s %*s %*s %127s",
|
||||
+ iface, dest, mask);
|
||||
+ cur = nl;
|
||||
+
|
||||
+ if (num != 3) {
|
||||
+ VIR_DEBUG("Failed to parse %s", PROC_NET_ROUTE);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (virStrToLong_ui(dest, NULL, 16, &addr_val) < 0) {
|
||||
+ VIR_DEBUG("Failed to convert network address %s to uint", dest);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ if (virStrToLong_ui(mask, NULL, 16, &mask_val) < 0) {
|
||||
+ VIR_DEBUG("Failed to convert network mask %s to uint", mask);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ addr_val &= mask_val;
|
||||
+
|
||||
+ if ((net_dest == addr_val) &&
|
||||
+ (innetmask.s_addr == mask_val)) {
|
||||
+ networkReportError(NULL, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Network %s/%s is already in use by "
|
||||
+ "interface %s"),
|
||||
+ network->def->ipAddress,
|
||||
+ network->def->netmask, iface);
|
||||
+ goto error;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+out:
|
||||
+ ret = 0;
|
||||
+error:
|
||||
+ VIR_FREE(buf);
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
static int networkStartNetworkDaemon(virConnectPtr conn,
|
||||
struct network_driver *driver,
|
||||
virNetworkObjPtr network) {
|
||||
@@ -854,6 +952,10 @@ static int networkStartNetworkDaemon(vir
|
||||
return -1;
|
||||
}
|
||||
|
||||
+ /* Check to see if network collides with an existing route */
|
||||
+ if (networkCheckRouteCollision(network) < 0)
|
||||
+ return -1;
|
||||
+
|
||||
if ((err = brAddBridge(driver->brctl, network->def->bridge))) {
|
||||
virReportSystemError(conn, err,
|
||||
_("cannot create bridge '%s'"),
|
||||
@@ -1,29 +0,0 @@
|
||||
commit c11a82b62aefc21e070c527f59a1f9c57a7b4f36
|
||||
Author: Richard Jones <rjones@redhat.com>
|
||||
Date: Thu Dec 10 16:39:07 2009 +0000
|
||||
|
||||
qemu driver: Fix segfault in libvirt/libvirtd when uri->path is NULL.
|
||||
|
||||
See also:
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=545400#c1
|
||||
|
||||
diff --git a/src/qemu/qemu_driver.c b/src/qemu/qemu_driver.c
|
||||
index 2fb059d..e9cc8c3 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -2651,6 +2651,15 @@ static virDrvOpenStatus qemudOpen(virConnectPtr conn,
|
||||
return VIR_DRV_OPEN_ERROR;
|
||||
}
|
||||
|
||||
+ if (conn->uri->path == NULL) {
|
||||
+ qemudReportError(conn, NULL, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("no QEMU URI path given, try %s"),
|
||||
+ qemu_driver->privileged
|
||||
+ ? "qemu:///system"
|
||||
+ : "qemu:///session");
|
||||
+ return VIR_DRV_OPEN_ERROR;
|
||||
+ }
|
||||
+
|
||||
if (qemu_driver->privileged) {
|
||||
if (STRNEQ (conn->uri->path, "/system") &&
|
||||
STRNEQ (conn->uri->path, "/session")) {
|
||||
@@ -1,143 +0,0 @@
|
||||
diff -rup libvirt-0.7.1/src/libvirt_private.syms paths/src/libvirt_private.syms
|
||||
--- libvirt-0.7.1/src/libvirt_private.syms 2010-05-26 12:48:49.276277000 -0400
|
||||
+++ paths/src/libvirt_private.syms 2010-05-26 13:00:47.501023000 -0400
|
||||
@@ -417,6 +417,7 @@ virParseMacAddr;
|
||||
virFileDeletePid;
|
||||
virFindFileInPath;
|
||||
virFileExists;
|
||||
+virFileSanitizePath;
|
||||
virFileHasSuffix;
|
||||
virFileLinkPointsTo;
|
||||
virFileMakePath;
|
||||
diff -rup libvirt-0.7.1/src/storage_conf.c paths/src/storage_conf.c
|
||||
--- libvirt-0.7.1/src/storage_conf.c 2010-05-26 12:48:48.885306000 -0400
|
||||
+++ paths/src/storage_conf.c 2010-05-26 13:00:17.027330000 -0400
|
||||
@@ -463,6 +463,7 @@ virStoragePoolDefParseXML(virConnectPtr
|
||||
char *type = NULL;
|
||||
char *uuid = NULL;
|
||||
char *authType = NULL;
|
||||
+ char *tmppath;
|
||||
|
||||
if (VIR_ALLOC(ret) < 0) {
|
||||
virReportOOMError(conn);
|
||||
@@ -610,11 +611,15 @@ virStoragePoolDefParseXML(virConnectPtr
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if ((ret->target.path = virXPathString(conn, "string(./target/path)", ctxt)) == NULL) {
|
||||
+ if ((tmppath = virXPathString(conn, "string(./target/path)", ctxt)) == NULL) {
|
||||
virStorageReportError(conn, VIR_ERR_XML_ERROR,
|
||||
"%s", _("missing storage pool target path"));
|
||||
goto cleanup;
|
||||
}
|
||||
+ ret->target.path = virFileSanitizePath(tmppath);
|
||||
+ VIR_FREE(tmppath);
|
||||
+ if (!ret->target.path)
|
||||
+ goto cleanup;
|
||||
|
||||
if (virStorageDefParsePerms(conn, ctxt, &ret->target.perms,
|
||||
"./target/permissions", 0700) < 0)
|
||||
diff -rup libvirt-0.7.1/src/storage_driver.c paths/src/storage_driver.c
|
||||
--- libvirt-0.7.1/src/storage_driver.c 2009-09-10 09:45:00.000000000 -0400
|
||||
+++ paths/src/storage_driver.c 2010-05-26 12:59:14.815537000 -0400
|
||||
@@ -1152,6 +1152,11 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
virStorageDriverStatePtr driver = conn->storagePrivateData;
|
||||
unsigned int i;
|
||||
virStorageVolPtr ret = NULL;
|
||||
+ char *cleanpath;
|
||||
+
|
||||
+ cleanpath = virFileSanitizePath(path);
|
||||
+ if (!cleanpath)
|
||||
+ return NULL;
|
||||
|
||||
storageDriverLock(driver);
|
||||
for (i = 0 ; i < driver->pools.count && !ret ; i++) {
|
||||
@@ -1162,7 +1167,7 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
|
||||
stable_path = virStorageBackendStablePath(conn,
|
||||
driver->pools.objs[i],
|
||||
- path);
|
||||
+ cleanpath);
|
||||
/*
|
||||
* virStorageBackendStablePath already does
|
||||
* virStorageReportError if it fails; we just need to keep
|
||||
@@ -1191,6 +1196,7 @@ storageVolumeLookupByPath(virConnectPtr
|
||||
"%s", _("no storage vol with matching path"));
|
||||
|
||||
cleanup:
|
||||
+ VIR_FREE(cleanpath);
|
||||
storageDriverUnlock(driver);
|
||||
return ret;
|
||||
}
|
||||
diff -rup libvirt-0.7.1/src/util.c paths/src/util.c
|
||||
--- libvirt-0.7.1/src/util.c 2010-05-26 12:48:48.840341000 -0400
|
||||
+++ paths/src/util.c 2010-05-26 12:58:02.088721000 -0400
|
||||
@@ -1126,6 +1126,55 @@ int virFileExists(const char *path)
|
||||
return(0);
|
||||
}
|
||||
|
||||
+/* Remove spurious / characters from a path. The result must be freed */
|
||||
+char *
|
||||
+virFileSanitizePath(const char *path)
|
||||
+{
|
||||
+ const char *cur = path;
|
||||
+ char *cleanpath;
|
||||
+ int idx = 0;
|
||||
+
|
||||
+ cleanpath = strdup(path);
|
||||
+ if (!cleanpath) {
|
||||
+ virReportOOMError(NULL);
|
||||
+ return NULL;
|
||||
+ }
|
||||
+
|
||||
+ /* Need to sanitize:
|
||||
+ * // -> //
|
||||
+ * /// -> /
|
||||
+ * /../foo -> /../foo
|
||||
+ * /foo///bar/ -> /foo/bar
|
||||
+ */
|
||||
+
|
||||
+ /* Starting with // is valid posix, but ///foo == /foo */
|
||||
+ if (cur[0] == '/' && cur[1] == '/' && cur[2] != '/') {
|
||||
+ idx = 2;
|
||||
+ cur += 2;
|
||||
+ }
|
||||
+
|
||||
+ /* Sanitize path in place */
|
||||
+ while (*cur != '\0') {
|
||||
+ if (*cur != '/') {
|
||||
+ cleanpath[idx++] = *cur++;
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ /* Skip all extra / */
|
||||
+ while (*++cur == '/')
|
||||
+ continue;
|
||||
+
|
||||
+ /* Don't add a trailing / */
|
||||
+ if (idx != 0 && *cur == '\0')
|
||||
+ break;
|
||||
+
|
||||
+ cleanpath[idx++] = '/';
|
||||
+ }
|
||||
+ cleanpath[idx] = '\0';
|
||||
+
|
||||
+ return cleanpath;
|
||||
+}
|
||||
+
|
||||
int virFileMakePath(const char *path)
|
||||
{
|
||||
struct stat st;
|
||||
diff -rup libvirt-0.7.1/src/util.h paths/src/util.h
|
||||
--- libvirt-0.7.1/src/util.h 2010-05-26 12:48:48.749342000 -0400
|
||||
+++ paths/src/util.h 2010-05-26 12:56:57.494264000 -0400
|
||||
@@ -107,6 +107,9 @@ char *virFindFileInPath(const char *file
|
||||
|
||||
int virFileExists(const char *path);
|
||||
|
||||
+char *virFileSanitizePath(const char *path);
|
||||
+
|
||||
+
|
||||
int virFileMakePath(const char *path);
|
||||
|
||||
int virFileBuildPath(const char *dir,
|
||||
@@ -1,34 +0,0 @@
|
||||
From bcd4180124afa20580d720912e2179b3a2f9295a Mon Sep 17 00:00:00 2001
|
||||
From: Daniel Veillard <veillard@redhat.com>
|
||||
Date: Mon, 5 Oct 2009 17:03:14 +0200
|
||||
Subject: [PATCH] 526769 change logrotate config default to weekly
|
||||
|
||||
* daemon/libvirtd.logrotate.in: change to weekly rotation of logs,
|
||||
keep a month worth of data and also extend to cover LXC and UML
|
||||
domain logs
|
||||
|
||||
(cherry picked from commit 529325bbdd050af89bda5a5c1a01b5553c49a57e)
|
||||
|
||||
Fedora-patch: libvirt-change-logrotate-config-to-weekly.patch
|
||||
---
|
||||
qemud/libvirtd.logrotate.in | 6 +++---
|
||||
1 files changed, 3 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.logrotate.in b/qemud/libvirtd.logrotate.in
|
||||
index 9b42630..093651c 100644
|
||||
--- a/qemud/libvirtd.logrotate.in
|
||||
+++ b/qemud/libvirtd.logrotate.in
|
||||
@@ -1,7 +1,7 @@
|
||||
-@localstatedir@/log/libvirt/qemu/*.log {
|
||||
- daily
|
||||
+@localstatedir@/log/libvirt/qemu/*.log @localstatedir@/log/libvirt/uml/*.log @localstatedir@/log/libvirt/lxc/*.log {
|
||||
+ weekly
|
||||
missingok
|
||||
- rotate 7
|
||||
+ rotate 4
|
||||
compress
|
||||
delaycompress
|
||||
copytruncate
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,77 +0,0 @@
|
||||
From 4721ceb9b85daabe53804627473b06ced821c695 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 14 Sep 2009 11:23:20 +0100
|
||||
Subject: [PATCH] Allow control over QEMU audio backend
|
||||
|
||||
When using VNC for graphics + keyboard + mouse, we shouldn't
|
||||
then use the host OS for audio. Audio should go back over
|
||||
VNC.
|
||||
|
||||
When using SDL for graphics, we should use the host OS for
|
||||
audio since that's where the display is. We need to allow
|
||||
certain QEMU env variables to be passed through to guest
|
||||
too to allow choice of QEMU audio backend.
|
||||
|
||||
* qemud/libvirtd.sysconf: Mention QEMU/SDL audio env vars
|
||||
* src/qemu_conf.c: Passthrough QEMU/SDL audio env for SDL display,
|
||||
disable host audio for VNC display
|
||||
|
||||
(cherry picked from commit b08e6d38ae7a0ed70300d7d82107f83fddb60f44)
|
||||
|
||||
Fedora-patch: libvirt-disable-audio-backend.patch
|
||||
---
|
||||
qemud/libvirtd.sysconf | 8 ++++++++
|
||||
src/qemu_conf.c | 14 ++++++++++++++
|
||||
2 files changed, 22 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.sysconf b/qemud/libvirtd.sysconf
|
||||
index fe4596a..28080a0 100644
|
||||
--- a/qemud/libvirtd.sysconf
|
||||
+++ b/qemud/libvirtd.sysconf
|
||||
@@ -7,3 +7,11 @@
|
||||
|
||||
# Override Kerberos service keytab for SASL/GSSAPI
|
||||
#KRB5_KTNAME=/etc/libvirt/krb5.tab
|
||||
+
|
||||
+# Override the QEMU/SDL default audio driver probing when
|
||||
+# starting virtual machines using SDL graphics
|
||||
+#
|
||||
+# NB these have no effect for VMs using VNC
|
||||
+#QEMU_AUDIO_DRV=sdl
|
||||
+#
|
||||
+#SDL_AUDIODRIVER=pulse
|
||||
diff --git a/src/qemu_conf.c b/src/qemu_conf.c
|
||||
index f92bcef..0dd0624 100644
|
||||
--- a/src/qemu_conf.c
|
||||
+++ b/src/qemu_conf.c
|
||||
@@ -2109,6 +2109,13 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
ADD_ARG_LIT("-k");
|
||||
ADD_ARG_LIT(def->graphics[0]->data.vnc.keymap);
|
||||
}
|
||||
+
|
||||
+ /* QEMU implements a VNC extension for providing audio, so we
|
||||
+ * set the audio backend to none, to prevent it opening the
|
||||
+ * host OS audio devices since that causes security issues
|
||||
+ * and is non-sensical when using VNC.
|
||||
+ */
|
||||
+ ADD_ENV_LIT("QEMU_AUDIO_DRV=none");
|
||||
} else if ((def->ngraphics == 1) &&
|
||||
def->graphics[0]->type == VIR_DOMAIN_GRAPHICS_TYPE_SDL) {
|
||||
char *xauth = NULL;
|
||||
@@ -2131,6 +2138,13 @@ int qemudBuildCommandLine(virConnectPtr conn,
|
||||
ADD_ENV(display);
|
||||
if (def->graphics[0]->data.sdl.fullscreen)
|
||||
ADD_ARG_LIT("-full-screen");
|
||||
+
|
||||
+ /* If using SDL for video, then we should just let it
|
||||
+ * use QEMU's host audio drivers, possibly SDL too
|
||||
+ * User can set these two before starting libvirtd
|
||||
+ */
|
||||
+ ADD_ENV_COPY("QEMU_AUDIO_DRV");
|
||||
+ ADD_ENV_COPY("SDL_AUDIODRIVER");
|
||||
}
|
||||
|
||||
if (def->nvideos) {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,31 +0,0 @@
|
||||
From a5fa9f63fcffbf70465386672f24edac439866b9 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Thu, 24 Sep 2009 15:42:25 +0100
|
||||
Subject: [PATCH] Fix crash in device hotplug cleanup code
|
||||
|
||||
* src/qemu/qemu_driver.c: Fix crash in scenario where XML
|
||||
parsing of hotplugged device failed & thus 'dev' is NULL
|
||||
|
||||
(cherry picked from commit 879cd8cc2ba00f795913f296556e05f25afa7877)
|
||||
|
||||
Fedora-patch: libvirt-fix-crash-on-device-hotplug-parse-error.patch
|
||||
---
|
||||
src/qemu_driver.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 0ce403c..c956258 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5912,7 +5912,7 @@ cleanup:
|
||||
if (cgroup)
|
||||
virCgroupFree(&cgroup);
|
||||
|
||||
- if (ret < 0) {
|
||||
+ if (ret < 0 && dev != NULL) {
|
||||
if (qemuDomainSetDeviceOwnership(dom->conn, driver, dev, 1) < 0)
|
||||
VIR_WARN0("Fail to restore disk device ownership");
|
||||
virDomainDeviceDefFree(dev);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,33 +0,0 @@
|
||||
From 7bc1491deba6338e514504d1b68fe097e7f2bf19 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel Veillard <veillard@redhat.com>
|
||||
Date: Thu, 1 Oct 2009 11:54:38 +0200
|
||||
Subject: [PATCH] Avoid a libvirtd crash on broken input 523418
|
||||
|
||||
* src/conf/domain_conf.c: a simple typo in an XML domain file could lead
|
||||
to a crash, because we called STRPREFIX() on the looked up value without
|
||||
checking it was non-null.
|
||||
|
||||
(cherry picked from commit 79d233b5ca62f86ab22d271d1f08ec20060eee88)
|
||||
|
||||
Fedora-patch: libvirt-fix-crash-on-missing-iface-target-dev.patch
|
||||
---
|
||||
src/domain_conf.c | 3 ++-
|
||||
1 files changed, 2 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.c b/src/domain_conf.c
|
||||
index c424c67..476cdd7 100644
|
||||
--- a/src/domain_conf.c
|
||||
+++ b/src/domain_conf.c
|
||||
@@ -1031,7 +1031,8 @@ virDomainNetDefParseXML(virConnectPtr conn,
|
||||
} else if ((ifname == NULL) &&
|
||||
xmlStrEqual(cur->name, BAD_CAST "target")) {
|
||||
ifname = virXMLPropString(cur, "dev");
|
||||
- if (STRPREFIX((const char*)ifname, "vnet")) {
|
||||
+ if ((ifname != NULL) &&
|
||||
+ (STRPREFIX((const char*)ifname, "vnet"))) {
|
||||
/* An auto-generated target name, blank it out */
|
||||
VIR_FREE(ifname);
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,29 +0,0 @@
|
||||
From 58c38896a67c170063401d8091bae7dca8842923 Mon Sep 17 00:00:00 2001
|
||||
From: Jiri Denemark <jdenemar@redhat.com>
|
||||
Date: Wed, 23 Sep 2009 18:46:23 +0200
|
||||
Subject: [PATCH] Fix a typo in virDiskHasValidPciAddr()
|
||||
|
||||
(cherry-picked from commit 3620e3cdcfe56cc4475b5ef1a0a893757240b795)
|
||||
|
||||
Signed-off-by: Jiri Denemark <jdenemar@redhat.com>
|
||||
Fedora-patch: libvirt-fix-device-detach-typo1.patch
|
||||
---
|
||||
src/domain_conf.h | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.h b/src/domain_conf.h
|
||||
index 09368d9..d494e54 100644
|
||||
--- a/src/domain_conf.h
|
||||
+++ b/src/domain_conf.h
|
||||
@@ -125,7 +125,7 @@ struct _virDomainDiskDef {
|
||||
static inline int
|
||||
virDiskHasValidPciAddr(virDomainDiskDefPtr def)
|
||||
{
|
||||
- return def->pci_addr.domain || def->pci_addr.domain || def->pci_addr.slot;
|
||||
+ return def->pci_addr.domain || def->pci_addr.bus || def->pci_addr.slot;
|
||||
}
|
||||
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
From 81e967c716ce8c085be8baad9169f7772452d187 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 24 Sep 2009 08:55:55 +0100
|
||||
Subject: [PATCH] Fix a typo in virNetHasValidPciAddr() too
|
||||
|
||||
* src/domain_conf.h: check domain/bus/slot, not domain/domain/slot
|
||||
|
||||
(cherry-picked from commit 6bfffce91635bb08de601747e94ed1182c0f47eb)
|
||||
|
||||
Fedora-patch: libvirt-fix-device-detach-typo2.patch
|
||||
---
|
||||
src/domain_conf.h | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/domain_conf.h b/src/domain_conf.h
|
||||
index d494e54..7c918a7 100644
|
||||
--- a/src/domain_conf.h
|
||||
+++ b/src/domain_conf.h
|
||||
@@ -207,7 +207,7 @@ struct _virDomainNetDef {
|
||||
static inline int
|
||||
virNetHasValidPciAddr(virDomainNetDefPtr def)
|
||||
{
|
||||
- return def->pci_addr.domain || def->pci_addr.domain || def->pci_addr.slot;
|
||||
+ return def->pci_addr.domain || def->pci_addr.bus || def->pci_addr.slot;
|
||||
}
|
||||
|
||||
enum virDomainChrSrcType {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
From 3a64779ec5a89d38d64e07bca2b11b19e1882d7a Mon Sep 17 00:00:00 2001
|
||||
From: Charles Duffy <charles@dyfis.net>
|
||||
Date: Thu, 24 Sep 2009 09:00:24 +0100
|
||||
Subject: [PATCH] Fix unitialized variable in qemudDomainDetachHostPciDevice()
|
||||
|
||||
* src/qemu_driver.c: initialize detach var
|
||||
|
||||
(cherry-picked from commit 580ad29288751234bee47ac9f6c04dac1dc529ea)
|
||||
|
||||
Fedora-patch: libvirt-fix-device-detach-typo3.patch
|
||||
---
|
||||
src/qemu_driver.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 7c7b985..550a59c 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -6126,7 +6126,7 @@ static int qemudDomainDetachHostPciDevice(virConnectPtr conn,
|
||||
virDomainObjPtr vm,
|
||||
virDomainDeviceDefPtr dev)
|
||||
{
|
||||
- virDomainHostdevDefPtr detach;
|
||||
+ virDomainHostdevDefPtr detach = NULL;
|
||||
char *cmd, *reply;
|
||||
int i, ret;
|
||||
pciDevice *pci;
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,32 +0,0 @@
|
||||
From 7692e1e19487c28454b1e5f6488d5574c70883f2 Mon Sep 17 00:00:00 2001
|
||||
From: Chris Lalancette <clalance@redhat.com>
|
||||
Date: Mon, 21 Sep 2009 14:53:31 +0200
|
||||
Subject: [PATCH] Don't do virSetConnError when virDrvSupportsFeature is successful.
|
||||
|
||||
Signed-off-by: Chris Lalancette <clalance@redhat.com>
|
||||
Fedora-patch: libvirt-fix-drv-supports-feature-bogus-error.patch
|
||||
---
|
||||
src/libvirt.c | 7 +++++--
|
||||
1 files changed, 5 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/libvirt.c b/src/libvirt.c
|
||||
index 4a11688..fa59dc7 100644
|
||||
--- a/src/libvirt.c
|
||||
+++ b/src/libvirt.c
|
||||
@@ -1349,8 +1349,11 @@ virDrvSupportsFeature (virConnectPtr conn, int feature)
|
||||
}
|
||||
|
||||
ret = VIR_DRV_SUPPORTS_FEATURE (conn->driver, conn, feature);
|
||||
- /* Copy to connection error object for back compatability */
|
||||
- virSetConnError(conn);
|
||||
+
|
||||
+ if (ret < 0)
|
||||
+ /* Copy to connection error object for back compatability */
|
||||
+ virSetConnError(conn);
|
||||
+
|
||||
return ret;
|
||||
}
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,79 +0,0 @@
|
||||
From 71de8d92f20a9a9ee76d4d5df77ff477f1b7d441 Mon Sep 17 00:00:00 2001
|
||||
From: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Wed, 30 Sep 2009 02:17:27 +0200
|
||||
Subject: [PATCH] Fix memory leaks in libvirtd's message processing
|
||||
|
||||
Commit 47cab734995fa9521b1df05d37e9978eedd8d3a2 changed the way how
|
||||
qemud_client_message objects were reused. Before this commit
|
||||
remoteDispatchClientRequest() reused the received message for normal responses
|
||||
and to report non-fatal errors. If a fatal error occurred qemudWorker() frees
|
||||
the message. After this commit non-fatal errors are reported by
|
||||
remoteSerializeReplyError() using a new qemud_client_message object and the
|
||||
original message leaks.
|
||||
|
||||
To fix this leak the original message has to be freed if
|
||||
remoteSerializeReplyError() succeeds. If remoteSerializeReplyError()
|
||||
fails the original message is freed in qemudWorker().
|
||||
|
||||
* daemon/dispatch.c: free qemud_client_message objects that will not be reused
|
||||
and would leak otherwise, also free the allocated qemud_client_message object
|
||||
in remoteSerializeError() if an error occurs
|
||||
|
||||
(cherry-picked from commit c6f1459eb998619ab21a92d9bb87341f26978181)
|
||||
|
||||
Fedora-patch: libvirt-fix-libvirtd-leak-in-error-reply.patch
|
||||
---
|
||||
qemud/dispatch.c | 15 +++++++++++++--
|
||||
1 files changed, 13 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/qemud/dispatch.c b/qemud/dispatch.c
|
||||
index a60f2f4..ddb3215 100644
|
||||
--- a/qemud/dispatch.c
|
||||
+++ b/qemud/dispatch.c
|
||||
@@ -191,6 +191,7 @@ remoteSerializeError(struct qemud_client *client,
|
||||
|
||||
xdr_error:
|
||||
xdr_destroy(&xdr);
|
||||
+ VIR_FREE(msg);
|
||||
fatal_error:
|
||||
xdr_free((xdrproc_t)xdr_remote_error, (char *)rerr);
|
||||
return -1;
|
||||
@@ -336,6 +337,7 @@ remoteDispatchClientRequest (struct qemud_server *server,
|
||||
struct qemud_client *client,
|
||||
struct qemud_client_message *msg)
|
||||
{
|
||||
+ int ret;
|
||||
remote_error rerr;
|
||||
|
||||
memset(&rerr, 0, sizeof rerr);
|
||||
@@ -364,7 +366,12 @@ remoteDispatchClientRequest (struct qemud_server *server,
|
||||
}
|
||||
|
||||
error:
|
||||
- return remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+ ret = remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+
|
||||
+ if (ret >= 0)
|
||||
+ VIR_FREE(msg);
|
||||
+
|
||||
+ return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -521,8 +528,12 @@ remoteDispatchClientCall (struct qemud_server *server,
|
||||
rpc_error:
|
||||
/* Semi-bad stuff happened, we can still try to send back
|
||||
* an RPC error message to client */
|
||||
- return remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+ rv = remoteSerializeReplyError(client, &rerr, &msg->hdr);
|
||||
+
|
||||
+ if (rv >= 0)
|
||||
+ VIR_FREE(msg);
|
||||
|
||||
+ return rv;
|
||||
|
||||
xdr_error:
|
||||
/* Seriously bad stuff happened, so we'll kill off this client
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,46 +0,0 @@
|
||||
From ba585ed6cff624c6c0f1f9801382fd6846466ee0 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 17 Sep 2009 15:31:08 +0100
|
||||
Subject: [PATCH] Fix net/disk hot-unplug segfault
|
||||
|
||||
When we hot-unplug the last device, we're currently double-freeing
|
||||
the device definition.
|
||||
|
||||
Reported by Michal Nowak here:
|
||||
|
||||
https://bugzilla.redhat.com/523953
|
||||
|
||||
* src/qemu_driver.c: fix double free
|
||||
|
||||
(cherry-picked from commit 8881ae1bf8783006777429403cc543c33187175d)
|
||||
|
||||
Fedora-patch: libvirt-fix-net-hotunplug-double-free.patch
|
||||
---
|
||||
src/qemu_driver.c | 4 ++--
|
||||
1 files changed, 2 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index a65334f..de31581 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -5998,7 +5998,7 @@ try_command:
|
||||
/* ignore, harmless */
|
||||
}
|
||||
} else {
|
||||
- VIR_FREE(vm->def->disks[0]);
|
||||
+ VIR_FREE(vm->def->disks);
|
||||
vm->def->ndisks = 0;
|
||||
}
|
||||
virDomainDiskDefFree(detach);
|
||||
@@ -6100,7 +6100,7 @@ qemudDomainDetachNetDevice(virConnectPtr conn,
|
||||
/* ignore, harmless */
|
||||
}
|
||||
} else {
|
||||
- VIR_FREE(vm->def->nets[0]);
|
||||
+ VIR_FREE(vm->def->nets);
|
||||
vm->def->nnets = 0;
|
||||
}
|
||||
virDomainNetDefFree(detach);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,50 +0,0 @@
|
||||
From 17831d20051f8de8f1f7d661e8a23f4fe67c2153 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 17 Sep 2009 15:32:45 +0100
|
||||
Subject: [PATCH] Fix leak in PCI hostdev hot-unplug
|
||||
|
||||
* src/qemu_driver.c: sync the hostdev hot-unplug code with the disk/net
|
||||
code.
|
||||
|
||||
(cherry-picked from commit a70da51ff76ed860bfc0cdee2e1d556da997c557)
|
||||
|
||||
Fedora-patch: libvirt-fix-pci-hostdev-hotunplug-leak.patch
|
||||
---
|
||||
src/qemu_driver.c | 20 +++++++++++++-------
|
||||
1 files changed, 13 insertions(+), 7 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index de31581..2ddcdc0 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -6206,14 +6206,20 @@ static int qemudDomainDetachHostPciDevice(virConnectPtr conn,
|
||||
pciFreeDevice(conn, pci);
|
||||
}
|
||||
|
||||
- if (i != --vm->def->nhostdevs)
|
||||
- memmove(&vm->def->hostdevs[i],
|
||||
- &vm->def->hostdevs[i+1],
|
||||
- sizeof(*vm->def->hostdevs) * (vm->def->nhostdevs-i));
|
||||
- if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs) < 0) {
|
||||
- virReportOOMError(conn);
|
||||
- ret = -1;
|
||||
+ if (vm->def->nhostdevs > 1) {
|
||||
+ memmove(vm->def->hostdevs + i,
|
||||
+ vm->def->hostdevs + i + 1,
|
||||
+ sizeof(*vm->def->hostdevs) *
|
||||
+ (vm->def->nhostdevs - (i + 1)));
|
||||
+ vm->def->nhostdevs--;
|
||||
+ if (VIR_REALLOC_N(vm->def->hostdevs, vm->def->nhostdevs) < 0) {
|
||||
+ /* ignore, harmless */
|
||||
+ }
|
||||
+ } else {
|
||||
+ VIR_FREE(vm->def->hostdevs);
|
||||
+ vm->def->nhostdevs = 0;
|
||||
}
|
||||
+ virDomainHostdevDefFree(detach);
|
||||
|
||||
return ret;
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,53 +0,0 @@
|
||||
From f1be5a4714e194a84840343e0937fe62463a18dc Mon Sep 17 00:00:00 2001
|
||||
From: Charles Duffy <Charles_Duffy@dell.com>
|
||||
Date: Fri, 18 Sep 2009 11:32:35 -0500
|
||||
Subject: [PATCH] Prevent attempt to call cat -c during virDomainSave to raw
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-raw-format-save.patch
|
||||
---
|
||||
src/qemu_driver.c | 28 ++++++++++++++++++----------
|
||||
1 files changed, 18 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 2ddcdc0..7c7b985 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -3905,17 +3905,25 @@ static int qemudDomainSave(virDomainPtr dom,
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
- if (prog == NULL) {
|
||||
- qemudReportError(dom->conn, dom, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
- _("Invalid compress format %d"), header.compressed);
|
||||
- goto cleanup;
|
||||
- }
|
||||
+ {
|
||||
+ const char *prog = qemudSaveCompressionTypeToString(header.compressed);
|
||||
+ const char *args;
|
||||
|
||||
- if (STREQ (prog, "raw"))
|
||||
- prog = "cat";
|
||||
- internalret = virAsprintf(&command, "migrate \"exec:"
|
||||
- "%s -c >> '%s' 2>/dev/null\"", prog, safe_path);
|
||||
+ if (prog == NULL) {
|
||||
+ qemudReportError(dom->conn, dom, NULL, VIR_ERR_INTERNAL_ERROR,
|
||||
+ _("Invalid compress format %d"), header.compressed);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ if (STREQ (prog, "raw")) {
|
||||
+ prog = "cat";
|
||||
+ args = "";
|
||||
+ } else {
|
||||
+ args = "-c";
|
||||
+ }
|
||||
+ internalret = virAsprintf(&command, "migrate \"exec:"
|
||||
+ "%s %s >> '%s' 2>/dev/null\"", prog, args, safe_path);
|
||||
+ }
|
||||
|
||||
if (internalret < 0) {
|
||||
virReportOOMError(dom->conn);
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,38 +0,0 @@
|
||||
From 0b846a30468a6b4586407f020ccde7bb51afaf98 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 20:03:50 +0100
|
||||
Subject: [PATCH] Fix QEMU restore from file in raw format
|
||||
|
||||
The logic for running the decompression programs was broken in
|
||||
commit f238709304f9f6c57204cdd943e542cbae38fa5f, so that for
|
||||
non-raw formats the decompression program was never run, and
|
||||
for raw formats, it tried to exec an argv[] with initial NULL
|
||||
in the program name.
|
||||
|
||||
* src/qemu/qemu_driver.c: Fix logic in runing decompression program
|
||||
|
||||
(cherry picked from commit 74b379cbd5ba9f472a3a2d5710e497966b1a3a37)
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-restore-from-raw1.patch
|
||||
---
|
||||
src/qemu_driver.c | 3 +--
|
||||
1 files changed, 1 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_driver.c b/src/qemu_driver.c
|
||||
index 550a59c..0ce403c 100644
|
||||
--- a/src/qemu_driver.c
|
||||
+++ b/src/qemu_driver.c
|
||||
@@ -4541,9 +4541,8 @@ static int qemudDomainRestore(virConnectPtr conn,
|
||||
goto cleanup;
|
||||
}
|
||||
|
||||
- if (header.compressed != QEMUD_SAVE_FORMAT_RAW)
|
||||
+ if (header.compressed != QEMUD_SAVE_FORMAT_RAW) {
|
||||
intermediate_argv[0] = prog;
|
||||
- else {
|
||||
intermediatefd = fd;
|
||||
fd = -1;
|
||||
if (virExec(conn, intermediate_argv, NULL, NULL,
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,120 +0,0 @@
|
||||
From 57d7cc602d14c6b50e2826e427a5de124e479f95 Mon Sep 17 00:00:00 2001
|
||||
From: Daniel P. Berrange <berrange@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 20:32:33 +0100
|
||||
Subject: [PATCH] Fix virFileReadLimFD/virFileReadAll to handle EINTR
|
||||
|
||||
The fread_file_lim() function uses fread() but never handles
|
||||
EINTR results, causing unexpected failures when reading QEMU
|
||||
help arg info. It was unneccessarily using FILE * instead
|
||||
of plain UNIX file handles, which prevented use of saferead()
|
||||
|
||||
* src/util/util.c: Switch fread_file_lim over to use saferead
|
||||
instead of fread, remove FILE * use, and rename
|
||||
|
||||
(cherry picked from commit 11a36d956cb8a5e439e535bff3e0cfce50a64bca)
|
||||
|
||||
Fedora-patch: libvirt-fix-qemu-restore-from-raw2.patch
|
||||
---
|
||||
src/util.c | 45 ++++++++++++---------------------------------
|
||||
1 files changed, 12 insertions(+), 33 deletions(-)
|
||||
|
||||
diff --git a/src/util.c b/src/util.c
|
||||
index 1878e33..7bc3a66 100644
|
||||
--- a/src/util.c
|
||||
+++ b/src/util.c
|
||||
@@ -887,7 +887,7 @@ virExec(virConnectPtr conn,
|
||||
number of bytes. If the length of the input is <= max_len, and
|
||||
upon error while reading that data, it works just like fread_file. */
|
||||
static char *
|
||||
-fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
+saferead_lim (int fd, size_t max_len, size_t *length)
|
||||
{
|
||||
char *buf = NULL;
|
||||
size_t alloc = 0;
|
||||
@@ -895,8 +895,8 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
int save_errno;
|
||||
|
||||
for (;;) {
|
||||
- size_t count;
|
||||
- size_t requested;
|
||||
+ int count;
|
||||
+ int requested;
|
||||
|
||||
if (size + BUFSIZ + 1 > alloc) {
|
||||
alloc += alloc / 2;
|
||||
@@ -912,12 +912,12 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
/* Ensure that (size + requested <= max_len); */
|
||||
requested = MIN (size < max_len ? max_len - size : 0,
|
||||
alloc - size - 1);
|
||||
- count = fread (buf + size, 1, requested, stream);
|
||||
+ count = saferead (fd, buf + size, requested);
|
||||
size += count;
|
||||
|
||||
if (count != requested || requested == 0) {
|
||||
save_errno = errno;
|
||||
- if (ferror (stream))
|
||||
+ if (count < 0)
|
||||
break;
|
||||
buf[size] = '\0';
|
||||
*length = size;
|
||||
@@ -930,12 +930,12 @@ fread_file_lim (FILE *stream, size_t max_len, size_t *length)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
-/* A wrapper around fread_file_lim that maps a failure due to
|
||||
+/* A wrapper around saferead_lim that maps a failure due to
|
||||
exceeding the maximum size limitation to EOVERFLOW. */
|
||||
-static int virFileReadLimFP(FILE *fp, int maxlen, char **buf)
|
||||
+int virFileReadLimFD(int fd, int maxlen, char **buf)
|
||||
{
|
||||
size_t len;
|
||||
- char *s = fread_file_lim (fp, maxlen+1, &len);
|
||||
+ char *s = saferead_lim (fd, maxlen+1, &len);
|
||||
if (s == NULL)
|
||||
return -1;
|
||||
if (len > maxlen || (int)len != len) {
|
||||
@@ -949,37 +949,16 @@ static int virFileReadLimFP(FILE *fp, int maxlen, char **buf)
|
||||
return len;
|
||||
}
|
||||
|
||||
-/* Like virFileReadLimFP, but use a file descriptor rather than a FILE*. */
|
||||
-int virFileReadLimFD(int fd_arg, int maxlen, char **buf)
|
||||
-{
|
||||
- int fd = dup (fd_arg);
|
||||
- if (fd >= 0) {
|
||||
- FILE *fp = fdopen (fd, "r");
|
||||
- if (fp) {
|
||||
- int len = virFileReadLimFP (fp, maxlen, buf);
|
||||
- int saved_errno = errno;
|
||||
- fclose (fp);
|
||||
- errno = saved_errno;
|
||||
- return len;
|
||||
- } else {
|
||||
- int saved_errno = errno;
|
||||
- close (fd);
|
||||
- errno = saved_errno;
|
||||
- }
|
||||
- }
|
||||
- return -1;
|
||||
-}
|
||||
-
|
||||
int virFileReadAll(const char *path, int maxlen, char **buf)
|
||||
{
|
||||
- FILE *fh = fopen(path, "r");
|
||||
- if (fh == NULL) {
|
||||
+ int fd = open(path, O_RDONLY);
|
||||
+ if (fd < 0) {
|
||||
virReportSystemError(NULL, errno, _("Failed to open file '%s'"), path);
|
||||
return -1;
|
||||
}
|
||||
|
||||
- int len = virFileReadLimFP (fh, maxlen, buf);
|
||||
- fclose(fh);
|
||||
+ int len = virFileReadLimFD(fd, maxlen, buf);
|
||||
+ close(fd);
|
||||
if (len < 0) {
|
||||
virReportSystemError(NULL, errno, _("Failed to read file '%s'"), path);
|
||||
return -1;
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,41 +0,0 @@
|
||||
From 6b12148864cf6a1d22a2cf4e0e9c48e9946331cb Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Wed, 30 Sep 2009 18:37:03 +0100
|
||||
Subject: [PATCH] Fix USB device re-labelling
|
||||
|
||||
A simple misplaced break out of a switch results in:
|
||||
|
||||
libvir: error : Failed to open file '/sys/bus/pci/devices/0000:00:54c./vendor': No such file or directory
|
||||
libvir: error : Failed to open file '/sys/bus/pci/devices/0000:00:54c./device': No such file or directory
|
||||
libvir: error : this function is not supported by the hypervisor: Failed to read product/vendor ID for 0000:00:54c.
|
||||
|
||||
when trying to passthrough a USB host device to qemu.
|
||||
|
||||
* src/security_selinux.c: fix a switch/break thinko
|
||||
|
||||
Fedora-patch: libvirt-fix-usb-device-passthrough.patch
|
||||
---
|
||||
src/security_selinux.c | 3 +--
|
||||
1 files changed, 1 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/src/security_selinux.c b/src/security_selinux.c
|
||||
index bc295b1..b4dc153 100644
|
||||
--- a/src/security_selinux.c
|
||||
+++ b/src/security_selinux.c
|
||||
@@ -464,12 +464,11 @@ SELinuxSetSecurityHostdevLabel(virConnectPtr conn,
|
||||
|
||||
ret = usbDeviceFileIterate(conn, usb, SELinuxSetSecurityUSBLabel, vm);
|
||||
usbFreeDevice(conn, usb);
|
||||
-
|
||||
- break;
|
||||
} else {
|
||||
/* XXX deal with product/vendor better */
|
||||
ret = 0;
|
||||
}
|
||||
+ break;
|
||||
}
|
||||
|
||||
case VIR_DOMAIN_HOSTDEV_SUBSYS_TYPE_PCI: {
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,103 +0,0 @@
|
||||
From cab81502320d97dac4c5c12e7496f30896709c49 Mon Sep 17 00:00:00 2001
|
||||
From: Matthias Bolte <matthias.bolte@googlemail.com>
|
||||
Date: Tue, 22 Sep 2009 15:12:48 +0200
|
||||
Subject: [PATCH] Fix xen driver refcounting.
|
||||
|
||||
The commit cb51aa48a777ddae6997faa9f28350cb62655ffd "Fix up connection
|
||||
reference counting." changed the driver closing and virConnectPtr
|
||||
unref-logic in virConnectClose().
|
||||
|
||||
Before this commit virConnectClose() closed all drivers of the given
|
||||
virConnectPtr and virUnrefConnect()'ed it afterwards. After this
|
||||
commit the driver-closing is done in virUnrefConnect() if and only if
|
||||
the ref-count of the virConnectPtr dropped to zero.
|
||||
|
||||
This change in execution order leads to a virConnectPtr leak, at least
|
||||
for connections to Xen.
|
||||
|
||||
The relevant call sequences:
|
||||
|
||||
virConnectOpen() -> xenUnifiedOpen() ...
|
||||
|
||||
... xenInotifyOpen() -> virConnectRef(conn)
|
||||
|
||||
... xenStoreOpen() -> xenStoreAddWatch() -> conn->refs++
|
||||
|
||||
virConnectClose() -> xenUnifiedClose() ...
|
||||
|
||||
... xenInotifyClose() -> virUnrefConnect(conn)
|
||||
|
||||
... xenStoreClose() -> xenStoreRemoveWatch() -> virUnrefConnect(conn)
|
||||
|
||||
Before the commit this additional virConnectRef/virUnrefConnect calls
|
||||
where no problem, because virConnectClose() closed the drivers
|
||||
explicitly and the additional refs added by the Xen subdrivers were
|
||||
removed properly. After the commit this additional refs result in a
|
||||
virConnectPtr leak (including a leak of the hypercall file handle;
|
||||
that's how I noticed this problem), because now the drivers are only
|
||||
close if and only if the ref-count drops to zero, but this cannot
|
||||
happen anymore, because the additional refs from the Xen subdrivers
|
||||
would only be removed if the drivers get closed, but that doesn't
|
||||
happen because the ref-count cannot drop to zero.
|
||||
|
||||
The fix for this problem is simple: remove the
|
||||
virConnectRef/virUnrefConnect calls from the Xen subdrivers (see
|
||||
attached patch). Maybe someone could explain why the Xen Inotify and
|
||||
Xen Store driver do this extra ref-counting, but none of the other Xen
|
||||
subdrivers. It seems unnecessary to me and can be removed without
|
||||
problems.
|
||||
|
||||
Signed-off-by: Chris Lalancette <clalance@redhat.com>
|
||||
|
||||
(cherry picked from commit 6ed7374c5a6c6a2b1b1801d7d041dc7f09748592)
|
||||
|
||||
Fedora-patch: libvirt-fix-xen-driver-refcounting.patch
|
||||
---
|
||||
src/xen_inotify.c | 2 --
|
||||
src/xs_internal.c | 3 ---
|
||||
2 files changed, 0 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/src/xen_inotify.c b/src/xen_inotify.c
|
||||
index e312b9e..ecaefaf 100644
|
||||
--- a/src/xen_inotify.c
|
||||
+++ b/src/xen_inotify.c
|
||||
@@ -463,7 +463,6 @@ xenInotifyOpen(virConnectPtr conn ATTRIBUTE_UNUSED,
|
||||
DEBUG0("Failed to add inotify handle, disabling events");
|
||||
}
|
||||
|
||||
- virConnectRef(conn);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -486,7 +485,6 @@ xenInotifyClose(virConnectPtr conn)
|
||||
if (priv->inotifyWatch != -1)
|
||||
virEventRemoveHandle(priv->inotifyWatch);
|
||||
close(priv->inotifyFD);
|
||||
- virUnrefConnect(conn);
|
||||
|
||||
return 0;
|
||||
}
|
||||
diff --git a/src/xs_internal.c b/src/xs_internal.c
|
||||
index 1f54b1f..a18dcad 100644
|
||||
--- a/src/xs_internal.c
|
||||
+++ b/src/xs_internal.c
|
||||
@@ -1139,8 +1139,6 @@ int xenStoreAddWatch(virConnectPtr conn,
|
||||
list->watches[n] = watch;
|
||||
list->count++;
|
||||
|
||||
- conn->refs++;
|
||||
-
|
||||
return xs_watch(priv->xshandle, watch->path, watch->token);
|
||||
}
|
||||
|
||||
@@ -1190,7 +1188,6 @@ int xenStoreRemoveWatch(virConnectPtr conn,
|
||||
; /* Failure to reduce memory allocation isn't fatal */
|
||||
}
|
||||
list->count--;
|
||||
- virUnrefConnect(conn);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,31 +0,0 @@
|
||||
From 918724aa76982224437384d712c182c332fa5ef9 Mon Sep 17 00:00:00 2001
|
||||
From: Dan Kenigsberg <danken@redhat.com>
|
||||
Date: Wed, 21 Oct 2009 13:56:04 +0200
|
||||
Subject: [PATCH] Do not log rotate very small logs
|
||||
|
||||
Without this, after few weeks without use, each defined domain grows a
|
||||
tail of empty gzipped logs, instead of keeping just the last log of
|
||||
interest.
|
||||
|
||||
* daemon/libvirtd.logrotate.in: only rotate when the log is over 100 KBytes
|
||||
|
||||
(cherry picked from commit b03fe2d0aefb57a096a102bf23375f0a167ca189)
|
||||
|
||||
Fedora-patch: libvirt-logrotate-avoid-compressing-small-logs.patch
|
||||
---
|
||||
qemud/libvirtd.logrotate.in | 1 +
|
||||
1 files changed, 1 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/qemud/libvirtd.logrotate.in b/qemud/libvirtd.logrotate.in
|
||||
index 093651c..0c51fd3 100644
|
||||
--- a/qemud/libvirtd.logrotate.in
|
||||
+++ b/qemud/libvirtd.logrotate.in
|
||||
@@ -5,4 +5,5 @@
|
||||
compress
|
||||
delaycompress
|
||||
copytruncate
|
||||
+ minsize 100k
|
||||
}
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,54 +0,0 @@
|
||||
From b7e3ac4f23befe67518b57e34691c301820a436c Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Tue, 6 Oct 2009 12:33:17 +0100
|
||||
Subject: [PATCH] Create /var/log/libvirt/{lxc,uml} dirs
|
||||
|
||||
Otherwise logrotate barfs:
|
||||
|
||||
error: error accessing /var/log/libvirt/uml: No such file or directory
|
||||
error: libvirtd:1 glob failed for /var/log/libvirt/uml/*.log
|
||||
error: found error in /var/log/libvirt/qemu/*.log /var/log/libvirt/uml/*.log /var/log/libvirt/lxc/*.log , skipping
|
||||
|
||||
* qemud/Makefile.am: always create /var/log/libvirt/{lxc,uml} when
|
||||
installing the logrotate conf; not ideal, but easier than making
|
||||
the logrotate conf depend on which drivers are enabled
|
||||
|
||||
Fedora-patch: libvirt-logrotate-create-lxc-uml-dirs.patch
|
||||
---
|
||||
qemud/Makefile.am | 6 ++++--
|
||||
1 files changed, 4 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/qemud/Makefile.am b/qemud/Makefile.am
|
||||
index 3d143da..a7f4bdf 100644
|
||||
--- a/qemud/Makefile.am
|
||||
+++ b/qemud/Makefile.am
|
||||
@@ -176,7 +176,7 @@ install-data-local: install-init install-data-sasl install-data-polkit \
|
||||
test -e $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml || \
|
||||
ln -s ../default.xml \
|
||||
$(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
- mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/run/libvirt
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/lib/libvirt
|
||||
|
||||
@@ -184,7 +184,7 @@ uninstall-local:: uninstall-init uninstall-data-sasl install-data-polkit
|
||||
rm -f $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart/default.xml
|
||||
rm -f $(DESTDIR)$(sysconfdir)/$(default_xml_dest)
|
||||
rmdir $(DESTDIR)$(sysconfdir)/libvirt/qemu/networks/autostart || :
|
||||
- rmdir $(DESTDIR)$(localstatedir)/log/libvirt/qemu || :
|
||||
+ rmdir $(DESTDIR)$(localstatedir)/log/libvirt || :
|
||||
rmdir $(DESTDIR)$(localstatedir)/run/libvirt || :
|
||||
rmdir $(DESTDIR)$(localstatedir)/lib/libvirt || :
|
||||
|
||||
@@ -240,6 +240,8 @@ libvirtd.logrotate: libvirtd.logrotate.in
|
||||
|
||||
install-logrotate: libvirtd.logrotate
|
||||
mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/qemu/
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/lxc/
|
||||
+ mkdir -p $(DESTDIR)$(localstatedir)/log/libvirt/uml/
|
||||
mkdir -p $(DESTDIR)$(sysconfdir)/logrotate.d/
|
||||
$(INSTALL_DATA) $< $(DESTDIR)$(sysconfdir)/logrotate.d/libvirtd
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,32 +0,0 @@
|
||||
From ba3bc9b22a21b8e9e110166c98be70e2ad6469cb Mon Sep 17 00:00:00 2001
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Tue, 13 Oct 2009 11:31:27 -0400
|
||||
Subject: [PATCH] network: Fix printing XML 'delay' attribute
|
||||
|
||||
When specifying bridge delay via network XML define, we were looking for
|
||||
the 'delay' attribute, but would dump the value as 'forwardDelay'. Have
|
||||
the output match the expected input (and schema).
|
||||
|
||||
(cherry picked from commit 3b13aa3db37bf5a692bccfa015a01999043e797b)
|
||||
|
||||
Fedora-patch: libvirt-network-delay-attribute-formatting.patch
|
||||
---
|
||||
src/network_conf.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/network_conf.c b/src/network_conf.c
|
||||
index 3764bb4..f75c457 100644
|
||||
--- a/src/network_conf.c
|
||||
+++ b/src/network_conf.c
|
||||
@@ -587,7 +587,7 @@ char *virNetworkDefFormat(virConnectPtr conn,
|
||||
virBufferAddLit(&buf, " <bridge");
|
||||
if (def->bridge)
|
||||
virBufferEscapeString(&buf, " name='%s'", def->bridge);
|
||||
- virBufferVSprintf(&buf, " stp='%s' forwardDelay='%ld' />\n",
|
||||
+ virBufferVSprintf(&buf, " stp='%s' delay='%ld' />\n",
|
||||
def->stp ? "on" : "off",
|
||||
def->delay);
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,177 +0,0 @@
|
||||
From d7722ed1cb04aa8a7b9fbf880882841867b69ab0 Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Mon, 12 Oct 2009 10:52:13 +0100
|
||||
Subject: [PATCH] Take domain type into account when looking up default machine
|
||||
|
||||
If one has e.g.
|
||||
|
||||
<guest>
|
||||
<os_type>hvm</os_type>
|
||||
<arch name='x86_64'>
|
||||
<wordsize>64</wordsize>
|
||||
<emulator>/usr/bin/qemu-system-x86_64</emulator>
|
||||
<machine>pc-0.11</machine>
|
||||
<machine canonical='pc-0.11'>pc</machine>
|
||||
<machine>pc-0.10</machine>
|
||||
<machine>isapc</machine>
|
||||
<domain type='qemu'>
|
||||
</domain>
|
||||
<domain type='kvm'>
|
||||
<emulator>/usr/bin/kvm</emulator>
|
||||
<machine>pc</machine>
|
||||
<machine>isapc</machine>
|
||||
</domain>
|
||||
</arch>
|
||||
</guest>
|
||||
|
||||
and start a guest with:
|
||||
|
||||
<domain type='kvm'>
|
||||
...
|
||||
<os>
|
||||
<type arch='x86_64'>hvm</type>
|
||||
...
|
||||
</os>
|
||||
</domain>
|
||||
|
||||
then the default machine type should be 'pc' and not 'pc-0.11'
|
||||
|
||||
Issue was reported by Anton Protopopov.
|
||||
|
||||
* src/capabilities.[ch]: pass the domain type to
|
||||
virCapabilitiesDefaultGuestArch() and use it to look up the default
|
||||
machine type from a specific guest domain if needed.
|
||||
|
||||
* src/conf/domain_conf.c, src/xen/xm_internal.c: update
|
||||
|
||||
* tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml: update
|
||||
the domain type to 'kvm' and remove the machine type to check
|
||||
that the default gets looked up correctly
|
||||
|
||||
(cherry picked from commit 73c901a8075c09203545fc81164c1e5f11c67c89)
|
||||
|
||||
Fedora-patch: libvirt-qemu-machine-type-fixes1.patch
|
||||
---
|
||||
src/capabilities.c | 31 ++++++++++++++++---
|
||||
src/capabilities.h | 3 +-
|
||||
src/domain_conf.c | 3 +-
|
||||
src/xm_internal.c | 3 +-
|
||||
.../qemuxml2argv-machine-aliases2.xml | 4 +-
|
||||
5 files changed, 34 insertions(+), 10 deletions(-)
|
||||
|
||||
diff --git a/src/capabilities.c b/src/capabilities.c
|
||||
index 38fe7fc..6ebddf5 100644
|
||||
--- a/src/capabilities.c
|
||||
+++ b/src/capabilities.c
|
||||
@@ -549,22 +549,43 @@ virCapabilitiesDefaultGuestArch(virCapsPtr caps,
|
||||
* @caps: capabilities to query
|
||||
* @ostype: OS type to search for
|
||||
* @arch: architecture to search for
|
||||
+ * @domain: domain type to search for
|
||||
*
|
||||
* Returns the first machine variant associated with
|
||||
- * the requested operating system type and architecture
|
||||
+ * the requested operating system type, architecture
|
||||
+ * and domain type
|
||||
*/
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestMachine(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
- const char *arch)
|
||||
+ const char *arch,
|
||||
+ const char *domain)
|
||||
{
|
||||
int i;
|
||||
+
|
||||
for (i = 0 ; i < caps->nguests ; i++) {
|
||||
- if (STREQ(caps->guests[i]->ostype, ostype) &&
|
||||
- STREQ(caps->guests[i]->arch.name, arch) &&
|
||||
- caps->guests[i]->arch.defaultInfo.nmachines)
|
||||
+ virCapsGuestPtr guest = caps->guests[i];
|
||||
+ int j;
|
||||
+
|
||||
+ if (!STREQ(guest->ostype, ostype) || !STREQ(guest->arch.name, arch))
|
||||
+ continue;
|
||||
+
|
||||
+ for (j = 0; j < guest->arch.ndomains; j++) {
|
||||
+ virCapsGuestDomainPtr dom= guest->arch.domains[j];
|
||||
+
|
||||
+ if (!STREQ(dom->type, domain))
|
||||
+ continue;
|
||||
+
|
||||
+ if (!dom->info.nmachines)
|
||||
+ break;
|
||||
+
|
||||
+ return dom->info.machines[0]->name;
|
||||
+ }
|
||||
+
|
||||
+ if (guest->arch.defaultInfo.nmachines)
|
||||
return caps->guests[i]->arch.defaultInfo.machines[0]->name;
|
||||
}
|
||||
+
|
||||
return NULL;
|
||||
}
|
||||
|
||||
diff --git a/src/capabilities.h b/src/capabilities.h
|
||||
index b958d95..2f24605 100644
|
||||
--- a/src/capabilities.h
|
||||
+++ b/src/capabilities.h
|
||||
@@ -207,7 +207,8 @@ virCapabilitiesDefaultGuestArch(virCapsPtr caps,
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestMachine(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
- const char *arch);
|
||||
+ const char *arch,
|
||||
+ const char *domain);
|
||||
extern const char *
|
||||
virCapabilitiesDefaultGuestEmulator(virCapsPtr caps,
|
||||
const char *ostype,
|
||||
diff --git a/src/domain_conf.c b/src/domain_conf.c
|
||||
index 5ae0775..c424c67 100644
|
||||
--- a/src/domain_conf.c
|
||||
+++ b/src/domain_conf.c
|
||||
@@ -2664,7 +2664,8 @@ static virDomainDefPtr virDomainDefParseXML(virConnectPtr conn,
|
||||
if (!def->os.machine) {
|
||||
const char *defaultMachine = virCapabilitiesDefaultGuestMachine(caps,
|
||||
def->os.type,
|
||||
- def->os.arch);
|
||||
+ def->os.arch,
|
||||
+ virDomainVirtTypeToString(def->virtType));
|
||||
if (defaultMachine != NULL) {
|
||||
if (!(def->os.machine = strdup(defaultMachine))) {
|
||||
virReportOOMError(conn);
|
||||
diff --git a/src/xm_internal.c b/src/xm_internal.c
|
||||
index de3aca9..6d351d4 100644
|
||||
--- a/src/xm_internal.c
|
||||
+++ b/src/xm_internal.c
|
||||
@@ -720,7 +720,8 @@ xenXMDomainConfigParse(virConnectPtr conn, virConfPtr conf) {
|
||||
|
||||
defaultMachine = virCapabilitiesDefaultGuestMachine(priv->caps,
|
||||
def->os.type,
|
||||
- def->os.arch);
|
||||
+ def->os.arch,
|
||||
+ virDomainVirtTypeToString(def->virtType));
|
||||
if (defaultMachine != NULL) {
|
||||
if (!(def->os.machine = strdup(defaultMachine)))
|
||||
goto no_memory;
|
||||
diff --git a/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml b/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
index 6f62243..a2c6254 100644
|
||||
--- a/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
+++ b/tests/qemuxml2argvdata/qemuxml2argv-machine-aliases2.xml
|
||||
@@ -1,11 +1,11 @@
|
||||
-<domain type='qemu'>
|
||||
+<domain type='kvm'>
|
||||
<name>QEMUGuest1</name>
|
||||
<uuid>c7a5fdbd-edaf-9455-926a-d65c16db1809</uuid>
|
||||
<memory>219200</memory>
|
||||
<currentMemory>219200</currentMemory>
|
||||
<vcpu>1</vcpu>
|
||||
<os>
|
||||
- <type arch='x86_64' machine='pc'>hvm</type>
|
||||
+ <type arch='x86_64'>hvm</type>
|
||||
<boot dev='hd'/>
|
||||
</os>
|
||||
<clock offset='utc'/>
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,42 +0,0 @@
|
||||
From bb64cc4cbe5d3c69057f63be2c1acaca72038e5a Mon Sep 17 00:00:00 2001
|
||||
From: Mark McLoughlin <markmc@redhat.com>
|
||||
Date: Thu, 15 Oct 2009 12:09:17 +0100
|
||||
Subject: [PATCH] Don't copy old machines from a domain which has none
|
||||
|
||||
If the the qemu and kvm binaries are the same, we don't include machine
|
||||
types in the kvm domain info.
|
||||
|
||||
However, the code which refreshes the machine types info from the
|
||||
previous capabilities structure first looks at the kvm domain's info,
|
||||
finds it matches and then copies the empty machine types list over
|
||||
for the top-level qemu domain.
|
||||
|
||||
That doesn't make sense, we shouldn't copy an empty machin types list.
|
||||
|
||||
* src/qemu/qemu_conf.c: qemudGetOldMachinesFromInfo(): don't copy an
|
||||
empty machine types list.
|
||||
|
||||
(cherry picked from commit 2210f8a3a8e2774ca4fb8b42e21899e5b85ca913)
|
||||
|
||||
Fedora-patch: libvirt-qemu-machine-type-fixes2.patch
|
||||
---
|
||||
src/qemu_conf.c | 3 +++
|
||||
1 files changed, 3 insertions(+), 0 deletions(-)
|
||||
|
||||
diff --git a/src/qemu_conf.c b/src/qemu_conf.c
|
||||
index 0dd0624..34a7fe1 100644
|
||||
--- a/src/qemu_conf.c
|
||||
+++ b/src/qemu_conf.c
|
||||
@@ -505,6 +505,9 @@ qemudGetOldMachinesFromInfo(virCapsGuestDomainInfoPtr info,
|
||||
virCapsGuestMachinePtr *list;
|
||||
int i;
|
||||
|
||||
+ if (!info->nmachines)
|
||||
+ return 0;
|
||||
+
|
||||
if (!info->emulator || !STREQ(emulator, info->emulator))
|
||||
return 0;
|
||||
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
@@ -1,30 +0,0 @@
|
||||
From a44bce591a8d746a4a00c8609cb0111c76271cab Mon Sep 17 00:00:00 2001
|
||||
From: Cole Robinson <crobinso@redhat.com>
|
||||
Date: Thu, 8 Oct 2009 18:05:36 -0400
|
||||
Subject: [PATCH] storage: Fix generating iscsi 'auth' xml
|
||||
|
||||
We were missing a closing tag, so the XML wasn't proper.
|
||||
|
||||
(cherry picked from commit 826cbac4591fd5929b497299a90d3a65226b2825)
|
||||
|
||||
Fedora-patch: libvirt-storage-iscsi-auth-xml-formatting.patch
|
||||
---
|
||||
src/storage_conf.c | 2 +-
|
||||
1 files changed, 1 insertions(+), 1 deletions(-)
|
||||
|
||||
diff --git a/src/storage_conf.c b/src/storage_conf.c
|
||||
index 788de15..1633aac 100644
|
||||
--- a/src/storage_conf.c
|
||||
+++ b/src/storage_conf.c
|
||||
@@ -799,7 +799,7 @@ virStoragePoolSourceFormat(virConnectPtr conn,
|
||||
|
||||
|
||||
if (src->authType == VIR_STORAGE_POOL_AUTH_CHAP)
|
||||
- virBufferVSprintf(buf," <auth type='chap' login='%s' passwd='%s'>\n",
|
||||
+ virBufferVSprintf(buf," <auth type='chap' login='%s' passwd='%s'/>\n",
|
||||
src->auth.chap.login,
|
||||
src->auth.chap.passwd);
|
||||
virBufferAddLit(buf," </source>\n");
|
||||
--
|
||||
1.6.2.5
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
+1878
-1072
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user