From d78269ffc160b5b6dd92720fb7f7e6bd401ba881 Mon Sep 17 00:00:00 2001 From: Ralf Schlatterbeck Date: Fri, 13 May 2016 16:01:10 +0200 Subject: [PATCH] Working wallclock example .. and cron probably would work if we had something to switch on/off for testing. --- examples/osd/ico-wallclock-time/Makefile | 15 +- examples/osd/ico-wallclock-time/icosoc.cfg | 3 + .../osd/ico-wallclock-time/riscv_flash.ld | 236 ++++++++++++++++++ examples/osd/ico-wallclock-time/wallclock.c | 28 +-- 4 files changed, 263 insertions(+), 19 deletions(-) create mode 100644 examples/osd/ico-wallclock-time/riscv_flash.ld diff --git a/examples/osd/ico-wallclock-time/Makefile b/examples/osd/ico-wallclock-time/Makefile index e9303810f..17bfe29eb 100644 --- a/examples/osd/ico-wallclock-time/Makefile +++ b/examples/osd/ico-wallclock-time/Makefile @@ -16,15 +16,16 @@ all: wallclock.$(TARGET) $(PLATFORM_FILES) CONTIKI=../../.. CFLAGS += -DPROJECT_CONF_H=\"project-conf.h\" +LDFLAGS += -T riscv_flash.ld -#FIXME PROJECTDIRS += $(REST_RESOURCES_DIR) $(REST_RESOURCES_DIR_COMMON) -#FIXME PROJECT_SOURCEFILES += $(REST_RESOURCES_FILES) +PROJECTDIRS += $(REST_RESOURCES_DIR) $(REST_RESOURCES_DIR_COMMON) +PROJECT_SOURCEFILES += $(REST_RESOURCES_FILES) PROJECT_SOURCEFILES += icosoc.c # REST Engine shall use Erbium CoAP implementation -#FIXME APPS += er-coap -#FIXME APPS += rest-engine -#FIXME APPS += json json-resource time +APPS += er-coap +APPS += rest-engine +APPS += json json-resource time CONTIKI_WITH_IPV6 = 1 include $(CONTIKI)/Makefile.include @@ -39,3 +40,7 @@ icosoc.mk: icosoc.cfg include icosoc.mk CLEAN += appimage.hex wallclock.$(TARGET) -include *.d + +flash-run: reset_boot + +flash: prog_flash diff --git a/examples/osd/ico-wallclock-time/icosoc.cfg b/examples/osd/ico-wallclock-time/icosoc.cfg index 7afbcab2d..51878f4ca 100644 --- a/examples/osd/ico-wallclock-time/icosoc.cfg +++ b/examples/osd/ico-wallclock-time/icosoc.cfg @@ -1,6 +1,9 @@ # enable compressed ISA support compressed_isa +# enable code in flash +flashpmem + # Digilent PmodUSBUART on PMOD3 # http://store.digilentinc.com/pmodusbuart-usb-to-uart-interface/ mod rs232 ser0 diff --git a/examples/osd/ico-wallclock-time/riscv_flash.ld b/examples/osd/ico-wallclock-time/riscv_flash.ld new file mode 100644 index 000000000..f6e06ced4 --- /dev/null +++ b/examples/osd/ico-wallclock-time/riscv_flash.ld @@ -0,0 +1,236 @@ +/*======================================================================*/ +/* Default maven linker script */ +/*======================================================================*/ +/* This is the default linker script for maven. It is based off of the + mips idt32.ld linker script. I have added many more comments and + tried to clean things up a bit. For more information about standard + MIPS sections see Section 9.5 of "See MIPS Run Linux" by Dominic + Sweetman. For more generic information about the init, fini, ctors, + and dtors sections see the paper titled "ELF From the Programmers + Perspective" by Hongiu Lu. */ + +/*----------------------------------------------------------------------*/ +/* Setup */ +/*----------------------------------------------------------------------*/ + +/* The OUTPUT_ARCH command specifies the machine architecture where the + argument is one of the names used in the BFD library. More + specifically one of the entires in bfd/cpu-mips.c */ + +OUTPUT_ARCH( "riscv" ) + +/* The ENTRY command specifies the entry point (ie. first instruction to + execute). The symbol _start is defined in crt0.S */ + +ENTRY( _start ) + +/* The GROUP command is special since the listed archives will be + searched repeatedly until there are no new undefined references. We + need this since -lc depends on -lgloss and -lgloss depends on -lc. I + thought gcc would automatically include -lgcc when needed, but + idt32.ld includes it explicitly here and I was seeing link errors + without it. */ + +GROUP( -lc -lgloss -lgcc ) + +/*----------------------------------------------------------------------*/ +/* Sections */ +/*----------------------------------------------------------------------*/ +/* This is where we specify how the input sections map to output + sections. The .= commands set the location counter, and the + sections are inserted in increasing address order according to the + location counter. The following statement will take all of the .bar + input sections and reloate them into the .foo output section which + starts at address 0x1000. + + . = 0.x1000; + .foo : { *(.bar) } + + If we wrap an input specification with a KEEP command then it + prevents it from being eliminted during "link-time garbage + collection". I'm not sure what this is, so I just followed what was + done in idt32.ld. + + We can also set a global external symbol to a specific address in the + output binary with this syntax: + + _etext = .; + PROVIDE( etext = . ); + + This will set the global symbol _ftext to the current location. If we + wrap this in a PROVIDE commad, the symbol will only be set if it is + not defined. We do this with symbols which don't begin with an + underscore since technically in ansi C someone might have a function + with the same name (eg. etext). + + If we need to label the beginning of a section we need to make sure + that the linker doesn't insert an orphan section inbetween where we + set the symbol and the actual begining of the section. We can do that + by assigning the location dot to itself. + + . = . + _ftext = .; + .text : + { } + + */ + +SECTIONS +{ + /* Stuff in .text.sram is located in SRAM */ + . = 0x00010000; + .text.sram : { + *(.text.sram) + } + text_sram_end = .; + + /*--------------------------------------------------------------------*/ + /* Code and read-only segment */ + /*--------------------------------------------------------------------*/ + + /* Begining of code and text segment */ + /* In "flashpmem" mode everything above 1MB in the flash is */ + /* mapped directly into the processor address space */ + . = 0x00100000; + _ftext = .; + PROVIDE( eprol = . ); + + /* text: Program code section */ + .text : + { + *(.text) + *(.text.*) + *(.gnu.linkonce.t.*) + } + + /* init: Code to execute before main (called by crt0.S) */ + .init : + { + KEEP( *(.init) ) + } + + /* fini: Code to execute after main (called by crt0.S) */ + .fini : + { + KEEP( *(.fini) ) + } + + /* rodata: Read-only data */ + .rodata : + { + *(.rdata) + *(.rodata) + *(.rodata.*) + *(.gnu.linkonce.r.*) + } + + /* End of code and read-only segment */ + PROVIDE( etext = . ); + _etext = .; + + /*--------------------------------------------------------------------*/ + /* Global constructor/destructor segement */ + /*--------------------------------------------------------------------*/ + + .preinit_array : + { + PROVIDE_HIDDEN (__preinit_array_start = .); + KEEP (*(.preinit_array)) + PROVIDE_HIDDEN (__preinit_array_end = .); + } + + .init_array : + { + PROVIDE_HIDDEN (__init_array_start = .); + KEEP (*(SORT(.init_array.*))) + KEEP (*(.init_array )) + PROVIDE_HIDDEN (__init_array_end = .); + } + + .fini_array : + { + PROVIDE_HIDDEN (__fini_array_start = .); + KEEP (*(SORT(.fini_array.*))) + KEEP (*(.fini_array )) + PROVIDE_HIDDEN (__fini_array_end = .); + } + + /*--------------------------------------------------------------------*/ + /* Other misc gcc segments (this was in idt32.ld) */ + /*--------------------------------------------------------------------*/ + /* I am not quite sure about these sections but it seems they are for + C++ exception handling. I think .jcr is for "Java Class + Registration" but it seems to end up in C++ binaries as well. */ + + .eh_frame_hdr : { *(.eh_frame_hdr) } + .eh_frame : { KEEP( *(.eh_frame) ) } + .gcc_except_table : { *(.gcc_except_table) } + .jcr : { KEEP (*(.jcr)) } + + /*--------------------------------------------------------------------*/ + /* Initialized data segment */ + /*--------------------------------------------------------------------*/ + + /* everything below is goind to be in SRAM */ + . = text_sram_end; + + /* Start of initialized data segment */ + . = ALIGN(16); + _fdata = .; + + /* data: Writable data */ + .data : + { + *(.data) + *(.data.*) + *(.gnu.linkonce.d.*) + } + + /* End of initialized data segment */ + PROVIDE( edata = . ); + _edata = .; + + /* Have _gp point to middle of sdata/sbss to maximize displacement range */ + . = ALIGN(16); + _gp = . + 0x800; + + /* Writable small data segment */ + .sdata : + { + *(.sdata) + *(.sdata.*) + *(.srodata.*) + *(.gnu.linkonce.s.*) + } + + /*--------------------------------------------------------------------*/ + /* Uninitialized data segment */ + /*--------------------------------------------------------------------*/ + + /* Start of uninitialized data segment */ + . = ALIGN(8); + _fbss = .; + + /* Writable uninitialized small data segment */ + .sbss : + { + *(.sbss) + *(.sbss.*) + *(.gnu.linkonce.sb.*) + } + + /* bss: Uninitialized writeable data section */ + . = .; + _bss_start = .; + .bss : + { + *(.bss) + *(.bss.*) + *(.gnu.linkonce.b.*) + *(COMMON) + } + + /* End of uninitialized data segment (used by syscalls.c for heap) */ + PROVIDE( end = . ); + _end = ALIGN(8); +} diff --git a/examples/osd/ico-wallclock-time/wallclock.c b/examples/osd/ico-wallclock-time/wallclock.c index 56ed32b56..f975a9ffc 100644 --- a/examples/osd/ico-wallclock-time/wallclock.c +++ b/examples/osd/ico-wallclock-time/wallclock.c @@ -43,11 +43,11 @@ #include "contiki.h" #include "params.h" #include "contiki-net.h" -//FIXME#include "er-coap-engine.h" -//FIXME#include "xtime.h" -//FIXME#include "cron.h" -//FIXME#include "time_resource.h" -//FIXME#include "jsonparse.h" +#include "er-coap-engine.h" +#include "xtime.h" +#include "cron.h" +#include "time_resource.h" +#include "jsonparse.h" #include "icosoc.h" #define DEBUG 1 @@ -107,19 +107,19 @@ PROCESS_THREAD(wallclock, ev, data) /* Initialize the Hardware. */ hw_init (); /* Initialize the REST engine. */ - //FIXME rest_init_engine (); + rest_init_engine (); - //FIXME rest_activate_resource (&res_timestamp, "clock/timestamp"); - //FIXME rest_activate_resource (&res_timezone, "clock/timezone"); - //FIXME rest_activate_resource (&res_localtime, "clock/localtime"); - //FIXME rest_activate_resource (&res_utc, "clock/utc"); + rest_activate_resource (&res_timestamp, "clock/timestamp"); + rest_activate_resource (&res_timezone, "clock/timezone"); + rest_activate_resource (&res_localtime, "clock/localtime"); + rest_activate_resource (&res_utc, "clock/utc"); /* Register callback function(s) */ - //FIXME cron_register_command ("led_on", led_set, (void *)1); - //FIXME cron_register_command ("led_off", led_set, (void *)0); + cron_register_command ("led_on", led_set, (void *)1); + cron_register_command ("led_off", led_set, (void *)0); /* Allocate all cron entries and the necessary resources */ - //FIXME activate_cron_resources (); + activate_cron_resources (); /* Define application-specific events here. * We need to call cron every 30 seconds or so (at least once a @@ -132,7 +132,7 @@ PROCESS_THREAD(wallclock, ev, data) printf ("In while loop: %08lx%08lx\n", (uint32_t)(cl>>32), (uint32_t)cl); PROCESS_WAIT_EVENT(); if (etimer_expired (&loop_periodic_timer)) { - //cron (); + cron (); etimer_reset (&loop_periodic_timer); } } /* while (1) */