diff --git a/include/app_memory/app_memdomain.h b/include/app_memory/app_memdomain.h index c7fa6cddad2..861e140b7d4 100644 --- a/include/app_memory/app_memdomain.h +++ b/include/app_memory/app_memdomain.h @@ -13,26 +13,26 @@ #error "Not implemented for this architecture" #endif -/* - * There has got to be a better way of doing this. This - * tries to ensure that a) each subsection has a - * data_smem_#id_b part and b) that each k_mem_partition - * matches the page size or MPU region. If there is no - * data_smem_#id_b subsection, then the size calculations - * will fail. Additionally, if each k_mem_partition does - * not match the page size or MPU region, then the - * partition will fail to be created. - * checkpatch.pl complains that __aligned(size) is - * preferred, but, if implemented, then complains about - * complex macro without parentheses. - */ -#define _app_dmem_pad(id) \ - __attribute__((aligned(MEM_DOMAIN_ALIGN_SIZE), \ - section("data_smem_" #id))) -#define _app_bmem_pad(id) \ - __attribute__((aligned(MEM_DOMAIN_ALIGN_SIZE), \ - section("data_smem_" #id "b"))) +/** + * @brief Name of the data section for a particular partition + * + * Useful for defining memory pools, or any other macro that takes a + * section name as a parameter. + * + * @param id Partition name + */ +#define K_APP_DMEM_SECTION(id) data_smem_##id##_data + +/** + * @brief Name of the bss section for a particular partition + * + * Useful for defining memory pools, or any other macro that takes a + * section name as a parameter. + * + * @param id Partition name + */ +#define K_APP_BMEM_SECTION(id) data_smem_##id##_bss /** * @brief Place data in a partition's data section @@ -43,8 +43,7 @@ * * @param id Name of the memory partition to associate this data */ -#define K_APP_DMEM(id) \ - __attribute__((section("data_smem_" #id))) +#define K_APP_DMEM(id) _GENERIC_SECTION(K_APP_DMEM_SECTION(id)) /** * @brief Place data in a partition's bss section @@ -54,35 +53,17 @@ * * @param id Name of the memory partition to associate this data */ -#define K_APP_BMEM(id) \ - __attribute__((section("data_smem_" #id "b"))) +#define K_APP_BMEM(id) _GENERIC_SECTION(K_APP_BMEM_SECTION(id)) -/* - * Creation of a struct to save start addresses, sizes, and - * a pointer to a k_mem_partition. It also adds a linked - * list node. - */ -struct app_region { - char *dmem_start; - char *bmem_start; - u32_t smem_size; - struct k_mem_partition *partition; +struct z_app_region { + void *bss_start; + size_t bss_size; }; -/* - * Declares a partition and provides a function to add the - * partition to the linked list 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_val(name) ((u32_t)&data_smem_##name##_size) -#else -#define smem_size_declare(name) -#define smem_size_val(name) 0 -#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ +#define Z_APP_START(id) data_smem_##id##_start +#define Z_APP_SIZE(id) data_smem_##id##_size +#define Z_APP_BSS_START(id) data_smem_##id##_bss_start +#define Z_APP_BSS_SIZE(id) data_smem_##id##_bss_size /** * @brief Define an application memory partition with linker support @@ -97,21 +78,20 @@ struct app_region { * @param name Name of the k_mem_partition to declare */ #define K_APPMEM_PARTITION_DEFINE(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; \ + extern char Z_APP_START(name)[]; \ + extern char Z_APP_SIZE(name)[]; \ struct k_mem_partition name = { \ - .start = (u32_t) &data_smem_##name, \ + .start = (u32_t) &Z_APP_START(name), \ + .size = (u32_t) &Z_APP_SIZE(name), \ .attr = K_MEM_PARTITION_P_RW_U_RW \ }; \ + extern char Z_APP_BSS_START(name)[]; \ + extern char Z_APP_BSS_SIZE(name)[]; \ _GENERIC_SECTION(.app_regions.name) \ - struct app_region name##_region = { \ - .dmem_start = (char *)&data_smem_##name, \ - .bmem_start = (char *)&data_smem_##name##b, \ - .smem_size = smem_size_val(name), \ - .partition = &name \ - }; + struct z_app_region name##_region = { \ + .bss_start = &Z_APP_BSS_START(name), \ + .bss_size = (size_t) &Z_APP_BSS_SIZE(name) \ + }; \ + K_APP_BMEM(name) char name##_placeholder; #endif /* ZEPHYR_INCLUDE_APP_MEMORY_APP_MEMDOMAIN_H_ */ diff --git a/include/arch/arc/v2/linker.ld b/include/arch/arc/v2/linker.ld index 58d8fc48523..69d8300c47f 100644 --- a/include/arch/arc/v2/linker.ld +++ b/include/arch/arc/v2/linker.ld @@ -139,22 +139,12 @@ SECTIONS { #include #if defined(CONFIG_APP_SHARED_MEM) -#if defined(CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT) #define APP_SHARED_ALIGN MPU_MIN_SIZE_ALIGN - #include -#else - SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) - { - MPU_MIN_SIZE_ALIGN - _image_ram_start = .; - _app_smem_start = .; - APP_SMEM_SECTION() - MPU_MIN_SIZE_ALIGN - _app_smem_end = .; - } GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION) +#define SMEM_PARTITION_ALIGN MPU_ALIGN -#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ +#include + _image_ram_start = _app_smem_start; _app_smem_size = _app_smem_end - _app_smem_start; _app_smem_rom_start = LOADADDR(_APP_SMEM_SECTION_NAME); #endif /* CONFIG_APP_SHARED_MEM */ diff --git a/include/arch/arm/cortex_m/scripts/linker.ld b/include/arch/arm/cortex_m/scripts/linker.ld index 38e16a88620..9dc74e6db7c 100644 --- a/include/arch/arm/cortex_m/scripts/linker.ld +++ b/include/arch/arm/cortex_m/scripts/linker.ld @@ -411,22 +411,9 @@ SECTIONS #if defined(CONFIG_APP_SHARED_MEM) #define APP_SHARED_ALIGN . = ALIGN(_region_min_align); -#if defined(CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT) - #include -#else - SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) - { - APP_SHARED_ALIGN; - _app_smem_start = .; - APP_SMEM_SECTION() - /* Align the end of shared app mem section with the - * minimum granularity required by MPU. - */ - APP_SHARED_ALIGN; - _app_smem_end = .; +#define SMEM_PARTITION_ALIGN MPU_ALIGN - } GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION) -#endif /* CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT */ +#include _app_smem_size = _app_smem_end - _app_smem_start; _app_smem_rom_start = LOADADDR(_APP_SMEM_SECTION_NAME); diff --git a/include/arch/x86/linker.ld b/include/arch/x86/linker.ld index f40435f95fa..9e4516f0504 100644 --- a/include/arch/x86/linker.ld +++ b/include/arch/x86/linker.ld @@ -203,26 +203,28 @@ SECTIONS __gcov_bss_size = __gcov_bss_end - __gcov_bss_start; #endif /* CONFIG_COVERAGE_GCOV */ +#ifdef CONFIG_APP_SHARED_MEM /* APP SHARED MEMORY REGION */ - SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) - { - _image_ram_start = .; - _app_smem_start = .; - APP_SMEM_SECTION() - MMU_PAGE_ALIGN - _app_smem_end = .; - } GROUP_DATA_LINK_IN(RAMABLE_REGION, RAMABLE_REGION) +#define SMEM_PARTITION_ALIGN(size) MMU_PAGE_ALIGN +#define APP_SHARED_ALIGN MMU_PAGE_ALIGN +#include + + _image_ram_start = _app_smem_start; _app_smem_size = _app_smem_end - _app_smem_start; _app_smem_num_words = _app_smem_size >> 2; _app_smem_rom_start = LOADADDR(_APP_SMEM_SECTION_NAME); - + _app_smem_num_words = _app_smem_size >> 2; +#endif /* CONFIG_APP_SHARED_MEM */ #ifdef CONFIG_APPLICATION_MEMORY SECTION_DATA_PROLOGUE(_APP_DATA_SECTION_NAME, (OPTIONAL),) { #ifndef CONFIG_XIP MMU_PAGE_ALIGN +#endif +#if !defined(CONFIG_APP_SHARED_MEM) + _image_ram_start = .; #endif __app_ram_start = .; __app_data_ram_start = .; @@ -258,7 +260,9 @@ SECTIONS SECTION_PROLOGUE(_BSS_SECTION_NAME, (NOLOAD OPTIONAL),) { MMU_PAGE_ALIGN - +#if !defined(CONFIG_APP_SHARED_MEM) && !defined(CONFIG_APPLICATION_MEMORY) + _image_ram_start = .; +#endif /* * For performance, BSS section is forced to be both 4 byte aligned and * a multiple of 4 bytes. diff --git a/scripts/gen_app_partitions.py b/scripts/gen_app_partitions.py index b8b407c5a29..6efc0fd3d40 100644 --- a/scripts/gen_app_partitions.py +++ b/scripts/gen_app_partitions.py @@ -13,15 +13,20 @@ from elf_helper import ElfHelper from elftools.elf.elffile import ELFFile -# This script will create linker comands for power of two aligned MPU -# when APP_SHARED_MEM is enabled. +# This script will create sections and linker variables to place the +# application shared memory partitions. +# these are later read by the macros defined in app_memdomain.h for +# initialization purpose when APP_SHARED_MEM is enabled. print_template = """ /* Auto generated code do not modify */ - MPU_ALIGN(data_smem_{0}b_end - data_smem_{0}); - data_smem_{0} = .; - KEEP(*(SORT(data_smem_{0}*))) - MPU_ALIGN(data_smem_{0}b_end - data_smem_{0}); - data_smem_{0}b_end = .; + SMEM_PARTITION_ALIGN(data_smem_{0}_bss_end - data_smem_{0}_start); + data_smem_{0}_start = .; + KEEP(*(data_smem_{0}_data)) + data_smem_{0}_bss_start = .; + KEEP(*(data_smem_{0}_bss)) + SMEM_PARTITION_ALIGN(data_smem_{0}_bss_end - data_smem_{0}_start); + data_smem_{0}_bss_end = .; + data_smem_{0}_end = .; """ linker_start_seq = """ SECTION_PROLOGUE(_APP_SMEM_SECTION_NAME, (OPTIONAL),) @@ -31,15 +36,17 @@ linker_start_seq = """ """ linker_end_seq = """ - _app_smem_end = .; APP_SHARED_ALIGN; + _app_smem_end = .; } GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION) """ size_cal_string = """ - data_smem_{0}_size = data_smem_{0}b_end - data_smem_{0}; + data_smem_{0}_size = data_smem_{0}_end - data_smem_{0}_start; + data_smem_{0}_bss_size = data_smem_{0}_bss_end - data_smem_{0}_bss_start; """ +section_regex = re.compile(r'data_smem_([A-Za-z0-9_]*)_(data|bss)') def find_partitions(filename, full_list_of_partitions, partitions_source_file): with open(filename, 'rb') as f: @@ -48,22 +55,19 @@ def find_partitions(filename, full_list_of_partitions, partitions_source_file): print("Error parsing file: ",filename) os.exit(1) - sections = [ x for x in full_lib.iter_sections()] + sections = [x for x in full_lib.iter_sections()] for section in sections: - if ("smem" in section.name and not ".rel" in section.name): - partition_name = section.name.split("data_smem_")[1] - if partition_name not in full_list_of_partitions: - full_list_of_partitions.append(partition_name) - if args.verbose: - partitions_source_file.update({partition_name: filename}) + m = section_regex.match(section.name) + if not m: + continue + + partition_name = m.groups()[0] + if partition_name not in full_list_of_partitions: + full_list_of_partitions.append(partition_name) + if args.verbose: + partitions_source_file.update({partition_name: filename}) - return( full_list_of_partitions, partitions_source_file) - -def cleanup_remove_bss_regions(full_list_of_partitions): - for partition in full_list_of_partitions: - if (partition+"b" in full_list_of_partitions): - full_list_of_partitions.remove(partition+"b") - return full_list_of_partitions + return (full_list_of_partitions, partitions_source_file) def generate_final_linker(linker_file, full_list_of_partitions): string = linker_start_seq @@ -105,11 +109,11 @@ def main(): fullname = os.path.join(dirpath, filename) full_list_of_partitions, partitions_source_file = find_partitions(fullname, full_list_of_partitions, partitions_source_file) - full_list_of_partitions = cleanup_remove_bss_regions(full_list_of_partitions) generate_final_linker(linker_file, full_list_of_partitions) if args.verbose: - print("Partitions retrieved: PARTITION, FILENAME") - print([key + " "+ partitions_source_file[key] for key in full_list_of_partitions]) + print("Partitions retrieved:") + for key in full_list_of_partitions: + print(" %s: %s\n", key, partitions_source_file[key]) if __name__ == '__main__': main() diff --git a/subsys/app_memory/app_memdomain.c b/subsys/app_memory/app_memdomain.c index 200b91690a1..53a9c713980 100644 --- a/subsys/app_memory/app_memdomain.c +++ b/subsys/app_memory/app_memdomain.c @@ -7,37 +7,18 @@ extern char __app_shmem_regions_start[]; extern char __app_shmem_regions_end[]; -static int app_shmem_setup(struct device *unused) +static int app_shmem_bss_zero(struct device *unused) { - struct app_region *region, *end; - size_t bss_size, data_size; + struct z_app_region *region, *end; - end = (struct app_region *)&__app_shmem_regions_end; - region = (struct app_region *)&__app_shmem_regions_start; + end = (struct z_app_region *)&__app_shmem_regions_end; + region = (struct z_app_region *)&__app_shmem_regions_start; for ( ; region < end; region++) { - /* Determine bounds and set partition appropriately */ -#ifndef CONFIG_MPU_REQUIRES_POWER_OF_TWO_ALIGNMENT - data_size = region->bmem_start - region->dmem_start; - if (region == end - 1) { - bss_size = _app_smem_end - region->bmem_start; - } else { - struct app_region *next = region + 1; - - __ASSERT_NO_MSG(region->bmem_start < next->dmem_start); - bss_size = next->dmem_start - region->bmem_start; - } -#else - data_size = region->bmem_start - region->dmem_start; - bss_size = region->smem_size - data_size; -#endif - region->partition->size = data_size + bss_size; - - /* Zero out BSS area of each partition */ - (void)memset(region->bmem_start, 0, bss_size); + (void)memset(region->bss_start, 0, region->bss_size); } return 0; } -SYS_INIT(app_shmem_setup, APPLICATION, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT); +SYS_INIT(app_shmem_bss_zero, APPLICATION, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT);