Commit ed7b8749 authored by David Mosberger's avatar David Mosberger

ia64: Fix efi_memmap_walk() to work with more complicated memory maps.

	Fix ACPI_ACQUIRE_GLOBAL_LOCK and ACPI_RELEASE_GLOBAL_LOCK.
	Both bugs reported by Charles Sluder.
parent 15f20a53
...@@ -306,7 +306,7 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg) ...@@ -306,7 +306,7 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg)
u64 start; u64 start;
u64 end; u64 end;
} prev, curr; } prev, curr;
void *efi_map_start, *efi_map_end, *p, *q; void *efi_map_start, *efi_map_end, *p, *q, *r;
efi_memory_desc_t *md, *check_md; efi_memory_desc_t *md, *check_md;
u64 efi_desc_size, start, end, granule_addr, first_non_wb_addr = 0; u64 efi_desc_size, start, end, granule_addr, first_non_wb_addr = 0;
...@@ -351,11 +351,10 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg) ...@@ -351,11 +351,10 @@ efi_memmap_walk (efi_freemem_callback_t callback, void *arg)
if (!(first_non_wb_addr > granule_addr)) if (!(first_non_wb_addr > granule_addr))
continue; /* couldn't find enough contiguous memory */ continue; /* couldn't find enough contiguous memory */
}
/* BUG_ON((md->phys_addr >> IA64_GRANULE_SHIFT) < first_non_wb_addr); */
trim_top(md, first_non_wb_addr); for (r = p; r < q; r += efi_desc_size)
trim_top(r, first_non_wb_addr);
}
if (is_available_memory(md)) { if (is_available_memory(md)) {
if (md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) > mem_limit) { if (md->phys_addr + (md->num_pages << EFI_PAGE_SHIFT) > mem_limit) {
......
...@@ -20,7 +20,13 @@ ...@@ -20,7 +20,13 @@
#define MB (1024*1024UL) #define MB (1024*1024UL)
#define NUM_MEM_DESCS 3 #define SIMPLE_MEMMAP 1
#if SIMPLE_MEMMAP
# define NUM_MEM_DESCS 4
#else
# define NUM_MEM_DESCS 16
#endif
static char fw_mem[( sizeof(struct ia64_boot_param) static char fw_mem[( sizeof(struct ia64_boot_param)
+ sizeof(efi_system_table_t) + sizeof(efi_system_table_t)
...@@ -379,6 +385,17 @@ sys_fw_init (const char *args, int arglen) ...@@ -379,6 +385,17 @@ sys_fw_init (const char *args, int arglen)
struct ia64_boot_param *bp; struct ia64_boot_param *bp;
unsigned char checksum = 0; unsigned char checksum = 0;
char *cp, *cmd_line; char *cp, *cmd_line;
int i = 0;
# define MAKE_MD(typ, attr, start, end) \
do { \
md = efi_memmap + i++; \
md->type = typ; \
md->pad = 0; \
md->phys_addr = start; \
md->virt_addr = 0; \
md->num_pages = (end - start) >> 12; \
md->attribute = attr; \
} while (0)
memset(fw_mem, 0, sizeof(fw_mem)); memset(fw_mem, 0, sizeof(fw_mem));
...@@ -464,47 +481,29 @@ sys_fw_init (const char *args, int arglen) ...@@ -464,47 +481,29 @@ sys_fw_init (const char *args, int arglen)
sal_systab->checksum = -checksum; sal_systab->checksum = -checksum;
#if SIMPLE_MEMMAP
/* simulate free memory at physical address zero */ /* simulate free memory at physical address zero */
md = &efi_memmap[0]; MAKE_MD(EFI_BOOT_SERVICES_DATA, EFI_MEMORY_WB, 0*MB, 1*MB);
md->type = EFI_BOOT_SERVICES_DATA; MAKE_MD(EFI_PAL_CODE, EFI_MEMORY_WB, 1*MB, 2*MB);
md->pad = 0; MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB, 2*MB, 130*MB);
md->phys_addr = 0*MB; MAKE_MD(EFI_CONVENTIONAL_MEMORY, EFI_MEMORY_WB, 4096*MB, 4128*MB);
md->virt_addr = 0; #else
md->num_pages = (1*MB) >> 12; /* 1MB (in 4KB pages) */ MAKE_MD( 4, 0x9, 0x0000000000000000, 0x0000000000001000);
md->attribute = EFI_MEMORY_WB; MAKE_MD( 7, 0x9, 0x0000000000001000, 0x000000000008a000);
MAKE_MD( 4, 0x9, 0x000000000008a000, 0x00000000000a0000);
/* fill in a memory descriptor: */ MAKE_MD( 5, 0x8000000000000009, 0x00000000000c0000, 0x0000000000100000);
md = &efi_memmap[1]; MAKE_MD( 7, 0x9, 0x0000000000100000, 0x0000000004400000);
md->type = EFI_CONVENTIONAL_MEMORY; MAKE_MD( 2, 0x9, 0x0000000004400000, 0x0000000004be5000);
md->pad = 0; MAKE_MD( 7, 0x9, 0x0000000004be5000, 0x000000007f77e000);
md->phys_addr = 2*MB; MAKE_MD( 6, 0x8000000000000009, 0x000000007f77e000, 0x000000007fb94000);
md->virt_addr = 0; MAKE_MD( 6, 0x8000000000000009, 0x000000007fb94000, 0x000000007fb95000);
md->num_pages = (128*MB) >> 12; /* 128MB (in 4KB pages) */ MAKE_MD( 6, 0x8000000000000009, 0x000000007fb95000, 0x000000007fc00000);
md->attribute = EFI_MEMORY_WB; MAKE_MD(13, 0x8000000000000009, 0x000000007fc00000, 0x000000007fc3a000);
MAKE_MD( 7, 0x9, 0x000000007fc3a000, 0x000000007fea0000);
/* descriptor for firmware emulator: */ MAKE_MD( 5, 0x8000000000000009, 0x000000007fea0000, 0x000000007fea8000);
md = &efi_memmap[2]; MAKE_MD( 7, 0x9, 0x000000007fea8000, 0x000000007feab000);
md->type = EFI_PAL_CODE; MAKE_MD( 5, 0x8000000000000009, 0x000000007feab000, 0x000000007ffff000);
md->pad = 0; MAKE_MD( 7, 0x9, 0x00000000ff400000, 0x0000000104000000);
md->phys_addr = 1*MB;
md->virt_addr = 1*MB;
md->num_pages = (1*MB) >> 12; /* 1MB (in 4KB pages) */
md->attribute = EFI_MEMORY_WB;
#if 0
/*
* XXX bootmem is broken for now... (remember to NUM_MEM_DESCS
* if you re-enable this!)
*/
/* descriptor for high memory (>4GB): */
md = &efi_memmap[3];
md->type = EFI_CONVENTIONAL_MEMORY;
md->pad = 0;
md->phys_addr = 4096*MB;
md->virt_addr = 0;
md->num_pages = (32*MB) >> 12; /* 32MB (in 4KB pages) */
md->attribute = EFI_MEMORY_WB;
#endif #endif
bp->efi_systab = __pa(&fw_mem); bp->efi_systab = __pa(&fw_mem);
......
...@@ -56,7 +56,7 @@ ...@@ -56,7 +56,7 @@
#define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq) \ #define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq) \
do { \ do { \
__asm__ volatile ("1: ld4 r29=%1\n" \ __asm__ volatile ("1: ld4 r29=[%1]\n" \
";;\n" \ ";;\n" \
"mov ar.ccv=r29\n" \ "mov ar.ccv=r29\n" \
"mov r2=r29\n" \ "mov r2=r29\n" \
...@@ -68,7 +68,7 @@ ...@@ -68,7 +68,7 @@
";;\n" \ ";;\n" \
"add r29=r29,r30\n" \ "add r29=r29,r30\n" \
";;\n" \ ";;\n" \
"cmpxchg4.acq r30=%1,r29,ar.ccv\n" \ "cmpxchg4.acq r30=[%1],r29,ar.ccv\n" \
";;\n" \ ";;\n" \
"cmp.eq p6,p7=r2,r30\n" \ "cmp.eq p6,p7=r2,r30\n" \
"(p7) br.dpnt.few 1b\n" \ "(p7) br.dpnt.few 1b\n" \
...@@ -76,24 +76,24 @@ ...@@ -76,24 +76,24 @@
";;\n" \ ";;\n" \
"(p8) mov %0=-1\n" \ "(p8) mov %0=-1\n" \
"(p9) mov %0=r0\n" \ "(p9) mov %0=r0\n" \
:"=r"(Acq):"m"(GLptr):"r2","r29","r30","memory"); \ :"=r"(Acq):"r"(GLptr):"r2","r29","r30","memory"); \
} while (0) } while (0)
#define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq) \ #define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq) \
do { \ do { \
__asm__ volatile ("1: ld4 r29=%1\n" \ __asm__ volatile ("1: ld4 r29=[%1]\n" \
";;\n" \ ";;\n" \
"mov ar.ccv=r29\n" \ "mov ar.ccv=r29\n" \
"mov r2=r29\n" \ "mov r2=r29\n" \
"and r29=-4,r29\n" \ "and r29=-4,r29\n" \
";;\n" \ ";;\n" \
"cmpxchg4.acq r30=%1,r29,ar.ccv\n" \ "cmpxchg4.acq r30=[%1],r29,ar.ccv\n" \
";;\n" \ ";;\n" \
"cmp.eq p6,p7=r2,r30\n" \ "cmp.eq p6,p7=r2,r30\n" \
"(p7) br.dpnt.few 1b\n" \ "(p7) br.dpnt.few 1b\n" \
"and %0=1,r2\n" \ "and %0=1,r2\n" \
";;\n" \ ";;\n" \
:"=r"(Acq):"m"(GLptr):"r2","r29","r30","memory"); \ :"=r"(Acq):"r"(GLptr):"r2","r29","r30","memory"); \
} while (0) } while (0)
const char *acpi_get_sysname (void); const char *acpi_get_sysname (void);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment