mk/efi.mk: Add libefi.a dependency
[syslinux.git] / efi / main.c
blob94878f93946fe531aa1e35d4299af17f091b6b53
1 /*
2 * Copyright 2011-2014 Intel Corporation - All Rights Reserved
3 */
5 #include <codepage.h>
6 #include <core.h>
7 #include <fs.h>
8 #include <com32.h>
9 #include <syslinux/memscan.h>
10 #include <syslinux/firmware.h>
11 #include <syslinux/linux.h>
12 #include <sys/ansi.h>
13 #include <setjmp.h>
15 #include "efi.h"
16 #include "fio.h"
17 #include "version.h"
19 __export uint16_t PXERetry;
20 __export char copyright_str[] = "Copyright (C) 2011-" YEAR_STR "\n";
21 uint8_t SerialNotice = 1;
22 __export char syslinux_banner[] = "Syslinux " VERSION_STR " (EFI; " DATE_STR ")\n";
23 char CurrentDirName[CURRENTDIR_MAX];
24 struct com32_sys_args __com32;
26 uint32_t _IdleTimer = 0;
27 char __lowmem_heap[32];
28 uint32_t BIOS_timer_next;
29 uint32_t timer_irq;
30 __export uint8_t KbdMap[256];
31 char aux_seg[256];
33 static jmp_buf load_error_buf;
35 static inline EFI_STATUS
36 efi_close_protocol(EFI_HANDLE handle, EFI_GUID *guid, EFI_HANDLE agent,
37 EFI_HANDLE controller)
39 return uefi_call_wrapper(BS->CloseProtocol, 4, handle,
40 guid, agent, controller);
43 struct efi_binding *efi_create_binding(EFI_GUID *bguid, EFI_GUID *pguid)
45 EFI_SERVICE_BINDING *sbp;
46 struct efi_binding *b;
47 EFI_STATUS status;
48 EFI_HANDLE protocol, child, *handles = NULL;
49 UINTN i, nr_handles = 0;
51 b = malloc(sizeof(*b));
52 if (!b)
53 return NULL;
55 status = LibLocateHandle(ByProtocol, bguid, NULL, &nr_handles, &handles);
56 if (status != EFI_SUCCESS)
57 goto free_binding;
59 for (i = 0; i < nr_handles; i++) {
60 status = uefi_call_wrapper(BS->OpenProtocol, 6, handles[i],
61 bguid, (void **)&sbp,
62 image_handle, handles[i],
63 EFI_OPEN_PROTOCOL_GET_PROTOCOL);
64 if (status == EFI_SUCCESS)
65 break;
67 uefi_call_wrapper(BS->CloseProtocol, 4, handles[i], bguid,
68 image_handle, handles[i]);
71 if (i == nr_handles)
72 goto free_binding;
74 child = NULL;
76 status = uefi_call_wrapper(sbp->CreateChild, 2, sbp, (EFI_HANDLE *)&child);
77 if (status != EFI_SUCCESS)
78 goto close_protocol;
80 status = uefi_call_wrapper(BS->OpenProtocol, 6, child,
81 pguid, (void **)&protocol,
82 image_handle, sbp,
83 EFI_OPEN_PROTOCOL_GET_PROTOCOL);
84 if (status != EFI_SUCCESS)
85 goto destroy_child;
87 b->parent = handles[i];
88 b->binding = sbp;
89 b->child = child;
90 b->this = protocol;
92 return b;
94 destroy_child:
95 uefi_call_wrapper(sbp->DestroyChild, 2, sbp, child);
97 close_protocol:
98 uefi_call_wrapper(BS->CloseProtocol, 4, handles[i], bguid,
99 image_handle, handles[i]);
101 free_binding:
102 free(b);
103 return NULL;
106 void efi_destroy_binding(struct efi_binding *b, EFI_GUID *guid)
108 efi_close_protocol(b->child, guid, image_handle, b->binding);
109 uefi_call_wrapper(b->binding->DestroyChild, 2, b->binding, b->child);
110 efi_close_protocol(b->parent, guid, image_handle, b->parent);
112 free(b);
115 #undef kaboom
116 void kaboom(void)
120 void comboot_cleanup_api(void)
124 void printf_init(void)
128 __export void local_boot(uint16_t ax)
131 * Inform the firmware that we failed to execute correctly, which
132 * will trigger the next entry in the EFI Boot Manager list.
134 longjmp(load_error_buf, 1);
137 void bios_timer_cleanup(void)
141 char trackbuf[4096];
143 void __cdecl core_farcall(uint32_t c, const com32sys_t *a, com32sys_t *b)
147 __export struct firmware *firmware = NULL;
148 void *__syslinux_adv_ptr;
149 size_t __syslinux_adv_size;
150 char core_xfer_buf[65536];
151 struct iso_boot_info {
152 uint32_t pvd; /* LBA of primary volume descriptor */
153 uint32_t file; /* LBA of boot file */
154 uint32_t length; /* Length of boot file */
155 uint32_t csum; /* Checksum of boot file */
156 uint32_t reserved[10]; /* Currently unused */
157 } iso_boot_info;
159 uint8_t DHCPMagic;
160 uint32_t RebootTime;
162 void pxenv(void)
166 uint16_t BIOS_fbm = 1;
167 far_ptr_t InitStack;
168 far_ptr_t PXEEntry;
169 __export unsigned int __bcopyxx_len = 0;
171 void gpxe_unload(void)
175 void do_idle(void)
179 void pxe_int1a(void)
183 uint8_t KeepPXE;
185 struct semaphore;
186 mstime_t sem_down(struct semaphore *sem, mstime_t time)
188 /* EFI is single threaded */
189 return 0;
192 void sem_up(struct semaphore *sem)
194 /* EFI is single threaded */
197 __export volatile uint32_t __ms_timer = 0;
198 volatile uint32_t __jiffies = 0;
200 void efi_write_char(uint8_t ch, uint8_t attribute)
202 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
203 uint16_t c[2];
205 uefi_call_wrapper(out->SetAttribute, 2, out, attribute);
207 /* Lookup primary Unicode encoding in the system codepage */
208 c[0] = codepage.uni[0][ch];
209 c[1] = '\0';
211 uefi_call_wrapper(out->OutputString, 2, out, c);
214 static void efi_showcursor(const struct term_state *st)
216 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
217 bool cursor = st->cursor ? true : false;
219 uefi_call_wrapper(out->EnableCursor, 2, out, cursor);
222 static void efi_set_cursor(int x, int y, bool visible)
224 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
226 uefi_call_wrapper(out->SetCursorPosition, 3, out, x, y);
229 static void efi_scroll_up(uint8_t cols, uint8_t rows, uint8_t attribute)
231 efi_write_char('\n', 0);
232 efi_write_char('\r', 0);
235 static void efi_get_mode(int *cols, int *rows)
237 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
238 UINTN c, r;
240 uefi_call_wrapper(out->QueryMode, 4, out, out->Mode->Mode, &c, &r);
241 *rows = r;
242 *cols = c;
245 static void efi_erase(int x0, int y0, int x1, int y1, uint8_t attribute)
247 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
248 int cols, rows;
250 efi_get_mode(&cols, &rows);
253 * The BIOS version of this function has the ability to erase
254 * parts or all of the screen - the UEFI console doesn't
255 * support this so we just set the cursor position unless
256 * we're clearing the whole screen.
258 if (!x0 && y0 == (cols - 1)) {
259 /* Really clear the screen */
260 uefi_call_wrapper(out->ClearScreen, 1, out);
261 } else {
262 uefi_call_wrapper(out->SetCursorPosition, 3, out, y1, x1);
266 static void efi_text_mode(void)
270 static void efi_get_cursor(uint8_t *x, uint8_t *y)
272 SIMPLE_TEXT_OUTPUT_INTERFACE *out = ST->ConOut;
273 *x = out->Mode->CursorColumn;
274 *y = out->Mode->CursorRow;
277 struct output_ops efi_ops = {
278 .erase = efi_erase,
279 .write_char = efi_write_char,
280 .showcursor = efi_showcursor,
281 .set_cursor = efi_set_cursor,
282 .scroll_up = efi_scroll_up,
283 .get_mode = efi_get_mode,
284 .text_mode = efi_text_mode,
285 .get_cursor = efi_get_cursor,
288 char SubvolName[2];
289 static inline EFI_MEMORY_DESCRIPTOR *
290 get_memory_map(UINTN *nr_entries, UINTN *key, UINTN *desc_sz,
291 uint32_t *desc_ver)
293 return LibMemoryMap(nr_entries, key, desc_sz, desc_ver);
297 int efi_scan_memory(scan_memory_callback_t callback, void *data)
299 UINTN i, nr_entries, key, desc_sz;
300 UINTN buf, bufpos;
301 UINT32 desc_ver;
302 int rv = 0;
304 buf = (UINTN)get_memory_map(&nr_entries, &key, &desc_sz, &desc_ver);
305 if (!buf)
306 return -1;
307 bufpos = buf;
309 for (i = 0; i < nr_entries; bufpos += desc_sz, i++) {
310 EFI_MEMORY_DESCRIPTOR *m;
311 UINT64 region_sz;
312 enum syslinux_memmap_types type;
314 m = (EFI_MEMORY_DESCRIPTOR *)bufpos;
315 region_sz = m->NumberOfPages * EFI_PAGE_SIZE;
317 switch (m->Type) {
318 case EfiConventionalMemory:
319 type = SMT_FREE;
320 break;
321 default:
322 type = SMT_RESERVED;
323 break;
326 rv = callback(data, m->PhysicalStart, region_sz, type);
327 if (rv)
328 break;
331 FreePool((void *)buf);
332 return rv;
335 static struct syslinux_memscan efi_memscan = {
336 .func = efi_scan_memory,
339 extern uint16_t *bios_free_mem;
340 void efi_init(void)
342 /* XXX timer */
343 *bios_free_mem = 0;
344 syslinux_memscan_add(&efi_memscan);
345 mem_init();
348 char efi_getchar(char *hi)
350 SIMPLE_INPUT_INTERFACE *in = ST->ConIn;
351 EFI_INPUT_KEY key;
352 EFI_STATUS status;
354 do {
355 status = uefi_call_wrapper(in->ReadKeyStroke, 2, in, &key);
356 } while (status == EFI_NOT_READY);
358 if (!key.ScanCode)
359 return (char)key.UnicodeChar;
362 * We currently only handle scan codes that fit in 8 bits.
364 *hi = (char)key.ScanCode;
365 return 0;
368 int efi_pollchar(void)
370 SIMPLE_INPUT_INTERFACE *in = ST->ConIn;
371 EFI_STATUS status;
373 status = WaitForSingleEvent(in->WaitForKey, 1);
374 return status != EFI_TIMEOUT;
377 struct input_ops efi_iops = {
378 .getchar = efi_getchar,
379 .pollchar = efi_pollchar,
382 extern void efi_adv_init(void);
383 extern int efi_adv_write(void);
385 struct adv_ops efi_adv_ops = {
386 .init = efi_adv_init,
387 .write = efi_adv_write,
390 struct efi_info {
391 uint32_t load_signature;
392 uint32_t systab;
393 uint32_t desc_size;
394 uint32_t desc_version;
395 uint32_t memmap;
396 uint32_t memmap_size;
397 uint32_t systab_hi;
398 uint32_t memmap_hi;
401 #define E820MAX 128
402 #define E820_RAM 1
403 #define E820_RESERVED 2
404 #define E820_ACPI 3
405 #define E820_NVS 4
406 #define E820_UNUSABLE 5
408 #define BOOT_SIGNATURE 0xaa55
409 #define SYSLINUX_EFILDR 0x30 /* Is this published value? */
410 #define DEFAULT_TIMER_TICK_DURATION 500000 /* 500000 == 500000 * 100 * 10^-9 == 50 msec */
411 #define DEFAULT_MSTIMER_INC 0x32 /* 50 msec */
412 struct e820_entry {
413 uint64_t start;
414 uint64_t len;
415 uint32_t type;
416 } __packed;
418 struct boot_params {
419 struct screen_info screen_info;
420 uint8_t _pad[0x1c0 - sizeof(struct screen_info)];
421 struct efi_info efi;
422 uint8_t _pad2[8];
423 uint8_t e820_entries;
424 uint8_t _pad3[0x2d0 - 0x1e8 - sizeof(uint8_t)];
425 struct e820_entry e820_map[E820MAX];
426 } __packed;
428 /* Allocate boot parameter block aligned to page */
429 #define BOOT_PARAM_BLKSIZE EFI_SIZE_TO_PAGES(sizeof(struct boot_params)) * EFI_PAGE_SIZE
431 /* Routines in support of efi boot loader were obtained from
432 * http://git.kernel.org/?p=boot/efilinux/efilinux.git:
433 * kernel_jump(), handover_jump(),
434 * emalloc()/efree, alloc_pages/free_pages
435 * allocate_pool()/free_pool()
436 * memory_map()
438 extern void kernel_jump(EFI_PHYSICAL_ADDRESS kernel_start,
439 struct boot_params *boot_params);
440 #if __SIZEOF_POINTER__ == 4
441 #define EFI_LOAD_SIG "EL32"
442 #elif __SIZEOF_POINTER__ == 8
443 #define EFI_LOAD_SIG "EL64"
444 #else
445 #error "unsupported architecture"
446 #endif
448 struct dt_desc {
449 uint16_t limit;
450 uint64_t *base;
451 } __packed;
453 struct dt_desc gdt = { 0x800, (uint64_t *)0 };
454 struct dt_desc idt = { 0, 0 };
456 static inline EFI_MEMORY_DESCRIPTOR *
457 get_mem_desc(unsigned long memmap, UINTN desc_sz, int i)
459 return (EFI_MEMORY_DESCRIPTOR *)(memmap + (i * desc_sz));
462 EFI_HANDLE image_handle;
464 static inline UINT64 round_up(UINT64 x, UINT64 y)
466 return (((x - 1) | (y - 1)) + 1);
469 static inline UINT64 round_down(UINT64 x, UINT64 y)
471 return (x & ~(y - 1));
474 static void find_addr(EFI_PHYSICAL_ADDRESS *first,
475 EFI_PHYSICAL_ADDRESS *last,
476 EFI_PHYSICAL_ADDRESS min,
477 EFI_PHYSICAL_ADDRESS max,
478 size_t size, size_t align)
480 EFI_MEMORY_DESCRIPTOR *map;
481 UINT32 desc_ver;
482 UINTN i, nr_entries, key, desc_sz;
484 map = get_memory_map(&nr_entries, &key, &desc_sz, &desc_ver);
485 if (!map)
486 return;
488 for (i = 0; i < nr_entries; i++) {
489 EFI_MEMORY_DESCRIPTOR *m;
490 EFI_PHYSICAL_ADDRESS best;
491 UINT64 start, end;
493 m = get_mem_desc((unsigned long)map, desc_sz, i);
494 if (m->Type != EfiConventionalMemory)
495 continue;
497 if (m->NumberOfPages < EFI_SIZE_TO_PAGES(size))
498 continue;
500 start = m->PhysicalStart;
501 end = m->PhysicalStart + (m->NumberOfPages << EFI_PAGE_SHIFT);
502 if (first) {
503 if (end < min)
504 continue;
506 /* What's the best address? */
507 if (start < min && min < end)
508 best = min;
509 else
510 best = m->PhysicalStart;
512 start = round_up(best, align);
513 if (start > max)
514 continue;
516 /* Have we run out of space in this region? */
517 if (end < start || (start + size) > end)
518 continue;
520 if (start < *first)
521 *first = start;
524 if (last) {
525 if (start > max)
526 continue;
528 /* What's the best address? */
529 if (start < max && max < end)
530 best = max - size;
531 else
532 best = end - size;
534 start = round_down(best, align);
535 if (start < min || start < m->PhysicalStart)
536 continue;
538 if (start > *last)
539 *last = start;
543 FreePool(map);
547 * allocate_pages - Allocate memory pages from the system
548 * @atype: type of allocation to perform
549 * @mtype: type of memory to allocate
550 * @num_pages: number of contiguous 4KB pages to allocate
551 * @memory: used to return the address of allocated pages
553 * Allocate @num_pages physically contiguous pages from the system
554 * memory and return a pointer to the base of the allocation in
555 * @memory if the allocation succeeds. On success, the firmware memory
556 * map is updated accordingly.
558 * If @atype is AllocateAddress then, on input, @memory specifies the
559 * address at which to attempt to allocate the memory pages.
561 static inline EFI_STATUS
562 allocate_pages(EFI_ALLOCATE_TYPE atype, EFI_MEMORY_TYPE mtype,
563 UINTN num_pages, EFI_PHYSICAL_ADDRESS *memory)
565 return uefi_call_wrapper(BS->AllocatePages, 4, atype,
566 mtype, num_pages, memory);
569 * free_pages - Return memory allocated by allocate_pages() to the firmware
570 * @memory: physical base address of the page range to be freed
571 * @num_pages: number of contiguous 4KB pages to free
573 * On success, the firmware memory map is updated accordingly.
575 static inline EFI_STATUS
576 free_pages(EFI_PHYSICAL_ADDRESS memory, UINTN num_pages)
578 return uefi_call_wrapper(BS->FreePages, 2, memory, num_pages);
581 static EFI_STATUS allocate_addr(EFI_PHYSICAL_ADDRESS *addr, size_t size)
583 UINTN npages = EFI_SIZE_TO_PAGES(size);
585 return uefi_call_wrapper(BS->AllocatePages, 4,
586 AllocateAddress,
587 EfiLoaderData, npages,
588 addr);
591 * allocate_pool - Allocate pool memory
592 * @type: the type of pool to allocate
593 * @size: number of bytes to allocate from pool of @type
594 * @buffer: used to return the address of allocated memory
596 * Allocate memory from pool of @type. If the pool needs more memory
597 * pages are allocated from EfiConventionalMemory in order to grow the
598 * pool.
600 * All allocations are eight-byte aligned.
602 static inline EFI_STATUS
603 allocate_pool(EFI_MEMORY_TYPE type, UINTN size, void **buffer)
605 return uefi_call_wrapper(BS->AllocatePool, 3, type, size, buffer);
609 * free_pool - Return pool memory to the system
610 * @buffer: the buffer to free
612 * Return @buffer to the system. The returned memory is marked as
613 * EfiConventionalMemory.
615 static inline EFI_STATUS free_pool(void *buffer)
617 return uefi_call_wrapper(BS->FreePool, 1, buffer);
620 static void free_addr(EFI_PHYSICAL_ADDRESS addr, size_t size)
622 UINTN npages = EFI_SIZE_TO_PAGES(size);
624 uefi_call_wrapper(BS->FreePages, 2, addr, npages);
627 /* cancel the established timer */
628 static EFI_STATUS cancel_timer(EFI_EVENT ev)
630 return uefi_call_wrapper(BS->SetTimer, 3, ev, TimerCancel, 0);
633 /* Check if timer went off and update default timer counter */
634 void timer_handler(EFI_EVENT ev, VOID *ctx)
636 __ms_timer += DEFAULT_MSTIMER_INC;
637 ++__jiffies;
640 /* Setup a default periodic timer */
641 static EFI_STATUS setup_default_timer(EFI_EVENT *ev)
643 EFI_STATUS efi_status;
645 *ev = NULL;
646 efi_status = uefi_call_wrapper( BS->CreateEvent, 5, EVT_TIMER|EVT_NOTIFY_SIGNAL, TPL_NOTIFY, (EFI_EVENT_NOTIFY)timer_handler, NULL, ev);
647 if (efi_status == EFI_SUCCESS) {
648 efi_status = uefi_call_wrapper(BS->SetTimer, 3, *ev, TimerPeriodic, DEFAULT_TIMER_TICK_DURATION);
650 return efi_status;
654 * emalloc - Allocate memory with a strict alignment requirement
655 * @size: size in bytes of the requested allocation
656 * @align: the required alignment of the allocation
657 * @addr: a pointer to the allocated address on success
659 * If we cannot satisfy @align we return 0.
661 EFI_STATUS emalloc(UINTN size, UINTN align, EFI_PHYSICAL_ADDRESS *addr)
663 UINTN i, nr_entries, map_key, desc_size;
664 EFI_MEMORY_DESCRIPTOR *map_buf;
665 UINTN d;
666 UINT32 desc_version;
667 EFI_STATUS err;
668 UINTN nr_pages = EFI_SIZE_TO_PAGES(size);
670 map_buf = get_memory_map(&nr_entries, &map_key,
671 &desc_size, &desc_version);
672 if (!map_buf)
673 goto fail;
675 d = (UINTN)map_buf;
677 for (i = 0; i < nr_entries; i++, d += desc_size) {
678 EFI_MEMORY_DESCRIPTOR *desc;
679 EFI_PHYSICAL_ADDRESS start, end, aligned;
681 desc = (EFI_MEMORY_DESCRIPTOR *)d;
682 if (desc->Type != EfiConventionalMemory)
683 continue;
685 if (desc->NumberOfPages < nr_pages)
686 continue;
688 start = desc->PhysicalStart;
689 end = start + (desc->NumberOfPages << EFI_PAGE_SHIFT);
691 /* Low-memory is super-precious! */
692 if (end <= 1 << 20)
693 continue;
694 if (start < 1 << 20)
695 start = (1 << 20);
697 aligned = (start + align -1) & ~(align -1);
699 if ((aligned + size) <= end) {
700 err = allocate_pages(AllocateAddress, EfiLoaderData,
701 nr_pages, &aligned);
702 if (err == EFI_SUCCESS) {
703 *addr = aligned;
704 break;
709 if (i == nr_entries)
710 err = EFI_OUT_OF_RESOURCES;
712 free_pool(map_buf);
713 fail:
714 return err;
717 * efree - Return memory allocated with emalloc
718 * @memory: the address of the emalloc() allocation
719 * @size: the size of the allocation
721 void efree(EFI_PHYSICAL_ADDRESS memory, UINTN size)
723 UINTN nr_pages = EFI_SIZE_TO_PAGES(size);
725 free_pages(memory, nr_pages);
729 * Check whether 'buf' contains a PE/COFF header and that the PE/COFF
730 * file can be executed by this architecture.
732 static bool valid_pecoff_image(char *buf)
734 struct pe_header {
735 uint16_t signature;
736 uint8_t _pad[0x3a];
737 uint32_t offset;
738 } *pehdr = (struct pe_header *)buf;
739 struct coff_header {
740 uint32_t signature;
741 uint16_t machine;
742 } *chdr;
744 if (pehdr->signature != 0x5a4d) {
745 dprintf("Invalid MS-DOS header signature\n");
746 return false;
749 if (!pehdr->offset || pehdr->offset > 512) {
750 dprintf("Invalid PE header offset\n");
751 return false;
754 chdr = (struct coff_header *)&buf[pehdr->offset];
755 if (chdr->signature != 0x4550) {
756 dprintf("Invalid PE header signature\n");
757 return false;
760 #if defined(__x86_64__)
761 if (chdr->machine != 0x8664) {
762 dprintf("Invalid PE machine field\n");
763 return false;
765 #else
766 if (chdr->machine != 0x14c) {
767 dprintf("Invalid PE machine field\n");
768 return false;
770 #endif
772 return true;
776 * Boot a Linux kernel using the EFI boot stub handover protocol.
778 * This function will not return to its caller if booting the kernel
779 * image succeeds. If booting the kernel image fails, a legacy boot
780 * method should be attempted.
782 static void handover_boot(struct linux_header *hdr, struct boot_params *bp)
784 unsigned long address = hdr->code32_start + hdr->handover_offset;
785 handover_func_t *func = efi_handover;
787 dprintf("Booting kernel using handover protocol\n");
790 * Ensure that the kernel is a valid PE32(+) file and that the
791 * architecture of the file matches this version of Syslinux - we
792 * can't mix firmware and kernel bitness (e.g. 32-bit kernel on
793 * 64-bit EFI firmware) using the handover protocol.
795 if (!valid_pecoff_image((char *)hdr))
796 return;
798 if (hdr->version >= 0x20c) {
799 if (hdr->xloadflags & XLF_EFI_HANDOVER_32)
800 func = efi_handover_32;
802 if (hdr->xloadflags & XLF_EFI_HANDOVER_64)
803 func = efi_handover_64;
806 efi_console_restore();
807 func(image_handle, ST, bp, address);
810 static int check_linux_header(struct linux_header *hdr)
812 if (hdr->version < 0x205)
813 hdr->relocatable_kernel = 0;
815 /* FIXME: check boot sector signature */
816 if (hdr->boot_flag != BOOT_SIGNATURE) {
817 printf("Invalid Boot signature 0x%x, bailing out\n", hdr->boot_flag);
818 return -1;
821 return 0;
824 static char *build_cmdline(char *str)
826 EFI_PHYSICAL_ADDRESS addr;
827 EFI_STATUS status;
828 char *cmdline = NULL; /* internal, in efi_physical below 0x3FFFFFFF */
831 * The kernel expects cmdline to be allocated pretty low,
832 * Documentation/x86/boot.txt says,
834 * "The kernel command line can be located anywhere
835 * between the end of the setup heap and 0xA0000"
837 addr = 0xA0000;
838 status = allocate_pages(AllocateMaxAddress, EfiLoaderData,
839 EFI_SIZE_TO_PAGES(strlen(str) + 1),
840 &addr);
841 if (status != EFI_SUCCESS) {
842 printf("Failed to allocate memory for kernel command line, bailing out\n");
843 return NULL;
845 cmdline = (char *)(UINTN)addr;
846 memcpy(cmdline, str, strlen(str) + 1);
847 return cmdline;
850 static int build_gdt(void)
852 EFI_STATUS status;
854 /* Allocate gdt consistent with the alignment for architecture */
855 status = emalloc(gdt.limit, __SIZEOF_POINTER__ , (EFI_PHYSICAL_ADDRESS *)&gdt.base);
856 if (status != EFI_SUCCESS) {
857 printf("Failed to allocate memory for GDT, bailing out\n");
858 return -1;
860 memset(gdt.base, 0x0, gdt.limit);
863 * 4Gb - (0x100000*0x1000 = 4Gb)
864 * base address=0
865 * code read/exec
866 * granularity=4096, 386 (+5th nibble of limit)
868 gdt.base[2] = 0x00cf9a000000ffff;
871 * 4Gb - (0x100000*0x1000 = 4Gb)
872 * base address=0
873 * data read/write
874 * granularity=4096, 386 (+5th nibble of limit)
876 gdt.base[3] = 0x00cf92000000ffff;
878 /* Task segment value */
879 gdt.base[4] = 0x0080890000000000;
881 return 0;
885 * Callers use ->ramdisk_size to check whether any memory was
886 * allocated (and therefore needs free'ing). The return value indicates
887 * hard error conditions, such as failing to alloc memory for the
888 * ramdisk image. Having no initramfs is not an error.
890 static int handle_ramdisks(struct linux_header *hdr,
891 struct initramfs *initramfs)
893 EFI_PHYSICAL_ADDRESS last;
894 struct initramfs *ip;
895 EFI_STATUS status;
896 addr_t irf_size;
897 addr_t next_addr, len, pad;
899 hdr->ramdisk_image = 0;
900 hdr->ramdisk_size = 0;
903 * Figure out the size of the initramfs, and where to put it.
904 * We should put it at the highest possible address which is
905 * <= hdr->initrd_addr_max, which fits the entire initramfs.
907 irf_size = initramfs_size(initramfs); /* Handles initramfs == NULL */
908 if (!irf_size)
909 return 0;
911 last = 0;
912 find_addr(NULL, &last, 0x1000, hdr->initrd_addr_max,
913 irf_size, INITRAMFS_MAX_ALIGN);
914 if (last)
915 status = allocate_addr(&last, irf_size);
917 if (!last || status != EFI_SUCCESS) {
918 printf("Failed to allocate initramfs memory, bailing out\n");
919 return -1;
922 hdr->ramdisk_image = (uint32_t)last;
923 hdr->ramdisk_size = irf_size;
925 /* Copy initramfs into allocated memory */
926 for (ip = initramfs->next; ip->len; ip = ip->next) {
927 len = ip->len;
928 next_addr = last + len;
931 * If this isn't the last entry, extend the
932 * zero-pad region to enforce the alignment of
933 * the next chunk.
935 if (ip->next->len) {
936 pad = -next_addr & (ip->next->align - 1);
937 len += pad;
938 next_addr += pad;
941 if (ip->data_len)
942 memcpy((void *)(UINTN)last, ip->data, ip->data_len);
944 if (len > ip->data_len)
945 memset((void *)(UINTN)(last + ip->data_len), 0,
946 len - ip->data_len);
948 last = next_addr;
950 return 0;
953 static int exit_boot(struct boot_params *bp)
955 struct e820_entry *e820buf, *e;
956 EFI_MEMORY_DESCRIPTOR *map;
957 EFI_STATUS status;
958 uint32_t e820_type;
959 UINTN i, nr_entries, key, desc_sz;
960 UINT32 desc_ver;
962 /* Build efi memory map */
963 map = get_memory_map(&nr_entries, &key, &desc_sz, &desc_ver);
964 if (!map)
965 return -1;
967 bp->efi.memmap = (uint32_t)(unsigned long)map;
968 bp->efi.memmap_size = nr_entries * desc_sz;
969 bp->efi.systab = (uint32_t)(unsigned long)ST;
970 bp->efi.desc_size = desc_sz;
971 bp->efi.desc_version = desc_ver;
972 #if defined(__x86_64__)
973 bp->efi.systab_hi = ((unsigned long)ST) >> 32;
974 bp->efi.memmap_hi = ((unsigned long)map) >> 32;
975 #endif
979 * Even though 'memmap' contains the memory map we provided
980 * previously in efi_scan_memory(), we should recalculate the
981 * e820 map because it will most likely have changed in the
982 * interim.
984 e = e820buf = bp->e820_map;
985 for (i = 0; i < nr_entries && i < E820MAX; i++) {
986 struct e820_entry *prev = NULL;
988 if (e > e820buf)
989 prev = e - 1;
991 map = get_mem_desc(bp->efi.memmap, desc_sz, i);
992 e->start = map->PhysicalStart;
993 e->len = map->NumberOfPages << EFI_PAGE_SHIFT;
995 switch (map->Type) {
996 case EfiReservedMemoryType:
997 case EfiRuntimeServicesCode:
998 case EfiRuntimeServicesData:
999 case EfiMemoryMappedIO:
1000 case EfiMemoryMappedIOPortSpace:
1001 case EfiPalCode:
1002 e820_type = E820_RESERVED;
1003 break;
1005 case EfiUnusableMemory:
1006 e820_type = E820_UNUSABLE;
1007 break;
1009 case EfiACPIReclaimMemory:
1010 e820_type = E820_ACPI;
1011 break;
1013 case EfiLoaderCode:
1014 case EfiLoaderData:
1015 case EfiBootServicesCode:
1016 case EfiBootServicesData:
1017 case EfiConventionalMemory:
1018 e820_type = E820_RAM;
1019 break;
1021 case EfiACPIMemoryNVS:
1022 e820_type = E820_NVS;
1023 break;
1024 default:
1025 continue;
1028 e->type = e820_type;
1030 /* Check for adjacent entries we can merge. */
1031 if (prev && (prev->start + prev->len) == e->start &&
1032 prev->type == e->type)
1033 prev->len += e->len;
1034 else
1035 e++;
1038 bp->e820_entries = e - e820buf;
1040 status = uefi_call_wrapper(BS->ExitBootServices, 2, image_handle, key);
1041 if (status != EFI_SUCCESS) {
1042 printf("Failed to exit boot services: 0x%016lx\n", status);
1043 FreePool(map);
1044 return -1;
1047 return 0;
1050 /* efi_boot_linux:
1051 * Boots the linux kernel using the image and parameters to boot with.
1052 * The EFI boot loader is reworked taking the cue from
1053 * http://git.kernel.org/?p=boot/efilinux/efilinux.git on the need to
1054 * cap key kernel data structures at * 0x3FFFFFFF.
1055 * The kernel image, kernel command line and boot parameter block are copied
1056 * into allocated memory areas that honor the address capping requirement
1057 * prior to kernel handoff.
1059 * FIXME
1060 * Can we move this allocation requirement to com32 linux loader in order
1061 * to avoid double copying kernel image?
1063 int efi_boot_linux(void *kernel_buf, size_t kernel_size,
1064 struct initramfs *initramfs,
1065 struct setup_data *setup_data,
1066 char *cmdline)
1068 struct linux_header *hdr;
1069 struct boot_params *bp;
1070 EFI_STATUS status;
1071 EFI_PHYSICAL_ADDRESS addr, pref_address, kernel_start = 0;
1072 UINT64 setup_sz, init_size = 0;
1073 char *_cmdline;
1075 if (check_linux_header(kernel_buf))
1076 goto bail;
1078 /* allocate for boot parameter block */
1079 addr = 0x3FFFFFFF;
1080 status = allocate_pages(AllocateMaxAddress, EfiLoaderData,
1081 BOOT_PARAM_BLKSIZE, &addr);
1082 if (status != EFI_SUCCESS) {
1083 printf("Failed to allocate memory for kernel boot parameter block, bailing out\n");
1084 goto bail;
1087 bp = (struct boot_params *)(UINTN)addr;
1089 memset((void *)bp, 0x0, BOOT_PARAM_BLKSIZE);
1090 /* Copy the first two sectors to boot_params */
1091 memcpy((char *)bp, kernel_buf, 2 * 512);
1092 hdr = (struct linux_header *)bp;
1094 setup_sz = (hdr->setup_sects + 1) * 512;
1095 if (hdr->version >= 0x20a) {
1096 pref_address = hdr->pref_address;
1097 init_size = hdr->init_size;
1098 } else {
1099 pref_address = 0x100000;
1102 * We need to account for the fact that the kernel
1103 * needs room for decompression, otherwise we could
1104 * end up trashing other chunks of allocated memory.
1106 init_size = (kernel_size - setup_sz) * 3;
1108 hdr->type_of_loader = SYSLINUX_EFILDR; /* SYSLINUX boot loader module */
1109 _cmdline = build_cmdline(cmdline);
1110 if (!_cmdline)
1111 goto bail;
1113 hdr->cmd_line_ptr = (UINT32)(UINTN)_cmdline;
1115 addr = pref_address;
1116 status = allocate_pages(AllocateAddress, EfiLoaderData,
1117 EFI_SIZE_TO_PAGES(init_size), &addr);
1118 if (status != EFI_SUCCESS) {
1120 * We failed to allocate the preferred address, so
1121 * just allocate some memory and hope for the best.
1123 if (!hdr->relocatable_kernel) {
1124 printf("Cannot relocate kernel, bailing out\n");
1125 goto bail;
1128 status = emalloc(init_size, hdr->kernel_alignment, &addr);
1129 if (status != EFI_SUCCESS) {
1130 printf("Failed to allocate memory for kernel image, bailing out\n");
1131 goto free_map;
1134 kernel_start = addr;
1135 /* FIXME: we copy the kernel into the physical memory allocated here
1136 * The syslinux kernel image load elsewhere could allocate the EFI memory from here
1137 * prior to copying kernel and save an extra copy
1139 memcpy((void *)(UINTN)kernel_start, kernel_buf+setup_sz, kernel_size-setup_sz);
1141 hdr->code32_start = (UINT32)((UINT64)kernel_start);
1143 dprintf("efi_boot_linux: kernel_start 0x%x kernel_size 0x%x initramfs 0x%x setup_data 0x%x cmdline 0x%x\n",
1144 kernel_start, kernel_size, initramfs, setup_data, _cmdline);
1146 if (handle_ramdisks(hdr, initramfs))
1147 goto free_map;
1149 /* Attempt to use the handover protocol if available */
1150 if (hdr->version >= 0x20b && hdr->handover_offset)
1151 handover_boot(hdr, bp);
1153 setup_screen(&bp->screen_info);
1155 if (build_gdt())
1156 goto free_map;
1158 dprintf("efi_boot_linux: setup_sects %d kernel_size %d\n", hdr->setup_sects, kernel_size);
1160 efi_console_restore();
1162 if (exit_boot(bp))
1163 goto free_map;
1165 memcpy(&bp->efi.load_signature, EFI_LOAD_SIG, sizeof(uint32_t));
1167 asm volatile ("lidt %0" :: "m" (idt));
1168 asm volatile ("lgdt %0" :: "m" (gdt));
1170 kernel_jump(kernel_start, bp);
1172 /* NOTREACHED */
1174 free_map:
1175 if (_cmdline)
1176 efree((EFI_PHYSICAL_ADDRESS)(unsigned long)_cmdline,
1177 strlen(_cmdline) + 1);
1179 if (bp)
1180 efree((EFI_PHYSICAL_ADDRESS)(unsigned long)bp,
1181 BOOT_PARAM_BLKSIZE);
1182 if (kernel_start) efree(kernel_start, init_size);
1183 if (hdr->ramdisk_size)
1184 free_addr(hdr->ramdisk_image, hdr->ramdisk_size);
1185 bail:
1186 return -1;
1189 extern struct disk *efi_disk_init(EFI_HANDLE);
1190 extern void serialcfg(uint16_t *, uint16_t *, uint16_t *);
1192 extern struct vesa_ops efi_vesa_ops;
1194 struct mem_ops efi_mem_ops = {
1195 .malloc = efi_malloc,
1196 .realloc = efi_realloc,
1197 .free = efi_free,
1200 struct firmware efi_fw = {
1201 .init = efi_init,
1202 .disk_init = efi_disk_init,
1203 .o_ops = &efi_ops,
1204 .i_ops = &efi_iops,
1205 .get_serial_console_info = serialcfg,
1206 .adv_ops = &efi_adv_ops,
1207 .boot_linux = efi_boot_linux,
1208 .vesa = &efi_vesa_ops,
1209 .mem = &efi_mem_ops,
1212 static inline void syslinux_register_efi(void)
1214 firmware = &efi_fw;
1217 extern void init(void);
1218 extern const struct fs_ops vfat_fs_ops;
1219 extern const struct fs_ops pxe_fs_ops;
1221 char free_high_memory[4096];
1223 extern char __bss_start[];
1224 extern char __bss_end[];
1226 static void efi_setcwd(CHAR16 *dp)
1228 CHAR16 *c16;
1229 char *c8;
1230 int i, j;
1232 /* Search for the start of the last path component */
1233 for (i = StrLen(dp) - 1; i >= 0; i--) {
1234 if (dp[i] == '\\' || dp[i] == '/')
1235 break;
1238 if (i < 0 || i > CURRENTDIR_MAX) {
1239 dp = L"\\";
1240 i = 1;
1243 c8 = CurrentDirName;
1244 c16 = dp;
1246 for (j = 0; j < i; j++) {
1247 if (*c16 == '\\') {
1248 *c8++ = '/';
1249 c16++;
1250 } else
1251 *c8++ = *c16++;
1254 *c8 = '\0';
1257 EFI_STATUS efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *table)
1259 EFI_PXE_BASE_CODE *pxe;
1260 EFI_LOADED_IMAGE *info;
1261 EFI_STATUS status = EFI_SUCCESS;
1262 const struct fs_ops *ops[] = { NULL, NULL };
1263 unsigned long len = (unsigned long)__bss_end - (unsigned long)__bss_start;
1264 static struct efi_disk_private priv;
1265 SIMPLE_INPUT_INTERFACE *in;
1266 EFI_INPUT_KEY key;
1267 EFI_EVENT timer_ev;
1269 memset(__bss_start, 0, len);
1270 InitializeLib(image, table);
1272 image_handle = image;
1273 syslinux_register_efi();
1275 efi_console_save();
1276 init();
1278 status = uefi_call_wrapper(BS->HandleProtocol, 3, image,
1279 &LoadedImageProtocol, (void **)&info);
1280 if (status != EFI_SUCCESS) {
1281 Print(L"Failed to lookup LoadedImageProtocol\n");
1282 goto out;
1285 status = uefi_call_wrapper(BS->HandleProtocol, 3, info->DeviceHandle,
1286 &PxeBaseCodeProtocol, (void **)&pxe);
1287 if (status != EFI_SUCCESS) {
1289 * Use device handle to set up the volume root to
1290 * proceed with ADV init.
1292 if (EFI_ERROR(efi_set_volroot(info->DeviceHandle))) {
1293 Print(L"Failed to locate root device to prep for ");
1294 Print(L"file operations & ADV initialization\n");
1295 goto out;
1298 efi_derivative(SYSLINUX_FS_SYSLINUX);
1299 ops[0] = &vfat_fs_ops;
1300 } else {
1301 efi_derivative(SYSLINUX_FS_PXELINUX);
1302 ops[0] = &pxe_fs_ops;
1305 /* setup timer for boot menu system support */
1306 status = setup_default_timer(&timer_ev);
1307 if (status != EFI_SUCCESS) {
1308 Print(L"Failed to set up EFI timer support, bailing out\n");
1309 goto out;
1312 /* TODO: once all errors are captured in efi_errno, bail out if necessary */
1314 priv.dev_handle = info->DeviceHandle;
1317 * Set the current working directory, which should be the
1318 * directory that syslinux.efi resides in.
1320 efi_setcwd(DevicePathToStr(info->FilePath));
1322 fs_init(ops, (void *)&priv);
1325 * There may be pending user input that wasn't processed by
1326 * whatever application invoked us. Consume and discard that
1327 * data now.
1329 in = ST->ConIn;
1330 do {
1331 status = uefi_call_wrapper(in->ReadKeyStroke, 2, in, &key);
1332 } while (status != EFI_NOT_READY);
1334 if (!setjmp(load_error_buf))
1335 load_env32(NULL);
1337 /* load_env32() failed.. cancel timer and bailout */
1338 status = cancel_timer(timer_ev);
1339 if (status != EFI_SUCCESS)
1340 Print(L"Failed to cancel EFI timer: %x\n", status);
1343 * Tell the firmware that Syslinux failed to load.
1345 status = EFI_LOAD_ERROR;
1346 out:
1347 efi_console_restore();
1348 return status;