int shutdown_then_destroy_domain(const char *instanceId)
{
    time_t deadline = 0;
    int error = 0;

    for (boolean done = FALSE; (!done);) {

        virConnectPtr conn = lock_hypervisor_conn();
        if (conn == NULL) {
            LOGERROR("[%s] cannot connect to hypervisor to shut down instance\n", instanceId);
            return -1;
        }

        virDomainPtr dom = virDomainLookupByName(conn, instanceId);
        if (dom == NULL) {             // domain is gone, so we are done
            LOGTRACE("[%s] domain not found\n", instanceId);
            unlock_hypervisor_conn();
            break;
        }

        boolean do_destroy = FALSE;

        if (deadline == 0) {           // first time through the loop
            deadline = time(NULL) + SHUTDOWN_GRACE_PERIOD_SEC;

            // give OS a chance to shut down cleanly
            LOGDEBUG("shutting down instance\n");
            error = virDomainShutdown(dom);
            if (error) {
                do_destroy = TRUE;
            }

        } else if (time(NULL) < deadline) { // within grace period - check on domain
            int dom_status = virDomainIsActive(dom);
            LOGTRACE("domain status '%d'\n", dom_status);
            if (dom_status != 1)       // 1 if running, 0 if inactive, -1 on error
                done = TRUE;

        } else {                       // deadline exceeded
            do_destroy = TRUE;
        }

        if (do_destroy) {
            LOGDEBUG("destroying instance\n");
            error = virDomainDestroy(dom);
            done = TRUE;
        }

        virDomainFree(dom);
        unlock_hypervisor_conn();

        if (!done)
            sleep(2);                  // sleep outside the hypervisor lock
    }

    return error;
}
int shutdown_then_destroy_domain(const char *instanceId)
{
    time_t deadline = 0;
    int error = 0;

    for (boolean done = FALSE; (!done);) {

        virConnectPtr conn = lock_hypervisor_conn();
        if (conn == NULL) {
            LOGERROR("[%s] cannot connect to hypervisor to shut down instance\n", instanceId);
            return -1;
        }

        virDomainPtr dom = virDomainLookupByName(conn, instanceId);
        if (dom == NULL) {              
            LOGTRACE("[%s] domain not found\n", instanceId);
            unlock_hypervisor_conn();
            break;
        }

        boolean do_destroy = FALSE;

        if (deadline == 0) {            
            deadline = time(NULL) + SHUTDOWN_GRACE_PERIOD_SEC;

             
            LOGDEBUG("shutting down instance\n");
            error = virDomainShutdown(dom);
            if (error) {
                do_destroy = TRUE;
            }

        } else if (time(NULL) < deadline) {  
            int dom_status = virDomainIsActive(dom);
            LOGTRACE("domain status '%d'\n", dom_status);
            if (dom_status != 1)        
                done = TRUE;

        } else {                        
            do_destroy = TRUE;
        }

        if (do_destroy) {
            LOGDEBUG("destroying instance\n");
            error = virDomainDestroy(dom);
            done = TRUE;
        }

        virDomainFree(dom);
        unlock_hypervisor_conn();

        if (!done)
            sleep(2);                   
    }

    return error;
}