src/libappimage_shared/elf.c
/* Return the offset, and the length of an ELF section with a given name in a given ELF file */
Return the offset, and the length of an ELF section with a given name in a given ELF file
Return the offset and the length of an ELF section with a given name in a given ELF file
bool appimage_get_elf_section_offset_and_length(const char* fname, const char* section_name, unsigned long* offset, unsigned long* length) {
	uint8_t* data;
	int i;
	int fd = open(fname, O_RDONLY);
	size_t map_size = (size_t) lseek(fd, 0, SEEK_END);
	data = mmap(NULL, map_size, PROT_READ, MAP_SHARED, fd, 0);
	close(fd);
	unsigned char class = data[EI_CLASS];
	if (class == ELFCLASS32) {
		Elf32_Ehdr* elf;
		Elf32_Shdr* shdr;
		elf = (Elf32_Ehdr*) data;
		shdr = (Elf32_Shdr*) (data + ((Elf32_Ehdr*) elf)->e_shoff);
		char* strTab = (char*) (data + shdr[elf->e_shstrndx].sh_offset);
		for (i = 0; i < elf->e_shnum; i++) {
			if (strcmp(&strTab[shdr[i].sh_name], section_name) == 0) {
				*offset = shdr[i].sh_offset;
				*length = shdr[i].sh_size;
			}
		}
	} else if (class == ELFCLASS64) {
		Elf64_Ehdr* elf;
		Elf64_Shdr* shdr;
		elf = (Elf64_Ehdr*) data;
		shdr = (Elf64_Shdr*) (data + elf->e_shoff);
		char* strTab = (char*) (data + shdr[elf->e_shstrndx].sh_offset);
		for (i = 0; i < elf->e_shnum; i++) {
			if (strcmp(&strTab[shdr[i].sh_name], section_name) == 0) {
				*offset = shdr[i].sh_offset;
				*length = shdr[i].sh_size;
			}
		}
	} else {
		fprintf(stderr, "Platforms other than 32-bit/64-bit are currently not supported!");
		munmap(data, map_size);
		return false;
	}
	munmap(data, map_size);
	return true;
}
bool appimage_get_elf_section_offset_and_length ( const char * fname , const char * section_name , unsigned long * offset , unsigned long * length ) { uint8_t * data ; int i ; int fd = open ( fname , O_RDONLY ) ; size_t map_size = ( size_t ) lseek ( fd , 0 , SEEK_END ) ; data = mmap ( NULL , map_size , PROT_READ , MAP_SHARED , fd , 0 ) ; close ( fd ) ; unsigned char class = data [ EI_CLASS ] ; if ( class == ELFCLASS32 ) { Elf32_Ehdr * elf ; Elf32_Shdr * shdr ; elf = ( Elf32_Ehdr * ) data ; shdr = ( Elf32_Shdr * ) ( data + ( ( Elf32_Ehdr * ) elf ) -> e_shoff ) ; char * strTab = ( char * ) ( data + shdr [ elf -> e_shstrndx ] . sh_offset ) ; for ( i = 0 ; i < elf -> e_shnum ; i ++ ) { if ( strcmp ( & strTab [ shdr [ i ] . sh_name ] , section_name ) == 0 ) { * offset = shdr [ i ] . sh_offset ; * length = shdr [ i ] . sh_size ; } } } else if ( class == ELFCLASS64 ) { Elf64_Ehdr * elf ; Elf64_Shdr * shdr ; elf = ( Elf64_Ehdr * ) data ; shdr = ( Elf64_Shdr * ) ( data + elf -> e_shoff ) ; char * strTab = ( char * ) ( data + shdr [ elf -> e_shstrndx ] . sh_offset ) ; for ( i = 0 ; i < elf -> e_shnum ; i ++ ) { if ( strcmp ( & strTab [ shdr [ i ] . sh_name ] , section_name ) == 0 ) { * offset = shdr [ i ] . sh_offset ; * length = shdr [ i ] . sh_size ; } } } else { fprintf ( stderr , " " ) ; munmap ( data , map_size ) ; return false ; } munmap ( data , map_size ) ; return true ; }
Return the offset, and the length of an ELF section with a given name in a given ELF file
Return the offset and the length of an ELF section with a given name in a given ELF file
// this trick works as both 32 and 64 bit ELF files start with the e_ident[EI_NINDENT] section