X-Git-Url: http://git.lttng.org/?a=blobdiff_plain;f=liblttng-ust%2Flttng-ust-elf.c;h=52078d9629f34df177e88857ccd82690a6fb6c4e;hb=c0c0989ab70574e09b2f7e8b48c2da6af664a849;hp=c9d2b6b3c406dcb33a8a39dfaab51af7dbe39917;hpb=e1f0c5692aa0f75c547e28efd734cc911503c4f3;p=lttng-ust.git diff --git a/liblttng-ust/lttng-ust-elf.c b/liblttng-ust/lttng-ust-elf.c index c9d2b6b3..52078d96 100644 --- a/liblttng-ust/lttng-ust-elf.c +++ b/liblttng-ust/lttng-ust-elf.c @@ -1,34 +1,31 @@ /* - * Copyright (C) 2015 Antoine Busque + * SPDX-License-Identifier: LGPL-2.1-or-later * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2.1 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * Copyright (C) 2015 Antoine Busque */ -#define _GNU_SOURCE +#define _LGPL_SOURCE +#include #include -#include #include #include -#include +#include +#include +#include #include -#include +#include #include + +#include + #include "lttng-tracer-core.h" #define BUF_LEN 4096 +#ifndef NT_GNU_BUILD_ID +# define NT_GNU_BUILD_ID 3 +#endif + /* * Retrieve the nth (where n is the `index` argument) phdr (program * header) from the given elf instance. @@ -236,21 +233,40 @@ struct lttng_ust_elf *lttng_ust_elf_create(const char *path) uint8_t e_ident[EI_NIDENT]; struct lttng_ust_elf_shdr *section_names_shdr; struct lttng_ust_elf *elf = NULL; + int ret, fd; elf = zmalloc(sizeof(struct lttng_ust_elf)); if (!elf) { goto error; } + /* Initialize fd field to -1. 0 is a valid fd number */ + elf->fd = -1; + elf->path = strdup(path); if (!elf->path) { goto error; } - elf->fd = open(elf->path, O_RDONLY | O_CLOEXEC); - if (elf->fd < 0) { + lttng_ust_lock_fd_tracker(); + fd = open(elf->path, O_RDONLY | O_CLOEXEC); + if (fd < 0) { + lttng_ust_unlock_fd_tracker(); + goto error; + } + + ret = lttng_ust_add_fd_to_tracker(fd); + if (ret < 0) { + ret = close(fd); + if (ret) { + PERROR("close on elf->fd"); + } + ret = -1; + lttng_ust_unlock_fd_tracker(); goto error; } + elf->fd = ret; + lttng_ust_unlock_fd_tracker(); if (lttng_ust_read(elf->fd, e_ident, EI_NIDENT) < EI_NIDENT) { goto error; @@ -303,16 +319,7 @@ struct lttng_ust_elf *lttng_ust_elf_create(const char *path) return elf; error: - if (elf) { - free(elf->ehdr); - if (elf->fd >= 0) { - if (close(elf->fd)) { - abort(); - } - } - free(elf->path); - free(elf); - } + lttng_ust_elf_destroy(elf); return NULL; } @@ -333,14 +340,25 @@ uint8_t lttng_ust_elf_is_pic(struct lttng_ust_elf *elf) */ void lttng_ust_elf_destroy(struct lttng_ust_elf *elf) { + int ret; + if (!elf) { return; } - free(elf->ehdr); - if (close(elf->fd)) { - abort(); + if (elf->fd >= 0) { + lttng_ust_lock_fd_tracker(); + ret = close(elf->fd); + if (!ret) { + lttng_ust_delete_fd_from_tracker(elf->fd); + } else { + PERROR("close"); + abort(); + } + lttng_ust_unlock_fd_tracker(); } + + free(elf->ehdr); free(elf->path); free(elf); } @@ -376,9 +394,9 @@ int lttng_ust_elf_get_memsz(struct lttng_ust_elf *elf, uint64_t *memsz) goto next_loop; } - low_addr = phdr->p_vaddr < low_addr ? phdr->p_vaddr : low_addr; - high_addr = phdr->p_vaddr + phdr->p_memsz > high_addr ? - phdr->p_vaddr + phdr->p_memsz : high_addr; + low_addr = min_t(uint64_t, low_addr, phdr->p_vaddr); + high_addr = max_t(uint64_t, high_addr, + phdr->p_vaddr + phdr->p_memsz); next_loop: free(phdr); } @@ -419,7 +437,7 @@ int lttng_ust_elf_get_build_id_from_segment( size_t read_len; /* Align start of note entry */ - offset += offset_align(offset, ELF_NOTE_ENTRY_ALIGN); + offset += lttng_ust_offset_align(offset, ELF_NOTE_ENTRY_ALIGN); if (offset >= segment_end) { break; } @@ -444,7 +462,7 @@ int lttng_ust_elf_get_build_id_from_segment( offset += sizeof(nhdr) + nhdr.n_namesz; /* Align start of desc entry */ - offset += offset_align(offset, ELF_NOTE_DESC_ALIGN); + offset += lttng_ust_offset_align(offset, ELF_NOTE_DESC_ALIGN); if (nhdr.n_type != NT_GNU_BUILD_ID) { /*