| From 40a340ecf2bd4c2857ec7afb7f1aa1250428d1a7 Mon Sep 17 00:00:00 2001 |
| From: Sasha Levin <sashal@kernel.org> |
| Date: Wed, 4 Nov 2020 17:42:29 +0800 |
| Subject: perf lock: Don't free "lock_seq_stat" if read_count isn't zero |
| |
| From: Leo Yan <leo.yan@linaro.org> |
| |
| [ Upstream commit b0e5a05cc9e37763c7f19366d94b1a6160c755bc ] |
| |
| When execute command "perf lock report", it hits failure and outputs log |
| as follows: |
| |
| perf: builtin-lock.c:623: report_lock_release_event: Assertion `!(seq->read_count < 0)' failed. |
| Aborted |
| |
| This is an imbalance issue. The locking sequence structure |
| "lock_seq_stat" contains the reader counter and it is used to check if |
| the locking sequence is balance or not between acquiring and releasing. |
| |
| If the tool wrongly frees "lock_seq_stat" when "read_count" isn't zero, |
| the "read_count" will be reset to zero when allocate a new structure at |
| the next time; thus it causes the wrong counting for reader and finally |
| results in imbalance issue. |
| |
| To fix this issue, if detects "read_count" is not zero (means still have |
| read user in the locking sequence), goto the "end" tag to skip freeing |
| structure "lock_seq_stat". |
| |
| Fixes: e4cef1f65061 ("perf lock: Fix state machine to recognize lock sequence") |
| Signed-off-by: Leo Yan <leo.yan@linaro.org> |
| Acked-by: Jiri Olsa <jolsa@redhat.com> |
| Link: https://lore.kernel.org/r/20201104094229.17509-2-leo.yan@linaro.org |
| Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com> |
| Signed-off-by: Sasha Levin <sashal@kernel.org> |
| --- |
| tools/perf/builtin-lock.c | 2 +- |
| 1 file changed, 1 insertion(+), 1 deletion(-) |
| |
| diff --git a/tools/perf/builtin-lock.c b/tools/perf/builtin-lock.c |
| index 6e0189df2b3ba..0cb7f7b731fb0 100644 |
| --- a/tools/perf/builtin-lock.c |
| +++ b/tools/perf/builtin-lock.c |
| @@ -620,7 +620,7 @@ static int report_lock_release_event(struct perf_evsel *evsel, |
| case SEQ_STATE_READ_ACQUIRED: |
| seq->read_count--; |
| BUG_ON(seq->read_count < 0); |
| - if (!seq->read_count) { |
| + if (seq->read_count) { |
| ls->nr_release++; |
| goto end; |
| } |
| -- |
| 2.27.0 |
| |