You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
154 lines
5.5 KiB
154 lines
5.5 KiB
diff -up bash-4.0/execute_cmd.c.nobits bash-4.0/execute_cmd.c |
|
--- bash-4.0/execute_cmd.c.nobits 2009-08-11 11:53:38.000000000 +0200 |
|
+++ bash-4.0/execute_cmd.c 2009-08-14 16:18:18.000000000 +0200 |
|
@@ -4747,6 +4747,7 @@ shell_execve (command, args, env) |
|
&& memcmp (sample, ELFMAG, SELFMAG) == 0) |
|
{ |
|
off_t offset = -1; |
|
+ int dynamic_nobits = 0; |
|
|
|
/* It is an ELF file. Now determine whether it is dynamically |
|
linked and if yes, get the offset of the interpreter |
|
@@ -4756,13 +4757,61 @@ shell_execve (command, args, env) |
|
{ |
|
Elf32_Ehdr ehdr; |
|
Elf32_Phdr *phdr; |
|
- int nphdr; |
|
+ Elf32_Shdr *shdr; |
|
+ int nphdr, nshdr; |
|
|
|
/* We have to copy the data since the sample buffer |
|
might not be aligned correctly to be accessed as |
|
an Elf32_Ehdr struct. */ |
|
memcpy (&ehdr, sample, sizeof (Elf32_Ehdr)); |
|
|
|
+ nshdr = ehdr.e_shnum; |
|
+ shdr = (Elf32_Shdr *) malloc (nshdr * ehdr.e_shentsize); |
|
+ |
|
+ if (shdr != NULL) |
|
+ { |
|
+#ifdef HAVE_PREAD |
|
+ sample_len = pread (fd, shdr, nshdr * ehdr.e_shentsize, |
|
+ ehdr.e_shoff); |
|
+#else |
|
+ if (lseek (fd, ehdr.e_shoff, SEEK_SET) != -1) |
|
+ sample_len = read (fd, shdr, |
|
+ nshdr * ehdr.e_shentsize); |
|
+ else |
|
+ sample_len = -1; |
|
+#endif |
|
+ if (sample_len == nshdr * ehdr.e_shentsize) |
|
+ { |
|
+ char *strings = (char *) malloc (shdr[ehdr.e_shstrndx].sh_size); |
|
+ if (strings != NULL) |
|
+ { |
|
+#ifdef HAVE_PREAD |
|
+ sample_len = pread (fd, strings, |
|
+ shdr[ehdr.e_shstrndx].sh_size, |
|
+ shdr[ehdr.e_shstrndx].sh_offset); |
|
+#else |
|
+ if (lseek (fd, shdr[ehdr.e_shstrndx].sh_offset, |
|
+ SEEK_SET) != -1) |
|
+ sample_len = read (fd, strings, |
|
+ shdr[ehdr.e_shstrndx].sh_size); |
|
+ else |
|
+ sample_len = -1; |
|
+#endif |
|
+ if (sample_len == shdr[ehdr.e_shstrndx].sh_size) |
|
+ while (nshdr-- > 0) |
|
+ if (strcmp (strings + shdr[nshdr].sh_name, |
|
+ ".interp") == 0 && |
|
+ shdr[nshdr].sh_type == SHT_NOBITS) |
|
+ { |
|
+ dynamic_nobits++; |
|
+ break; |
|
+ } |
|
+ free (strings); |
|
+ } |
|
+ } |
|
+ free (shdr); |
|
+ } |
|
+ |
|
nphdr = ehdr.e_phnum; |
|
phdr = (Elf32_Phdr *) malloc (nphdr * ehdr.e_phentsize); |
|
if (phdr != NULL) |
|
@@ -4792,13 +4841,60 @@ shell_execve (command, args, env) |
|
{ |
|
Elf64_Ehdr ehdr; |
|
Elf64_Phdr *phdr; |
|
- int nphdr; |
|
+ Elf64_Shdr *shdr; |
|
+ int nphdr, nshdr; |
|
|
|
/* We have to copy the data since the sample buffer |
|
might not be aligned correctly to be accessed as |
|
an Elf64_Ehdr struct. */ |
|
memcpy (&ehdr, sample, sizeof (Elf64_Ehdr)); |
|
|
|
+ nshdr = ehdr.e_shnum; |
|
+ shdr = (Elf64_Shdr *) malloc (nshdr * ehdr.e_shentsize); |
|
+ if (shdr != NULL) |
|
+ { |
|
+#ifdef HAVE_PREAD |
|
+ sample_len = pread (fd, shdr, nshdr * ehdr.e_shentsize, |
|
+ ehdr.e_shoff); |
|
+#else |
|
+ if (lseek (fd, ehdr.e_shoff, SEEK_SET) != -1) |
|
+ sample_len = read (fd, shdr, |
|
+ nshdr * ehdr.e_shentsize); |
|
+ else |
|
+ sample_len = -1; |
|
+#endif |
|
+ if (sample_len == nshdr * ehdr.e_shentsize) |
|
+ { |
|
+ char *strings = (char *) malloc (shdr[ehdr.e_shstrndx].sh_size); |
|
+ if (strings != NULL) |
|
+ { |
|
+#ifdef HAVE_PREAD |
|
+ sample_len = pread (fd, strings, |
|
+ shdr[ehdr.e_shstrndx].sh_size, |
|
+ shdr[ehdr.e_shstrndx].sh_offset); |
|
+#else |
|
+ if (lseek (fd, shdr[ehdr.e_shstrndx].sh_offset, |
|
+ SEEK_SET) != -1) |
|
+ sample_len = read (fd, strings, |
|
+ shdr[ehdr.e_shstrndx].sh_size); |
|
+ else |
|
+ sample_len = -1; |
|
+#endif |
|
+ if (sample_len == shdr[ehdr.e_shstrndx].sh_size) |
|
+ while (nshdr-- > 0) |
|
+ if (strcmp (strings + shdr[nshdr].sh_name, |
|
+ ".interp") == 0 && |
|
+ shdr[nshdr].sh_type == SHT_NOBITS) |
|
+ { |
|
+ dynamic_nobits++; |
|
+ break; |
|
+ } |
|
+ free (strings); |
|
+ } |
|
+ } |
|
+ free (shdr); |
|
+ } |
|
+ |
|
nphdr = ehdr.e_phnum; |
|
phdr = (Elf64_Phdr *) malloc (nphdr * ehdr.e_phentsize); |
|
if (phdr != NULL) |
|
@@ -4858,8 +4954,15 @@ shell_execve (command, args, env) |
|
{ |
|
close (fd); |
|
errno = i; |
|
- sys_error ("%s: %s: bad ELF interpreter", command, |
|
- interp); |
|
+ if (dynamic_nobits > 0) |
|
+ { |
|
+ sys_error ("%s: bad ELF interpreter", command); |
|
+ } |
|
+ else |
|
+ { |
|
+ sys_error ("%s: %s: bad ELF interpreter", command, |
|
+ interp); |
|
+ } |
|
free (interp); |
|
return (EX_NOEXEC); |
|
}
|
|
|