[RFC PATCH 0/9] mm/damon: introduce DAMOS failed region quota charge ratio

1 view
Skip to first unread message

SeongJae Park

unread,
Apr 4, 2026, 12:39:55 PM (7 days ago) Apr 4
to SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
TL; DR: Let users set different DAMOS quota charge ratios for DAMOS
action failed regions, for deterministic and consistent DAMOS action
progress.

Common Reports: Unexpectedly Slow DAMOS
=======================================

One common issue report that we get from DAMON users is that DAMOS
action applying progress speed is sometimes much slower than expected.
And one common root cause is that the DAMOS quota is exceeded by the
action applying failed memory regions.

For example, a group of users tried to run DAMOS-based proactive memory
reclamation (DAMON_RECLAIM) with 100 MiB per second DAMOS quota. They
ran it on a system having no active workload which means all memory of
the system is cold. The expectation was that the system will show 100
MiB per second reclamation until (nearly) all memory is reclaimed. But
what they found is that the speed is quite inconsistent and sometimes it
becomes very slower than the expectation, sometimes even no reclamation
at all for about tens of seconds. The upper limit of the speed (100 MiB
per second) was being kept as expected, though.

By monitoring the qt_exceeds (number of DAMOS quota exceed events) DAMOS
stat, we found DAMOS quota is always exceeded when the speed is slow. By
monitoring sz_tried and sz_applied (the total amount of DAMOS action
tried memory and succeeded memory) DAMOS stats together, we found the
reclamation attempts nearly always failed when the speed is slow.

DAMOS quota charges DAMOS action tried regions regardless of the
successfulness of the try. Hence in the example reported case, there
was unreclaimable memory spread around the system memory. Sometimes
nearly 100 MiB of memory that DAMOS tried to reclaim in the given quota
interval was reclaimable, and therefore showed nearly 100 MiB per second
speed. Sometimes nearly 99 MiB of memory that DAMOS was trying to
reclaim in the given quota interval was unreclaimable, and therefore
showing only about 1 MiB per second reclaim speed.

We explained it is an expected behavior of the feature rather than a
bug, as DAMOS quota is there for only the upper-limit of the speed. The
users agreed and later reported a huge win from the adoption of
DAMON_RECLAIM on their products.

It is Not a Bug but a Feature; But...
=====================================

So nothing is broken. DAMOS quota is working as intended, as the upper
limit of the speed. It also provides its behavior observability via
DAMOS stat. In the real world production environment that runs long
term active workloads and matters stability, the speed sometimes being
slow is not a real problem.

But, the non-deterministic behavior is sometimes annoying, especially in
lab environments. Even in a realistic production environment, when
there is a huge amount of DAMOS action unapplicable memory, the speed
could be problematically slow. Let's suppose a virtual machines
provider that setup 99% of the host memory as hugetlb pages that cannot
be reclaimed, to give it to virtual machines. Also, when aim-oriented
DAMOS auto-tuning is applied, this could also make the internal feedback
loop confused.

The intention of the current behavior was that trying DAMOS action to
regions would anyway impose some overhead, and therefore somehow be
charged. But in the real world, the overhead for failed action is much
lighter than successful action. Charging those at the same ratio may be
unfair, or at least suboptimum in some environments.

DAMOS Action Failed Region Quota Charge Ratio
=============================================

Let users set the charge ratio for the action-failed memory, for more
optimal and deterministic use of DAMOS. It allows users to specify the
numerator and the denominator of the ratio for flexible setup. For
example, let's suppose the numerator and the denominator are set to 1
and 4,096, respectively. The ratio is 1 / 4,096. A DAMOS scheme action
is applied to 5 GiB memory. For 1 GiB of the memory, the action is
succeeded. For the rest (4 GiB), the action is failed. Then, only 1
GiB and 1 MiB quota is charged.

The optimal charge ratio will depend on the use case and
system/workload. I'd recommend starting from setting the nominator as 1
and the denominator as PAGE_SIZE and tune based on the results, because
many DAMOS actions are applied at page level.

Tests
=====

I tested this feature in the steps below.

