[PATCH v2] x86, efi: Break up large initrd reads

From: Maarten Lankhorst
Date: Fri Dec 16 2011 - 07:31:14 EST


[PATCH 11/11] x86, efi: Break up large initrd reads

The efi boot stub tries to read the entire initrd in 1 go,
however some efi implementations hang if too much if asked
to read too much data at the same time. After some
experimentation I found out that my asrock p67 board will
hang if asked to read chunks of 4MiB, so use a safe value.

elilo reads in chunks of 16KiB, but since that requires
many read calls I use a value of 1 MiB. hpa suggested
adding individual blacklists for when systems are found
where this value causes a crash.

Signed-off-by: Maarten Lankhorst <m.b.lankhorst@xxxxxxxxx>
---

v2: Bump read size to 1 MiB, and use a #define for chunk size

arch/x86/boot/compressed/eboot.c | 21 +++++++++++++++------
1 files changed, 15 insertions(+), 6 deletions(-)

diff --git a/arch/x86/boot/compressed/eboot.c b/arch/x86/boot/compressed/eboot.c
index 8627a56..df4f552 100644
--- a/arch/x86/boot/compressed/eboot.c
+++ b/arch/x86/boot/compressed/eboot.c
@@ -23,6 +23,7 @@
#define DESC_TYPE_CODE_DATA (1 << 0)

#define EFI_PAGE_SIZE (1UL << EFI_PAGE_SHIFT)
+#define EFI_READ_CHUNK_SIZE (1024 * 1024)

#define PIXEL_RGB_RESERVED_8BIT_PER_COLOR 0
#define PIXEL_BGR_RESERVED_8BIT_PER_COLOR 1
@@ -695,14 +696,22 @@ grow:
u64 size;

size = initrds[j].size;
- status = efi_call_phys3(fh->read, initrds[j].handle,
- &size, addr);
- if (status != EFI_SUCCESS)
- goto free_initrd_total;
+ while (size) {
+ u64 chunksize;
+ if (size > EFI_READ_CHUNK_SIZE)
+ chunksize = EFI_READ_CHUNK_SIZE;
+ else
+ chunksize = size;
+ status = efi_call_phys3(fh->read,
+ initrds[j].handle,
+ &chunksize, addr);
+ if (status != EFI_SUCCESS)
+ goto free_initrd_total;
+ addr += chunksize;
+ size -= chunksize;
+ }

efi_call_phys1(fh->close, initrds[j].handle);
-
- addr += size;
}

}
--
1.7.7.4


--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/