Skip to content

Commit 2d4cf7b

Browse files
committed
binfmt_elf: Calculate total_size earlier
In preparation to support PT_LOAD with large p_align values on non-PT_INTERP ET_DYN executables (i.e. "static pie"), we'll need to use the total_size details earlier. Move this separately now to make the next patch more readable. As total_size and load_bias are currently calculated separately, this has no behavioral impact. Link: https://lore.kernel.org/r/[email protected] Signed-off-by: Kees Cook <[email protected]>
1 parent b57a290 commit 2d4cf7b

File tree

1 file changed

+27
-25
lines changed

1 file changed

+27
-25
lines changed

fs/binfmt_elf.c

Lines changed: 27 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1061,7 +1061,34 @@ static int load_elf_binary(struct linux_binprm *bprm)
10611061
* Header for ET_DYN binaries to calculate the
10621062
* randomization (load_bias) for all the LOAD
10631063
* Program Headers.
1064+
*/
1065+
1066+
/*
1067+
* Calculate the entire size of the ELF mapping
1068+
* (total_size), used for the initial mapping,
1069+
* due to load_addr_set which is set to true later
1070+
* once the initial mapping is performed.
1071+
*
1072+
* Note that this is only sensible when the LOAD
1073+
* segments are contiguous (or overlapping). If
1074+
* used for LOADs that are far apart, this would
1075+
* cause the holes between LOADs to be mapped,
1076+
* running the risk of having the mapping fail,
1077+
* as it would be larger than the ELF file itself.
10641078
*
1079+
* As a result, only ET_DYN does this, since
1080+
* some ET_EXEC (e.g. ia64) may have large virtual
1081+
* memory holes between LOADs.
1082+
*
1083+
*/
1084+
total_size = total_mapping_size(elf_phdata,
1085+
elf_ex->e_phnum);
1086+
if (!total_size) {
1087+
retval = -EINVAL;
1088+
goto out_free_dentry;
1089+
}
1090+
1091+
/*
10651092
* There are effectively two types of ET_DYN
10661093
* binaries: programs (i.e. PIE: ET_DYN with INTERP)
10671094
* and loaders (ET_DYN without INTERP, since they
@@ -1102,31 +1129,6 @@ static int load_elf_binary(struct linux_binprm *bprm)
11021129
* is then page aligned.
11031130
*/
11041131
load_bias = ELF_PAGESTART(load_bias - vaddr);
1105-
1106-
/*
1107-
* Calculate the entire size of the ELF mapping
1108-
* (total_size), used for the initial mapping,
1109-
* due to load_addr_set which is set to true later
1110-
* once the initial mapping is performed.
1111-
*
1112-
* Note that this is only sensible when the LOAD
1113-
* segments are contiguous (or overlapping). If
1114-
* used for LOADs that are far apart, this would
1115-
* cause the holes between LOADs to be mapped,
1116-
* running the risk of having the mapping fail,
1117-
* as it would be larger than the ELF file itself.
1118-
*
1119-
* As a result, only ET_DYN does this, since
1120-
* some ET_EXEC (e.g. ia64) may have large virtual
1121-
* memory holes between LOADs.
1122-
*
1123-
*/
1124-
total_size = total_mapping_size(elf_phdata,
1125-
elf_ex->e_phnum);
1126-
if (!total_size) {
1127-
retval = -EINVAL;
1128-
goto out_free_dentry;
1129-
}
11301132
}
11311133

11321134
error = elf_load(bprm->file, load_bias + vaddr, elf_ppnt,

0 commit comments

Comments
 (0)