From nobody Mon Feb 9 09:57:43 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) client-ip=8.43.85.245; envelope-from=devel-bounces@lists.libvirt.org; helo=lists.libvirt.org; Authentication-Results: mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) smtp.mailfrom=devel-bounces@lists.libvirt.org; dmarc=pass(p=reject dis=none) header.from=lists.libvirt.org ARC-Seal: i=1; a=rsa-sha256; t=1743433587; cv=none; d=zohomail.com; s=zohoarc; b=B84zdUIySGCCfQe6jDq9nfmDFHUHNVMIJrZvlG0gDADXZVrepCRNjmLdddhuk6s+lGXC6zuJ6hb58zOXbOeskrMgEcXw0ZYYhROA9iFfYvTjVvy3mXGQ33oD3ntr10o93DrhT9CXqM/KvlLHkwgFYeI71EqyvnOjTPSRCY68HUs= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1743433587; h=Content-Type:Content-Transfer-Encoding:Cc:Cc:Date:Date:From:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:Reply-To:Reply-To:References:Subject:Subject:To:To:Message-Id; bh=fs42qJdKMftofxJVUhpuFGNUZG3OYotI6pWpMFp+tTI=; b=g0/GN+myI0qKtGQzj6SzDYCZCGvKJOVnc+/xI6X+7134MMGwubTWJLwj9P7ecSBaw7sLFK4d0q5G5ItL7Oj+0CgumZi/NxUG73rqOVUiBtQw5fV+/aVlkeQgFP/lQtqMG1hNkIgXZD6HNb/qLnP9ArcC9ExP+lg6z8T7PooTYu0= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=fail; spf=pass (zohomail.com: domain of lists.libvirt.org designates 8.43.85.245 as permitted sender) smtp.mailfrom=devel-bounces@lists.libvirt.org; dmarc=pass header.from= (p=reject dis=none) Return-Path: Received: from lists.libvirt.org (lists.libvirt.org [8.43.85.245]) by mx.zohomail.com with SMTPS id 1743433587748827.2804749497799; Mon, 31 Mar 2025 08:06:27 -0700 (PDT) Received: by lists.libvirt.org (Postfix, from userid 996) id C164F1240; Mon, 31 Mar 2025 11:06:26 -0400 (EDT) Received: from lists.libvirt.org (localhost [IPv6:::1]) by lists.libvirt.org (Postfix) with ESMTP id E8CFF1384; Mon, 31 Mar 2025 11:04:21 -0400 (EDT) Received: by lists.libvirt.org (Postfix, from userid 996) id 87E6111AC; Mon, 31 Mar 2025 11:04:13 -0400 (EDT) Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by lists.libvirt.org (Postfix) with ESMTPS id E14A41183 for ; Mon, 31 Mar 2025 11:04:12 -0400 (EDT) Received: from mx-prod-mc-06.mail-002.prod.us-west-2.aws.redhat.com (ec2-35-165-154-97.us-west-2.compute.amazonaws.com [35.165.154.97]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-690-7o5MSs37Oymw88zSvyvbuw-1; Mon, 31 Mar 2025 11:04:11 -0400 Received: from mx-prod-int-04.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-04.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.40]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mx-prod-mc-06.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id C8064180025C for ; Mon, 31 Mar 2025 15:04:10 +0000 (UTC) Received: from kshcheti-thinkpadp1gen4i.tpbc.com (unknown [10.43.2.246]) by mx-prod-int-04.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id D7CE61955BF1; Mon, 31 Mar 2025 15:04:09 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on lists.libvirt.org X-Spam-Level: X-Spam-Status: No, score=-0.8 required=5.0 tests=DKIM_INVALID,DKIM_SIGNED, MAILING_LIST_MULTI,RCVD_IN_DNSWL_NONE,RCVD_IN_VALIDITY_RPBL_BLOCKED, RCVD_IN_VALIDITY_SAFE_BLOCKED,SPF_HELO_NONE autolearn=unavailable autolearn_force=no version=3.4.4 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1743433452; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=LP3rjfLyacj/bvtxz996woAnhw+zaR4G0fzH+qz6u5o=; b=Q4t3wbujllduz+JT+m1dXr0ncnaLhCwRzDXo5B39/E1Pu7eHW8EUGzA7EqV9qTWtDDInol 0geslfD7qlHarVVBb0AjIzoQC+IjRGxsqd/FxoleznMlNh/pdH1DiUgTgznfxccX9Iv/nK KJzNTwG3rQxhjKY+DW/Xi/oauPfEzoU= X-MC-Unique: 7o5MSs37Oymw88zSvyvbuw-1 X-Mimecast-MFC-AGG-ID: 7o5MSs37Oymw88zSvyvbuw_1743433450 To: devel@lists.libvirt.org Subject: [PATCH 3/4] ch: add reconnection to running domains Date: Mon, 31 Mar 2025 17:01:40 +0200 Message-ID: <20250331150359.276206-4-kshcheti@redhat.com> In-Reply-To: <20250331150359.276206-1-kshcheti@redhat.com> References: <20250331150359.276206-1-kshcheti@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.0 on 10.30.177.40 X-Mimecast-Spam-Score: 0 X-Mimecast-MFC-PROC-ID: 6gFYDNioN4t1kCeQ-m4F7M0Bc9V65RugvC3nDjI7X50_1743433450 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: quoted-printable Message-ID-Hash: 23JD5OIO5WJ52R46OOIKM3FMNG6W443O X-Message-ID-Hash: 23JD5OIO5WJ52R46OOIKM3FMNG6W443O X-MailFrom: kshcheti@redhat.com X-Mailman-Rule-Misses: dmarc-mitigation; no-senders; approved; emergency; loop; banned-address; member-moderation; header-match-config-1; header-match-config-2; header-match-config-3; header-match-devel.lists.libvirt.org-0; nonmember-moderation; administrivia; implicit-dest; max-recipients; max-size; news-moderation; no-subject; suspicious-header CC: Kirill Shchetiniuk X-Mailman-Version: 3.2.2 Precedence: list List-Id: Development discussions about the libvirt library & tools Archived-At: List-Archive: List-Help: List-Post: List-Subscribe: List-Unsubscribe: From: Kirill Shchetiniuk via Devel Reply-To: Kirill Shchetiniuk X-ZohoMail-DKIM: fail (Header signature does not verify) X-ZM-MESSAGEID: 1743433591902019100 Content-Type: text/plain; charset="utf-8"; x-default="true" Previously, if any domain was still running, the driver was unable to reconnect to it, preventing further interactions with running domain. To resolve this, the driver now attempts to reconnect to the domains' monitors, which transient definitions are stored in state dir, during the initialization step. This allows us to perform further actions on domains even if the CH driver was restarted. Resolves: https://gitlab.com/libvirt/libvirt/-/issues/743 Signed-off-by: Kirill Shchetiniuk --- src/ch/ch_driver.c | 2 + src/ch/ch_monitor.c | 65 +++++++++++++++++++++++++ src/ch/ch_monitor.h | 2 + src/ch/ch_process.c | 116 ++++++++++++++++++++++++++++++++++++++++++++ src/ch/ch_process.h | 2 + 5 files changed, 187 insertions(+) diff --git a/src/ch/ch_driver.c b/src/ch/ch_driver.c index 4ce68c9299..465528baf1 100644 --- a/src/ch/ch_driver.c +++ b/src/ch/ch_driver.c @@ -1489,6 +1489,8 @@ chStateInitialize(bool privileged, NULL, NULL) < 0) goto cleanup; =20 + virCHProcessReconnectAll(ch_driver); + ch_driver->chCaps =3D virCHCapsInitCHVersionCaps(ch_driver->version); =20 ch_driver->privileged =3D privileged; diff --git a/src/ch/ch_monitor.c b/src/ch/ch_monitor.c index 1dc085a755..4ea79506ce 100644 --- a/src/ch/ch_monitor.c +++ b/src/ch/ch_monitor.c @@ -581,6 +581,71 @@ chMonitorCreateSocket(const char *socket_path) return -1; } =20 +virCHMonitor * +virCHMonitorReconnectNew(virDomainObj *vm, virCHDriverConfig *cfg) +{ + g_autoptr(virCHMonitor) mon =3D NULL; + virCHDomainObjPrivate *priv =3D vm->privateData; + int event_monitor_fd; + int rv; + + if (virCHMonitorInitialize() < 0) + return NULL; + + if (!(mon =3D virObjectLockableNew(virCHMonitorClass))) + return NULL; + + mon->eventmonitorfd =3D -1; + + if (!vm->def) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("VM is not defined")); + return NULL; + } + + mon->socketpath =3D g_strdup_printf("%s/%s-socket", + cfg->stateDir, vm->def->name); + + mon->eventmonitorpath =3D g_strdup_printf("%s/%s-event-monitor-fifo", + cfg->stateDir, vm->def->name); + + if ((rv =3D virPidFileReadPathIfLocked(priv->pidfile, &mon->pid)) < 0)= { + VIR_WARN("Pidfile of %1$s can't be read error", vm->def->name); + return NULL; + } + + if (mon->pid =3D=3D -1) { + VIR_WARN("Vm %1$s isn't running", vm->def->name); + return NULL; + } + + VIR_DEBUG("CH vm=3D%p name=3D%s is running as pid=3D%lld", vm, vm->def= ->name, (long long)vm->pid); + + /* open the reader end of fifo before start Event Handler */ + while ((event_monitor_fd =3D open(mon->eventmonitorpath, O_RDONLY)) < = 0) { + if (errno =3D=3D EINTR) { + g_usleep(100000); + continue; + } + VIR_ERROR(_("%1$s: Failed to open the event monitor FIFO(%2$s) rea= d end!"), + vm->def->name, mon->eventmonitorpath); + return NULL; + } + + mon->eventmonitorfd =3D event_monitor_fd; + VIR_DEBUG("%s: Opened the event monitor FIFO(%s)", vm->def->name, mon-= >eventmonitorpath); + + mon->vm =3D virObjectRef(vm); + + if (virCHStartEventHandler(mon) < 0) + return NULL; + + mon->handle =3D curl_easy_init(); + + return g_steal_pointer(&mon); +} + + virCHMonitor * virCHMonitorNew(virDomainObj *vm, virCHDriverConfig *cfg, int logfile) { diff --git a/src/ch/ch_monitor.h b/src/ch/ch_monitor.h index 185de0dbfd..f6d7119c96 100644 --- a/src/ch/ch_monitor.h +++ b/src/ch/ch_monitor.h @@ -143,3 +143,5 @@ virCHMonitorBuildNetJson(virDomainNetDef *netdef, int virCHMonitorBuildRestoreJson(virDomainDef *vmdef, const char *from, char **jsonstr); + +virCHMonitor *virCHMonitorReconnectNew(virDomainObj *vm, virCHDriverConfig= *cfg); diff --git a/src/ch/ch_process.c b/src/ch/ch_process.c index 08331352a4..d7a5ecc09c 100644 --- a/src/ch/ch_process.c +++ b/src/ch/ch_process.c @@ -1194,3 +1194,119 @@ virCHProcessStartRestore(virCHDriver *driver, virDo= mainObj *vm, const char *from virCHProcessStop(driver, vm, VIR_DOMAIN_SHUTOFF_FAILED); return ret; } + + +struct virCHProcessReconnectData +{ + virDomainObj *vm; + virCHDriver *driver; +}; + + +static void +virCHProcessReconnect(void *opaque) +{ + struct virCHProcessReconnectData *data =3D opaque; + virDomainObj *vm =3D data->vm; + virCHDriver *driver =3D data->driver; + g_autoptr(virCHDriverConfig) cfg =3D virCHDriverGetConfig(driver); + virCHDomainObjPrivate *priv =3D vm->privateData; + + if (virDomainObjBeginJob(vm, VIR_JOB_MODIFY)) + goto error; + + VIR_DEBUG("Reconnecting to vm=3D%p name=3D%s", vm, vm->def->name); + + /* Build pidfile path where is running domain pid stored */ + if (!(priv->pidfile =3D virPidFileBuildPath(cfg->stateDir, vm->def->na= me))) { + virReportSystemError(errno, "%s", _("Failed to build pidfile path.= ")); + goto error; + } + + /* Create new monitor object without new CH startup */ + if (!priv->monitor) { + if (!(priv->monitor =3D virCHMonitorReconnectNew(vm, cfg))) + goto error; + } + + vm->pid =3D priv->monitor->pid; + vm->def->id =3D vm->pid; + priv->machineName =3D virCHDomainGetMachineName(vm); + + if (!priv->machineName) + goto error; + + if (virDomainCgroupConnectCgroup("ch", + vm, + &priv->cgroup, + cfg->cgroupControllers, + priv->driver->privileged, + priv->machineName) < 0) + goto error; + + + if (virDomainInterfaceStartDevices(vm->def) < 0) + goto error; + + virCHProcessUpdateInfo(vm); + + if (virDomainObjSave(vm, driver->xmlopt, cfg->stateDir) < 0) + goto error; + + cleanup: + virDomainObjEndJob(vm); + virDomainObjEndAPI(&vm); + return; + + error: + virCHProcessStop(driver, vm, VIR_DOMAIN_SHUTOFF_FAILED); + + goto cleanup; +} + +static int +virCHProcessReconnectHelper(virDomainObj *vm, void *opaque) +{ + struct virCHProcessReconnectData *src =3D opaque; + struct virCHProcessReconnectData *data; + virThread thread; + g_autofree char *name =3D NULL; + + /* Skip reconnect is domain if is not running */ + if (vm->pid =3D=3D 0) + return 0; + + data =3D g_new0(struct virCHProcessReconnectData, 1); + + memcpy(data, src, sizeof(*data)); + data->vm =3D vm; + + virObjectLock(vm); + virObjectRef(vm); + + name =3D g_strdup_printf("reconnect-%s", vm->def->name); + + VIR_DEBUG("Reconnecting vm=3D%p name=3D%s", vm, vm->def->name); + + if (virThreadCreateFull(&thread, false, virCHProcessReconnect, + name, false, data) < 0) { + virReportError(VIR_ERR_INTERNAL_ERROR, "%s", + _("Could not create thread.")); + + virCHProcessStop(src->driver, vm, VIR_DOMAIN_SHUTOFF_FAILED); + + virDomainObjEndAPI(&vm); + VIR_FREE(data); + return -1; + } + + return 0; +} + +void +virCHProcessReconnectAll(virCHDriver *driver) +{ + struct virCHProcessReconnectData data =3D {.driver =3D driver}; + virDomainObjListForEach(driver->domains, true, + virCHProcessReconnectHelper, &data); +} diff --git a/src/ch/ch_process.h b/src/ch/ch_process.h index 7a6995b7cf..ff8267b497 100644 --- a/src/ch/ch_process.h +++ b/src/ch/ch_process.h @@ -38,3 +38,5 @@ int virCHProcessStartRestore(virCHDriver *driver, const char *from); =20 int virCHProcessUpdateInfo(virDomainObj *vm); + +void virCHProcessReconnectAll(virCHDriver *driver); --=20 2.48.1