Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

perf thread: Generalize function to copy from thread addr space from intel-bts code

Add a utility function to fetch executable code. Convert one
user over to it. There are more places doing that, but they
do significantly different actions, so they are not
easy to fit into a single library function.

Committer changes:

. No need to cast around, make 'buf' be a void pointer.

. Rename it to thread__memcpy() to reflect the fact it is about copying
a chunk of memory from a thread, i.e. from its address space.

. No need to have it in a separate object file, move it to thread.[ch]

. Check the return of map__load(), the original code didn't do it, but
since we're moving this around, check that as well.

Signed-off-by: Andi Kleen <ak@linux.intel.com>
Cc: Jiri Olsa <jolsa@kernel.org>
Cc: Namhyung Kim <namhyung@kernel.org>
Link: https://lkml.kernel.org/r/20190305144758.12397-2-andi@firstfloor.org
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>

authored by

Andi Kleen and committed by
Arnaldo Carvalho de Melo
15325938 bc3bb795

+28 -18
+2 -18
tools/perf/util/intel-bts.c
··· 328 328 { 329 329 struct machine *machine = btsq->bts->machine; 330 330 struct thread *thread; 331 - struct addr_location al; 332 331 unsigned char buf[INTEL_PT_INSN_BUF_SZ]; 333 332 ssize_t len; 334 - int x86_64; 335 - uint8_t cpumode; 333 + bool x86_64; 336 334 int err = -1; 337 - 338 - if (machine__kernel_ip(machine, ip)) 339 - cpumode = PERF_RECORD_MISC_KERNEL; 340 - else 341 - cpumode = PERF_RECORD_MISC_USER; 342 335 343 336 thread = machine__find_thread(machine, -1, btsq->tid); 344 337 if (!thread) 345 338 return -1; 346 339 347 - if (!thread__find_map(thread, cpumode, ip, &al) || !al.map->dso) 348 - goto out_put; 349 - 350 - len = dso__data_read_addr(al.map->dso, al.map, machine, ip, buf, 351 - INTEL_PT_INSN_BUF_SZ); 340 + len = thread__memcpy(thread, machine, buf, ip, INTEL_PT_INSN_BUF_SZ, &x86_64); 352 341 if (len <= 0) 353 342 goto out_put; 354 - 355 - /* Load maps to ensure dso->is_64_bit has been updated */ 356 - map__load(al.map); 357 - 358 - x86_64 = al.map->dso->is_64_bit; 359 343 360 344 if (intel_pt_get_insn(buf, len, x86_64, &btsq->intel_pt_insn)) 361 345 goto out_put;
+23
tools/perf/util/thread.c
··· 12 12 #include "debug.h" 13 13 #include "namespaces.h" 14 14 #include "comm.h" 15 + #include "map.h" 15 16 #include "symbol.h" 16 17 #include "unwind.h" 17 18 ··· 393 392 return NULL; 394 393 395 394 return machine__find_thread(machine, thread->pid_, thread->pid_); 395 + } 396 + 397 + int thread__memcpy(struct thread *thread, struct machine *machine, 398 + void *buf, u64 ip, int len, bool *is64bit) 399 + { 400 + u8 cpumode = PERF_RECORD_MISC_USER; 401 + struct addr_location al; 402 + long offset; 403 + 404 + if (machine__kernel_ip(machine, ip)) 405 + cpumode = PERF_RECORD_MISC_KERNEL; 406 + 407 + if (!thread__find_map(thread, cpumode, ip, &al) || !al.map->dso || 408 + al.map->dso->data.status == DSO_DATA_STATUS_ERROR || 409 + map__load(al.map) < 0) 410 + return -1; 411 + 412 + offset = al.map->map_ip(al.map, ip); 413 + if (is64bit) 414 + *is64bit = al.map->dso->is_64_bit; 415 + 416 + return dso__data_read_offset(al.map->dso, machine, offset, buf, len); 396 417 }
+3
tools/perf/util/thread.h
··· 113 113 void thread__find_cpumode_addr_location(struct thread *thread, u64 addr, 114 114 struct addr_location *al); 115 115 116 + int thread__memcpy(struct thread *thread, struct machine *machine, 117 + void *buf, u64 ip, int len, bool *is64bit); 118 + 116 119 static inline void *thread__priv(struct thread *thread) 117 120 { 118 121 return thread->priv;