diff --git a/include/app_memory/app_memdomain.h b/include/app_memory/app_memdomain.h index bea1527843d..62a8eaba36b 100644 --- a/include/app_memory/app_memdomain.h +++ b/include/app_memory/app_memdomain.h @@ -55,7 +55,11 @@ struct app_region { char *dmem_start; char *bmem_start; +#ifdef CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT + char *smem_size; +#else u32_t smem_size; +#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ u32_t dmem_size; u32_t bmem_size; struct k_mem_partition *partition; @@ -66,9 +70,21 @@ struct app_region { * Declares a partition and provides a function to add the * partition to the linke dlist and initialize the partition. */ +#ifdef CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT +/* For power of 2 MPUs linker provides support to help us + * calculate the region sizes. + */ +#define smem_size_declare(name) extern char data_smem_##name##_size[] +#define smem_size_assign(name) name.smem_size = data_smem_##name##_size +#else +#define smem_size_declare(name) +#define smem_size_assign(name) +#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ + #define appmem_partition(name) \ extern char *data_smem_##name; \ extern char *data_smem_##name##b; \ + smem_size_declare(name); \ _app_dmem_pad(name) char name##_dmem_pad; \ _app_bmem_pad(name) char name##_bmem_pad; \ __kernel struct k_mem_partition mem_domain_##name; \ @@ -77,6 +93,7 @@ struct app_region { { \ name.dmem_start = (char *)&data_smem_##name; \ name.bmem_start = (char *)&data_smem_##name##b; \ + smem_size_assign(name); \ sys_dlist_append(&app_mem_list, &name.lnode); \ mem_domain_##name.start = (u32_t) name.dmem_start; \ mem_domain_##name.attr = K_MEM_PARTITION_P_RW_U_RW; \ diff --git a/include/arch/arm/cortex_m/scripts/linker.ld b/include/arch/arm/cortex_m/scripts/linker.ld index 5c8635800f1..3c6730df41c 100644 --- a/include/arch/arm/cortex_m/scripts/linker.ld +++ b/include/arch/arm/cortex_m/scripts/linker.ld @@ -236,22 +236,26 @@ SECTIONS #endif #include + +#if defined(CONFIG_APP_SHARED_MEM) +#if defined(CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT) + #include +#else SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) { . = ALIGN(4); _image_ram_start = .; _app_smem_start = .; -#if defined(CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT) - #include -#else APP_SMEM_SECTION() -#endif _app_smem_end = .; _app_smem_size = _app_smem_end - _app_smem_start; . = ALIGN(4); } GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION) +#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ _app_smem_rom_start = LOADADDR(_APP_SMEM_SECTION_NAME); +#endif /* CONFIG_APP_SHARED_MEM */ + #ifdef CONFIG_APPLICATION_MEMORY SECTION_DATA_PROLOGUE(_APP_DATA_SECTION_NAME, (OPTIONAL),) { diff --git a/scripts/gen_app_partitions.py b/scripts/gen_app_partitions.py index 6bac8c0c0b2..528490bbe7f 100644 --- a/scripts/gen_app_partitions.py +++ b/scripts/gen_app_partitions.py @@ -11,13 +11,31 @@ from elftools.elf.elffile import ELFFile # This script will create linker comands for power of two aligned MPU # when APP_SHARED_MEM is enabled. print_template = """ -/* Auto generated code do not modify */ -. = ALIGN( 1 << LOG2CEIL(data_smem_{0}b_end - data_smem_{0})); -data_smem_{0} = .; -KEEP(*(SORT(data_smem_{0}*))) -. = ALIGN(_app_data_align); -data_smem_{0}b_end = .; -. = ALIGN( 1 << LOG2CEIL(data_smem_{0}b_end - data_smem_{0})); + /* Auto generated code do not modify */ + . = ALIGN( 1 << LOG2CEIL(data_smem_{0}b_end - data_smem_{0})); + data_smem_{0} = .; + KEEP(*(SORT(data_smem_{0}*))) + . = ALIGN(_app_data_align); + . = ALIGN( 1 << LOG2CEIL(data_smem_{0}b_end - data_smem_{0})); + data_smem_{0}b_end = .; +""" +linker_start_seq = """ + SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) + { + . = ALIGN(4); + _image_ram_start = .; + _app_smem_start = .; +""" + +linker_end_seq = """ + _app_smem_end = .; + _app_smem_size = _app_smem_end - _app_smem_start; + . = ALIGN(4); + } GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION) +""" + +size_cal_string = """ + data_smem_{0}_size = data_smem_{0}b_end - data_smem_{0}; """ @@ -46,10 +64,14 @@ def cleanup_remove_bss_regions(full_list_of_partitions): return full_list_of_partitions def generate_final_linker(linker_file, full_list_of_partitions): - string= '' + string = linker_start_seq + size_string = '' for partition in full_list_of_partitions: string += print_template.format(partition) + size_string += size_cal_string.format(partition) + string += linker_end_seq + string += size_string with open(linker_file, "w") as fw: fw.write(string) diff --git a/subsys/app_memory/app_memdomain.c b/subsys/app_memory/app_memdomain.c index c089c1633c5..121cdb163f1 100644 --- a/subsys/app_memory/app_memdomain.c +++ b/subsys/app_memory/app_memdomain.c @@ -37,6 +37,7 @@ void app_calc_size(void) SYS_DLIST_FOR_EACH_NODE_SAFE(&app_mem_list, node, next_node) { +#ifndef CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT if (sys_dlist_is_tail(&app_mem_list, node)) { struct app_region *region = CONTAINER_OF(node, struct app_region, lnode); @@ -67,6 +68,21 @@ void app_calc_size(void) region->partition[0].size = region->dmem_size + region->bmem_size; } + +#else + /* For power of 2 MPUs linker provides support to help us + * calculate the region sizes. + */ + struct app_region *region = + CONTAINER_OF(node, struct app_region, lnode); + + region->dmem_size = (char *)region->bmem_start - + (char *)region->dmem_start; + region->bmem_size = (char *)region->smem_size - + (char *)region->dmem_size; + + region->partition[0].size = (s32_t)region->smem_size; +#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ } }