diff --git a/second/bank.c b/second/bank.c index 30de916..2a4875f 100644 --- a/second/bank.c +++ b/second/bank.c @@ -7,6 +7,7 @@ */ #include +#include #include "arch.h" #include "lowmem.h" @@ -174,6 +175,20 @@ static int bank_find_by_physical(unsigned long physical) return -1; } +static int bank_find_by_logical(unsigned long logical) +{ + int i; + + for (i = 0; i < memory_map.bank_number; i++) + { + if ( (memory_map.bank[i].logiAddr <= logical) && + ( logical < memory_map.bank[i].logiAddr + memory_map.bank[i].size) ) + return i; + } + + return -1; +} + int logical2physical(unsigned long logical, unsigned long *physical) { if ( (mmu_type == gestaltNoMMU) || (mmu_type == gestaltEMMU1) ) @@ -223,23 +238,46 @@ unsigned long bank_mem_avail() int check_full_in_bank(unsigned long start, unsigned long size) { - int i; + int bank0; + int bank1; - for (i = 0; i < memory_map.bank_number; i++) + bank0 = bank_find_by_logical(start); + bank1 = bank_find_by_logical(start + size); + + return (bank0 == bank1); +} + +void *malloc_contiguous(size_t size) +{ + void* tmp; + void* contiguous; + int bank; + size_t part_size; + + tmp = malloc(size); + + if (check_full_in_bank((unsigned long)tmp, size)) + return tmp; + + /* not in one contiguous block */ + + bank = bank_find_by_logical((unsigned long)tmp); + + part_size = memory_map.bank[bank].size - + ((unsigned long)tmp - memory_map.bank[bank].logiAddr); + free(tmp); + + tmp = malloc(part_size); + contiguous = malloc(size); + free(tmp); + + if (!check_full_in_bank((unsigned long)contiguous, size)) { - if ( ( (memory_map.bank[i].logiAddr <= start) && - (start < memory_map.bank[i].logiAddr + memory_map.bank[i].size) ) && - ! ( (memory_map.bank[i].logiAddr <= start + size) && - (start + size < memory_map.bank[i].logiAddr + memory_map.bank[i].size) ) ) - { - printf("0x%lx in 0x%lx : 0x%lx\n", start, - memory_map.bank[i].logiAddr, - memory_map.bank[i].logiAddr + memory_map.bank[i].size); - printf("0x%lx out of bound\n", start + size); - return -1; - } + free(contiguous); + return NULL; } - return 0; + + return contiguous; } #ifdef BANK_DUMP diff --git a/second/bank.h b/second/bank.h index 00bf432..309e2c4 100644 --- a/second/bank.h +++ b/second/bank.h @@ -27,3 +27,4 @@ extern void bank_dump(); extern int logical2physical(unsigned long logical, unsigned long *physical); extern int physical2logical(unsigned long physical, unsigned long *logical); extern int check_full_in_bank(unsigned long start, unsigned long size); +extern void *malloc_contiguous(size_t size); diff --git a/second/load.c b/second/load.c index 73c3c52..081fb61 100644 --- a/second/load.c +++ b/second/load.c @@ -6,6 +6,7 @@ #include #include +#include "bank.h" #include "misc.h" #include "glue.h" #include "load.h" @@ -19,7 +20,7 @@ char* load_image(unsigned long offset, unsigned long size) if (size == 0) return NULL; - image = malloc(size + 4); + image = malloc_contiguous(size + 4); if (image == 0) { free(image); diff --git a/second/main.c b/second/main.c index 112c8c2..099d67b 100644 --- a/second/main.c +++ b/second/main.c @@ -106,7 +106,7 @@ int start(emile_l2_header_t* info) */ printf("Allocating %d bytes for kernel\n", info->kernel_size); - kernel = (char*)malloc(info->kernel_size + 4 + BI_ALLOC_SIZE + + kernel = (char*)malloc_contiguous(info->kernel_size + 4 + BI_ALLOC_SIZE + end_enter_kernel - enter_kernel); if (kernel == 0) { @@ -120,7 +120,7 @@ int start(emile_l2_header_t* info) uncompressed_size = uncompress(kernel, (char*)kernel_image_start); printf("\n"); - if (check_full_in_bank((unsigned long)kernel, uncompressed_size)) + if (!check_full_in_bank((unsigned long)kernel, uncompressed_size)) error("Kernel between two banks, send a mail to LaurentVivier@wanadoo.fr for support\n"); /* copy enter_kernel at end of kernel */ @@ -154,7 +154,7 @@ int start(emile_l2_header_t* info) info->ramdisk_size); printf("RAMDISK loaded at 0x%lx\n", ramdisk_start); printf("RAMDISK size is %d Bytes\n", info->ramdisk_size); - if (check_full_in_bank(ramdisk_start, info->ramdisk_size)) + if (!check_full_in_bank(ramdisk_start, info->ramdisk_size)) error("ramdisk between two banks, send a mail to LaurentVivier@wanadoo.fr for support\n"); } else