On Wed, 2012-03-07 at 09:51 -0800, Sharad Mishra wrote:
Visual inspection looks good.
Need to apply and test
-Sharad
On Tue, 2012-03-06 at 14:55 -0300, Eduardo Lima (Etrunko) wrote:
> From: "Eduardo Lima (Etrunko)" <eblima(a)br.ibm.com>
>
> As it happens for Shutdown, the RequestStateChange method returns immediately
> with return code 0 (successful) even though the state change is still not
> completed.
>
> Change the current job implementation to support reboot as well. For this we
> need the libvirt domain events APIs and event loop implementation, which are
> only available in libvirt version 0.9.0 or newer.
>
> Signed-off-by: Eduardo Lima (Etrunko) <eblima(a)br.ibm.com>
> ---
> src/Virt_ComputerSystem.c | 90 ++++++++++++++++++++++++++++++++++++++-------
> 1 files changed, 76 insertions(+), 14 deletions(-)
>
> diff --git a/src/Virt_ComputerSystem.c b/src/Virt_ComputerSystem.c
> index 778809d..04584f3 100644
> --- a/src/Virt_ComputerSystem.c
> +++ b/src/Virt_ComputerSystem.c
> @@ -32,6 +32,7 @@
>
> #include <uuid.h>
> #include <libvirt/libvirt.h>
> +#include <libvirt/virterror.h>
>
> #include <libcmpiutil/libcmpiutil.h>
> #include <libcmpiutil/std_invokemethod.h>
> @@ -61,6 +62,8 @@ struct _state_change_job {
> uint16_t status; /* job status */
> };
>
> +static bool events_registered = false;
> +
> /* Set the "Name" property of an instance from a domain */
> static int set_name_from_dom(virDomainPtr dom, CMPIInstance *instance)
> {
> @@ -1203,14 +1206,12 @@ static CMPIStatus __state_change(const char *name,
> s = state_change_enable(dom, &info);
> else if (state == CIM_STATE_DISABLED)
> s = state_change_disable(dom, &info);
> - else if (state == CIM_STATE_SHUTDOWN)
> - s.rc = CIM_SVPC_RETURN_JOB_STARTED;
> else if (state == CIM_STATE_PAUSED)
> s = state_change_pause(dom, &info);
> - else if (state == CIM_STATE_REBOOT)
> - s = state_change_reboot(dom, &info);
> else if (state == CIM_STATE_RESET)
> s = state_change_reset(dom, &info);
> + else if (state == CIM_STATE_SHUTDOWN || state == CIM_STATE_REBOOT)
> + s.rc = CIM_SVPC_RETURN_JOB_STARTED;
> else
> cu_statusf(_BROKER, &s,
> CMPI_RC_ERR_NOT_SUPPORTED,
> @@ -1333,6 +1334,25 @@ static CMPIStatus create_state_change_job(const
CMPIObjectPath *ref,
> return s;
> }
>
> +static void state_change_reboot_cb(virConnectPtr conn,
> + virDomainPtr dom,
> + void *data)
> +{
> + state_change_job_t *job = (state_change_job_t *) data;
> + job->status = CIM_JOB_STATE_COMPLETED;
> +}
> +
> +static void state_change_shutdown_cb(virConnectPtr conn,
> + virDomainPtr dom,
> + int event,
> + int detail,
> + void *data)
> +{
> + state_change_job_t *job = (state_change_job_t *) data;
> + if (event == VIR_DOMAIN_EVENT_SHUTDOWN)
I don't see "VIR_DOMAIN_EVENT_SHUTDOWN" defined in libvirt.h.
-Sharad
> + job->status = CIM_JOB_STATE_COMPLETED;
> +}
> +
> static CMPI_THREAD_RETURN state_change_thread(void *data)
> {
> CMPIStatus s;
> @@ -1341,8 +1361,10 @@ static CMPI_THREAD_RETURN state_change_thread(void *data)
> virConnectPtr conn = NULL;
> virDomainPtr dom = NULL;
> virDomainInfo info;
> + int job_cb = -1;
>
> - if (job->dom_state != CIM_STATE_SHUTDOWN) {
> + if (job->dom_state != CIM_STATE_SHUTDOWN &&
> + job->dom_state != CIM_STATE_REBOOT) {
> CU_DEBUG("Unrecognized state '%d'",
job->dom_state);
> goto end;
> }
> @@ -1382,17 +1404,56 @@ static CMPI_THREAD_RETURN state_change_thread(void *data)
> goto out;
> }
>
> - s = state_change_shutdown(dom, &info);
> - if (s.rc != CMPI_RC_OK) {
> - CU_DEBUG("Unable to trigger domain shutdown:
'%s'",
> - CMGetCharPtr(s.msg));
> - goto out;
> + if (events_registered == false) {
> + events_registered = true;
> + virEventRegisterDefaultImpl();
> + }
> +
> + if (job->dom_state == CIM_STATE_REBOOT) {
> + job_cb = virConnectDomainEventRegisterAny(conn, NULL,
> + VIR_DOMAIN_EVENT_ID_REBOOT,
> + VIR_DOMAIN_EVENT_CALLBACK(state_change_reboot_cb),
> + job, NULL);
> +
> + if (job_cb == -1) {
> + CU_DEBUG("Unable to connect domain reboot
callback");
> + goto out;
> + }
> +
> + s = state_change_reboot(dom, &info);
> +
> + if (s.rc != CMPI_RC_OK) {
> + CU_DEBUG("Unable to trigger domain reboot:
'%s'",
> + CMGetCharPtr(s.msg));
> + goto out;
> + }
> + } else if (job->dom_state == CIM_STATE_SHUTDOWN) {
> + job_cb = virConnectDomainEventRegisterAny(conn, NULL,
> + VIR_DOMAIN_EVENT_ID_LIFECYCLE,
> +
VIR_DOMAIN_EVENT_CALLBACK(state_change_shutdown_cb),
> + job, NULL);
> +
> + if (job_cb == -1) {
> + CU_DEBUG("Unable to connect domain shutdown
callback");
> + goto out;
> + }
> +
> + s = state_change_shutdown(dom, &info);
> +
> + if (s.rc != CMPI_RC_OK) {
> + CU_DEBUG("Unable to trigger domain shutdown:
'%s'",
> + CMGetCharPtr(s.msg));
> + goto out;
> + }
> }
>
> /* Wait for operation (shutdown/reboot) to complete */
> - while (info.state != VIR_DOMAIN_SHUTOFF) {
> - usleep(100 * 1000);
> - virDomainGetInfo(dom, &info);
> + while (job->status == CIM_JOB_STATE_RUNNING) {
> + if (virEventRunDefaultImpl() < 0) {
> + virErrorPtr err = virGetLastError();
> + CU_DEBUG("Failed to run event loop: %s\n",
> + err && err->message ? err->message :
"Unknown error");
> + }
> }
>
> CU_DEBUG("Job completed");
> @@ -1405,6 +1466,8 @@ static CMPI_THREAD_RETURN state_change_thread(void *data)
> (CMPIValue *) "Completed", CMPI_chars);
> }
>
> + virConnectDomainEventDeregisterAny(conn, job_cb);
> +
> out:
> virDomainFree(dom);
> virConnectClose(conn);
> @@ -1412,7 +1475,6 @@ static CMPI_THREAD_RETURN state_change_thread(void *data)
> CBDetachThread(_BROKER, job->context);
> free(job->dom_name);
> free(job);
> -
> end:
> return NULL;
> }
_______________________________________________
Libvirt-cim mailing list
Libvirt-cim(a)redhat.com
https://www.redhat.com/mailman/listinfo/libvirt-cim