diff options
| author | bellard <bellard> | 2005-09-03 18:31:43 +0000 |
|---|---|---|
| committer | bellard <bellard> | 2005-09-03 18:31:43 +0000 |
| commit | b0b8ac13ce0217dfd6049ade6fca5d308e72ba21 (patch) | |
| tree | 1b5686b6ea1ef1db5f6bcf8226aaf78d96599dc0 | |
| parent | 16559cd60c53fd0a728bbc212fa2e560d0fccb12 (diff) | |
| download | tinycc-b0b8ac13ce0217dfd6049ade6fca5d308e72ba21.tar.gz tinycc-b0b8ac13ce0217dfd6049ade6fca5d308e72ba21.tar.bz2 | |
mark executable sections as executable when running in memory
| -rw-r--r-- | tcc.c | 32 |
1 files changed, 31 insertions, 1 deletions
@@ -40,14 +40,20 @@ #include <time.h> #ifdef WIN32 #include <sys/timeb.h> +#include <windows.h> #endif #ifndef WIN32 #include <sys/time.h> #include <sys/ucontext.h> +#include <sys/mman.h> #endif #endif /* !CONFIG_TCCBOOT */ +#ifndef PAGESIZE +#define PAGESIZE 4096 +#endif + #include "elf.h" #include "stab.h" @@ -199,7 +205,7 @@ typedef struct Section { int sh_entsize; /* elf entry size */ unsigned long sh_size; /* section size (only used during output) */ unsigned long sh_addr; /* address at which the section is relocated */ - unsigned long sh_offset; /* address at which the section is relocated */ + unsigned long sh_offset; /* file offset */ int nb_hashed_syms; /* used to resize the hash table */ struct Section *link; /* link to another section */ struct Section *reloc; /* corresponding section for relocation, if any */ @@ -9615,6 +9621,30 @@ int tcc_relocate(TCCState *s1) if (s->reloc) relocate_section(s1, s); } + + /* mark executable sections as executable in memory */ + for(i = 1; i < s1->nb_sections; i++) { + s = s1->sections[i]; + if ((s->sh_flags & (SHF_ALLOC | SHF_EXECINSTR)) == + (SHF_ALLOC | SHF_EXECINSTR)) { +#ifdef WIN32 + { + DWORD old_protect; + VirtualProtect(s->data, s->data_offset, + PAGE_EXECUTE_READWRITE, &old_protect); + } +#else + { + unsigned long start, end; + start = (unsigned long)(s->data) & ~(PAGESIZE - 1); + end = (unsigned long)(s->data + s->data_offset); + end = (end + PAGESIZE - 1) & ~(PAGESIZE - 1); + mprotect((void *)start, end - start, + PROT_READ | PROT_WRITE | PROT_EXEC); + } +#endif + } + } return 0; } |