1. Allocate 50% of system memory and mlock() it using a test program.
2. Fill up the page cache to exhaust nearly all free memory.
3. Start DAMON-based proactive reclamation with 100 MiB/second DAMOS
hard-quota. Auto-tune the DAMOS soft-quota under the hard-quota for
achieving 40% free memory of the system with 'temporal' tuner.

For step 1, I run a simple C program that is written by Gemini. It is
quite straightforward, so I'm not sharing the code here.

For step 2, I use dd command like below:

dd if=/dev/zero of=foo bs=1M count=$50_percent_of_system_memory

For step 3, I use the latest version of DAMON user-space tool (damo)
like below.

sudo damo start --damos_action pageout \
` # Do the pageout only up to 100 MiB per second ` \
--damos_quota_space 100M --damos_quota_interval 1s \
` # Auto-tune the quota below the hard quota aiming` \
` # 40% free memory of the node 0 ` \
` # (entire node of the test system)` \
--damos_quota_goal node_mem_free_bp 40% 0 \
` # use temporal tuner, which is easy to understnd ` \
--damos_quota_goal_tuner temporal

As expected, the progress of the reclamation is not consistent, because
the quota is exceeded for the failed reclamation of the unreclaimable
memory.

I do this again, but with the failed region charge ratio feature. For
this, the above 'damo' command is used, after appending command line
option for setup of the charge ratio like below. Note that the option
was added to 'damo' after v3.1.9.

sudo ./damo start --damos_action pageout \
[...]
` # quota-charge only 1/4096 for pageout-failed regions ` \
--damos_quota_fail_charge_ratio 1 4096

The progress of the reclamation was nearly 100 MiB per second until the
goal was achieved, meeting the expectation.

Patches Sequence
================

Patch 1 implements the feature and exposes it via DAMON core API.
Patch 2 implements DAMON sysfs ABI for the feature. Three following
patches (3-5) document the feature and ABI on design, usage, and ABI
documents, respectively. Four patches for testing of the new feature
follow. Patch 6 implements a kunit test for the feature. Patches 7
and 8 extend DAMON selftest helpers for DAMON sysfs control and internal
state dumping for adding a new selftest for the feature. Patch 9
extends existing DAMON sysfs interface selftest to test the new feature
using the extended helper scripts.

SeongJae Park (9):
mm/damon/core: introduce failed region quota charge ratio
mm/damon/sysfs-schemes: implement fail_charge_{num,denom} files
Docs/mm/damon/design: document fail_charge_{num,denom}
Docs/admin-guide/mm/damon/usage: document fail_charge_{num,denom}
files
Docs/ABI/damon: document fail_charge_{num,denom}
mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
selftets/damon/_damon_sysfs: support failed region quota charge ratio
selftests/damon/drgn_dump_damon_status: support failed region quota
charge ratio
selftets/damon/sysfs.py: test failed region quota charge ratio

.../ABI/testing/sysfs-kernel-mm-damon | 12 +++++
Documentation/admin-guide/mm/damon/usage.rst | 18 +++++--
Documentation/mm/damon/design.rst | 21 ++++++++
include/linux/damon.h | 9 ++++
mm/damon/core.c | 9 +++-
mm/damon/sysfs-schemes.c | 54 +++++++++++++++++++
mm/damon/tests/core-kunit.h | 6 +++
tools/testing/selftests/damon/_damon_sysfs.py | 21 +++++++-
.../selftests/damon/drgn_dump_damon_status.py | 2 +
tools/testing/selftests/damon/sysfs.py | 6 +++
10 files changed, 151 insertions(+), 7 deletions(-)


base-commit: 9e634d6813be2e3d1cb023a0b83619fd2bcdd13b
--
2.47.3

SeongJae Park

unread,
Apr 4, 2026, 12:39:59 PM (7 days ago) Apr 4
to SeongJae Park, Andrew Morton, Brendan Higgins, David Gow, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Extend damos_test_commit_quotas() kunit test to ensure
damos_commit_quota() handles fail_charge_{num,denom} parameters.

Signed-off-by: SeongJae Park <s...@kernel.org>
---
mm/damon/tests/core-kunit.h | 6 ++++++
1 file changed, 6 insertions(+)

