grub_err_t
grub_cmd_initrd (grub_command_t cmd __attribute__ ((unused)),
int argc, char *argv[])
{
struct linux_kernel_header *lh;
/* 打开initrd并计算其需要的页面 */
file = grub_file_open (argv[0]);
size = grub_file_size (file);
initrd_pages = (page_align (size) >> 12);
/* 计算initrd加载地址 */
lh = (struct linux_kernel_header *) real_mode_mem;
/* Get the highest address available for the initrd. */
if (grub_le_to_cpu16 (lh->version) >= 0x0203)
{
addr_max = grub_cpu_to_le32 (lh->initrd_addr_max);
}
addr_max -= 0x10000;
/* Usually, the compression ratio is about 50%. */
addr_min = (grub_addr_t) prot_mode_target + ((prot_mode_pages * 3) << 12)
+ page_align (size);
/* Put the initrd as high as possible, 4KiB aligned. */
addr = (addr_max - size) & ~0xFFF;
/* 分配空间 */
grub_relocator_chunk_t ch;
err = grub_relocator_alloc_chunk_align (relocator, &ch,
addr_min, addr, size, 0x1000,
GRUB_RELOCATOR_PREFERENCE_HIGH);
initrd_mem = get_virtual_current_address (ch);
initrd_mem_target = get_physical_target_address (ch);
/* 读取initrd到缓存 */
grub_file_read (file, initrd_mem, size) != size
lh->ramdisk_image = initrd_mem_target;
lh->ramdisk_size = size;
lh->root_dev = 0x0100;
}