Direct naar de inhoud
Kritieke cyberalerts voor jouw sector & systemen — direct in je inbox. Aanmelden →
cybernieuws.nl Cybersecurity en informatiebeveiling nieuws alerts live · 1 min 98 bronnen 1 kritiek 19 vandaag
CVE's Videos Dagbriefing

← Terug naar CVE-database

CVE-2026-46025

MEDIUM · 4.7 CVSS Gepubliceerd: CWE-362

Beschrijving NL

In de Linux kernel is de volgende kwetsbaarheid verholpen:

mm/damon/core: fix damon_call() vs kdamond_fn() exit race

Patch serie "mm/damon/core: fix damon_call()/damos_walk() vs kdmond exit
race". damon_call() en damos_walk() kunnen geheugen lekken en/of vastlopen wanneer ze
race met kdamond-beëindigingen. Los die op. Deze pleister (van 2);

Wanneer kdamond_fn() hoofdlus is voltooid, annuleert de functie alle
resterend damon_call() vraagt en zet de damon_ctx->kdamond uit zodat
API-bellers en API-functies kunnen zelf weten dat de context
beëindigd. damon_call() voegt het verzoek van de beller eerst toe aan de wachtrij. Daarna laat het zien of de kdamond van de damon_ctx nog steeds draait
(damon_ctx->kdamond is ingesteld). Alleen als de kdamond draait, damon_call()
begint te wachten op de afhandeling door de kdamond van het nieuw toegevoegde verzoek. De damon_call() vraagt om registratie en damon_ctx->kdamond unset zijn
beschermd door verschillende mutexen. Daarom kan damon_call() racen
met damon_ctx->kdamond uitgeschakeld, en resulteren in deadlocks. Laten we bijvoorbeeld aannemen dat kdamond de damon_call() met succes heeft voltooid
annulatieverzoeken. Direct daarna wordt damon_call() aangeroepen voor de
context. Het registreert de nieuwe aanvraag en laat zien dat de context nog steeds
draaien, omdat damon_ctx->kdamond unset nog niet klaar is. Vandaar dat de
damon_call() beller begint te wachten op de afhandeling van het verzoek. De kdamond staat echter al op de opzeggingsstappen, zodat deze nooit
behandelt de nieuwe aanvraag. Dientengevolge, de damon_call() caller threads
wacht oneindig. Los dit op door een ander damon_ctx-veld te introduceren, namelijk
call_controls_obsolete. Het wordt beschermd door de
damon_ctx->call_controls_lock, die damon_call() aanvragen beschermt
registratie. Initialiseren (uitzetten) in kdamond_fn() alvorens te verhuren
damon_start() retourneert en stelt deze in vlak voor de annulering van de resterende
damon_call() aanvragen worden uitgevoerd. damon_call() leest het verouderde veld
onder het slot en vermijdt het toevoegen van een nieuwe aanvraag. Na deze wijziging worden alleen aanvragen afgehandeld die gegarandeerd worden afgehandeld of
opgezegd worden geregistreerd. Vandaar de na-registratie DAMON CONTEXT
beëindigingscontrole is niet langer nodig. Verwijder het samen. Merk op dat de impasse niet zal optreden wanneer damon_call() wordt opgeroepen
herhaalmodusverzoek. In dit geval retourneert damon_call() in plaats van te wachten
voor de afhandeling wanneer de aanvraagregistratie slaagt en het toont de
kdamond draait. Als het verzoek echter ook dealloc_on_cancel heeft,
het verzoekgeheugen zou worden gelekt. Het probleem wordt gevonden door sashiko [1].

Origineel (Engels) tonen

In the Linux kernel, the following vulnerability has been resolved:

mm/damon/core: fix damon_call() vs kdamond_fn() exit race

Patch series "mm/damon/core: fix damon_call()/damos_walk() vs kdmond exit
race".

damon_call() and damos_walk() can leak memory and/or deadlock when they
race with kdamond terminations. Fix those.

This patch (of 2);

When kdamond_fn() main loop is finished, the function cancels all
remaining damon_call() requests and unset the damon_ctx->kdamond so that
API callers and API functions themselves can know the context is
terminated. damon_call() adds the caller's request to the queue first.
After that, it shows if the kdamond of the damon_ctx is still running
(damon_ctx->kdamond is set). Only if the kdamond is running, damon_call()
starts waiting for the kdamond's handling of the newly added request.

The damon_call() requests registration and damon_ctx->kdamond unset are
protected by different mutexes, though. Hence, damon_call() could race
with damon_ctx->kdamond unset, and result in deadlocks.

For example, let's suppose kdamond successfully finished the damon_call()
requests cancelling. Right after that, damon_call() is called for the
context. It registers the new request, and shows the context is still
running, because damon_ctx->kdamond unset is not yet done. Hence the
damon_call() caller starts waiting for the handling of the request.
However, the kdamond is already on the termination steps, so it never
handles the new request. As a result, the damon_call() caller threads
infinitely waits.

Fix this by introducing another damon_ctx field, namely
call_controls_obsolete. It is protected by the
damon_ctx->call_controls_lock, which protects damon_call() requests
registration. Initialize (unset) it in kdamond_fn() before letting
damon_start() returns and set it just before the cancelling of remaining
damon_call() requests is executed. damon_call() reads the obsolete field
under the lock and avoids adding a new request.

After this change, only requests that are guaranteed to be handled or
cancelled are registered. Hence the after-registration DAMON context
termination check is no longer needed. Remove it together.

Note that the deadlock will not happen when damon_call() is called for
repeat mode request. In tis case, damon_call() returns instead of waiting
for the handling when the request registration succeeds and it shows the
kdamond is running. However, if the request also has dealloc_on_cancel,
the request memory would be leaked.

The issue is found by sashiko [1].

Vendors

Linux

Affected products

Linux Kernel

References