diff --git a/mm/damon/tests/core-kunit.h b/mm/damon/tests/core-kunit.h
index 0030f682b23b7..16f68315ba119 100644
--- a/mm/damon/tests/core-kunit.h
+++ b/mm/damon/tests/core-kunit.h
@@ -694,6 +694,8 @@ static void damos_test_commit_quota(struct kunit *test)
.ms = 2,
.sz = 3,
.goal_tuner = DAMOS_QUOTA_GOAL_TUNER_CONSIST,
+ .fail_charge_num = 2,
+ .fail_charge_denom = 3,
.weight_sz = 4,
.weight_nr_accesses = 5,
.weight_age = 6,
@@ -703,6 +705,8 @@ static void damos_test_commit_quota(struct kunit *test)
.ms = 8,
.sz = 9,
.goal_tuner = DAMOS_QUOTA_GOAL_TUNER_TEMPORAL,
+ .fail_charge_num = 1,
+ .fail_charge_denom = 1024,
.weight_sz = 10,
.weight_nr_accesses = 11,
.weight_age = 12,
@@ -717,6 +721,8 @@ static void damos_test_commit_quota(struct kunit *test)
KUNIT_EXPECT_EQ(test, dst.ms, src.ms);
KUNIT_EXPECT_EQ(test, dst.sz, src.sz);
KUNIT_EXPECT_EQ(test, dst.goal_tuner, src.goal_tuner);
+ KUNIT_EXPECT_EQ(test, dst.fail_charge_num, 1);
+ KUNIT_EXPECT_EQ(test, dst.fail_charge_denom, 1024);
KUNIT_EXPECT_EQ(test, dst.weight_sz, src.weight_sz);
KUNIT_EXPECT_EQ(test, dst.weight_nr_accesses, src.weight_nr_accesses);
KUNIT_EXPECT_EQ(test, dst.weight_age, src.weight_age);
--
2.47.3

SeongJae Park

unread,
Apr 4, 2026, 5:04:00 PM (7 days ago) Apr 4
to SeongJae Park, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Dropped individuals from Cc list to reduce the traffic.

TL; DR: sashiko made a good suggestion to improve this patch. I will do so in
the next revision.

Forwarding sashiko review in a reply format with my inline
comments below, for details of my view and doing discussions
via mails if needed.

> # review url: https://sashiko.dev/#/patchset/202604041639...@kernel.org
> # start of sashiko.dev inline review
> commit 2c875b613d1b0d252222336af28714d95bf57930
> Author: SeongJae Park <s...@kernel.org>
>
> mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
>
> This commit extends the damos_test_commit_quotas() kunit test to verify
> that damos_commit_quota() correctly copies the fail_charge_num and
> fail_charge_denom parameters.
>
> > diff --git a/mm/damon/tests/core-kunit.h b/mm/damon/tests/core-kunit.h
> > index 9e5904c2beeb2..1eb70f721d1e1 100644
> > --- a/mm/damon/tests/core-kunit.h
> > +++ b/mm/damon/tests/core-kunit.h
> [ ... ]
> > @@ -717,6 +721,8 @@ static void damos_test_commit_quota(struct kunit *test)
> > KUNIT_EXPECT_EQ(test, dst.ms, src.ms);
> > KUNIT_EXPECT_EQ(test, dst.sz, src.sz);
> > KUNIT_EXPECT_EQ(test, dst.goal_tuner, src.goal_tuner);
> > + KUNIT_EXPECT_EQ(test, dst.fail_charge_num, 1);
> > + KUNIT_EXPECT_EQ(test, dst.fail_charge_denom, 1024);
>
> This isn't a bug, but should these assertions use src.fail_charge_num and
> src.fail_charge_denom instead of the hardcoded 1 and 1024?
>
> Using the src fields would keep this consistent with the surrounding
> assertions. It would also prevent the test from becoming brittle if the
> src structure's initialization values are changed in the future.

Makes sense, I will do so in the next revision.


Thanks,
SJ

