Skip to content

Commit

Permalink
fix: code in non-executable ELF sections
Browse files Browse the repository at this point in the history
  • Loading branch information
JonathanWilbur committed Jul 30, 2024
1 parent c85efac commit e4d874d
Show file tree
Hide file tree
Showing 4 changed files with 45 additions and 0 deletions.
3 changes: 3 additions & 0 deletions tccasm.c
Original file line number Diff line number Diff line change
Expand Up @@ -893,6 +893,9 @@ static void asm_parse_directive(TCCState *s1, int global)
if (old_nb_section != s1->nb_sections)
cur_text_section->sh_addralign = 1;
}
/* The section directive supports flags, but they are unsupported.
For now, just assume any section contains code. */
cur_text_section->sh_flags |= SHF_EXECINSTR;
break;
case TOK_ASMDIR_previous:
{
Expand Down
1 change: 1 addition & 0 deletions tccgen.c
Original file line number Diff line number Diff line change
Expand Up @@ -8303,6 +8303,7 @@ static void gen_function(Sym *sym)
cur_scope = root_scope = &f;
nocode_wanted = 0;

cur_text_section->sh_flags |= SHF_EXECINSTR;
ind = cur_text_section->data_offset;
if (sym->a.aligned) {
size_t newoff = section_add(cur_text_section, 0,
Expand Down
28 changes: 28 additions & 0 deletions tests/exec_section_in_asm.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/* Previously in TinyCC, ELF sections defined in assembly would always have the
execute bit not set, so you would get segmentation faults when code in these
sections was exectuted. This file is a minimal example of a file that will put
the resulting code in a non-executable section (and invoke it) prior to the fix.
*/
#include <stdio.h>

void *memset(void *dst, int c, int len);

__asm__ (
".section .text.nolibc_memset\n"
".weak memset\n"
"memset:\n"
"xchgl %eax, %esi\n\t"
"movq %rdx, %rcx\n\t"
"pushq %rdi\n\t"
"rep stosb\n\t"
"popq %rax\n\t"
"retq\n"
);

int main () {
char buf[10];
memset(&buf[0], 'A', 9);
buf[9] = 0;
puts(buf);
return 0;
}
13 changes: 13 additions & 0 deletions tests/exec_section_in_c.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
/* Previously in TinyCC, ELF sections defined in attributes would always have
the execute bit not set, so you would get segmentation faults when code in these
sections was exectuted. This file is a minimal example of a file that will put
the resulting code in a non-executable section (and invoke it) prior to the fix.
*/
__attribute__((section(".text.wumbo")))
int wumbo (int arg) {
return arg * 2;
}

int main () {
return wumbo(2);
}

0 comments on commit e4d874d

Please sign in to comment.