public inbox for linux-perf-users@vger.kernel.org
 help / color / mirror / Atom feed
From: sashiko-bot@kernel.org
To: "Akinobu Mita" <akinobu.mita@gmail.com>
Cc: damon@lists.linux.dev, linux-perf-users@vger.kernel.org
Subject: Re: [RFC PATCH v3 2/4] mm/damon/core: add common code for perf event based access check
Date: Thu, 23 Apr 2026 01:58:23 +0000	[thread overview]
Message-ID: <20260423015824.81098C19425@smtp.kernel.org> (raw)
In-Reply-To: <20260423004211.7037-3-akinobu.mita@gmail.com>

Sashiko AI review found 3 potential issue(s):
- [High] Memory leak in `damon_perf_init()` when `perf_event_create_kernel_counter()` fails with `-ENODEV` for all CPUs.
- [Medium] Unnecessary `PERF_SAMPLE_WEIGHT_STRUCT` flag in perf event attributes arbitrarily restricts hardware compatibility.
- [Low] Linker error when `CONFIG_DAMON_VADDR=n` but `CONFIG_PERF_EVENTS=y`.
--

commit 97617fb5ae7981867a46207cd14a68c3cbb4813d
Author: Akinobu Mita <akinobu.mita@gmail.com>

mm/damon/core: add common code for perf event based access check

This commit creates the necessary infrastructure (structure definitions,
functions, sysfs interfaces) to support perf event based access checks
for both physical and virtual address space monitoring.