>
> > KUNIT_EXPECT_EQ(test, dst.weight_sz, src.weight_sz);
> > KUNIT_EXPECT_EQ(test, dst.weight_nr_accesses, src.weight_nr_accesses);
> > KUNIT_EXPECT_EQ(test, dst.weight_age, src.weight_age);
>
>
> # end of sashiko.dev inline review
> # review url: https://sashiko.dev/#/patchset/202604041639...@kernel.org

# hkml [1] generated a draft of this mail. You can regenerate
# this using below command:
#
# hkml patch sashiko_dev --for_forwarding \
# 202604041639...@kernel.org
#
# [1] https://github.com/sjp38/hackermail

SeongJae Park

unread,
Apr 4, 2026, 5:06:40 PM (7 days ago) Apr 4
to SeongJae Park, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Dropped individuals from Cc list to reduce the traffic.

TL; DR: sashiko made a few useful findings. I will address those in the next
revision.

Forwarding sashiko.dev review status for the overall picture. Read my replies
to 'ISSUES MAY FOUND' patches for more details.
- [RFC PATCH 1/9] mm/damon/core: introduce failed region quota charge ratio
- status: Reviewed
- review: ISSUES MAY FOUND
- [RFC PATCH 2/9] mm/damon/sysfs-schemes: implement fail_charge_{num,denom} files
- status: Reviewed
- review: ISSUES MAY FOUND
- [RFC PATCH 3/9] Docs/mm/damon/design: document fail_charge_{num,denom}
- status: Reviewed
- review: ISSUES MAY FOUND
- [RFC PATCH 4/9] Docs/admin-guide/mm/damon/usage: document fail_charge_{num,denom} files
- status: Reviewed
- review: ISSUES MAY FOUND
- [RFC PATCH 5/9] Docs/ABI/damon: document fail_charge_{num,denom}
- status: Reviewed
- review: No issues found.
- [RFC PATCH 6/9] mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
- status: Reviewed
- review: ISSUES MAY FOUND
- [RFC PATCH 7/9] selftets/damon/_damon_sysfs: support failed region quota charge ratio
- status: Reviewed
- review: No issues found.
- [RFC PATCH 8/9] selftests/damon/drgn_dump_damon_status: support failed region quota charge ratio
- status: Reviewed
- review: No issues found.
- [RFC PATCH 9/9] selftets/damon/sysfs.py: test failed region quota charge ratio
- status: Reviewed
- review: No issues found.

# hkml [1] generated a draft of this mail. It can be regenerated
# using below command:
#
# hkml patch sashiko_dev --thread_status --for_forwarding \
Thanks,
SJ

SeongJae Park

unread,
Apr 5, 2026, 11:12:38 AM (6 days ago) Apr 5
to SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Changelog
=========

