git: 63fc4e820c86 - main - rtld: extract header validation into new helper check_elf_headers()
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Mon, 06 Dec 2021 18:48:21 UTC
The branch main has been updated by kib: URL: https://cgit.FreeBSD.org/src/commit/?id=63fc4e820c86f5dedb80cc31b7918deb284b455e commit 63fc4e820c86f5dedb80cc31b7918deb284b455e Author: Konstantin Belousov <kib@FreeBSD.org> AuthorDate: 2021-11-11 17:51:26 +0000 Commit: Konstantin Belousov <kib@FreeBSD.org> CommitDate: 2021-12-06 18:46:49 +0000 rtld: extract header validation into new helper check_elf_headers() Reviewed by: emaste Discussed with: jrtc27 Tested by: pho Sponsored by: The FreeBSD Foundation MFC after: 1 week Differential revision: https://reviews.freebsd.org/D32960 --- libexec/rtld-elf/map_object.c | 60 ++++++++++++++++++++++++------------------- libexec/rtld-elf/rtld.h | 1 + 2 files changed, 35 insertions(+), 26 deletions(-) diff --git a/libexec/rtld-elf/map_object.c b/libexec/rtld-elf/map_object.c index b725fe93b8f6..2da323c115cc 100644 --- a/libexec/rtld-elf/map_object.c +++ b/libexec/rtld-elf/map_object.c @@ -345,6 +345,39 @@ error: return (NULL); } +bool +check_elf_headers(const Elf_Ehdr *hdr, const char *path) +{ + if (!IS_ELF(*hdr)) { + _rtld_error("%s: invalid file format", path); + return (false); + } + if (hdr->e_ident[EI_CLASS] != ELF_TARG_CLASS || + hdr->e_ident[EI_DATA] != ELF_TARG_DATA) { + _rtld_error("%s: unsupported file layout", path); + return (false); + } + if (hdr->e_ident[EI_VERSION] != EV_CURRENT || + hdr->e_version != EV_CURRENT) { + _rtld_error("%s: unsupported file version", path); + return (false); + } + if (hdr->e_type != ET_EXEC && hdr->e_type != ET_DYN) { + _rtld_error("%s: unsupported file type", path); + return (false); + } + if (hdr->e_machine != ELF_TARG_MACH) { + _rtld_error("%s: unsupported machine", path); + return (false); + } + if (hdr->e_phentsize != sizeof(Elf_Phdr)) { + _rtld_error( + "%s: invalid shared object: e_phentsize != sizeof(Elf_Phdr)", path); + return (false); + } + return (true); +} + static Elf_Ehdr * get_elf_header(int fd, const char *path, const struct stat *sbp, Elf_Phdr **phdr_p) @@ -366,39 +399,14 @@ get_elf_header(int fd, const char *path, const struct stat *sbp, } /* Make sure the file is valid */ - if (!IS_ELF(*hdr)) { - _rtld_error("%s: invalid file format", path); + if (!check_elf_headers(hdr, path)) goto error; - } - if (hdr->e_ident[EI_CLASS] != ELF_TARG_CLASS || - hdr->e_ident[EI_DATA] != ELF_TARG_DATA) { - _rtld_error("%s: unsupported file layout", path); - goto error; - } - if (hdr->e_ident[EI_VERSION] != EV_CURRENT || - hdr->e_version != EV_CURRENT) { - _rtld_error("%s: unsupported file version", path); - goto error; - } - if (hdr->e_type != ET_EXEC && hdr->e_type != ET_DYN) { - _rtld_error("%s: unsupported file type", path); - goto error; - } - if (hdr->e_machine != ELF_TARG_MACH) { - _rtld_error("%s: unsupported machine", path); - goto error; - } /* * We rely on the program header being in the first page. This is * not strictly required by the ABI specification, but it seems to * always true in practice. And, it simplifies things considerably. */ - if (hdr->e_phentsize != sizeof(Elf_Phdr)) { - _rtld_error( - "%s: invalid shared object: e_phentsize != sizeof(Elf_Phdr)", path); - goto error; - } if (phdr_in_zero_page(hdr)) { phdr = (Elf_Phdr *)((char *)hdr + hdr->e_phoff); } else { diff --git a/libexec/rtld-elf/rtld.h b/libexec/rtld-elf/rtld.h index b216e80115bc..48b3ad526828 100644 --- a/libexec/rtld-elf/rtld.h +++ b/libexec/rtld-elf/rtld.h @@ -405,6 +405,7 @@ void free_tls_offset(Obj_Entry *obj); const Ver_Entry *fetch_ventry(const Obj_Entry *obj, unsigned long); int convert_prot(int elfflags); void *_get_tp(void); /* libc implementation */ +bool check_elf_headers(const Elf_Ehdr *hdr, const char *path); /* * MD function declarations.