> diff --git a/mm/damon/core.c b/mm/damon/core.c
> index a52b2962aa22a..220b105482daa 100644
> --- a/mm/damon/core.c
> +++ b/mm/damon/core.c
[ ... ]
> @@ -2933,6 +2990,7 @@ static void kdamond_init_ctx(struct damon_ctx *ctx)
>  	unsigned long sample_interval = ctx->attrs.sample_interval ?
>  		ctx->attrs.sample_interval : 1;
>  	struct damos *scheme;
> +	struct damon_perf_event *event, *next;
>  
>  	ctx->passed_sample_intervals = 0;
>  	ctx->next_aggregation_sis = ctx->attrs.aggr_interval / sample_interval;
> @@ -2945,6 +3003,15 @@ static void kdamond_init_ctx(struct damon_ctx *ctx)
>  		damos_set_next_apply_sis(scheme, ctx);
>  		damos_set_filters_default_reject(scheme);
>  	}
> +
> +	list_for_each_entry_safe(event, next, &ctx->perf_events, list) {
> +		int err = damon_perf_init(ctx, event);

If the kernel is configured with CONFIG_DAMON_VADDR=n and
CONFIG_PERF_EVENTS=y, will this cause a linker error? The function
damon_perf_init() is defined in mm/damon/vaddr.c, which would not be
compiled in that configuration.

> +
> +		if (err) {
> +			list_del(&event->list);
> +			kfree(event);
> +		}
> +	}
>  }
>  
>  /*
> diff --git a/mm/damon/vaddr.c b/mm/damon/vaddr.c
> index b069dbc7e3d25..1534372e7637c 100644
> --- a/mm/damon/vaddr.c
> +++ b/mm/damon/vaddr.c
[ ... ]
> @@ -936,6 +939,161 @@ static int damon_va_scheme_score(struct damon_ctx *context,
>  	return DAMOS_MAX_SCORE;
>  }
>  
> +#ifdef CONFIG_PERF_EVENTS
[ ... ]
> +int damon_perf_init(struct damon_ctx *ctx, struct damon_perf_event *event)
> +{
> +	struct damon_perf *perf;
> +	struct perf_event_attr attr = {
> +		.type = PERF_TYPE_RAW,
> +		.size = sizeof(attr),
> +		.type = event->attr.type,
> +		.config = event->attr.config,
> +		.config1 = event->attr.config1,
> +		.config2 = event->attr.config2,
> +		.sample_freq = event->attr.sample_freq,
> +		.freq = 1,
> +		.sample_type = PERF_SAMPLE_TIME | PERF_SAMPLE_ADDR |
> +			PERF_SAMPLE_PERIOD | PERF_SAMPLE_DATA_SRC |
> +			(event->attr.sample_phys_addr ? PERF_SAMPLE_PHYS_ADDR : 0) |
> +			PERF_SAMPLE_WEIGHT_STRUCT,

Does this configuration need to include PERF_SAMPLE_WEIGHT_STRUCT?

The overflow handler damon_perf_overflow() doesn't appear to read any
weight metrics from the sample data. If the underlying hardware PMU does
not support extended weight sampling, could this cause
perf_event_create_kernel_counter() to return -EINVAL and unnecessarily
reject the configuration?

> +		.precise_ip = 2,
> +		.pinned = 1,
> +		.disabled = 1,
> +	};
> +	int cpu;
> +	int err = -ENOMEM;
> +	bool found = false;
> +
> +	perf = kzalloc_obj(*perf);
> +	if (!perf)
> +		return -ENOMEM;
> +
> +	perf->event = alloc_percpu(typeof(*perf->event));
> +	if (!perf->event)
> +		goto free_percpu;
> +
> +	perf->buffer = alloc_percpu(typeof(*perf->buffer));
> +	if (!perf->buffer)
> +		goto free_percpu;
> +
> +	for_each_possible_cpu(cpu) {
> +		struct perf_event *perf_event;
> +		struct damon_perf_buffer *buffer = per_cpu_ptr(perf->buffer, cpu);
> +
> +		perf_event = perf_event_create_kernel_counter(&attr, cpu, NULL,
> +				damon_perf_overflow, event);
> +		if (IS_ERR(perf_event)) {
> +			err = PTR_ERR(perf_event);
> +			if (err == -ENODEV)
> +				continue;
> +			pr_err("perf event create on CPU %d failed with %d\n", cpu, err);
> +			goto free_for_each_cpu;
> +		}
> +		found = true;
> +		*per_cpu_ptr(perf->event, cpu) = perf_event;
> +
> +		buffer->size = DAMON_PERF_INIT_RECORDS;
> +		buffer->reports = kvcalloc_node(buffer->size, sizeof(buffer->reports[0]),
> +						GFP_KERNEL, cpu_to_node(cpu));
> +		if (!buffer->reports)
> +			goto free_for_each_cpu;
> +	}
> +	event->priv = perf;
> +
> +	return found ? 0 : -ENODEV;

If perf_event_create_kernel_counter() returns -ENODEV for all possible CPUs,
the found flag remains false, and this returns -ENODEV.

Since the caller will receive a non-zero error code and free the event
wrapper without calling damon_perf_cleanup(), does this leak the memory
allocated for perf, perf->event, and perf->buffer?

> +
> +free_for_each_cpu:
> +	for_each_possible_cpu(cpu) {
> +		struct perf_event *perf_event = per_cpu(*perf->event, cpu);
> +		struct damon_perf_buffer *buffer = per_cpu_ptr(perf->buffer, cpu);
> +
> +		if (perf_event)
> +			perf_event_release_kernel(perf_event);
> +		kvfree(buffer->reports);
> +	}
> +free_percpu:
> +	free_percpu(perf->event);
> +	free_percpu(perf->buffer);
> +	kfree(perf);
> +
> +	return err;
> +}

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260423004211.7037-1-akinobu.mita@gmail.com?part=2

  reply	other threads:[~2026-04-23  1:58 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-04-23  0:42 [RFC PATCH v3 0/4] mm/damon: introduce perf event based access check Akinobu Mita
2026-04-23  0:42 ` [RFC PATCH v3 1/4] mm/damon/core: add code borrowed from report-based monitoring work Akinobu Mita
2026-04-23  1:21   ` sashiko-bot
2026-04-23  0:42 ` [RFC PATCH v3 2/4] mm/damon/core: add common code for perf event based access check Akinobu Mita
2026-04-23  1:58   ` sashiko-bot [this message]
2026-04-23  0:42 ` [RFC PATCH v3 3/4] mm/damon/vaddr: support " Akinobu Mita
2026-04-23  2:48   ` sashiko-bot
2026-04-23  0:42 ` [RFC PATCH v3 4/4] mm/damon/paddr: " Akinobu Mita
2026-04-23  3:22   ` sashiko-bot
2026-04-23  4:34 ` [RFC PATCH v3 0/4] mm/damon: introduce " SeongJae Park
2026-04-24  3:27   ` Akinobu Mita
2026-04-24 23:31     ` SeongJae Park
2026-04-25 12:33       ` Akinobu Mita
2026-04-25 15:33         ` SeongJae Park

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260423015824.81098C19425@smtp.kernel.org \
    --to=sashiko-bot@kernel.org \
    --cc=akinobu.mita@gmail.com \
    --cc=damon@lists.linux.dev \
    --cc=linux-perf-users@vger.kernel.org \
    --cc=sashiko@lists.linux.dev \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox