File Index
Files and directories
Sign in
FILE

symbol-elf.c

File preview with syntax highlighting.

linux-6.19.14/tools/perf/util/symbol-elf.c C
   1// SPDX-License-Identifier: GPL-2.0
   2#include <fcntl.h>
   3#include <stdio.h>
   4#include <errno.h>
   5#include <stdlib.h>
   6#include <string.h>
   7#include <unistd.h>
   8#include <inttypes.h>
   9
  10#include "compress.h"
  11#include "dso.h"
  12#include "libbfd.h"
  13#include "map.h"
  14#include "maps.h"
  15#include "symbol.h"
  16#include "symsrc.h"
  17#include "machine.h"
  18#include "vdso.h"
  19#include "debug.h"
  20#include "util/copyfile.h"
  21#include <linux/ctype.h>
  22#include <linux/kernel.h>
  23#include <linux/zalloc.h>
  24#include <linux/string.h>
  25#include <symbol/kallsyms.h>
  26#include <internal/lib.h>
  27
  28#ifndef EM_AARCH64
  29#define EM_AARCH64	183  /* ARM 64 bit */
  30#endif
  31
  32#ifndef EM_LOONGARCH
  33#define EM_LOONGARCH	258
  34#endif
  35
  36#ifndef ELF32_ST_VISIBILITY
  37#define ELF32_ST_VISIBILITY(o)	((o) & 0x03)
  38#endif
  39
  40/* For ELF64 the definitions are the same.  */
  41#ifndef ELF64_ST_VISIBILITY
  42#define ELF64_ST_VISIBILITY(o)	ELF32_ST_VISIBILITY (o)
  43#endif
  44
  45/* How to extract information held in the st_other field.  */
  46#ifndef GELF_ST_VISIBILITY
  47#define GELF_ST_VISIBILITY(val)	ELF64_ST_VISIBILITY (val)
  48#endif
  49
  50typedef Elf64_Nhdr GElf_Nhdr;
  51
  52
  53#ifndef HAVE_ELF_GETPHDRNUM_SUPPORT
  54static int elf_getphdrnum(Elf *elf, size_t *dst)
  55{
  56	GElf_Ehdr gehdr;
  57	GElf_Ehdr *ehdr;
  58
  59	ehdr = gelf_getehdr(elf, &gehdr);
  60	if (!ehdr)
  61		return -1;
  62
  63	*dst = ehdr->e_phnum;
  64
  65	return 0;
  66}
  67#endif
  68
  69#ifndef HAVE_ELF_GETSHDRSTRNDX_SUPPORT
  70static int elf_getshdrstrndx(Elf *elf __maybe_unused, size_t *dst __maybe_unused)
  71{
  72	pr_err("%s: update your libelf to > 0.140, this one lacks elf_getshdrstrndx().\n", __func__);
  73	return -1;
  74}
  75#endif
  76
  77#ifndef NT_GNU_BUILD_ID
  78#define NT_GNU_BUILD_ID 3
  79#endif
  80
  81/**
  82 * elf_symtab__for_each_symbol - iterate thru all the symbols
  83 *
  84 * @syms: struct elf_symtab instance to iterate
  85 * @idx: uint32_t idx
  86 * @sym: GElf_Sym iterator
  87 */
  88#define elf_symtab__for_each_symbol(syms, nr_syms, idx, sym) \
  89	for (idx = 0, gelf_getsym(syms, idx, &sym);\
  90	     idx < nr_syms; \
  91	     idx++, gelf_getsym(syms, idx, &sym))
  92
  93static inline uint8_t elf_sym__type(const GElf_Sym *sym)
  94{
  95	return GELF_ST_TYPE(sym->st_info);
  96}
  97
  98static inline uint8_t elf_sym__visibility(const GElf_Sym *sym)
  99{
 100	return GELF_ST_VISIBILITY(sym->st_other);
 101}
 102
 103#ifndef STT_GNU_IFUNC
 104#define STT_GNU_IFUNC 10
 105#endif
 106
 107static inline int elf_sym__is_function(const GElf_Sym *sym)
 108{
 109	return (elf_sym__type(sym) == STT_FUNC ||
 110		elf_sym__type(sym) == STT_GNU_IFUNC) &&
 111	       sym->st_name != 0 &&
 112	       sym->st_shndx != SHN_UNDEF;
 113}
 114
 115static inline bool elf_sym__is_object(const GElf_Sym *sym)
 116{
 117	return elf_sym__type(sym) == STT_OBJECT &&
 118		sym->st_name != 0 &&
 119		sym->st_shndx != SHN_UNDEF;
 120}
 121
 122static inline int elf_sym__is_label(const GElf_Sym *sym)
 123{
 124	return elf_sym__type(sym) == STT_NOTYPE &&
 125		sym->st_name != 0 &&
 126		sym->st_shndx != SHN_UNDEF &&
 127		sym->st_shndx != SHN_ABS &&
 128		elf_sym__visibility(sym) != STV_HIDDEN &&
 129		elf_sym__visibility(sym) != STV_INTERNAL;
 130}
 131
 132static bool elf_sym__filter(GElf_Sym *sym)
 133{
 134	return elf_sym__is_function(sym) || elf_sym__is_object(sym);
 135}
 136
 137static inline const char *elf_sym__name(const GElf_Sym *sym,
 138					const Elf_Data *symstrs)
 139{
 140	return symstrs->d_buf + sym->st_name;
 141}
 142
 143static inline const char *elf_sec__name(const GElf_Shdr *shdr,
 144					const Elf_Data *secstrs)
 145{
 146	return secstrs->d_buf + shdr->sh_name;
 147}
 148
 149static inline int elf_sec__is_text(const GElf_Shdr *shdr,
 150					const Elf_Data *secstrs)
 151{
 152	return strstr(elf_sec__name(shdr, secstrs), "text") != NULL;
 153}
 154
 155static inline bool elf_sec__is_data(const GElf_Shdr *shdr,
 156				    const Elf_Data *secstrs)
 157{
 158	return strstr(elf_sec__name(shdr, secstrs), "data") != NULL;
 159}
 160
 161static bool elf_sec__filter(GElf_Shdr *shdr, Elf_Data *secstrs)
 162{
 163	return elf_sec__is_text(shdr, secstrs) ||
 164	       elf_sec__is_data(shdr, secstrs);
 165}
 166
 167static size_t elf_addr_to_index(Elf *elf, GElf_Addr addr)
 168{
 169	Elf_Scn *sec = NULL;
 170	GElf_Shdr shdr;
 171	size_t cnt = 1;
 172
 173	while ((sec = elf_nextscn(elf, sec)) != NULL) {
 174		gelf_getshdr(sec, &shdr);
 175
 176		if ((addr >= shdr.sh_addr) &&
 177		    (addr < (shdr.sh_addr + shdr.sh_size)))
 178			return cnt;
 179
 180		++cnt;
 181	}
 182
 183	return -1;
 184}
 185
 186Elf_Scn *elf_section_by_name(Elf *elf, GElf_Ehdr *ep,
 187			     GElf_Shdr *shp, const char *name, size_t *idx)
 188{
 189	Elf_Scn *sec = NULL;
 190	size_t cnt = 1;
 191
 192	/* ELF is corrupted/truncated, avoid calling elf_strptr. */
 193	if (!elf_rawdata(elf_getscn(elf, ep->e_shstrndx), NULL))
 194		return NULL;
 195
 196	while ((sec = elf_nextscn(elf, sec)) != NULL) {
 197		char *str;
 198
 199		gelf_getshdr(sec, shp);
 200		str = elf_strptr(elf, ep->e_shstrndx, shp->sh_name);
 201		if (str && !strcmp(name, str)) {
 202			if (idx)
 203				*idx = cnt;
 204			return sec;
 205		}
 206		++cnt;
 207	}
 208
 209	return NULL;
 210}
 211
 212bool filename__has_section(const char *filename, const char *sec)
 213{
 214	int fd;
 215	Elf *elf;
 216	GElf_Ehdr ehdr;
 217	GElf_Shdr shdr;
 218	bool found = false;
 219
 220	fd = open(filename, O_RDONLY);
 221	if (fd < 0)
 222		return false;
 223
 224	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
 225	if (elf == NULL)
 226		goto out;
 227
 228	if (gelf_getehdr(elf, &ehdr) == NULL)
 229		goto elf_out;
 230
 231	found = !!elf_section_by_name(elf, &ehdr, &shdr, sec, NULL);
 232
 233elf_out:
 234	elf_end(elf);
 235out:
 236	close(fd);
 237	return found;
 238}
 239
 240static int elf_read_program_header(Elf *elf, u64 vaddr, GElf_Phdr *phdr)
 241{
 242	size_t i, phdrnum;
 243	u64 sz;
 244
 245	if (elf_getphdrnum(elf, &phdrnum))
 246		return -1;
 247
 248	for (i = 0; i < phdrnum; i++) {
 249		if (gelf_getphdr(elf, i, phdr) == NULL)
 250			return -1;
 251
 252		if (phdr->p_type != PT_LOAD)
 253			continue;
 254
 255		sz = max(phdr->p_memsz, phdr->p_filesz);
 256		if (!sz)
 257			continue;
 258
 259		if (vaddr >= phdr->p_vaddr && (vaddr < phdr->p_vaddr + sz))
 260			return 0;
 261	}
 262
 263	/* Not found any valid program header */
 264	return -1;
 265}
 266
 267struct rel_info {
 268	u32		nr_entries;
 269	u32		*sorted;
 270	bool		is_rela;
 271	Elf_Data	*reldata;
 272	GElf_Rela	rela;
 273	GElf_Rel	rel;
 274};
 275
 276static u32 get_rel_symidx(struct rel_info *ri, u32 idx)
 277{
 278	idx = ri->sorted ? ri->sorted[idx] : idx;
 279	if (ri->is_rela) {
 280		gelf_getrela(ri->reldata, idx, &ri->rela);
 281		return GELF_R_SYM(ri->rela.r_info);
 282	}
 283	gelf_getrel(ri->reldata, idx, &ri->rel);
 284	return GELF_R_SYM(ri->rel.r_info);
 285}
 286
 287static u64 get_rel_offset(struct rel_info *ri, u32 x)
 288{
 289	if (ri->is_rela) {
 290		GElf_Rela rela;
 291
 292		gelf_getrela(ri->reldata, x, &rela);
 293		return rela.r_offset;
 294	} else {
 295		GElf_Rel rel;
 296
 297		gelf_getrel(ri->reldata, x, &rel);
 298		return rel.r_offset;
 299	}
 300}
 301
 302static int rel_cmp(const void *a, const void *b, void *r)
 303{
 304	struct rel_info *ri = r;
 305	u64 a_offset = get_rel_offset(ri, *(const u32 *)a);
 306	u64 b_offset = get_rel_offset(ri, *(const u32 *)b);
 307
 308	return a_offset < b_offset ? -1 : (a_offset > b_offset ? 1 : 0);
 309}
 310
 311static int sort_rel(struct rel_info *ri)
 312{
 313	size_t sz = sizeof(ri->sorted[0]);
 314	u32 i;
 315
 316	ri->sorted = calloc(ri->nr_entries, sz);
 317	if (!ri->sorted)
 318		return -1;
 319	for (i = 0; i < ri->nr_entries; i++)
 320		ri->sorted[i] = i;
 321	qsort_r(ri->sorted, ri->nr_entries, sz, rel_cmp, ri);
 322	return 0;
 323}
 324
 325/*
 326 * For x86_64, the GNU linker is putting IFUNC information in the relocation
 327 * addend.
 328 */
 329static bool addend_may_be_ifunc(GElf_Ehdr *ehdr, struct rel_info *ri)
 330{
 331	return ehdr->e_machine == EM_X86_64 && ri->is_rela &&
 332	       GELF_R_TYPE(ri->rela.r_info) == R_X86_64_IRELATIVE;
 333}
 334
 335static bool get_ifunc_name(Elf *elf, struct dso *dso, GElf_Ehdr *ehdr,
 336			   struct rel_info *ri, char *buf, size_t buf_sz)
 337{
 338	u64 addr = ri->rela.r_addend;
 339	struct symbol *sym;
 340	GElf_Phdr phdr;
 341
 342	if (!addend_may_be_ifunc(ehdr, ri))
 343		return false;
 344
 345	if (elf_read_program_header(elf, addr, &phdr))
 346		return false;
 347
 348	addr -= phdr.p_vaddr - phdr.p_offset;
 349
 350	sym = dso__find_symbol_nocache(dso, addr);
 351
 352	/* Expecting the address to be an IFUNC or IFUNC alias */
 353	if (!sym || sym->start != addr || (sym->type != STT_GNU_IFUNC && !sym->ifunc_alias))
 354		return false;
 355
 356	snprintf(buf, buf_sz, "%s@plt", sym->name);
 357
 358	return true;
 359}
 360
 361static void exit_rel(struct rel_info *ri)
 362{
 363	zfree(&ri->sorted);
 364}
 365
 366static bool get_plt_sizes(struct dso *dso, GElf_Ehdr *ehdr, GElf_Shdr *shdr_plt,
 367			  u64 *plt_header_size, u64 *plt_entry_size)
 368{
 369	switch (ehdr->e_machine) {
 370	case EM_ARM:
 371		*plt_header_size = 20;
 372		*plt_entry_size = 12;
 373		return true;
 374	case EM_AARCH64:
 375		*plt_header_size = 32;
 376		*plt_entry_size = 16;
 377		return true;
 378	case EM_LOONGARCH:
 379		*plt_header_size = 32;
 380		*plt_entry_size = 16;
 381		return true;
 382	case EM_SPARC:
 383		*plt_header_size = 48;
 384		*plt_entry_size = 12;
 385		return true;
 386	case EM_SPARCV9:
 387		*plt_header_size = 128;
 388		*plt_entry_size = 32;
 389		return true;
 390	case EM_386:
 391	case EM_X86_64:
 392		*plt_entry_size = shdr_plt->sh_entsize;
 393		/* Size is 8 or 16, if not, assume alignment indicates size */
 394		if (*plt_entry_size != 8 && *plt_entry_size != 16)
 395			*plt_entry_size = shdr_plt->sh_addralign == 8 ? 8 : 16;
 396		*plt_header_size = *plt_entry_size;
 397		break;
 398	default: /* FIXME: s390/alpha/mips/parisc/poperpc/sh/xtensa need to be checked */
 399		*plt_header_size = shdr_plt->sh_entsize;
 400		*plt_entry_size = shdr_plt->sh_entsize;
 401		break;
 402	}
 403	if (*plt_entry_size)
 404		return true;
 405	pr_debug("Missing PLT entry size for %s\n", dso__long_name(dso));
 406	return false;
 407}
 408
 409static bool machine_is_x86(GElf_Half e_machine)
 410{
 411	return e_machine == EM_386 || e_machine == EM_X86_64;
 412}
 413
 414struct rela_dyn {
 415	GElf_Addr	offset;
 416	u32		sym_idx;
 417};
 418
 419struct rela_dyn_info {
 420	struct dso	*dso;
 421	Elf_Data	*plt_got_data;
 422	u32		nr_entries;
 423	struct rela_dyn	*sorted;
 424	Elf_Data	*dynsym_data;
 425	Elf_Data	*dynstr_data;
 426	Elf_Data	*rela_dyn_data;
 427};
 428
 429static void exit_rela_dyn(struct rela_dyn_info *di)
 430{
 431	zfree(&di->sorted);
 432}
 433
 434static int cmp_offset(const void *a, const void *b)
 435{
 436	const struct rela_dyn *va = a;
 437	const struct rela_dyn *vb = b;
 438
 439	return va->offset < vb->offset ? -1 : (va->offset > vb->offset ? 1 : 0);
 440}
 441
 442static int sort_rela_dyn(struct rela_dyn_info *di)
 443{
 444	u32 i, n;
 445
 446	di->sorted = calloc(di->nr_entries, sizeof(di->sorted[0]));
 447	if (!di->sorted)
 448		return -1;
 449
 450	/* Get data for sorting: the offset and symbol index */
 451	for (i = 0, n = 0; i < di->nr_entries; i++) {
 452		GElf_Rela rela;
 453		u32 sym_idx;
 454
 455		gelf_getrela(di->rela_dyn_data, i, &rela);
 456		sym_idx = GELF_R_SYM(rela.r_info);
 457		if (sym_idx) {
 458			di->sorted[n].sym_idx = sym_idx;
 459			di->sorted[n].offset = rela.r_offset;
 460			n += 1;
 461		}
 462	}
 463
 464	/* Sort by offset */
 465	di->nr_entries = n;
 466	qsort(di->sorted, n, sizeof(di->sorted[0]), cmp_offset);
 467
 468	return 0;
 469}
 470
 471static void get_rela_dyn_info(Elf *elf, GElf_Ehdr *ehdr, struct rela_dyn_info *di, Elf_Scn *scn)
 472{
 473	GElf_Shdr rela_dyn_shdr;
 474	GElf_Shdr shdr;
 475
 476	di->plt_got_data = elf_getdata(scn, NULL);
 477
 478	scn = elf_section_by_name(elf, ehdr, &rela_dyn_shdr, ".rela.dyn", NULL);
 479	if (!scn || !rela_dyn_shdr.sh_link || !rela_dyn_shdr.sh_entsize)
 480		return;
 481
 482	di->nr_entries = rela_dyn_shdr.sh_size / rela_dyn_shdr.sh_entsize;
 483	di->rela_dyn_data = elf_getdata(scn, NULL);
 484
 485	scn = elf_getscn(elf, rela_dyn_shdr.sh_link);
 486	if (!scn || !gelf_getshdr(scn, &shdr) || !shdr.sh_link)
 487		return;
 488
 489	di->dynsym_data = elf_getdata(scn, NULL);
 490	di->dynstr_data = elf_getdata(elf_getscn(elf, shdr.sh_link), NULL);
 491
 492	if (!di->plt_got_data || !di->dynstr_data || !di->dynsym_data || !di->rela_dyn_data)
 493		return;
 494
 495	/* Sort into offset order */
 496	sort_rela_dyn(di);
 497}
 498
 499/* Get instruction displacement from a plt entry for x86_64 */
 500static u32 get_x86_64_plt_disp(const u8 *p)
 501{
 502	u8 endbr64[] = {0xf3, 0x0f, 0x1e, 0xfa};
 503	int n = 0;
 504
 505	/* Skip endbr64 */
 506	if (!memcmp(p, endbr64, sizeof(endbr64)))
 507		n += sizeof(endbr64);
 508	/* Skip bnd prefix */
 509	if (p[n] == 0xf2)
 510		n += 1;
 511	/* jmp with 4-byte displacement */
 512	if (p[n] == 0xff && p[n + 1] == 0x25) {
 513		u32 disp;
 514
 515		n += 2;
 516		/* Also add offset from start of entry to end of instruction */
 517		memcpy(&disp, p + n, sizeof(disp));
 518		return n + 4 + le32toh(disp);
 519	}
 520	return 0;
 521}
 522
 523static bool get_plt_got_name(GElf_Shdr *shdr, size_t i,
 524			     struct rela_dyn_info *di,
 525			     char *buf, size_t buf_sz)
 526{
 527	struct rela_dyn vi, *vr;
 528	const char *sym_name;
 529	char *demangled;
 530	GElf_Sym sym;
 531	bool result;
 532	u32 disp;
 533
 534	if (!di->sorted)
 535		return false;
 536
 537	disp = get_x86_64_plt_disp(di->plt_got_data->d_buf + i);
 538	if (!disp)
 539		return false;
 540
 541	/* Compute target offset of the .plt.got entry */
 542	vi.offset = shdr->sh_offset + di->plt_got_data->d_off + i + disp;
 543
 544	/* Find that offset in .rela.dyn (sorted by offset) */
 545	vr = bsearch(&vi, di->sorted, di->nr_entries, sizeof(di->sorted[0]), cmp_offset);
 546	if (!vr)
 547		return false;
 548
 549	/* Get the associated symbol */
 550	gelf_getsym(di->dynsym_data, vr->sym_idx, &sym);
 551	sym_name = elf_sym__name(&sym, di->dynstr_data);
 552	demangled = dso__demangle_sym(di->dso, /*kmodule=*/0, sym_name);
 553	if (demangled != NULL)
 554		sym_name = demangled;
 555
 556	snprintf(buf, buf_sz, "%s@plt", sym_name);
 557
 558	result = *sym_name;
 559
 560	free(demangled);
 561
 562	return result;
 563}
 564
 565static int dso__synthesize_plt_got_symbols(struct dso *dso, Elf *elf,
 566					   GElf_Ehdr *ehdr,
 567					   char *buf, size_t buf_sz)
 568{
 569	struct rela_dyn_info di = { .dso = dso };
 570	struct symbol *sym;
 571	GElf_Shdr shdr;
 572	Elf_Scn *scn;
 573	int err = -1;
 574	size_t i;
 575
 576	scn = elf_section_by_name(elf, ehdr, &shdr, ".plt.got", NULL);
 577	if (!scn || !shdr.sh_entsize)
 578		return 0;
 579
 580	if (ehdr->e_machine == EM_X86_64)
 581		get_rela_dyn_info(elf, ehdr, &di, scn);
 582
 583	for (i = 0; i < shdr.sh_size; i += shdr.sh_entsize) {
 584		if (!get_plt_got_name(&shdr, i, &di, buf, buf_sz))
 585			snprintf(buf, buf_sz, "offset_%#" PRIx64 "@plt", (u64)shdr.sh_offset + i);
 586		sym = symbol__new(shdr.sh_offset + i, shdr.sh_entsize, STB_GLOBAL, STT_FUNC, buf);
 587		if (!sym)
 588			goto out;
 589		symbols__insert(dso__symbols(dso), sym);
 590	}
 591	err = 0;
 592out:
 593	exit_rela_dyn(&di);
 594	return err;
 595}
 596
 597/*
 598 * We need to check if we have a .dynsym, so that we can handle the
 599 * .plt, synthesizing its symbols, that aren't on the symtabs (be it
 600 * .dynsym or .symtab).
 601 * And always look at the original dso, not at debuginfo packages, that
 602 * have the PLT data stripped out (shdr_rel_plt.sh_type == SHT_NOBITS).
 603 */
 604int dso__synthesize_plt_symbols(struct dso *dso, struct symsrc *ss)
 605{
 606	uint32_t idx;
 607	GElf_Sym sym;
 608	u64 plt_offset, plt_header_size, plt_entry_size;
 609	GElf_Shdr shdr_plt, plt_sec_shdr;
 610	struct symbol *f, *plt_sym;
 611	GElf_Shdr shdr_rel_plt, shdr_dynsym;
 612	Elf_Data *syms, *symstrs;
 613	Elf_Scn *scn_plt_rel, *scn_symstrs, *scn_dynsym;
 614	GElf_Ehdr ehdr;
 615	char sympltname[1024];
 616	Elf *elf;
 617	int nr = 0, err = -1;
 618	struct rel_info ri = { .is_rela = false };
 619	bool lazy_plt;
 620
 621	elf = ss->elf;
 622	ehdr = ss->ehdr;
 623
 624	if (!elf_section_by_name(elf, &ehdr, &shdr_plt, ".plt", NULL))
 625		return 0;
 626
 627	/*
 628	 * A symbol from a previous section (e.g. .init) can have been expanded
 629	 * by symbols__fixup_end() to overlap .plt. Truncate it before adding
 630	 * a symbol for .plt header.
 631	 */
 632	f = dso__find_symbol_nocache(dso, shdr_plt.sh_offset);
 633	if (f && f->start < shdr_plt.sh_offset && f->end > shdr_plt.sh_offset)
 634		f->end = shdr_plt.sh_offset;
 635
 636	if (!get_plt_sizes(dso, &ehdr, &shdr_plt, &plt_header_size, &plt_entry_size))
 637		return 0;
 638
 639	/* Add a symbol for .plt header */
 640	plt_sym = symbol__new(shdr_plt.sh_offset, plt_header_size, STB_GLOBAL, STT_FUNC, ".plt");
 641	if (!plt_sym)
 642		goto out_elf_end;
 643	symbols__insert(dso__symbols(dso), plt_sym);
 644
 645	/* Only x86 has .plt.got */
 646	if (machine_is_x86(ehdr.e_machine) &&
 647	    dso__synthesize_plt_got_symbols(dso, elf, &ehdr, sympltname, sizeof(sympltname)))
 648		goto out_elf_end;
 649
 650	/* Only x86 has .plt.sec */
 651	if (machine_is_x86(ehdr.e_machine) &&
 652	    elf_section_by_name(elf, &ehdr, &plt_sec_shdr, ".plt.sec", NULL)) {
 653		if (!get_plt_sizes(dso, &ehdr, &plt_sec_shdr, &plt_header_size, &plt_entry_size))
 654			return 0;
 655		/* Extend .plt symbol to entire .plt */
 656		plt_sym->end = plt_sym->start + shdr_plt.sh_size;
 657		/* Use .plt.sec offset */
 658		plt_offset = plt_sec_shdr.sh_offset;
 659		lazy_plt = false;
 660	} else {
 661		plt_offset = shdr_plt.sh_offset;
 662		lazy_plt = true;
 663	}
 664
 665	scn_plt_rel = elf_section_by_name(elf, &ehdr, &shdr_rel_plt,
 666					  ".rela.plt", NULL);
 667	if (scn_plt_rel == NULL) {
 668		scn_plt_rel = elf_section_by_name(elf, &ehdr, &shdr_rel_plt,
 669						  ".rel.plt", NULL);
 670		if (scn_plt_rel == NULL)
 671			return 0;
 672	}
 673
 674	if (shdr_rel_plt.sh_type != SHT_RELA &&
 675	    shdr_rel_plt.sh_type != SHT_REL)
 676		return 0;
 677
 678	if (!shdr_rel_plt.sh_link)
 679		return 0;
 680
 681	if (shdr_rel_plt.sh_link == ss->dynsym_idx) {
 682		scn_dynsym = ss->dynsym;
 683		shdr_dynsym = ss->dynshdr;
 684	} else if (shdr_rel_plt.sh_link == ss->symtab_idx) {
 685		/*
 686		 * A static executable can have a .plt due to IFUNCs, in which
 687		 * case .symtab is used not .dynsym.
 688		 */
 689		scn_dynsym = ss->symtab;
 690		shdr_dynsym = ss->symshdr;
 691	} else {
 692		goto out_elf_end;
 693	}
 694
 695	if (!scn_dynsym)
 696		return 0;
 697
 698	/*
 699	 * Fetch the relocation section to find the idxes to the GOT
 700	 * and the symbols in the .dynsym they refer to.
 701	 */
 702	ri.reldata = elf_getdata(scn_plt_rel, NULL);
 703	if (!ri.reldata)
 704		goto out_elf_end;
 705
 706	syms = elf_getdata(scn_dynsym, NULL);
 707	if (syms == NULL)
 708		goto out_elf_end;
 709
 710	scn_symstrs = elf_getscn(elf, shdr_dynsym.sh_link);
 711	if (scn_symstrs == NULL)
 712		goto out_elf_end;
 713
 714	symstrs = elf_getdata(scn_symstrs, NULL);
 715	if (symstrs == NULL)
 716		goto out_elf_end;
 717
 718	if (symstrs->d_size == 0)
 719		goto out_elf_end;
 720
 721	ri.nr_entries = shdr_rel_plt.sh_size / shdr_rel_plt.sh_entsize;
 722
 723	ri.is_rela = shdr_rel_plt.sh_type == SHT_RELA;
 724
 725	if (lazy_plt) {
 726		/*
 727		 * Assume a .plt with the same number of entries as the number
 728		 * of relocation entries is not lazy and does not have a header.
 729		 */
 730		if (ri.nr_entries * plt_entry_size == shdr_plt.sh_size)
 731			dso__delete_symbol(dso, plt_sym);
 732		else
 733			plt_offset += plt_header_size;
 734	}
 735
 736	/*
 737	 * x86 doesn't insert IFUNC relocations in .plt order, so sort to get
 738	 * back in order.
 739	 */
 740	if (machine_is_x86(ehdr.e_machine) && sort_rel(&ri))
 741		goto out_elf_end;
 742
 743	for (idx = 0; idx < ri.nr_entries; idx++) {
 744		const char *elf_name = NULL;
 745		char *demangled = NULL;
 746
 747		gelf_getsym(syms, get_rel_symidx(&ri, idx), &sym);
 748
 749		elf_name = elf_sym__name(&sym, symstrs);
 750		demangled = dso__demangle_sym(dso, /*kmodule=*/0, elf_name);
 751		if (demangled)
 752			elf_name = demangled;
 753		if (*elf_name)
 754			snprintf(sympltname, sizeof(sympltname), "%s@plt", elf_name);
 755		else if (!get_ifunc_name(elf, dso, &ehdr, &ri, sympltname, sizeof(sympltname)))
 756			snprintf(sympltname, sizeof(sympltname),
 757				 "offset_%#" PRIx64 "@plt", plt_offset);
 758		free(demangled);
 759
 760		f = symbol__new(plt_offset, plt_entry_size, STB_GLOBAL, STT_FUNC, sympltname);
 761		if (!f)
 762			goto out_elf_end;
 763
 764		plt_offset += plt_entry_size;
 765		symbols__insert(dso__symbols(dso), f);
 766		++nr;
 767	}
 768
 769	err = 0;
 770out_elf_end:
 771	exit_rel(&ri);
 772	if (err == 0)
 773		return nr;
 774	pr_debug("%s: problems reading %s PLT info.\n",
 775		 __func__, dso__long_name(dso));
 776	return 0;
 777}
 778
 779/*
 780 * Align offset to 4 bytes as needed for note name and descriptor data.
 781 */
 782#define NOTE_ALIGN(n) (((n) + 3) & -4U)
 783
 784static int elf_read_build_id(Elf *elf, void *bf, size_t size)
 785{
 786	int err = -1;
 787	GElf_Ehdr ehdr;
 788	GElf_Shdr shdr;
 789	Elf_Data *data;
 790	Elf_Scn *sec;
 791	Elf_Kind ek;
 792	void *ptr;
 793
 794	if (size < BUILD_ID_SIZE)
 795		goto out;
 796
 797	ek = elf_kind(elf);
 798	if (ek != ELF_K_ELF)
 799		goto out;
 800
 801	if (gelf_getehdr(elf, &ehdr) == NULL) {
 802		pr_err("%s: cannot get elf header.\n", __func__);
 803		goto out;
 804	}
 805
 806	/*
 807	 * Check following sections for notes:
 808	 *   '.note.gnu.build-id'
 809	 *   '.notes'
 810	 *   '.note' (VDSO specific)
 811	 */
 812	do {
 813		sec = elf_section_by_name(elf, &ehdr, &shdr,
 814					  ".note.gnu.build-id", NULL);
 815		if (sec)
 816			break;
 817
 818		sec = elf_section_by_name(elf, &ehdr, &shdr,
 819					  ".notes", NULL);
 820		if (sec)
 821			break;
 822
 823		sec = elf_section_by_name(elf, &ehdr, &shdr,
 824					  ".note", NULL);
 825		if (sec)
 826			break;
 827
 828		return err;
 829
 830	} while (0);
 831
 832	data = elf_getdata(sec, NULL);
 833	if (data == NULL)
 834		goto out;
 835
 836	ptr = data->d_buf;
 837	while (ptr < (data->d_buf + data->d_size)) {
 838		GElf_Nhdr *nhdr = ptr;
 839		size_t namesz = NOTE_ALIGN(nhdr->n_namesz),
 840		       descsz = NOTE_ALIGN(nhdr->n_descsz);
 841		const char *name;
 842
 843		ptr += sizeof(*nhdr);
 844		name = ptr;
 845		ptr += namesz;
 846		if (nhdr->n_type == NT_GNU_BUILD_ID &&
 847		    nhdr->n_namesz == sizeof("GNU")) {
 848			if (memcmp(name, "GNU", sizeof("GNU")) == 0) {
 849				size_t sz = min(size, descsz);
 850				memcpy(bf, ptr, sz);
 851				memset(bf + sz, 0, size - sz);
 852				err = sz;
 853				break;
 854			}
 855		}
 856		ptr += descsz;
 857	}
 858
 859out:
 860	return err;
 861}
 862
 863static int read_build_id(const char *filename, struct build_id *bid)
 864{
 865	size_t size = sizeof(bid->data);
 866	int fd, err;
 867	Elf *elf;
 868
 869	err = libbfd__read_build_id(filename, bid);
 870	if (err >= 0)
 871		goto out;
 872
 873	if (size < BUILD_ID_SIZE)
 874		goto out;
 875
 876	fd = open(filename, O_RDONLY);
 877	if (fd < 0)
 878		goto out;
 879
 880	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
 881	if (elf == NULL) {
 882		pr_debug2("%s: cannot read %s ELF file.\n", __func__, filename);
 883		goto out_close;
 884	}
 885
 886	err = elf_read_build_id(elf, bid->data, size);
 887	if (err > 0)
 888		bid->size = err;
 889
 890	elf_end(elf);
 891out_close:
 892	close(fd);
 893out:
 894	return err;
 895}
 896
 897int filename__read_build_id(const char *filename, struct build_id *bid)
 898{
 899	struct kmod_path m = { .name = NULL, };
 900	char path[PATH_MAX];
 901	int err;
 902
 903	if (!filename)
 904		return -EFAULT;
 905
 906	errno = 0;
 907	if (!is_regular_file(filename))
 908		return errno == 0 ? -EWOULDBLOCK : -errno;
 909
 910	err = kmod_path__parse(&m, filename);
 911	if (err)
 912		return -1;
 913
 914	if (m.comp) {
 915		int error = 0, fd;
 916
 917		fd = filename__decompress(filename, path, sizeof(path), m.comp, &error);
 918		if (fd < 0) {
 919			pr_debug("Failed to decompress (error %d) %s\n",
 920				 error, filename);
 921			return -1;
 922		}
 923		close(fd);
 924		filename = path;
 925	}
 926
 927	err = read_build_id(filename, bid);
 928
 929	if (m.comp)
 930		unlink(filename);
 931	return err;
 932}
 933
 934int sysfs__read_build_id(const char *filename, struct build_id *bid)
 935{
 936	size_t size = sizeof(bid->data);
 937	int fd, err = -1;
 938
 939	fd = open(filename, O_RDONLY);
 940	if (fd < 0)
 941		goto out;
 942
 943	while (1) {
 944		char bf[BUFSIZ];
 945		GElf_Nhdr nhdr;
 946		size_t namesz, descsz;
 947
 948		if (read(fd, &nhdr, sizeof(nhdr)) != sizeof(nhdr))
 949			break;
 950
 951		namesz = NOTE_ALIGN(nhdr.n_namesz);
 952		descsz = NOTE_ALIGN(nhdr.n_descsz);
 953		if (nhdr.n_type == NT_GNU_BUILD_ID &&
 954		    nhdr.n_namesz == sizeof("GNU")) {
 955			if (read(fd, bf, namesz) != (ssize_t)namesz)
 956				break;
 957			if (memcmp(bf, "GNU", sizeof("GNU")) == 0) {
 958				size_t sz = min(descsz, size);
 959				if (read(fd, bid->data, sz) == (ssize_t)sz) {
 960					memset(bid->data + sz, 0, size - sz);
 961					bid->size = sz;
 962					err = 0;
 963					break;
 964				}
 965			} else if (read(fd, bf, descsz) != (ssize_t)descsz)
 966				break;
 967		} else {
 968			int n = namesz + descsz;
 969
 970			if (n > (int)sizeof(bf)) {
 971				n = sizeof(bf);
 972				pr_debug("%s: truncating reading of build id in sysfs file %s: n_namesz=%u, n_descsz=%u.\n",
 973					 __func__, filename, nhdr.n_namesz, nhdr.n_descsz);
 974			}
 975			if (read(fd, bf, n) != n)
 976				break;
 977		}
 978	}
 979	close(fd);
 980out:
 981	return err;
 982}
 983
 984int filename__read_debuglink(const char *filename, char *debuglink,
 985			     size_t size)
 986{
 987	int fd, err = -1;
 988	Elf *elf;
 989	GElf_Ehdr ehdr;
 990	GElf_Shdr shdr;
 991	Elf_Data *data;
 992	Elf_Scn *sec;
 993	Elf_Kind ek;
 994
 995	err = libbfd_filename__read_debuglink(filename, debuglink, size);
 996	if (err >= 0)
 997		goto out;
 998
 999	fd = open(filename, O_RDONLY);
1000	if (fd < 0)
1001		goto out;
1002
1003	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
1004	if (elf == NULL) {
1005		pr_debug2("%s: cannot read %s ELF file.\n", __func__, filename);
1006		goto out_close;
1007	}
1008
1009	ek = elf_kind(elf);
1010	if (ek != ELF_K_ELF)
1011		goto out_elf_end;
1012
1013	if (gelf_getehdr(elf, &ehdr) == NULL) {
1014		pr_err("%s: cannot get elf header.\n", __func__);
1015		goto out_elf_end;
1016	}
1017
1018	sec = elf_section_by_name(elf, &ehdr, &shdr,
1019				  ".gnu_debuglink", NULL);
1020	if (sec == NULL)
1021		goto out_elf_end;
1022
1023	data = elf_getdata(sec, NULL);
1024	if (data == NULL)
1025		goto out_elf_end;
1026
1027	/* the start of this section is a zero-terminated string */
1028	strncpy(debuglink, data->d_buf, size);
1029
1030	err = 0;
1031
1032out_elf_end:
1033	elf_end(elf);
1034out_close:
1035	close(fd);
1036out:
1037	return err;
1038}
1039
1040bool symsrc__possibly_runtime(struct symsrc *ss)
1041{
1042	return ss->dynsym || ss->opdsec;
1043}
1044
1045bool symsrc__has_symtab(struct symsrc *ss)
1046{
1047	return ss->symtab != NULL;
1048}
1049
1050void symsrc__destroy(struct symsrc *ss)
1051{
1052	zfree(&ss->name);
1053	elf_end(ss->elf);
1054	close(ss->fd);
1055}
1056
1057bool elf__needs_adjust_symbols(GElf_Ehdr ehdr)
1058{
1059	/*
1060	 * Usually vmlinux is an ELF file with type ET_EXEC for most
1061	 * architectures; except Arm64 kernel is linked with option
1062	 * '-share', so need to check type ET_DYN.
1063	 */
1064	return ehdr.e_type == ET_EXEC || ehdr.e_type == ET_REL ||
1065	       ehdr.e_type == ET_DYN;
1066}
1067
1068static Elf *read_gnu_debugdata(struct dso *dso, Elf *elf, const char *name, int *fd_ret)
1069{
1070	Elf *elf_embedded;
1071	GElf_Ehdr ehdr;
1072	GElf_Shdr shdr;
1073	Elf_Scn *scn;
1074	Elf_Data *scn_data;
1075	FILE *wrapped;
1076	size_t shndx;
1077	char temp_filename[] = "/tmp/perf.gnu_debugdata.elf.XXXXXX";
1078	int ret, temp_fd;
1079
1080	if (gelf_getehdr(elf, &ehdr) == NULL) {
1081		pr_debug("%s: cannot read %s ELF file.\n", __func__, name);
1082		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1083		return NULL;
1084	}
1085
1086	scn = elf_section_by_name(elf, &ehdr, &shdr, ".gnu_debugdata", &shndx);
1087	if (!scn) {
1088		*dso__load_errno(dso) = -ENOENT;
1089		return NULL;
1090	}
1091
1092	if (shdr.sh_type == SHT_NOBITS) {
1093		pr_debug("%s: .gnu_debugdata of ELF file %s has no data.\n", __func__, name);
1094		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1095		return NULL;
1096	}
1097
1098	scn_data = elf_rawdata(scn, NULL);
1099	if (!scn_data) {
1100		pr_debug("%s: error reading .gnu_debugdata of %s: %s\n", __func__,
1101			 name, elf_errmsg(-1));
1102		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1103		return NULL;
1104	}
1105
1106	wrapped = fmemopen(scn_data->d_buf, scn_data->d_size, "r");
1107	if (!wrapped) {
1108		pr_debug("%s: fmemopen: %s\n", __func__, strerror(errno));
1109		*dso__load_errno(dso) = -errno;
1110		return NULL;
1111	}
1112
1113	temp_fd = mkstemp(temp_filename);
1114	if (temp_fd < 0) {
1115		pr_debug("%s: mkstemp: %s\n", __func__, strerror(errno));
1116		*dso__load_errno(dso) = -errno;
1117		fclose(wrapped);
1118		return NULL;
1119	}
1120	unlink(temp_filename);
1121
1122	ret = lzma_decompress_stream_to_file(wrapped, temp_fd);
1123	fclose(wrapped);
1124	if (ret < 0) {
1125		*dso__load_errno(dso) = -errno;
1126		close(temp_fd);
1127		return NULL;
1128	}
1129
1130	elf_embedded = elf_begin(temp_fd, PERF_ELF_C_READ_MMAP, NULL);
1131	if (!elf_embedded) {
1132		pr_debug("%s: error reading .gnu_debugdata of %s: %s\n", __func__,
1133			 name, elf_errmsg(-1));
1134		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1135		close(temp_fd);
1136		return NULL;
1137	}
1138	pr_debug("%s: using .gnu_debugdata of %s\n", __func__, name);
1139	*fd_ret = temp_fd;
1140	return elf_embedded;
1141}
1142
1143int symsrc__init(struct symsrc *ss, struct dso *dso, const char *name,
1144		 enum dso_binary_type type)
1145{
1146	GElf_Ehdr ehdr;
1147	Elf *elf;
1148	int fd;
1149
1150	if (dso__needs_decompress(dso)) {
1151		fd = dso__decompress_kmodule_fd(dso, name);
1152		if (fd < 0)
1153			return -1;
1154
1155		type = dso__symtab_type(dso);
1156	} else {
1157		fd = open(name, O_RDONLY);
1158		if (fd < 0) {
1159			*dso__load_errno(dso) = errno;
1160			return -1;
1161		}
1162	}
1163
1164	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
1165	if (elf == NULL) {
1166		pr_debug("%s: cannot read %s ELF file.\n", __func__, name);
1167		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1168		goto out_close;
1169	}
1170
1171	if (type == DSO_BINARY_TYPE__GNU_DEBUGDATA) {
1172		int new_fd;
1173		Elf *embedded = read_gnu_debugdata(dso, elf, name, &new_fd);
1174
1175		if (!embedded)
1176			goto out_elf_end;
1177
1178		elf_end(elf);
1179		close(fd);
1180		fd = new_fd;
1181		elf = embedded;
1182	}
1183
1184	if (gelf_getehdr(elf, &ehdr) == NULL) {
1185		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INVALID_ELF;
1186		pr_debug("%s: cannot get elf header.\n", __func__);
1187		goto out_elf_end;
1188	}
1189
1190	if (dso__swap_init(dso, ehdr.e_ident[EI_DATA])) {
1191		*dso__load_errno(dso) = DSO_LOAD_ERRNO__INTERNAL_ERROR;
1192		goto out_elf_end;
1193	}
1194
1195	/* Always reject images with a mismatched build-id: */
1196	if (dso__has_build_id(dso) && !symbol_conf.ignore_vmlinux_buildid) {
1197		u8 build_id[BUILD_ID_SIZE];
1198		struct build_id bid;
1199		int size;
1200
1201		size = elf_read_build_id(elf, build_id, BUILD_ID_SIZE);
1202		if (size <= 0) {
1203			*dso__load_errno(dso) = DSO_LOAD_ERRNO__CANNOT_READ_BUILDID;
1204			goto out_elf_end;
1205		}
1206
1207		build_id__init(&bid, build_id, size);
1208		if (!dso__build_id_equal(dso, &bid)) {
1209			pr_debug("%s: build id mismatch for %s.\n", __func__, name);
1210			*dso__load_errno(dso) = DSO_LOAD_ERRNO__MISMATCHING_BUILDID;
1211			goto out_elf_end;
1212		}
1213	}
1214
1215	ss->is_64_bit = (gelf_getclass(elf) == ELFCLASS64);
1216
1217	ss->symtab_idx = 0;
1218	ss->symtab = elf_section_by_name(elf, &ehdr, &ss->symshdr, ".symtab",
1219			&ss->symtab_idx);
1220	if (ss->symshdr.sh_type != SHT_SYMTAB)
1221		ss->symtab = NULL;
1222
1223	ss->dynsym_idx = 0;
1224	ss->dynsym = elf_section_by_name(elf, &ehdr, &ss->dynshdr, ".dynsym",
1225			&ss->dynsym_idx);
1226	if (ss->dynshdr.sh_type != SHT_DYNSYM)
1227		ss->dynsym = NULL;
1228
1229	ss->opdidx = 0;
1230	ss->opdsec = elf_section_by_name(elf, &ehdr, &ss->opdshdr, ".opd",
1231			&ss->opdidx);
1232	if (ss->opdshdr.sh_type != SHT_PROGBITS)
1233		ss->opdsec = NULL;
1234
1235	if (dso__kernel(dso) == DSO_SPACE__USER)
1236		ss->adjust_symbols = true;
1237	else
1238		ss->adjust_symbols = elf__needs_adjust_symbols(ehdr);
1239
1240	ss->name   = strdup(name);
1241	if (!ss->name) {
1242		*dso__load_errno(dso) = errno;
1243		goto out_elf_end;
1244	}
1245
1246	ss->elf    = elf;
1247	ss->fd     = fd;
1248	ss->ehdr   = ehdr;
1249	ss->type   = type;
1250
1251	return 0;
1252
1253out_elf_end:
1254	elf_end(elf);
1255out_close:
1256	close(fd);
1257	return -1;
1258}
1259
1260static bool is_exe_text(int flags)
1261{
1262	return (flags & (SHF_ALLOC | SHF_EXECINSTR)) == (SHF_ALLOC | SHF_EXECINSTR);
1263}
1264
1265/*
1266 * Some executable module sections like .noinstr.text might be laid out with
1267 * .text so they can use the same mapping (memory address to file offset).
1268 * Check if that is the case. Refer to kernel layout_sections(). Return the
1269 * maximum offset.
1270 */
1271static u64 max_text_section(Elf *elf, GElf_Ehdr *ehdr)
1272{
1273	Elf_Scn *sec = NULL;
1274	GElf_Shdr shdr;
1275	u64 offs = 0;
1276
1277	/* Doesn't work for some arch */
1278	if (ehdr->e_machine == EM_PARISC ||
1279	    ehdr->e_machine == EM_ALPHA)
1280		return 0;
1281
1282	/* ELF is corrupted/truncated, avoid calling elf_strptr. */
1283	if (!elf_rawdata(elf_getscn(elf, ehdr->e_shstrndx), NULL))
1284		return 0;
1285
1286	while ((sec = elf_nextscn(elf, sec)) != NULL) {
1287		char *sec_name;
1288
1289		if (!gelf_getshdr(sec, &shdr))
1290			break;
1291
1292		if (!is_exe_text(shdr.sh_flags))
1293			continue;
1294
1295		/* .init and .exit sections are not placed with .text */
1296		sec_name = elf_strptr(elf, ehdr->e_shstrndx, shdr.sh_name);
1297		if (!sec_name ||
1298		    strstarts(sec_name, ".init") ||
1299		    strstarts(sec_name, ".exit"))
1300			break;
1301
1302		/* Must be next to previous, assumes .text is first */
1303		if (offs && PERF_ALIGN(offs, shdr.sh_addralign ?: 1) != shdr.sh_offset)
1304			break;
1305
1306		offs = shdr.sh_offset + shdr.sh_size;
1307	}
1308
1309	return offs;
1310}
1311
1312/**
1313 * ref_reloc_sym_not_found - has kernel relocation symbol been found.
1314 * @kmap: kernel maps and relocation reference symbol
1315 *
1316 * This function returns %true if we are dealing with the kernel maps and the
1317 * relocation reference symbol has not yet been found.  Otherwise %false is
1318 * returned.
1319 */
1320static bool ref_reloc_sym_not_found(struct kmap *kmap)
1321{
1322	return kmap && kmap->ref_reloc_sym && kmap->ref_reloc_sym->name &&
1323	       !kmap->ref_reloc_sym->unrelocated_addr;
1324}
1325
1326/**
1327 * ref_reloc - kernel relocation offset.
1328 * @kmap: kernel maps and relocation reference symbol
1329 *
1330 * This function returns the offset of kernel addresses as determined by using
1331 * the relocation reference symbol i.e. if the kernel has not been relocated
1332 * then the return value is zero.
1333 */
1334static u64 ref_reloc(struct kmap *kmap)
1335{
1336	if (kmap && kmap->ref_reloc_sym &&
1337	    kmap->ref_reloc_sym->unrelocated_addr)
1338		return kmap->ref_reloc_sym->addr -
1339		       kmap->ref_reloc_sym->unrelocated_addr;
1340	return 0;
1341}
1342
1343void __weak arch__sym_update(struct symbol *s __maybe_unused,
1344		GElf_Sym *sym __maybe_unused) { }
1345
1346static int dso__process_kernel_symbol(struct dso *dso, struct map *map,
1347				      GElf_Sym *sym, GElf_Shdr *shdr,
1348				      struct maps *kmaps, struct kmap *kmap,
1349				      struct dso **curr_dsop,
1350				      const char *section_name,
1351				      bool adjust_kernel_syms, bool kmodule, bool *remap_kernel,
1352				      u64 max_text_sh_offset)
1353{
1354	struct dso *curr_dso = *curr_dsop;
1355	struct map *curr_map;
1356	char dso_name[PATH_MAX];
1357
1358	/* Adjust symbol to map to file offset */
1359	if (adjust_kernel_syms)
1360		sym->st_value -= shdr->sh_addr - shdr->sh_offset;
1361
1362	if (strcmp(section_name, (dso__short_name(curr_dso) + dso__short_name_len(dso))) == 0)
1363		return 0;
1364
1365	if (strcmp(section_name, ".text") == 0) {
1366		/*
1367		 * The initial kernel mapping is based on
1368		 * kallsyms and identity maps.  Overwrite it to
1369		 * map to the kernel dso.
1370		 */
1371		if (*remap_kernel && dso__kernel(dso) && !kmodule) {
1372			*remap_kernel = false;
1373			map__set_start(map, shdr->sh_addr + ref_reloc(kmap));
1374			map__set_end(map, map__start(map) + shdr->sh_size);
1375			map__set_pgoff(map, shdr->sh_offset);
1376			map__set_mapping_type(map, MAPPING_TYPE__DSO);
1377			/* Ensure maps are correctly ordered */
1378			if (kmaps) {
1379				int err;
1380				struct map *tmp = map__get(map);
1381
1382				maps__remove(kmaps, map);
1383				err = maps__insert(kmaps, map);
1384				map__put(tmp);
1385				if (err)
1386					return err;
1387			}
1388		}
1389
1390		/*
1391		 * The initial module mapping is based on
1392		 * /proc/modules mapped to offset zero.
1393		 * Overwrite it to map to the module dso.
1394		 */
1395		if (*remap_kernel && kmodule) {
1396			*remap_kernel = false;
1397			map__set_pgoff(map, shdr->sh_offset);
1398		}
1399
1400		dso__put(*curr_dsop);
1401		*curr_dsop = dso__get(dso);
1402		return 0;
1403	}
1404
1405	if (!kmap)
1406		return 0;
1407
1408	/*
1409	 * perf does not record module section addresses except for .text, but
1410	 * some sections can use the same mapping as .text.
1411	 */
1412	if (kmodule && adjust_kernel_syms && is_exe_text(shdr->sh_flags) &&
1413	    shdr->sh_offset <= max_text_sh_offset) {
1414		dso__put(*curr_dsop);
1415		*curr_dsop = dso__get(dso);
1416		return 0;
1417	}
1418
1419	snprintf(dso_name, sizeof(dso_name), "%s%s", dso__short_name(dso), section_name);
1420
1421	curr_map = maps__find_by_name(kmaps, dso_name);
1422	if (curr_map == NULL) {
1423		u64 start = sym->st_value;
1424
1425		if (kmodule)
1426			start += map__start(map) + shdr->sh_offset;
1427
1428		curr_dso = dso__new(dso_name);
1429		if (curr_dso == NULL)
1430			return -1;
1431		dso__set_kernel(curr_dso, dso__kernel(dso));
1432		RC_CHK_ACCESS(curr_dso)->long_name = dso__long_name(dso);
1433		RC_CHK_ACCESS(curr_dso)->long_name_len = dso__long_name_len(dso);
1434		dso__set_binary_type(curr_dso, dso__binary_type(dso));
1435		dso__set_adjust_symbols(curr_dso, dso__adjust_symbols(dso));
1436		curr_map = map__new2(start, curr_dso);
1437		if (curr_map == NULL) {
1438			dso__put(curr_dso);
1439			return -1;
1440		}
1441		if (dso__kernel(curr_dso))
1442			map__kmap(curr_map)->kmaps = kmaps;
1443
1444		if (adjust_kernel_syms) {
1445			map__set_start(curr_map, shdr->sh_addr + ref_reloc(kmap));
1446			map__set_end(curr_map, map__start(curr_map) + shdr->sh_size);
1447			map__set_pgoff(curr_map, shdr->sh_offset);
1448		} else {
1449			map__set_mapping_type(curr_map, MAPPING_TYPE__IDENTITY);
1450		}
1451		dso__set_symtab_type(curr_dso, dso__symtab_type(dso));
1452		if (maps__insert(kmaps, curr_map)) {
1453			dso__put(curr_dso);
1454			map__put(curr_map);
1455			return -1;
1456		}
1457		dsos__add(&maps__machine(kmaps)->dsos, curr_dso);
1458		dso__set_loaded(curr_dso);
1459		dso__put(*curr_dsop);
1460		*curr_dsop = curr_dso;
1461	} else {
1462		dso__put(*curr_dsop);
1463		*curr_dsop = dso__get(map__dso(curr_map));
1464	}
1465	map__put(curr_map);
1466
1467	return 0;
1468}
1469
1470static int
1471dso__load_sym_internal(struct dso *dso, struct map *map, struct symsrc *syms_ss,
1472		       struct symsrc *runtime_ss, int kmodule, int dynsym)
1473{
1474	struct kmap *kmap = dso__kernel(dso) ? map__kmap(map) : NULL;
1475	struct maps *kmaps = kmap ? map__kmaps(map) : NULL;
1476	struct dso *curr_dso = NULL;
1477	Elf_Data *symstrs, *secstrs, *secstrs_run, *secstrs_sym;
1478	uint32_t nr_syms;
1479	uint32_t idx;
1480	GElf_Ehdr ehdr;
1481	GElf_Shdr shdr;
1482	GElf_Shdr tshdr;
1483	Elf_Data *syms, *opddata = NULL;
1484	GElf_Sym sym;
1485	Elf_Scn *sec, *sec_strndx;
1486	Elf *elf;
1487	int nr = 0;
1488	bool remap_kernel = false, adjust_kernel_syms = false;
1489	u64 max_text_sh_offset = 0;
1490
1491	if (kmap && !kmaps)
1492		return -1;
1493
1494	elf = syms_ss->elf;
1495	ehdr = syms_ss->ehdr;
1496	if (dynsym) {
1497		sec  = syms_ss->dynsym;
1498		shdr = syms_ss->dynshdr;
1499	} else {
1500		sec =  syms_ss->symtab;
1501		shdr = syms_ss->symshdr;
1502	}
1503
1504	if (elf_section_by_name(runtime_ss->elf, &runtime_ss->ehdr, &tshdr,
1505				".text", NULL)) {
1506		dso__set_text_offset(dso, tshdr.sh_addr - tshdr.sh_offset);
1507		dso__set_text_end(dso, tshdr.sh_offset + tshdr.sh_size);
1508	}
1509
1510	if (runtime_ss->opdsec)
1511		opddata = elf_rawdata(runtime_ss->opdsec, NULL);
1512
1513	syms = elf_getdata(sec, NULL);
1514	if (syms == NULL)
1515		goto out_elf_end;
1516
1517	sec = elf_getscn(elf, shdr.sh_link);
1518	if (sec == NULL)
1519		goto out_elf_end;
1520
1521	symstrs = elf_getdata(sec, NULL);
1522	if (symstrs == NULL)
1523		goto out_elf_end;
1524
1525	sec_strndx = elf_getscn(runtime_ss->elf, runtime_ss->ehdr.e_shstrndx);
1526	if (sec_strndx == NULL)
1527		goto out_elf_end;
1528
1529	secstrs_run = elf_getdata(sec_strndx, NULL);
1530	if (secstrs_run == NULL)
1531		goto out_elf_end;
1532
1533	sec_strndx = elf_getscn(elf, ehdr.e_shstrndx);
1534	if (sec_strndx == NULL)
1535		goto out_elf_end;
1536
1537	secstrs_sym = elf_getdata(sec_strndx, NULL);
1538	if (secstrs_sym == NULL)
1539		goto out_elf_end;
1540
1541	nr_syms = shdr.sh_size / shdr.sh_entsize;
1542
1543	memset(&sym, 0, sizeof(sym));
1544
1545	/*
1546	 * The kernel relocation symbol is needed in advance in order to adjust
1547	 * kernel maps correctly.
1548	 */
1549	if (ref_reloc_sym_not_found(kmap)) {
1550		elf_symtab__for_each_symbol(syms, nr_syms, idx, sym) {
1551			const char *elf_name = elf_sym__name(&sym, symstrs);
1552
1553			if (strcmp(elf_name, kmap->ref_reloc_sym->name))
1554				continue;
1555			kmap->ref_reloc_sym->unrelocated_addr = sym.st_value;
1556			map__set_reloc(map, kmap->ref_reloc_sym->addr - kmap->ref_reloc_sym->unrelocated_addr);
1557			break;
1558		}
1559	}
1560
1561	/*
1562	 * Handle any relocation of vdso necessary because older kernels
1563	 * attempted to prelink vdso to its virtual address.
1564	 */
1565	if (dso__is_vdso(dso))
1566		map__set_reloc(map, map__start(map) - dso__text_offset(dso));
1567
1568	dso__set_adjust_symbols(dso, runtime_ss->adjust_symbols || ref_reloc(kmap));
1569	/*
1570	 * Initial kernel and module mappings do not map to the dso.
1571	 * Flag the fixups.
1572	 */
1573	if (dso__kernel(dso)) {
1574		remap_kernel = true;
1575		adjust_kernel_syms = dso__adjust_symbols(dso);
1576	}
1577
1578	if (kmodule && adjust_kernel_syms)
1579		max_text_sh_offset = max_text_section(runtime_ss->elf, &runtime_ss->ehdr);
1580
1581	curr_dso = dso__get(dso);
1582	elf_symtab__for_each_symbol(syms, nr_syms, idx, sym) {
1583		struct symbol *f;
1584		const char *elf_name = elf_sym__name(&sym, symstrs);
1585		char *demangled = NULL;
1586		int is_label = elf_sym__is_label(&sym);
1587		const char *section_name;
1588		bool used_opd = false;
1589
1590		if (!is_label && !elf_sym__filter(&sym))
1591			continue;
1592
1593		/* Reject ARM ELF "mapping symbols": these aren't unique and
1594		 * don't identify functions, so will confuse the profile
1595		 * output: */
1596		if (ehdr.e_machine == EM_ARM || ehdr.e_machine == EM_AARCH64) {
1597			if (elf_name[0] == '$' && strchr("adtx", elf_name[1])
1598			    && (elf_name[2] == '\0' || elf_name[2] == '.'))
1599				continue;
1600		}
1601
1602		/* Reject RISCV ELF "mapping symbols" */
1603		if (ehdr.e_machine == EM_RISCV) {
1604			if (elf_name[0] == '$' && strchr("dx", elf_name[1]))
1605				continue;
1606		}
1607
1608		if (runtime_ss->opdsec && sym.st_shndx == runtime_ss->opdidx) {
1609			u32 offset = sym.st_value - syms_ss->opdshdr.sh_addr;
1610			u64 *opd = opddata->d_buf + offset;
1611			sym.st_value = DSO__SWAP(dso, u64, *opd);
1612			sym.st_shndx = elf_addr_to_index(runtime_ss->elf,
1613					sym.st_value);
1614			used_opd = true;
1615		}
1616
1617		/*
1618		 * When loading symbols in a data mapping, ABS symbols (which
1619		 * has a value of SHN_ABS in its st_shndx) failed at
1620		 * elf_getscn().  And it marks the loading as a failure so
1621		 * already loaded symbols cannot be fixed up.
1622		 *
1623		 * I'm not sure what should be done. Just ignore them for now.
1624		 * - Namhyung Kim
1625		 */
1626		if (sym.st_shndx == SHN_ABS)
1627			continue;
1628
1629		sec = elf_getscn(syms_ss->elf, sym.st_shndx);
1630		if (!sec)
1631			goto out_elf_end;
1632
1633		gelf_getshdr(sec, &shdr);
1634
1635		/*
1636		 * If the attribute bit SHF_ALLOC is not set, the section
1637		 * doesn't occupy memory during process execution.
1638		 * E.g. ".gnu.warning.*" section is used by linker to generate
1639		 * warnings when calling deprecated functions, the symbols in
1640		 * the section aren't loaded to memory during process execution,
1641		 * so skip them.
1642		 */
1643		if (!(shdr.sh_flags & SHF_ALLOC))
1644			continue;
1645
1646		secstrs = secstrs_sym;
1647
1648		/*
1649		 * We have to fallback to runtime when syms' section header has
1650		 * NOBITS set. NOBITS results in file offset (sh_offset) not
1651		 * being incremented. So sh_offset used below has different
1652		 * values for syms (invalid) and runtime (valid).
1653		 */
1654		if (shdr.sh_type == SHT_NOBITS) {
1655			sec = elf_getscn(runtime_ss->elf, sym.st_shndx);
1656			if (!sec)
1657				goto out_elf_end;
1658
1659			gelf_getshdr(sec, &shdr);
1660			secstrs = secstrs_run;
1661		}
1662
1663		if (is_label && !elf_sec__filter(&shdr, secstrs))
1664			continue;
1665
1666		section_name = elf_sec__name(&shdr, secstrs);
1667
1668		/* On ARM, symbols for thumb functions have 1 added to
1669		 * the symbol address as a flag - remove it */
1670		if ((ehdr.e_machine == EM_ARM) &&
1671		    (GELF_ST_TYPE(sym.st_info) == STT_FUNC) &&
1672		    (sym.st_value & 1))
1673			--sym.st_value;
1674
1675		if (dso__kernel(dso)) {
1676			if (dso__process_kernel_symbol(dso, map, &sym, &shdr,
1677						       kmaps, kmap, &curr_dso,
1678						       section_name,
1679						       adjust_kernel_syms,
1680						       kmodule,
1681						       &remap_kernel,
1682						       max_text_sh_offset))
1683				goto out_elf_end;
1684		} else if ((used_opd && runtime_ss->adjust_symbols) ||
1685			   (!used_opd && syms_ss->adjust_symbols)) {
1686			GElf_Phdr phdr;
1687
1688			if (elf_read_program_header(runtime_ss->elf,
1689						    (u64)sym.st_value, &phdr)) {
1690				pr_debug4("%s: failed to find program header for "
1691					   "symbol: %s st_value: %#" PRIx64 "\n",
1692					   __func__, elf_name, (u64)sym.st_value);
1693				pr_debug4("%s: adjusting symbol: st_value: %#" PRIx64 " "
1694					"sh_addr: %#" PRIx64 " sh_offset: %#" PRIx64 "\n",
1695					__func__, (u64)sym.st_value, (u64)shdr.sh_addr,
1696					(u64)shdr.sh_offset);
1697				/*
1698				 * Fail to find program header, let's rollback
1699				 * to use shdr.sh_addr and shdr.sh_offset to
1700				 * calibrate symbol's file address, though this
1701				 * is not necessary for normal C ELF file, we
1702				 * still need to handle java JIT symbols in this
1703				 * case.
1704				 */
1705				sym.st_value -= shdr.sh_addr - shdr.sh_offset;
1706			} else {
1707				pr_debug4("%s: adjusting symbol: st_value: %#" PRIx64 " "
1708					"p_vaddr: %#" PRIx64 " p_offset: %#" PRIx64 "\n",
1709					__func__, (u64)sym.st_value, (u64)phdr.p_vaddr,
1710					(u64)phdr.p_offset);
1711				sym.st_value -= phdr.p_vaddr - phdr.p_offset;
1712			}
1713		}
1714
1715		demangled = dso__demangle_sym(dso, kmodule, elf_name);
1716		if (demangled != NULL)
1717			elf_name = demangled;
1718
1719		f = symbol__new(sym.st_value, sym.st_size,
1720				GELF_ST_BIND(sym.st_info),
1721				GELF_ST_TYPE(sym.st_info), elf_name);
1722		free(demangled);
1723		if (!f)
1724			goto out_elf_end;
1725
1726		arch__sym_update(f, &sym);
1727
1728		__symbols__insert(dso__symbols(curr_dso), f, dso__kernel(dso));
1729		nr++;
1730	}
1731	dso__put(curr_dso);
1732
1733	/*
1734	 * For misannotated, zeroed, ASM function sizes.
1735	 */
1736	if (nr > 0) {
1737		symbols__fixup_end(dso__symbols(dso), false);
1738		symbols__fixup_duplicate(dso__symbols(dso));
1739		if (kmap) {
1740			/*
1741			 * We need to fixup this here too because we create new
1742			 * maps here, for things like vsyscall sections.
1743			 */
1744			maps__fixup_end(kmaps);
1745		}
1746	}
1747	return nr;
1748out_elf_end:
1749	dso__put(curr_dso);
1750	return -1;
1751}
1752
1753int dso__load_sym(struct dso *dso, struct map *map, struct symsrc *syms_ss,
1754		  struct symsrc *runtime_ss, int kmodule)
1755{
1756	int nr = 0;
1757	int err = -1;
1758
1759	dso__set_symtab_type(dso, syms_ss->type);
1760	dso__set_is_64_bit(dso, syms_ss->is_64_bit);
1761	dso__set_rel(dso, syms_ss->ehdr.e_type == ET_REL);
1762
1763	/*
1764	 * Modules may already have symbols from kallsyms, but those symbols
1765	 * have the wrong values for the dso maps, so remove them.
1766	 */
1767	if (kmodule && syms_ss->symtab)
1768		symbols__delete(dso__symbols(dso));
1769
1770	if (!syms_ss->symtab) {
1771		/*
1772		 * If the vmlinux is stripped, fail so we will fall back
1773		 * to using kallsyms. The vmlinux runtime symbols aren't
1774		 * of much use.
1775		 */
1776		if (dso__kernel(dso))
1777			return err;
1778	} else  {
1779		err = dso__load_sym_internal(dso, map, syms_ss, runtime_ss,
1780					     kmodule, 0);
1781		if (err < 0)
1782			return err;
1783		nr = err;
1784	}
1785
1786	if (syms_ss->dynsym) {
1787		err = dso__load_sym_internal(dso, map, syms_ss, runtime_ss,
1788					     kmodule, 1);
1789		if (err < 0)
1790			return err;
1791		nr += err;
1792	}
1793
1794	/*
1795	 * The .gnu_debugdata is a special situation: it contains a symbol
1796	 * table, but the runtime file may also contain dynsym entries which are
1797	 * not present there. We need to load both.
1798	 */
1799	if (syms_ss->type == DSO_BINARY_TYPE__GNU_DEBUGDATA && runtime_ss->dynsym) {
1800		err = dso__load_sym_internal(dso, map, runtime_ss, runtime_ss,
1801					     kmodule, 1);
1802		if (err < 0)
1803			return err;
1804		nr += err;
1805	}
1806
1807	return nr;
1808}
1809
1810static int elf_read_maps(Elf *elf, bool exe, mapfn_t mapfn, void *data)
1811{
1812	GElf_Phdr phdr;
1813	size_t i, phdrnum;
1814	int err;
1815	u64 sz;
1816
1817	if (elf_getphdrnum(elf, &phdrnum))
1818		return -1;
1819
1820	for (i = 0; i < phdrnum; i++) {
1821		if (gelf_getphdr(elf, i, &phdr) == NULL)
1822			return -1;
1823		if (phdr.p_type != PT_LOAD)
1824			continue;
1825		if (exe) {
1826			if (!(phdr.p_flags & PF_X))
1827				continue;
1828		} else {
1829			if (!(phdr.p_flags & PF_R))
1830				continue;
1831		}
1832		sz = min(phdr.p_memsz, phdr.p_filesz);
1833		if (!sz)
1834			continue;
1835		err = mapfn(phdr.p_vaddr, sz, phdr.p_offset, data);
1836		if (err)
1837			return err;
1838	}
1839	return 0;
1840}
1841
1842int file__read_maps(int fd, bool exe, mapfn_t mapfn, void *data,
1843		    bool *is_64_bit)
1844{
1845	int err;
1846	Elf *elf;
1847
1848	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
1849	if (elf == NULL)
1850		return -1;
1851
1852	if (is_64_bit)
1853		*is_64_bit = (gelf_getclass(elf) == ELFCLASS64);
1854
1855	err = elf_read_maps(elf, exe, mapfn, data);
1856
1857	elf_end(elf);
1858	return err;
1859}
1860
1861enum dso_type dso__type_fd(int fd)
1862{
1863	enum dso_type dso_type = DSO__TYPE_UNKNOWN;
1864	GElf_Ehdr ehdr;
1865	Elf_Kind ek;
1866	Elf *elf;
1867
1868	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
1869	if (elf == NULL)
1870		goto out;
1871
1872	ek = elf_kind(elf);
1873	if (ek != ELF_K_ELF)
1874		goto out_end;
1875
1876	if (gelf_getclass(elf) == ELFCLASS64) {
1877		dso_type = DSO__TYPE_64BIT;
1878		goto out_end;
1879	}
1880
1881	if (gelf_getehdr(elf, &ehdr) == NULL)
1882		goto out_end;
1883
1884	if (ehdr.e_machine == EM_X86_64)
1885		dso_type = DSO__TYPE_X32BIT;
1886	else
1887		dso_type = DSO__TYPE_32BIT;
1888out_end:
1889	elf_end(elf);
1890out:
1891	return dso_type;
1892}
1893
1894static int copy_bytes(int from, off_t from_offs, int to, off_t to_offs, u64 len)
1895{
1896	ssize_t r;
1897	size_t n;
1898	int err = -1;
1899	char *buf = malloc(page_size);
1900
1901	if (buf == NULL)
1902		return -1;
1903
1904	if (lseek(to, to_offs, SEEK_SET) != to_offs)
1905		goto out;
1906
1907	if (lseek(from, from_offs, SEEK_SET) != from_offs)
1908		goto out;
1909
1910	while (len) {
1911		n = page_size;
1912		if (len < n)
1913			n = len;
1914		/* Use read because mmap won't work on proc files */
1915		r = read(from, buf, n);
1916		if (r < 0)
1917			goto out;
1918		if (!r)
1919			break;
1920		n = r;
1921		r = write(to, buf, n);
1922		if (r < 0)
1923			goto out;
1924		if ((size_t)r != n)
1925			goto out;
1926		len -= n;
1927	}
1928
1929	err = 0;
1930out:
1931	free(buf);
1932	return err;
1933}
1934
1935struct kcore {
1936	int fd;
1937	int elfclass;
1938	Elf *elf;
1939	GElf_Ehdr ehdr;
1940};
1941
1942static int kcore__open(struct kcore *kcore, const char *filename)
1943{
1944	GElf_Ehdr *ehdr;
1945
1946	kcore->fd = open(filename, O_RDONLY);
1947	if (kcore->fd == -1)
1948		return -1;
1949
1950	kcore->elf = elf_begin(kcore->fd, ELF_C_READ, NULL);
1951	if (!kcore->elf)
1952		goto out_close;
1953
1954	kcore->elfclass = gelf_getclass(kcore->elf);
1955	if (kcore->elfclass == ELFCLASSNONE)
1956		goto out_end;
1957
1958	ehdr = gelf_getehdr(kcore->elf, &kcore->ehdr);
1959	if (!ehdr)
1960		goto out_end;
1961
1962	return 0;
1963
1964out_end:
1965	elf_end(kcore->elf);
1966out_close:
1967	close(kcore->fd);
1968	return -1;
1969}
1970
1971static int kcore__init(struct kcore *kcore, char *filename, int elfclass,
1972		       bool temp)
1973{
1974	kcore->elfclass = elfclass;
1975
1976	if (temp)
1977		kcore->fd = mkstemp(filename);
1978	else
1979		kcore->fd = open(filename, O_WRONLY | O_CREAT | O_EXCL, 0400);
1980	if (kcore->fd == -1)
1981		return -1;
1982
1983	kcore->elf = elf_begin(kcore->fd, ELF_C_WRITE, NULL);
1984	if (!kcore->elf)
1985		goto out_close;
1986
1987	if (!gelf_newehdr(kcore->elf, elfclass))
1988		goto out_end;
1989
1990	memset(&kcore->ehdr, 0, sizeof(GElf_Ehdr));
1991
1992	return 0;
1993
1994out_end:
1995	elf_end(kcore->elf);
1996out_close:
1997	close(kcore->fd);
1998	unlink(filename);
1999	return -1;
2000}
2001
2002static void kcore__close(struct kcore *kcore)
2003{
2004	elf_end(kcore->elf);
2005	close(kcore->fd);
2006}
2007
2008static int kcore__copy_hdr(struct kcore *from, struct kcore *to, size_t count)
2009{
2010	GElf_Ehdr *ehdr = &to->ehdr;
2011	GElf_Ehdr *kehdr = &from->ehdr;
2012
2013	memcpy(ehdr->e_ident, kehdr->e_ident, EI_NIDENT);
2014	ehdr->e_type      = kehdr->e_type;
2015	ehdr->e_machine   = kehdr->e_machine;
2016	ehdr->e_version   = kehdr->e_version;
2017	ehdr->e_entry     = 0;
2018	ehdr->e_shoff     = 0;
2019	ehdr->e_flags     = kehdr->e_flags;
2020	ehdr->e_phnum     = count;
2021	ehdr->e_shentsize = 0;
2022	ehdr->e_shnum     = 0;
2023	ehdr->e_shstrndx  = 0;
2024
2025	if (from->elfclass == ELFCLASS32) {
2026		ehdr->e_phoff     = sizeof(Elf32_Ehdr);
2027		ehdr->e_ehsize    = sizeof(Elf32_Ehdr);
2028		ehdr->e_phentsize = sizeof(Elf32_Phdr);
2029	} else {
2030		ehdr->e_phoff     = sizeof(Elf64_Ehdr);
2031		ehdr->e_ehsize    = sizeof(Elf64_Ehdr);
2032		ehdr->e_phentsize = sizeof(Elf64_Phdr);
2033	}
2034
2035	if (!gelf_update_ehdr(to->elf, ehdr))
2036		return -1;
2037
2038	if (!gelf_newphdr(to->elf, count))
2039		return -1;
2040
2041	return 0;
2042}
2043
2044static int kcore__add_phdr(struct kcore *kcore, int idx, off_t offset,
2045			   u64 addr, u64 len)
2046{
2047	GElf_Phdr phdr = {
2048		.p_type		= PT_LOAD,
2049		.p_flags	= PF_R | PF_W | PF_X,
2050		.p_offset	= offset,
2051		.p_vaddr	= addr,
2052		.p_paddr	= 0,
2053		.p_filesz	= len,
2054		.p_memsz	= len,
2055		.p_align	= page_size,
2056	};
2057
2058	if (!gelf_update_phdr(kcore->elf, idx, &phdr))
2059		return -1;
2060
2061	return 0;
2062}
2063
2064static off_t kcore__write(struct kcore *kcore)
2065{
2066	return elf_update(kcore->elf, ELF_C_WRITE);
2067}
2068
2069struct phdr_data {
2070	off_t offset;
2071	off_t rel;
2072	u64 addr;
2073	u64 len;
2074	struct list_head node;
2075	struct phdr_data *remaps;
2076};
2077
2078struct sym_data {
2079	u64 addr;
2080	struct list_head node;
2081};
2082
2083struct kcore_copy_info {
2084	u64 stext;
2085	u64 etext;
2086	u64 first_symbol;
2087	u64 last_symbol;
2088	u64 first_module;
2089	u64 first_module_symbol;
2090	u64 last_module_symbol;
2091	size_t phnum;
2092	struct list_head phdrs;
2093	struct list_head syms;
2094};
2095
2096#define kcore_copy__for_each_phdr(k, p) \
2097	list_for_each_entry((p), &(k)->phdrs, node)
2098
2099static struct phdr_data *phdr_data__new(u64 addr, u64 len, off_t offset)
2100{
2101	struct phdr_data *p = zalloc(sizeof(*p));
2102
2103	if (p) {
2104		p->addr   = addr;
2105		p->len    = len;
2106		p->offset = offset;
2107	}
2108
2109	return p;
2110}
2111
2112static struct phdr_data *kcore_copy_info__addnew(struct kcore_copy_info *kci,
2113						 u64 addr, u64 len,
2114						 off_t offset)
2115{
2116	struct phdr_data *p = phdr_data__new(addr, len, offset);
2117
2118	if (p)
2119		list_add_tail(&p->node, &kci->phdrs);
2120
2121	return p;
2122}
2123
2124static void kcore_copy__free_phdrs(struct kcore_copy_info *kci)
2125{
2126	struct phdr_data *p, *tmp;
2127
2128	list_for_each_entry_safe(p, tmp, &kci->phdrs, node) {
2129		list_del_init(&p->node);
2130		free(p);
2131	}
2132}
2133
2134static struct sym_data *kcore_copy__new_sym(struct kcore_copy_info *kci,
2135					    u64 addr)
2136{
2137	struct sym_data *s = zalloc(sizeof(*s));
2138
2139	if (s) {
2140		s->addr = addr;
2141		list_add_tail(&s->node, &kci->syms);
2142	}
2143
2144	return s;
2145}
2146
2147static void kcore_copy__free_syms(struct kcore_copy_info *kci)
2148{
2149	struct sym_data *s, *tmp;
2150
2151	list_for_each_entry_safe(s, tmp, &kci->syms, node) {
2152		list_del_init(&s->node);
2153		free(s);
2154	}
2155}
2156
2157static int kcore_copy__process_kallsyms(void *arg, const char *name, char type,
2158					u64 start)
2159{
2160	struct kcore_copy_info *kci = arg;
2161
2162	if (!kallsyms__is_function(type))
2163		return 0;
2164
2165	if (strchr(name, '[')) {
2166		if (!kci->first_module_symbol || start < kci->first_module_symbol)
2167			kci->first_module_symbol = start;
2168		if (start > kci->last_module_symbol)
2169			kci->last_module_symbol = start;
2170		return 0;
2171	}
2172
2173	if (!kci->first_symbol || start < kci->first_symbol)
2174		kci->first_symbol = start;
2175
2176	if (!kci->last_symbol || start > kci->last_symbol)
2177		kci->last_symbol = start;
2178
2179	if (!strcmp(name, "_stext")) {
2180		kci->stext = start;
2181		return 0;
2182	}
2183
2184	if (!strcmp(name, "_etext")) {
2185		kci->etext = start;
2186		return 0;
2187	}
2188
2189	if (is_entry_trampoline(name) && !kcore_copy__new_sym(kci, start))
2190		return -1;
2191
2192	return 0;
2193}
2194
2195static int kcore_copy__parse_kallsyms(struct kcore_copy_info *kci,
2196				      const char *dir)
2197{
2198	char kallsyms_filename[PATH_MAX];
2199
2200	scnprintf(kallsyms_filename, PATH_MAX, "%s/kallsyms", dir);
2201
2202	if (symbol__restricted_filename(kallsyms_filename, "/proc/kallsyms"))
2203		return -1;
2204
2205	if (kallsyms__parse(kallsyms_filename, kci,
2206			    kcore_copy__process_kallsyms) < 0)
2207		return -1;
2208
2209	return 0;
2210}
2211
2212static int kcore_copy__process_modules(void *arg,
2213				       const char *name __maybe_unused,
2214				       u64 start, u64 size __maybe_unused)
2215{
2216	struct kcore_copy_info *kci = arg;
2217
2218	if (!kci->first_module || start < kci->first_module)
2219		kci->first_module = start;
2220
2221	return 0;
2222}
2223
2224static int kcore_copy__parse_modules(struct kcore_copy_info *kci,
2225				     const char *dir)
2226{
2227	char modules_filename[PATH_MAX];
2228
2229	scnprintf(modules_filename, PATH_MAX, "%s/modules", dir);
2230
2231	if (symbol__restricted_filename(modules_filename, "/proc/modules"))
2232		return -1;
2233
2234	if (modules__parse(modules_filename, kci,
2235			   kcore_copy__process_modules) < 0)
2236		return -1;
2237
2238	return 0;
2239}
2240
2241static int kcore_copy__map(struct kcore_copy_info *kci, u64 start, u64 end,
2242			   u64 pgoff, u64 s, u64 e)
2243{
2244	u64 len, offset;
2245
2246	if (s < start || s >= end)
2247		return 0;
2248
2249	offset = (s - start) + pgoff;
2250	len = e < end ? e - s : end - s;
2251
2252	return kcore_copy_info__addnew(kci, s, len, offset) ? 0 : -1;
2253}
2254
2255static int kcore_copy__read_map(u64 start, u64 len, u64 pgoff, void *data)
2256{
2257	struct kcore_copy_info *kci = data;
2258	u64 end = start + len;
2259	struct sym_data *sdat;
2260
2261	if (kcore_copy__map(kci, start, end, pgoff, kci->stext, kci->etext))
2262		return -1;
2263
2264	if (kcore_copy__map(kci, start, end, pgoff, kci->first_module,
2265			    kci->last_module_symbol))
2266		return -1;
2267
2268	list_for_each_entry(sdat, &kci->syms, node) {
2269		u64 s = round_down(sdat->addr, page_size);
2270
2271		if (kcore_copy__map(kci, start, end, pgoff, s, s + len))
2272			return -1;
2273	}
2274
2275	return 0;
2276}
2277
2278static int kcore_copy__read_maps(struct kcore_copy_info *kci, Elf *elf)
2279{
2280	if (elf_read_maps(elf, true, kcore_copy__read_map, kci) < 0)
2281		return -1;
2282
2283	return 0;
2284}
2285
2286static void kcore_copy__find_remaps(struct kcore_copy_info *kci)
2287{
2288	struct phdr_data *p, *k = NULL;
2289	u64 kend;
2290
2291	if (!kci->stext)
2292		return;
2293
2294	/* Find phdr that corresponds to the kernel map (contains stext) */
2295	kcore_copy__for_each_phdr(kci, p) {
2296		u64 pend = p->addr + p->len - 1;
2297
2298		if (p->addr <= kci->stext && pend >= kci->stext) {
2299			k = p;
2300			break;
2301		}
2302	}
2303
2304	if (!k)
2305		return;
2306
2307	kend = k->offset + k->len;
2308
2309	/* Find phdrs that remap the kernel */
2310	kcore_copy__for_each_phdr(kci, p) {
2311		u64 pend = p->offset + p->len;
2312
2313		if (p == k)
2314			continue;
2315
2316		if (p->offset >= k->offset && pend <= kend)
2317			p->remaps = k;
2318	}
2319}
2320
2321static void kcore_copy__layout(struct kcore_copy_info *kci)
2322{
2323	struct phdr_data *p;
2324	off_t rel = 0;
2325
2326	kcore_copy__find_remaps(kci);
2327
2328	kcore_copy__for_each_phdr(kci, p) {
2329		if (!p->remaps) {
2330			p->rel = rel;
2331			rel += p->len;
2332		}
2333		kci->phnum += 1;
2334	}
2335
2336	kcore_copy__for_each_phdr(kci, p) {
2337		struct phdr_data *k = p->remaps;
2338
2339		if (k)
2340			p->rel = p->offset - k->offset + k->rel;
2341	}
2342}
2343
2344static int kcore_copy__calc_maps(struct kcore_copy_info *kci, const char *dir,
2345				 Elf *elf)
2346{
2347	if (kcore_copy__parse_kallsyms(kci, dir))
2348		return -1;
2349
2350	if (kcore_copy__parse_modules(kci, dir))
2351		return -1;
2352
2353	if (kci->stext)
2354		kci->stext = round_down(kci->stext, page_size);
2355	else
2356		kci->stext = round_down(kci->first_symbol, page_size);
2357
2358	if (kci->etext) {
2359		kci->etext = round_up(kci->etext, page_size);
2360	} else if (kci->last_symbol) {
2361		kci->etext = round_up(kci->last_symbol, page_size);
2362		kci->etext += page_size;
2363	}
2364
2365	if (kci->first_module_symbol &&
2366	    (!kci->first_module || kci->first_module_symbol < kci->first_module))
2367		kci->first_module = kci->first_module_symbol;
2368
2369	kci->first_module = round_down(kci->first_module, page_size);
2370
2371	if (kci->last_module_symbol) {
2372		kci->last_module_symbol = round_up(kci->last_module_symbol,
2373						   page_size);
2374		kci->last_module_symbol += page_size;
2375	}
2376
2377	if (!kci->stext || !kci->etext)
2378		return -1;
2379
2380	if (kci->first_module && !kci->last_module_symbol)
2381		return -1;
2382
2383	if (kcore_copy__read_maps(kci, elf))
2384		return -1;
2385
2386	kcore_copy__layout(kci);
2387
2388	return 0;
2389}
2390
2391static int kcore_copy__copy_file(const char *from_dir, const char *to_dir,
2392				 const char *name)
2393{
2394	char from_filename[PATH_MAX];
2395	char to_filename[PATH_MAX];
2396
2397	scnprintf(from_filename, PATH_MAX, "%s/%s", from_dir, name);
2398	scnprintf(to_filename, PATH_MAX, "%s/%s", to_dir, name);
2399
2400	return copyfile_mode(from_filename, to_filename, 0400);
2401}
2402
2403static int kcore_copy__unlink(const char *dir, const char *name)
2404{
2405	char filename[PATH_MAX];
2406
2407	scnprintf(filename, PATH_MAX, "%s/%s", dir, name);
2408
2409	return unlink(filename);
2410}
2411
2412static int kcore_copy__compare_fds(int from, int to)
2413{
2414	char *buf_from;
2415	char *buf_to;
2416	ssize_t ret;
2417	size_t len;
2418	int err = -1;
2419
2420	buf_from = malloc(page_size);
2421	buf_to = malloc(page_size);
2422	if (!buf_from || !buf_to)
2423		goto out;
2424
2425	while (1) {
2426		/* Use read because mmap won't work on proc files */
2427		ret = read(from, buf_from, page_size);
2428		if (ret < 0)
2429			goto out;
2430
2431		if (!ret)
2432			break;
2433
2434		len = ret;
2435
2436		if (readn(to, buf_to, len) != (int)len)
2437			goto out;
2438
2439		if (memcmp(buf_from, buf_to, len))
2440			goto out;
2441	}
2442
2443	err = 0;
2444out:
2445	free(buf_to);
2446	free(buf_from);
2447	return err;
2448}
2449
2450static int kcore_copy__compare_files(const char *from_filename,
2451				     const char *to_filename)
2452{
2453	int from, to, err = -1;
2454
2455	from = open(from_filename, O_RDONLY);
2456	if (from < 0)
2457		return -1;
2458
2459	to = open(to_filename, O_RDONLY);
2460	if (to < 0)
2461		goto out_close_from;
2462
2463	err = kcore_copy__compare_fds(from, to);
2464
2465	close(to);
2466out_close_from:
2467	close(from);
2468	return err;
2469}
2470
2471static int kcore_copy__compare_file(const char *from_dir, const char *to_dir,
2472				    const char *name)
2473{
2474	char from_filename[PATH_MAX];
2475	char to_filename[PATH_MAX];
2476
2477	scnprintf(from_filename, PATH_MAX, "%s/%s", from_dir, name);
2478	scnprintf(to_filename, PATH_MAX, "%s/%s", to_dir, name);
2479
2480	return kcore_copy__compare_files(from_filename, to_filename);
2481}
2482
2483/**
2484 * kcore_copy - copy kallsyms, modules and kcore from one directory to another.
2485 * @from_dir: from directory
2486 * @to_dir: to directory
2487 *
2488 * This function copies kallsyms, modules and kcore files from one directory to
2489 * another.  kallsyms and modules are copied entirely.  Only code segments are
2490 * copied from kcore.  It is assumed that two segments suffice: one for the
2491 * kernel proper and one for all the modules.  The code segments are determined
2492 * from kallsyms and modules files.  The kernel map starts at _stext or the
2493 * lowest function symbol, and ends at _etext or the highest function symbol.
2494 * The module map starts at the lowest module address and ends at the highest
2495 * module symbol.  Start addresses are rounded down to the nearest page.  End
2496 * addresses are rounded up to the nearest page.  An extra page is added to the
2497 * highest kernel symbol and highest module symbol to, hopefully, encompass that
2498 * symbol too.  Because it contains only code sections, the resulting kcore is
2499 * unusual.  One significant peculiarity is that the mapping (start -> pgoff)
2500 * is not the same for the kernel map and the modules map.  That happens because
2501 * the data is copied adjacently whereas the original kcore has gaps.  Finally,
2502 * kallsyms file is compared with its copy to check that modules have not been
2503 * loaded or unloaded while the copies were taking place.
2504 *
2505 * Return: %0 on success, %-1 on failure.
2506 */
2507int kcore_copy(const char *from_dir, const char *to_dir)
2508{
2509	struct kcore kcore;
2510	struct kcore extract;
2511	int idx = 0, err = -1;
2512	off_t offset, sz;
2513	struct kcore_copy_info kci = { .stext = 0, };
2514	char kcore_filename[PATH_MAX];
2515	char extract_filename[PATH_MAX];
2516	struct phdr_data *p;
2517
2518	INIT_LIST_HEAD(&kci.phdrs);
2519	INIT_LIST_HEAD(&kci.syms);
2520
2521	if (kcore_copy__copy_file(from_dir, to_dir, "kallsyms"))
2522		return -1;
2523
2524	if (kcore_copy__copy_file(from_dir, to_dir, "modules"))
2525		goto out_unlink_kallsyms;
2526
2527	scnprintf(kcore_filename, PATH_MAX, "%s/kcore", from_dir);
2528	scnprintf(extract_filename, PATH_MAX, "%s/kcore", to_dir);
2529
2530	if (kcore__open(&kcore, kcore_filename))
2531		goto out_unlink_modules;
2532
2533	if (kcore_copy__calc_maps(&kci, from_dir, kcore.elf))
2534		goto out_kcore_close;
2535
2536	if (kcore__init(&extract, extract_filename, kcore.elfclass, false))
2537		goto out_kcore_close;
2538
2539	if (kcore__copy_hdr(&kcore, &extract, kci.phnum))
2540		goto out_extract_close;
2541
2542	offset = gelf_fsize(extract.elf, ELF_T_EHDR, 1, EV_CURRENT) +
2543		 gelf_fsize(extract.elf, ELF_T_PHDR, kci.phnum, EV_CURRENT);
2544	offset = round_up(offset, page_size);
2545
2546	kcore_copy__for_each_phdr(&kci, p) {
2547		off_t offs = p->rel + offset;
2548
2549		if (kcore__add_phdr(&extract, idx++, offs, p->addr, p->len))
2550			goto out_extract_close;
2551	}
2552
2553	sz = kcore__write(&extract);
2554	if (sz < 0 || sz > offset)
2555		goto out_extract_close;
2556
2557	kcore_copy__for_each_phdr(&kci, p) {
2558		off_t offs = p->rel + offset;
2559
2560		if (p->remaps)
2561			continue;
2562		if (copy_bytes(kcore.fd, p->offset, extract.fd, offs, p->len))
2563			goto out_extract_close;
2564	}
2565
2566	if (kcore_copy__compare_file(from_dir, to_dir, "kallsyms"))
2567		goto out_extract_close;
2568
2569	err = 0;
2570
2571out_extract_close:
2572	kcore__close(&extract);
2573	if (err)
2574		unlink(extract_filename);
2575out_kcore_close:
2576	kcore__close(&kcore);
2577out_unlink_modules:
2578	if (err)
2579		kcore_copy__unlink(to_dir, "modules");
2580out_unlink_kallsyms:
2581	if (err)
2582		kcore_copy__unlink(to_dir, "kallsyms");
2583
2584	kcore_copy__free_phdrs(&kci);
2585	kcore_copy__free_syms(&kci);
2586
2587	return err;
2588}
2589
2590int kcore_extract__create(struct kcore_extract *kce)
2591{
2592	struct kcore kcore;
2593	struct kcore extract;
2594	size_t count = 1;
2595	int idx = 0, err = -1;
2596	off_t offset = page_size, sz;
2597
2598	if (kcore__open(&kcore, kce->kcore_filename))
2599		return -1;
2600
2601	strcpy(kce->extract_filename, PERF_KCORE_EXTRACT);
2602	if (kcore__init(&extract, kce->extract_filename, kcore.elfclass, true))
2603		goto out_kcore_close;
2604
2605	if (kcore__copy_hdr(&kcore, &extract, count))
2606		goto out_extract_close;
2607
2608	if (kcore__add_phdr(&extract, idx, offset, kce->addr, kce->len))
2609		goto out_extract_close;
2610
2611	sz = kcore__write(&extract);
2612	if (sz < 0 || sz > offset)
2613		goto out_extract_close;
2614
2615	if (copy_bytes(kcore.fd, kce->offs, extract.fd, offset, kce->len))
2616		goto out_extract_close;
2617
2618	err = 0;
2619
2620out_extract_close:
2621	kcore__close(&extract);
2622	if (err)
2623		unlink(kce->extract_filename);
2624out_kcore_close:
2625	kcore__close(&kcore);
2626
2627	return err;
2628}
2629
2630void kcore_extract__delete(struct kcore_extract *kce)
2631{
2632	unlink(kce->extract_filename);
2633}
2634
2635#ifdef HAVE_GELF_GETNOTE_SUPPORT
2636
2637static void sdt_adjust_loc(struct sdt_note *tmp, GElf_Addr base_off)
2638{
2639	if (!base_off)
2640		return;
2641
2642	if (tmp->bit32)
2643		tmp->addr.a32[SDT_NOTE_IDX_LOC] =
2644			tmp->addr.a32[SDT_NOTE_IDX_LOC] + base_off -
2645			tmp->addr.a32[SDT_NOTE_IDX_BASE];
2646	else
2647		tmp->addr.a64[SDT_NOTE_IDX_LOC] =
2648			tmp->addr.a64[SDT_NOTE_IDX_LOC] + base_off -
2649			tmp->addr.a64[SDT_NOTE_IDX_BASE];
2650}
2651
2652static void sdt_adjust_refctr(struct sdt_note *tmp, GElf_Addr base_addr,
2653			      GElf_Addr base_off)
2654{
2655	if (!base_off)
2656		return;
2657
2658	if (tmp->bit32 && tmp->addr.a32[SDT_NOTE_IDX_REFCTR])
2659		tmp->addr.a32[SDT_NOTE_IDX_REFCTR] -= (base_addr - base_off);
2660	else if (tmp->addr.a64[SDT_NOTE_IDX_REFCTR])
2661		tmp->addr.a64[SDT_NOTE_IDX_REFCTR] -= (base_addr - base_off);
2662}
2663
2664/**
2665 * populate_sdt_note : Parse raw data and identify SDT note
2666 * @elf: elf of the opened file
2667 * @data: raw data of a section with description offset applied
2668 * @len: note description size
2669 * @type: type of the note
2670 * @sdt_notes: List to add the SDT note
2671 *
2672 * Responsible for parsing the @data in section .note.stapsdt in @elf and
2673 * if its an SDT note, it appends to @sdt_notes list.
2674 */
2675static int populate_sdt_note(Elf **elf, const char *data, size_t len,
2676			     struct list_head *sdt_notes)
2677{
2678	const char *provider, *name, *args;
2679	struct sdt_note *tmp = NULL;
2680	GElf_Ehdr ehdr;
2681	GElf_Shdr shdr;
2682	int ret = -EINVAL;
2683
2684	union {
2685		Elf64_Addr a64[NR_ADDR];
2686		Elf32_Addr a32[NR_ADDR];
2687	} buf;
2688
2689	Elf_Data dst = {
2690		.d_buf = &buf, .d_type = ELF_T_ADDR, .d_version = EV_CURRENT,
2691		.d_size = gelf_fsize((*elf), ELF_T_ADDR, NR_ADDR, EV_CURRENT),
2692		.d_off = 0, .d_align = 0
2693	};
2694	Elf_Data src = {
2695		.d_buf = (void *) data, .d_type = ELF_T_ADDR,
2696		.d_version = EV_CURRENT, .d_size = dst.d_size, .d_off = 0,
2697		.d_align = 0
2698	};
2699
2700	tmp = (struct sdt_note *)calloc(1, sizeof(struct sdt_note));
2701	if (!tmp) {
2702		ret = -ENOMEM;
2703		goto out_err;
2704	}
2705
2706	INIT_LIST_HEAD(&tmp->note_list);
2707
2708	if (len < dst.d_size + 3)
2709		goto out_free_note;
2710
2711	/* Translation from file representation to memory representation */
2712	if (gelf_xlatetom(*elf, &dst, &src,
2713			  elf_getident(*elf, NULL)[EI_DATA]) == NULL) {
2714		pr_err("gelf_xlatetom : %s\n", elf_errmsg(-1));
2715		goto out_free_note;
2716	}
2717
2718	/* Populate the fields of sdt_note */
2719	provider = data + dst.d_size;
2720
2721	name = (const char *)memchr(provider, '\0', data + len - provider);
2722	if (name++ == NULL)
2723		goto out_free_note;
2724
2725	tmp->provider = strdup(provider);
2726	if (!tmp->provider) {
2727		ret = -ENOMEM;
2728		goto out_free_note;
2729	}
2730	tmp->name = strdup(name);
2731	if (!tmp->name) {
2732		ret = -ENOMEM;
2733		goto out_free_prov;
2734	}
2735
2736	args = memchr(name, '\0', data + len - name);
2737
2738	/*
2739	 * There is no argument if:
2740	 * - We reached the end of the note;
2741	 * - There is not enough room to hold a potential string;
2742	 * - The argument string is empty or just contains ':'.
2743	 */
2744	if (args == NULL || data + len - args < 2 ||
2745		args[1] == ':' || args[1] == '\0')
2746		tmp->args = NULL;
2747	else {
2748		tmp->args = strdup(++args);
2749		if (!tmp->args) {
2750			ret = -ENOMEM;
2751			goto out_free_name;
2752		}
2753	}
2754
2755	if (gelf_getclass(*elf) == ELFCLASS32) {
2756		memcpy(&tmp->addr, &buf, 3 * sizeof(Elf32_Addr));
2757		tmp->bit32 = true;
2758	} else {
2759		memcpy(&tmp->addr, &buf, 3 * sizeof(Elf64_Addr));
2760		tmp->bit32 = false;
2761	}
2762
2763	if (!gelf_getehdr(*elf, &ehdr)) {
2764		pr_debug("%s : cannot get elf header.\n", __func__);
2765		ret = -EBADF;
2766		goto out_free_args;
2767	}
2768
2769	/* Adjust the prelink effect :
2770	 * Find out the .stapsdt.base section.
2771	 * This scn will help us to handle prelinking (if present).
2772	 * Compare the retrieved file offset of the base section with the
2773	 * base address in the description of the SDT note. If its different,
2774	 * then accordingly, adjust the note location.
2775	 */
2776	if (elf_section_by_name(*elf, &ehdr, &shdr, SDT_BASE_SCN, NULL))
2777		sdt_adjust_loc(tmp, shdr.sh_offset);
2778
2779	/* Adjust reference counter offset */
2780	if (elf_section_by_name(*elf, &ehdr, &shdr, SDT_PROBES_SCN, NULL))
2781		sdt_adjust_refctr(tmp, shdr.sh_addr, shdr.sh_offset);
2782
2783	list_add_tail(&tmp->note_list, sdt_notes);
2784	return 0;
2785
2786out_free_args:
2787	zfree(&tmp->args);
2788out_free_name:
2789	zfree(&tmp->name);
2790out_free_prov:
2791	zfree(&tmp->provider);
2792out_free_note:
2793	free(tmp);
2794out_err:
2795	return ret;
2796}
2797
2798/**
2799 * construct_sdt_notes_list : constructs a list of SDT notes
2800 * @elf : elf to look into
2801 * @sdt_notes : empty list_head
2802 *
2803 * Scans the sections in 'elf' for the section
2804 * .note.stapsdt. It, then calls populate_sdt_note to find
2805 * out the SDT events and populates the 'sdt_notes'.
2806 */
2807static int construct_sdt_notes_list(Elf *elf, struct list_head *sdt_notes)
2808{
2809	GElf_Ehdr ehdr;
2810	Elf_Scn *scn = NULL;
2811	Elf_Data *data;
2812	GElf_Shdr shdr;
2813	size_t shstrndx, next;
2814	GElf_Nhdr nhdr;
2815	size_t name_off, desc_off, offset;
2816	int ret = 0;
2817
2818	if (gelf_getehdr(elf, &ehdr) == NULL) {
2819		ret = -EBADF;
2820		goto out_ret;
2821	}
2822	if (elf_getshdrstrndx(elf, &shstrndx) != 0) {
2823		ret = -EBADF;
2824		goto out_ret;
2825	}
2826
2827	/* Look for the required section */
2828	scn = elf_section_by_name(elf, &ehdr, &shdr, SDT_NOTE_SCN, NULL);
2829	if (!scn) {
2830		ret = -ENOENT;
2831		goto out_ret;
2832	}
2833
2834	if ((shdr.sh_type != SHT_NOTE) || (shdr.sh_flags & SHF_ALLOC)) {
2835		ret = -ENOENT;
2836		goto out_ret;
2837	}
2838
2839	data = elf_getdata(scn, NULL);
2840
2841	/* Get the SDT notes */
2842	for (offset = 0; (next = gelf_getnote(data, offset, &nhdr, &name_off,
2843					      &desc_off)) > 0; offset = next) {
2844		if (nhdr.n_namesz == sizeof(SDT_NOTE_NAME) &&
2845		    !memcmp(data->d_buf + name_off, SDT_NOTE_NAME,
2846			    sizeof(SDT_NOTE_NAME))) {
2847			/* Check the type of the note */
2848			if (nhdr.n_type != SDT_NOTE_TYPE)
2849				goto out_ret;
2850
2851			ret = populate_sdt_note(&elf, ((data->d_buf) + desc_off),
2852						nhdr.n_descsz, sdt_notes);
2853			if (ret < 0)
2854				goto out_ret;
2855		}
2856	}
2857	if (list_empty(sdt_notes))
2858		ret = -ENOENT;
2859
2860out_ret:
2861	return ret;
2862}
2863
2864/**
2865 * get_sdt_note_list : Wrapper to construct a list of sdt notes
2866 * @head : empty list_head
2867 * @target : file to find SDT notes from
2868 *
2869 * This opens the file, initializes
2870 * the ELF and then calls construct_sdt_notes_list.
2871 */
2872int get_sdt_note_list(struct list_head *head, const char *target)
2873{
2874	Elf *elf;
2875	int fd, ret;
2876
2877	fd = open(target, O_RDONLY);
2878	if (fd < 0)
2879		return -EBADF;
2880
2881	elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
2882	if (!elf) {
2883		ret = -EBADF;
2884		goto out_close;
2885	}
2886	ret = construct_sdt_notes_list(elf, head);
2887	elf_end(elf);
2888out_close:
2889	close(fd);
2890	return ret;
2891}
2892
2893/**
2894 * cleanup_sdt_note_list : free the sdt notes' list
2895 * @sdt_notes: sdt notes' list
2896 *
2897 * Free up the SDT notes in @sdt_notes.
2898 * Returns the number of SDT notes free'd.
2899 */
2900int cleanup_sdt_note_list(struct list_head *sdt_notes)
2901{
2902	struct sdt_note *tmp, *pos;
2903	int nr_free = 0;
2904
2905	list_for_each_entry_safe(pos, tmp, sdt_notes, note_list) {
2906		list_del_init(&pos->note_list);
2907		zfree(&pos->args);
2908		zfree(&pos->name);
2909		zfree(&pos->provider);
2910		free(pos);
2911		nr_free++;
2912	}
2913	return nr_free;
2914}
2915
2916/**
2917 * sdt_notes__get_count: Counts the number of sdt events
2918 * @start: list_head to sdt_notes list
2919 *
2920 * Returns the number of SDT notes in a list
2921 */
2922int sdt_notes__get_count(struct list_head *start)
2923{
2924	struct sdt_note *sdt_ptr;
2925	int count = 0;
2926
2927	list_for_each_entry(sdt_ptr, start, note_list)
2928		count++;
2929	return count;
2930}
2931#endif
2932
2933void symbol__elf_init(void)
2934{
2935	elf_version(EV_CURRENT);
2936}
~/ Read-only file preview.