diff options
author | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2015-10-19 08:44:33 +0200 |
---|---|---|
committer | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2015-10-19 09:51:28 +0200 |
commit | e29f1f551cce4a4660895535a8e22fbb8059670d (patch) | |
tree | 38e55b79b01994bf811893cb777737ba467e2801 /c | |
parent | libfdt: Merge into librtemscpu (diff) | |
download | rtems-e29f1f551cce4a4660895535a8e22fbb8059670d.tar.bz2 |
bsp/qoriq: Use U-Boot provided FDT
Diffstat (limited to 'c')
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/Makefile.am | 2 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/README | 13 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/configure.ac | 38 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/preinstall.am | 4 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/start/start.S | 4 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/startup/bspsmp.c | 98 | ||||
-rw-r--r-- | c/src/lib/libbsp/powerpc/qoriq/startup/bspstart.c | 57 | ||||
-rw-r--r-- | c/src/lib/libbsp/shared/include/fatal.h | 5 | ||||
-rw-r--r-- | c/src/lib/libbsp/shared/include/fdt.h | 30 | ||||
-rw-r--r-- | c/src/lib/libbsp/shared/src/bsp-fdt.c | 59 |
10 files changed, 268 insertions, 42 deletions
diff --git a/c/src/lib/libbsp/powerpc/qoriq/Makefile.am b/c/src/lib/libbsp/powerpc/qoriq/Makefile.am index dea5964042..e77c32d1a9 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/Makefile.am +++ b/c/src/lib/libbsp/powerpc/qoriq/Makefile.am @@ -22,6 +22,7 @@ include_bsp_HEADERS = include/irq.h \ ../../shared/include/irq-generic.h \ ../../shared/include/irq-info.h \ ../../shared/include/bootcard.h \ + ../../shared/include/fdt.h \ ../../shared/include/u-boot.h \ ../../shared/include/utility.h \ ../shared/include/u-boot-board-info.h \ @@ -63,6 +64,7 @@ libbsp_a_SOURCES += ../../shared/bsplibc.c \ ../../shared/gnatinstallhandler.c \ ../../shared/bspclean.c \ ../../shared/bspgetworkarea.c \ + ../../shared/src/bsp-fdt.c \ ../../shared/src/bsp-uboot-board-info.c \ ../shared/src/ppc-exc-handler-table.c \ ../shared/src/tictac.c \ diff --git a/c/src/lib/libbsp/powerpc/qoriq/README b/c/src/lib/libbsp/powerpc/qoriq/README index bf8335469d..1a6794b851 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/README +++ b/c/src/lib/libbsp/powerpc/qoriq/README @@ -2,4 +2,15 @@ Board support package for the Freescale QorIQ platform: http://en.wikipedia.org/wiki/QorIQ -Development board P1020RDB. +Development boards P1020RDB, T2080RDB and T4240RDB. + +For the T series boot via U-Boot is mandatory since the FDT is used. Use + + mkimage -A ppc -O linux -T kernel -a 0x4000 -e 0x4000 -n RTEMS -d app.bin.gz app.img + +to create a bootable image. You must use the "linux" image type. Boot it for +example via the + + bootm 0xe9000000 - 0xe8800000 + +U-Boot command. diff --git a/c/src/lib/libbsp/powerpc/qoriq/configure.ac b/c/src/lib/libbsp/powerpc/qoriq/configure.ac index 3cf8547d5b..466ddaf68d 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/configure.ac +++ b/c/src/lib/libbsp/powerpc/qoriq/configure.ac @@ -52,38 +52,48 @@ RTEMS_BSPOPTS_HELP([BSP_CONSOLE_BAUD],[default baud for console and other serial RTEMS_BSPOPTS_SET([BSP_USE_UART_INTERRUPTS],[*],[1]) RTEMS_BSPOPTS_HELP([BSP_USE_UART_INTERRUPTS],[enable usage of interrupts for the UART modules]) +RTEMS_BSPOPTS_SET([U_BOOT_USE_FDT],[qoriq_t*],[1]) +RTEMS_BSPOPTS_SET([U_BOOT_USE_FDT],[*],[]) +RTEMS_BSPOPTS_HELP([U_BOOT_USE_FDT],[enables U-Boot support using FDT]) + +RTEMS_BSPOPTS_SET([BSP_FDT_BLOB_SIZE_MAX],[qoriq_t*],[131072]) +RTEMS_BSPOPTS_SET([BSP_FDT_BLOB_SIZE_MAX],[*],[]) +RTEMS_BSPOPTS_HELP([BSP_FDT_BLOB_SIZE_MAX],[maximum size of the FDT blob in bytes]) + +RTEMS_BSPOPTS_SET([BSP_FDT_BLOB_READ_ONLY],[qoriq_t*],[1]) +RTEMS_BSPOPTS_SET([BSP_FDT_BLOB_READ_ONLY],[*],[]) +RTEMS_BSPOPTS_HELP([BSP_FDT_BLOB_READ_ONLY],[place the FDT blob into the read-only data area]) + +RTEMS_BSPOPTS_SET([HAS_UBOOT],[qoriq_t*],[]) RTEMS_BSPOPTS_SET([HAS_UBOOT],[*],[1]) -RTEMS_BSPOPTS_HELP([HAS_UBOOT],[enables U-Boot support]) +RTEMS_BSPOPTS_HELP([HAS_UBOOT],[enables legacy U-Boot support without FDT]) RTEMS_BSPOPTS_SET([U_BOOT_64_BIT_PHYS_SIZE],[qoriq_t*],[1]) RTEMS_BSPOPTS_SET([U_BOOT_64_BIT_PHYS_SIZE],[*],[]) -RTEMS_BSPOPTS_HELP([U_BOOT_64_BIT_PHYS_SIZE],[if defined, then use uint64_t for phys_size_t]) +RTEMS_BSPOPTS_HELP([U_BOOT_64_BIT_PHYS_SIZE],[if defined, then use uint64_t for phys_size_t (only used by legacy U-Boot support)]) RTEMS_BSPOPTS_SET([U_BOOT_GENERIC_BOARD_INFO],[qoriq_t*],[1]) RTEMS_BSPOPTS_SET([U_BOOT_GENERIC_BOARD_INFO],[*],[]) -RTEMS_BSPOPTS_HELP([U_BOOT_GENERIC_BOARD_INFO],[if defined, then use the generic bd_t structure]) +RTEMS_BSPOPTS_HELP([U_BOOT_GENERIC_BOARD_INFO],[if defined, then use the generic bd_t structure (only used by legacy U-Boot support)]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_BEGIN],[qoriq_p2020*],[0x3fff0000]) -RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_BEGIN],[qoriq_t2080*],[0x7fef4000]) -RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_BEGIN],[qoriq_t4240*],[0x7ff33000]) +RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_BEGIN],[qoriq_t*],[]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_BEGIN],[*],[0x1fff0000]) -RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_BEGIN],[the begin address of the boot page set up by U-Boot]) +RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_BEGIN],[the begin address of the boot page set up by U-Boot (only used by legacy U-Boot support)]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_LAST],[qoriq_p2020*],[0x3fffffff]) -RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_LAST],[qoriq_t2080*],[0x7fef4fff]) -RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_LAST],[qoriq_t4240*],[0x7ff33fff]) +RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_LAST],[qoriq_t*],[]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_LAST],[*],[0x1fffffff]) -RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_LAST],[the last address of the boot page set up by U-Boot]) +RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_LAST],[the last address of the boot page set up by U-Boot (only used by legacy U-Boot support)]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[qoriq_p2020*],[0xf240]) -RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[qoriq_t*],[0x0200]) +RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[qoriq_t*],[]) RTEMS_BSPOPTS_SET([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[*],[0xf2a0]) -RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[the offset to the spin table in the boot page set up by U-Boot]) +RTEMS_BSPOPTS_HELP([U_BOOT_BOOT_PAGE_SPIN_OFFSET],[the offset to the spin table in the boot page set up by U-Boot (only used by legacy U-Boot support)]) -RTEMS_BSPOPTS_SET([QORIQ_CPU_COUNT],[qoriq_t2080*],[8]) -RTEMS_BSPOPTS_SET([QORIQ_CPU_COUNT],[qoriq_t4240*],[24]) +RTEMS_BSPOPTS_SET([QORIQ_CPU_COUNT],[qoriq_t*],[24]) RTEMS_BSPOPTS_SET([QORIQ_CPU_COUNT],[*],[2]) -RTEMS_BSPOPTS_HELP([QORIQ_CPU_COUNT],[virtual processor count]) +RTEMS_BSPOPTS_HELP([QORIQ_CPU_COUNT],[maximum virtual processor count]) RTEMS_BSPOPTS_SET([QORIQ_THREAD_COUNT],[qoriq_t*],[2]) RTEMS_BSPOPTS_SET([QORIQ_THREAD_COUNT],[*],[1]) diff --git a/c/src/lib/libbsp/powerpc/qoriq/preinstall.am b/c/src/lib/libbsp/powerpc/qoriq/preinstall.am index 484821b5d5..6a08135b33 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/preinstall.am +++ b/c/src/lib/libbsp/powerpc/qoriq/preinstall.am @@ -69,6 +69,10 @@ $(PROJECT_INCLUDE)/bsp/bootcard.h: ../../shared/include/bootcard.h $(PROJECT_INC $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/bootcard.h PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/bootcard.h +$(PROJECT_INCLUDE)/bsp/fdt.h: ../../shared/include/fdt.h $(PROJECT_INCLUDE)/bsp/$(dirstamp) + $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/fdt.h +PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/fdt.h + $(PROJECT_INCLUDE)/bsp/u-boot.h: ../../shared/include/u-boot.h $(PROJECT_INCLUDE)/bsp/$(dirstamp) $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/u-boot.h PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/u-boot.h diff --git a/c/src/lib/libbsp/powerpc/qoriq/start/start.S b/c/src/lib/libbsp/powerpc/qoriq/start/start.S index c6fef7d2a7..4499850b5b 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/start/start.S +++ b/c/src/lib/libbsp/powerpc/qoriq/start/start.S @@ -56,6 +56,10 @@ _start: bl bsp_uboot_copy_board_info #endif /* HAS_UBOOT */ +#ifdef U_BOOT_USE_FDT + bl bsp_fdt_copy +#endif /* U_BOOT_USE_FDT */ + /* Get start stack */ LWI START_STACK, start_stack_end diff --git a/c/src/lib/libbsp/powerpc/qoriq/startup/bspsmp.c b/c/src/lib/libbsp/powerpc/qoriq/startup/bspsmp.c index 8952d3e809..119d3f023a 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/startup/bspsmp.c +++ b/c/src/lib/libbsp/powerpc/qoriq/startup/bspsmp.c @@ -14,9 +14,12 @@ #include <rtems/score/smpimpl.h> +#include <libfdt.h> + #include <libcpu/powerpc-utility.h> #include <bsp.h> +#include <bsp/fdt.h> #include <bsp/mmu.h> #include <bsp/fatal.h> #include <bsp/qoriq.h> @@ -41,13 +44,15 @@ void _start_secondary_processor(void); #define TLB_COUNT (TLB_END - TLB_BEGIN) -/* - * These values can be obtained with the debugger or a look into the - * U-Boot sources (arch/powerpc/cpu/mpc85xx/release.S). - */ -#define BOOT_BEGIN U_BOOT_BOOT_PAGE_BEGIN -#define BOOT_LAST U_BOOT_BOOT_PAGE_LAST -#define SPIN_TABLE (BOOT_BEGIN + U_BOOT_BOOT_PAGE_SPIN_OFFSET) +#ifdef HAS_UBOOT + /* + * These values can be obtained with the debugger or a look into the U-Boot + * sources (arch/powerpc/cpu/mpc85xx/release.S). + */ + #define BOOT_BEGIN U_BOOT_BOOT_PAGE_BEGIN + #define BOOT_LAST U_BOOT_BOOT_PAGE_LAST + #define SPIN_TABLE (BOOT_BEGIN + U_BOOT_BOOT_PAGE_SPIN_OFFSET) +#endif typedef struct { uint32_t addr_upper; @@ -138,16 +143,71 @@ static void bsp_inter_processor_interrupt(void *arg) _SMP_Inter_processor_interrupt_handler(); } +#ifdef U_BOOT_USE_FDT +static uboot_spin_table *spin_table_addr[QORIQ_CPU_COUNT / QORIQ_THREAD_COUNT]; +#endif + +static uint32_t discover_processors(uint32_t *boot_begin, uint32_t *boot_last) +{ +#if defined(HAS_UBOOT) + *boot_begin = BOOT_BEGIN; + *boot_last = BOOT_LAST; + + return QORIQ_CPU_COUNT; +#elif defined(U_BOOT_USE_FDT) + const void *fdt = bsp_fdt_get(); + int cpus = fdt_path_offset(fdt, "/cpus"); + int node = fdt_first_subnode(fdt, cpus); + uint32_t cpu = 0; + uintptr_t last = 0; + uintptr_t begin = last - 1; + + while (node >= 0) { + int len; + fdt64_t *addr_fdt = (fdt64_t *) + fdt_getprop(fdt, node, "cpu-release-addr", &len); + + if (addr_fdt != NULL && cpu < RTEMS_ARRAY_SIZE(spin_table_addr)) { + uintptr_t addr = (uintptr_t) fdt64_to_cpu(*addr_fdt); + + if (addr < begin) { + begin = addr; + } + + if (addr > last) { + last = addr; + } + + spin_table_addr[cpu] = (uboot_spin_table *) addr; + ++cpu; + } + + node = fdt_next_subnode(fdt, node); + } + + *boot_begin = begin; + *boot_last = last; + + return cpu * QORIQ_THREAD_COUNT; +#endif +} + uint32_t _CPU_SMP_Initialize(void) { + uint32_t cpu_count = 1; + if (rtems_configuration_get_maximum_processors() > 0) { qoriq_mmu_context mmu_context; + uint32_t boot_begin; + uint32_t boot_last; + + cpu_count = discover_processors(&boot_begin, &boot_last); qoriq_mmu_context_init(&mmu_context); qoriq_mmu_add( &mmu_context, - BOOT_BEGIN, - BOOT_LAST, + boot_begin, + boot_last, 0, 0, FSL_EIS_MAS3_SR | FSL_EIS_MAS3_SW, @@ -159,7 +219,7 @@ uint32_t _CPU_SMP_Initialize(void) start_thread_if_necessary(0); - return QORIQ_CPU_COUNT; + return cpu_count; } static void release_processor(uboot_spin_table *spin_table, uint32_t cpu_index) @@ -175,12 +235,24 @@ static void release_processor(uboot_spin_table *spin_table, uint32_t cpu_index) rtems_cache_flush_multiple_data_lines(spin_table, sizeof(*spin_table)); } +static uboot_spin_table *get_spin_table(uint32_t cpu_index) +{ +#if defined(HAS_UBOOT) +#if QORIQ_THREAD_COUNT > 1 + return &((uboot_spin_table *) SPIN_TABLE)[cpu_index / 2 - 1]; +#else + return (uboot_spin_table *) SPIN_TABLE; +#endif +#elif defined(U_BOOT_USE_FDT) + return spin_table_addr[cpu_index / 2]; +#endif +} + bool _CPU_SMP_Start_processor(uint32_t cpu_index) { #if QORIQ_THREAD_COUNT > 1 if (is_started_by_u_boot(cpu_index)) { - uboot_spin_table *spin_table = - &((uboot_spin_table *) SPIN_TABLE)[cpu_index / 2 - 1]; + uboot_spin_table *spin_table = get_spin_table(cpu_index); release_processor(spin_table, cpu_index); @@ -189,7 +261,7 @@ bool _CPU_SMP_Start_processor(uint32_t cpu_index) return _SMP_Should_start_processor(cpu_index - 1); } #else - uboot_spin_table *spin_table = (uboot_spin_table *) SPIN_TABLE; + uboot_spin_table *spin_table = get_spin_table(cpu_index); release_processor(spin_table, cpu_index); diff --git a/c/src/lib/libbsp/powerpc/qoriq/startup/bspstart.c b/c/src/lib/libbsp/powerpc/qoriq/startup/bspstart.c index 5f8f25bf5a..1f9308112c 100644 --- a/c/src/lib/libbsp/powerpc/qoriq/startup/bspstart.c +++ b/c/src/lib/libbsp/powerpc/qoriq/startup/bspstart.c @@ -7,10 +7,10 @@ */ /* - * Copyright (c) 2010-2012 embedded brains GmbH. All rights reserved. + * Copyright (c) 2010-2015 embedded brains GmbH. All rights reserved. * * embedded brains GmbH - * Obere Lagerstr. 30 + * Dornierstr. 4 * 82178 Puchheim * Germany * <rtems@embedded-brains.de> @@ -20,6 +20,8 @@ * http://www.rtems.org/license/LICENSE. */ +#include <libfdt.h> + #include <rtems.h> #include <rtems/config.h> #include <rtems/counter.h> @@ -29,14 +31,16 @@ #include <libcpu/powerpc-utility.h> #include <bsp.h> -#include <bsp/vectors.h> #include <bsp/bootcard.h> +#include <bsp/console-termios.h> +#include <bsp/fatal.h> +#include <bsp/fdt.h> #include <bsp/irq-generic.h> -#include <bsp/u-boot.h> #include <bsp/linker-symbols.h> #include <bsp/mmu.h> #include <bsp/qoriq.h> -#include <bsp/console-termios.h> +#include <bsp/u-boot.h> +#include <bsp/vectors.h> LINKER_SYMBOL(bsp_exc_vector_base); @@ -86,7 +90,7 @@ void bsp_start(void) get_ppc_cpu_revision(); /* Initialize some device driver parameters */ - #ifdef HAS_UBOOT + #if defined(HAS_UBOOT) BSP_bus_frequency = bsp_uboot_board_info.bi_busfreq / QORIQ_BUS_CLOCK_DIVIDER; bsp_clicks_per_usec = BSP_bus_frequency / 8000000; @@ -97,7 +101,36 @@ void bsp_start(void) BSP_bus_frequency / 8 #endif ); - #endif /* HAS_UBOOT */ + #elif defined(U_BOOT_USE_FDT) + { + const void *fdt = bsp_fdt_get(); + int node; + int len; + fdt32_t *val_fdt; + + node = fdt_node_offset_by_prop_value(fdt, -1, "device_type", "cpu", 4); + + val_fdt = (fdt32_t *) fdt_getprop(fdt, node, "bus-frequency", &len); + if (val_fdt == NULL || len != 4) { + bsp_fatal(QORIQ_FATAL_FDT_NO_BUS_FREQUENCY); + } + BSP_bus_frequency = fdt32_to_cpu(*val_fdt) / QORIQ_BUS_CLOCK_DIVIDER; + + val_fdt = (fdt32_t *) fdt_getprop(fdt, node, "timebase-frequency", &len); + if (val_fdt == NULL || len != 4) { + bsp_fatal(QORIQ_FATAL_FDT_NO_BUS_FREQUENCY); + } + bsp_clicks_per_usec = fdt32_to_cpu(*val_fdt) / 1000000; + + #ifdef __PPC_CPU_E6500__ + val_fdt = (fdt32_t *) fdt_getprop(fdt, node, "clock-frequency", &len); + if (val_fdt == NULL || len != 4) { + bsp_fatal(QORIQ_FATAL_FDT_NO_CLOCK_FREQUENCY); + } + #endif + rtems_counter_initialize_converter(fdt32_to_cpu(*val_fdt)); + } + #endif /* Initialize some console parameters */ for (i = 0; i < console_device_count; ++i) { @@ -114,12 +147,10 @@ void bsp_start(void) ctx->clock = BSP_bus_frequency; - #ifdef HAS_UBOOT - #ifdef U_BOOT_GENERIC_BOARD_INFO - ctx->initial_baud = 115200; - #else - ctx->initial_baud = bsp_uboot_board_info.bi_baudrate; - #endif + #if defined(HAS_UBOOT) && !defined(U_BOOT_GENERIC_BOARD_INFO) + ctx->initial_baud = bsp_uboot_board_info.bi_baudrate; + #else + ctx->initial_baud = 115200; #endif } } diff --git a/c/src/lib/libbsp/shared/include/fatal.h b/c/src/lib/libbsp/shared/include/fatal.h index 45db9d43bd..d4cd50f517 100644 --- a/c/src/lib/libbsp/shared/include/fatal.h +++ b/c/src/lib/libbsp/shared/include/fatal.h @@ -114,7 +114,10 @@ typedef enum { ARM_FATAL_L2C_310_EXCLUSIVE_CONFIG, /* QorIQ fatal codes */ - QORIQ_FATAL_SMP_IPI_HANDLER_INSTALL = BSP_FATAL_CODE_BLOCK(10) + QORIQ_FATAL_SMP_IPI_HANDLER_INSTALL = BSP_FATAL_CODE_BLOCK(10), + QORIQ_FATAL_FDT_NO_BUS_FREQUENCY, + QORIQ_FATAL_FDT_NO_CLOCK_FREQUENCY, + QORIQ_FATAL_FDT_NO_TIMEBASE_FREQUENCY } bsp_fatal_code; RTEMS_COMPILER_NO_RETURN_ATTRIBUTE static inline void diff --git a/c/src/lib/libbsp/shared/include/fdt.h b/c/src/lib/libbsp/shared/include/fdt.h new file mode 100644 index 0000000000..a4c7df6dc1 --- /dev/null +++ b/c/src/lib/libbsp/shared/include/fdt.h @@ -0,0 +1,30 @@ +/* + * Copyright (c) 2015 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rtems@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +#ifndef LIBBSP_SHARED_FDT_H +#define LIBBSP_SHARED_FDT_H + +#ifdef __cplusplus +extern "C" { +#endif /* __cplusplus */ + +void bsp_fdt_copy(const void *src); + +const void *bsp_fdt_get(void); + +#ifdef __cplusplus +} +#endif /* __cplusplus */ + +#endif /* LIBBSP_SHARED_FDT_H */ diff --git a/c/src/lib/libbsp/shared/src/bsp-fdt.c b/c/src/lib/libbsp/shared/src/bsp-fdt.c new file mode 100644 index 0000000000..1b149d9aa3 --- /dev/null +++ b/c/src/lib/libbsp/shared/src/bsp-fdt.c @@ -0,0 +1,59 @@ +/* + * Copyright (c) 2015 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rtems@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +#include <sys/param.h> + +#include <libfdt.h> + +#include <bsp.h> +#include <bsp/fdt.h> +#include <bsp/linker-symbols.h> + +#ifndef BSP_FDT_BLOB_SIZE_MAX +#define BSP_FDT_BLOB_SIZE_MAX 0 +#endif + +#ifdef BSP_FDT_BLOB_READ_ONLY +static const uint32_t +bsp_fdt_blob[BSP_FDT_BLOB_SIZE_MAX / sizeof(uint32_t)] = { 0xdeadbeef }; +#else +static uint32_t +bsp_fdt_blob[BSP_FDT_BLOB_SIZE_MAX / sizeof(uint32_t)]; +#endif + +void bsp_fdt_copy(const void *src) +{ + const uint32_t *s = (const uint32_t *) src; +#ifdef BSP_FDT_BLOB_READ_ONLY + uint32_t *d = (uint32_t *) ((uintptr_t) &bsp_fdt_blob[0] + - (uintptr_t) bsp_section_rodata_begin + + (uintptr_t) bsp_section_rodata_load_begin); +#else + uint32_t *d = &bsp_fdt_blob[0]; +#endif + uint32_t m = MIN(sizeof(bsp_fdt_blob), fdt_totalsize(src)); + uint32_t n = (m + sizeof(*d) - 1) / sizeof(*d); + uint32_t i; + + for (i = 0; i < n; ++i) { + d[i] = s[i]; + } + + rtems_cache_flush_multiple_data_lines(d, m); +} + +const void *bsp_fdt_get(void) +{ + return &bsp_fdt_blob[0]; +} |