Skip to content

Commit d8e7cb3

Browse files
Alexey Dobriyantorvalds
authored andcommitted
fs/binfmt_elf.c: extract PROT_* calculations
There are two places where mapping protections are calculated: one for executable, another one for interpreter -- take them out. ELF read and execute permissions are interchanged with Linux PROT_READ and PROT_EXEC, microoptimizations are welcome! Link: http://lkml.kernel.org/r/20190417213413.GB26474@avx2 Signed-off-by: Alexey Dobriyan <[email protected]> Reviewed-by: Andrew Morton <[email protected]> Signed-off-by: Andrew Morton <[email protected]> Signed-off-by: Linus Torvalds <[email protected]>
1 parent 8526431 commit d8e7cb3

File tree

1 file changed

+16
-14
lines changed

1 file changed

+16
-14
lines changed

fs/binfmt_elf.c

Lines changed: 16 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -524,6 +524,19 @@ static inline int arch_check_elf(struct elfhdr *ehdr, bool has_interp,
524524

525525
#endif /* !CONFIG_ARCH_BINFMT_ELF_STATE */
526526

527+
static inline int make_prot(u32 p_flags)
528+
{
529+
int prot = 0;
530+
531+
if (p_flags & PF_R)
532+
prot |= PROT_READ;
533+
if (p_flags & PF_W)
534+
prot |= PROT_WRITE;
535+
if (p_flags & PF_X)
536+
prot |= PROT_EXEC;
537+
return prot;
538+
}
539+
527540
/* This is much more generalized than the library routine read function,
528541
so we keep this separate. Technically the library read function
529542
is only provided so that we can read a.out libraries that have
@@ -563,16 +576,10 @@ static unsigned long load_elf_interp(struct elfhdr *interp_elf_ex,
563576
for (i = 0; i < interp_elf_ex->e_phnum; i++, eppnt++) {
564577
if (eppnt->p_type == PT_LOAD) {
565578
int elf_type = MAP_PRIVATE | MAP_DENYWRITE;
566-
int elf_prot = 0;
579+
int elf_prot = make_prot(eppnt->p_flags);
567580
unsigned long vaddr = 0;
568581
unsigned long k, map_addr;
569582

570-
if (eppnt->p_flags & PF_R)
571-
elf_prot = PROT_READ;
572-
if (eppnt->p_flags & PF_W)
573-
elf_prot |= PROT_WRITE;
574-
if (eppnt->p_flags & PF_X)
575-
elf_prot |= PROT_EXEC;
576583
vaddr = eppnt->p_vaddr;
577584
if (interp_elf_ex->e_type == ET_EXEC || load_addr_set)
578585
elf_type |= MAP_FIXED_NOREPLACE;
@@ -891,7 +898,7 @@ static int load_elf_binary(struct linux_binprm *bprm)
891898
the correct location in memory. */
892899
for(i = 0, elf_ppnt = elf_phdata;
893900
i < loc->elf_ex.e_phnum; i++, elf_ppnt++) {
894-
int elf_prot = 0, elf_flags, elf_fixed = MAP_FIXED_NOREPLACE;
901+
int elf_prot, elf_flags, elf_fixed = MAP_FIXED_NOREPLACE;
895902
unsigned long k, vaddr;
896903
unsigned long total_size = 0;
897904

@@ -932,12 +939,7 @@ static int load_elf_binary(struct linux_binprm *bprm)
932939
elf_fixed = MAP_FIXED;
933940
}
934941

935-
if (elf_ppnt->p_flags & PF_R)
936-
elf_prot |= PROT_READ;
937-
if (elf_ppnt->p_flags & PF_W)
938-
elf_prot |= PROT_WRITE;
939-
if (elf_ppnt->p_flags & PF_X)
940-
elf_prot |= PROT_EXEC;
942+
elf_prot = make_prot(elf_ppnt->p_flags);
941943

942944
elf_flags = MAP_PRIVATE | MAP_DENYWRITE | MAP_EXECUTABLE;
943945

0 commit comments

Comments
 (0)