Pass the new virDomainBlockSetWriteThreshold() API and WRITE_THRESHOLD event across RPC. The event takes the bulk of the patch, but everything here is pretty mechanical and copies patterns from existing code. Yes, it is intentional that registration takes a single mandatory string (which can be either "vda" or path notation), while the reported event has two strings (one mandatory, for "vda"; the other optional for when path is available). I debated about splitting the event separately from the API for setting the threshold, in case we ever want to support setting a write threshold by overloading an existing API such as virDomainSetBlockIoTune(); but consensus on the design was that overloading existing API was not appropriate, and that no one is expecting to use this functionality without also being prepared to require the .so bump. * daemon/remote.c (remoteRelayDomainEventWriteThreshold): New function. * src/remote/remote_driver.c (remoteDomainBuildEventCallbackWriteThreshold): Likewise. * src/remote/remote_protocol.x (remote_domain_event_callback_write_threshold_msg) (remote_domain_block_set_write_threshold_args): New structs. * src/remote_protocol-structs: Update. Signed-off-by: Eric Blake <eblake@xxxxxxxxxx> --- daemon/remote.c | 53 ++++++++++++++++++++++++++++++++++++++++++-- src/remote/remote_driver.c | 35 +++++++++++++++++++++++++++++ src/remote/remote_protocol.x | 30 ++++++++++++++++++++++++- src/remote_protocol-structs | 16 +++++++++++++ 4 files changed, 131 insertions(+), 3 deletions(-) diff --git a/daemon/remote.c b/daemon/remote.c index 283ece2..457e220 100644 --- a/daemon/remote.c +++ b/daemon/remote.c @@ -1079,6 +1079,56 @@ remoteRelayDomainEventDeviceAdded(virConnectPtr conn, } +static int +remoteRelayDomainEventWriteThreshold(virConnectPtr conn, + virDomainPtr dom, + const char *disk, + const char *path, + unsigned long long threshold, + unsigned long long length, + void *opaque) +{ + daemonClientEventCallbackPtr callback = opaque; + remote_domain_event_callback_write_threshold_msg data; + char **path_p = NULL; + + if (callback->callbackID < 0 || + !remoteRelayDomainEventCheckACL(callback->client, conn, dom)) + return -1; + + VIR_DEBUG("Relaying domain write threshold event %s %d %s (%s) %llu %llu, " + "callback %d", dom->name, dom->id, + disk, NULLSTR(path), threshold, length, callback->callbackID); + + /* build return data */ + memset(&data, 0, sizeof(data)); + + if (VIR_STRDUP(data.disk, disk) < 0) + goto error; + if (path && + ((VIR_ALLOC(path_p) < 0) || + VIR_STRDUP(*path_p, path) < 0)) + goto error; + + make_nonnull_domain(&data.dom, dom); + data.callbackID = callback->callbackID; + data.path = path_p; + data.threshold = threshold; + data.length = length; + + remoteDispatchObjectEventSend(callback->client, remoteProgram, + REMOTE_PROC_DOMAIN_EVENT_CALLBACK_WRITE_THRESHOLD, + (xdrproc_t)xdr_remote_domain_event_callback_write_threshold_msg, + &data); + + return 0; + error: + VIR_FREE(data.disk); + VIR_FREE(data.path); + VIR_FREE(path_p); + return -1; +} + static virConnectDomainEventGenericCallback domainEventCallbacks[] = { @@ -1102,8 +1152,7 @@ static virConnectDomainEventGenericCallback domainEventCallbacks[] = { VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventTunable), VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventAgentLifecycle), VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventDeviceAdded), - /* TODO: Implement RPC support for this */ - VIR_DOMAIN_EVENT_CALLBACK(NULL), + VIR_DOMAIN_EVENT_CALLBACK(remoteRelayDomainEventWriteThreshold), }; verify(ARRAY_CARDINALITY(domainEventCallbacks) == VIR_DOMAIN_EVENT_ID_LAST); diff --git a/src/remote/remote_driver.c b/src/remote/remote_driver.c index 273799b..f0b1941 100644 --- a/src/remote/remote_driver.c +++ b/src/remote/remote_driver.c @@ -342,6 +342,12 @@ remoteDomainBuildEventCallbackAgentLifecycle(virNetClientProgramPtr prog, void *evdata, void *opaque); static void +remoteDomainBuildEventCallbackWriteThreshold(virNetClientProgramPtr prog, + virNetClientPtr client, + void *evdata, void *opaque); + + +static void remoteNetworkBuildEventLifecycle(virNetClientProgramPtr prog ATTRIBUTE_UNUSED, virNetClientPtr client ATTRIBUTE_UNUSED, void *evdata, void *opaque); @@ -504,6 +510,10 @@ static virNetClientProgramEvent remoteEvents[] = { remoteDomainBuildEventCallbackDeviceAdded, sizeof(remote_domain_event_callback_device_added_msg), (xdrproc_t)xdr_remote_domain_event_callback_device_added_msg }, + { REMOTE_PROC_DOMAIN_EVENT_CALLBACK_WRITE_THRESHOLD, + remoteDomainBuildEventCallbackWriteThreshold, + sizeof(remote_domain_event_callback_write_threshold_msg), + (xdrproc_t)xdr_remote_domain_event_callback_write_threshold_msg }, }; @@ -5518,6 +5528,30 @@ remoteDomainBuildEventCallbackAgentLifecycle(virNetClientProgramPtr prog ATTRIBU } static void +remoteDomainBuildEventCallbackWriteThreshold(virNetClientProgramPtr prog ATTRIBUTE_UNUSED, + virNetClientPtr client ATTRIBUTE_UNUSED, + void *evdata, void *opaque) +{ + virConnectPtr conn = opaque; + remote_domain_event_callback_write_threshold_msg *msg = evdata; + struct private_data *priv = conn->privateData; + virDomainPtr dom; + virObjectEventPtr event = NULL; + const char *path = msg->path ? *msg->path : NULL; + + if (!(dom = get_nonnull_domain(conn, msg->dom))) + return; + + event = virDomainEventWriteThresholdNewFromDom(dom, msg->disk, path, + msg->threshold, + msg->length); + + virObjectUnref(dom); + + remoteEventQueue(priv, event, msg->callbackID); +} + +static void remoteNetworkBuildEventLifecycle(virNetClientProgramPtr prog ATTRIBUTE_UNUSED, virNetClientPtr client ATTRIBUTE_UNUSED, void *evdata, void *opaque) @@ -8275,6 +8309,7 @@ static virHypervisorDriver hypervisor_driver = { .domainBlockResize = remoteDomainBlockResize, /* 0.9.8 */ .domainBlockStats = remoteDomainBlockStats, /* 0.3.2 */ .domainBlockStatsFlags = remoteDomainBlockStatsFlags, /* 0.9.5 */ + .domainBlockSetWriteThreshold = remoteDomainBlockSetWriteThreshold, /* 1.3.0 */ .domainInterfaceStats = remoteDomainInterfaceStats, /* 0.3.2 */ .domainSetInterfaceParameters = remoteDomainSetInterfaceParameters, /* 0.9.9 */ .domainGetInterfaceParameters = remoteDomainGetInterfaceParameters, /* 0.9.9 */ diff --git a/src/remote/remote_protocol.x b/src/remote/remote_protocol.x index 9f1be6b..0461319 100644 --- a/src/remote/remote_protocol.x +++ b/src/remote/remote_protocol.x @@ -3230,6 +3230,22 @@ struct remote_domain_set_user_password_args { unsigned int flags; }; +struct remote_domain_event_callback_write_threshold_msg { + int callbackID; + remote_nonnull_domain dom; + remote_nonnull_string disk; + remote_string path; + unsigned hyper threshold; + unsigned hyper length; +}; + +struct remote_domain_block_set_write_threshold_args { + remote_nonnull_domain dom; + remote_nonnull_string disk; + unsigned hyper threshold; + unsigned int flags; +}; + /*----- Protocol. -----*/ @@ -5696,5 +5712,17 @@ enum remote_procedure { * @generate:both * @acl: domain:set_password */ - REMOTE_PROC_DOMAIN_SET_USER_PASSWORD = 357 + REMOTE_PROC_DOMAIN_SET_USER_PASSWORD = 357, + + /** + * @generate: both + * @acl: none + */ + REMOTE_PROC_DOMAIN_EVENT_CALLBACK_WRITE_THRESHOLD = 358, + + /** + * @generate: both + * @acl: domain:block_write + */ + REMOTE_PROC_DOMAIN_BLOCK_SET_WRITE_THRESHOLD = 359 }; diff --git a/src/remote_protocol-structs b/src/remote_protocol-structs index 48c3bd8..bfa3d3c 100644 --- a/src/remote_protocol-structs +++ b/src/remote_protocol-structs @@ -2684,6 +2684,20 @@ struct remote_domain_set_user_password_args { remote_string password; u_int flags; }; +struct remote_domain_event_callback_write_threshold_msg { + int callbackID; + remote_nonnull_domain dom; + remote_nonnull_string disk; + remote_string path; + uint64_t threshold; + uint64_t length; +}; +struct remote_domain_block_set_write_threshold_args { + remote_nonnull_domain dom; + remote_nonnull_string disk; + uint64_t threshold; + u_int flags; +}; enum remote_procedure { REMOTE_PROC_CONNECT_OPEN = 1, REMOTE_PROC_CONNECT_CLOSE = 2, @@ -3042,4 +3056,6 @@ enum remote_procedure { REMOTE_PROC_DOMAIN_ADD_IOTHREAD = 355, REMOTE_PROC_DOMAIN_DEL_IOTHREAD = 356, REMOTE_PROC_DOMAIN_SET_USER_PASSWORD = 357, + REMOTE_PROC_DOMAIN_EVENT_CALLBACK_WRITE_THRESHOLD = 358, + REMOTE_PROC_DOMAIN_BLOCK_SET_WRITE_THRESHOLD = 359, }; -- 2.4.3 -- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list