Changes from RFC v1
(https://lore.kernel.org/202604041639...@kernel.org)
- Avoid overflows in charge amount calculation.
- Fix/wordsmith documentation for grammar, typo, and wrong examples.
- Improve unit test for more consistent comparison source use.

SeongJae Park (9):
mm/damon/core: introduce failed region quota charge ratio
mm/damon/sysfs-schemes: implement fail_charge_{num,denom} files
Docs/mm/damon/design: document fail_charge_{num,denom}
Docs/admin-guide/mm/damon/usage: document fail_charge_{num,denom}
files
Docs/ABI/damon: document fail_charge_{num,denom}
mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
selftets/damon/_damon_sysfs: support failed region quota charge ratio
selftests/damon/drgn_dump_damon_status: support failed region quota
charge ratio
selftets/damon/sysfs.py: test failed region quota charge ratio

.../ABI/testing/sysfs-kernel-mm-damon | 12 +++++
Documentation/admin-guide/mm/damon/usage.rst | 18 +++++--
Documentation/mm/damon/design.rst | 21 ++++++++
include/linux/damon.h | 9 ++++
mm/damon/core.c | 21 +++++++-
mm/damon/sysfs-schemes.c | 54 +++++++++++++++++++
mm/damon/tests/core-kunit.h | 6 +++
tools/testing/selftests/damon/_damon_sysfs.py | 21 +++++++-
.../selftests/damon/drgn_dump_damon_status.py | 2 +
tools/testing/selftests/damon/sysfs.py | 6 +++
10 files changed, 163 insertions(+), 7 deletions(-)


base-commit: 36eed23041e834175ca57dc38ac0e128808b1abb
--
2.47.3

SeongJae Park

unread,
Apr 5, 2026, 11:12:41 AM (6 days ago) Apr 5
to SeongJae Park, Andrew Morton, Brendan Higgins, David Gow, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Extend damos_test_commit_quotas() kunit test to ensure
damos_commit_quota() handles fail_charge_{num,denom} parameters.

Signed-off-by: SeongJae Park <s...@kernel.org>
---
mm/damon/tests/core-kunit.h | 6 ++++++
1 file changed, 6 insertions(+)

diff --git a/mm/damon/tests/core-kunit.h b/mm/damon/tests/core-kunit.h
index 0030f682b23b7..1b23a22ac04c4 100644
--- a/mm/damon/tests/core-kunit.h
+++ b/mm/damon/tests/core-kunit.h
@@ -694,6 +694,8 @@ static void damos_test_commit_quota(struct kunit *test)
.ms = 2,
.sz = 3,
.goal_tuner = DAMOS_QUOTA_GOAL_TUNER_CONSIST,
+ .fail_charge_num = 2,
+ .fail_charge_denom = 3,
.weight_sz = 4,
.weight_nr_accesses = 5,
.weight_age = 6,
@@ -703,6 +705,8 @@ static void damos_test_commit_quota(struct kunit *test)
.ms = 8,
.sz = 9,
.goal_tuner = DAMOS_QUOTA_GOAL_TUNER_TEMPORAL,
+ .fail_charge_num = 1,
+ .fail_charge_denom = 1024,
.weight_sz = 10,
.weight_nr_accesses = 11,
.weight_age = 12,
@@ -717,6 +721,8 @@ static void damos_test_commit_quota(struct kunit *test)
KUNIT_EXPECT_EQ(test, dst.ms, src.ms);
KUNIT_EXPECT_EQ(test, dst.sz, src.sz);
KUNIT_EXPECT_EQ(test, dst.goal_tuner, src.goal_tuner);
+ KUNIT_EXPECT_EQ(test, dst.fail_charge_num, src.fail_charge_num);
+ KUNIT_EXPECT_EQ(test, dst.fail_charge_denom, src.fail_charge_denom);
KUNIT_EXPECT_EQ(test, dst.weight_sz, src.weight_sz);
KUNIT_EXPECT_EQ(test, dst.weight_nr_accesses, src.weight_nr_accesses);
KUNIT_EXPECT_EQ(test, dst.weight_age, src.weight_age);
--
2.47.3

SeongJae Park

unread,
Apr 6, 2026, 9:05:42 PM (5 days ago) Apr 6
to SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Patch 1 updates fully charged quota check to handle <min_region_sz
remaining quota, which will be able to exist after this series is
applied. Patch 2 implements the feature and exposes it via DAMON core
API. Patch 3 implements DAMON sysfs ABI for the feature. Three
following patches (4-6) document the feature and ABI on design, usage,
and ABI documents, respectively. Four patches for testing of the new
feature follow. Patch 7 implements a kunit test for the feature.
Patches 8 and 9 extend DAMON selftest helpers for DAMON sysfs control
and internal state dumping for adding a new selftest for the feature.
Patch 10 extends existing DAMON sysfs interface selftest to test the new
feature using the extended helper scripts.

Changelog
=========

Changes from RFC v2
(https://lore.kernel.org/2026040515123...@kernel.org)
- Handle <min_region_sz remaining quota.
- Document zero denum behavior.
- Fix typos: s/selftets/selftests/
Changes from RFC v1
(https://lore.kernel.org/202604041639...@kernel.org)
- Avoid overflows in charge amount calculation.
- Fix/wordsmith documentation for grammar, typo, and wrong examples.
- Improve unit test for more consistent comparison source use.

SeongJae Park (10):
mm/damon/core: handle <min_region_sz remaining quota as empty
mm/damon/core: introduce failed region quota charge ratio
mm/damon/sysfs-schemes: implement fail_charge_{num,denom} files
Docs/mm/damon/design: document fail_charge_{num,denom}
Docs/admin-guide/mm/damon/usage: document fail_charge_{num,denom}
files
Docs/ABI/damon: document fail_charge_{num,denom}
mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
selftests/damon/_damon_sysfs: support failed region quota charge ratio
selftests/damon/drgn_dump_damon_status: support failed region quota
charge ratio
selftests/damon/sysfs.py: test failed region quota charge ratio

.../ABI/testing/sysfs-kernel-mm-damon | 12 +++++
Documentation/admin-guide/mm/damon/usage.rst | 18 +++++--
Documentation/mm/damon/design.rst | 22 ++++++++
include/linux/damon.h | 9 ++++
mm/damon/core.c | 38 ++++++++++---
mm/damon/sysfs-schemes.c | 54 +++++++++++++++++++
mm/damon/tests/core-kunit.h | 6 +++
tools/testing/selftests/damon/_damon_sysfs.py | 21 +++++++-
.../selftests/damon/drgn_dump_damon_status.py | 2 +
tools/testing/selftests/damon/sysfs.py | 6 +++
10 files changed, 175 insertions(+), 13 deletions(-)


base-commit: b1ca86c92674eaf92a32ce3a2d89a0349e406df1
--
2.47.3

SeongJae Park

unread,
Apr 6, 2026, 9:05:44 PM (5 days ago) Apr 6
to SeongJae Park, Andrew Morton, Brendan Higgins, David Gow, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org

Bijan Tabatabai

unread,
Apr 8, 2026, 12:51:20 PM (3 days ago) Apr 8
to SeongJae Park, Bijan Tabatabai, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
On Mon, 6 Apr 2026 18:05:22 -0700 SeongJae Park <s...@kernel.org> wrote:

Hi SJ,
Thanks for this series. This is a problem I have come across and am looking
forward to seeing this land.
This makes sense, but the quota is also considered when setting the minimum
allowable score in damos_adjust_quota(), which, to my understanding, assumes
that all of the all of a region's data will by applied. If an action fails for
a significant amount of the memory, a lower score than what was calculated in
damos_adjust_quota() could be valid. If that's the case, the scheme would be
applied to fewer regions than strictly necessary.

As you mention above, this is not a correctness issue because the quota only
guarantees an upper limit on the amount of data the scheme is applied to.
Additionally, it may very well be true that what I listed above would not be
very noticeable in practice. I just thought this was worth pointing out as
something to think about.

Thanks,
Bijan

<snip>

Sent using hkml (https://github.com/sjp38/hackermail)

SeongJae Park

unread,
Apr 8, 2026, 8:00:53 PM (3 days ago) Apr 8
to Bijan Tabatabai, SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Thank you for acknowledging. I'm hoping this to land on 7.2-rc1.

[...]
> > DAMOS Action Failed Region Quota Charge Ratio
> > =============================================
> >
> > Let users set the charge ratio for the action-failed memory, for more
> > optimal and deterministic use of DAMOS. It allows users to specify the
> > numerator and the denominator of the ratio for flexible setup. For
> > example, let's suppose the numerator and the denominator are set to 1
> > and 4,096, respectively. The ratio is 1 / 4,096. A DAMOS scheme action
> > is applied to 5 GiB memory. For 1 GiB of the memory, the action is
> > succeeded. For the rest (4 GiB), the action is failed. Then, only 1
> > GiB and 1 MiB quota is charged.
> >
> > The optimal charge ratio will depend on the use case and
> > system/workload. I'd recommend starting from setting the nominator as 1
> > and the denominator as PAGE_SIZE and tune based on the results, because
> > many DAMOS actions are applied at page level.
>
> This makes sense, but the quota is also considered when setting the minimum
> allowable score in damos_adjust_quota(), which, to my understanding, assumes
> that all of the all of a region's data will by applied. If an action fails for
> a significant amount of the memory, a lower score than what was calculated in
> damos_adjust_quota() could be valid. If that's the case, the scheme would be
> applied to fewer regions than strictly necessary.

Good point, you are right.

>
> As you mention above, this is not a correctness issue because the quota only
> guarantees an upper limit on the amount of data the scheme is applied to.

I agree.

> Additionally, it may very well be true that what I listed above would not be
> very noticeable in practice.

I guess it is hopefully true, for following reason.

The score for each region is calculated as a weigted sum of the access
frequency and the age of the region. To avoid DAMOS action is repeatedly
applied to only a few regions, we reset age of regions after a DAMOS action is
applied to the region, regardless of the action failure. So, periodically the
score of the regions having the action unapplicable region will get low, make
no big impact to the minimum score threshold calculation.

But real data could say something different. I will be happy to be proven
wrong my real data. :)

> I just thought this was worth pointing out as
> something to think about.

Indeed. Thank you for pointing out. Nonetheless this is not a new issue that
introduced by this patch series. And the impact is not clear at the moment. I
will be happy to revisit this in parallel to this patch series.


Thanks,
SJ

[...]

SeongJae Park

unread,
Apr 9, 2026, 10:21:59 AM (2 days ago) Apr 9
to SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
It is Not a Bug but a Feature; But...
=====================================

So nothing is broken. DAMOS quota is working as intended, as the upper
limit of the speed. It also provides its behavior observability via
DAMOS stat. In the real world production environment that runs long
term active workloads and matters stability, the speed sometimes being
slow is not a real problem.

But, the non-deterministic behavior is sometimes annoying, especially in
lab environments. Even in a realistic production environment, when
there is a huge amount of DAMOS action unapplicable memory, the speed
could be problematically slow. Let's suppose a virtual machines
provider that setup 99% of the host memory as hugetlb pages that cannot
be reclaimed, to give it to virtual machines. Also, when aim-oriented
DAMOS auto-tuning is applied, this could also make the internal feedback
loop confused.

The intention of the current behavior was that trying DAMOS action to
regions would anyway impose some overhead, and therefore somehow be
charged. But in the real world, the overhead for failed action is much
lighter than successful action. Charging those at the same ratio may be
unfair, or at least suboptimum in some environments.

DAMOS Action Failed Region Quota Charge Ratio
=============================================

Let users set the charge ratio for the action-failed memory, for more
optimal and deterministic use of DAMOS. It allows users to specify the
numerator and the denominator of the ratio for flexible setup. For
example, let's suppose the numerator and the denominator are set to 1
and 4,096, respectively. The ratio is 1 / 4,096. A DAMOS scheme action
is applied to 5 GiB memory. For 1 GiB of the memory, the action is
succeeded. For the rest (4 GiB), the action is failed. Then, only 1
GiB and 1 MiB quota is charged.

The optimal charge ratio will depend on the use case and
system/workload. I'd recommend starting from setting the nominator as 1
and the denominator as PAGE_SIZE and tune based on the results, because
many DAMOS actions are applied at page level.

First two patches make preparational changes. Patch 1 updates fully
charged quota check to handle <min_region_sz remaining quota, which will
be able to exist after this series is applied. Patch 2 merges regions
that split out for quota as soon as possible, since the split can happen
much more frequently under a corner case that this series will make
available.

Patch 3 implements the feature and exposes it via DAMON core API. Patch
4 implements DAMON sysfs ABI for the feature. Three following patches
(5-7) document the feature and ABI on design, usage, and ABI documents,
respectively. Four patches for testing of the new feature follow.
Patch 8 implements a kunit test for the feature. Patches 9 and 10
extend DAMON selftest helpers for DAMON sysfs control and internal state
dumping for adding a new selftest for the feature. Patch 11 extends
existing DAMON sysfs interface selftest to test the new feature using
the extended helper scripts.

Changelog
=========

Changes from RFC v3
(https://lore.kernel.org/202604070105...@kernel.org)
- Make damos_quota_is_full() safe from overflow and easier to read.
- Avoid quota-based region split making too many new regions.
Changes from RFC v2
(https://lore.kernel.org/2026040515123...@kernel.org)
- Handle <min_region_sz remaining quota.
- Document zero denum behavior.
- Fix typos: s/selftets/selftests/
Changes from RFC v1
(https://lore.kernel.org/202604041639...@kernel.org)
- Avoid overflows in charge amount calculation.
- Fix/wordsmith documentation for grammar, typo, and wrong examples.
- Improve unit test for more consistent comparison source use.

SeongJae Park (11):
mm/damon/core: handle <min_region_sz remaining quota as empty
mm/damon/core: merge quota-sliced regions back
mm/damon/core: introduce failed region quota charge ratio
mm/damon/sysfs-schemes: implement fail_charge_{num,denom} files
Docs/mm/damon/design: document fail_charge_{num,denom}
Docs/admin-guide/mm/damon/usage: document fail_charge_{num,denom}
files
Docs/ABI/damon: document fail_charge_{num,denom}
mm/damon/tests/core-kunit: test fail_charge_{num,denom} committing
selftests/damon/_damon_sysfs: support failed region quota charge ratio
selftests/damon/drgn_dump_damon_status: support failed region quota
charge ratio
selftests/damon/sysfs.py: test failed region quota charge ratio

.../ABI/testing/sysfs-kernel-mm-damon | 12 +++
Documentation/admin-guide/mm/damon/usage.rst | 18 ++++-
Documentation/mm/damon/design.rst | 22 ++++++
include/linux/damon.h | 9 +++
mm/damon/core.c | 76 ++++++++++++++++---
mm/damon/sysfs-schemes.c | 54 +++++++++++++
mm/damon/tests/core-kunit.h | 6 ++
tools/testing/selftests/damon/_damon_sysfs.py | 21 ++++-
.../selftests/damon/drgn_dump_damon_status.py | 2 +
tools/testing/selftests/damon/sysfs.py | 6 ++
10 files changed, 209 insertions(+), 17 deletions(-)


base-commit: dcd9caafdc7ec3f936d87d9698a6c126f77e9750
--
2.47.3

SeongJae Park

unread,
Apr 9, 2026, 10:22:04 AM (2 days ago) Apr 9
to SeongJae Park, Andrew Morton, Brendan Higgins, David Gow, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org

SeongJae Park

unread,
Apr 10, 2026, 10:20:49 AM (yesterday) Apr 10
to SeongJae Park, Andrew Morton, Brendan Higgins, David Gow, da...@lists.linux.dev, kuni...@googlegroups.com, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org

SeongJae Park

unread,
Apr 10, 2026, 10:20:49 AM (yesterday) Apr 10
to SeongJae Park, Liam R. Howlett, Andrew Morton, Brendan Higgins, David Gow, David Hildenbrand, Jonathan Corbet, Lorenzo Stoakes, Michal Hocko, Mike Rapoport, Shuah Khan, Shuah Khan, Suren Baghdasaryan, Vlastimil Babka, da...@lists.linux.dev, kuni...@googlegroups.com, linu...@vger.kernel.org, linux-...@vger.kernel.org, linux-k...@vger.kernel.org, linu...@kvack.org
Changes from RFC v4
(https://lore.kernel.org/202604091421...@kernel.org)
- Fix quota-sliced region merge-back issues.
- Use damon_for_each_region() instead of damon_for_each_region_safe().
- Avoid merging back of sliced but scheme unapplied regions, to keep
the monitoring information.
Documentation/admin-guide/mm/damon/usage.rst | 18 +++-
Documentation/mm/damon/design.rst | 22 +++++
include/linux/damon.h | 9 ++
mm/damon/core.c | 83 ++++++++++++++++---
mm/damon/sysfs-schemes.c | 54 ++++++++++++
mm/damon/tests/core-kunit.h | 6 ++
tools/testing/selftests/damon/_damon_sysfs.py | 21 ++++-
.../selftests/damon/drgn_dump_damon_status.py | 2 +
tools/testing/selftests/damon/sysfs.py | 6 ++
10 files changed, 216 insertions(+), 17 deletions(-)


base-commit: fe17d40616ec462138186edb32f3105b0c064674
--
2.47.3
Reply all
Reply to author
Forward
0 new messages