[v2,2/2] perf machine: Include data symbols in the kernel map

Message ID 20230725001929.368041-2-namhyung@kernel.org
State New
Headers
Series [v2,1/2] perf tools: Add kallsyms__get_symbol_start() |

Commit Message

Namhyung Kim July 25, 2023, 12:19 a.m. UTC
  When perf record -d is used, it needs data mmaps to symbolize global data.
But it missed to collect kernel data maps so it cannot symbolize them.
Instead of having a separate map, just increase the kernel map size to
include the data section.

Probably we can have a separate kernel map for data, but the current
code assumes a single kernel map.  So it'd require more changes in other
places and looks error-prone.  I decided not to go that way for now.

Also it seems the kernel module size already includes the data section.

For example, my system has the following.

  $ grep -e _stext -e _etext -e _edata /proc/kallsyms
  ffffffff99800000 T _stext
  ffffffff9a601ac8 T _etext
  ffffffff9b446a00 D _edata

Size of the text section is (0x9a601ac8 - 0x99800000 = 0xe01ac8) and
size including data section is (0x9b446a00 - 0x99800000 = 0x1c46a00).

Before:
  $ perf record -d true

  $ perf report -D | grep MMAP | head -1
  0 0 0x460 [0x60]: PERF_RECORD_MMAP -1/0: [0xffffffff99800000(0xe01ac8) @ 0xffffffff99800000]: x [kernel.kallsyms]_text
                                                               ^^^^^^^^
                                                                 here
After:
  $ perf report -D | grep MMAP | head -1
  0 0 0x460 [0x60]: PERF_RECORD_MMAP -1/0: [0xffffffff99800000(0x1c46a00) @ 0xffffffff99800000]: x [kernel.kallsyms]_text
                                                               ^^^^^^^^^

Instead of just replacing it to _edata, try _edata first and then fall
back to _etext just in case.

Signed-off-by: Namhyung Kim <namhyung@kernel.org>
---
 tools/perf/util/machine.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)
  

Comments

Adrian Hunter July 25, 2023, 2:08 p.m. UTC | #1
On 25/07/23 03:19, Namhyung Kim wrote:
> When perf record -d is used, it needs data mmaps to symbolize global data.
> But it missed to collect kernel data maps so it cannot symbolize them.
> Instead of having a separate map, just increase the kernel map size to
> include the data section.
> 
> Probably we can have a separate kernel map for data, but the current
> code assumes a single kernel map.  So it'd require more changes in other
> places and looks error-prone.  I decided not to go that way for now.
> 
> Also it seems the kernel module size already includes the data section.
> 
> For example, my system has the following.
> 
>   $ grep -e _stext -e _etext -e _edata /proc/kallsyms
>   ffffffff99800000 T _stext
>   ffffffff9a601ac8 T _etext
>   ffffffff9b446a00 D _edata
> 
> Size of the text section is (0x9a601ac8 - 0x99800000 = 0xe01ac8) and
> size including data section is (0x9b446a00 - 0x99800000 = 0x1c46a00).
> 
> Before:
>   $ perf record -d true
> 
>   $ perf report -D | grep MMAP | head -1
>   0 0 0x460 [0x60]: PERF_RECORD_MMAP -1/0: [0xffffffff99800000(0xe01ac8) @ 0xffffffff99800000]: x [kernel.kallsyms]_text
>                                                                ^^^^^^^^
>                                                                  here
> After:
>   $ perf report -D | grep MMAP | head -1
>   0 0 0x460 [0x60]: PERF_RECORD_MMAP -1/0: [0xffffffff99800000(0x1c46a00) @ 0xffffffff99800000]: x [kernel.kallsyms]_text
>                                                                ^^^^^^^^^
> 
> Instead of just replacing it to _edata, try _edata first and then fall
> back to _etext just in case.
> 
> Signed-off-by: Namhyung Kim <namhyung@kernel.org>

Acked-by: Adrian Hunter <adrian.hunter@intel.com>

> ---
>  tools/perf/util/machine.c | 4 +++-
>  1 file changed, 3 insertions(+), 1 deletion(-)
> 
> diff --git a/tools/perf/util/machine.c b/tools/perf/util/machine.c
> index 4e62843d51b7..11de3ca8d4fa 100644
> --- a/tools/perf/util/machine.c
> +++ b/tools/perf/util/machine.c
> @@ -1216,7 +1216,9 @@ static int machine__get_running_kernel_start(struct machine *machine,
>  
>  	*start = addr;
>  
> -	err = kallsyms__get_function_start(filename, "_etext", &addr);
> +	err = kallsyms__get_symbol_start(filename, "_edata", &addr);
> +	if (err)
> +		err = kallsyms__get_function_start(filename, "_etext", &addr);
>  	if (!err)
>  		*end = addr;
>
  

Patch

diff --git a/tools/perf/util/machine.c b/tools/perf/util/machine.c
index 4e62843d51b7..11de3ca8d4fa 100644
--- a/tools/perf/util/machine.c
+++ b/tools/perf/util/machine.c
@@ -1216,7 +1216,9 @@  static int machine__get_running_kernel_start(struct machine *machine,
 
 	*start = addr;
 
-	err = kallsyms__get_function_start(filename, "_etext", &addr);
+	err = kallsyms__get_symbol_start(filename, "_edata", &addr);
+	if (err)
+		err = kallsyms__get_function_start(filename, "_etext", &addr);
 	if (!err)
 		*end = addr;