+
+/*
+ * checkfix_initrd()
+ * Check and possibly fix allocation of initrd memory.
+ */
+VOID *
+sysdeps_checkfix_initrd(VOID *start_addr, memdesc_t *imem)
+{
+ UINTN pgcnt = EFI_SIZE_TO_PAGES(imem->size);
+ UINT64 initrd_addr_max = (UINT64)param_start->s.initrd_addr_max;
+ UINT64 ki_max = initrd_addr_max - imem->size + 1;
+ VOID *ki_max_addr;
+
+ VERB_PRT( 3, Print(L"loadfile: start_addr="PTR_FMT
+ " ki_max_addr="PTR_FMT"\n", start_addr, (VOID *)ki_max));
+ if (ki_max > UINT32_MAX) {
+ ERR_PRT((L"Force kernel specified initrd_addr_max="PTR_FMT
+ " below 4GB\n", (VOID *)initrd_addr_max));
+ ki_max = UINT32_MAX - imem->size + 1;
+ }
+ ki_max_addr = (VOID *)ki_max;
+
+ if ((UINT64)start_addr > ki_max) {
+ VERB_PRT(1, Print(L"initrd start_addr="PTR_FMT" above "
+ "limit="PTR_FMT"\n", start_addr, ki_max_addr));
+ free(start_addr);
+ start_addr = NULL;
+ }
+ /* so either the initial allocation failed or it's been to high! */
+ if (start_addr == NULL) {
+ start_addr = alloc_pages(pgcnt, EfiLoaderData,
+ AllocateMaxAddress, ki_max_addr);
+ }
+ if ((UINT64)start_addr > ki_max) {
+ ERR_PRT((L"Failed to allocate %d pages below %dMB",
+ pgcnt, (param_start->s.initrd_addr_max+1)>>20));
+ free(start_addr);
+ start_addr = NULL;
+ }
+ return start_addr;
+}
+