0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016 #define pr_fmt(fmt) "kexec_elf: " fmt
0017
0018 #include <linux/elf.h>
0019 #include <linux/kexec.h>
0020 #include <linux/module.h>
0021 #include <linux/slab.h>
0022 #include <linux/types.h>
0023
0024 static inline bool elf_is_elf_file(const struct elfhdr *ehdr)
0025 {
0026 return memcmp(ehdr->e_ident, ELFMAG, SELFMAG) == 0;
0027 }
0028
0029 static uint64_t elf64_to_cpu(const struct elfhdr *ehdr, uint64_t value)
0030 {
0031 if (ehdr->e_ident[EI_DATA] == ELFDATA2LSB)
0032 value = le64_to_cpu(value);
0033 else if (ehdr->e_ident[EI_DATA] == ELFDATA2MSB)
0034 value = be64_to_cpu(value);
0035
0036 return value;
0037 }
0038
0039 static uint32_t elf32_to_cpu(const struct elfhdr *ehdr, uint32_t value)
0040 {
0041 if (ehdr->e_ident[EI_DATA] == ELFDATA2LSB)
0042 value = le32_to_cpu(value);
0043 else if (ehdr->e_ident[EI_DATA] == ELFDATA2MSB)
0044 value = be32_to_cpu(value);
0045
0046 return value;
0047 }
0048
0049 static uint16_t elf16_to_cpu(const struct elfhdr *ehdr, uint16_t value)
0050 {
0051 if (ehdr->e_ident[EI_DATA] == ELFDATA2LSB)
0052 value = le16_to_cpu(value);
0053 else if (ehdr->e_ident[EI_DATA] == ELFDATA2MSB)
0054 value = be16_to_cpu(value);
0055
0056 return value;
0057 }
0058
0059
0060
0061
0062
0063 static bool elf_is_ehdr_sane(const struct elfhdr *ehdr, size_t buf_len)
0064 {
0065 if (ehdr->e_phnum > 0 && ehdr->e_phentsize != sizeof(struct elf_phdr)) {
0066 pr_debug("Bad program header size.\n");
0067 return false;
0068 } else if (ehdr->e_shnum > 0 &&
0069 ehdr->e_shentsize != sizeof(struct elf_shdr)) {
0070 pr_debug("Bad section header size.\n");
0071 return false;
0072 } else if (ehdr->e_ident[EI_VERSION] != EV_CURRENT ||
0073 ehdr->e_version != EV_CURRENT) {
0074 pr_debug("Unknown ELF version.\n");
0075 return false;
0076 }
0077
0078 if (ehdr->e_phoff > 0 && ehdr->e_phnum > 0) {
0079 size_t phdr_size;
0080
0081
0082
0083
0084
0085 phdr_size = sizeof(struct elf_phdr) * ehdr->e_phnum;
0086
0087
0088 if (ehdr->e_phoff + phdr_size < ehdr->e_phoff) {
0089 pr_debug("Program headers at invalid location.\n");
0090 return false;
0091 } else if (ehdr->e_phoff + phdr_size > buf_len) {
0092 pr_debug("Program headers truncated.\n");
0093 return false;
0094 }
0095 }
0096
0097 if (ehdr->e_shoff > 0 && ehdr->e_shnum > 0) {
0098 size_t shdr_size;
0099
0100
0101
0102
0103
0104 shdr_size = sizeof(struct elf_shdr) * ehdr->e_shnum;
0105
0106
0107 if (ehdr->e_shoff + shdr_size < ehdr->e_shoff) {
0108 pr_debug("Section headers at invalid location.\n");
0109 return false;
0110 } else if (ehdr->e_shoff + shdr_size > buf_len) {
0111 pr_debug("Section headers truncated.\n");
0112 return false;
0113 }
0114 }
0115
0116 return true;
0117 }
0118
0119 static int elf_read_ehdr(const char *buf, size_t len, struct elfhdr *ehdr)
0120 {
0121 struct elfhdr *buf_ehdr;
0122
0123 if (len < sizeof(*buf_ehdr)) {
0124 pr_debug("Buffer is too small to hold ELF header.\n");
0125 return -ENOEXEC;
0126 }
0127
0128 memset(ehdr, 0, sizeof(*ehdr));
0129 memcpy(ehdr->e_ident, buf, sizeof(ehdr->e_ident));
0130 if (!elf_is_elf_file(ehdr)) {
0131 pr_debug("No ELF header magic.\n");
0132 return -ENOEXEC;
0133 }
0134
0135 if (ehdr->e_ident[EI_CLASS] != ELF_CLASS) {
0136 pr_debug("Not a supported ELF class.\n");
0137 return -ENOEXEC;
0138 } else if (ehdr->e_ident[EI_DATA] != ELFDATA2LSB &&
0139 ehdr->e_ident[EI_DATA] != ELFDATA2MSB) {
0140 pr_debug("Not a supported ELF data format.\n");
0141 return -ENOEXEC;
0142 }
0143
0144 buf_ehdr = (struct elfhdr *) buf;
0145 if (elf16_to_cpu(ehdr, buf_ehdr->e_ehsize) != sizeof(*buf_ehdr)) {
0146 pr_debug("Bad ELF header size.\n");
0147 return -ENOEXEC;
0148 }
0149
0150 ehdr->e_type = elf16_to_cpu(ehdr, buf_ehdr->e_type);
0151 ehdr->e_machine = elf16_to_cpu(ehdr, buf_ehdr->e_machine);
0152 ehdr->e_version = elf32_to_cpu(ehdr, buf_ehdr->e_version);
0153 ehdr->e_flags = elf32_to_cpu(ehdr, buf_ehdr->e_flags);
0154 ehdr->e_phentsize = elf16_to_cpu(ehdr, buf_ehdr->e_phentsize);
0155 ehdr->e_phnum = elf16_to_cpu(ehdr, buf_ehdr->e_phnum);
0156 ehdr->e_shentsize = elf16_to_cpu(ehdr, buf_ehdr->e_shentsize);
0157 ehdr->e_shnum = elf16_to_cpu(ehdr, buf_ehdr->e_shnum);
0158 ehdr->e_shstrndx = elf16_to_cpu(ehdr, buf_ehdr->e_shstrndx);
0159
0160 switch (ehdr->e_ident[EI_CLASS]) {
0161 case ELFCLASS64:
0162 ehdr->e_entry = elf64_to_cpu(ehdr, buf_ehdr->e_entry);
0163 ehdr->e_phoff = elf64_to_cpu(ehdr, buf_ehdr->e_phoff);
0164 ehdr->e_shoff = elf64_to_cpu(ehdr, buf_ehdr->e_shoff);
0165 break;
0166
0167 case ELFCLASS32:
0168 ehdr->e_entry = elf32_to_cpu(ehdr, buf_ehdr->e_entry);
0169 ehdr->e_phoff = elf32_to_cpu(ehdr, buf_ehdr->e_phoff);
0170 ehdr->e_shoff = elf32_to_cpu(ehdr, buf_ehdr->e_shoff);
0171 break;
0172
0173 default:
0174 pr_debug("Unknown ELF class.\n");
0175 return -EINVAL;
0176 }
0177
0178 return elf_is_ehdr_sane(ehdr, len) ? 0 : -ENOEXEC;
0179 }
0180
0181
0182
0183
0184
0185 static bool elf_is_phdr_sane(const struct elf_phdr *phdr, size_t buf_len)
0186 {
0187
0188 if (phdr->p_offset + phdr->p_filesz < phdr->p_offset) {
0189 pr_debug("ELF segment location wraps around.\n");
0190 return false;
0191 } else if (phdr->p_offset + phdr->p_filesz > buf_len) {
0192 pr_debug("ELF segment not in file.\n");
0193 return false;
0194 } else if (phdr->p_paddr + phdr->p_memsz < phdr->p_paddr) {
0195 pr_debug("ELF segment address wraps around.\n");
0196 return false;
0197 }
0198
0199 return true;
0200 }
0201
0202 static int elf_read_phdr(const char *buf, size_t len,
0203 struct kexec_elf_info *elf_info,
0204 int idx)
0205 {
0206
0207 struct elf_phdr *phdr = (struct elf_phdr *) &elf_info->proghdrs[idx];
0208 const struct elfhdr *ehdr = elf_info->ehdr;
0209 const char *pbuf;
0210 struct elf_phdr *buf_phdr;
0211
0212 pbuf = buf + elf_info->ehdr->e_phoff + (idx * sizeof(*buf_phdr));
0213 buf_phdr = (struct elf_phdr *) pbuf;
0214
0215 phdr->p_type = elf32_to_cpu(elf_info->ehdr, buf_phdr->p_type);
0216 phdr->p_flags = elf32_to_cpu(elf_info->ehdr, buf_phdr->p_flags);
0217
0218 switch (ehdr->e_ident[EI_CLASS]) {
0219 case ELFCLASS64:
0220 phdr->p_offset = elf64_to_cpu(ehdr, buf_phdr->p_offset);
0221 phdr->p_paddr = elf64_to_cpu(ehdr, buf_phdr->p_paddr);
0222 phdr->p_vaddr = elf64_to_cpu(ehdr, buf_phdr->p_vaddr);
0223 phdr->p_filesz = elf64_to_cpu(ehdr, buf_phdr->p_filesz);
0224 phdr->p_memsz = elf64_to_cpu(ehdr, buf_phdr->p_memsz);
0225 phdr->p_align = elf64_to_cpu(ehdr, buf_phdr->p_align);
0226 break;
0227
0228 case ELFCLASS32:
0229 phdr->p_offset = elf32_to_cpu(ehdr, buf_phdr->p_offset);
0230 phdr->p_paddr = elf32_to_cpu(ehdr, buf_phdr->p_paddr);
0231 phdr->p_vaddr = elf32_to_cpu(ehdr, buf_phdr->p_vaddr);
0232 phdr->p_filesz = elf32_to_cpu(ehdr, buf_phdr->p_filesz);
0233 phdr->p_memsz = elf32_to_cpu(ehdr, buf_phdr->p_memsz);
0234 phdr->p_align = elf32_to_cpu(ehdr, buf_phdr->p_align);
0235 break;
0236
0237 default:
0238 pr_debug("Unknown ELF class.\n");
0239 return -EINVAL;
0240 }
0241
0242 return elf_is_phdr_sane(phdr, len) ? 0 : -ENOEXEC;
0243 }
0244
0245
0246
0247
0248
0249
0250
0251 static int elf_read_phdrs(const char *buf, size_t len,
0252 struct kexec_elf_info *elf_info)
0253 {
0254 size_t phdr_size, i;
0255 const struct elfhdr *ehdr = elf_info->ehdr;
0256
0257
0258
0259
0260
0261 phdr_size = sizeof(struct elf_phdr) * ehdr->e_phnum;
0262
0263 elf_info->proghdrs = kzalloc(phdr_size, GFP_KERNEL);
0264 if (!elf_info->proghdrs)
0265 return -ENOMEM;
0266
0267 for (i = 0; i < ehdr->e_phnum; i++) {
0268 int ret;
0269
0270 ret = elf_read_phdr(buf, len, elf_info, i);
0271 if (ret) {
0272 kfree(elf_info->proghdrs);
0273 elf_info->proghdrs = NULL;
0274 return ret;
0275 }
0276 }
0277
0278 return 0;
0279 }
0280
0281
0282
0283
0284
0285
0286
0287
0288
0289
0290
0291
0292
0293
0294
0295
0296 static int elf_read_from_buffer(const char *buf, size_t len,
0297 struct elfhdr *ehdr,
0298 struct kexec_elf_info *elf_info)
0299 {
0300 int ret;
0301
0302 ret = elf_read_ehdr(buf, len, ehdr);
0303 if (ret)
0304 return ret;
0305
0306 elf_info->buffer = buf;
0307 elf_info->ehdr = ehdr;
0308 if (ehdr->e_phoff > 0 && ehdr->e_phnum > 0) {
0309 ret = elf_read_phdrs(buf, len, elf_info);
0310 if (ret)
0311 return ret;
0312 }
0313 return 0;
0314 }
0315
0316
0317
0318
0319 void kexec_free_elf_info(struct kexec_elf_info *elf_info)
0320 {
0321 kfree(elf_info->proghdrs);
0322 memset(elf_info, 0, sizeof(*elf_info));
0323 }
0324
0325
0326
0327 int kexec_build_elf_info(const char *buf, size_t len, struct elfhdr *ehdr,
0328 struct kexec_elf_info *elf_info)
0329 {
0330 int i;
0331 int ret;
0332
0333 ret = elf_read_from_buffer(buf, len, ehdr, elf_info);
0334 if (ret)
0335 return ret;
0336
0337
0338 if (ehdr->e_type != ET_EXEC && ehdr->e_type != ET_DYN) {
0339 pr_err("Not an ELF executable.\n");
0340 goto error;
0341 } else if (!elf_info->proghdrs) {
0342 pr_err("No ELF program header.\n");
0343 goto error;
0344 }
0345
0346 for (i = 0; i < ehdr->e_phnum; i++) {
0347
0348
0349
0350
0351
0352 if (elf_info->proghdrs[i].p_type == PT_INTERP) {
0353 pr_err("Requires an ELF interpreter.\n");
0354 goto error;
0355 }
0356 }
0357
0358 return 0;
0359 error:
0360 kexec_free_elf_info(elf_info);
0361 return -ENOEXEC;
0362 }
0363
0364
0365 int kexec_elf_probe(const char *buf, unsigned long len)
0366 {
0367 struct elfhdr ehdr;
0368 struct kexec_elf_info elf_info;
0369 int ret;
0370
0371 ret = kexec_build_elf_info(buf, len, &ehdr, &elf_info);
0372 if (ret)
0373 return ret;
0374
0375 kexec_free_elf_info(&elf_info);
0376
0377 return elf_check_arch(&ehdr) ? 0 : -ENOEXEC;
0378 }
0379
0380
0381
0382
0383
0384
0385
0386
0387
0388 int kexec_elf_load(struct kimage *image, struct elfhdr *ehdr,
0389 struct kexec_elf_info *elf_info,
0390 struct kexec_buf *kbuf,
0391 unsigned long *lowest_load_addr)
0392 {
0393 unsigned long lowest_addr = UINT_MAX;
0394 int ret;
0395 size_t i;
0396
0397
0398 for (i = 0; i < ehdr->e_phnum; i++) {
0399 unsigned long load_addr;
0400 size_t size;
0401 const struct elf_phdr *phdr;
0402
0403 phdr = &elf_info->proghdrs[i];
0404 if (phdr->p_type != PT_LOAD)
0405 continue;
0406
0407 size = phdr->p_filesz;
0408 if (size > phdr->p_memsz)
0409 size = phdr->p_memsz;
0410
0411 kbuf->buffer = (void *) elf_info->buffer + phdr->p_offset;
0412 kbuf->bufsz = size;
0413 kbuf->memsz = phdr->p_memsz;
0414 kbuf->buf_align = phdr->p_align;
0415 kbuf->buf_min = phdr->p_paddr;
0416 kbuf->mem = KEXEC_BUF_MEM_UNKNOWN;
0417 ret = kexec_add_buffer(kbuf);
0418 if (ret)
0419 goto out;
0420 load_addr = kbuf->mem;
0421
0422 if (load_addr < lowest_addr)
0423 lowest_addr = load_addr;
0424 }
0425
0426 *lowest_load_addr = lowest_addr;
0427 ret = 0;
0428 out:
0429 return ret;
0430 }