From nobody Mon Apr 6 19:59:51 2026 Received: from mail-yx1-f46.google.com (mail-yx1-f46.google.com [74.125.224.46]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D86EB3DA7C2 for ; Wed, 18 Mar 2026 14:17:03 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=74.125.224.46 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1773843429; cv=none; b=PwDqrc7yoq9qn+ec41iZC57kGXZZHh8UXh1d1TGIu0n3JPfK5cMrJCLHpFP0+JH+ksqj6HkMHYX/C5PQQ8IEoEJ7i95Afz4X+JEk3Lk4tKf/UoV4wUFkAezdLVSGat7UrEKBpeYKyKWaPEhMoLCpiYxd569Y7n4EFNxGAHC6/tc= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1773843429; c=relaxed/simple; bh=EalrGmrqwRzzH6yUEQF0bva997eCnPDMp/i8mRFTvIA=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Q9CXEjutWP7SFbJ0SrqopCAp5F+lKxDPpo/WExdLldTw1uoy+ukb/muyYg2o4Q2tP8W1LLeZv0KGy5oXKx8s4f2reUwkWGlhEt8BwByHSMyt/bHla3oKdVdoYty8MWURkGEKpDDuj75/dtUqxZzsuubA2CMV6bZL2eb0h9QKR8s= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=soleen.com; spf=pass smtp.mailfrom=soleen.com; dkim=pass (2048-bit key) header.d=soleen.com header.i=@soleen.com header.b=F0cJ3AJP; arc=none smtp.client-ip=74.125.224.46 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=soleen.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=soleen.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=soleen.com header.i=@soleen.com header.b="F0cJ3AJP" Received: by mail-yx1-f46.google.com with SMTP id 956f58d0204a3-64c9a6d68e5so5958183d50.3 for ; Wed, 18 Mar 2026 07:17:03 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=soleen.com; s=google; t=1773843423; x=1774448223; darn=vger.kernel.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:to:from:from:to:cc:subject:date:message-id :reply-to; bh=J4M6tHJH+NIswtfacOyFlweafgc3XAP5SglzYx4YyzE=; b=F0cJ3AJPh4UEOTpmJK6CCyv0K1N24Fp6Y615VYZNJqSNU7KYQb/AxA0zOWZD+gDlqf 6/HelNw9s4Cns207hwd+r+/UEdJBEKbp/d/X2IlVc/KQ6IG1YMCrRWgg9XtftNoYFD+3 ga2iAvYwKj+vWCmJme9GC/ip/UIHHiK6F8+/GfYrQzv+koJN6PL8t+Kycn1E18DamBtR Hc7J6cjxwp3g6dgLFJcHPdZQRgyF5bMmtATW9fAHfLZH+CNjZIrHujDu9FYGJPdJ/3BL cAiKH51YdhurDGKHXPQ/FCk4n+LhqkwkE0LOWil2qWxqoFMMqCIMwb4LaBWFezp2g1pr e+RQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1773843423; x=1774448223; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:to:from:x-gm-gg:x-gm-message-state:from:to :cc:subject:date:message-id:reply-to; bh=J4M6tHJH+NIswtfacOyFlweafgc3XAP5SglzYx4YyzE=; b=XXoibcV3N77Tn3TXKH66wW/ph8iUNWDiq/2qF8Teq+yrv9DKV+zKD5jzzY0lpB1lV6 ESITaX3KHJvRMLnzfFazN/bvjtpVvggcOXhN5RcSAvUxRc2+eRLE5uPDGz26D7nMJg3H sLgXBVz8ovBimti+HhWxWCCA2teIh0dE59UDg+pLagoOFIvvxcFn3PYPThDq/WVjIPdr +67Ip3mfoJHOI5mP3eZHjgIH9UD7TFuI4EAydIdBxwUJGGqgPSNC5nt2SBlCisK2bf7q oTOvFveyPJGaxHVOqwJY0M5j7Qw/fIW1JNmQMpD+ZdtJh+n+zoen32msavlt7jxSwJef YHZA== X-Forwarded-Encrypted: i=1; AJvYcCWfQ4PzExBhZ7tGsjvytqFRxPHYO35TNneg0C9MYl/MEWeQUPJJxa65QBvMzPN4nexgr5sTQORFV7QcfMQ=@vger.kernel.org X-Gm-Message-State: AOJu0Yyr9rFRMBJcCcdIyAiND3bOFeXbJFPu+Fnj07Rxfm95+l4dn3io I4hnw+9aFP3fFbbA18g/TVLL/0J1pKzXiGjP1OxcdFKPNttFw6rc+k+/QVZkdXq3Ibc= X-Gm-Gg: ATEYQzxue+27I84wFE4tX8aBoUJ6cO3h/Imv88v8O4/bKUjyRIEyLjCq1vjm8FcW+VD W/YzOU13b3i0/8pSNEaYbURHX599r1NublbtwVK8lie61C/WHNiIZIimji/oH8UnNJUqS+rA5+h lPikASV40mlEhzwOtTKHdXVfWGZ2x4oB5558QdjqbaA4ZPmTxMO6ckvfpKuee8MbzRKViQUdTuC aUacuVQcJSo/+9RvDM3x/qQzcWQfXBdqLd9WituhFfjgDA2zDv3nSqIGLn0O45sTz3A3GyyxyR3 c25GAak4ZSoihThVgQJk3KRFjmXYge7fWCHAxR9AwMjEe2G/NHs237A0qfZrsmQYuVk5MlL1X8u rpIV+m+TRQfvZSzp2GaHM/Qk/p6DIr35ZGZxordDBWfujMpGAVMFi1zjP0g0p1ZCedbZKzBxGgx aA7X931VpMyD4vbUG8/ySLZvJmo3TUQCU0D8VQOcG+53bwJmX+E0wf0eimKObSUoQs5frt/Z0ff 2k/RK7vDfsTIE8R/uIk3yzOQgkRFQZHhtjiv0YvE1aISWev+g== X-Received: by 2002:a53:ccc1:0:b0:64c:f90c:740b with SMTP id 956f58d0204a3-64e9133cc6cmr2802395d50.18.1773843422693; Wed, 18 Mar 2026 07:17:02 -0700 (PDT) Received: from soleen.c.googlers.com.com (57.233.150.34.bc.googleusercontent.com. [34.150.233.57]) by smtp.gmail.com with ESMTPSA id 956f58d0204a3-64e91be0e91sm1672028d50.15.2026.03.18.07.17.01 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Wed, 18 Mar 2026 07:17:01 -0700 (PDT) From: Pasha Tatashin To: rppt@kernel.org, akpm@linux-foundation.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org, pasha.tatashin@soleen.com, dmatlack@google.com, pratyush@kernel.org Subject: [PATCH v2 6/8] liveupdate: Auto unregister FLBs on file handler unregistration Date: Wed, 18 Mar 2026 10:16:44 -0400 Message-ID: <20260318141637.1870220-16-pasha.tatashin@soleen.com> X-Mailer: git-send-email 2.53.0.851.ga537e3e6e9-goog In-Reply-To: <20260318141637.1870220-10-pasha.tatashin@soleen.com> References: <20260318141637.1870220-10-pasha.tatashin@soleen.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=6387; i=pasha.tatashin@soleen.com; h=from:subject; bh=EalrGmrqwRzzH6yUEQF0bva997eCnPDMp/i8mRFTvIA=; b=owEBbQKS/ZANAwAKAbt3KEzbc3reAcsmYgBpurPNTzeG4rxv/awumbGni4KwSHI8Znp/TwC3c +0LmOIOqaCJAjMEAAEKAB0WIQRBMaqT7LRvGvB/NmK7dyhM23N63gUCabqzzQAKCRC7dyhM23N6 3kp7D/9rYKOXxrYJk2Vo8xunmH8iFfYAyW1VooFl+SuhHbwZjw1AkNif4cjY4Xf2ewk0ThMNTQ5 7l987GROBYr+Z0JBaB15vSO79amsq+XsNBD1TbTm+9jRbfF6apyY0ul5pXw43lbV45CkDJ7LvNF sRia+95B/ECSas2//sdqLD/8UqD1R3fDMUBkdSguuoONWkgWfLBoC8fV9KOLr+E50PAAor1XYjw lEpaTVF58eKKeGAN4VGmKVfl7QdaQnd+vx/Zopnbh6L1H677NPE5YE0YXhmE+olW6opFlj4DYFH aQkrt4D2J0jx9QY6eMKGXoadD6ufLUxRDJF6XEEA+8CrZAmOWbNJycefp87udjAuU/pWIdr1FCh gMTLC9X3bwlqkZffir6BfwyCHbZ7zxR8Hhtwq4zYD3DCZo1QkkQrzz0ACo1JtHDGU2bB9/QhWZO I6nJLQVYAtReRso101qqMvsqWnGBcmkdRUPngcLoUzVJ3cGH8prwiLR5ik99jac8O3NEMsBvYMh 83BUndZnaVme2f950b7mUDo7ufJJwxTYK3++gQ41Cupfa5216iaZZeU7MzLvSMzVhYuiodHQwFt 7i7tBY0VF869IR1E6E8RaIan+ol65/ZJHYkfqd4aiVPoWlArw395OleHCAUbSOFfbn+jdvh5+gG uTeI/EbAK1ZhyBA== X-Developer-Key: i=pasha.tatashin@soleen.com; a=openpgp; fpr=CAAAB722DD22A081F0D49F35633A6A993D43B569 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" To ensure that unregistration is always successful and doesn't leave dangling resources, introduce auto-unregistration of FLBs: when a file handler is unregistered, all FLBs associated with it are automatically unregistered. Introduce a new helper luo_flb_unregister_all() which unregisters all FLBs linked to the given file handler. Signed-off-by: Pasha Tatashin --- kernel/liveupdate/luo_file.c | 17 +----- kernel/liveupdate/luo_flb.c | 93 ++++++++++++++++++++------------ kernel/liveupdate/luo_internal.h | 1 + 3 files changed, 61 insertions(+), 50 deletions(-) diff --git a/kernel/liveupdate/luo_file.c b/kernel/liveupdate/luo_file.c index c0ce08d55747..b9ba1b8dce84 100644 --- a/kernel/liveupdate/luo_file.c +++ b/kernel/liveupdate/luo_file.c @@ -873,15 +873,6 @@ int liveupdate_register_file_handler(struct liveupdate= _file_handler *fh) * * Unregisters the file handler from the liveupdate core. This function * reverses the operations of liveupdate_register_file_handler(). - * - * It ensures safe removal by checking that: - * No FLB registered with this file handler. - * - * If the unregistration fails, the internal test state is reverted. - * - * Return: 0 Success. -EOPNOTSUPP when live update is not enabled. -EBUSY = A live - * update is in progress, FLB is registred with - * this file handler. */ int liveupdate_unregister_file_handler(struct liveupdate_file_handler *fh) { @@ -891,15 +882,9 @@ int liveupdate_unregister_file_handler(struct liveupda= te_file_handler *fh) liveupdate_test_unregister(fh); =20 scoped_guard(rwsem_write, &luo_file_handler_lock) { - if (!list_empty(&ACCESS_PRIVATE(fh, flb_list))) - goto err_register; - + luo_flb_unregister_all(fh); list_del(&ACCESS_PRIVATE(fh, list)); } =20 return 0; - -err_register: - liveupdate_test_register(fh); - return -EBUSY; } diff --git a/kernel/liveupdate/luo_flb.c b/kernel/liveupdate/luo_flb.c index 8bbe11a7286b..5b61c0844a49 100644 --- a/kernel/liveupdate/luo_flb.c +++ b/kernel/liveupdate/luo_flb.c @@ -316,6 +316,64 @@ void luo_flb_file_finish(struct liveupdate_file_handle= r *fh) luo_flb_file_finish_one(iter->flb); } =20 +static void luo_flb_unregister_one(struct liveupdate_file_handler *fh, + struct liveupdate_flb *flb) +{ + struct luo_flb_private *private =3D luo_flb_get_private(flb); + struct list_head *flb_list =3D &ACCESS_PRIVATE(fh, flb_list); + struct luo_flb_link *iter; + bool found =3D false; + + /* Find and remove the link from the file handler's list */ + list_for_each_entry(iter, flb_list, list) { + if (iter->flb =3D=3D flb) { + list_del(&iter->list); + kfree(iter); + found =3D true; + break; + } + } + + if (!found) { + pr_warn("Failed to unregister FLB '%s': not found in file handler '%s'\n= ", + flb->compatible, fh->compatible); + return; + } + + private->users--; + + /* + * If this is the last file-handler with which we are registred, remove + * from the global list. + */ + if (!private->users) { + list_del_init(&private->list); + luo_flb_global.count--; + } +} + +/** + * luo_flb_unregister_all - Unregister all FLBs associated with a file han= dler. + * @fh: The file handler whose FLBs should be unregistered. + * + * This function iterates through the list of FLBs associated with the giv= en + * file handler and unregisters them all one by one. + */ +void luo_flb_unregister_all(struct liveupdate_file_handler *fh) +{ + struct list_head *flb_list =3D &ACCESS_PRIVATE(fh, flb_list); + struct luo_flb_link *iter, *tmp; + + if (!liveupdate_enabled()) + return; + + guard(rwsem_write)(&luo_flb_lock); + guard(rwsem_write)(&ACCESS_PRIVATE(fh, flb_lock)); + + list_for_each_entry_safe(iter, tmp, flb_list, list) + luo_flb_unregister_one(fh, iter->flb); +} + /** * liveupdate_register_flb - Associate an FLB with a file handler and regi= ster it globally. * @fh: The file handler that will now depend on the FLB. @@ -417,50 +475,17 @@ int liveupdate_register_flb(struct liveupdate_file_ha= ndler *fh, * the FLB is removed from the global registry and the reference to its * owner module (acquired during registration) is released. * - * Context: This function ensures the session is quiesced (no active FDs - * being created) during the update. It is typically called from a - * subsystem's module exit function. - * Return: 0 on success. - * -EOPNOTSUPP if live update is disabled. - * -EBUSY if the live update session is active and cannot be quies= ced. - * -ENOENT if the FLB was not found in the file handler's list. */ int liveupdate_unregister_flb(struct liveupdate_file_handler *fh, struct liveupdate_flb *flb) { - struct luo_flb_private *private =3D luo_flb_get_private(flb); - struct list_head *flb_list =3D &ACCESS_PRIVATE(fh, flb_list); - struct luo_flb_link *iter; - int err =3D -ENOENT; - if (!liveupdate_enabled()) return -EOPNOTSUPP; =20 guard(rwsem_write)(&luo_flb_lock); guard(rwsem_write)(&ACCESS_PRIVATE(fh, flb_lock)); =20 - /* Find and remove the link from the file handler's list */ - list_for_each_entry(iter, flb_list, list) { - if (iter->flb =3D=3D flb) { - list_del(&iter->list); - kfree(iter); - err =3D 0; - break; - } - } - - if (err) - return err; - - private->users--; - /* - * If this is the last file-handler with which we are registred, remove - * from the global list. - */ - if (!private->users) { - list_del_init(&private->list); - luo_flb_global.count--; - } + luo_flb_unregister_one(fh, flb); =20 return 0; } diff --git a/kernel/liveupdate/luo_internal.h b/kernel/liveupdate/luo_inter= nal.h index ec949f91c8c1..730c3faa7616 100644 --- a/kernel/liveupdate/luo_internal.h +++ b/kernel/liveupdate/luo_internal.h @@ -101,6 +101,7 @@ void luo_file_set_destroy(struct luo_file_set *file_set= ); int luo_flb_file_preserve(struct liveupdate_file_handler *fh); void luo_flb_file_unpreserve(struct liveupdate_file_handler *fh); void luo_flb_file_finish(struct liveupdate_file_handler *fh); +void luo_flb_unregister_all(struct liveupdate_file_handler *fh); int __init luo_flb_setup_outgoing(void *fdt); int __init luo_flb_setup_incoming(void *fdt); void luo_flb_serialize(void); --=20 2.53.0.851.ga537e3e6e9-goog