ref: 129b80feb976b22ba4eacaed59bd1c1f54804e1a
parent: 893983575da0f76075ffd8f3d60cb23d6c3475e6
author: Roberto E. Vargas Caballero <k0ga@shike2.com>
date: Sat Oct 30 07:21:08 EDT 2021
libmach: Add elf64getsec() This function can be used to run over the full list of sections of a file and retrieve information for every one of them.
--- a/src/libmach/deps.mk
+++ b/src/libmach/deps.mk
@@ -56,6 +56,9 @@
elf64/elf64del.o: $(INCDIR)/scc/scc/mach.h
elf64/elf64del.o: elf64/../libmach.h
elf64/elf64del.o: elf64/elf64.h
+elf64/elf64getsec.o: $(INCDIR)/scc/scc/mach.h
+elf64/elf64getsec.o: elf64/../libmach.h
+elf64/elf64getsec.o: elf64/elf64.h
elf64/elf64new.o: $(INCDIR)/scc/scc/mach.h
elf64/elf64new.o: elf64/../libmach.h
elf64/elf64new.o: elf64/elf64.h
--- a/src/libmach/elf64/elf64.c
+++ b/src/libmach/elf64/elf64.c
@@ -15,8 +15,7 @@
.strip = NULL,
.del = elf64del,
.write = NULL,
- .getsym = NULL,
- .getsec = NULL,
+ .getsec = elf64getsec,
.loadmap = NULL,
};
--- /dev/null
+++ b/src/libmach/elf64/elf64getsec.c
@@ -1,0 +1,59 @@
+#include <stdio.h>
+
+#include <scc/mach.h>
+
+#include "../libmach.h"
+#include "elf64.h"
+
+Section *
+elf64getsec(Obj *obj, int *idx, Section *sec)
+{
+ int stype, n = *idx;
+ unsigned long flags, type;
+ unsigned sflags;
+ Elf64 *elf = obj->data;
+ Elf_Ehdr *hdr = &elf->hdr;
+ Elf_Shdr *shdr;
+
+ if (n >= elf->nsec)
+ return NULL;
+
+ shdr = &elf->shdr[n];
+ flags = shdr->sh_flags;
+ type = shdr->sh_type;
+
+ if (flags & SHF_ALLOC) {
+ if (type == SHT_NOBITS)
+ stype = 'B';
+ else if (flags & SHF_WRITE)
+ stype = 'D';
+ else
+ stype = 'T';
+ } else {
+ stype = 'N';
+ }
+
+ sflags = 0;
+ if (flags & SHF_WRITE)
+ sflags |= SWRITE;
+ if (flags & SHF_EXECINSTR)
+ sflags |= SEXEC;
+ if (flags & SHF_ALLOC)
+ sflags |= SALLOC|SREAD;
+ if (type != SHT_NOBITS)
+ sflags |= SLOAD;
+ if (flags & SHF_MERGE)
+ sflags |= SSHARED; /* TODO: Check SSHARED in coff */
+ if (stype == 'T' || stype == 'D')
+ sflags |= SRELOC; /* TODO: Check SRELOC in coff */
+
+ sec->name = elf64str(obj, SEC_STRTBL, shdr->sh_name);
+ sec->index = n;
+ sec->size = shdr->sh_size;
+ sec->base = shdr->sh_addr;
+ sec->type = stype;
+ sec->flags = sflags;
+ sec->align = shdr->sh_addralign;
+
+ return sec;
+}
--- a/src/libmach/elf64/rules.mk
+++ b/src/libmach/elf64/rules.mk
@@ -3,4 +3,5 @@
elf64/elf64new.o\
elf64/elf64probe.o\
elf64/elf64read.o\
+ elf64/elf64getsec.o\
elf64/elf64del.o\