int machine_kexec_post_load(struct kimage *kimage)
{ int rc;
pgd_t *trans_pgd; void *reloc_code = page_to_virt(kimage->control_code_page); long reloc_size; struct trans_pgd_info info = {
.trans_alloc_page = kexec_page_alloc,
.trans_alloc_arg = kimage,
};
/* If in place, relocation is not used, only flush next kernel */ if (kimage->head & IND_DONE) {
kexec_segment_flush(kimage);
kexec_image_info(kimage); return0;
}
kimage->arch.el2_vectors = 0; if (is_hyp_nvhe()) {
rc = trans_pgd_copy_el2_vectors(&info,
&kimage->arch.el2_vectors); if (rc) return rc;
}
/* Create a copy of the linear map */
trans_pgd = kexec_page_alloc(kimage); if (!trans_pgd) return -ENOMEM;
rc = trans_pgd_create_copy(&info, &trans_pgd, PAGE_OFFSET, PAGE_END); if (rc) return rc;
kimage->arch.ttbr1 = __pa(trans_pgd);
kimage->arch.zero_page = __pa_symbol(empty_zero_page);
/* Flush the reloc_code in preparation for its execution. */
dcache_clean_inval_poc((unsignedlong)reloc_code,
(unsignedlong)reloc_code + reloc_size);
icache_inval_pou((uintptr_t)reloc_code,
(uintptr_t)reloc_code + reloc_size);
kexec_image_info(kimage);
bool crash_is_nosave(unsignedlong pfn)
{ int i;
phys_addr_t addr;
if (!crashk_res.end) returnfalse;
/* in reserved memory? */
addr = __pfn_to_phys(pfn); if ((addr < crashk_res.start) || (crashk_res.end < addr)) { if (!crashk_low_res.end) returnfalse;
if ((addr < crashk_low_res.start) || (crashk_low_res.end < addr)) returnfalse;
}
if (!kexec_crash_image) returntrue;
/* not part of loaded kernel image? */ for (i = 0; i < kexec_crash_image->nr_segments; i++) if (addr >= kexec_crash_image->segment[i].mem &&
addr < (kexec_crash_image->segment[i].mem +
kexec_crash_image->segment[i].memsz)) returnfalse;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.