summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGaurav-Aggarwal-AWS <33462878+aggarg@users.noreply.github.com>2021-07-15 18:40:22 -0700
committerGitHub <noreply@github.com>2021-07-15 18:40:22 -0700
commit2fedeff3328346fcd97e8b8e68176e62a1ed7ff9 (patch)
treed8a4c6bb53d749ced89c8415f9a0f77ffb70ee1b
parentb550e6090d26a19dc72b390f64e7b6573c214ef1 (diff)
downloadfreertos-git-2fedeff3328346fcd97e8b8e68176e62a1ed7ff9.tar.gz
Update BSP and SDK for HiFive board (#645)
* Update BSP and SDK for HiFive board This commit also adds demo start and success/failure output messages.
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.cproject269
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.project606
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.settings/language.settings.xml40
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/FreeRTOSConfig.h207
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/SiFive_HiFive1_RTOS_demo.url10
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/blinky_demo/main_blinky.c394
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/README.md13
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/core.dts262
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.dts215
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.svd3169
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/atomic.h259
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/button.h16
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cache.h82
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/clock.h119
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/compiler.h15
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cpu.h138
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/csr.h32
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-clock.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-factor-clock.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_clint0.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_cpu.h269
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_plic0.h8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_buserror0.h184
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_ccache0.h140
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_clic0.h32
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_hfrosc.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_lfrosc.h21
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_prci.h8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fu540-c000_l2.h23
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-buttons.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-leds.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-switches.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio0.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_i2c0.h24
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_l2pf0.h78
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_local-external-interrupts0.h1
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_pwm0.h29
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_rtc0.h26
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_simuart0.h29
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_spi0.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_test0.h1
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_trace.h23
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_uart0.h9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_wdog0.h26
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/ucb_htif0.h48
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/gpio.h194
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/hpm.h146
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/i2c.h112
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/init.h130
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/interrupt.h520
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/io.h11
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/itim.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/led.h23
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lim.h20
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lock.h62
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine.h1056
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/inline.h285
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/platform.h95
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/memory.h40
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pmp.h40
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/privilege.h156
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pwm.h162
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/rtc.h137
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/scrub.h13
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/shutdown.h11
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/spi.h45
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/switch.h17
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/time.h21
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/timer.h5
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/tty.h16
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/uart.h149
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/watchdog.h168
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-inline.h285
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-platform.h95
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.default.lds508
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.freertos.lds327
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.h1056
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.ramrodata.lds306
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.scratchpad.lds294
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/settings.mk13
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.clang-format5
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.travis.yml35
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Doxyfile2537
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.Apache2202
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.MIT21
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.am238
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.in1443
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/README.md4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/aclocal.m41268
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/ar-lib270
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/build.wake150
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/compile347
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.guess1441
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.sub1813
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure5491
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure.ac97
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/depcomp791
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/doc/link_to_docs_in_github.url5
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/crt0.S90
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/nanosleep.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/synchronize_harts.c59
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_access.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chdir.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chmod.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chown.c10
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_clock_gettime.c60
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_close.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_execve.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_exit.c9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_faccessat.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fork.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstat.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstatat.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_ftime.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getcwd.c9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getpid.c6
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_gettimeofday.c7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_isatty.c6
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_kill.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_link.c7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lseek.c10
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lstat.c7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_open.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_openat.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_read.c10
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sbrk.c52
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_stat.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sysconf.c16
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_times.c75
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_unlink.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_utime.c8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_wait.c7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_write.c25
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-git-hooks9
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-sh508
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/m4/ax_check_compile_flag.m453
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/atomic.h259
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/button.h16
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cache.h54
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/clock.h52
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/compiler.h15
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cpu.h132
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/csr.h32
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-clock.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-factor-clock.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_clint0.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_cpu.h254
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_plic0.h8
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_buserror0.h184
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_ccache0.h141
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_clic0.h33
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_hfrosc.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_lfrosc.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_prci.h7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fu540-c000_l2.h23
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-buttons.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-leds.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-switches.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio0.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_i2c0.h24
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_l2pf0.h78
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_local-external-interrupts0.h1
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_pwm0.h29
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_rtc0.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_simuart0.h29
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_spi0.h2
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_test0.h1
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_uart0.h7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_wdog0.h4
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/ucb_htif0.h48
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/gpio.h103
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/hpm.h146
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/i2c.h112
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/init.h130
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/interrupt.h269
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/io.h9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/itim.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/led.h23
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lim.h20
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lock.h37
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/memory.h36
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pmp.h29
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/privilege.h154
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pwm.h162
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/rtc.h38
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/scrub.h13
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/shutdown.h11
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/spi.h31
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/switch.h17
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/time.h3
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/timer.h5
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/tty.h17
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/uart.h133
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/watchdog.h107
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/missing215
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/check-format19
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/format8
-rwxr-xr-xFreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/git-version21
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/atomic.c19
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/button.c12
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cache.c138
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/clock.c18
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cpu.c52
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-clock.c9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-factor-clock.c17
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/inline.c1
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_clint0.c259
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_cpu.c839
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_plic0.c345
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_buserror0.c257
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_ccache0.c322
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_clic0.c745
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfrosc.c26
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfxosc.c24
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_lfrosc.c30
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_pll.c348
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_prci.c7
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fu540-c000_l2.c84
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_global-external-interrupts0.c141
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-buttons.c26
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-leds.c47
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-switches.c26
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio0.c268
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_i2c0.c428
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_l2pf0.c164
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_local-external-interrupts0.c130
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_pwm0.c340
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_rtc0.c46
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_simuart0.c79
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_spi0.c203
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_test0.c12
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_trace.c9
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_uart0.c199
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_wdog0.c139
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/ucb_htif0.c128
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/entry.S48
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/gpio.c44
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/hpm.c345
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/i2c.c28
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/init.c72
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/interrupt.c99
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/led.c17
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/memory.c31
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pmp.c313
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/privilege.c90
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pwm.c36
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/rtc.c18
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/scrub.S132
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/shutdown.c14
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/spi.c13
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/switch.c11
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/synchronize_harts.c40
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/time.c18
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/timer.c71
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/trap.S15
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/tty.c47
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/uart.c33
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/watchdog.c37
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/RegTest.S532
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/main_full.c619
-rw-r--r--FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/main.c542
-rw-r--r--lexicon.txt1
263 files changed, 36586 insertions, 6658 deletions
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.cproject b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.cproject
index 648ec1c9f..baa18f1aa 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.cproject
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.cproject
@@ -1,176 +1,93 @@
-<?xml version="1.0" encoding="UTF-8" standalone="no"?>
-<?fileVersion 4.0.0?><cproject storage_type_id="org.eclipse.cdt.core.XmlProjectDescriptionStorage">
-
- <storageModule moduleId="org.eclipse.cdt.core.settings">
-
- <cconfiguration id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480">
-
- <storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" moduleId="org.eclipse.cdt.core.settings" name="Debug">
-
- <externalSettings/>
-
- <extensions>
-
- <extension id="org.eclipse.cdt.core.ELF" point="org.eclipse.cdt.core.BinaryParser"/>
-
- <extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
-
- <extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
-
- <extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
-
- <extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser"/>
-
- <extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
-
- </extensions>
-
- </storageModule>
-
- <storageModule moduleId="cdtBuildSystem" version="4.0.0">
-
- <configuration artifactName="${ProjName}" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe,org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug" cleanCommand="rm -rf" description="" id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" name="Debug" parent="cdt.managedbuild.config.gnu.cross.exe.debug">
-
- <folderInfo id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480." name="/" resourcePath="">
-
- <toolChain id="cdt.managedbuild.toolchain.gnu.cross.exe.debug.1023181676" name="Cross GCC" superClass="cdt.managedbuild.toolchain.gnu.cross.exe.debug">
-
- <option id="cdt.managedbuild.option.gnu.cross.path.2116215758" name="Path" superClass="cdt.managedbuild.option.gnu.cross.path" useByScannerDiscovery="false" value="${eclipse_home}/SiFive/riscv64-unknown-elf-gcc-8.3.0-2019.08.0/bin" valueType="string"/>
-
- <targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.ELF" id="cdt.managedbuild.targetPlatform.gnu.cross.1119183919" isAbstract="false" osList="all" superClass="cdt.managedbuild.targetPlatform.gnu.cross"/>
-
- <builder buildPath="${workspace_loc:/RTOSDemo}/Debug" id="cdt.managedbuild.builder.gnu.cross.1388532167" keepEnvironmentInBuildfile="false" managedBuildOn="true" name="Gnu Make Builder" parallelBuildOn="true" parallelizationNumber="optimal" superClass="cdt.managedbuild.builder.gnu.cross"/>
-
- <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.c.compiler.1469975065" name="Cross GCC Compiler" superClass="cdt.managedbuild.tool.gnu.cross.c.compiler">
-
- <option defaultValue="gnu.c.optimization.level.none" id="gnu.c.compiler.option.optimization.level.440219377" name="Optimization Level" superClass="gnu.c.compiler.option.optimization.level" useByScannerDiscovery="false" valueType="enumerated"/>
-
- <option id="gnu.c.compiler.option.debugging.level.1721555429" name="Debug Level" superClass="gnu.c.compiler.option.debugging.level" useByScannerDiscovery="false" value="gnu.c.debugging.level.max" valueType="enumerated"/>
-
- <option id="gnu.c.compiler.option.dialect.std.1648189865" name="Language standard" superClass="gnu.c.compiler.option.dialect.std" useByScannerDiscovery="true" value="gnu.c.compiler.dialect.default" valueType="enumerated"/>
-
- <option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="gnu.c.compiler.option.include.paths.1720192082" name="Include paths (-I)" superClass="gnu.c.compiler.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/include}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/full_demo/Common_Demo_Tasks/include}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/portable/GCC/RISC-V}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/include}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/freedom-metal}&quot;"/>
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/bsp/install/include}&quot;"/>
-
- </option>
-
- <option id="gnu.c.compiler.option.misc.other.257964774" name="Other flags" superClass="gnu.c.compiler.option.misc.other" useByScannerDiscovery="false" value="-c -fmessage-length=0 -march=rv32imac -mabi=ilp32 -mcmodel=medlow -ffunction-sections -fdata-sections --specs=nano.specs -Wno-unused-parameter" valueType="string"/>
-
- <option id="gnu.c.compiler.option.warnings.extrawarn.1802410957" name="Extra warnings (-Wextra)" superClass="gnu.c.compiler.option.warnings.extrawarn" useByScannerDiscovery="false" value="true" valueType="boolean"/>
-
- <inputType id="cdt.managedbuild.tool.gnu.c.compiler.input.1079251302" superClass="cdt.managedbuild.tool.gnu.c.compiler.input"/>
-
- </tool>
-
- <tool id="cdt.managedbuild.tool.gnu.cross.cpp.compiler.420742449" name="Cross G++ Compiler" superClass="cdt.managedbuild.tool.gnu.cross.cpp.compiler">
-
- <option id="gnu.cpp.compiler.option.optimization.level.1056760450" name="Optimization Level" superClass="gnu.cpp.compiler.option.optimization.level" useByScannerDiscovery="false" value="gnu.cpp.compiler.optimization.level.none" valueType="enumerated"/>
-
- <option id="gnu.cpp.compiler.option.debugging.level.52506316" name="Debug Level" superClass="gnu.cpp.compiler.option.debugging.level" useByScannerDiscovery="false" value="gnu.cpp.compiler.debugging.level.max" valueType="enumerated"/>
-
- </tool>
-
- <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.c.linker.558060359" name="Cross GCC Linker" superClass="cdt.managedbuild.tool.gnu.cross.c.linker">
-
- <option id="gnu.c.link.option.ldflags.46965227" name="Linker flags" superClass="gnu.c.link.option.ldflags" useByScannerDiscovery="false" value="-Xlinker --gc-sections -Wl,-Map,RTOSDemo.map -T../bsp/metal.default.lds -march=rv32imac -mabi=ilp32 -mcmodel=medlow -Wl,--start-group -lc -lgcc -Wl,--end-group --specs=nano.specs" valueType="string"/>
-
- <option id="gnu.c.link.option.nostart.1038463237" name="Do not use standard start files (-nostartfiles)" superClass="gnu.c.link.option.nostart" useByScannerDiscovery="false" value="true" valueType="boolean"/>
-
- <option id="gnu.c.link.option.nostdlibs.934043026" name="No startup or default libs (-nostdlib)" superClass="gnu.c.link.option.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
-
- <option id="gnu.c.link.option.nodeflibs.1095611620" name="Do not use default libraries (-nodefaultlibs)" superClass="gnu.c.link.option.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
-
- <inputType id="cdt.managedbuild.tool.gnu.c.linker.input.549526426" superClass="cdt.managedbuild.tool.gnu.c.linker.input">
-
- <additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
-
- <additionalInput kind="additionalinput" paths="$(LIBS)"/>
-
- </inputType>
-
- </tool>
-
- <tool id="cdt.managedbuild.tool.gnu.cross.cpp.linker.2105463183" name="Cross G++ Linker" superClass="cdt.managedbuild.tool.gnu.cross.cpp.linker"/>
-
- <tool id="cdt.managedbuild.tool.gnu.cross.archiver.424513814" name="Cross GCC Archiver" superClass="cdt.managedbuild.tool.gnu.cross.archiver"/>
-
- <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.assembler.825438707" name="Cross GCC Assembler" superClass="cdt.managedbuild.tool.gnu.cross.assembler">
-
- <option id="gnu.both.asm.option.flags.1946908814" name="Assembler flags" superClass="gnu.both.asm.option.flags" useByScannerDiscovery="false" value="-march=rv32imac -mabi=ilp32 -mcmodel=medlow -c -DportasmHANDLE_INTERRUPT=handle_trap -g3" valueType="string"/>
-
- <option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="gnu.both.asm.option.include.paths.1448234506" name="Include paths (-I)" superClass="gnu.both.asm.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
-
- <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/portable/GCC/RISC-V/chip_specific_extensions/RV32I_CLINT_no_extensions}&quot;"/>
-
- </option>
-
- <inputType id="cdt.managedbuild.tool.gnu.assembler.input.1723023894" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
-
- </tool>
-
- </toolChain>
-
- </folderInfo>
-
- <sourceEntries>
-
- <entry flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name=""/>
-
- </sourceEntries>
-
- </configuration>
-
- </storageModule>
-
- <storageModule moduleId="org.eclipse.cdt.core.externalSettings"/>
-
- </cconfiguration>
-
- </storageModule>
-
- <storageModule moduleId="cdtBuildSystem" version="4.0.0">
-
- <project id="RTOSDemo.cdt.managedbuild.target.gnu.cross.exe.1669036252" name="Executable" projectType="cdt.managedbuild.target.gnu.cross.exe"/>
-
- </storageModule>
-
- <storageModule moduleId="scannerConfiguration">
-
- <autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
-
- <scannerConfigBuildInfo instanceId="cdt.managedbuild.config.gnu.cross.exe.debug.206163480;cdt.managedbuild.config.gnu.cross.exe.debug.206163480.;cdt.managedbuild.tool.gnu.cross.c.compiler.1469975065;cdt.managedbuild.tool.gnu.c.compiler.input.1079251302">
-
- <autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
-
- </scannerConfigBuildInfo>
-
- </storageModule>
-
- <storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders"/>
-
- <storageModule moduleId="org.eclipse.cdt.make.core.buildtargets"/>
-
- <storageModule moduleId="refreshScope" versionNumber="2">
-
- <configuration configurationName="Debug">
-
- <resource resourceType="PROJECT" workspacePath="/RTOSDemo"/>
-
- </configuration>
-
- </storageModule>
-
-</cproject>
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<?fileVersion 4.0.0?><cproject storage_type_id="org.eclipse.cdt.core.XmlProjectDescriptionStorage">
+ <storageModule moduleId="org.eclipse.cdt.core.settings">
+ <cconfiguration id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480">
+ <storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" moduleId="org.eclipse.cdt.core.settings" name="Debug">
+ <externalSettings/>
+ <extensions>
+ <extension id="org.eclipse.cdt.core.ELF" point="org.eclipse.cdt.core.BinaryParser"/>
+ <extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+ <extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+ <extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+ <extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser"/>
+ <extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
+ </extensions>
+ </storageModule>
+ <storageModule moduleId="cdtBuildSystem" version="4.0.0">
+ <configuration artifactName="${ProjName}" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe,org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug" cleanCommand="rm -rf" description="" id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" name="Debug" parent="cdt.managedbuild.config.gnu.cross.exe.debug" postbuildStep="riscv64-unknown-elf-objcopy -O binary ${ProjName} ${ProjName}.bin">
+ <folderInfo id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480." name="/" resourcePath="">
+ <toolChain id="cdt.managedbuild.toolchain.gnu.cross.exe.debug.1023181676" name="Cross GCC" superClass="cdt.managedbuild.toolchain.gnu.cross.exe.debug">
+ <option id="cdt.managedbuild.option.gnu.cross.path.2116215758" name="Path" superClass="cdt.managedbuild.option.gnu.cross.path" useByScannerDiscovery="false" value="${eclipse_home}/SiFive/riscv64-unknown-elf-toolchain-10.2.0-2020.12.8/bin" valueType="string"/>
+ <targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.ELF" id="cdt.managedbuild.targetPlatform.gnu.cross.1119183919" isAbstract="false" osList="all" superClass="cdt.managedbuild.targetPlatform.gnu.cross"/>
+ <builder buildPath="${workspace_loc:/RTOSDemo}/Debug" id="cdt.managedbuild.builder.gnu.cross.1388532167" keepEnvironmentInBuildfile="false" managedBuildOn="true" name="Gnu Make Builder" parallelBuildOn="true" parallelizationNumber="optimal" superClass="cdt.managedbuild.builder.gnu.cross"/>
+ <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.c.compiler.1469975065" name="Cross GCC Compiler" superClass="cdt.managedbuild.tool.gnu.cross.c.compiler">
+ <option defaultValue="gnu.c.optimization.level.none" id="gnu.c.compiler.option.optimization.level.440219377" name="Optimization Level" superClass="gnu.c.compiler.option.optimization.level" useByScannerDiscovery="false" valueType="enumerated"/>
+ <option id="gnu.c.compiler.option.debugging.level.1721555429" name="Debug Level" superClass="gnu.c.compiler.option.debugging.level" useByScannerDiscovery="false" value="gnu.c.debugging.level.max" valueType="enumerated"/>
+ <option id="gnu.c.compiler.option.dialect.std.1648189865" name="Language standard" superClass="gnu.c.compiler.option.dialect.std" useByScannerDiscovery="true" value="gnu.c.compiler.dialect.default" valueType="enumerated"/>
+ <option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="gnu.c.compiler.option.include.paths.1720192082" name="Include paths (-I)" superClass="gnu.c.compiler.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/include}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/full_demo/Common_Demo_Tasks/include}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/portable/GCC/RISC-V}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/include}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/freedom-metal}&quot;"/>
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/bsp/install/include}&quot;"/>
+ </option>
+ <option id="gnu.c.compiler.option.misc.other.257964774" name="Other flags" superClass="gnu.c.compiler.option.misc.other" useByScannerDiscovery="false" value="-c -fmessage-length=0 -march=rv32imac -mabi=ilp32 -mcmodel=medlow -ffunction-sections -fdata-sections --specs=nano.specs -Wno-unused-parameter" valueType="string"/>
+ <option id="gnu.c.compiler.option.warnings.extrawarn.1802410957" name="Extra warnings (-Wextra)" superClass="gnu.c.compiler.option.warnings.extrawarn" useByScannerDiscovery="false" value="true" valueType="boolean"/>
+ <inputType id="cdt.managedbuild.tool.gnu.c.compiler.input.1079251302" superClass="cdt.managedbuild.tool.gnu.c.compiler.input"/>
+ </tool>
+ <tool id="cdt.managedbuild.tool.gnu.cross.cpp.compiler.420742449" name="Cross G++ Compiler" superClass="cdt.managedbuild.tool.gnu.cross.cpp.compiler">
+ <option id="gnu.cpp.compiler.option.optimization.level.1056760450" name="Optimization Level" superClass="gnu.cpp.compiler.option.optimization.level" useByScannerDiscovery="false" value="gnu.cpp.compiler.optimization.level.none" valueType="enumerated"/>
+ <option id="gnu.cpp.compiler.option.debugging.level.52506316" name="Debug Level" superClass="gnu.cpp.compiler.option.debugging.level" useByScannerDiscovery="false" value="gnu.cpp.compiler.debugging.level.max" valueType="enumerated"/>
+ </tool>
+ <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.c.linker.558060359" name="Cross GCC Linker" superClass="cdt.managedbuild.tool.gnu.cross.c.linker">
+ <option id="gnu.c.link.option.ldflags.46965227" name="Linker flags" superClass="gnu.c.link.option.ldflags" useByScannerDiscovery="false" value="-Xlinker --gc-sections -Wl,-Map,RTOSDemo.map -T../bsp/metal.default.lds -march=rv32imac -mabi=ilp32 -mcmodel=medlow -Wl,--start-group -lc -lgcc -Wl,--end-group --specs=nano.specs" valueType="string"/>
+ <option id="gnu.c.link.option.nostart.1038463237" name="Do not use standard start files (-nostartfiles)" superClass="gnu.c.link.option.nostart" useByScannerDiscovery="false" value="true" valueType="boolean"/>
+ <option id="gnu.c.link.option.nostdlibs.934043026" name="No startup or default libs (-nostdlib)" superClass="gnu.c.link.option.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
+ <option id="gnu.c.link.option.nodeflibs.1095611620" name="Do not use default libraries (-nodefaultlibs)" superClass="gnu.c.link.option.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
+ <option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="gnu.c.link.option.other.875927818" name="Other options (-Xlinker [option])" superClass="gnu.c.link.option.other" useByScannerDiscovery="false" valueType="stringList">
+ <listOptionValue builtIn="false" value="--defsym=__heap_max=1"/>
+ </option>
+ <inputType id="cdt.managedbuild.tool.gnu.c.linker.input.549526426" superClass="cdt.managedbuild.tool.gnu.c.linker.input">
+ <additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
+ <additionalInput kind="additionalinput" paths="$(LIBS)"/>
+ </inputType>
+ </tool>
+ <tool id="cdt.managedbuild.tool.gnu.cross.cpp.linker.2105463183" name="Cross G++ Linker" superClass="cdt.managedbuild.tool.gnu.cross.cpp.linker"/>
+ <tool id="cdt.managedbuild.tool.gnu.cross.archiver.424513814" name="Cross GCC Archiver" superClass="cdt.managedbuild.tool.gnu.cross.archiver"/>
+ <tool command="riscv64-unknown-elf-gcc" id="cdt.managedbuild.tool.gnu.cross.assembler.825438707" name="Cross GCC Assembler" superClass="cdt.managedbuild.tool.gnu.cross.assembler">
+ <option id="gnu.both.asm.option.flags.1946908814" name="Assembler flags" superClass="gnu.both.asm.option.flags" useByScannerDiscovery="false" value="-march=rv32imac -mabi=ilp32 -mcmodel=medlow -c -DportasmHANDLE_INTERRUPT=handle_trap -g3" valueType="string"/>
+ <option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="gnu.both.asm.option.include.paths.1448234506" name="Include paths (-I)" superClass="gnu.both.asm.option.include.paths" useByScannerDiscovery="false" valueType="includePath">
+ <listOptionValue builtIn="false" value="&quot;${workspace_loc:/${ProjName}/FreeRTOS_Source/portable/GCC/RISC-V/chip_specific_extensions/RV32I_CLINT_no_extensions}&quot;"/>
+ </option>
+ <inputType id="cdt.managedbuild.tool.gnu.assembler.input.1723023894" superClass="cdt.managedbuild.tool.gnu.assembler.input"/>
+ </tool>
+ </toolChain>
+ </folderInfo>
+ <sourceEntries>
+ <entry flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name=""/>
+ </sourceEntries>
+ </configuration>
+ </storageModule>
+ <storageModule moduleId="org.eclipse.cdt.core.externalSettings"/>
+ </cconfiguration>
+ </storageModule>
+ <storageModule moduleId="cdtBuildSystem" version="4.0.0">
+ <project id="RTOSDemo.cdt.managedbuild.target.gnu.cross.exe.1669036252" name="Executable" projectType="cdt.managedbuild.target.gnu.cross.exe"/>
+ </storageModule>
+ <storageModule moduleId="scannerConfiguration">
+ <autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
+ <scannerConfigBuildInfo instanceId="cdt.managedbuild.config.gnu.cross.exe.debug.206163480;cdt.managedbuild.config.gnu.cross.exe.debug.206163480.;cdt.managedbuild.tool.gnu.cross.c.compiler.1469975065;cdt.managedbuild.tool.gnu.c.compiler.input.1079251302">
+ <autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
+ </scannerConfigBuildInfo>
+ </storageModule>
+ <storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders"/>
+ <storageModule moduleId="org.eclipse.cdt.make.core.buildtargets"/>
+ <storageModule moduleId="refreshScope" versionNumber="2">
+ <configuration configurationName="Debug">
+ <resource resourceType="PROJECT" workspacePath="/RTOSDemo"/>
+ </configuration>
+ </storageModule>
+ <storageModule moduleId="org.eclipse.cdt.internal.ui.text.commentOwnerProjectMappings"/>
+</cproject> \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.project b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.project
index f22f74077..f5bd48af5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.project
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.project
@@ -1,303 +1,303 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<projectDescription>
- <name>RTOSDemo</name>
- <comment></comment>
- <projects>
- </projects>
- <buildSpec>
- <buildCommand>
- <name>org.eclipse.cdt.managedbuilder.core.genmakebuilder</name>
- <triggers>clean,full,incremental,</triggers>
- <arguments>
- </arguments>
- </buildCommand>
- <buildCommand>
- <name>org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder</name>
- <triggers>full,incremental,</triggers>
- <arguments>
- </arguments>
- </buildCommand>
- </buildSpec>
- <natures>
- <nature>org.eclipse.cdt.core.cnature</nature>
- <nature>org.eclipse.cdt.managedbuilder.core.managedBuildNature</nature>
- <nature>org.eclipse.cdt.managedbuilder.core.ScannerConfigNature</nature>
- </natures>
- <linkedResources>
- <link>
- <name>FreeRTOS_Source</name>
- <type>2</type>
- <locationURI>FREERTOS_ROOT/FreeRTOS/Source</locationURI>
- </link>
- <link>
- <name>full_demo/Common_Demo_Tasks</name>
- <type>2</type>
- <locationURI>FREERTOS_ROOT/FreeRTOS/Demo/Common/Minimal</locationURI>
- </link>
- <link>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>2</type>
- <locationURI>FREERTOS_ROOT/FreeRTOS/Demo/Common/include</locationURI>
- </link>
- </linkedResources>
- <filteredResources>
- <filter>
- <id>1570727806810</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-event_groups.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727806825</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-list.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727806841</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-queue.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727806841</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-stream_buffer.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727806841</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-timers.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727806856</id>
- <name>FreeRTOS_Source</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-tasks.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892841</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-event_groups.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892856</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-FreeRTOS.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892856</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-message_buffer.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892856</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-queue.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892872</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-semphr.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892872</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-stream_buffer.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892888</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-task.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727892888</id>
- <name>FreeRTOS_Source/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-timers.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727962643</id>
- <name>FreeRTOS_Source/portable</name>
- <type>9</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-MemMang</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727962643</id>
- <name>FreeRTOS_Source/portable</name>
- <type>9</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-GCC</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005814144</id>
- <name>full_demo/Common_Demo_Tasks</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-TimerDemo.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005814150</id>
- <name>full_demo/Common_Demo_Tasks</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-blocktim.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005814159</id>
- <name>full_demo/Common_Demo_Tasks</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-dynamic.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005814167</id>
- <name>full_demo/Common_Demo_Tasks</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-TaskNotify.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727992991</id>
- <name>FreeRTOS_Source/portable/GCC</name>
- <type>9</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-RISC-V</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570727979500</id>
- <name>FreeRTOS_Source/portable/MemMang</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-heap_4.c</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005832815</id>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-TimerDemo.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005832820</id>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-blocktim.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005832824</id>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-dynamic.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005832829</id>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-MessageBufferDemo.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1571005832835</id>
- <name>full_demo/Common_Demo_Tasks/include</name>
- <type>5</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-TaskNotify.h</arguments>
- </matcher>
- </filter>
- <filter>
- <id>1570728021983</id>
- <name>FreeRTOS_Source/portable/GCC/RISC-V/chip_specific_extensions</name>
- <type>9</type>
- <matcher>
- <id>org.eclipse.ui.ide.multiFilter</id>
- <arguments>1.0-name-matches-false-false-RV32I_CLINT_no_extensions</arguments>
- </matcher>
- </filter>
- </filteredResources>
- <variableList>
- <variable>
- <name>FREERTOS_ROOT</name>
- <value>$%7BPARENT-3-PROJECT_LOC%7D</value>
- </variable>
- </variableList>
-</projectDescription>
+<?xml version="1.0" encoding="UTF-8"?>
+<projectDescription>
+ <name>RTOSDemo</name>
+ <comment></comment>
+ <projects>
+ </projects>
+ <buildSpec>
+ <buildCommand>
+ <name>org.eclipse.cdt.managedbuilder.core.genmakebuilder</name>
+ <triggers>clean,full,incremental,</triggers>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ <buildCommand>
+ <name>org.eclipse.cdt.managedbuilder.core.ScannerConfigBuilder</name>
+ <triggers>full,incremental,</triggers>
+ <arguments>
+ </arguments>
+ </buildCommand>
+ </buildSpec>
+ <natures>
+ <nature>org.eclipse.cdt.core.cnature</nature>
+ <nature>org.eclipse.cdt.managedbuilder.core.managedBuildNature</nature>
+ <nature>org.eclipse.cdt.managedbuilder.core.ScannerConfigNature</nature>
+ </natures>
+ <linkedResources>
+ <link>
+ <name>FreeRTOS_Source</name>
+ <type>2</type>
+ <locationURI>FREERTOS_ROOT/FreeRTOS/Source</locationURI>
+ </link>
+ <link>
+ <name>full_demo/Common_Demo_Tasks</name>
+ <type>2</type>
+ <locationURI>FREERTOS_ROOT/FreeRTOS/Demo/Common/Minimal</locationURI>
+ </link>
+ <link>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>2</type>
+ <locationURI>FREERTOS_ROOT/FreeRTOS/Demo/Common/include</locationURI>
+ </link>
+ </linkedResources>
+ <filteredResources>
+ <filter>
+ <id>1570727806810</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-event_groups.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727806825</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-list.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727806841</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-queue.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727806841</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-stream_buffer.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727806841</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-timers.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727806856</id>
+ <name>FreeRTOS_Source</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-tasks.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892841</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-event_groups.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892856</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-FreeRTOS.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892856</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-message_buffer.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892856</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-queue.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892872</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-semphr.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892872</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-stream_buffer.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892888</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-task.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727892888</id>
+ <name>FreeRTOS_Source/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-timers.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727962643</id>
+ <name>FreeRTOS_Source/portable</name>
+ <type>9</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-MemMang</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727962643</id>
+ <name>FreeRTOS_Source/portable</name>
+ <type>9</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-GCC</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005814144</id>
+ <name>full_demo/Common_Demo_Tasks</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-TimerDemo.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005814150</id>
+ <name>full_demo/Common_Demo_Tasks</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-blocktim.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005814159</id>
+ <name>full_demo/Common_Demo_Tasks</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-dynamic.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005814167</id>
+ <name>full_demo/Common_Demo_Tasks</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-TaskNotify.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727992991</id>
+ <name>FreeRTOS_Source/portable/GCC</name>
+ <type>9</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-RISC-V</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570727979500</id>
+ <name>FreeRTOS_Source/portable/MemMang</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-heap_4.c</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005832815</id>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-TimerDemo.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005832820</id>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-blocktim.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005832824</id>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-dynamic.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005832829</id>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-MessageBufferDemo.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1571005832835</id>
+ <name>full_demo/Common_Demo_Tasks/include</name>
+ <type>5</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-TaskNotify.h</arguments>
+ </matcher>
+ </filter>
+ <filter>
+ <id>1570728021983</id>
+ <name>FreeRTOS_Source/portable/GCC/RISC-V/chip_specific_extensions</name>
+ <type>9</type>
+ <matcher>
+ <id>org.eclipse.ui.ide.multiFilter</id>
+ <arguments>1.0-name-matches-false-false-RV32I_CLINT_no_extensions</arguments>
+ </matcher>
+ </filter>
+ </filteredResources>
+ <variableList>
+ <variable>
+ <name>FREERTOS_ROOT</name>
+ <value>$%7BPARENT-3-PROJECT_LOC%7D</value>
+ </variable>
+ </variableList>
+</projectDescription>
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.settings/language.settings.xml b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.settings/language.settings.xml
index 49f601efa..b1990cea1 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.settings/language.settings.xml
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/.settings/language.settings.xml
@@ -1,26 +1,14 @@
-<?xml version="1.0" encoding="UTF-8" standalone="no"?>
-<project>
-
- <configuration id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" name="Debug">
-
- <extension point="org.eclipse.cdt.core.LanguageSettingsProvider">
-
- <provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
-
- <provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
-
- <provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
-
- <provider class="org.eclipse.cdt.internal.build.crossgcc.CrossGCCBuiltinSpecsDetector" console="false" env-hash="-1852838222473283" id="org.eclipse.cdt.build.crossgcc.CrossGCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT Cross GCC Built-in Compiler Settings" parameter="${COMMAND} ${FLAGS} -E -P -v -dD &quot;${INPUTS}&quot;" prefer-non-shared="true">
-
- <language-scope id="org.eclipse.cdt.core.gcc"/>
-
- <language-scope id="org.eclipse.cdt.core.g++"/>
-
- </provider>
-
- </extension>
-
- </configuration>
-
-</project>
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<project>
+ <configuration id="cdt.managedbuild.config.gnu.cross.exe.debug.206163480" name="Debug">
+ <extension point="org.eclipse.cdt.core.LanguageSettingsProvider">
+ <provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
+ <provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
+ <provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
+ <provider class="org.eclipse.cdt.internal.build.crossgcc.CrossGCCBuiltinSpecsDetector" console="false" env-hash="644150116465149599" id="org.eclipse.cdt.build.crossgcc.CrossGCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT Cross GCC Built-in Compiler Settings" parameter="${COMMAND} ${FLAGS} -E -P -v -dD &quot;${INPUTS}&quot;" prefer-non-shared="true">
+ <language-scope id="org.eclipse.cdt.core.gcc"/>
+ <language-scope id="org.eclipse.cdt.core.g++"/>
+ </provider>
+ </extension>
+ </configuration>
+</project> \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/FreeRTOSConfig.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/FreeRTOSConfig.h
index 6f5106c9a..9ea57c84f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/FreeRTOSConfig.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/FreeRTOSConfig.h
@@ -1,102 +1,105 @@
-/*
- * FreeRTOS V202104.00
- * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
-
-#ifndef FREERTOS_CONFIG_H
-#define FREERTOS_CONFIG_H
-
-/*-----------------------------------------------------------
- * Application specific definitions.
- *
- * These definitions should be adjusted for your particular hardware and
- * application requirements.
- *
- * THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE
- * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE.
- *
- * See http://www.freertos.org/a00110.html.
- *----------------------------------------------------------*/
-#define CLINT_CTRL_ADDR ( 0x02000000UL )
-#define configMTIME_BASE_ADDRESS ( CLINT_CTRL_ADDR + 0xBFF8UL )
-#define configMTIMECMP_BASE_ADDRESS ( CLINT_CTRL_ADDR + 0x4000UL )
-#define configUSE_PREEMPTION 1
-#define configUSE_IDLE_HOOK 0
-#define configUSE_TICK_HOOK 1
-#define configCPU_CLOCK_HZ ( 32768 )
-#define configTICK_RATE_HZ ( ( TickType_t ) 1000 )
-#define configMAX_PRIORITIES ( 7 )
-#define configMINIMAL_STACK_SIZE ( ( unsigned short ) 120 ) /* Only needs to be this high as some demo tasks also use this constant. In production only the idle task would use this. */
-#define configTOTAL_HEAP_SIZE ( ( size_t ) 10900 )
-#define configMAX_TASK_NAME_LEN ( 16 )
-#define configUSE_TRACE_FACILITY 0
-#define configUSE_16_BIT_TICKS 0
-#define configIDLE_SHOULD_YIELD 0
-#define configUSE_MUTEXES 1
-#define configQUEUE_REGISTRY_SIZE 8
-#define configCHECK_FOR_STACK_OVERFLOW 2
-#define configUSE_RECURSIVE_MUTEXES 1
-#define configUSE_MALLOC_FAILED_HOOK 1
-#define configUSE_APPLICATION_TASK_TAG 0
-#define configUSE_COUNTING_SEMAPHORES 1
-#define configGENERATE_RUN_TIME_STATS 0
-#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1
-
-/* Co-routine definitions. */
-#define configUSE_CO_ROUTINES 0
-#define configMAX_CO_ROUTINE_PRIORITIES ( 2 )
-
-/* Software timer definitions. */
-#define configUSE_TIMERS 1
-#define configTIMER_TASK_PRIORITY ( configMAX_PRIORITIES - 1 )
-#define configTIMER_QUEUE_LENGTH 8
-#define configTIMER_TASK_STACK_DEPTH ( 160 )
-
-/* Task priorities. Allow these to be overridden. */
-#ifndef uartPRIMARY_PRIORITY
- #define uartPRIMARY_PRIORITY ( configMAX_PRIORITIES - 3 )
-#endif
-
-/* Set the following definitions to 1 to include the API function, or zero
-to exclude the API function. */
-#define INCLUDE_vTaskPrioritySet 1
-#define INCLUDE_uxTaskPriorityGet 1
-#define INCLUDE_vTaskDelete 1
-#define INCLUDE_vTaskCleanUpResources 1
-#define INCLUDE_vTaskSuspend 1
-#define INCLUDE_vTaskDelayUntil 1
-#define INCLUDE_vTaskDelay 1
-#define INCLUDE_eTaskGetState 1
-#define INCLUDE_xTimerPendFunctionCall 1
-#define INCLUDE_xTaskAbortDelay 1
-#define INCLUDE_xTaskGetHandle 1
-#define INCLUDE_xSemaphoreGetMutexHolder 1
-
-/* Normal assert() semantics without relying on the provision of an assert.h
-header file. */
-void vAssertCalled( void );
-#define configASSERT( x ) if( ( x ) == 0 ) vAssertCalled()
-
-#endif /* FREERTOS_CONFIG_H */
+/*
+ * FreeRTOS V202104.00
+ * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of
+ * this software and associated documentation files (the "Software"), to deal in
+ * the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+ * the Software, and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+ * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+ * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+ * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ * http://www.FreeRTOS.org
+ * http://aws.amazon.com/freertos
+ *
+ * 1 tab == 4 spaces!
+ */
+
+#ifndef FREERTOS_CONFIG_H
+#define FREERTOS_CONFIG_H
+
+/*-----------------------------------------------------------
+ * Application specific definitions.
+ *
+ * These definitions should be adjusted for your particular hardware and
+ * application requirements.
+ *
+ * THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE
+ * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE.
+ *
+ * See http://www.freertos.org/a00110.html.
+ *----------------------------------------------------------*/
+#define CLINT_CTRL_ADDR ( 0x02000000UL )
+#define configMTIME_BASE_ADDRESS ( CLINT_CTRL_ADDR + 0xBFF8UL )
+#define configMTIMECMP_BASE_ADDRESS ( CLINT_CTRL_ADDR + 0x4000UL )
+#define configUSE_PREEMPTION 1
+#define configUSE_IDLE_HOOK 0
+#define configUSE_TICK_HOOK 1
+#define configCPU_CLOCK_HZ ( 32768 )
+#define configTICK_RATE_HZ ( ( TickType_t ) 1000 )
+#define configMAX_PRIORITIES ( 7 )
+#define configMINIMAL_STACK_SIZE ( ( unsigned short ) 120 ) /* Only needs to be this high as some demo tasks also use this constant. In production only the idle task would use this. */
+#define configTOTAL_HEAP_SIZE ( ( size_t ) 10900 )
+#define configMAX_TASK_NAME_LEN ( 16 )
+#define configUSE_TRACE_FACILITY 0
+#define configUSE_16_BIT_TICKS 0
+#define configIDLE_SHOULD_YIELD 0
+#define configUSE_MUTEXES 1
+#define configQUEUE_REGISTRY_SIZE 8
+#define configCHECK_FOR_STACK_OVERFLOW 2
+#define configUSE_RECURSIVE_MUTEXES 1
+#define configUSE_MALLOC_FAILED_HOOK 1
+#define configUSE_APPLICATION_TASK_TAG 0
+#define configUSE_COUNTING_SEMAPHORES 1
+#define configGENERATE_RUN_TIME_STATS 0
+#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1
+
+/* Co-routine definitions. */
+#define configUSE_CO_ROUTINES 0
+#define configMAX_CO_ROUTINE_PRIORITIES ( 2 )
+
+/* Software timer definitions. */
+#define configUSE_TIMERS 1
+#define configTIMER_TASK_PRIORITY ( configMAX_PRIORITIES - 1 )
+#define configTIMER_QUEUE_LENGTH 8
+#define configTIMER_TASK_STACK_DEPTH ( 160 )
+
+/* Task priorities. Allow these to be overridden. */
+#ifndef uartPRIMARY_PRIORITY
+ #define uartPRIMARY_PRIORITY ( configMAX_PRIORITIES - 3 )
+#endif
+
+/* Set the following definitions to 1 to include the API function, or zero
+to exclude the API function. */
+#define INCLUDE_vTaskPrioritySet 1
+#define INCLUDE_uxTaskPriorityGet 1
+#define INCLUDE_vTaskDelete 1
+#define INCLUDE_vTaskCleanUpResources 1
+#define INCLUDE_vTaskSuspend 1
+#define INCLUDE_vTaskDelayUntil 1
+#define INCLUDE_vTaskDelay 1
+#define INCLUDE_eTaskGetState 1
+#define INCLUDE_xTimerPendFunctionCall 1
+#define INCLUDE_xTaskAbortDelay 1
+#define INCLUDE_xTaskGetHandle 1
+#define INCLUDE_xSemaphoreGetMutexHolder 1
+
+/* Normal assert() semantics without relying on the provision of an assert.h
+header file. */
+void vAssertCalled( void );
+#define configASSERT( x ) if( ( x ) == 0 ) vAssertCalled()
+
+/* Map to the platform write function. */
+#define configPRINT_STRING( pcString ) write( STDOUT_FILENO, pcString, strlen( pcString ) )
+
+#endif /* FREERTOS_CONFIG_H */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/SiFive_HiFive1_RTOS_demo.url b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/SiFive_HiFive1_RTOS_demo.url
index 809b91304..34f8fc0bc 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/SiFive_HiFive1_RTOS_demo.url
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/SiFive_HiFive1_RTOS_demo.url
@@ -1,5 +1,5 @@
-[InternetShortcut]
-URL=https://www.freertos.org/RTOS-RISC-V-FreedomStudio-IAR-HiFive-RevB.html
-IDList=
-[{000214A0-0000-0000-C000-000000000046}]
-Prop3=19,2
+[InternetShortcut]
+URL=https://www.freertos.org/RTOS-RISC-V-FreedomStudio-IAR-HiFive-RevB.html
+IDList=
+[{000214A0-0000-0000-C000-000000000046}]
+Prop3=19,2
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/blinky_demo/main_blinky.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/blinky_demo/main_blinky.c
index de0a85bf3..e4e572e1f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/blinky_demo/main_blinky.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/blinky_demo/main_blinky.c
@@ -1,197 +1,197 @@
-/*
- * FreeRTOS V202104.00
- * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
-
-/******************************************************************************
- * NOTE 1: This project provides two demo applications. A simple blinky
- * style project, and a more comprehensive test and demo application. The
- * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select
- * between the two. See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY
- * in main.c. This file implements the simply blinky style version.
- *
- * NOTE 2: This file only contains the source code that is specific to the
- * blinky demo. Generic functions, such FreeRTOS hook functions, and functions
- * required to configure the hardware are defined in main.c.
- ******************************************************************************
- *
- * main_blinky() creates one queue, and two tasks. It then starts the
- * scheduler.
- *
- * The Queue Send Task:
- * The queue send task is implemented by the prvQueueSendTask() function in
- * this file. prvQueueSendTask() sits in a loop that causes it to repeatedly
- * block for 1000 milliseconds, before sending the value 100 to the queue that
- * was created within main_blinky(). Once the value is sent, the task loops
- * back around to block for another 1000 milliseconds...and so on.
- *
- * The Queue Receive Task:
- * The queue receive task is implemented by the prvQueueReceiveTask() function
- * in this file. prvQueueReceiveTask() sits in a loop where it repeatedly
- * blocks on attempts to read data from the queue that was created within
- * main_blinky(). When data is received, the task checks the value of the
- * data, and if the value equals the expected 100, toggles an LED. The 'block
- * time' parameter passed to the queue receive function specifies that the task
- * should be held in the Blocked state indefinitely to wait for data to be
- * available on the queue. The queue receive task will only leave the Blocked
- * state when the queue send task writes to the queue. As the queue send task
- * writes to the queue every 1000 milliseconds, the queue receive task leaves
- * the Blocked state every 1000 milliseconds, and therefore toggles the LED
- * every 200 milliseconds.
- */
-
-/* Standard includes. */
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-
-/* Kernel includes. */
-#include "FreeRTOS.h"
-#include "task.h"
-#include "queue.h"
-
-/* Priorities used by the tasks. */
-#define mainQUEUE_RECEIVE_TASK_PRIORITY ( tskIDLE_PRIORITY + 2 )
-#define mainQUEUE_SEND_TASK_PRIORITY ( tskIDLE_PRIORITY + 1 )
-
-/* The rate at which data is sent to the queue. The 200ms value is converted
-to ticks using the pdMS_TO_TICKS() macro. */
-#define mainQUEUE_SEND_FREQUENCY_MS pdMS_TO_TICKS( 1000 )
-
-/* The maximum number items the queue can hold. The priority of the receiving
-task is above the priority of the sending task, so the receiving task will
-preempt the sending task and remove the queue items each time the sending task
-writes to the queue. Therefore the queue will never have more than one item in
-it at any time, and even with a queue length of 1, the sending task will never
-find the queue full. */
-#define mainQUEUE_LENGTH ( 1 )
-
-/*-----------------------------------------------------------*/
-
-/*
- * Called by main when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1 in
- * main.c.
- */
-void main_blinky( void );
-
-/*
- * The tasks as described in the comments at the top of this file.
- */
-static void prvQueueReceiveTask( void *pvParameters );
-static void prvQueueSendTask( void *pvParameters );
-
-/*-----------------------------------------------------------*/
-
-/* The queue used by both tasks. */
-static QueueHandle_t xQueue = NULL;
-
-/*-----------------------------------------------------------*/
-
-void main_blinky( void )
-{
- /* Create the queue. */
- xQueue = xQueueCreate( mainQUEUE_LENGTH, sizeof( uint32_t ) );
-
- if( xQueue != NULL )
- {
- /* Start the two tasks as described in the comments at the top of this
- file. */
- xTaskCreate( prvQueueReceiveTask, /* The function that implements the task. */
- "Rx", /* The text name assigned to the task - for debug only as it is not used by the kernel. */
- configMINIMAL_STACK_SIZE, /* The size of the stack to allocate to the task. */
- NULL, /* The parameter passed to the task - not used in this case. */
- mainQUEUE_RECEIVE_TASK_PRIORITY, /* The priority assigned to the task. */
- NULL ); /* The task handle is not required, so NULL is passed. */
-
- xTaskCreate( prvQueueSendTask, "TX", configMINIMAL_STACK_SIZE, NULL, mainQUEUE_SEND_TASK_PRIORITY, NULL );
-
- /* Start the tasks and timer running. */
- vTaskStartScheduler();
- }
-
- /* If all is well, the scheduler will now be running, and the following
- line will never be reached. If the following line does execute, then
- there was insufficient FreeRTOS heap memory available for the Idle and/or
- timer tasks to be created. See the memory management section on the
- FreeRTOS web site for more details on the FreeRTOS heap
- http://www.freertos.org/a00111.html. */
- for( ;; );
-}
-/*-----------------------------------------------------------*/
-
-static void prvQueueSendTask( void *pvParameters )
-{
-TickType_t xNextWakeTime;
-const unsigned long ulValueToSend = 100UL;
-BaseType_t xReturned;
-
- /* Remove compiler warning about unused parameter. */
- ( void ) pvParameters;
-
- /* Initialise xNextWakeTime - this only needs to be done once. */
- xNextWakeTime = xTaskGetTickCount();
-
- for( ;; )
- {
- /* Place this task in the blocked state until it is time to run again. */
- vTaskDelayUntil( &xNextWakeTime, mainQUEUE_SEND_FREQUENCY_MS );
-
- /* Send to the queue - causing the queue receive task to unblock and
- toggle the LED. 0 is used as the block time so the sending operation
- will not block - it shouldn't need to block as the queue should always
- be empty at this point in the code. */
- xReturned = xQueueSend( xQueue, &ulValueToSend, 0U );
- configASSERT( xReturned == pdPASS );
- }
-}
-/*-----------------------------------------------------------*/
-
-static void prvQueueReceiveTask( void *pvParameters )
-{
-unsigned long ulReceivedValue;
-const unsigned long ulExpectedValue = 100UL;
-extern void vToggleLED( void );
-
- /* Remove compiler warning about unused parameter. */
- ( void ) pvParameters;
-
- for( ;; )
- {
- /* Wait until something arrives in the queue - this task will block
- indefinitely provided INCLUDE_vTaskSuspend is set to 1 in
- FreeRTOSConfig.h. */
- xQueueReceive( xQueue, &ulReceivedValue, portMAX_DELAY );
-
- /* To get here something must have been received from the queue, but
- is it the expected value? If it is, toggle the LED. */
- if( ulReceivedValue == ulExpectedValue )
- {
- vToggleLED();
- ulReceivedValue = 0U;
- }
- }
-}
-/*-----------------------------------------------------------*/
-
+/*
+ * FreeRTOS V202104.00
+ * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of
+ * this software and associated documentation files (the "Software"), to deal in
+ * the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+ * the Software, and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+ * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+ * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+ * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ * http://www.FreeRTOS.org
+ * http://aws.amazon.com/freertos
+ *
+ * 1 tab == 4 spaces!
+ */
+
+/******************************************************************************
+ * NOTE 1: This project provides two demo applications. A simple blinky
+ * style project, and a more comprehensive test and demo application. The
+ * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select
+ * between the two. See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY
+ * in main.c. This file implements the simply blinky style version.
+ *
+ * NOTE 2: This file only contains the source code that is specific to the
+ * blinky demo. Generic functions, such FreeRTOS hook functions, and functions
+ * required to configure the hardware are defined in main.c.
+ ******************************************************************************
+ *
+ * main_blinky() creates one queue, and two tasks. It then starts the
+ * scheduler.
+ *
+ * The Queue Send Task:
+ * The queue send task is implemented by the prvQueueSendTask() function in
+ * this file. prvQueueSendTask() sits in a loop that causes it to repeatedly
+ * block for 1000 milliseconds, before sending the value 100 to the queue that
+ * was created within main_blinky(). Once the value is sent, the task loops
+ * back around to block for another 1000 milliseconds...and so on.
+ *
+ * The Queue Receive Task:
+ * The queue receive task is implemented by the prvQueueReceiveTask() function
+ * in this file. prvQueueReceiveTask() sits in a loop where it repeatedly
+ * blocks on attempts to read data from the queue that was created within
+ * main_blinky(). When data is received, the task checks the value of the
+ * data, and if the value equals the expected 100, toggles an LED. The 'block
+ * time' parameter passed to the queue receive function specifies that the task
+ * should be held in the Blocked state indefinitely to wait for data to be
+ * available on the queue. The queue receive task will only leave the Blocked
+ * state when the queue send task writes to the queue. As the queue send task
+ * writes to the queue every 1000 milliseconds, the queue receive task leaves
+ * the Blocked state every 1000 milliseconds, and therefore toggles the LED
+ * every 200 milliseconds.
+ */
+
+/* Standard includes. */
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+
+/* Kernel includes. */
+#include "FreeRTOS.h"
+#include "task.h"
+#include "queue.h"
+
+/* Priorities used by the tasks. */
+#define mainQUEUE_RECEIVE_TASK_PRIORITY ( tskIDLE_PRIORITY + 2 )
+#define mainQUEUE_SEND_TASK_PRIORITY ( tskIDLE_PRIORITY + 1 )
+
+/* The rate at which data is sent to the queue. The 200ms value is converted
+to ticks using the pdMS_TO_TICKS() macro. */
+#define mainQUEUE_SEND_FREQUENCY_MS pdMS_TO_TICKS( 1000 )
+
+/* The maximum number items the queue can hold. The priority of the receiving
+task is above the priority of the sending task, so the receiving task will
+preempt the sending task and remove the queue items each time the sending task
+writes to the queue. Therefore the queue will never have more than one item in
+it at any time, and even with a queue length of 1, the sending task will never
+find the queue full. */
+#define mainQUEUE_LENGTH ( 1 )
+
+/*-----------------------------------------------------------*/
+
+/*
+ * Called by main when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1 in
+ * main.c.
+ */
+void main_blinky( void );
+
+/*
+ * The tasks as described in the comments at the top of this file.
+ */
+static void prvQueueReceiveTask( void *pvParameters );
+static void prvQueueSendTask( void *pvParameters );
+
+/*-----------------------------------------------------------*/
+
+/* The queue used by both tasks. */
+static QueueHandle_t xQueue = NULL;
+
+/*-----------------------------------------------------------*/
+
+void main_blinky( void )
+{
+ /* Create the queue. */
+ xQueue = xQueueCreate( mainQUEUE_LENGTH, sizeof( uint32_t ) );
+
+ if( xQueue != NULL )
+ {
+ /* Start the two tasks as described in the comments at the top of this
+ file. */
+ xTaskCreate( prvQueueReceiveTask, /* The function that implements the task. */
+ "Rx", /* The text name assigned to the task - for debug only as it is not used by the kernel. */
+ configMINIMAL_STACK_SIZE, /* The size of the stack to allocate to the task. */
+ NULL, /* The parameter passed to the task - not used in this case. */
+ mainQUEUE_RECEIVE_TASK_PRIORITY, /* The priority assigned to the task. */
+ NULL ); /* The task handle is not required, so NULL is passed. */
+
+ xTaskCreate( prvQueueSendTask, "TX", configMINIMAL_STACK_SIZE, NULL, mainQUEUE_SEND_TASK_PRIORITY, NULL );
+
+ /* Start the tasks and timer running. */
+ vTaskStartScheduler();
+ }
+
+ /* If all is well, the scheduler will now be running, and the following
+ line will never be reached. If the following line does execute, then
+ there was insufficient FreeRTOS heap memory available for the Idle and/or
+ timer tasks to be created. See the memory management section on the
+ FreeRTOS web site for more details on the FreeRTOS heap
+ http://www.freertos.org/a00111.html. */
+ for( ;; );
+}
+/*-----------------------------------------------------------*/
+
+static void prvQueueSendTask( void *pvParameters )
+{
+TickType_t xNextWakeTime;
+const unsigned long ulValueToSend = 100UL;
+BaseType_t xReturned;
+
+ /* Remove compiler warning about unused parameter. */
+ ( void ) pvParameters;
+
+ /* Initialise xNextWakeTime - this only needs to be done once. */
+ xNextWakeTime = xTaskGetTickCount();
+
+ for( ;; )
+ {
+ /* Place this task in the blocked state until it is time to run again. */
+ vTaskDelayUntil( &xNextWakeTime, mainQUEUE_SEND_FREQUENCY_MS );
+
+ /* Send to the queue - causing the queue receive task to unblock and
+ toggle the LED. 0 is used as the block time so the sending operation
+ will not block - it shouldn't need to block as the queue should always
+ be empty at this point in the code. */
+ xReturned = xQueueSend( xQueue, &ulValueToSend, 0U );
+ configASSERT( xReturned == pdPASS );
+ }
+}
+/*-----------------------------------------------------------*/
+
+static void prvQueueReceiveTask( void *pvParameters )
+{
+unsigned long ulReceivedValue;
+const unsigned long ulExpectedValue = 100UL;
+extern void vToggleLED( void );
+
+ /* Remove compiler warning about unused parameter. */
+ ( void ) pvParameters;
+
+ for( ;; )
+ {
+ /* Wait until something arrives in the queue - this task will block
+ indefinitely provided INCLUDE_vTaskSuspend is set to 1 in
+ FreeRTOSConfig.h. */
+ xQueueReceive( xQueue, &ulReceivedValue, portMAX_DELAY );
+
+ /* To get here something must have been received from the queue, but
+ is it the expected value? If it is, toggle the LED. */
+ if( ulReceivedValue == ulExpectedValue )
+ {
+ vToggleLED();
+ ulReceivedValue = 0U;
+ }
+ }
+}
+/*-----------------------------------------------------------*/
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/README.md b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/README.md
new file mode 100644
index 000000000..f5abca5bf
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/README.md
@@ -0,0 +1,13 @@
+HiFive1 Rev B is a low-cost, Arduino-compatible development board featuring the Freedom E310. It’s the best way to start prototyping and developing your RISC‑V applications.
+
+This target is ideal for getting familiar with the RISC-V ISA instruction set and the freedom-metal libraries. It supports:
+
+- 1 hart with RV32IMAC core
+- 4 hardware breakpoints
+- Physical Memory Protection with 8 regions
+- 16 local interrupts signal that can be connected to off core complex devices
+- Up to 127 PLIC interrupt signals that can be connected to off core complex devices, with 7 priority levels
+- GPIO memory with 16 interrupt lines
+- SPI memory with 1 interrupt line
+- Serial port with 1 interrupt line
+- 1 RGB LEDS
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/core.dts b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/core.dts
new file mode 100644
index 000000000..f68e58441
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/core.dts
@@ -0,0 +1,262 @@
+/dts-v1/;
+/ {
+ #address-cells = <1>;
+ #size-cells = <1>;
+ compatible = "sifive,hifive1-revb";
+ model = "sifive,hifive1-revb";
+ cpus {
+ #address-cells = <1>;
+ #size-cells = <0>;
+ compatible = "sifive,fe310-g000";
+ L6: cpu@0 {
+ clocks = <&hfclk>;
+ compatible = "sifive,rocket0", "riscv";
+ device_type = "cpu";
+ i-cache-block-size = <64>;
+ i-cache-sets = <128>;
+ i-cache-size = <16384>;
+ next-level-cache = <&spi0>;
+ reg = <0>;
+ riscv,isa = "rv32imac";
+ riscv,pmpregions = <8>;
+ sifive,itim = <&itim>;
+ sifive,dtim = <&dtim>;
+ status = "okay";
+ timebase-frequency = <16000000>;
+ hardware-exec-breakpoint-count = <4>;
+ hlic: interrupt-controller {
+ #interrupt-cells = <1>;
+ compatible = "riscv,cpu-intc";
+ interrupt-controller;
+ };
+ };
+ };
+ soc {
+ #address-cells = <1>;
+ #size-cells = <1>;
+ #clock-cells = <1>;
+ compatible = "sifive,hifive1";
+ ranges;
+ hfxoscin: clock@0 {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+ clock-frequency = <16000000>;
+ };
+ hfxoscout: clock@1 {
+ compatible = "sifive,fe310-g000,hfxosc";
+ clocks = <&hfxoscin>;
+ reg = <&prci 0x4>;
+ reg-names = "config";
+ };
+ hfroscin: clock@2 {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+ clock-frequency = <72000000>;
+ };
+ hfroscout: clock@3 {
+ compatible = "sifive,fe310-g000,hfrosc";
+ clocks = <&hfroscin>;
+ reg = <&prci 0x0>;
+ reg-names = "config";
+ };
+ hfclk: clock@4 {
+ compatible = "sifive,fe310-g000,pll";
+ clocks = <&hfxoscout &hfroscout>;
+ clock-names = "pllref", "pllsel0";
+ reg = <&prci 0x8 &prci 0xc>;
+ reg-names = "config", "divider";
+ clock-frequency = <16000000>;
+ };
+ lfrosc: clock@5 {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+ clock-frequency = <32768>;
+ };
+ psdlfaltclk: clock@6 {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+ clock-frequency = <32768>;
+ };
+ lfclk: clock@7 {
+ compatible = "sifive,fe310-g000,lfrosc";
+ clocks = <&lfrosc &psdlfaltclk>;
+ clock-names = "lfrosc", "psdlfaltclk";
+ reg = <&aon 0x70 &aon 0x7C>;
+ reg-names = "config", "mux";
+ };
+ debug-controller@0 {
+ compatible = "sifive,debug-011", "riscv,debug-011";
+ interrupts-extended = <&hlic 65535>;
+ reg = <0x0 0x1000>;
+ reg-names = "control";
+ };
+ /* Missing: Error device */
+ maskrom@1000 {
+ reg = <0x1000 0x2000>;
+ reg-names = "mem";
+ };
+ otp@20000 {
+ reg = <0x20000 0x2000 0x10010000 0x1000>;
+ reg-names = "mem", "control";
+ };
+ clint: clint@2000000 {
+ compatible = "riscv,clint0";
+ interrupts-extended = <&hlic 3 &hlic 7>;
+ reg = <0x2000000 0x10000>;
+ reg-names = "control";
+ };
+ itim: itim@8000000 {
+ compatible = "sifive,itim0";
+ reg = <0x8000000 0x2000>;
+ reg-names = "mem";
+ };
+ plic: interrupt-controller@c000000 {
+ #interrupt-cells = <1>;
+ compatible = "riscv,plic0";
+ interrupt-controller;
+ interrupts-extended = <&hlic 11>;
+ reg = <0xc000000 0x4000000>;
+ reg-names = "control";
+ riscv,max-priority = <7>;
+ riscv,ndev = <52>;
+ };
+ aon: aon@10000000 {
+ compatible = "sifive,aon0";
+ reg = <0x10000000 0x8000>;
+ reg-names = "mem";
+ interrupt-parent = <&plic>;
+ interrupts = <1 2>;
+ clocks = <&lfclk>;
+ };
+ prci: prci@10008000 {
+ compatible = "sifive,fe310-g000,prci";
+ reg = <0x10008000 0x8000>;
+ reg-names = "mem";
+ };
+ gpio0: gpio@10012000 {
+ compatible = "sifive,gpio0";
+ interrupt-parent = <&plic>;
+ interrupts = <8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
+ 23 24 25 26 27 28 29 30 31 32 33 34 35 36
+ 27 28 29>;
+ reg = <0x10012000 0x1000>;
+ reg-names = "control";
+ };
+ led@0 {
+ compatible = "sifive,gpio-leds";
+ label = "LD0red";
+ gpios = <&gpio0 22>;
+ linux,default-trigger = "none";
+ };
+ led@1 {
+ compatible = "sifive,gpio-leds";
+ label = "LD0green";
+ gpios = <&gpio0 19>;
+ linux,default-trigger = "none";
+ };
+ led@2 {
+ compatible = "sifive,gpio-leds";
+ label = "LD0blue";
+ gpios = <&gpio0 21>;
+ linux,default-trigger = "none";
+ };
+ uart0: serial@10013000 {
+ compatible = "sifive,uart0";
+ interrupt-parent = <&plic>;
+ interrupts = <3>;
+ reg = <0x10013000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0x30000>;
+ };
+ spi0: spi@10014000 {
+ compatible = "sifive,spi0";
+ interrupt-parent = <&plic>;
+ interrupts = <5>;
+ reg = <0x10014000 0x1000 0x20000000 0x7A120>;
+ reg-names = "control", "mem";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0x0>;
+ #address-cells = <1>;
+ #size-cells = <1>;
+ flash@0 {
+ compatible = "jedec,spi-nor";
+ reg = <0x20000000 0x424000>;
+ };
+ };
+ pwm0: pwm@10015000 {
+ compatible = "sifive,pwm0";
+ sifive,comparator-widthbits = <8>;
+ sifive,ncomparators = <4>;
+ interrupt-parent = <&plic>;
+ interrupts = <40 41 42 43>;
+ reg = <0x10015000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0F 0x0F>;
+ };
+ i2c0: i2c@10016000 {
+ compatible = "sifive,i2c0";
+ interrupt-parent = <&plic>;
+ interrupts = <52>;
+ reg = <0x10016000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0x3000>;
+ };
+ uart1: serial@10023000 {
+ compatible = "sifive,uart0";
+ interrupt-parent = <&plic>;
+ interrupts = <4>;
+ reg = <0x10023000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0x840000>;
+ };
+ spi1: spi@10024000 {
+ compatible = "sifive,spi0";
+ interrupt-parent = <&plic>;
+ interrupts = <6>;
+ reg = <0x10024000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0x0003C>;
+ };
+ pwm1: pwm@10025000 {
+ compatible = "sifive,pwm0";
+ sifive,comparator-widthbits = <16>;
+ sifive,ncomparators = <4>;
+ interrupt-parent = <&plic>;
+ interrupts = <44 45 46 47>;
+ reg = <0x10025000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x780000 0x780000>;
+ };
+ spi2: spi@10034000 {
+ compatible = "sifive,spi0";
+ interrupt-parent = <&plic>;
+ interrupts = <7>;
+ reg = <0x10034000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x0 0xFC000000>;
+ };
+ pwm2: pwm@10035000 {
+ compatible = "sifive,pwm0";
+ sifive,comparator-widthbits = <16>;
+ sifive,ncomparators = <4>;
+ interrupt-parent = <&plic>;
+ interrupts = <48 49 50 51>;
+ reg = <0x10035000 0x1000>;
+ reg-names = "control";
+ clocks = <&hfclk>;
+ pinmux = <&gpio0 0x3C00 0x3C00>;
+ };
+ dtim: dtim@80000000 {
+ compatible = "sifive,dtim0";
+ reg = <0x80000000 0x4000>;
+ reg-names = "mem";
+ };
+ };
+};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.dts b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.dts
index 970d3be72..098c25c4b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.dts
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.dts
@@ -1,209 +1,10 @@
-/dts-v1/;
-
+/include/ "core.dts"
/ {
- #address-cells = <1>;
- #size-cells = <1>;
- compatible = "sifive,hifive1-revb";
- model = "sifive,hifive1-revb";
-
- chosen {
- stdout-path = "/soc/serial@10013000:115200";
- metal,entry = <&spi0 0x10000>;
- };
-
- cpus {
- #address-cells = <1>;
- #size-cells = <0>;
- compatible = "sifive,fe310-g000";
- L6: cpu@0 {
- clocks = <&hfclk>;
- compatible = "sifive,rocket0", "riscv";
- device_type = "cpu";
- i-cache-block-size = <64>;
- i-cache-sets = <128>;
- i-cache-size = <16384>;
- next-level-cache = <&spi0>;
- reg = <0>;
- riscv,isa = "rv32imac";
- riscv,pmpregions = <8>;
- sifive,dtim = <&dtim>;
- status = "okay";
- timebase-frequency = <1000000>;
- hardware-exec-breakpoint-count = <4>;
- hlic: interrupt-controller {
- #interrupt-cells = <1>;
- compatible = "riscv,cpu-intc";
- interrupt-controller;
- };
- };
- };
-
- soc {
- #address-cells = <1>;
- #size-cells = <1>;
- #clock-cells = <1>;
- compatible = "sifive,hifive1";
- ranges;
- hfxoscin: clock@0 {
- #clock-cells = <0>;
- compatible = "fixed-clock";
- clock-frequency = <16000000>;
- };
- hfxoscout: clock@1 {
- compatible = "sifive,fe310-g000,hfxosc";
- clocks = <&hfxoscin>;
- reg = <&prci 0x4>;
- reg-names = "config";
- };
- hfroscin: clock@2 {
- #clock-cells = <0>;
- compatible = "fixed-clock";
- clock-frequency = <72000000>;
- };
- hfroscout: clock@3 {
- compatible = "sifive,fe310-g000,hfrosc";
- clocks = <&hfroscin>;
- reg = <&prci 0x0>;
- reg-names = "config";
- };
- hfclk: clock@4 {
- compatible = "sifive,fe310-g000,pll";
- clocks = <&hfxoscout &hfroscout>;
- clock-names = "pllref", "pllsel0";
- reg = <&prci 0x8 &prci 0xc>;
- reg-names = "config", "divider";
- clock-frequency = <16000000>;
- };
-
- lfroscin: clock@5 {
- #clock-cells = <0>;
- compatible = "fixed-clock";
- clock-frequency = <32000000>;
- };
- lfclk: clock@6 {
- compatible = "sifive,fe310-g000,lfrosc";
- clocks = <&lfroscin>;
- reg = <&aon 0x70>;
- reg-names = "config";
- };
-
- aon: aon@10000000 {
- compatible = "sifive,aon0";
- reg = <0x10000000 0x8000>;
- reg-names = "mem";
- };
-
- prci: prci@10008000 {
- compatible = "sifive,fe310-g000,prci";
- reg = <0x10008000 0x8000>;
- reg-names = "mem";
- };
-
- clint: clint@2000000 {
- compatible = "riscv,clint0";
- interrupts-extended = <&hlic 3 &hlic 7>;
- reg = <0x2000000 0x10000>;
- reg-names = "control";
- };
- local-external-interrupts-0 {
- compatible = "sifive,local-external-interrupts0";
- interrupt-parent = <&hlic>;
- interrupts = <16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31>;
- };
- plic: interrupt-controller@c000000 {
- #interrupt-cells = <1>;
- compatible = "riscv,plic0";
- interrupt-controller;
- interrupts-extended = <&hlic 11>;
- reg = <0xc000000 0x4000000>;
- reg-names = "control";
- riscv,max-priority = <7>;
- riscv,ndev = <26>;
- };
- global-external-interrupts {
- compatile = "sifive,global-external-interrupts0";
- interrupt-parent = <&plic>;
- interrupts = <1 2 3 4>;
- };
-
- debug-controller@0 {
- compatible = "sifive,debug-011", "riscv,debug-011";
- interrupts-extended = <&hlic 65535>;
- reg = <0x0 0x100>;
- reg-names = "control";
- };
-
- maskrom@1000 {
- reg = <0x1000 0x2000>;
- reg-names = "mem";
- };
- otp@20000 {
- reg = <0x20000 0x2000 0x10010000 0x1000>;
- reg-names = "mem", "control";
- };
-
- dtim: dtim@80000000 {
- compatible = "sifive,dtim0";
- reg = <0x80000000 0x4000>;
- reg-names = "mem";
- };
-
- pwm@10015000 {
- compatible = "sifive,pwm0";
- interrupt-parent = <&plic>;
- interrupts = <23 24 25 26>;
- reg = <0x10015000 0x1000>;
- reg-names = "control";
- };
- gpio0: gpio@10012000 {
- compatible = "sifive,gpio0";
- interrupt-parent = <&plic>;
- interrupts = <7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22>;
- reg = <0x10012000 0x1000>;
- reg-names = "control";
- };
- uart0: serial@10013000 {
- compatible = "sifive,uart0";
- interrupt-parent = <&plic>;
- interrupts = <5>;
- reg = <0x10013000 0x1000>;
- reg-names = "control";
- clocks = <&hfclk>;
- pinmux = <&gpio0 0x30000 0x30000>;
- };
- spi0: spi@10014000 {
- compatible = "sifive,spi0";
- interrupt-parent = <&plic>;
- interrupts = <6>;
- reg = <0x10014000 0x1000 0x20000000 0x7A120>;
- reg-names = "control", "mem";
- clocks = <&hfclk>;
- pinmux = <&gpio0 0x0003C 0x0003C>;
- };
- i2c0: i2c@10016000 {
- compatible = "sifive,i2c0";
- interrupt-parent = <&plic>;
- interrupts = <52>;
- reg = <0x10016000 0x1000>;
- reg-names = "control";
- };
- led@0red {
- compatible = "sifive,gpio-leds";
- label = "LD0red";
- gpios = <&gpio0 22>;
- linux,default-trigger = "none";
- };
- led@0green {
- compatible = "sifive,gpio-leds";
- label = "LD0green";
- gpios = <&gpio0 19>;
- linux,default-trigger = "none";
- };
- led@0blue {
- compatible = "sifive,gpio-leds";
- label = "LD0blue";
- gpios = <&gpio0 21>;
- linux,default-trigger = "none";
- };
- };
+ chosen {
+ metal,entry = <&spi0 1 65536>;
+ metal,boothart = <&L6>;
+ stdout-path = "/soc/serial@10013000:115200";
+ metal,itim = <&itim 0 0>;
+ metal,ram = <&dtim 0 0>;
+ };
};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.svd b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.svd
new file mode 100644
index 000000000..3ad2768bd
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/design.svd
@@ -0,0 +1,3169 @@
+<?xml version="1.0" encoding="utf-8"?>
+<device schemaVersion="1.3" xmlns:xs="http://www.w3.org/2001/XMLSchema-instance" xs:noNamespaceSchemaLocation="CMSIS-SVD.xsd">
+ <name>sifive_hifive1_revb</name>
+ <version>0.1</version>
+ <description>From sifive,hifive1-revb,model device generator</description>
+ <addressUnitBits>8</addressUnitBits>
+ <width>32</width>
+ <size>32</size>
+ <access>read-write</access>
+ <peripherals>
+ <peripheral>
+ <name>riscv_clint0_0</name>
+ <description>From riscv,clint0,control peripheral generator</description>
+ <baseAddress>0x2000000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x10000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>msip_0</name>
+ <description>MSIP Register for hart 0</description>
+ <addressOffset>0x0</addressOffset>
+ </register>
+ <register>
+ <name>mtimecmp_0</name>
+ <description>MTIMECMP Register for hart 0</description>
+ <addressOffset>0x4000</addressOffset>
+ <size>64</size>
+ </register>
+ <register>
+ <name>mtime</name>
+ <description>MTIME Register</description>
+ <addressOffset>0xBFF8</addressOffset>
+ <size>64</size>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>riscv_plic0_0</name>
+ <description>From riscv,plic0,control peripheral generator</description>
+ <baseAddress>0xC000000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x4000000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>priority_1</name>
+ <description>PRIORITY Register for interrupt id 1</description>
+ <addressOffset>0x4</addressOffset>
+ </register>
+ <register>
+ <name>priority_2</name>
+ <description>PRIORITY Register for interrupt id 2</description>
+ <addressOffset>0x8</addressOffset>
+ </register>
+ <register>
+ <name>priority_3</name>
+ <description>PRIORITY Register for interrupt id 3</description>
+ <addressOffset>0xC</addressOffset>
+ </register>
+ <register>
+ <name>priority_4</name>
+ <description>PRIORITY Register for interrupt id 4</description>
+ <addressOffset>0x10</addressOffset>
+ </register>
+ <register>
+ <name>priority_5</name>
+ <description>PRIORITY Register for interrupt id 5</description>
+ <addressOffset>0x14</addressOffset>
+ </register>
+ <register>
+ <name>priority_6</name>
+ <description>PRIORITY Register for interrupt id 6</description>
+ <addressOffset>0x18</addressOffset>
+ </register>
+ <register>
+ <name>priority_7</name>
+ <description>PRIORITY Register for interrupt id 7</description>
+ <addressOffset>0x1C</addressOffset>
+ </register>
+ <register>
+ <name>priority_8</name>
+ <description>PRIORITY Register for interrupt id 8</description>
+ <addressOffset>0x20</addressOffset>
+ </register>
+ <register>
+ <name>priority_9</name>
+ <description>PRIORITY Register for interrupt id 9</description>
+ <addressOffset>0x24</addressOffset>
+ </register>
+ <register>
+ <name>priority_10</name>
+ <description>PRIORITY Register for interrupt id 10</description>
+ <addressOffset>0x28</addressOffset>
+ </register>
+ <register>
+ <name>priority_11</name>
+ <description>PRIORITY Register for interrupt id 11</description>
+ <addressOffset>0x2C</addressOffset>
+ </register>
+ <register>
+ <name>priority_12</name>
+ <description>PRIORITY Register for interrupt id 12</description>
+ <addressOffset>0x30</addressOffset>
+ </register>
+ <register>
+ <name>priority_13</name>
+ <description>PRIORITY Register for interrupt id 13</description>
+ <addressOffset>0x34</addressOffset>
+ </register>
+ <register>
+ <name>priority_14</name>
+ <description>PRIORITY Register for interrupt id 14</description>
+ <addressOffset>0x38</addressOffset>
+ </register>
+ <register>
+ <name>priority_15</name>
+ <description>PRIORITY Register for interrupt id 15</description>
+ <addressOffset>0x3C</addressOffset>
+ </register>
+ <register>
+ <name>priority_16</name>
+ <description>PRIORITY Register for interrupt id 16</description>
+ <addressOffset>0x40</addressOffset>
+ </register>
+ <register>
+ <name>priority_17</name>
+ <description>PRIORITY Register for interrupt id 17</description>
+ <addressOffset>0x44</addressOffset>
+ </register>
+ <register>
+ <name>priority_18</name>
+ <description>PRIORITY Register for interrupt id 18</description>
+ <addressOffset>0x48</addressOffset>
+ </register>
+ <register>
+ <name>priority_19</name>
+ <description>PRIORITY Register for interrupt id 19</description>
+ <addressOffset>0x4C</addressOffset>
+ </register>
+ <register>
+ <name>priority_20</name>
+ <description>PRIORITY Register for interrupt id 20</description>
+ <addressOffset>0x50</addressOffset>
+ </register>
+ <register>
+ <name>priority_21</name>
+ <description>PRIORITY Register for interrupt id 21</description>
+ <addressOffset>0x54</addressOffset>
+ </register>
+ <register>
+ <name>priority_22</name>
+ <description>PRIORITY Register for interrupt id 22</description>
+ <addressOffset>0x58</addressOffset>
+ </register>
+ <register>
+ <name>priority_23</name>
+ <description>PRIORITY Register for interrupt id 23</description>
+ <addressOffset>0x5C</addressOffset>
+ </register>
+ <register>
+ <name>priority_24</name>
+ <description>PRIORITY Register for interrupt id 24</description>
+ <addressOffset>0x60</addressOffset>
+ </register>
+ <register>
+ <name>priority_25</name>
+ <description>PRIORITY Register for interrupt id 25</description>
+ <addressOffset>0x64</addressOffset>
+ </register>
+ <register>
+ <name>priority_26</name>
+ <description>PRIORITY Register for interrupt id 26</description>
+ <addressOffset>0x68</addressOffset>
+ </register>
+ <register>
+ <name>priority_27</name>
+ <description>PRIORITY Register for interrupt id 27</description>
+ <addressOffset>0x6C</addressOffset>
+ </register>
+ <register>
+ <name>priority_28</name>
+ <description>PRIORITY Register for interrupt id 28</description>
+ <addressOffset>0x70</addressOffset>
+ </register>
+ <register>
+ <name>priority_29</name>
+ <description>PRIORITY Register for interrupt id 29</description>
+ <addressOffset>0x74</addressOffset>
+ </register>
+ <register>
+ <name>priority_30</name>
+ <description>PRIORITY Register for interrupt id 30</description>
+ <addressOffset>0x78</addressOffset>
+ </register>
+ <register>
+ <name>priority_31</name>
+ <description>PRIORITY Register for interrupt id 31</description>
+ <addressOffset>0x7C</addressOffset>
+ </register>
+ <register>
+ <name>priority_32</name>
+ <description>PRIORITY Register for interrupt id 32</description>
+ <addressOffset>0x80</addressOffset>
+ </register>
+ <register>
+ <name>priority_33</name>
+ <description>PRIORITY Register for interrupt id 33</description>
+ <addressOffset>0x84</addressOffset>
+ </register>
+ <register>
+ <name>priority_34</name>
+ <description>PRIORITY Register for interrupt id 34</description>
+ <addressOffset>0x88</addressOffset>
+ </register>
+ <register>
+ <name>priority_35</name>
+ <description>PRIORITY Register for interrupt id 35</description>
+ <addressOffset>0x8C</addressOffset>
+ </register>
+ <register>
+ <name>priority_36</name>
+ <description>PRIORITY Register for interrupt id 36</description>
+ <addressOffset>0x90</addressOffset>
+ </register>
+ <register>
+ <name>priority_37</name>
+ <description>PRIORITY Register for interrupt id 37</description>
+ <addressOffset>0x94</addressOffset>
+ </register>
+ <register>
+ <name>priority_38</name>
+ <description>PRIORITY Register for interrupt id 38</description>
+ <addressOffset>0x98</addressOffset>
+ </register>
+ <register>
+ <name>priority_39</name>
+ <description>PRIORITY Register for interrupt id 39</description>
+ <addressOffset>0x9C</addressOffset>
+ </register>
+ <register>
+ <name>priority_40</name>
+ <description>PRIORITY Register for interrupt id 40</description>
+ <addressOffset>0xA0</addressOffset>
+ </register>
+ <register>
+ <name>priority_41</name>
+ <description>PRIORITY Register for interrupt id 41</description>
+ <addressOffset>0xA4</addressOffset>
+ </register>
+ <register>
+ <name>priority_42</name>
+ <description>PRIORITY Register for interrupt id 42</description>
+ <addressOffset>0xA8</addressOffset>
+ </register>
+ <register>
+ <name>priority_43</name>
+ <description>PRIORITY Register for interrupt id 43</description>
+ <addressOffset>0xAC</addressOffset>
+ </register>
+ <register>
+ <name>priority_44</name>
+ <description>PRIORITY Register for interrupt id 44</description>
+ <addressOffset>0xB0</addressOffset>
+ </register>
+ <register>
+ <name>priority_45</name>
+ <description>PRIORITY Register for interrupt id 45</description>
+ <addressOffset>0xB4</addressOffset>
+ </register>
+ <register>
+ <name>priority_46</name>
+ <description>PRIORITY Register for interrupt id 46</description>
+ <addressOffset>0xB8</addressOffset>
+ </register>
+ <register>
+ <name>priority_47</name>
+ <description>PRIORITY Register for interrupt id 47</description>
+ <addressOffset>0xBC</addressOffset>
+ </register>
+ <register>
+ <name>priority_48</name>
+ <description>PRIORITY Register for interrupt id 48</description>
+ <addressOffset>0xC0</addressOffset>
+ </register>
+ <register>
+ <name>priority_49</name>
+ <description>PRIORITY Register for interrupt id 49</description>
+ <addressOffset>0xC4</addressOffset>
+ </register>
+ <register>
+ <name>priority_50</name>
+ <description>PRIORITY Register for interrupt id 50</description>
+ <addressOffset>0xC8</addressOffset>
+ </register>
+ <register>
+ <name>priority_51</name>
+ <description>PRIORITY Register for interrupt id 51</description>
+ <addressOffset>0xCC</addressOffset>
+ </register>
+ <register>
+ <name>priority_52</name>
+ <description>PRIORITY Register for interrupt id 52</description>
+ <addressOffset>0xD0</addressOffset>
+ </register>
+ <register>
+ <name>pending_0</name>
+ <description>PENDING Register for interrupt ids 31 to 0</description>
+ <addressOffset>0x1000</addressOffset>
+ </register>
+ <register>
+ <name>pending_1</name>
+ <description>PENDING Register for interrupt ids 52 to 32</description>
+ <addressOffset>0x1004</addressOffset>
+ </register>
+ <register>
+ <name>enable_0_0</name>
+ <description>ENABLE Register for interrupt ids 31 to 0 for hart 0</description>
+ <addressOffset>0x2000</addressOffset>
+ </register>
+ <register>
+ <name>enable_1_0</name>
+ <description>ENABLE Register for interrupt ids 52 to 32 for hart 0</description>
+ <addressOffset>0x2004</addressOffset>
+ </register>
+ <register>
+ <name>threshold_0</name>
+ <description>PRIORITY THRESHOLD Register for hart 0</description>
+ <addressOffset>0x200000</addressOffset>
+ </register>
+ <register>
+ <name>claimplete_0</name>
+ <description>CLAIM and COMPLETE Register for hart 0</description>
+ <addressOffset>0x200004</addressOffset>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_aon0_0</name>
+ <description>From sifive,aon0,mem peripheral generator</description>
+ <baseAddress>0x10000000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x8000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>backup_0</name>
+ <description>Backup Register 0</description>
+ <addressOffset>0x80</addressOffset>
+ </register>
+ <register>
+ <name>backup_1</name>
+ <description>Backup Register 1</description>
+ <addressOffset>0x84</addressOffset>
+ </register>
+ <register>
+ <name>backup_2</name>
+ <description>Backup Register 2</description>
+ <addressOffset>0x88</addressOffset>
+ </register>
+ <register>
+ <name>backup_3</name>
+ <description>Backup Register 3</description>
+ <addressOffset>0x8C</addressOffset>
+ </register>
+ <register>
+ <name>backup_4</name>
+ <description>Backup Register 4</description>
+ <addressOffset>0x90</addressOffset>
+ </register>
+ <register>
+ <name>backup_5</name>
+ <description>Backup Register 5</description>
+ <addressOffset>0x94</addressOffset>
+ </register>
+ <register>
+ <name>backup_6</name>
+ <description>Backup Register 6</description>
+ <addressOffset>0x98</addressOffset>
+ </register>
+ <register>
+ <name>backup_7</name>
+ <description>Backup Register 7</description>
+ <addressOffset>0x9C</addressOffset>
+ </register>
+ <register>
+ <name>backup_8</name>
+ <description>Backup Register 8</description>
+ <addressOffset>0xA0</addressOffset>
+ </register>
+ <register>
+ <name>backup_9</name>
+ <description>Backup Register 9</description>
+ <addressOffset>0xA4</addressOffset>
+ </register>
+ <register>
+ <name>backup_10</name>
+ <description>Backup Register 10</description>
+ <addressOffset>0xA8</addressOffset>
+ </register>
+ <register>
+ <name>backup_11</name>
+ <description>Backup Register 11</description>
+ <addressOffset>0xAC</addressOffset>
+ </register>
+ <register>
+ <name>backup_12</name>
+ <description>Backup Register 12</description>
+ <addressOffset>0xB0</addressOffset>
+ </register>
+ <register>
+ <name>backup_13</name>
+ <description>Backup Register 13</description>
+ <addressOffset>0xB4</addressOffset>
+ </register>
+ <register>
+ <name>backup_14</name>
+ <description>Backup Register 14</description>
+ <addressOffset>0xB8</addressOffset>
+ </register>
+ <register>
+ <name>backup_15</name>
+ <description>Backup Register 15</description>
+ <addressOffset>0xBC</addressOffset>
+ </register>
+ <register>
+ <name>wdogcfg</name>
+ <description>wdog Configuration</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>wdogscale</name>
+ <description>Counter scale value.</description>
+ <bitRange>[3:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wdogrsten</name>
+ <description>Controls whether the comparator output can set the wdogrst bit and hence cause a full reset.</description>
+ <bitRange>[8:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wdogzerocmp</name>
+ <description>Reset counter to zero after match.</description>
+ <bitRange>[9:9]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wdogenalways</name>
+ <description>Enable Always - run continuously</description>
+ <bitRange>[12:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wdogcoreawake</name>
+ <description>Increment the watchdog counter if the processor is not asleep</description>
+ <bitRange>[13:13]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wdogip0</name>
+ <description>Interrupt 0 Pending</description>
+ <bitRange>[28:28]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>wdogcount</name>
+ <description>Counter Register</description>
+ <addressOffset>0x8</addressOffset>
+ </register>
+ <register>
+ <name>wdogs</name>
+ <description>Scaled value of Counter</description>
+ <addressOffset>0x10</addressOffset>
+ </register>
+ <register>
+ <name>wdogfeed</name>
+ <description>Feed register</description>
+ <addressOffset>0x18</addressOffset>
+ </register>
+ <register>
+ <name>wdogkey</name>
+ <description>Key Register</description>
+ <addressOffset>0x1C</addressOffset>
+ </register>
+ <register>
+ <name>wdogcmp0</name>
+ <description>Comparator 0</description>
+ <addressOffset>0x20</addressOffset>
+ </register>
+ <register>
+ <name>rtccfg</name>
+ <description>rtc Configuration</description>
+ <addressOffset>0x40</addressOffset>
+ <fields>
+ <field>
+ <name>rtcscale</name>
+ <description>Counter scale value.</description>
+ <bitRange>[3:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rtcenalways</name>
+ <description>Enable Always - run continuously</description>
+ <bitRange>[12:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rtcip0</name>
+ <description>Interrupt 0 Pending</description>
+ <bitRange>[28:28]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rtccountlo</name>
+ <description>Low bits of Counter</description>
+ <addressOffset>0x48</addressOffset>
+ </register>
+ <register>
+ <name>rtccounthi</name>
+ <description>High bits of Counter</description>
+ <addressOffset>0x4C</addressOffset>
+ </register>
+ <register>
+ <name>rtcs</name>
+ <description>Scaled value of Counter</description>
+ <addressOffset>0x50</addressOffset>
+ </register>
+ <register>
+ <name>rtccmp0</name>
+ <description>Comparator 0</description>
+ <addressOffset>0x60</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi0</name>
+ <description>Wakeup program instruction 0</description>
+ <addressOffset>0x100</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi1</name>
+ <description>Wakeup program instruction 1</description>
+ <addressOffset>0x104</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi2</name>
+ <description>Wakeup program instruction 2</description>
+ <addressOffset>0x108</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi3</name>
+ <description>Wakeup program instruction 3</description>
+ <addressOffset>0x10C</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi4</name>
+ <description>Wakeup program instruction 4</description>
+ <addressOffset>0x110</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi5</name>
+ <description>Wakeup program instruction 5</description>
+ <addressOffset>0x114</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi6</name>
+ <description>Wakeup program instruction 6</description>
+ <addressOffset>0x118</addressOffset>
+ </register>
+ <register>
+ <name>pmuwakeupi7</name>
+ <description>Wakeup program instruction 7</description>
+ <addressOffset>0x11C</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi0</name>
+ <description>Sleep program instruction 0</description>
+ <addressOffset>0x120</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi1</name>
+ <description>Sleep program instruction 1</description>
+ <addressOffset>0x124</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi2</name>
+ <description>Sleep program instruction 2</description>
+ <addressOffset>0x128</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi3</name>
+ <description>Sleep program instruction 3</description>
+ <addressOffset>0x12C</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi4</name>
+ <description>Sleep program instruction 4</description>
+ <addressOffset>0x130</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi5</name>
+ <description>Sleep program instruction 5</description>
+ <addressOffset>0x134</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi6</name>
+ <description>Sleep program instruction 6</description>
+ <addressOffset>0x138</addressOffset>
+ </register>
+ <register>
+ <name>pmusleepi7</name>
+ <description>Sleep program instruction 7</description>
+ <addressOffset>0x13C</addressOffset>
+ </register>
+ <register>
+ <name>pmuie</name>
+ <description>PMU Interrupt Enables</description>
+ <addressOffset>0x140</addressOffset>
+ </register>
+ <register>
+ <name>pmucause</name>
+ <description>PMU Wakeup Cause</description>
+ <addressOffset>0x144</addressOffset>
+ </register>
+ <register>
+ <name>pmusleep</name>
+ <description>Initiate PMU Sleep Sequence</description>
+ <addressOffset>0x148</addressOffset>
+ </register>
+ <register>
+ <name>pmukey</name>
+ <description>PMU Key. Reads as 1 when PMU is unlocked</description>
+ <addressOffset>0x14C</addressOffset>
+ </register>
+ <register>
+ <name>aoncfg</name>
+ <description>AON Block Configuration Information</description>
+ <addressOffset>0x300</addressOffset>
+ <fields>
+ <field>
+ <name>has_bandgap</name>
+ <description>Bandgap feature is present</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_bod</name>
+ <description>Brownout detector feature is present</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_lfrosc</name>
+ <description>Low Frequency Ring Oscillator feature is present</description>
+ <bitRange>[2:2]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_lfrcosc</name>
+ <description>Low Frequency RC Oscillator feature is present</description>
+ <bitRange>[3:3]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_lfxosc</name>
+ <description>Low Frequency Crystal Oscillator feature is present</description>
+ <bitRange>[4:4]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_por</name>
+ <description>Power-On-Reset feature is present</description>
+ <bitRange>[5:5]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>has_ldo</name>
+ <description>Low Dropout Regulator feature is present</description>
+ <bitRange>[6:6]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>lfrosccfg</name>
+ <description>Ring Oscillator Configuration and Status</description>
+ <addressOffset>0x70</addressOffset>
+ <fields>
+ <field>
+ <name>lfroscdiv</name>
+ <description>Ring Oscillator Divider Register</description>
+ <bitRange>[5:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>lfrosctrim</name>
+ <description>Ring Oscillator Trim Register</description>
+ <bitRange>[20:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>lfroscen</name>
+ <description>Ring Oscillator Enable</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>lfroscrdy</name>
+ <description>Ring Oscillator Ready</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>lfclkmux</name>
+ <description>Low-Frequency Clock Mux Control and Status</description>
+ <addressOffset>0x7C</addressOffset>
+ <fields>
+ <field>
+ <name>lfextclk_sel</name>
+ <description>Low Frequency Clock Source Selector</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ <enumeratedValues>
+ <enumeratedValue>
+ <name>internal</name>
+ <description>Use internal LF clock source</description>
+ <value>0</value>
+ </enumeratedValue>
+ <enumeratedValue>
+ <name>external</name>
+ <description>Use external LF clock source</description>
+ <value>1</value>
+ </enumeratedValue>
+ </enumeratedValues>
+ </field>
+ <field>
+ <name>lfextclk_mux_status</name>
+ <description>Setting of the aon_lfclksel pin</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ <enumeratedValues>
+ <enumeratedValue>
+ <name>external</name>
+ <description>Use external LF clock source</description>
+ <value>0</value>
+ </enumeratedValue>
+ <enumeratedValue>
+ <name>sw</name>
+ <description>Use clock source selected by lfextclk_sel</description>
+ <value>1</value>
+ </enumeratedValue>
+ </enumeratedValues>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_fe310_g000_prci_0</name>
+ <description>From sifive,fe310-g000,prci,mem peripheral generator</description>
+ <baseAddress>0x10008000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x8000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>hfrosccfg</name>
+ <description>Ring Oscillator Configuration and Status</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>hfroscdiv</name>
+ <description>Ring Oscillator Divider Register</description>
+ <bitRange>[5:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>hfrosctrim</name>
+ <description>Ring Oscillator Trim Register</description>
+ <bitRange>[20:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>hfroscen</name>
+ <description>Ring Oscillator Enable</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>hfroscrdy</name>
+ <description>Ring Oscillator Ready</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>hfxosccfg</name>
+ <description>Crystal Oscillator Configuration and Status</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>hfxoscen</name>
+ <description>Crystal Oscillator Enable</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>hfxoscrdy</name>
+ <description>Crystal Oscillator Ready</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pllcfg</name>
+ <description>PLL Configuration and Status</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>pllr</name>
+ <description>PLL R Value</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pllf</name>
+ <description>PLL F Value</description>
+ <bitRange>[9:4]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pllq</name>
+ <description>PLL Q Value</description>
+ <bitRange>[11:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pllsel</name>
+ <description>PLL Select</description>
+ <bitRange>[16:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pllrefsel</name>
+ <description>PLL Reference Select</description>
+ <bitRange>[17:17]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pllbypass</name>
+ <description>PLL Bypass</description>
+ <bitRange>[18:18]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>plllock</name>
+ <description>PLL Lock</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>plloutdiv</name>
+ <description>PLL Final Divide Configuration</description>
+ <addressOffset>0xC</addressOffset>
+ <fields>
+ <field>
+ <name>plloutdiv</name>
+ <description>PLL Final Divider Value</description>
+ <bitRange>[5:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>plloutdivby1</name>
+ <description>PLL Final Divide By 1</description>
+ <bitRange>[13:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>procmoncfg</name>
+ <description>Process Monitor Configuration and Status</description>
+ <addressOffset>0xF0</addressOffset>
+ <fields>
+ <field>
+ <name>procmon_div_sel</name>
+ <description>Proccess Monitor Divider</description>
+ <bitRange>[4:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>procmon_delay_sel</name>
+ <description>Process Monitor Delay Selector</description>
+ <bitRange>[12:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>procmon_en</name>
+ <description>Process Monitor Enable</description>
+ <bitRange>[16:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>procomon_sel</name>
+ <description>Process Monitor Select</description>
+ <bitRange>[25:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_gpio0_0</name>
+ <description>From sifive,gpio0,control peripheral generator</description>
+ <baseAddress>0x10012000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>input_val</name>
+ <description>Pin value</description>
+ <addressOffset>0x0</addressOffset>
+ </register>
+ <register>
+ <name>input_en</name>
+ <description>Pin input enable</description>
+ <addressOffset>0x4</addressOffset>
+ </register>
+ <register>
+ <name>output_en</name>
+ <description>Pin output enable</description>
+ <addressOffset>0x8</addressOffset>
+ </register>
+ <register>
+ <name>output_val</name>
+ <description>Output value</description>
+ <addressOffset>0xC</addressOffset>
+ </register>
+ <register>
+ <name>pue</name>
+ <description>Internal pull-up enable</description>
+ <addressOffset>0x10</addressOffset>
+ </register>
+ <register>
+ <name>ds</name>
+ <description>Pin drive strength</description>
+ <addressOffset>0x14</addressOffset>
+ </register>
+ <register>
+ <name>rise_ie</name>
+ <description>Rise interrupt enable</description>
+ <addressOffset>0x18</addressOffset>
+ </register>
+ <register>
+ <name>rise_ip</name>
+ <description>Rise interrupt pending</description>
+ <addressOffset>0x1C</addressOffset>
+ </register>
+ <register>
+ <name>fall_ie</name>
+ <description>Fall interrupt enable</description>
+ <addressOffset>0x20</addressOffset>
+ </register>
+ <register>
+ <name>fall_ip</name>
+ <description>Fall interrupt pending</description>
+ <addressOffset>0x24</addressOffset>
+ </register>
+ <register>
+ <name>high_ie</name>
+ <description>High interrupt enable</description>
+ <addressOffset>0x28</addressOffset>
+ </register>
+ <register>
+ <name>high_ip</name>
+ <description>High interrupt pending</description>
+ <addressOffset>0x2C</addressOffset>
+ </register>
+ <register>
+ <name>low_ie</name>
+ <description>Low interrupt enable</description>
+ <addressOffset>0x30</addressOffset>
+ </register>
+ <register>
+ <name>low_ip</name>
+ <description>Low interrupt pending</description>
+ <addressOffset>0x34</addressOffset>
+ </register>
+ <register>
+ <name>iof_en</name>
+ <description>I/O function enable</description>
+ <addressOffset>0x38</addressOffset>
+ </register>
+ <register>
+ <name>iof_sel</name>
+ <description>I/O function select</description>
+ <addressOffset>0x3C</addressOffset>
+ </register>
+ <register>
+ <name>out_xor</name>
+ <description>Output XOR (invert)</description>
+ <addressOffset>0x40</addressOffset>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_uart0_0</name>
+ <description>From sifive,uart0,control peripheral generator</description>
+ <baseAddress>0x10013000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>txdata</name>
+ <description>Transmit data register</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Transmit data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>full</name>
+ <description>Transmit FIFO full</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxdata</name>
+ <description>Receive data register</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Received data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>empty</name>
+ <description>Receive FIFO empty</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txctrl</name>
+ <description>Transmit control register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>txen</name>
+ <description>Transmit enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>nstop</name>
+ <description>Number of stop bits</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>txcnt</name>
+ <description>Transmit watermark level</description>
+ <bitRange>[18:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxctrl</name>
+ <description>Receive control register</description>
+ <addressOffset>0xC</addressOffset>
+ <fields>
+ <field>
+ <name>rxen</name>
+ <description>Receive enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxcnt</name>
+ <description>Receive watermark level</description>
+ <bitRange>[18:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ie</name>
+ <description>UART interrupt enable</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark interrupt enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark interrupt enable</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ip</name>
+ <description>UART interrupt pending</description>
+ <addressOffset>0x14</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark interrupt pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark interrupt pending</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>div</name>
+ <description>Baud rate divisor</description>
+ <addressOffset>0x18</addressOffset>
+ <fields>
+ <field>
+ <name>div</name>
+ <description>Baud rate divisor.</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_spi0_0</name>
+ <description>From sifive,spi0,control peripheral generator</description>
+ <baseAddress>0x10014000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>sckdiv</name>
+ <description>Serial clock divisor</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>div</name>
+ <description>Divisor for serial clock.</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sckmode</name>
+ <description>Serial clock mode</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>pha</name>
+ <description>Serial clock phase</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pol</name>
+ <description>Serial clock polarity</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csid</name>
+ <description>Chip select ID</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>csid</name>
+ <description>Chip select ID.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csdef</name>
+ <description>Chip select default</description>
+ <addressOffset>0x14</addressOffset>
+ <fields>
+ <field>
+ <name>csdef</name>
+ <description>Chip select default value. Reset to all-1s.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csmode</name>
+ <description>Chip select mode</description>
+ <addressOffset>0x18</addressOffset>
+ <fields>
+ <field>
+ <name>mode</name>
+ <description>Chip select mode</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay0</name>
+ <description>Delay control 0</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>cssck</name>
+ <description>CS to SCK Delay</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>sckcs</name>
+ <description>SCK to CS Delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay1</name>
+ <description>Delay control 1</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>intercs</name>
+ <description>Minimum CS inactive time</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>interxfr</name>
+ <description>Maximum interframe delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>extradel</name>
+ <description>SPI extra sampling delay to increase the SPI frequency</description>
+ <addressOffset>0x38</addressOffset>
+ <fields>
+ <field>
+ <name>coarse</name>
+ <description>Coarse grain sample delay (multiples of system clocks)</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>fine</name>
+ <description>Fine grain sample delay (multiples of process-specific buffer delay)</description>
+ <bitRange>[16:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sampledel</name>
+ <description>Number of delay stages from slave to the SPI controller</description>
+ <addressOffset>0x3C</addressOffset>
+ <fields>
+ <field>
+ <name>sd</name>
+ <description>Number of delay stages from slave to SPI controller</description>
+ <bitRange>[4:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fmt</name>
+ <description>Frame format</description>
+ <addressOffset>0x40</addressOffset>
+ <fields>
+ <field>
+ <name>proto</name>
+ <description>SPI protocol</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>endian</name>
+ <description>SPI endianness</description>
+ <bitRange>[2:2]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>dir</name>
+ <description>SPI I/O direction. This is reset to 1 for flash-enabled SPI controllers, 0 otherwise.</description>
+ <bitRange>[3:3]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>len</name>
+ <description>Number of bits per frame</description>
+ <bitRange>[19:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txdata</name>
+ <description>Tx FIFO Data</description>
+ <addressOffset>0x48</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Transmit data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>full</name>
+ <description>FIFO full flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxdata</name>
+ <description>Rx FIFO data</description>
+ <addressOffset>0x4C</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Received data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>empty</name>
+ <description>FIFO empty flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txmark</name>
+ <description>Tx FIFO watermark</description>
+ <addressOffset>0x50</addressOffset>
+ <fields>
+ <field>
+ <name>txmark</name>
+ <description>Transmit watermark. The reset value is 1 for flash-enabled controllers, 0 otherwise.</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxmark</name>
+ <description>Rx FIFO watermark</description>
+ <addressOffset>0x54</addressOffset>
+ <fields>
+ <field>
+ <name>rxmark</name>
+ <description>Receive watermark</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fctrl</name>
+ <description>SPI flash interface control</description>
+ <addressOffset>0x60</addressOffset>
+ <fields>
+ <field>
+ <name>en</name>
+ <description>SPI Flash Mode Select</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ffmt</name>
+ <description>SPI flash instruction format</description>
+ <addressOffset>0x64</addressOffset>
+ <fields>
+ <field>
+ <name>cmd_en</name>
+ <description>Enable sending of command</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_len</name>
+ <description>Number of address bytes (0 to 4)</description>
+ <bitRange>[3:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_cnt</name>
+ <description>Number of dummy cycles</description>
+ <bitRange>[7:4]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_proto</name>
+ <description>Protocol for transmitting command</description>
+ <bitRange>[9:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_proto</name>
+ <description>Protocol for transmitting address and padding</description>
+ <bitRange>[11:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>data_proto</name>
+ <description>Protocol for receiving data bytes</description>
+ <bitRange>[13:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_code</name>
+ <description>Value of command byte</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_code</name>
+ <description>First 8 bits to transmit during dummy cycles</description>
+ <bitRange>[31:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ie</name>
+ <description>SPI interrupt enable</description>
+ <addressOffset>0x70</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark enable</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ip</name>
+ <description>SPI interrupt pending</description>
+ <addressOffset>0x74</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark pending</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_pwm0_0</name>
+ <description>From sifive,pwm0,control peripheral generator</description>
+ <baseAddress>0x10015000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>pwmcfg</name>
+ <description>PWM configuration register</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>pwmscale</name>
+ <description>PWM Counter scale</description>
+ <bitRange>[3:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmsticky</name>
+ <description>PWM Sticky - disallow clearing pwmcmpXip bits</description>
+ <bitRange>[8:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmzerocmp</name>
+ <description>PWM Zero - counter resets to zero after match</description>
+ <bitRange>[9:9]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmdeglitch</name>
+ <description>PWM Deglitch - latch pwmcmpXip within same cycle</description>
+ <bitRange>[10:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenalways</name>
+ <description>PWM enable always - run continuously</description>
+ <bitRange>[12:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenoneshot</name>
+ <description>PWM enable one shot - run one cycle</description>
+ <bitRange>[13:13]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0center</name>
+ <description>PWM0 Compare Center</description>
+ <bitRange>[16:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1center</name>
+ <description>PWM1 Compare Center</description>
+ <bitRange>[17:17]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2center</name>
+ <description>PWM2 Compare Center</description>
+ <bitRange>[18:18]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3center</name>
+ <description>PWM3 Compare Center</description>
+ <bitRange>[19:19]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0invert</name>
+ <description>PWM0 Invert</description>
+ <bitRange>[20:20]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1invert</name>
+ <description>PWM1 Invert</description>
+ <bitRange>[21:21]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2invert</name>
+ <description>PWM2 Invert</description>
+ <bitRange>[22:22]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3invert</name>
+ <description>PWM3 Invert</description>
+ <bitRange>[23:23]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0gang</name>
+ <description>PWM0/PWM1 Compare Gang</description>
+ <bitRange>[24:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1gang</name>
+ <description>PWM1/PWM2 Compare Gang</description>
+ <bitRange>[25:25]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2gang</name>
+ <description>PWM2/PWM3 Compare Gang</description>
+ <bitRange>[26:26]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3gang</name>
+ <description>PWM3/PWM0 Compare Gang</description>
+ <bitRange>[27:27]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0ip</name>
+ <description>PWM0 Interrupt Pending</description>
+ <bitRange>[28:28]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1ip</name>
+ <description>PWM1 Interrupt Pending</description>
+ <bitRange>[29:29]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2ip</name>
+ <description>PWM2 Interrupt Pending</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3ip</name>
+ <description>PWM3 Interrupt Pending</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcount</name>
+ <description>PWM count register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcount</name>
+ <description>PWM count register.</description>
+ <bitRange>[30:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwms</name>
+ <description>Scaled PWM count register</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>pwms</name>
+ <description>Scaled PWM count register.</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp0</name>
+ <description>PWM 0 compare register</description>
+ <addressOffset>0x20</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp0</name>
+ <description>PWM 0 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp1</name>
+ <description>PWM 1 compare register</description>
+ <addressOffset>0x24</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp1</name>
+ <description>PWM 1 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp2</name>
+ <description>PWM 2 compare register</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp2</name>
+ <description>PWM 2 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp3</name>
+ <description>PWM 3 compare register</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp3</name>
+ <description>PWM 3 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_i2c0_0</name>
+ <description>From sifive,i2c0,control peripheral generator</description>
+ <baseAddress>0x10016000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>prescale_low</name>
+ <description>Clock Prescale register lo-byte</description>
+ <addressOffset>0x0</addressOffset>
+ </register>
+ <register>
+ <name>prescale_high</name>
+ <description>Clock Prescale register hi-byte</description>
+ <addressOffset>0x4</addressOffset>
+ </register>
+ <register>
+ <name>control</name>
+ <description>Control register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>en</name>
+ <description>I2C core enable bit</description>
+ <bitRange>[6:6]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>ien</name>
+ <description>I2C core interrupt enable bit</description>
+ <bitRange>[7:7]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>transmit__receive</name>
+ <description>Transmit and receive data byte register</description>
+ <addressOffset>0xC</addressOffset>
+ </register>
+ <register>
+ <name>command__status</name>
+ <description>Command write and status read register</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>wr_iack__rd_if</name>
+ <description>Clear interrupt and Interrupt pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_res__rd_tip</name>
+ <description>Reserved and Transfer in progress</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_res__rd_res</name>
+ <description>Reserved and Reserved</description>
+ <bitRange>[2:2]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_ack__rd_res</name>
+ <description>Send ACK/NACK and Reserved</description>
+ <bitRange>[3:3]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_txd__rd_res</name>
+ <description>Transmit data and Reserved</description>
+ <bitRange>[4:4]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_rxd__rd_al</name>
+ <description>Receive data and Arbitration lost</description>
+ <bitRange>[5:5]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_sto__rd_busy</name>
+ <description>Generate stop and I2C bus busy</description>
+ <bitRange>[6:6]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>wr_sta__rd_rxack</name>
+ <description>Generate start and Got ACK/NACK</description>
+ <bitRange>[7:7]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_uart0_1</name>
+ <description>From sifive,uart0,control peripheral generator</description>
+ <baseAddress>0x10023000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>txdata</name>
+ <description>Transmit data register</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Transmit data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>full</name>
+ <description>Transmit FIFO full</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxdata</name>
+ <description>Receive data register</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Received data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>empty</name>
+ <description>Receive FIFO empty</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txctrl</name>
+ <description>Transmit control register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>txen</name>
+ <description>Transmit enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>nstop</name>
+ <description>Number of stop bits</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>txcnt</name>
+ <description>Transmit watermark level</description>
+ <bitRange>[18:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxctrl</name>
+ <description>Receive control register</description>
+ <addressOffset>0xC</addressOffset>
+ <fields>
+ <field>
+ <name>rxen</name>
+ <description>Receive enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxcnt</name>
+ <description>Receive watermark level</description>
+ <bitRange>[18:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ie</name>
+ <description>UART interrupt enable</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark interrupt enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark interrupt enable</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ip</name>
+ <description>UART interrupt pending</description>
+ <addressOffset>0x14</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark interrupt pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark interrupt pending</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>div</name>
+ <description>Baud rate divisor</description>
+ <addressOffset>0x18</addressOffset>
+ <fields>
+ <field>
+ <name>div</name>
+ <description>Baud rate divisor.</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_spi0_1</name>
+ <description>From sifive,spi0,control peripheral generator</description>
+ <baseAddress>0x10024000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>sckdiv</name>
+ <description>Serial clock divisor</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>div</name>
+ <description>Divisor for serial clock.</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sckmode</name>
+ <description>Serial clock mode</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>pha</name>
+ <description>Serial clock phase</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pol</name>
+ <description>Serial clock polarity</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csid</name>
+ <description>Chip select ID</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>csid</name>
+ <description>Chip select ID.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csdef</name>
+ <description>Chip select default</description>
+ <addressOffset>0x14</addressOffset>
+ <fields>
+ <field>
+ <name>csdef</name>
+ <description>Chip select default value. Reset to all-1s.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csmode</name>
+ <description>Chip select mode</description>
+ <addressOffset>0x18</addressOffset>
+ <fields>
+ <field>
+ <name>mode</name>
+ <description>Chip select mode</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay0</name>
+ <description>Delay control 0</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>cssck</name>
+ <description>CS to SCK Delay</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>sckcs</name>
+ <description>SCK to CS Delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay1</name>
+ <description>Delay control 1</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>intercs</name>
+ <description>Minimum CS inactive time</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>interxfr</name>
+ <description>Maximum interframe delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>extradel</name>
+ <description>SPI extra sampling delay to increase the SPI frequency</description>
+ <addressOffset>0x38</addressOffset>
+ <fields>
+ <field>
+ <name>coarse</name>
+ <description>Coarse grain sample delay (multiples of system clocks)</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>fine</name>
+ <description>Fine grain sample delay (multiples of process-specific buffer delay)</description>
+ <bitRange>[16:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sampledel</name>
+ <description>Number of delay stages from slave to the SPI controller</description>
+ <addressOffset>0x3C</addressOffset>
+ <fields>
+ <field>
+ <name>sd</name>
+ <description>Number of delay stages from slave to SPI controller</description>
+ <bitRange>[4:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fmt</name>
+ <description>Frame format</description>
+ <addressOffset>0x40</addressOffset>
+ <fields>
+ <field>
+ <name>proto</name>
+ <description>SPI protocol</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>endian</name>
+ <description>SPI endianness</description>
+ <bitRange>[2:2]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>dir</name>
+ <description>SPI I/O direction. This is reset to 1 for flash-enabled SPI controllers, 0 otherwise.</description>
+ <bitRange>[3:3]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>len</name>
+ <description>Number of bits per frame</description>
+ <bitRange>[19:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txdata</name>
+ <description>Tx FIFO Data</description>
+ <addressOffset>0x48</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Transmit data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>full</name>
+ <description>FIFO full flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxdata</name>
+ <description>Rx FIFO data</description>
+ <addressOffset>0x4C</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Received data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>empty</name>
+ <description>FIFO empty flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txmark</name>
+ <description>Tx FIFO watermark</description>
+ <addressOffset>0x50</addressOffset>
+ <fields>
+ <field>
+ <name>txmark</name>
+ <description>Transmit watermark. The reset value is 1 for flash-enabled controllers, 0 otherwise.</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxmark</name>
+ <description>Rx FIFO watermark</description>
+ <addressOffset>0x54</addressOffset>
+ <fields>
+ <field>
+ <name>rxmark</name>
+ <description>Receive watermark</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fctrl</name>
+ <description>SPI flash interface control</description>
+ <addressOffset>0x60</addressOffset>
+ <fields>
+ <field>
+ <name>en</name>
+ <description>SPI Flash Mode Select</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ffmt</name>
+ <description>SPI flash instruction format</description>
+ <addressOffset>0x64</addressOffset>
+ <fields>
+ <field>
+ <name>cmd_en</name>
+ <description>Enable sending of command</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_len</name>
+ <description>Number of address bytes (0 to 4)</description>
+ <bitRange>[3:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_cnt</name>
+ <description>Number of dummy cycles</description>
+ <bitRange>[7:4]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_proto</name>
+ <description>Protocol for transmitting command</description>
+ <bitRange>[9:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_proto</name>
+ <description>Protocol for transmitting address and padding</description>
+ <bitRange>[11:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>data_proto</name>
+ <description>Protocol for receiving data bytes</description>
+ <bitRange>[13:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_code</name>
+ <description>Value of command byte</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_code</name>
+ <description>First 8 bits to transmit during dummy cycles</description>
+ <bitRange>[31:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ie</name>
+ <description>SPI interrupt enable</description>
+ <addressOffset>0x70</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark enable</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ip</name>
+ <description>SPI interrupt pending</description>
+ <addressOffset>0x74</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark pending</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_pwm0_1</name>
+ <description>From sifive,pwm0,control peripheral generator</description>
+ <baseAddress>0x10025000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>pwmcfg</name>
+ <description>PWM configuration register</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>pwmscale</name>
+ <description>PWM Counter scale</description>
+ <bitRange>[3:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmsticky</name>
+ <description>PWM Sticky - disallow clearing pwmcmpXip bits</description>
+ <bitRange>[8:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmzerocmp</name>
+ <description>PWM Zero - counter resets to zero after match</description>
+ <bitRange>[9:9]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmdeglitch</name>
+ <description>PWM Deglitch - latch pwmcmpXip within same cycle</description>
+ <bitRange>[10:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenalways</name>
+ <description>PWM enable always - run continuously</description>
+ <bitRange>[12:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenoneshot</name>
+ <description>PWM enable one shot - run one cycle</description>
+ <bitRange>[13:13]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0center</name>
+ <description>PWM0 Compare Center</description>
+ <bitRange>[16:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1center</name>
+ <description>PWM1 Compare Center</description>
+ <bitRange>[17:17]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2center</name>
+ <description>PWM2 Compare Center</description>
+ <bitRange>[18:18]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3center</name>
+ <description>PWM3 Compare Center</description>
+ <bitRange>[19:19]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0invert</name>
+ <description>PWM0 Invert</description>
+ <bitRange>[20:20]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1invert</name>
+ <description>PWM1 Invert</description>
+ <bitRange>[21:21]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2invert</name>
+ <description>PWM2 Invert</description>
+ <bitRange>[22:22]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3invert</name>
+ <description>PWM3 Invert</description>
+ <bitRange>[23:23]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0gang</name>
+ <description>PWM0/PWM1 Compare Gang</description>
+ <bitRange>[24:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1gang</name>
+ <description>PWM1/PWM2 Compare Gang</description>
+ <bitRange>[25:25]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2gang</name>
+ <description>PWM2/PWM3 Compare Gang</description>
+ <bitRange>[26:26]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3gang</name>
+ <description>PWM3/PWM0 Compare Gang</description>
+ <bitRange>[27:27]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0ip</name>
+ <description>PWM0 Interrupt Pending</description>
+ <bitRange>[28:28]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1ip</name>
+ <description>PWM1 Interrupt Pending</description>
+ <bitRange>[29:29]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2ip</name>
+ <description>PWM2 Interrupt Pending</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3ip</name>
+ <description>PWM3 Interrupt Pending</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcount</name>
+ <description>PWM count register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcount</name>
+ <description>PWM count register.</description>
+ <bitRange>[30:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwms</name>
+ <description>Scaled PWM count register</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>pwms</name>
+ <description>Scaled PWM count register.</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp0</name>
+ <description>PWM 0 compare register</description>
+ <addressOffset>0x20</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp0</name>
+ <description>PWM 0 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp1</name>
+ <description>PWM 1 compare register</description>
+ <addressOffset>0x24</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp1</name>
+ <description>PWM 1 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp2</name>
+ <description>PWM 2 compare register</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp2</name>
+ <description>PWM 2 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp3</name>
+ <description>PWM 3 compare register</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp3</name>
+ <description>PWM 3 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_spi0_2</name>
+ <description>From sifive,spi0,control peripheral generator</description>
+ <baseAddress>0x10034000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>sckdiv</name>
+ <description>Serial clock divisor</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>div</name>
+ <description>Divisor for serial clock.</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sckmode</name>
+ <description>Serial clock mode</description>
+ <addressOffset>0x4</addressOffset>
+ <fields>
+ <field>
+ <name>pha</name>
+ <description>Serial clock phase</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pol</name>
+ <description>Serial clock polarity</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csid</name>
+ <description>Chip select ID</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>csid</name>
+ <description>Chip select ID.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csdef</name>
+ <description>Chip select default</description>
+ <addressOffset>0x14</addressOffset>
+ <fields>
+ <field>
+ <name>csdef</name>
+ <description>Chip select default value. Reset to all-1s.</description>
+ <bitRange>[31:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>csmode</name>
+ <description>Chip select mode</description>
+ <addressOffset>0x18</addressOffset>
+ <fields>
+ <field>
+ <name>mode</name>
+ <description>Chip select mode</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay0</name>
+ <description>Delay control 0</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>cssck</name>
+ <description>CS to SCK Delay</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>sckcs</name>
+ <description>SCK to CS Delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>delay1</name>
+ <description>Delay control 1</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>intercs</name>
+ <description>Minimum CS inactive time</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>interxfr</name>
+ <description>Maximum interframe delay</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>extradel</name>
+ <description>SPI extra sampling delay to increase the SPI frequency</description>
+ <addressOffset>0x38</addressOffset>
+ <fields>
+ <field>
+ <name>coarse</name>
+ <description>Coarse grain sample delay (multiples of system clocks)</description>
+ <bitRange>[11:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>fine</name>
+ <description>Fine grain sample delay (multiples of process-specific buffer delay)</description>
+ <bitRange>[16:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>sampledel</name>
+ <description>Number of delay stages from slave to the SPI controller</description>
+ <addressOffset>0x3C</addressOffset>
+ <fields>
+ <field>
+ <name>sd</name>
+ <description>Number of delay stages from slave to SPI controller</description>
+ <bitRange>[4:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fmt</name>
+ <description>Frame format</description>
+ <addressOffset>0x40</addressOffset>
+ <fields>
+ <field>
+ <name>proto</name>
+ <description>SPI protocol</description>
+ <bitRange>[1:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>endian</name>
+ <description>SPI endianness</description>
+ <bitRange>[2:2]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>dir</name>
+ <description>SPI I/O direction. This is reset to 1 for flash-enabled SPI controllers, 0 otherwise.</description>
+ <bitRange>[3:3]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>len</name>
+ <description>Number of bits per frame</description>
+ <bitRange>[19:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txdata</name>
+ <description>Tx FIFO Data</description>
+ <addressOffset>0x48</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Transmit data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>full</name>
+ <description>FIFO full flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxdata</name>
+ <description>Rx FIFO data</description>
+ <addressOffset>0x4C</addressOffset>
+ <fields>
+ <field>
+ <name>data</name>
+ <description>Received data</description>
+ <bitRange>[7:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>empty</name>
+ <description>FIFO empty flag</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>txmark</name>
+ <description>Tx FIFO watermark</description>
+ <addressOffset>0x50</addressOffset>
+ <fields>
+ <field>
+ <name>txmark</name>
+ <description>Transmit watermark. The reset value is 1 for flash-enabled controllers, 0 otherwise.</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>rxmark</name>
+ <description>Rx FIFO watermark</description>
+ <addressOffset>0x54</addressOffset>
+ <fields>
+ <field>
+ <name>rxmark</name>
+ <description>Receive watermark</description>
+ <bitRange>[2:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>fctrl</name>
+ <description>SPI flash interface control</description>
+ <addressOffset>0x60</addressOffset>
+ <fields>
+ <field>
+ <name>en</name>
+ <description>SPI Flash Mode Select</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ffmt</name>
+ <description>SPI flash instruction format</description>
+ <addressOffset>0x64</addressOffset>
+ <fields>
+ <field>
+ <name>cmd_en</name>
+ <description>Enable sending of command</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_len</name>
+ <description>Number of address bytes (0 to 4)</description>
+ <bitRange>[3:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_cnt</name>
+ <description>Number of dummy cycles</description>
+ <bitRange>[7:4]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_proto</name>
+ <description>Protocol for transmitting command</description>
+ <bitRange>[9:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>addr_proto</name>
+ <description>Protocol for transmitting address and padding</description>
+ <bitRange>[11:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>data_proto</name>
+ <description>Protocol for receiving data bytes</description>
+ <bitRange>[13:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>cmd_code</name>
+ <description>Value of command byte</description>
+ <bitRange>[23:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pad_code</name>
+ <description>First 8 bits to transmit during dummy cycles</description>
+ <bitRange>[31:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ie</name>
+ <description>SPI interrupt enable</description>
+ <addressOffset>0x70</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark enable</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark enable</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>ip</name>
+ <description>SPI interrupt pending</description>
+ <addressOffset>0x74</addressOffset>
+ <fields>
+ <field>
+ <name>txwm</name>
+ <description>Transmit watermark pending</description>
+ <bitRange>[0:0]</bitRange>
+ <access>read-only</access>
+ </field>
+ <field>
+ <name>rxwm</name>
+ <description>Receive watermark pending</description>
+ <bitRange>[1:1]</bitRange>
+ <access>read-only</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ <peripheral>
+ <name>sifive_pwm0_2</name>
+ <description>From sifive,pwm0,control peripheral generator</description>
+ <baseAddress>0x10035000</baseAddress>
+ <addressBlock>
+ <offset>0</offset>
+ <size>0x1000</size>
+ <usage>registers</usage>
+ </addressBlock>
+ <registers>
+ <register>
+ <name>pwmcfg</name>
+ <description>PWM configuration register</description>
+ <addressOffset>0x0</addressOffset>
+ <fields>
+ <field>
+ <name>pwmscale</name>
+ <description>PWM Counter scale</description>
+ <bitRange>[3:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmsticky</name>
+ <description>PWM Sticky - disallow clearing pwmcmpXip bits</description>
+ <bitRange>[8:8]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmzerocmp</name>
+ <description>PWM Zero - counter resets to zero after match</description>
+ <bitRange>[9:9]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmdeglitch</name>
+ <description>PWM Deglitch - latch pwmcmpXip within same cycle</description>
+ <bitRange>[10:10]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenalways</name>
+ <description>PWM enable always - run continuously</description>
+ <bitRange>[12:12]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmenoneshot</name>
+ <description>PWM enable one shot - run one cycle</description>
+ <bitRange>[13:13]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0center</name>
+ <description>PWM0 Compare Center</description>
+ <bitRange>[16:16]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1center</name>
+ <description>PWM1 Compare Center</description>
+ <bitRange>[17:17]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2center</name>
+ <description>PWM2 Compare Center</description>
+ <bitRange>[18:18]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3center</name>
+ <description>PWM3 Compare Center</description>
+ <bitRange>[19:19]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0invert</name>
+ <description>PWM0 Invert</description>
+ <bitRange>[20:20]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1invert</name>
+ <description>PWM1 Invert</description>
+ <bitRange>[21:21]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2invert</name>
+ <description>PWM2 Invert</description>
+ <bitRange>[22:22]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3invert</name>
+ <description>PWM3 Invert</description>
+ <bitRange>[23:23]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0gang</name>
+ <description>PWM0/PWM1 Compare Gang</description>
+ <bitRange>[24:24]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1gang</name>
+ <description>PWM1/PWM2 Compare Gang</description>
+ <bitRange>[25:25]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2gang</name>
+ <description>PWM2/PWM3 Compare Gang</description>
+ <bitRange>[26:26]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3gang</name>
+ <description>PWM3/PWM0 Compare Gang</description>
+ <bitRange>[27:27]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp0ip</name>
+ <description>PWM0 Interrupt Pending</description>
+ <bitRange>[28:28]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp1ip</name>
+ <description>PWM1 Interrupt Pending</description>
+ <bitRange>[29:29]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp2ip</name>
+ <description>PWM2 Interrupt Pending</description>
+ <bitRange>[30:30]</bitRange>
+ <access>read-write</access>
+ </field>
+ <field>
+ <name>pwmcmp3ip</name>
+ <description>PWM3 Interrupt Pending</description>
+ <bitRange>[31:31]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcount</name>
+ <description>PWM count register</description>
+ <addressOffset>0x8</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcount</name>
+ <description>PWM count register.</description>
+ <bitRange>[30:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwms</name>
+ <description>Scaled PWM count register</description>
+ <addressOffset>0x10</addressOffset>
+ <fields>
+ <field>
+ <name>pwms</name>
+ <description>Scaled PWM count register.</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp0</name>
+ <description>PWM 0 compare register</description>
+ <addressOffset>0x20</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp0</name>
+ <description>PWM 0 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp1</name>
+ <description>PWM 1 compare register</description>
+ <addressOffset>0x24</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp1</name>
+ <description>PWM 1 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp2</name>
+ <description>PWM 2 compare register</description>
+ <addressOffset>0x28</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp2</name>
+ <description>PWM 2 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ <register>
+ <name>pwmcmp3</name>
+ <description>PWM 3 compare register</description>
+ <addressOffset>0x2C</addressOffset>
+ <fields>
+ <field>
+ <name>pwmcmp3</name>
+ <description>PWM 3 Compare Value</description>
+ <bitRange>[15:0]</bitRange>
+ <access>read-write</access>
+ </field>
+ </fields>
+ </register>
+ </registers>
+ </peripheral>
+ </peripherals>
+</device> \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/atomic.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/atomic.h
new file mode 100644
index 000000000..32a33abd7
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/atomic.h
@@ -0,0 +1,259 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__ATOMIC_H
+#define METAL__ATOMIC_H
+
+#include <stdint.h>
+
+#include <metal/compiler.h>
+
+typedef volatile int32_t metal_atomic_t;
+
+#define METAL_ATOMIC_DECLARE(name) \
+ __attribute((section(".data.atomics"))) metal_atomic_t name
+
+#define _METAL_STORE_AMO_ACCESS_FAULT 7
+
+/* This macro stores the memory address in mtval like a normal store/amo access
+ * fault, triggers a trap, and then if execution returns, returns 0 as an
+ * arbitrary choice */
+#define _METAL_TRAP_AMO_ACCESS(addr) \
+ __asm__("csrw mtval, %[atomic]" ::[atomic] "r"(a)); \
+ _metal_trap(_METAL_STORE_AMO_ACCESS_FAULT); \
+ return 0;
+
+/*!
+ * @brief Check if the platform supports atomic operations
+ *
+ * @return 1 if atomic operations are supported, 0 if not
+ */
+__inline__ int32_t metal_atomic_available(void) {
+#ifdef __riscv_atomic
+ return 1;
+#else
+ return 0;
+#endif
+}
+
+/*!
+ * @brief Atomically increment a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to increment
+ * @param increment the amount to increment the value
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_add(metal_atomic_t *a, int32_t increment) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoadd.w %[old], %[increment], (%[atomic])"
+ : [old] "=r"(old)
+ : [increment] "r"(increment), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-AND a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-AND
+ * @param mask the bitmask to AND
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_and(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoand.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-OR a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-OR
+ * @param mask the bitmask to OR
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_or(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoor.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically swap a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param new_value the value to store in the metal_atomic_t
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_swap(metal_atomic_t *a, int32_t new_value) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoswap.w %[old], %[newval], (%[atomic])"
+ : [old] "=r"(old)
+ : [newval] "r"(new_value), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-XOR a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-XOR
+ * @param mask the bitmask to XOR
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_xor(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoxor.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the greater of
+ * its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_max(metal_atomic_t *a, int32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomax.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the (unsigned)
+ * greater of its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ uint32_t metal_atomic_max_u(metal_atomic_t *a, uint32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomaxu.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the lesser of
+ * its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_min(metal_atomic_t *a, int32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomin.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the (unsigned) lesser
+ * of its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ uint32_t metal_atomic_min_u(metal_atomic_t *a, uint32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amominu.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+#endif /* METAL__ATOMIC_H */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/button.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/button.h
index 0c26f435a..bef645967 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/button.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/button.h
@@ -15,7 +15,8 @@ struct metal_button;
struct metal_button_vtable {
int (*button_exist)(struct metal_button *button, char *label);
- struct metal_interrupt* (*interrupt_controller)(struct metal_button *button);
+ struct metal_interrupt *(*interrupt_controller)(
+ struct metal_button *button);
int (*get_interrupt_id)(struct metal_button *button);
};
@@ -35,8 +36,7 @@ struct metal_button {
* @param label The DeviceTree label for the button
* @return A handle for the button
*/
-struct metal_button* metal_button_get(char *label);
-
+struct metal_button *metal_button_get(char *label);
/*!
* @brief Get the interrupt controller for a button
@@ -45,8 +45,10 @@ struct metal_button* metal_button_get(char *label);
* @return A pointer to the interrupt controller responsible for handling
* button interrupts.
*/
-inline struct metal_interrupt*
- metal_button_interrupt_controller(struct metal_button *button) { return button->vtable->interrupt_controller(button); }
+__inline__ struct metal_interrupt *
+metal_button_interrupt_controller(struct metal_button *button) {
+ return button->vtable->interrupt_controller(button);
+}
/*!
* @brief Get the interrupt id for a button
@@ -54,6 +56,8 @@ inline struct metal_interrupt*
* @param button The handle for the button
* @return The interrupt id corresponding to a button.
*/
-inline int metal_button_get_interrupt_id(struct metal_button *button) { return button->vtable->get_interrupt_id(button); }
+__inline__ int metal_button_get_interrupt_id(struct metal_button *button) {
+ return button->vtable->get_interrupt_id(button);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cache.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cache.h
index a8a60ada6..673a8b13e 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cache.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cache.h
@@ -1,4 +1,4 @@
-/* Copyright 2018 SiFive, Inc */
+/* Copyright 2020 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
#ifndef METAL__CACHE_H
@@ -9,40 +9,58 @@
*
* @brief API for configuring caches
*/
-
-struct metal_cache;
-
-struct __metal_cache_vtable {
- void (*init)(struct metal_cache *cache, int ways);
- int (*get_enabled_ways)(struct metal_cache *cache);
- int (*set_enabled_ways)(struct metal_cache *cache, int ways);
-};
+#include <stdint.h>
/*!
* @brief a handle for a cache
+ * Note: To be deprecated in next release.
*/
struct metal_cache {
- const struct __metal_cache_vtable *vtable;
+ uint8_t __no_empty_structs;
};
/*!
+ * @brief Initialize L2 cache controller.
+ * Enables all available cache ways.
+ * @param None
+ * @return 0 If no error
+ */
+int metal_l2cache_init(void);
+
+/*!
+ * @brief Get the current number of enabled L2 cache ways
+ * @param None
+ * @return The current number of enabled L2 cache ways
+ */
+int metal_l2cache_get_enabled_ways(void);
+
+/*!
+ * @brief Enable the requested number of L2 cache ways
+ * @param ways Number of ways to enable
+ * @return 0 if the ways are successfully enabled
+ */
+int metal_l2cache_set_enabled_ways(int ways);
+
+/*!
* @brief Initialize a cache
* @param cache The handle for the cache to initialize
* @param ways The number of ways to enable
*
* Initializes a cache with the requested number of ways enabled.
+ * Note: API to be deprecated in next release.
*/
-inline void metal_cache_init(struct metal_cache *cache, int ways) {
- return cache->vtable->init(cache, ways);
+__inline__ void metal_cache_init(struct metal_cache *cache, int ways) {
+ metal_l2cache_init();
}
/*!
* @brief Get the current number of enabled cache ways
* @param cache The handle for the cache
* @return The current number of enabled cache ways
+ * Note: API to be deprecated in next release.
*/
-inline int metal_cache_get_enabled_ways(struct metal_cache *cache) {
- return cache->vtable->get_enabled_ways(cache);
+__inline__ int metal_cache_get_enabled_ways(struct metal_cache *cache) {
+ return metal_l2cache_get_enabled_ways();
}
/*!
@@ -50,9 +68,41 @@ inline int metal_cache_get_enabled_ways(struct metal_cache *cache) {
* @param cache The handle for the cache
* @param ways The number of ways to enabled
* @return 0 if the ways are successfully enabled
+ * Note: API to be deprecated in next release.
*/
-inline int metal_cache_set_enabled_ways(struct metal_cache *cache, int ways) {
- return cache->vtable->set_enabled_ways(cache, ways);
+__inline__ int metal_cache_set_enabled_ways(struct metal_cache *cache,
+ int ways) {
+ return metal_l2cache_set_enabled_ways(ways);
}
+/*!
+ * @brief Check if dcache is supported on the core
+ * @param hartid The core to check
+ * @return 1 if dcache is present
+ */
+int metal_dcache_l1_available(int hartid);
+
+/*!
+ * @brief Flush dcache for L1 on the requested core with write back
+ * @param hartid The core to flush
+ * @param address The virtual address of cacheline to invalidate
+ * @return None
+ */
+void metal_dcache_l1_flush(int hartid, uintptr_t address);
+
+/*!
+ * @brief Discard dcache for L1 on the requested core with no write back
+ * @param hartid The core to discard
+ * @param address The virtual address of cacheline to invalidate
+ * @return None
+ */
+void metal_dcache_l1_discard(int hartid, uintptr_t address);
+
+/*!
+ * @brief Check if icache is supported on the core
+ * @param hartid The core to check
+ * @return 1 if icache is present
+ */
+int metal_icache_l1_available(int hartid);
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/clock.h
index 277841e01..cfe29f6b7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/clock.h
@@ -4,11 +4,12 @@
#ifndef METAL__CLOCK_H
#define METAL__CLOCK_H
-/*!
+/*!
* @file clock.h
* @brief API for manipulating clock sources
*
- * The clock interface allows for controlling the rate of various clocks in the system.
+ * The clock interface allows for controlling the rate of various clocks in the
+ * system.
*/
struct metal_clock;
@@ -22,37 +23,82 @@ struct __metal_clock_vtable {
};
/*!
- * @brief Function signature of clock pre-rate change callbacks
+ * @brief Function signature of clock rate change callbacks
+ */
+typedef void (*metal_clock_rate_change_callback)(void *priv);
+
+struct _metal_clock_callback_t;
+struct _metal_clock_callback_t {
+ /* The callback function */
+ metal_clock_rate_change_callback callback;
+
+ /* Private data for the callback function */
+ void *priv;
+
+ struct _metal_clock_callback_t *_next;
+};
+
+/*!
+ * @brief Type for the linked list of callbacks for clock rate changes
*/
-typedef void (*metal_clock_pre_rate_change_callback)(void *priv);
+typedef struct _metal_clock_callback_t metal_clock_callback;
/*!
- * @brief Function signature of clock post-rate change callbacks
+ * @brief Call all callbacks in the linked list, if any are registered
*/
-typedef void (*metal_clock_post_rate_change_callback)(void *priv);
+__inline__ void
+_metal_clock_call_all_callbacks(const metal_clock_callback *const list) {
+ const metal_clock_callback *current = list;
+ while (current) {
+ current->callback(current->priv);
+ current = current->_next;
+ }
+}
+
+/*!
+ * @brief Append a callback to the linked list and return the head of the list
+ */
+__inline__ metal_clock_callback *
+_metal_clock_append_to_callbacks(metal_clock_callback *list,
+ metal_clock_callback *const cb) {
+ cb->_next = NULL;
+
+ if (!list) {
+ return cb;
+ }
+
+ metal_clock_callback *current = list;
+
+ while ((current->_next) != NULL) {
+ current = current->_next;
+ }
+
+ current->_next = cb;
+
+ return list;
+}
/*!
* @struct metal_clock
* @brief The handle for a clock
*
- * Clocks are defined as a pointer to a `struct metal_clock`, the contents of which
- * are implementation defined. Users of the clock interface must call functions
- * which accept a `struct metal_clock *` as an argument to interract with the clock.
+ * Clocks are defined as a pointer to a `struct metal_clock`, the contents of
+ * which are implementation defined. Users of the clock interface must call
+ * functions which accept a `struct metal_clock *` as an argument to interract
+ * with the clock.
*
- * Note that no mechanism for obtaining a pointer to a `struct metal_clock` has been
- * defined, making it impossible to call any of these functions without invoking
- * implementation-defined behavior.
+ * Note that no mechanism for obtaining a pointer to a `struct metal_clock` has
+ * been defined, making it impossible to call any of these functions without
+ * invoking implementation-defined behavior.
*/
struct metal_clock {
const struct __metal_clock_vtable *vtable;
- /* Pre-rate change callback */
- metal_clock_pre_rate_change_callback _pre_rate_change_callback;
- void *_pre_rate_change_callback_priv;
+ /* Pre-rate change callback linked list */
+ metal_clock_callback *_pre_rate_change_callback;
- /* Post-rate change callback */
- metal_clock_post_rate_change_callback _post_rate_change_callback;
- void *_post_rate_change_callback_priv;
+ /* Post-rate change callback linked list */
+ metal_clock_callback *_post_rate_change_callback;
};
/*!
@@ -61,7 +107,9 @@ struct metal_clock {
* @param clk The handle for the clock
* @return The current rate of the clock in Hz
*/
-inline long metal_clock_get_rate_hz(const struct metal_clock *clk) { return clk->vtable->get_rate_hz(clk); }
+__inline__ long metal_clock_get_rate_hz(const struct metal_clock *clk) {
+ return clk->vtable->get_rate_hz(clk);
+}
/*!
* @brief Set the current rate of a clock
@@ -74,18 +122,15 @@ inline long metal_clock_get_rate_hz(const struct metal_clock *clk) { return clk-
* to the given rate in Hz. Returns the actual value that's been selected, which
* could be anything!
*
- * Prior to and after the rate change of the clock, this will call the registered
- * pre- and post-rate change callbacks.
+ * Prior to and after the rate change of the clock, this will call the
+ * registered pre- and post-rate change callbacks.
*/
-inline long metal_clock_set_rate_hz(struct metal_clock *clk, long hz)
-{
- if(clk->_pre_rate_change_callback != NULL)
- clk->_pre_rate_change_callback(clk->_pre_rate_change_callback_priv);
+__inline__ long metal_clock_set_rate_hz(struct metal_clock *clk, long hz) {
+ _metal_clock_call_all_callbacks(clk->_pre_rate_change_callback);
long out = clk->vtable->set_rate_hz(clk, hz);
- if (clk->_post_rate_change_callback != NULL)
- clk->_post_rate_change_callback(clk->_post_rate_change_callback_priv);
+ _metal_clock_call_all_callbacks(clk->_post_rate_change_callback);
return out;
}
@@ -95,12 +140,12 @@ inline long metal_clock_set_rate_hz(struct metal_clock *clk, long hz)
*
* @param clk The handle for the clock
* @param cb The callback to be registered
- * @param priv Private data for the callback handler
*/
-inline void metal_clock_register_pre_rate_change_callback(struct metal_clock *clk, metal_clock_pre_rate_change_callback cb, void *priv)
-{
- clk->_pre_rate_change_callback = cb;
- clk->_pre_rate_change_callback_priv = priv;
+__inline__ void
+metal_clock_register_pre_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb) {
+ clk->_pre_rate_change_callback =
+ _metal_clock_append_to_callbacks(clk->_pre_rate_change_callback, cb);
}
/*!
@@ -108,12 +153,12 @@ inline void metal_clock_register_pre_rate_change_callback(struct metal_clock *cl
*
* @param clk The handle for the clock
* @param cb The callback to be registered
- * @param priv Private data for the callback handler
*/
-inline void metal_clock_register_post_rate_change_callback(struct metal_clock *clk, metal_clock_post_rate_change_callback cb, void *priv)
-{
- clk->_post_rate_change_callback = cb;
- clk->_post_rate_change_callback_priv = priv;
+__inline__ void
+metal_clock_register_post_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb) {
+ clk->_post_rate_change_callback =
+ _metal_clock_append_to_callbacks(clk->_post_rate_change_callback, cb);
}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/compiler.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/compiler.h
index 62c0ea975..80ca5fee4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/compiler.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/compiler.h
@@ -4,18 +4,19 @@
#ifndef METAL__COMPILER_H
#define METAL__COMPILER_H
-#define __METAL_DECLARE_VTABLE(type) \
- extern const struct type type;
+#define __METAL_DECLARE_VTABLE(type) extern const struct type type;
-#define __METAL_DEFINE_VTABLE(type) \
- const struct type type
+#define __METAL_DEFINE_VTABLE(type) const struct type type
-#define __METAL_GET_FIELD(reg, mask) \
+#define __METAL_GET_FIELD(reg, mask) \
(((reg) & (mask)) / ((mask) & ~((mask) << 1)))
/* Set field with mask for a given value */
-#define __METAL_SET_FIELD(reg, mask, val) \
- (((reg) & ~(mask)) | (((val) * ((mask) & ~((mask) << 1))) & (mask)))
+#define __METAL_SET_FIELD(reg, mask, val) \
+ (((reg) & ~(mask)) | (((val) * ((mask) & ~((mask) << 1))) & (mask)))
+
+#define __METAL_MIN(a, b) ((a) < (b) ? (a) : (b))
+#define __METAL_MAX(a, b) ((a) > (b) ? (a) : (b))
void _metal_trap(int ecode);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cpu.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cpu.h
index 453bd12de..98d7e6680 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cpu.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/cpu.h
@@ -9,33 +9,35 @@
#ifndef METAL__CPU_H
#define METAL__CPU_H
-#include <stdint.h>
#include <metal/interrupt.h>
+#include <stdint.h>
struct metal_cpu;
/*!
* @brief Function signature for exception handlers
*/
-typedef void (*metal_exception_handler_t) (struct metal_cpu *cpu, int ecode);
+typedef void (*metal_exception_handler_t)(struct metal_cpu *cpu, int ecode);
struct metal_cpu_vtable {
- unsigned long long (*timer_get)(struct metal_cpu *cpu);
+ unsigned long long (*mcycle_get)(struct metal_cpu *cpu);
unsigned long long (*timebase_get)(struct metal_cpu *cpu);
unsigned long long (*mtime_get)(struct metal_cpu *cpu);
int (*mtimecmp_set)(struct metal_cpu *cpu, unsigned long long time);
- struct metal_interrupt* (*tmr_controller_interrupt)(struct metal_cpu *cpu);
+ struct metal_interrupt *(*tmr_controller_interrupt)(struct metal_cpu *cpu);
int (*get_tmr_interrupt_id)(struct metal_cpu *cpu);
- struct metal_interrupt* (*sw_controller_interrupt)(struct metal_cpu *cpu);
+ struct metal_interrupt *(*sw_controller_interrupt)(struct metal_cpu *cpu);
int (*get_sw_interrupt_id)(struct metal_cpu *cpu);
int (*set_sw_ipi)(struct metal_cpu *cpu, int hartid);
int (*clear_sw_ipi)(struct metal_cpu *cpu, int hartid);
int (*get_msip)(struct metal_cpu *cpu, int hartid);
- struct metal_interrupt* (*controller_interrupt)(struct metal_cpu *cpu);
- int (*exception_register)(struct metal_cpu *cpu, int ecode, metal_exception_handler_t handler);
+ struct metal_interrupt *(*controller_interrupt)(struct metal_cpu *cpu);
+ int (*exception_register)(struct metal_cpu *cpu, int ecode,
+ metal_exception_handler_t handler);
int (*get_ilen)(struct metal_cpu *cpu, uintptr_t epc);
uintptr_t (*get_epc)(struct metal_cpu *cpu);
int (*set_epc)(struct metal_cpu *cpu, uintptr_t epc);
+ struct metal_buserror *(*get_buserror)(struct metal_cpu *cpu);
};
/*! @brief A device handle for a CPU hart
@@ -49,17 +51,17 @@ struct metal_cpu {
* @param hartid The ID of the desired CPU hart
* @return A pointer to the CPU device handle
*/
-struct metal_cpu* metal_cpu_get(int hartid);
+struct metal_cpu *metal_cpu_get(unsigned int hartid);
/*! @brief Get the hartid of the CPU hart executing this function
*
* @return The hartid of the current CPU hart */
-int metal_cpu_get_current_hartid();
+int metal_cpu_get_current_hartid(void);
/*! @brief Get the number of CPU harts
- *
+ *
* @return The number of CPU harts */
-int metal_cpu_get_num_harts();
+int metal_cpu_get_num_harts(void);
/*! @brief Get the CPU cycle count timer value
*
@@ -68,8 +70,9 @@ int metal_cpu_get_num_harts();
* @param cpu The CPU device handle
* @return The value of the CPU cycle count timer
*/
-inline unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu)
-{ return cpu->vtable->timer_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu) {
+ return cpu->vtable->mcycle_get(cpu);
+}
/*! @brief Get the timebase of the CPU
*
@@ -78,8 +81,9 @@ inline unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu)
* @param cpu The CPU device handle
* @return The value of the cycle count timer timebase
*/
-inline unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu)
-{ return cpu->vtable->timebase_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu) {
+ return cpu->vtable->timebase_get(cpu);
+}
/*! @brief Get the value of the mtime RTC
*
@@ -90,8 +94,9 @@ inline unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu)
* @param cpu The CPU device handle
* @return The value of mtime, or 0 if failure
*/
-inline unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu)
-{ return cpu->vtable->mtime_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu) {
+ return cpu->vtable->mtime_get(cpu);
+}
/*! @brief Set the value of the RTC mtimecmp RTC
*
@@ -103,20 +108,24 @@ inline unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu)
* @param time The value to set the compare register to
* @return The value of mtimecmp or -1 if error
*/
-inline int metal_cpu_set_mtimecmp(struct metal_cpu *cpu, unsigned long long time)
-{ return cpu->vtable->mtimecmp_set(cpu, time); }
+__inline__ int metal_cpu_set_mtimecmp(struct metal_cpu *cpu,
+ unsigned long long time) {
+ return cpu->vtable->mtimecmp_set(cpu, time);
+}
/*! @brief Get a reference to RTC timer interrupt controller
*
- * Get a reference to the interrupt controller for the real-time clock interrupt.
- * The controller returned by this function must be initialized before any interrupts
- * are registered or enabled with it.
+ * Get a reference to the interrupt controller for the real-time clock
+ * interrupt. The controller returned by this function must be initialized
+ * before any interrupts are registered or enabled with it.
*
* @param cpu The CPU device handle
* @return A pointer to the timer interrupt handle
*/
-inline struct metal_interrupt* metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->tmr_controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->tmr_controller_interrupt(cpu);
+}
/*! @brief Get the RTC timer interrupt id
*
@@ -125,20 +134,23 @@ inline struct metal_interrupt* metal_cpu_timer_interrupt_controller(struct metal
* @param cpu The CPU device handle
* @return The timer interrupt ID
*/
-inline int metal_cpu_timer_get_interrupt_id(struct metal_cpu *cpu)
-{ return cpu->vtable->get_tmr_interrupt_id(cpu); }
+__inline__ int metal_cpu_timer_get_interrupt_id(struct metal_cpu *cpu) {
+ return cpu->vtable->get_tmr_interrupt_id(cpu);
+}
/*! @brief Get a reference to the software interrupt controller
*
* Get a reference to the interrupt controller for the software/inter-process
- * interrupt. The controller returned by this function must be initialized before
- * any interrupts are registered or enabled with it.
+ * interrupt. The controller returned by this function must be initialized
+ * before any interrupts are registered or enabled with it.
*
* @param cpu The CPU device handle
* @return A pointer to the software interrupt handle
*/
-inline struct metal_interrupt* metal_cpu_software_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->sw_controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_software_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->sw_controller_interrupt(cpu);
+}
/*! @brief Get the software interrupt id
*
@@ -147,8 +159,9 @@ inline struct metal_interrupt* metal_cpu_software_interrupt_controller(struct me
* @param cpu The CPU device handle
* @return the software interrupt ID
*/
-inline int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu)
-{ return cpu->vtable->get_sw_interrupt_id(cpu); }
+__inline__ int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu) {
+ return cpu->vtable->get_sw_interrupt_id(cpu);
+}
/*!
* @brief Set the inter-process interrupt for a hart
@@ -161,8 +174,9 @@ inline int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu)
* @param hartid The CPU hart ID to be interrupted
* @return 0 upon success
*/
-inline int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->set_sw_ipi(cpu, hartid); }
+__inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->set_sw_ipi(cpu, hartid);
+}
/*!
* @brief Clear the inter-process interrupt for a hart
@@ -175,8 +189,9 @@ inline int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid)
* @param hartid The CPU hart ID to clear
* @return 0 upon success
*/
-inline int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->clear_sw_ipi(cpu, hartid); }
+__inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->clear_sw_ipi(cpu, hartid);
+}
/*!
* @brief Get the value of MSIP for the given hart
@@ -190,8 +205,9 @@ inline int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid)
* @param hartid The CPU hart to read
* @return 0 upon success
*/
-inline int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->get_msip(cpu, hartid); }
+__inline__ int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->get_msip(cpu, hartid);
+}
/*!
* @brief Get the interrupt controller for the CPU
@@ -204,22 +220,26 @@ inline int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid)
* @param cpu The CPU device handle
* @return The handle for the CPU interrupt controller
*/
-inline struct metal_interrupt* metal_cpu_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->controller_interrupt(cpu);
+}
/*!
* @brief Register an exception handler
- *
- * Register an exception handler for the CPU. The CPU interrupt controller must be initialized
- * before this function is called.
+ *
+ * Register an exception handler for the CPU. The CPU interrupt controller must
+ * be initialized before this function is called.
*
* @param cpu The CPU device handle
* @param ecode The exception code to register a handler for
* @param handler Callback function for the exception handler
* @return 0 upon success
*/
-inline int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode, metal_exception_handler_t handler)
-{ return cpu->vtable->exception_register(cpu, ecode, handler); }
+__inline__ int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode,
+ metal_exception_handler_t handler) {
+ return cpu->vtable->exception_register(cpu, ecode, handler);
+}
/*!
* @brief Get the length of an instruction in bytes
@@ -237,8 +257,10 @@ inline int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode, metal_
* @param epc The address of the instruction to measure
* @return the length of the instruction in bytes
*/
-inline int metal_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t epc)
-{ return cpu->vtable->get_ilen(cpu, epc); }
+__inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu,
+ uintptr_t epc) {
+ return cpu->vtable->get_ilen(cpu, epc);
+}
/*!
* @brief Get the program counter of the current exception.
@@ -249,8 +271,9 @@ inline int metal_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t epc
* @param cpu The CPU device handle
* @return The value of the program counter at the time of the exception
*/
-inline uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu)
-{ return cpu->vtable->get_epc(cpu); }
+__inline__ uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu) {
+ return cpu->vtable->get_epc(cpu);
+}
/*!
* @brief Set the exception program counter
@@ -265,7 +288,20 @@ inline uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu)
* @param epc The address to set the exception program counter to
* @return 0 upon success
*/
-inline int metal_cpu_set_exception_pc(struct metal_cpu *cpu, uintptr_t epc)
-{ return cpu->vtable->set_epc(cpu, epc); }
+__inline__ int metal_cpu_set_exception_pc(struct metal_cpu *cpu,
+ uintptr_t epc) {
+ return cpu->vtable->set_epc(cpu, epc);
+}
+
+/*!
+ * @brief Get the handle for the hart's bus error unit
+ *
+ * @param cpu The CPU device handle
+ * @return A pointer to the bus error unit handle
+ */
+__inline__ struct metal_buserror *
+metal_cpu_get_buserror(struct metal_cpu *cpu) {
+ return cpu->vtable->get_buserror(cpu);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/csr.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/csr.h
new file mode 100644
index 000000000..8375d8a44
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/csr.h
@@ -0,0 +1,32 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__CSR_H
+#define METAL__CSR_H
+
+#include <metal/compiler.h>
+#include <stddef.h>
+#include <stdint.h>
+
+/*!
+ * @file csr.h
+ * @brief A collection of APIs for get and set CSR registers
+ */
+
+/*!
+ * @brief Read a given CSR register without checking validity of CSR offset
+ * @param crs Register label or hex value offset to read from
+ * @param value Variable name of uintprt_t type to get the value
+ */
+#define METAL_CPU_GET_CSR(reg, value) \
+ __asm__ volatile("csrr %0, " #reg : "=r"(value));
+
+/*!
+ * @brief Write to a given CSR register without checking validity of CSR offset
+ * @param crs Register label or hex value offset to write to
+ * @param value Variable name of uintprt_t type to set the value
+ */
+#define METAL_CPU_SET_CSR(reg, value) \
+ __asm__ volatile("csrw " #reg ", %0" : : "r"(value));
+
+#endif // METAL__CSR_H
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-clock.h
index 2647c5981..b25f54144 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-clock.h
@@ -6,8 +6,8 @@
struct __metal_driver_fixed_clock;
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
struct __metal_driver_vtable_fixed_clock {
struct __metal_clock_vtable clock;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-factor-clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-factor-clock.h
index 936ce8d77..84e4fd580 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-factor-clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/fixed-factor-clock.h
@@ -6,8 +6,8 @@
struct __metal_driver_fixed_factor_clock;
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
struct __metal_driver_vtable_fixed_factor_clock {
struct __metal_clock_vtable clock;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_clint0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_clint0.h
index 08d571e1c..ceda473e2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_clint0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_clint0.h
@@ -21,4 +21,7 @@ struct __metal_driver_riscv_clint0 {
};
#undef __METAL_MACHINE_MACROS
+int __metal_driver_riscv_clint0_command_request(
+ struct metal_interrupt *controller, int command, void *data);
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_cpu.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_cpu.h
index eb1e5b8ca..f3005f01f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_cpu.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_cpu.h
@@ -4,148 +4,154 @@
#ifndef METAL__DRIVERS__RISCV_CPU_H
#define METAL__DRIVERS__RISCV_CPU_H
-#include <stdint.h>
-#include <metal/cpu.h>
#include <metal/compiler.h>
+#include <metal/cpu.h>
+#include <stdint.h>
-#define METAL_MAX_CORES 8
-#define METAL_MAX_MI 32 /* Per ISA MCause interrupts 32+ are Reserved */
-#define METAL_MAX_ME 12 /* Per ISA Exception codes 12+ are Reserved */
-#define METAL_DEFAULT_RTC_FREQ 32768
-
-#define METAL_DISABLE 0
-#define METAL_ENABLE 1
-
-#define METAL_ISA_A_EXTENSIONS 0x0001
-#define METAL_ISA_C_EXTENSIONS 0x0004
-#define METAL_ISA_D_EXTENSIONS 0x0008
-#define METAL_ISA_E_EXTENSIONS 0x0010
-#define METAL_ISA_F_EXTENSIONS 0x0020
-#define METAL_ISA_G_EXTENSIONS 0x0040
-#define METAL_ISA_I_EXTENSIONS 0x0100
-#define METAL_ISA_M_EXTENSIONS 0x1000
-#define METAL_ISA_N_EXTENSIONS 0x2000
-#define METAL_ISA_Q_EXTENSIONS 0x10000
-#define METAL_ISA_S_EXTENSIONS 0x40000
-#define METAL_ISA_U_EXTENSIONS 0x100000
-#define METAL_ISA_V_EXTENSIONS 0x200000
-#define METAL_ISA_XL32_EXTENSIONS 0x40000000UL
-#define METAL_ISA_XL64_EXTENSIONS 0x8000000000000000UL
+#define METAL_MAX_CORES 8
+#define METAL_MAX_MI 32 /* Per ISA MCause interrupts 32+ are Reserved */
+#define METAL_MAX_ME 12 /* Per ISA Exception codes 12+ are Reserved */
+#define METAL_DEFAULT_RTC_FREQ 32768
+
+#define METAL_DISABLE 0
+#define METAL_ENABLE 1
+
+#define METAL_ISA_A_EXTENSIONS 0x0001
+#define METAL_ISA_C_EXTENSIONS 0x0004
+#define METAL_ISA_D_EXTENSIONS 0x0008
+#define METAL_ISA_E_EXTENSIONS 0x0010
+#define METAL_ISA_F_EXTENSIONS 0x0020
+#define METAL_ISA_G_EXTENSIONS 0x0040
+#define METAL_ISA_I_EXTENSIONS 0x0100
+#define METAL_ISA_M_EXTENSIONS 0x1000
+#define METAL_ISA_N_EXTENSIONS 0x2000
+#define METAL_ISA_Q_EXTENSIONS 0x10000
+#define METAL_ISA_S_EXTENSIONS 0x40000
+#define METAL_ISA_U_EXTENSIONS 0x100000
+#define METAL_ISA_V_EXTENSIONS 0x200000
+#define METAL_ISA_XL32_EXTENSIONS 0x40000000UL
+#define METAL_ISA_XL64_EXTENSIONS 0x8000000000000000UL
#define METAL_ISA_XL128_EXTENSIONS 0xC000000000000000UL
-#define METAL_MTVEC_DIRECT 0x00
-#define METAL_MTVEC_VECTORED 0x01
-#define METAL_MTVEC_CLIC 0x02
-#define METAL_MTVEC_CLIC_VECTORED 0x03
-#define METAL_MTVEC_CLIC_RESERVED 0x3C
-#define METAL_MTVEC_MASK 0x3F
+#define METAL_MTVEC_DIRECT 0x00
+#define METAL_MTVEC_VECTORED 0x01
+#define METAL_MTVEC_CLIC 0x02
+#define METAL_MTVEC_CLIC_VECTORED 0x03
+#define METAL_MTVEC_CLIC_RESERVED 0x3C
+#define METAL_MTVEC_MASK 0x3F
#if __riscv_xlen == 32
-#define METAL_MCAUSE_INTR 0x80000000UL
-#define METAL_MCAUSE_CAUSE 0x000003FFUL
+#define METAL_MCAUSE_INTR 0x80000000UL
+#define METAL_MCAUSE_CAUSE 0x000003FFUL
#else
-#define METAL_MCAUSE_INTR 0x8000000000000000UL
-#define METAL_MCAUSE_CAUSE 0x00000000000003FFUL
+#define METAL_MCAUSE_INTR 0x8000000000000000UL
+#define METAL_MCAUSE_CAUSE 0x00000000000003FFUL
#endif
-#define METAL_MCAUSE_MINHV 0x40000000UL
-#define METAL_MCAUSE_MPP 0x30000000UL
-#define METAL_MCAUSE_MPIE 0x08000000UL
-#define METAL_MCAUSE_MPIL 0x00FF0000UL
-#define METAL_MSTATUS_MIE 0x00000008UL
-#define METAL_MSTATUS_MPIE 0x00000080UL
-#define METAL_MSTATUS_MPP 0x00001800UL
-#define METAL_MSTATUS_FS_INIT 0x00002000UL
-#define METAL_MSTATUS_FS_CLEAN 0x00004000UL
-#define METAL_MSTATUS_FS_DIRTY 0x00006000UL
-#define METAL_MSTATUS_MPRV 0x00020000UL
-#define METAL_MSTATUS_MXR 0x00080000UL
-#define METAL_MINTSTATUS_MIL 0xFF000000UL
-#define METAL_MINTSTATUS_SIL 0x0000FF00UL
-#define METAL_MINTSTATUS_UIL 0x000000FFUL
-
-#define METAL_LOCAL_INTR(X) (16 + X)
-#define METAL_MCAUSE_EVAL(cause) (cause & METAL_MCAUSE_INTR)
-#define METAL_INTERRUPT(cause) (METAL_MCAUSE_EVAL(cause) ? 1 : 0)
-#define METAL_EXCEPTION(cause) (METAL_MCAUSE_EVAL(cause) ? 0 : 1)
-#define METAL_SW_INTR_EXCEPTION (METAL_MCAUSE_INTR + 3)
-#define METAL_TMR_INTR_EXCEPTION (METAL_MCAUSE_INTR + 7)
-#define METAL_EXT_INTR_EXCEPTION (METAL_MCAUSE_INTR + 11)
+#define METAL_MCAUSE_MINHV 0x40000000UL
+#define METAL_MCAUSE_MPP 0x30000000UL
+#define METAL_MCAUSE_MPIE 0x08000000UL
+#define METAL_MCAUSE_MPIL 0x00FF0000UL
+#define METAL_MSTATUS_MIE 0x00000008UL
+#define METAL_MSTATUS_MPIE 0x00000080UL
+#define METAL_MSTATUS_MPP 0x00001800UL
+#define METAL_MSTATUS_FS_INIT 0x00002000UL
+#define METAL_MSTATUS_FS_CLEAN 0x00004000UL
+#define METAL_MSTATUS_FS_DIRTY 0x00006000UL
+#define METAL_MSTATUS_MPRV 0x00020000UL
+#define METAL_MSTATUS_MXR 0x00080000UL
+#define METAL_MINTSTATUS_MIL 0xFF000000UL
+#define METAL_MINTSTATUS_SIL 0x0000FF00UL
+#define METAL_MINTSTATUS_UIL 0x000000FFUL
+
+#define METAL_LOCAL_INTR(X) (16 + X)
+#define METAL_MCAUSE_EVAL(cause) (cause & METAL_MCAUSE_INTR)
+#define METAL_INTERRUPT(cause) (METAL_MCAUSE_EVAL(cause) ? 1 : 0)
+#define METAL_EXCEPTION(cause) (METAL_MCAUSE_EVAL(cause) ? 0 : 1)
+#define METAL_SW_INTR_EXCEPTION (METAL_MCAUSE_INTR + 3)
+#define METAL_TMR_INTR_EXCEPTION (METAL_MCAUSE_INTR + 7)
+#define METAL_EXT_INTR_EXCEPTION (METAL_MCAUSE_INTR + 11)
#define METAL_LOCAL_INTR_EXCEPTION(X) (METAL_MCAUSE_INTR + METAL_LOCAL_INTR(X))
-#define METAL_LOCAL_INTR_RESERVE0 1
-#define METAL_LOCAL_INTR_RESERVE1 2
-#define METAL_LOCAL_INTR_RESERVE2 4
-#define METAL_LOCAL_INTERRUPT_SW 8 /* Bit3 0x008 */
-#define METAL_LOCAL_INTR_RESERVE4 16
-#define METAL_LOCAL_INTR_RESERVE5 32
-#define METAL_LOCAL_INTR_RESERVE6 64
-#define METAL_LOCAL_INTERRUPT_TMR 128 /* Bit7 0x080 */
-#define METAL_LOCAL_INTR_RESERVE8 256
-#define METAL_LOCAL_INTR_RESERVE9 512
-#define METAL_LOCAL_INTR_RESERVE10 1024
-#define METAL_LOCAL_INTERRUPT_EXT 2048 /* Bit11 0x800 */
+#define METAL_LOCAL_INTR_RESERVE0 1
+#define METAL_LOCAL_INTR_RESERVE1 2
+#define METAL_LOCAL_INTR_RESERVE2 4
+#define METAL_LOCAL_INTERRUPT_SW 8 /* Bit3 0x008 */
+#define METAL_LOCAL_INTR_RESERVE4 16
+#define METAL_LOCAL_INTR_RESERVE5 32
+#define METAL_LOCAL_INTR_RESERVE6 64
+#define METAL_LOCAL_INTERRUPT_TMR 128 /* Bit7 0x080 */
+#define METAL_LOCAL_INTR_RESERVE8 256
+#define METAL_LOCAL_INTR_RESERVE9 512
+#define METAL_LOCAL_INTR_RESERVE10 1024
+#define METAL_LOCAL_INTERRUPT_EXT 2048 /* Bit11 0x800 */
/* Bit12 to Bit15 are Reserved */
-#define METAL_LOCAL_INTERRUPT(X) (0x10000 << X) /* Bit16+ Start of Custom Local Interrupt */
-#define METAL_MIE_INTERRUPT METAL_MSTATUS_MIE
+#define METAL_LOCAL_INTERRUPT(X) \
+ (0x10000 << X) /* Bit16+ Start of Custom Local Interrupt */
+#define METAL_MIE_INTERRUPT METAL_MSTATUS_MIE
+
+#define METAL_INSN_LENGTH_MASK 3
+#define METAL_INSN_NOT_COMPRESSED 3
typedef enum {
- METAL_MACHINE_PRIVILEGE_MODE,
- METAL_SUPERVISOR_PRIVILEGE_MODE,
- METAL_USER_PRIVILEGE_MODE,
+ METAL_MACHINE_PRIVILEGE_MODE,
+ METAL_SUPERVISOR_PRIVILEGE_MODE,
+ METAL_USER_PRIVILEGE_MODE,
} metal_privilege_mode_e;
typedef enum {
- METAL_INTERRUPT_ID_BASE,
- METAL_INTERRUPT_ID_SW = (METAL_INTERRUPT_ID_BASE + 3),
- METAL_INTERRUPT_ID_TMR = (METAL_INTERRUPT_ID_BASE + 7),
- METAL_INTERRUPT_ID_EXT = (METAL_INTERRUPT_ID_BASE + 11),
- METAL_INTERRUPT_ID_LC0 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(0)),
- METAL_INTERRUPT_ID_LC1 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(1)),
- METAL_INTERRUPT_ID_LC2 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(2)),
- METAL_INTERRUPT_ID_LC3 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(3)),
- METAL_INTERRUPT_ID_LC4 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(4)),
- METAL_INTERRUPT_ID_LC5 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(5)),
- METAL_INTERRUPT_ID_LC6 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(6)),
- METAL_INTERRUPT_ID_LC7 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(7)),
- METAL_INTERRUPT_ID_LC8 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(8)),
- METAL_INTERRUPT_ID_LC9 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(9)),
- METAL_INTERRUPT_ID_LC10 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(10)),
- METAL_INTERRUPT_ID_LC11 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(11)),
- METAL_INTERRUPT_ID_LC12 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(12)),
- METAL_INTERRUPT_ID_LC13 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(13)),
- METAL_INTERRUPT_ID_LC14 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(14)),
- METAL_INTERRUPT_ID_LC15 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(15)),
- METAL_INTERRUPT_ID_LCMX,
- METAL_INTERRUPT_ID_GL0 = METAL_INTERRUPT_ID_LCMX,
- METAL_INTERRUPT_ID_GLMX = (METAL_MCAUSE_CAUSE + 1),
+ METAL_INTERRUPT_ID_BASE,
+ METAL_INTERRUPT_ID_SW = (METAL_INTERRUPT_ID_BASE + 3),
+ METAL_INTERRUPT_ID_TMR = (METAL_INTERRUPT_ID_BASE + 7),
+ METAL_INTERRUPT_ID_EXT = (METAL_INTERRUPT_ID_BASE + 11),
+ METAL_INTERRUPT_ID_CSW = (METAL_INTERRUPT_ID_BASE + 12),
+ METAL_INTERRUPT_ID_LC0 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(0)),
+ METAL_INTERRUPT_ID_LC1 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(1)),
+ METAL_INTERRUPT_ID_LC2 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(2)),
+ METAL_INTERRUPT_ID_LC3 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(3)),
+ METAL_INTERRUPT_ID_LC4 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(4)),
+ METAL_INTERRUPT_ID_LC5 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(5)),
+ METAL_INTERRUPT_ID_LC6 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(6)),
+ METAL_INTERRUPT_ID_LC7 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(7)),
+ METAL_INTERRUPT_ID_LC8 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(8)),
+ METAL_INTERRUPT_ID_LC9 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(9)),
+ METAL_INTERRUPT_ID_LC10 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(10)),
+ METAL_INTERRUPT_ID_LC11 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(11)),
+ METAL_INTERRUPT_ID_LC12 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(12)),
+ METAL_INTERRUPT_ID_LC13 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(13)),
+ METAL_INTERRUPT_ID_LC14 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(14)),
+ METAL_INTERRUPT_ID_LC15 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(15)),
+ METAL_INTERRUPT_ID_LCMX,
+ METAL_INTERRUPT_ID_GL0 = METAL_INTERRUPT_ID_LCMX,
+ METAL_INTERRUPT_ID_GLMX = (METAL_MCAUSE_CAUSE + 1),
+ METAL_INTERRUPT_ID_BEU = 128,
} metal_interrupt_id_e;
typedef enum {
- METAL_IAM_EXCEPTION_CODE, /* Instruction address misaligned */
- METAL_IAF_EXCEPTION_CODE, /* Instruction access faultd */
- METAL_II_EXCEPTION_CODE, /* Illegal instruction */
- METAL_BREAK_EXCEPTION_CODE, /* Breakpoint */
- METAL_LAM_EXCEPTION_CODE, /* Load address misaligned */
- METAL_LAF_EXCEPTION_CODE, /* Load access fault */
- METAL_SAMOAM_EXCEPTION_CODE, /* Store/AMO address misaligned */
- METAL_SAMOAF_EXCEPTION_CODE, /* Store/AMO access fault */
- METAL_ECALL_U_EXCEPTION_CODE, /* Environment call from U-mode */
- METAL_R9_EXCEPTION_CODE, /* Reserved */
- METAL_R10_EXCEPTION_CODE, /* Reserved */
- METAL_ECALL_M_EXCEPTION_CODE, /* Environment call from M-mode */
- METAL_MAX_EXCEPTION_CODE,
+ METAL_IAM_EXCEPTION_CODE, /* Instruction address misaligned */
+ METAL_IAF_EXCEPTION_CODE, /* Instruction access faultd */
+ METAL_II_EXCEPTION_CODE, /* Illegal instruction */
+ METAL_BREAK_EXCEPTION_CODE, /* Breakpoint */
+ METAL_LAM_EXCEPTION_CODE, /* Load address misaligned */
+ METAL_LAF_EXCEPTION_CODE, /* Load access fault */
+ METAL_SAMOAM_EXCEPTION_CODE, /* Store/AMO address misaligned */
+ METAL_SAMOAF_EXCEPTION_CODE, /* Store/AMO access fault */
+ METAL_ECALL_U_EXCEPTION_CODE, /* Environment call from U-mode */
+ METAL_R9_EXCEPTION_CODE, /* Reserved */
+ METAL_R10_EXCEPTION_CODE, /* Reserved */
+ METAL_ECALL_M_EXCEPTION_CODE, /* Environment call from M-mode */
+ METAL_MAX_EXCEPTION_CODE,
} metal_exception_code_e;
typedef enum {
- METAL_TIMER_MTIME_GET = 1,
- METAL_SOFTWARE_IPI_CLEAR,
- METAL_SOFTWARE_IPI_SET,
- METAL_SOFTWARE_MSIP_GET,
- METAL_MAX_INTERRUPT_GET,
- METAL_INDEX_INTERRUPT_GET,
+ METAL_TIMER_MTIME_GET = 1,
+ METAL_SOFTWARE_IPI_CLEAR,
+ METAL_SOFTWARE_IPI_SET,
+ METAL_SOFTWARE_MSIP_GET,
+ METAL_MAX_INTERRUPT_GET,
+ METAL_INDEX_INTERRUPT_GET,
} metal_interrup_cmd_e;
typedef struct __metal_interrupt_data {
long long pad : 64;
- metal_interrupt_handler_t handler;
+ metal_interrupt_handler_t handler;
void *sub_int;
void *exint_data;
} __metal_interrupt_data;
@@ -154,30 +160,15 @@ typedef struct __metal_interrupt_data {
uintptr_t __metal_myhart_id(void);
-struct __metal_driver_interrupt_controller_vtable {
- void (*interrupt_init)(struct metal_interrupt *controller);
- int (*interrupt_register)(struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr, void *priv_data);
- int (*interrupt_enable)(struct metal_interrupt *controller, int id);
- int (*interrupt_disable)(struct metal_interrupt *controller, int id);
- int (*command_request)(struct metal_interrupt *intr, int cmd, void *data);
-};
-
struct __metal_driver_vtable_riscv_cpu_intc {
- struct metal_interrupt_vtable controller_vtable;
+ struct metal_interrupt_vtable controller_vtable;
};
-
void __metal_interrupt_global_enable(void);
void __metal_interrupt_global_disable(void);
-void __metal_controller_interrupt_vector(metal_vector_mode mode, void *vec_table);
-inline int __metal_controller_interrupt_is_selective_vectored (void)
-{
- uintptr_t val;
-
- asm volatile ("csrr %0, mtvec" : "=r"(val));
- return ((val & METAL_MTVEC_CLIC_VECTORED) == METAL_MTVEC_CLIC);
-}
+metal_vector_mode __metal_controller_interrupt_vector_mode(void);
+void __metal_controller_interrupt_vector(metal_vector_mode mode,
+ void *vec_table);
__METAL_DECLARE_VTABLE(__metal_driver_vtable_riscv_cpu_intc)
@@ -186,18 +177,20 @@ struct __metal_driver_riscv_cpu_intc {
int init_done;
uintptr_t metal_mtvec_table[METAL_MAX_MI];
__metal_interrupt_data metal_int_table[METAL_MAX_MI];
+ __metal_interrupt_data metal_int_beu;
metal_exception_handler_t metal_exception_table[METAL_MAX_ME];
};
/* CPU driver*/
struct __metal_driver_vtable_cpu {
- struct metal_cpu_vtable cpu_vtable;
+ struct metal_cpu_vtable cpu_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_cpu)
struct __metal_driver_cpu {
struct metal_cpu cpu;
+ unsigned int hpm_count; /* Available HPM counters per CPU */
};
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_plic0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_plic0.h
index 159ee6d69..fac76fbc3 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_plic0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/riscv_plic0.h
@@ -7,10 +7,10 @@
#include <metal/compiler.h>
#include <metal/drivers/riscv_cpu.h>
-#define METAL_PLIC_SOURCE_MASK 0x1F
-#define METAL_PLIC_SOURCE_SHIFT 5
-#define METAL_PLIC_SOURCE_PRIORITY_SHIFT 2
-#define METAL_PLIC_SOURCE_PENDING_SHIFT 0
+#define METAL_PLIC_SOURCE_MASK 0x1F
+#define METAL_PLIC_SOURCE_SHIFT 5
+#define METAL_PLIC_SOURCE_PRIORITY_SHIFT 2
+#define METAL_PLIC_SOURCE_PENDING_SHIFT 0
struct __metal_driver_vtable_riscv_plic0 {
struct metal_interrupt_vtable plic_vtable;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_buserror0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_buserror0.h
new file mode 100644
index 000000000..20972109b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_buserror0.h
@@ -0,0 +1,184 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_BUSERROR0_H
+#define METAL__DRIVERS__SIFIVE_BUSERROR0_H
+
+/*!
+ * @file sifive_buserror0.h
+ *
+ * @brief API for configuring the SiFive Bus Error Unit
+ */
+
+#include <metal/compiler.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+/*!
+ * @brief The set of possible events handled by a SiFive Bus Error Unit
+ */
+typedef enum {
+ /*! @brief No event or error has been detected */
+ METAL_BUSERROR_EVENT_NONE = 0,
+
+ /*! @brief A correctable ECC error has occurred in the I$ or ITIM */
+ METAL_BUSERROR_EVENT_INST_CORRECTABLE_ECC_ERROR = (1 << 2),
+ /*! @brief An uncorrectable ECC error has occurred in the I$ or ITIM */
+ METAL_BUSERROR_EVENT_INST_UNCORRECTABLE_ECC_ERROR = (1 << 3),
+ /*! @brief A TileLink load or store bus error has occurred */
+ METAL_BUSERROR_EVENT_LOAD_STORE_ERROR = (1 << 5),
+ /*! @brief A correctable ECC error has occurred in the D$ or DTIM */
+ METAL_BUSERROR_EVENT_DATA_CORRECTABLE_ECC_ERROR = (1 << 6),
+ /*! @brief An uncorrectable ECC error has occurred in the D$ or DTIM */
+ METAL_BUSERROR_EVENT_DATA_UNCORRECTABLE_ECC_ERROR = (1 << 7),
+
+ /*! @brief Used to set/clear all interrupts or query/clear all accrued
+ events */
+ METAL_BUSERROR_EVENT_ALL =
+ METAL_BUSERROR_EVENT_INST_CORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_INST_UNCORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_LOAD_STORE_ERROR |
+ METAL_BUSERROR_EVENT_DATA_CORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_DATA_UNCORRECTABLE_ECC_ERROR,
+ /*! @brief A synonym of METAL_BUSERROR_EVENT_ALL */
+ METAL_BUSERROR_EVENT_ANY = METAL_BUSERROR_EVENT_ALL,
+
+ /*! @brief A value which is impossible for the bus error unit to report.
+ * Indicates an error has occurred if provided as a return value. */
+ METAL_BUSERROR_EVENT_INVALID = (1 << 8),
+} metal_buserror_event_t;
+
+/*!
+ * @brief The handle for a bus error unit
+ */
+struct metal_buserror {
+ uint8_t __no_empty_structs;
+};
+
+/*!
+ * @brief Enable bus error events
+ *
+ * Enabling bus error events causes them to be registered as accrued and,
+ * if the corresponding interrupt is inabled, trigger interrupts.
+ *
+ * @param beu The bus error unit handle
+ * @param events A mask of error events to enable
+ * @param enabled True if the mask should be enabled, false if they should be
+ * disabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_event_enabled(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Get enabled bus error events
+ * @param beu The bus error unit handle
+ * @return A mask of all enabled events
+ */
+metal_buserror_event_t
+metal_buserror_get_event_enabled(struct metal_buserror *beu);
+
+/*!
+ * @brief Enable or disable the platform interrupt
+ *
+ * @param beu The bus error unit handle
+ * @param event The error event which would trigger the interrupt
+ * @param enabled True if the interrupt should be enabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_platform_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Enable or disable the hart-local interrupt
+ *
+ * @param beu The bus error unit handle
+ * @param event The error event which would trigger the interrupt
+ * @param enabled True if the interrupt should be enabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_local_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Get the error event which caused the most recent interrupt
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The event which caused the interrupt
+ */
+metal_buserror_event_t metal_buserror_get_cause(struct metal_buserror *beu);
+
+/*!
+ * @brief Clear the cause register for the bus error unit
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit to un-latch the cause register for the next event
+ *
+ * @param beu The bus error unit handle
+ * @return 0 upon success
+ */
+int metal_buserror_clear_cause(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the physical address of the error event
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit.
+ *
+ * @param beu The bus error unit handle
+ * @return The address of the error event
+ */
+uintptr_t metal_buserror_get_event_address(struct metal_buserror *beu);
+
+/*!
+ * @brief Returns true if the event is set in the accrued register
+ *
+ * @param beu The bus error unit handle
+ * @param event The event to query
+ * @return True if the event is set in the accrued register
+ */
+bool metal_buserror_is_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events);
+
+/*!
+ * @brief Clear the given event from the accrued register
+ *
+ * @param beu The bus error unit handle
+ * @param event The event to clear
+ * @return 0 upon success
+ */
+int metal_buserror_clear_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events);
+
+/*!
+ * @brief get the platform-level interrupt parent of the bus error unit
+ *
+ * @param beu The bus error unit handle
+ * @return A pointer to the interrupt parent
+ */
+struct metal_interrupt *
+metal_buserror_get_platform_interrupt_parent(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the platform-level interrupt id for the bus error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The interrupt id
+ */
+int metal_buserror_get_platform_interrupt_id(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the hart-local interrupt id for the bus error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The interrupt id
+ */
+int metal_buserror_get_local_interrupt_id(struct metal_buserror *beu);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_ccache0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_ccache0.h
new file mode 100644
index 000000000..13a47c0b9
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_ccache0.h
@@ -0,0 +1,140 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_CCACHE0_H
+#define METAL__DRIVERS__SIFIVE_CCACHE0_H
+
+/*!
+ * @file sifive_ccache0.h
+ *
+ * @brief API for configuring the SiFive L2 cache controller
+ */
+
+#include <metal/interrupt.h>
+#include <stdint.h>
+
+/*! @brief Cache configuration data */
+typedef struct {
+ uint32_t num_bank;
+ uint32_t num_ways;
+ uint32_t num_sets;
+ uint32_t block_size;
+} sifive_ccache0_config;
+
+/*! @brief Set of values for ECC error type */
+typedef enum {
+ SIFIVE_CCACHE0_DATA = 0,
+ SIFIVE_CCACHE0_DIR = 1,
+} sifive_ccache0_ecc_errtype_t;
+
+/*! @brief Initialize cache controller, enables all available
+ * cache-ways.
+ * Note: If LIM is in use, corresponding cache ways are not enabled.
+ * @param None.
+ * @return 0 If no error.*/
+int sifive_ccache0_init(void);
+
+/*! @brief Get cache configuration data.
+ * @param config User specified data buffer.
+ * @return None.*/
+void sifive_ccache0_get_config(sifive_ccache0_config *config);
+
+/*! @brief Get currently active cache ways.
+ * @param None.
+ * @return Number of cache ways enabled.*/
+uint32_t sifive_ccache0_get_enabled_ways(void);
+
+/*! @brief Enable specified cache ways.
+ * @param ways Number of ways to be enabled.
+ * @return 0 If no error.*/
+int sifive_ccache0_set_enabled_ways(uint32_t ways);
+
+/*! @brief Inject ECC error into data or meta-data.
+ * @param bitindex Bit index to be corrupted on next cache operation.
+ * @param type ECC error target location.
+ * @return None.*/
+void sifive_ccache0_inject_ecc_error(uint32_t bitindex,
+ sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Flush out entire cache block containing given address.
+ * @param flush_addr Address for the cache block to be flushed.
+ * @return None.*/
+void sifive_ccache0_flush(uintptr_t flush_addr);
+
+/*! @brief Get most recently ECC corrected address.
+ * @param type ECC error target location.
+ * @return Last corrected ECC address.*/
+uintptr_t sifive_ccache0_get_ecc_fix_addr(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get number of times ECC errors were corrected.
+ * Clears related ECC interrupt signals.
+ * @param type ECC error target location.
+ * @return Corrected ECC error count.*/
+uint32_t sifive_ccache0_get_ecc_fix_count(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get address location of most recent uncorrected ECC error.
+ * @param type ECC error target location.
+ * @return Last uncorrected ECC address.*/
+uintptr_t sifive_ccache0_get_ecc_fail_addr(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get number of times ECC errors were not corrected.
+ * Clears related ECC interrupt signals.
+ * @param type ECC error target location.
+ * @return Uncorrected ECC error count.*/
+uint32_t sifive_ccache0_get_ecc_fail_count(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get currently active way enable mask value for the given master ID.
+ * @param master_id Cache controller master ID.
+ * @return Way enable mask. */
+uint64_t sifive_ccache0_get_way_mask(uint32_t master_id);
+
+/*! @brief Set way enable mask for the given master ID.
+ * @param master_id Cache controller master ID.
+ * @param waymask Specify ways to be enabled.
+ * @return 0 If no error.*/
+int sifive_ccache0_set_way_mask(uint32_t master_id, uint64_t waymask);
+
+/*! @brief Select cache performance events to be counted.
+ * @param counter Cache performance monitor counter index.
+ * @param mask Event selection mask.
+ * @return None.*/
+void sifive_ccache0_set_pmevent_selector(uint32_t counter, uint64_t mask);
+
+/*! @brief Get currently set events for the given counter index.
+ * @param counter Cache performance monitor counter index.
+ * @return Event selection mask.*/
+uint64_t sifive_ccache0_get_pmevent_selector(uint32_t counter);
+
+/*! @brief Clears specified cache performance counter.
+ * @param counter Cache performance monitor counter index.
+ * @return None.*/
+void sifive_ccache0_clr_pmevent_counter(uint32_t counter);
+
+/*! @brief Reads specified cache performance counter.
+ * @param counter Cache performance monitor counter index.
+ * @return Counter value.*/
+uint64_t sifive_ccache0_get_pmevent_counter(uint32_t counter);
+
+/*! @brief Select cache clients to be excluded from performance monitoring.
+ * @param mask Client disable mask.
+ * @return None.*/
+void sifive_ccache0_set_client_filter(uint64_t mask);
+
+/*! @brief Get currently set cache client disable mask.
+ * @param None.
+ * @return Client disable mask.*/
+uint64_t sifive_ccache0_get_client_filter(void);
+
+/*! @brief Get interrupt IDs for the cache controller.
+ * @param src Interrupt trigger source index.
+ * @return Interrupt id.*/
+int sifive_ccache0_get_interrupt_id(uint32_t src);
+
+/*! @brief Get interrupt controller of the cache.
+ * The interrupt controller must be initialized before any interrupts can be
+ * registered or enabled with it.
+ * @param None.
+ * @return Handle for the interrupt controller.*/
+struct metal_interrupt *sifive_ccache0_interrupt_controller(void);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_clic0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_clic0.h
index db9674625..b8ff82271 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_clic0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_clic0.h
@@ -7,21 +7,21 @@
#include <metal/compiler.h>
#include <metal/drivers/riscv_cpu.h>
-#define METAL_CLIC_MAX_NMBITS 2
-#define METAL_CLIC_MAX_NLBITS 8
-#define METAL_CLIC_MAX_NVBITS 1
+#define METAL_CLIC_MAX_NMBITS 2
+#define METAL_CLIC_MAX_NLBITS 8
+#define METAL_CLIC_MAX_NVBITS 1
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MMODE 0x00
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE1 0x20
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE2 0x40
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MASK 0x60
-#define METAL_SIFIVE_CLIC0_CLICCFG_NLBITS_MASK 0x1E
-#define METAL_SIFIVE_CLIC0_CLICCFG_NVBIT_MASK 0x01
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MMODE 0x00
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE1 0x20
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE2 0x40
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MASK 0x60
+#define METAL_SIFIVE_CLIC0_CLICCFG_NLBITS_MASK 0x1E
+#define METAL_SIFIVE_CLIC0_CLICCFG_NVBIT_MASK 0x01
-#define METAL_CLIC_ICTRL_SMODE1_MASK 0x7F /* b8 set imply M-mode */
-#define METAL_CLIC_ICTRL_SMODE2_MASK 0x3F /* b8 set M-mode, b7 clear U-mode */
+#define METAL_CLIC_ICTRL_SMODE1_MASK 0x7F /* b8 set imply M-mode */
+#define METAL_CLIC_ICTRL_SMODE2_MASK 0x3F /* b8 set M-mode, b7 clear U-mode */
-#define METAL_MAX_INTERRUPT_LEVEL ((1 << METAL_CLIC_MAX_NLBITS) - 1)
+#define METAL_MAX_INTERRUPT_LEVEL ((1 << METAL_CLIC_MAX_NLBITS) - 1)
struct __metal_driver_vtable_sifive_clic0 {
struct metal_interrupt_vtable clic_vtable;
@@ -34,9 +34,15 @@ __METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_clic0)
struct __metal_driver_sifive_clic0 {
struct metal_interrupt controller;
int init_done;
- metal_interrupt_handler_t metal_mtvt_table[__METAL_CLIC_SUBINTERRUPTS];
+ struct {
+ } __attribute__((aligned(64)));
+ metal_interrupt_vector_handler_t
+ metal_mtvt_table[__METAL_CLIC_SUBINTERRUPTS];
__metal_interrupt_data metal_exint_table[__METAL_CLIC_SUBINTERRUPTS];
};
#undef __METAL_MACHINE_MACROS
+int __metal_driver_sifive_clic0_command_request(
+ struct metal_interrupt *controller, int command, void *data);
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_hfrosc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_hfrosc.h
index d311f0cf2..d60d3a3bd 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_hfrosc.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_hfrosc.h
@@ -4,9 +4,9 @@
#ifndef METAL__DRIVERS__SIFIVE_FE310_G000_HFROSC_H
#define METAL__DRIVERS__SIFIVE_FE310_G000_HFROSC_H
-#include <metal/drivers/sifive_fe310-g000_prci.h>
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/sifive_fe310-g000_prci.h>
#include <metal/io.h>
struct __metal_driver_vtable_sifive_fe310_g000_hfrosc {
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_lfrosc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_lfrosc.h
new file mode 100644
index 000000000..2650584ad
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_lfrosc.h
@@ -0,0 +1,21 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_FE310_G000_LFROSC_H
+#define METAL__DRIVERS__SIFIVE_FE310_G000_LFROSC_H
+
+#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/io.h>
+
+struct __metal_driver_vtable_sifive_fe310_g000_lfrosc {
+ struct __metal_clock_vtable clock;
+};
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_fe310_g000_lfrosc)
+
+struct __metal_driver_sifive_fe310_g000_lfrosc {
+ struct metal_clock clock;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_prci.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_prci.h
index 87c9ca985..4fca30167 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_prci.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fe310-g000_prci.h
@@ -10,14 +10,16 @@
struct __metal_driver_sifive_fe310_g000_prci;
struct __metal_driver_vtable_sifive_fe310_g000_prci {
- long (*get_reg)(const struct __metal_driver_sifive_fe310_g000_prci *, long offset);
- long (*set_reg)(const struct __metal_driver_sifive_fe310_g000_prci *, long offset, long value);
+ long (*get_reg)(const struct __metal_driver_sifive_fe310_g000_prci *,
+ long offset);
+ long (*set_reg)(const struct __metal_driver_sifive_fe310_g000_prci *,
+ long offset, long value);
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_fe310_g000_prci)
struct __metal_driver_sifive_fe310_g000_prci {
+ const struct __metal_driver_vtable_sifive_fe310_g000_prci *vtable;
};
#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fu540-c000_l2.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fu540-c000_l2.h
deleted file mode 100644
index 8c3cf907e..000000000
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_fu540-c000_l2.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Copyright 2018 SiFive, Inc */
-/* SPDX-License-Identifier: Apache-2.0 */
-
-#ifndef METAL__DRIVERS__SIFIVE_FU540_C000_L2_H
-#define METAL__DRIVERS__SIFIVE_FU540_C000_L2_H
-
-struct __metal_driver_sifive_fu540_c000_l2;
-
-#include <stdint.h>
-#include <metal/cache.h>
-
-struct __metal_driver_vtable_sifive_fu540_c000_l2 {
- struct __metal_cache_vtable cache;
-};
-
-__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_fu540_c000_l2)
-
-struct __metal_driver_sifive_fu540_c000_l2 {
- struct metal_cache cache;
-};
-
-#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-buttons.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-buttons.h
index a0caeaba8..7227eee02 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-buttons.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-buttons.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_BUTTONS_H
#define METAL__DRIVERS__SIFIVE_GPIO_BUTTONS_H
-#include <string.h>
#include <metal/button.h>
#include <metal/compiler.h>
+#include <string.h>
struct __metal_driver_vtable_sifive_button {
- struct metal_button_vtable button_vtable;
+ struct metal_button_vtable button_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_button)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-leds.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-leds.h
index a8dacf116..abfca01c2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-leds.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-leds.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_LEDS_H
#define METAL__DRIVERS__SIFIVE_GPIO_LEDS_H
+#include <metal/compiler.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/led.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_led {
- struct metal_led_vtable led_vtable;
+ struct metal_led_vtable led_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_led)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-switches.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-switches.h
index c9c7839e9..be55a0446 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-switches.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio-switches.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_SWITCHES_H
#define METAL__DRIVERS__SIFIVE_GPIO_SWITCHES_H
+#include <metal/compiler.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/switch.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_switch {
- struct metal_switch_vtable switch_vtable;
+ struct metal_switch_vtable switch_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_switch)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio0.h
index cc56dc722..50314222d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_gpio0.h
@@ -11,7 +11,7 @@ struct __metal_driver_vtable_sifive_gpio0 {
const struct __metal_gpio_vtable gpio;
};
-//struct __metal_driver_sifive_gpio0;
+// struct __metal_driver_sifive_gpio0;
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_gpio0)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_i2c0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_i2c0.h
new file mode 100644
index 000000000..8fbbe21e1
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_i2c0.h
@@ -0,0 +1,24 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_I2C0_H
+#define METAL__DRIVERS__SIFIVE_I2C0_H
+
+#include <metal/clock.h>
+#include <metal/i2c.h>
+
+struct __metal_driver_vtable_sifive_i2c0 {
+ const struct metal_i2c_vtable i2c;
+};
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_i2c0)
+
+struct __metal_driver_sifive_i2c0 {
+ struct metal_i2c i2c;
+ unsigned int init_done;
+ unsigned int baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_l2pf0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_l2pf0.h
new file mode 100644
index 000000000..63c8e6536
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_l2pf0.h
@@ -0,0 +1,78 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_L2PF0_H
+#define METAL__DRIVERS__SIFIVE_L2PF0_H
+
+/*!
+ * @file sifive_l2pf0.h
+ *
+ * @brief API for configuring the SiFive L2 prefetcher.
+ */
+
+#include <stdint.h>
+
+/*! @brief L2 prefetcher configuration */
+typedef struct {
+ /* Enable L2 hardware prefetcher */
+ uint8_t HwPrefetchEnable;
+
+ /* Only works when CrossPageEn === 0.
+ Cross Page optimization disable:
+ 0 -> Entry goes into Pause state while crossing Page boundary.
+ Next time when the demand miss happens on the same page, it doesn’t need
+ to train again. 1 -> The entry is invalidated in case of a cross page. */
+ uint8_t CrossPageOptmDisable;
+
+ /* Enable prefetches to cross pages */
+ uint8_t CrossPageEn;
+
+ /* Age-out mechanism enable */
+ uint8_t AgeOutEn;
+
+ uint32_t PrefetchDistance;
+
+ uint32_t MaxAllowedDistance;
+
+ /* Linear to exponential threshold */
+ uint32_t LinToExpThreshold;
+
+ /* No. of non-matching loads to edge out an entry */
+ uint32_t NumLdsToAgeOut;
+
+ /* Threshold no. of Fullness (L2 MSHRs used/ total available) to stop
+ * sending hits */
+ uint32_t QFullnessThreshold;
+
+ /* Threshold no. of CacheHits for evicting SPF entry */
+ uint32_t HitCacheThreshold;
+
+ /* Threshold no. of MSHR hits for increasing SPF distance */
+ uint32_t hitMSHRThreshold;
+
+ /* Size of the comparison window for address matching */
+ uint32_t Window;
+
+} sifive_l2pf0_config;
+
+/*! @brief Enable L2 hardware prefetcher unit.
+ * @param None.
+ * @return None.*/
+void sifive_l2pf0_enable(void);
+
+/*! @brief Disable L2 hardware prefetcher unit.
+ * @param None.
+ * @return None.*/
+void sifive_l2pf0_disable(void);
+
+/*! @brief Get currently active L2 prefetcher configuration.
+ * @param config Pointer to user specified configuration structure.
+ * @return None.*/
+void sifive_l2pf0_get_config(sifive_l2pf0_config *config);
+
+/*! @brief Enables fine grain access to L2 prefetcher configuration.
+ * @param config Pointer to user structure with values to be set.
+ * @return None.*/
+void sifive_l2pf0_set_config(sifive_l2pf0_config *config);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_local-external-interrupts0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_local-external-interrupts0.h
index aa8d63078..320ab10d2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_local-external-interrupts0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_local-external-interrupts0.h
@@ -18,5 +18,4 @@ struct __metal_driver_sifive_local_external_interrupts0 {
int init_done;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_pwm0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_pwm0.h
new file mode 100644
index 000000000..caa774401
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_pwm0.h
@@ -0,0 +1,29 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_PWM0_H
+#define METAL__DRIVERS__SIFIVE_PWM0_H
+
+#include <metal/clock.h>
+#include <metal/pwm.h>
+
+struct __metal_driver_vtable_sifive_pwm0 {
+ const struct metal_pwm_vtable pwm;
+};
+
+/* Max possible PWM channel count */
+#define METAL_MAX_PWM_CHANNELS 16
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_pwm0)
+
+struct __metal_driver_sifive_pwm0 {
+ struct metal_pwm pwm;
+ unsigned int max_count;
+ unsigned int count_val;
+ unsigned int freq;
+ unsigned int duty[METAL_MAX_PWM_CHANNELS];
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_rtc0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_rtc0.h
new file mode 100644
index 000000000..a35ab9a09
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_rtc0.h
@@ -0,0 +1,26 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_RTC0_H
+#define METAL__DRIVERS__SIFIVE_RTC0_H
+
+#include <metal/compiler.h>
+#include <metal/io.h>
+
+#include <metal/clock.h>
+#include <metal/interrupt.h>
+#include <metal/rtc.h>
+
+struct __metal_driver_vtable_sifive_rtc0 {
+ const struct metal_rtc_vtable rtc;
+};
+
+struct __metal_driver_sifive_rtc0;
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_rtc0)
+
+struct __metal_driver_sifive_rtc0 {
+ const struct metal_rtc rtc;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_simuart0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_simuart0.h
new file mode 100644
index 000000000..f6b739143
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_simuart0.h
@@ -0,0 +1,29 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_SIMUART0_H
+#define METAL__DRIVERS__SIFIVE_SIMUART0_H
+
+#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/riscv_plic0.h>
+#include <metal/drivers/sifive_gpio0.h>
+#include <metal/io.h>
+#include <metal/uart.h>
+
+struct __metal_driver_vtable_sifive_simuart0 {
+ const struct metal_uart_vtable uart;
+};
+
+struct __metal_driver_sifive_simuart0;
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_simuart0)
+
+struct __metal_driver_sifive_simuart0 {
+ struct metal_uart uart;
+ unsigned long baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_spi0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_spi0.h
index 90d4c831e..73527944b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_spi0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_spi0.h
@@ -4,9 +4,9 @@
#ifndef METAL__DRIVERS__SIFIVE_SPI0_H
#define METAL__DRIVERS__SIFIVE_SPI0_H
-#include <metal/drivers/sifive_gpio0.h>
#include <metal/clock.h>
#include <metal/compiler.h>
+#include <metal/drivers/sifive_gpio0.h>
#include <metal/io.h>
#include <metal/spi.h>
@@ -19,6 +19,8 @@ __METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_spi0)
struct __metal_driver_sifive_spi0 {
struct metal_spi spi;
unsigned long baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
};
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_test0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_test0.h
index e87db2c83..debd3fb9d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_test0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_test0.h
@@ -17,5 +17,4 @@ struct __metal_driver_sifive_test0 {
struct __metal_shutdown shutdown;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_trace.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_trace.h
new file mode 100644
index 000000000..3c67522f4
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_trace.h
@@ -0,0 +1,23 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_TRACE_H
+#define METAL__DRIVERS__SIFIVE_TRACE_H
+
+#include <metal/compiler.h>
+#include <metal/io.h>
+#include <metal/uart.h>
+
+struct __metal_driver_vtable_sifive_trace {
+ const struct metal_uart_vtable uart;
+};
+
+struct __metal_driver_sifive_trace;
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_trace)
+
+struct __metal_driver_sifive_trace {
+ struct metal_uart uart;
+};
+
+#endif /* METAL__DRIVERS__SIFIVE_TRACE_H */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_uart0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_uart0.h
index 11d954002..2b38e4631 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_uart0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_uart0.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_UART0_H
#define METAL__DRIVERS__SIFIVE_UART0_H
-#include <metal/drivers/sifive_gpio0.h>
-#include <metal/drivers/riscv_plic0.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/riscv_plic0.h>
+#include <metal/drivers/sifive_gpio0.h>
#include <metal/io.h>
#include <metal/uart.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_uart0 {
const struct metal_uart_vtable uart;
@@ -22,7 +22,8 @@ __METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_uart0)
struct __metal_driver_sifive_uart0 {
struct metal_uart uart;
unsigned long baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_wdog0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_wdog0.h
new file mode 100644
index 000000000..bb3424584
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/sifive_wdog0.h
@@ -0,0 +1,26 @@
+/* Copyright 2018 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_WDOG0_H
+#define METAL__DRIVERS__SIFIVE_WDOG0_H
+
+#include <metal/compiler.h>
+#include <metal/io.h>
+
+#include <metal/clock.h>
+#include <metal/interrupt.h>
+#include <metal/watchdog.h>
+
+struct __metal_driver_vtable_sifive_wdog0 {
+ const struct metal_watchdog_vtable watchdog;
+};
+
+struct __metal_driver_sifive_wdog0;
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_wdog0)
+
+struct __metal_driver_sifive_wdog0 {
+ const struct metal_watchdog watchdog;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/ucb_htif0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/ucb_htif0.h
new file mode 100644
index 000000000..210d0819b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/drivers/ucb_htif0.h
@@ -0,0 +1,48 @@
+/* Copyright 2018 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__UCB_HTIF0_H
+#define METAL__DRIVERS__UCB_HTIF0_H
+
+#include <metal/compiler.h>
+#include <metal/shutdown.h>
+#include <metal/uart.h>
+
+struct __metal_driver_vtable_ucb_htif0_shutdown {
+ const struct __metal_shutdown_vtable shutdown;
+};
+
+struct __metal_driver_vtable_ucb_htif0_uart {
+ const struct metal_uart_vtable uart;
+};
+
+struct __metal_driver_ucb_htif0;
+
+void __metal_driver_ucb_htif0_exit(const struct __metal_shutdown *test,
+ int code) __attribute__((noreturn));
+
+void __metal_driver_ucb_htif0_init(struct metal_uart *uart, int baud_rate);
+int __metal_driver_ucb_htif0_putc(struct metal_uart *uart, int c);
+int __metal_driver_ucb_htif0_getc(struct metal_uart *uart, int *c);
+int __metal_driver_ucb_htif0_get_baud_rate(struct metal_uart *guart);
+int __metal_driver_ucb_htif0_set_baud_rate(struct metal_uart *guart,
+ int baud_rate);
+struct metal_interrupt *
+__metal_driver_ucb_htif0_interrupt_controller(struct metal_uart *uart);
+int __metal_driver_ucb_htif0_get_interrupt_id(struct metal_uart *uart);
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_ucb_htif0_shutdown)
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_ucb_htif0_uart)
+
+struct __metal_driver_ucb_htif0_shutdown {
+ struct __metal_shutdown shutdown;
+ const struct __metal_driver_vtable_ucb_htif0_shutdown *vtable;
+};
+
+struct __metal_driver_ucb_htif0_uart {
+ struct metal_uart uart;
+ const struct __metal_driver_vtable_ucb_htif0_uart *vtable;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/gpio.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/gpio.h
index 513687dd7..df9adb451 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/gpio.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/gpio.h
@@ -5,6 +5,7 @@
#define METAL__GPIO_H
#include <metal/compiler.h>
+#include <metal/interrupt.h>
/*!
* @file gpio.h
@@ -15,20 +16,37 @@ struct metal_gpio;
struct __metal_gpio_vtable {
int (*disable_input)(struct metal_gpio *, long pins);
+ int (*enable_input)(struct metal_gpio *, long pins);
+ long (*input)(struct metal_gpio *);
long (*output)(struct metal_gpio *);
+ int (*disable_output)(struct metal_gpio *, long pins);
int (*enable_output)(struct metal_gpio *, long pins);
int (*output_set)(struct metal_gpio *, long value);
int (*output_clear)(struct metal_gpio *, long value);
int (*output_toggle)(struct metal_gpio *, long value);
int (*enable_io)(struct metal_gpio *, long pins, long dest);
+ int (*disable_io)(struct metal_gpio *, long pins);
+ int (*config_int)(struct metal_gpio *, long pins, int intr_type);
+ int (*clear_int)(struct metal_gpio *, long pins, int intr_type);
+ struct metal_interrupt *(*interrupt_controller)(struct metal_gpio *gpio);
+ int (*get_interrupt_id)(struct metal_gpio *gpio, int pin);
};
+#define METAL_GPIO_INT_DISABLE 0
+#define METAL_GPIO_INT_RISING 1
+#define METAL_GPIO_INT_FALLING 2
+#define METAL_GPIO_INT_BOTH_EDGE 3
+#define METAL_GPIO_INT_LOW 4
+#define METAL_GPIO_INT_HIGH 5
+#define METAL_GPIO_INT_BOTH_LEVEL 6
+#define METAL_GPIO_INT_MAX 7
+
/*!
* @struct metal_gpio
* @brief The handle for a GPIO interface
*/
struct metal_gpio {
- const struct __metal_gpio_vtable *vtable;
+ const struct __metal_gpio_vtable *vtable;
};
/*!
@@ -36,7 +54,21 @@ struct metal_gpio {
* @param device_num The GPIO device index
* @return The GPIO device handle, or NULL if there is no device at that index
*/
-struct metal_gpio *metal_gpio_get_device(int device_num);
+struct metal_gpio *metal_gpio_get_device(unsigned int device_num);
+
+/*!
+ * @brief enable input on a pin
+ * @param gpio The handle for the GPIO interface
+ * @param pin The pin number indexed from 0
+ * @return 0 if the input is successfully enabled
+ */
+__inline__ int metal_gpio_enable_input(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
+ }
+
+ return gpio->vtable->enable_input(gpio, (1 << pin));
+}
/*!
* @brief Disable input on a pin
@@ -44,9 +76,9 @@ struct metal_gpio *metal_gpio_get_device(int device_num);
* @param pin The pin number indexed from 0
* @return 0 if the input is successfully disabled
*/
-inline int metal_gpio_disable_input(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_disable_input(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->disable_input(gpio, (1 << pin));
@@ -58,30 +90,64 @@ inline int metal_gpio_disable_input(struct metal_gpio *gpio, int pin) {
* @param pin The pin number indexed from 0
* @return 0 if the output is successfully enabled
*/
-inline int metal_gpio_enable_output(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_enable_output(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->enable_output(gpio, (1 << pin));
}
/*!
+ * @brief Disable output on a pin
+ * @param gpio The handle for the GPIO interface
+ * @param pin The pin number indexed from 0
+ * @return 0 if the output is successfully disabled
+ */
+__inline__ int metal_gpio_disable_output(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
+ }
+
+ return gpio->vtable->disable_output(gpio, (1 << pin));
+}
+
+/*!
* @brief Set the output value of a GPIO pin
* @param gpio The handle for the GPIO interface
* @param pin The pin number indexed from 0
* @param value The value to set the pin to
* @return 0 if the output is successfully set
*/
-inline int metal_gpio_set_pin(struct metal_gpio *gpio, int pin, int value) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_set_pin(struct metal_gpio *gpio, int pin, int value) {
+ if (!gpio) {
+ return 1;
+ }
+
+ if (value == 0) {
+ return gpio->vtable->output_clear(gpio, (1 << pin));
+ } else {
+ return gpio->vtable->output_set(gpio, (1 << pin));
}
+}
+
+/*!
+ * @brief Get the value of the GPIO pin
+ * @param gpio The handle for the GPIO interface
+ * @param pin The pin number indexed from 0
+ * @return The value of the GPIO pin
+ */
+__inline__ int metal_gpio_get_input_pin(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 0;
+ }
+
+ long value = gpio->vtable->input(gpio);
- if(value == 0) {
- return gpio->vtable->output_clear(gpio, (1 << pin));
+ if (value & (1 << pin)) {
+ return 1;
} else {
- return gpio->vtable->output_set(gpio, (1 << pin));
+ return 0;
}
}
@@ -91,17 +157,17 @@ inline int metal_gpio_set_pin(struct metal_gpio *gpio, int pin, int value) {
* @param pin The pin number indexed from 0
* @return The value of the GPIO pin
*/
-inline int metal_gpio_get_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 0;
+__inline__ int metal_gpio_get_output_pin(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 0;
}
long value = gpio->vtable->output(gpio);
- if(value & (1 << pin)) {
- return 1;
+ if (value & (1 << pin)) {
+ return 1;
} else {
- return 0;
+ return 0;
}
}
@@ -111,9 +177,9 @@ inline int metal_gpio_get_pin(struct metal_gpio *gpio, int pin) {
* @param pin The pin number indexed from 0
* @return 0 if the pin is successfully cleared
*/
-inline int metal_gpio_clear_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_clear_pin(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->output_clear(gpio, (1 << pin));
@@ -125,9 +191,9 @@ inline int metal_gpio_clear_pin(struct metal_gpio *gpio, int pin) {
* @param pin The pin number indexed from 0
* @return 0 if the pin is successfully toggled
*/
-inline int metal_gpio_toggle_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_toggle_pin(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->output_toggle(gpio, (1 << pin));
@@ -140,12 +206,82 @@ inline int metal_gpio_toggle_pin(struct metal_gpio *gpio, int pin) {
* @param io_function The IO function to set
* @return 0 if the pinmux is successfully set
*/
-inline int metal_gpio_enable_pinmux(struct metal_gpio *gpio, int pin, int io_function) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_enable_pinmux(struct metal_gpio *gpio, int pin,
+ int io_function) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->enable_io(gpio, (1 << pin), (io_function << pin));
}
+/*!
+ * @brief Disables the pinmux for a GPIO pin
+ * @param gpio The handle for the GPIO interface
+ * @param pin The bitmask for the pin to disable pinmux on
+ * @return 0 if the pinmux is successfully set
+ */
+__inline__ int metal_gpio_disable_pinmux(struct metal_gpio *gpio, int pin) {
+ if (!gpio) {
+ return 1;
+ }
+
+ return gpio->vtable->disable_io(gpio, (1 << pin));
+}
+
+/*!
+ * @brief Config gpio interrupt type
+ * @param gpio The handle for the GPIO interface
+ * @param pin The bitmask for the pin to enable gpio interrupt
+ * @param intr_type The interrupt type
+ * @return 0 if the interrupt mode is setup properly
+ */
+__inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio, int pin,
+ int intr_type) {
+ if (!gpio) {
+ return 1;
+ }
+
+ return gpio->vtable->config_int(gpio, (1 << pin), intr_type);
+}
+
+/*!
+ * @brief Clear gpio interrupt status
+ * @param gpio The handle for the GPIO interface
+ * @param pin The bitmask for the pin to clear gpio interrupt
+ * @param intr_type The interrupt type to be clear
+ * @return 0 if the interrupt is cleared
+ */
+__inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio, int pin,
+ int intr_type) {
+ if (!gpio) {
+ return 1;
+ }
+
+ return gpio->vtable->clear_int(gpio, (1 << pin), intr_type);
+}
+
+/*!
+ * @brief Get the interrupt controller for a gpio
+ *
+ * @param gpio The handle for the gpio
+ * @return A pointer to the interrupt controller responsible for handling
+ * gpio interrupts.
+ */
+__inline__ struct metal_interrupt *
+metal_gpio_interrupt_controller(struct metal_gpio *gpio) {
+ return gpio->vtable->interrupt_controller(gpio);
+}
+
+/*!
+ * @brief Get the interrupt id for a gpio
+ *
+ * @param gpio The handle for the gpio
+ * @param pin The bitmask for the pin to get gpio interrupt id
+ * @return The interrupt id corresponding to a gpio.
+ */
+__inline__ int metal_gpio_get_interrupt_id(struct metal_gpio *gpio, int pin) {
+ return gpio->vtable->get_interrupt_id(gpio, pin);
+}
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/hpm.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/hpm.h
new file mode 100644
index 000000000..290f7ec3f
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/hpm.h
@@ -0,0 +1,146 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__HPM_H
+#define METAL__HPM_H
+
+#include <metal/cpu.h>
+
+/*! @brief Macros for valid Event IDs */
+#define METAL_HPM_EVENTID_8 (1UL << 8)
+#define METAL_HPM_EVENTID_9 (1UL << 9)
+#define METAL_HPM_EVENTID_10 (1UL << 10)
+#define METAL_HPM_EVENTID_11 (1UL << 11)
+#define METAL_HPM_EVENTID_12 (1UL << 12)
+#define METAL_HPM_EVENTID_13 (1UL << 13)
+#define METAL_HPM_EVENTID_14 (1UL << 14)
+#define METAL_HPM_EVENTID_15 (1UL << 15)
+#define METAL_HPM_EVENTID_16 (1UL << 16)
+#define METAL_HPM_EVENTID_17 (1UL << 17)
+#define METAL_HPM_EVENTID_18 (1UL << 18)
+#define METAL_HPM_EVENTID_19 (1UL << 19)
+#define METAL_HPM_EVENTID_20 (1UL << 20)
+#define METAL_HPM_EVENTID_21 (1UL << 21)
+#define METAL_HPM_EVENTID_22 (1UL << 22)
+#define METAL_HPM_EVENTID_23 (1UL << 23)
+#define METAL_HPM_EVENTID_24 (1UL << 24)
+#define METAL_HPM_EVENTID_25 (1UL << 25)
+#define METAL_HPM_EVENTID_26 (1UL << 26)
+#define METAL_HPM_EVENTID_27 (1UL << 27)
+#define METAL_HPM_EVENTID_28 (1UL << 28)
+#define METAL_HPM_EVENTID_29 (1UL << 29)
+#define METAL_HPM_EVENTID_30 (1UL << 30)
+#define METAL_HPM_EVENTID_31 (1UL << 31)
+
+/*! @brief Macros for valid Event Class */
+#define METAL_HPM_EVENTCLASS_0 (0UL)
+#define METAL_HPM_EVENTCLASS_1 (1UL)
+#define METAL_HPM_EVENTCLASS_2 (2UL)
+#define METAL_HPM_EVENTCLASS_3 (3UL)
+#define METAL_HPM_EVENTCLASS_4 (4UL)
+#define METAL_HPM_EVENTCLASS_5 (5UL)
+#define METAL_HPM_EVENTCLASS_6 (6UL)
+#define METAL_HPM_EVENTCLASS_7 (7UL)
+#define METAL_HPM_EVENTCLASS_8 (8UL)
+
+/*! @brief Enums for available HPM counters */
+typedef enum {
+ METAL_HPM_CYCLE = 0,
+ METAL_HPM_TIME = 1,
+ METAL_HPM_INSTRET = 2,
+ METAL_HPM_COUNTER_3 = 3,
+ METAL_HPM_COUNTER_4 = 4,
+ METAL_HPM_COUNTER_5 = 5,
+ METAL_HPM_COUNTER_6 = 6,
+ METAL_HPM_COUNTER_7 = 7,
+ METAL_HPM_COUNTER_8 = 8,
+ METAL_HPM_COUNTER_9 = 9,
+ METAL_HPM_COUNTER_10 = 10,
+ METAL_HPM_COUNTER_11 = 11,
+ METAL_HPM_COUNTER_12 = 12,
+ METAL_HPM_COUNTER_13 = 13,
+ METAL_HPM_COUNTER_14 = 14,
+ METAL_HPM_COUNTER_15 = 15,
+ METAL_HPM_COUNTER_16 = 16,
+ METAL_HPM_COUNTER_17 = 17,
+ METAL_HPM_COUNTER_18 = 18,
+ METAL_HPM_COUNTER_19 = 19,
+ METAL_HPM_COUNTER_20 = 20,
+ METAL_HPM_COUNTER_21 = 21,
+ METAL_HPM_COUNTER_22 = 22,
+ METAL_HPM_COUNTER_23 = 23,
+ METAL_HPM_COUNTER_24 = 24,
+ METAL_HPM_COUNTER_25 = 25,
+ METAL_HPM_COUNTER_26 = 26,
+ METAL_HPM_COUNTER_27 = 27,
+ METAL_HPM_COUNTER_28 = 28,
+ METAL_HPM_COUNTER_29 = 29,
+ METAL_HPM_COUNTER_30 = 30,
+ METAL_HPM_COUNTER_31 = 31
+} metal_hpm_counter;
+
+/*! @brief Initialize hardware performance monitor counters.
+ * @param cpu The CPU device handle.
+ * @return 0 If no error.*/
+int metal_hpm_init(struct metal_cpu *cpu);
+
+/*! @brief Disables hardware performance monitor counters.
+ * Note - Disabled HPM counters may reduce power consumption.
+ * @param cpu The CPU device handle.
+ * @return 0 If no error.*/
+int metal_hpm_disable(struct metal_cpu *cpu);
+
+/*! @brief Set events which will cause the specified counter to increment.
+ * Counter will start incrementing from the moment events are set.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter to be incremented by selected events.
+ * @param bitmask Bit-mask to select events for a particular counter,
+ * refer core reference manual for selection of events.
+ * Event bit mask is partitioned as follows:
+ * [XLEN-1:8] - Event selection mask [7:0] - Event class
+ * @return 0 If no error.*/
+int metal_hpm_set_event(struct metal_cpu *cpu, metal_hpm_counter counter,
+ unsigned int bitmask);
+
+/*! @brief Get events selection mask set for specified counter.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return Event selection bit mask. refer core reference manual for details.*/
+unsigned int metal_hpm_get_event(struct metal_cpu *cpu,
+ metal_hpm_counter counter);
+
+/*! @brief Clear event selector bits as per specified bit-mask.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_clr_event(struct metal_cpu *cpu, metal_hpm_counter counter,
+ unsigned int bitmask);
+
+/*! @brief Enable counter access to next lower privilege mode.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_enable_access(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+/*! @brief Disable counter access to next lower privilege mode.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_disable_access(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+/*! @brief Reads current value of specified hardware counter.
+ * Note: 'mtime' register is memory mapped into CLINT block.
+ * Use CLINT APIs to access this register.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return Current value of hardware counter on success, 0 on failure.*/
+unsigned long long metal_hpm_read_counter(struct metal_cpu *cpu,
+ metal_hpm_counter counter);
+
+/*! @brief Clears off specified counter.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_clear_counter(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/i2c.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/i2c.h
new file mode 100644
index 000000000..baf62e5d6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/i2c.h
@@ -0,0 +1,112 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__I2C_H
+#define METAL__I2C_H
+
+/*! @brief Enums to enable/disable stop condition. */
+typedef enum {
+ METAL_I2C_STOP_DISABLE = 0,
+ METAL_I2C_STOP_ENABLE = 1
+} metal_i2c_stop_bit_t;
+
+/*! @brief Enums to set up I2C device modes. */
+typedef enum { METAL_I2C_SLAVE = 0, METAL_I2C_MASTER = 1 } metal_i2c_mode_t;
+
+struct metal_i2c;
+
+struct metal_i2c_vtable {
+ void (*init)(struct metal_i2c *i2c, unsigned int baud_rate,
+ metal_i2c_mode_t mode);
+ int (*write)(struct metal_i2c *i2c, unsigned int addr, unsigned int len,
+ unsigned char buf[], metal_i2c_stop_bit_t stop_bit);
+ int (*read)(struct metal_i2c *i2c, unsigned int addr, unsigned int len,
+ unsigned char buf[], metal_i2c_stop_bit_t stop_bit);
+ int (*transfer)(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen);
+ int (*get_baud_rate)(struct metal_i2c *i2c);
+ int (*set_baud_rate)(struct metal_i2c *i2c, unsigned int baud_rate);
+};
+
+/*! @brief A handle for a I2C device. */
+struct metal_i2c {
+ const struct metal_i2c_vtable *vtable;
+};
+
+/*! @brief Get a handle for a I2C device.
+ * @param device_num The index of the desired I2C device.
+ * @return A handle to the I2C device, or NULL if the device does not exist.*/
+struct metal_i2c *metal_i2c_get_device(unsigned int device_num);
+
+/*! @brief Initialize a I2C device with a certain baud rate.
+ * @param i2c The handle for the I2C device to initialize.
+ * @param baud_rate The baud rate for the I2C device to operate at.
+ * @param mode I2C operation mode.
+ */
+inline void metal_i2c_init(struct metal_i2c *i2c, unsigned int baud_rate,
+ metal_i2c_mode_t mode) {
+ i2c->vtable->init(i2c, baud_rate, mode);
+}
+
+/*! @brief Perform a I2C write.
+ * @param i2c The handle for the I2C device to perform the write operation.
+ * @param addr The I2C slave address for the write operation.
+ * @param len The number of bytes to transfer.
+ * @param buf The buffer to send over the I2C bus. Must be len bytes long.
+ * @param stop_bit Enable / Disable STOP condition.
+ * @return 0 if the write succeeds.
+ */
+inline int metal_i2c_write(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ return i2c->vtable->write(i2c, addr, len, buf, stop_bit);
+}
+
+/*! @brief Perform a I2C read.
+ * @param i2c The handle for the I2C device to perform the read operation.
+ * @param addr The I2C slave address for the read operation.
+ * @param len The number of bytes to transfer.
+ * @param buf The buffer to store data from I2C bus. Must be len bytes long.
+ * @param stop_bit Enable / Disable STOP condition.
+ * @return 0 if the read succeeds.
+ */
+inline int metal_i2c_read(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ return i2c->vtable->read(i2c, addr, len, buf, stop_bit);
+}
+
+/*! @brief Performs back to back I2C write and read operations.
+ * @param i2c The handle for the I2C device to perform the transfer operation.
+ * @param addr The I2C slave address for the transfer operation.
+ * @param txbuf The data buffer to be transmitted over I2C bus.
+ * @param txlen The number of bytes to write over I2C.
+ * @param rxbuf The buffer to store data received over I2C bus.
+ * @param rxlen The number of bytes to read over I2C.
+ * @return 0 if the transfer succeeds.
+ */
+inline int metal_i2c_transfer(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen) {
+ return i2c->vtable->transfer(i2c, addr, txbuf, txlen, rxbuf, rxlen);
+}
+
+/*! @brief Get the current baud rate of the I2C device.
+ * @param i2c The handle for the I2C device.
+ * @return The baud rate in Hz.
+ */
+inline int metal_i2c_get_baud_rate(struct metal_i2c *i2c) {
+ return i2c->vtable->get_baud_rate(i2c);
+}
+
+/*! @brief Set the current baud rate of the I2C device.
+ * @param i2c The handle for the I2C device.
+ * @param baud_rate The desired baud rate of the I2C device.
+ * @return 0 If the baud rate is successfully changed.
+ */
+inline int metal_i2c_set_baud_rate(struct metal_i2c *i2c, int baud_rate) {
+ return i2c->vtable->set_baud_rate(i2c, baud_rate);
+}
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/init.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/init.h
new file mode 100644
index 000000000..0214d0add
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/init.h
@@ -0,0 +1,130 @@
+/* Copyright 2019 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL_INIT
+#define METAL_INIT
+
+/*!
+ * @file init.h
+ * API for Metal constructors and destructors
+ */
+
+typedef void (*metal_constructor_t)(void);
+typedef void (*metal_destructor_t)(void);
+
+#define METAL_INIT_HIGHEST_PRIORITY 0
+#define METAL_INIT_DEFAULT_PRIORITY 5000
+#define METAL_INIT_LOWEST_PRIORITY 9999
+
+/*! @def METAL_CONSTRUCTOR
+ * @brief Define a Metal constructor
+ *
+ * Functions defined with METAL_CONSTRUCTOR will be added to the list of
+ * Metal constructors. By default, these functions are called before main by
+ * the metal_init() function.
+ */
+#define METAL_CONSTRUCTOR(function_name) \
+ METAL_CONSTRUCTOR_PRIO(function_name, METAL_INIT_DEFAULT_PRIORITY)
+
+/*! @def METAL_CONSTRUCTOR_PRIO
+ * @brief Define a Metal constructor with a given priority
+ *
+ * The priority argument should be an integer between 0 and 9999, where 0
+ * is the highest priority (runs first) and 9999 is the lowest priority
+ * (runs last).
+ *
+ * Functions defined with METAL_CONSTRUCTOR_PRIO will be added to the list of
+ * Metal constructors. By default, these functions are called before main by
+ * the metal_init() function.
+ */
+#define METAL_CONSTRUCTOR_PRIO(function_name, priority) \
+ __METAL_CONSTRUCTOR_PRIO(function_name, priority)
+
+/* We use this wrapper for METAL_CONSTRUCTOR_PRIORITY so that macros passed
+ * as 'priority' are expanded before being stringified by the # operator.
+ * If we don't do this, then
+ * METAL_CONSTRUCTOR(my_fn_name, METAL_INIT_DEFAULT_PRIORITY)
+ * results in .metal.init_array.METAL_INIT_DEFAULT_PRIORITY instead of
+ * .metal.init_array.5000 */
+#define __METAL_CONSTRUCTOR_PRIO(function_name, priority) \
+ __attribute__((section(".metal.ctors"))) void function_name(void); \
+ __attribute__((section(".metal.init_array." #priority))) \
+ metal_constructor_t _##function_name##_ptr = &function_name; \
+ void function_name(void)
+
+/*! @def METAL_DESTRUCTOR
+ * @brief Define a Metal destructor
+ *
+ * Functions defined with METAL_DESTRUCTOR will be added to the list of
+ * Metal destructors. By default, these functions are called on exit by
+ * the metal_fini() function.
+ */
+#define METAL_DESTRUCTOR(function_name) \
+ METAL_DESTRUCTOR_PRIO(function_name, METAL_INIT_DEFAULT_PRIORITY)
+
+/*! @def METAL_DESTRUCTOR_PRIO
+ * @brief Define a Metal destructor with a given priority
+ *
+ * The priority argument should be an integer between 0 and 9999, where 0
+ * is the highest priority (runs first) and 9999 is the lowest priority
+ * (runs last).
+ *
+ * Functions defined with METAL_DESTRUCTOR_PRIO will be added to the list of
+ * Metal destructors. By default, these functions are called on exit by
+ * the metal_fini() function.
+ */
+#define METAL_DESTRUCTOR_PRIO(function_name, priority) \
+ __METAL_DESTRUCTOR_PRIO(function_name, priority)
+#define __METAL_DESTRUCTOR_PRIO(function_name, priority) \
+ __attribute__((section(".metal.dtors"))) void function_name(void); \
+ __attribute__((section(".metal.fini_array." #priority))) \
+ metal_destructor_t _##function_name##_ptr = &function_name; \
+ void function_name(void)
+
+/*!
+ * @brief Call all Metal constructors
+ *
+ * Devices supported by Metal may define Metal constructors to perform
+ * initialization before main. This function iterates over the constructors
+ * and calls them in turn.
+ *
+ * You can add your own constructors to the functions called by metal_init()
+ * by defining functions with the METAL_CONSTRUCTOR() macro.
+ *
+ * This function is called before main by default by metal_init_run().
+ */
+void metal_init(void);
+
+/*!
+ * @brief Call all Metal destructors
+ *
+ * Devices supported by Metal may define Metal destructors to perform
+ * initialization on exit. This function iterates over the destructors
+ * and calls them in turn.
+ *
+ * You can add your own destructors to the functions called by metal_fini()
+ * by defining functions with the METAL_DESTRUCTOR() macro.
+ *
+ * This function is called on exit by default by metal_fini_run().
+ */
+void metal_fini(void);
+
+/*!
+ * @brief Weak function to call metal_init() before main
+ *
+ * This function calls metal_init() before main by default. If you wish to
+ * replace or augment this call to the Metal constructors, you can redefine
+ * metal_init_run()
+ */
+void metal_init_run(void);
+
+/*!
+ * @brief Weak function to call metal_fini() before main
+ *
+ * This function calls metal_fini() at exit by default. If you wish to
+ * replace or augment this call to the Metal destructors, you can redefine
+ * metal_fini_run()
+ */
+void metal_fini_run(void);
+
+#endif /* METAL_INIT */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/interrupt.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/interrupt.h
index 43f587aca..11df019de 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/interrupt.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/interrupt.h
@@ -11,33 +11,104 @@
#include <stddef.h>
/*!
+ * @brief Possible interrupt controllers
+ */
+typedef enum metal_interrupt_controller_ {
+ METAL_CPU_CONTROLLER = 0,
+ METAL_CLINT_CONTROLLER = 1,
+ METAL_CLIC_CONTROLLER = 2,
+ METAL_PLIC_CONTROLLER = 3
+} metal_intr_cntrl_type;
+
+/*!
* @brief Possible mode of interrupts to operate
*/
typedef enum metal_vector_mode_ {
METAL_DIRECT_MODE = 0,
METAL_VECTOR_MODE = 1,
- METAL_SELECTIVE_VECTOR_MODE = 2,
- METAL_HARDWARE_VECTOR_MODE = 3
+ METAL_SELECTIVE_NONVECTOR_MODE = 2,
+ METAL_SELECTIVE_VECTOR_MODE = 3,
+ METAL_HARDWARE_VECTOR_MODE = 4
} metal_vector_mode;
/*!
+ * @brief Possible mode of privilege interrupts to operate
+ */
+typedef enum metal_intr_priv_mode_ {
+ METAL_INTR_PRIV_M_MODE = 0,
+ METAL_INTR_PRIV_MU_MODE = 1,
+ METAL_INTR_PRIV_MSU_MODE = 2
+} metal_intr_priv_mode;
+
+/*!
+ * @brief The bitmask of hart context
+ */
+typedef struct metal_affinity_ {
+ unsigned long bitmask;
+} metal_affinity;
+
+#define for_each_metal_affinity(bit, metal_affinity) \
+ for (bit = 0; metal_affinity.bitmask; bit++, metal_affinity.bitmask >>= 1)
+
+#define metal_affinity_set_val(metal_affinity, val) \
+ metal_affinity.bitmask = val;
+
+#define metal_affinity_set_bit(metal_affinity, bit, val) \
+ metal_affinity.bitmask |= ((val & 0x1) << bit);
+
+/*!
* @brief Function signature for interrupt callback handlers
*/
-typedef void (*metal_interrupt_handler_t) (int, void *);
+typedef void (*metal_interrupt_handler_t)(int, void *);
+typedef void (*metal_interrupt_vector_handler_t)(void);
struct metal_interrupt;
struct metal_interrupt_vtable {
void (*interrupt_init)(struct metal_interrupt *controller);
+ int (*interrupt_set_vector_mode)(struct metal_interrupt *controller,
+ metal_vector_mode mode);
+ metal_vector_mode (*interrupt_get_vector_mode)(
+ struct metal_interrupt *controller);
+ int (*interrupt_set_privilege)(struct metal_interrupt *controller,
+ metal_intr_priv_mode priv);
+ metal_intr_priv_mode (*interrupt_get_privilege)(
+ struct metal_interrupt *controller);
+ int (*interrupt_clear)(struct metal_interrupt *controller, int id);
+ int (*interrupt_set)(struct metal_interrupt *controller, int id);
int (*interrupt_register)(struct metal_interrupt *controller, int id,
- metal_interrupt_handler_t isr, void *priv_data);
+ metal_interrupt_handler_t isr, void *priv_data);
+ int (*interrupt_vector_register)(struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t isr,
+ void *priv_data);
int (*interrupt_enable)(struct metal_interrupt *controller, int id);
int (*interrupt_disable)(struct metal_interrupt *controller, int id);
- int (*interrupt_vector_enable)(struct metal_interrupt *controller,
- int id, metal_vector_mode mode);
+ int (*interrupt_vector_enable)(struct metal_interrupt *controller, int id);
int (*interrupt_vector_disable)(struct metal_interrupt *controller, int id);
- int (*command_request)(struct metal_interrupt *controller, int cmd, void *data);
- int (*mtimecmp_set)(struct metal_interrupt *controller, int hartid, unsigned long long time);
+ unsigned int (*interrupt_get_threshold)(struct metal_interrupt *controller);
+ int (*interrupt_set_threshold)(struct metal_interrupt *controller,
+ unsigned int threshold);
+ unsigned int (*interrupt_get_priority)(struct metal_interrupt *controller,
+ int id);
+ int (*interrupt_set_priority)(struct metal_interrupt *controller, int id,
+ unsigned int priority);
+ unsigned int (*interrupt_get_preemptive_level)(
+ struct metal_interrupt *controller, int id);
+ int (*interrupt_set_preemptive_level)(struct metal_interrupt *controller,
+ int id, unsigned int level);
+ int (*command_request)(struct metal_interrupt *controller, int cmd,
+ void *data);
+ int (*mtimecmp_set)(struct metal_interrupt *controller, int hartid,
+ unsigned long long time);
+ metal_affinity (*interrupt_affinity_enable)(
+ struct metal_interrupt *controller, metal_affinity bitmask, int id);
+ metal_affinity (*interrupt_affinity_disable)(
+ struct metal_interrupt *controller, metal_affinity bitmask, int id);
+ metal_affinity (*interrupt_affinity_set_threshold)(
+ struct metal_interrupt *controller, metal_affinity bitmask,
+ unsigned int threshold);
+ unsigned int (*interrupt_affinity_get_threshold)(
+ struct metal_interrupt *controller, int context_id);
};
/*!
@@ -56,11 +127,104 @@ struct metal_interrupt {
*
* @param controller The handle for the interrupt controller
*/
-inline void metal_interrupt_init(struct metal_interrupt *controller)
-{
- return controller->vtable->interrupt_init(controller);
+__inline__ void metal_interrupt_init(struct metal_interrupt *controller) {
+ controller->vtable->interrupt_init(controller);
+}
+
+/*!
+ * @brief Get the handle for an given interrupt controller type
+ * @param cntrl The type ofinterrupt controller
+ * @param id The instance of the interrupt controller
+ * @return A handle to the interrupt controller (CLINT, CLIC, PLIC), or
+ * NULL if none is found for the requested label
+ */
+struct metal_interrupt *
+metal_interrupt_get_controller(metal_intr_cntrl_type cntrl, int id);
+
+/*!
+ * @brief Configure vector mode for an interrupt controller
+ *
+ * Configure vector mode for an interrupt controller.
+ * This function must be called after initialization and before
+ * configuring individual interrupts, registering ISR.
+ *
+ * @param controller The handle for the interrupt controller
+ * @param mode The vector mode of the interrupt controller.
+ * @return 0 upon success
+ */
+__inline__ int
+metal_interrupt_set_vector_mode(struct metal_interrupt *controller,
+ metal_vector_mode mode) {
+ return controller->vtable->interrupt_set_vector_mode(controller, mode);
+}
+
+/*!
+ * @brief Get vector mode of a given an interrupt controller
+ *
+ * Configure vector mode for an interrupt controller.
+ * This function must be called after initialization and before
+ * configuring individual interrupts, registering ISR.
+ *
+ * @param controller The handle for the interrupt controller
+ * @param mode The vector mode of the interrupt controller.
+ * @return The interrupt vector mode
+ */
+__inline__ metal_vector_mode
+metal_interrupt_get_vector_mode(struct metal_interrupt *controller) {
+ return controller->vtable->interrupt_get_vector_mode(controller);
+}
+
+/*!
+ * @brief Configure privilege mode a of given interrupt controller
+ *
+ * Configure privilege mode for a given interrupt controller.
+ * This function must be called after initialization and before
+ * configuring individual interrupts, registering ISR.
+ *
+ * @param controller The handle for the interrupt controller
+ * @param privilege The privilege mode of the interrupt controller.
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_set_privilege(struct metal_interrupt *controller,
+ metal_intr_priv_mode privilege) {
+ return controller->vtable->interrupt_set_privilege(controller, privilege);
+}
+
+/*!
+ * @brief Get privilege mode a of given interrupt controller
+ *
+ * Get privilege mode for a given interrupt controller.
+ * This function must be called after initialization and before
+ * configuring individual interrupts, registering ISR.
+ *
+ * @param controller The handle for the interrupt controller
+ * @return The interrupt privilege mode
+ */
+__inline__ metal_intr_priv_mode
+metal_interrupt_get_privilege(struct metal_interrupt *controller) {
+ return controller->vtable->interrupt_get_privilege(controller);
+}
+
+/*!
+ * @brief clear an interrupt
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to trigger
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_clear(struct metal_interrupt *controller,
+ int id) {
+ return controller->vtable->interrupt_clear(controller, id);
}
+/*!
+ * @brief Set an interrupt
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to trigger
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_set(struct metal_interrupt *controller, int id) {
+ return controller->vtable->interrupt_set(controller, id);
+}
/*!
* @brief Register an interrupt handler
@@ -70,12 +234,27 @@ inline void metal_interrupt_init(struct metal_interrupt *controller)
* @param priv_data Private data for the interrupt handler
* @return 0 upon success
*/
-inline int metal_interrupt_register_handler(struct metal_interrupt *controller,
- int id,
- metal_interrupt_handler_t handler,
- void *priv_data)
-{
- return controller->vtable->interrupt_register(controller, id, handler, priv_data);
+__inline__ int
+metal_interrupt_register_handler(struct metal_interrupt *controller, int id,
+ metal_interrupt_handler_t handler,
+ void *priv_data) {
+ return controller->vtable->interrupt_register(controller, id, handler,
+ priv_data);
+}
+
+/*!
+ * @brief Register an interrupt vector handler
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to register
+ * @param handler The interrupt vector handler callback
+ * @param priv_data Private data for the interrupt handler
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_register_vector_handler(
+ struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t handler, void *priv_data) {
+ return controller->vtable->interrupt_vector_register(controller, id,
+ handler, priv_data);
}
/*!
@@ -84,8 +263,8 @@ inline int metal_interrupt_register_handler(struct metal_interrupt *controller,
* @param id The interrupt ID to enable
* @return 0 upon success
*/
-inline int metal_interrupt_enable(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_enable(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_enable(controller, id);
}
@@ -95,22 +274,100 @@ inline int metal_interrupt_enable(struct metal_interrupt *controller, int id)
* @param id The interrupt ID to disable
* @return 0 upon success
*/
-inline int metal_interrupt_disable(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_disable(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_disable(controller, id);
}
/*!
+ * @brief Set interrupt threshold level
+ * @param controller The handle for the interrupt controller
+ * @param threshold The interrupt threshold level
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_set_threshold(struct metal_interrupt *controller,
+ unsigned int level) {
+ return controller->vtable->interrupt_set_threshold(controller, level);
+}
+
+/*!
+ * @brief Get an interrupt threshold level
+ * @param controller The handle for the interrupt controller
+ * @return The interrupt threshold level
+ */
+__inline__ unsigned int
+metal_interrupt_get_threshold(struct metal_interrupt *controller) {
+ return controller->vtable->interrupt_get_threshold(controller);
+}
+
+/*!
+ * @brief Set an interrupt priority level
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @param priority The interrupt priority level
+ * @return 0 upon success
+ */
+__inline__ int metal_interrupt_set_priority(struct metal_interrupt *controller,
+ int id, unsigned int priority) {
+ return controller->vtable->interrupt_set_priority(controller, id, priority);
+}
+
+/*!
+ * @brief Get an interrupt priority level
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @return The interrupt priority level
+ */
+__inline__ unsigned int
+metal_interrupt_get_priority(struct metal_interrupt *controller, int id) {
+ return controller->vtable->interrupt_get_priority(controller, id);
+}
+
+/*!
+ * @brief Set preemptive level and priority for a given interrupt ID
+ *
+ * Set the preemptive level and priority for a given interrupt ID.
+ *
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @param level The interrupt level and priority are encoded together
+ * @return 0 upon success
+ */
+__inline__ int
+metal_interrupt_set_preemptive_level(struct metal_interrupt *controller, int id,
+ unsigned int level) {
+ if (controller->vtable->interrupt_set_preemptive_level)
+ return controller->vtable->interrupt_set_preemptive_level(controller,
+ id, level);
+ else
+ return 0;
+}
+
+/*!
+ * @brief Get an interrupt preemptive level
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @return The interrupt level
+ */
+__inline__ unsigned int
+metal_interrupt_get_preemptive_level(struct metal_interrupt *controller,
+ int id) {
+ if (controller->vtable->interrupt_get_preemptive_level)
+ return controller->vtable->interrupt_get_preemptive_level(controller,
+ id);
+ else
+ return 0;
+}
+
+/*!
* @brief Enable an interrupt vector
* @param controller The handle for the interrupt controller
* @param id The interrupt ID to enable
- * @param mode The interrupt mode type to enable
* @return 0 upon success
*/
-inline int metal_interrupt_vector_enable(struct metal_interrupt *controller,
- int id, metal_vector_mode mode)
-{
- return controller->vtable->interrupt_vector_enable(controller, id, mode);
+__inline__ int metal_interrupt_vector_enable(struct metal_interrupt *controller,
+ int id) {
+ return controller->vtable->interrupt_vector_enable(controller, id);
}
/*!
@@ -119,16 +376,215 @@ inline int metal_interrupt_vector_enable(struct metal_interrupt *controller,
* @param id The interrupt ID to disable
* @return 0 upon success
*/
-inline int metal_interrupt_vector_disable(struct metal_interrupt *controller, int id)
-{
+__inline__ int
+metal_interrupt_vector_disable(struct metal_interrupt *controller, int id) {
return controller->vtable->interrupt_vector_disable(controller, id);
}
-/* Utilities function to controll, manages devices via a given interrupt controller */
-inline int _metal_interrupt_command_request(struct metal_interrupt *controller,
- int cmd, void *data)
-{
+/*!
+ * @brief Default interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Software interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt))
+metal_software_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Timer interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt))
+metal_timer_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal External interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt))
+metal_external_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 0 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc0_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 1 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc1_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 2 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc2_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 3 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc3_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 4 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc4_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 5 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc5_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 6 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc6_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 7 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc7_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 8 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc8_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 9 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc9_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 10 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc10_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 11 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc11_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 12 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc12_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 13 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc13_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 14 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc14_interrupt_vector_handler(void);
+
+/*!
+ * @brief Metal Local 15 interrupt vector handler, that can be overriden by user
+ * @param None
+ * @return None
+ */
+void __attribute__((weak, interrupt)) metal_lc15_interrupt_vector_handler(void);
+
+/* Utilities function to controll, manages devices via a given interrupt
+ * controller */
+__inline__ int
+_metal_interrupt_command_request(struct metal_interrupt *controller, int cmd,
+ void *data) {
return controller->vtable->command_request(controller, cmd, data);
}
+/*!
+ * @brief Enable an interrupt for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to enable
+ * @param id The interrupt ID to enable
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_enable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ return controller->vtable->interrupt_affinity_enable(controller, bitmask,
+ id);
+}
+
+/*!
+ * @brief Disable an interrupt for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to disable
+ * @param id The interrupt ID to disable
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_disable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ return controller->vtable->interrupt_affinity_disable(controller, bitmask,
+ id);
+}
+
+/*!
+ * @brief Set interrupt threshold level for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to set threshold
+ * @param threshold The interrupt threshold level
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_set_threshold(struct metal_interrupt *controller,
+ metal_affinity bitmask,
+ unsigned int level) {
+ return controller->vtable->interrupt_affinity_set_threshold(controller,
+ bitmask, level);
+}
+
+/*!
+ * @brief Get an interrupt threshold level from the hart context
+ * @param controller The handle for the interrupt controller
+ * @param context_id The hart context ID to get threshold
+ * @return The interrupt threshold level
+ */
+__inline__ unsigned int
+metal_interrupt_affinity_get_threshold(struct metal_interrupt *controller,
+ int context_id) {
+ return controller->vtable->interrupt_affinity_get_threshold(controller,
+ context_id);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/io.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/io.h
index 450054142..f1df85518 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/io.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/io.h
@@ -5,18 +5,19 @@
#define METAL__IO_H
/* This macro enforces that the compiler will not elide the given access. */
-#define __METAL_ACCESS_ONCE(x) (*(typeof(*x) volatile *)(x))
+#define __METAL_ACCESS_ONCE(x) (*(__typeof__(*x) volatile *)(x))
/* Allows users to specify arbitrary fences. */
-#define __METAL_IO_FENCE(pred, succ) __asm__ volatile ("fence " #pred "," #succ ::: "memory");
+#define __METAL_IO_FENCE(pred, succ) \
+ __asm__ volatile("fence " #pred "," #succ ::: "memory");
/* Types that explicitly describe an address as being used for memory-mapped
* IO. These should only be accessed via __METAL_ACCESS_ONCE. */
-typedef unsigned char __metal_io_u8;
+typedef unsigned char __metal_io_u8;
typedef unsigned short __metal_io_u16;
-typedef unsigned int __metal_io_u32;
+typedef unsigned int __metal_io_u32;
#if __riscv_xlen >= 64
-typedef unsigned long __metal_io_u64;
+typedef unsigned long __metal_io_u64;
#endif
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/itim.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/itim.h
index 1a2a05b8b..3decefff2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/itim.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/itim.h
@@ -9,13 +9,12 @@
* API for manipulating ITIM allocation
*/
-
/*! @def METAL_PLACE_IN_ITIM
* @brief Link a function into the ITIM
*
* Link a function into the ITIM (Instruction Tightly Integrated
* Memory) if the ITIM is present on the target device.
*/
-#define METAL_PLACE_IN_ITIM __attribute__((section(".itim")))
+#define METAL_PLACE_IN_ITIM __attribute__((section(".itim")))
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/led.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/led.h
index a430b84c2..da2555fb8 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/led.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/led.h
@@ -31,38 +31,47 @@ struct metal_led {
* @param label The DeviceTree label for the desired LED
* @return A handle to the LED, or NULL if none is found for the requested label
*/
-struct metal_led* metal_led_get(char *label);
+struct metal_led *metal_led_get(char *label);
/*!
* @brief Get a handle for a channel of an RGB LED
* @param label The DeviceTree label for the desired LED
* @param color The color for the LED in the DeviceTree
- * @return A handle to the LED, or NULL if none is found for the requested label and color
+ * @return A handle to the LED, or NULL if none is found for the requested label
+ * and color
*/
-struct metal_led* metal_led_get_rgb(char *label, char *color);
+struct metal_led *metal_led_get_rgb(char *label, char *color);
/*!
* @brief Enable an LED
* @param led The handle for the LED
*/
-inline void metal_led_enable(struct metal_led *led) { led->vtable->led_enable(led); }
+__inline__ void metal_led_enable(struct metal_led *led) {
+ led->vtable->led_enable(led);
+}
/*!
* @brief Turn an LED on
* @param led The handle for the LED
*/
-inline void metal_led_on(struct metal_led *led) { led->vtable->led_on(led); }
+__inline__ void metal_led_on(struct metal_led *led) {
+ led->vtable->led_on(led);
+}
/*!
* @brief Turn an LED off
* @param led The handle for the LED
*/
-inline void metal_led_off(struct metal_led *led) { led->vtable->led_off(led); }
+__inline__ void metal_led_off(struct metal_led *led) {
+ led->vtable->led_off(led);
+}
/*!
* @brief Toggle the on/off state of an LED
* @param led The handle for the LED
*/
-inline void metal_led_toggle(struct metal_led *led) { led->vtable->led_toggle(led); }
+__inline__ void metal_led_toggle(struct metal_led *led) {
+ led->vtable->led_toggle(led);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lim.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lim.h
new file mode 100644
index 000000000..1e573cad6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lim.h
@@ -0,0 +1,20 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__LIM_H
+#define METAL__LIM_H
+
+/*! @file lim.h
+ *
+ * API for manipulating LIM allocation
+ */
+
+/*! @def METAL_PLACE_IN_LIM
+ * @brief Link a function into the LIM
+ *
+ * Link a function into the LIM (Loosely Integrated
+ * Memory) if the LIM is present on the target device.
+ */
+#define METAL_PLACE_IN_LIM __attribute__((section(".lim")))
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lock.h
index d863aa96e..e591eaefa 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/lock.h
@@ -4,8 +4,9 @@
#ifndef METAL__LOCK_H
#define METAL__LOCK_H
-#include <metal/memory.h>
#include <metal/compiler.h>
+#include <metal/machine.h>
+#include <metal/memory.h>
/*!
* @file lock.h
@@ -15,6 +16,9 @@
/* TODO: How can we make the exception code platform-independant? */
#define _METAL_STORE_AMO_ACCESS_FAULT 7
+#define METAL_LOCK_BACKOFF_CYCLES 32
+#define METAL_LOCK_BACKOFF_EXPONENT 2
+
/*!
* @def METAL_LOCK_DECLARE
* @brief Declare a lock
@@ -22,35 +26,36 @@
* Locks must be declared with METAL_LOCK_DECLARE to ensure that the lock
* is linked into a memory region which supports atomic memory operations.
*/
-#define METAL_LOCK_DECLARE(name) \
- __attribute__((section(".data.locks"))) \
- struct metal_lock name
+#define METAL_LOCK_DECLARE(name) \
+ __attribute__((section(".data.locks"))) struct metal_lock name
/*!
* @brief A handle for a lock
*/
struct metal_lock {
- int _state;
+ int _state;
};
/*!
* @brief Initialize a lock
* @param lock The handle for a lock
- * @return 0 if the lock is successfully initialized. A non-zero code indicates failure.
+ * @return 0 if the lock is successfully initialized. A non-zero code indicates
+ * failure.
*
* If the lock cannot be initialized, attempts to take or give the lock
* will result in a Store/AMO access fault.
*/
-inline int metal_lock_init(struct metal_lock *lock) {
+__inline__ int metal_lock_init(struct metal_lock *lock) {
#ifdef __riscv_atomic
/* Get a handle for the memory which holds the lock state */
- struct metal_memory *lock_mem = metal_get_memory_from_address((uintptr_t) &(lock->_state));
- if(!lock_mem) {
+ struct metal_memory *lock_mem =
+ metal_get_memory_from_address((uintptr_t) & (lock->_state));
+ if (!lock_mem) {
return 1;
}
/* If the memory doesn't support atomics, report an error */
- if(!metal_memory_supports_atomics(lock_mem)) {
+ if (!metal_memory_supports_atomics(lock_mem)) {
return 2;
}
@@ -70,23 +75,37 @@ inline int metal_lock_init(struct metal_lock *lock) {
* If the lock initialization failed, attempts to take a lock will result in
* a Store/AMO access fault.
*/
-inline int metal_lock_take(struct metal_lock *lock) {
+__inline__ int metal_lock_take(struct metal_lock *lock) {
#ifdef __riscv_atomic
int old = 1;
int new = 1;
- while(old != 0) {
+ int backoff = 1;
+ const int max_backoff = METAL_LOCK_BACKOFF_CYCLES * METAL_MAX_CORES;
+
+ while (1) {
__asm__ volatile("amoswap.w.aq %[old], %[new], (%[state])"
- : [old] "=r" (old)
- : [new] "r" (new), [state] "r" (&(lock->_state))
+ : [old] "=r"(old)
+ : [new] "r"(new), [state] "r"(&(lock->_state))
: "memory");
+
+ if (old == 0) {
+ break;
+ }
+
+ for (int i = 0; i < backoff; i++) {
+ __asm__ volatile("");
+ }
+
+ if (backoff < max_backoff) {
+ backoff *= METAL_LOCK_BACKOFF_EXPONENT;
+ }
}
return 0;
#else
/* Store the memory address in mtval like a normal store/amo access fault */
- __asm__ ("csrw mtval, %[state]"
- :: [state] "r" (&(lock->_state)));
+ __asm__("csrw mtval, %[state]" ::[state] "r"(&(lock->_state)));
/* Trigger a Store/AMO access fault */
_metal_trap(_METAL_STORE_AMO_ACCESS_FAULT);
@@ -104,17 +123,16 @@ inline int metal_lock_take(struct metal_lock *lock) {
* If the lock initialization failed, attempts to give a lock will result in
* a Store/AMO access fault.
*/
-inline int metal_lock_give(struct metal_lock *lock) {
+__inline__ int metal_lock_give(struct metal_lock *lock) {
#ifdef __riscv_atomic
- __asm__ volatile("amoswap.w.rl x0, x0, (%[state])"
- :: [state] "r" (&(lock->_state))
- : "memory");
+ __asm__ volatile(
+ "amoswap.w.rl x0, x0, (%[state])" ::[state] "r"(&(lock->_state))
+ : "memory");
return 0;
#else
/* Store the memory address in mtval like a normal store/amo access fault */
- __asm__ ("csrw mtval, %[state]"
- :: [state] "r" (&(lock->_state)));
+ __asm__("csrw mtval, %[state]" ::[state] "r"(&(lock->_state)));
/* Trigger a Store/AMO access fault */
_metal_trap(_METAL_STORE_AMO_ACCESS_FAULT);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine.h
index f76dbd632..74c361b4b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine.h
@@ -9,15 +9,15 @@
#ifdef __METAL_MACHINE_MACROS
-#ifndef MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H
-#define MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H
+#ifndef MACROS_IF_METAL_H
+#define MACROS_IF_METAL_H
#define __METAL_CLINT_NUM_PARENTS 2
#ifndef __METAL_CLINT_NUM_PARENTS
#define __METAL_CLINT_NUM_PARENTS 0
#endif
-#define __METAL_PLIC_SUBINTERRUPTS 27
+#define __METAL_PLIC_SUBINTERRUPTS 53
#define __METAL_PLIC_NUM_PARENTS 1
@@ -31,12 +31,12 @@
#define __METAL_CLIC_SUBINTERRUPTS 0
#endif
-#endif /* MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H*/
+#endif /* MACROS_IF_METAL_H*/
#else /* ! __METAL_MACHINE_MACROS */
-#ifndef MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H
-#define MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H
+#ifndef MACROS_ELSE_METAL_H
+#define MACROS_ELSE_METAL_H
#define __METAL_CLINT_2000000_INTERRUPTS 2
@@ -46,7 +46,7 @@
#define __METAL_INTERRUPT_CONTROLLER_C000000_INTERRUPTS 1
-#define __METAL_PLIC_SUBINTERRUPTS 27
+#define __METAL_PLIC_SUBINTERRUPTS 53
#define METAL_MAX_PLIC_INTERRUPTS 1
@@ -55,20 +55,36 @@
#define __METAL_CLIC_SUBINTERRUPTS 0
#define METAL_MAX_CLIC_INTERRUPTS 0
-#define __METAL_LOCAL_EXTERNAL_INTERRUPTS_0_INTERRUPTS 16
-
-#define METAL_MAX_LOCAL_EXT_INTERRUPTS 16
+#define METAL_MAX_LOCAL_EXT_INTERRUPTS 0
#define METAL_MAX_GLOBAL_EXT_INTERRUPTS 0
-#define __METAL_GPIO_10012000_INTERRUPTS 16
+#define __METAL_GPIO_10012000_INTERRUPTS 32
+
+#define METAL_MAX_GPIO_INTERRUPTS 32
+
+#define __METAL_I2C_10016000_INTERRUPTS 1
+
+#define METAL_MAX_I2C0_INTERRUPTS 1
+
+#define __METAL_PWM_10015000_INTERRUPTS 4
-#define METAL_MAX_GPIO_INTERRUPTS 16
+#define __METAL_PWM_10025000_INTERRUPTS 4
+
+#define __METAL_PWM_10035000_INTERRUPTS 4
+
+#define METAL_MAX_PWM0_INTERRUPTS 4
+
+#define METAL_MAX_PWM0_NCMP 4
#define __METAL_SERIAL_10013000_INTERRUPTS 1
+#define __METAL_SERIAL_10023000_INTERRUPTS 1
+
#define METAL_MAX_UART_INTERRUPTS 1
+#define METAL_MAX_SIMUART_INTERRUPTS 0
+
#include <metal/drivers/fixed-clock.h>
#include <metal/memory.h>
@@ -76,79 +92,119 @@
#include <metal/drivers/riscv_cpu.h>
#include <metal/drivers/riscv_plic0.h>
#include <metal/pmp.h>
-#include <metal/drivers/sifive_local-external-interrupts0.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/drivers/sifive_gpio-leds.h>
+#include <metal/drivers/sifive_i2c0.h>
+#include <metal/drivers/sifive_pwm0.h>
+#include <metal/drivers/sifive_rtc0.h>
#include <metal/drivers/sifive_spi0.h>
#include <metal/drivers/sifive_uart0.h>
+#include <metal/drivers/sifive_wdog0.h>
#include <metal/drivers/sifive_fe310-g000_hfrosc.h>
#include <metal/drivers/sifive_fe310-g000_hfxosc.h>
+#include <metal/drivers/sifive_fe310-g000_lfrosc.h>
#include <metal/drivers/sifive_fe310-g000_pll.h>
#include <metal/drivers/sifive_fe310-g000_prci.h>
/* From clock@0 */
-struct __metal_driver_fixed_clock __metal_dt_clock_0;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_0;
/* From clock@2 */
-struct __metal_driver_fixed_clock __metal_dt_clock_2;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_2;
/* From clock@5 */
-struct __metal_driver_fixed_clock __metal_dt_clock_5;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_5;
+
+/* From clock@6 */
+extern struct __metal_driver_fixed_clock __metal_dt_clock_6;
+
+extern struct metal_memory __metal_dt_mem_dtim_80000000;
+
+extern struct metal_memory __metal_dt_mem_itim_8000000;
-struct metal_memory __metal_dt_mem_dtim_80000000;
+extern struct metal_memory __metal_dt_mem_spi_10014000;
-struct metal_memory __metal_dt_mem_spi_10014000;
+extern struct metal_memory __metal_dt_mem_spi_10024000;
+
+extern struct metal_memory __metal_dt_mem_spi_10034000;
/* From clint@2000000 */
-struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000;
+extern struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000;
/* From cpu@0 */
-struct __metal_driver_cpu __metal_dt_cpu_0;
+extern struct __metal_driver_cpu __metal_dt_cpu_0;
-struct __metal_driver_riscv_cpu_intc __metal_dt_cpu_0_interrupt_controller;
+extern struct __metal_driver_riscv_cpu_intc __metal_dt_cpu_0_interrupt_controller;
/* From interrupt_controller@c000000 */
-struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000;
-
-struct metal_pmp __metal_dt_pmp;
+extern struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000;
-/* From local_external_interrupts_0 */
-struct __metal_driver_sifive_local_external_interrupts0 __metal_dt_local_external_interrupts_0;
+extern struct metal_pmp __metal_dt_pmp;
/* From gpio@10012000 */
-struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000;
+extern struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000;
+
+/* From led@0 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_0;
+
+/* From led@1 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_1;
-/* From led@0red */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0red;
+/* From led@2 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_2;
-/* From led@0green */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0green;
+/* From i2c@10016000 */
+extern struct __metal_driver_sifive_i2c0 __metal_dt_i2c_10016000;
-/* From led@0blue */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0blue;
+/* From pwm@10015000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10015000;
+
+/* From pwm@10025000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10025000;
+
+/* From pwm@10035000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10035000;
+
+/* From aon@10000000 */
+extern struct __metal_driver_sifive_rtc0 __metal_dt_rtc_10000000;
/* From spi@10014000 */
-struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000;
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000;
+
+/* From spi@10024000 */
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10024000;
+
+/* From spi@10034000 */
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10034000;
/* From serial@10013000 */
-struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000;
+extern struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000;
+
+/* From serial@10023000 */
+extern struct __metal_driver_sifive_uart0 __metal_dt_serial_10023000;
+
+/* From aon@10000000 */
+extern struct __metal_driver_sifive_wdog0 __metal_dt_aon_10000000;
/* From clock@3 */
-struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3;
+extern struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3;
/* From clock@1 */
-struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1;
+extern struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1;
+
+/* From clock@7 */
+extern struct __metal_driver_sifive_fe310_g000_lfrosc __metal_dt_clock_7;
/* From clock@4 */
-struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4;
+extern struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4;
/* From prci@10008000 */
-struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000;
+extern struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000;
/* --------------------- fixed_clock ------------ */
-static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock)
+static __inline__ unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock)
{
if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_0) {
return METAL_FIXED_CLOCK_0_CLOCK_FREQUENCY;
@@ -159,6 +215,9 @@ static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_c
else if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_5) {
return METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY;
}
+ else if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_6) {
+ return METAL_FIXED_CLOCK_6_CLOCK_FREQUENCY;
+ }
else {
return 0;
}
@@ -170,7 +229,7 @@ static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_c
/* --------------------- sifive_clint0 ------------ */
-static inline unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_RISCV_CLINT0_2000000_BASE_ADDRESS;
@@ -180,7 +239,7 @@ static inline unsigned long __metal_driver_sifive_clint0_control_base(struct met
}
}
-static inline unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_RISCV_CLINT0_2000000_SIZE;
@@ -190,7 +249,7 @@ static inline unsigned long __metal_driver_sifive_clint0_control_size(struct met
}
}
-static inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_MAX_CLINT_INTERRUPTS;
@@ -200,7 +259,7 @@ static inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_inter
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
@@ -213,7 +272,7 @@ static inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_pa
}
}
-static inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return 3;
@@ -229,7 +288,7 @@ static inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_inte
/* --------------------- cpu ------------ */
-static inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return 0;
@@ -239,17 +298,17 @@ static inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
}
}
-static inline int __metal_driver_cpu_timebase(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_timebase(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
- return 1000000;
+ return 16000000;
}
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu)
+static __inline__ struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return &__metal_dt_cpu_0_interrupt_controller.controller;
@@ -259,7 +318,7 @@ static inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(s
}
}
-static inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return 8;
@@ -269,10 +328,20 @@ static inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
}
}
+static __inline__ struct metal_buserror * __metal_driver_cpu_buserror(struct metal_cpu *cpu)
+{
+ if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
+ return NULL;
+ }
+ else {
+ return NULL;
+ }
+}
+
/* --------------------- sifive_plic0 ------------ */
-static inline unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_BASE_ADDRESS;
@@ -282,7 +351,7 @@ static inline unsigned long __metal_driver_sifive_plic0_control_base(struct meta
}
}
-static inline unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_SIZE;
@@ -292,7 +361,7 @@ static inline unsigned long __metal_driver_sifive_plic0_control_size(struct meta
}
}
-static inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_RISCV_NDEV;
@@ -302,7 +371,7 @@ static inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interr
}
}
-static inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_RISCV_MAX_PRIORITY;
@@ -312,108 +381,189 @@ static inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrup
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
}
- else if (idx == 0) {
- return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
- }
else {
return NULL;
}
}
-static inline int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return 11;
}
- else if (idx == 0) {
- return 11;
- }
else {
return 0;
}
}
+static __inline__ int __metal_driver_sifive_plic0_context_ids(int hartid)
+{
+ if (hartid == 0) {
+ return 0;
+ }
+ else {
+ return -1;
+ }
+}
+
+
+
+/* --------------------- sifive_buserror0 ------------ */
/* --------------------- sifive_clic0 ------------ */
/* --------------------- sifive_local_external_interrupts0 ------------ */
-static inline struct metal_interrupt * __metal_driver_sifive_local_external_interrupts0_interrupt_parent(struct metal_interrupt *controller)
+
+
+/* --------------------- sifive_global_external_interrupts0 ------------ */
+
+
+/* --------------------- sifive_gpio0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio)
{
- if ((uintptr_t)controller == (uintptr_t)&__metal_dt_local_external_interrupts_0) {
- return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_SIFIVE_GPIO0_10012000_BASE_ADDRESS;
}
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_local_external_interrupts0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio)
{
- if ((uintptr_t)controller == (uintptr_t)&__metal_dt_local_external_interrupts_0) {
- return METAL_MAX_LOCAL_EXT_INTERRUPTS;
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_SIFIVE_GPIO0_10012000_SIZE;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio)
{
- if (idx == 0) {
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_MAX_GPIO_INTERRUPTS;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio)
+{
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx)
+{
+ if (((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 0)) {
+ return 8;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 1))) {
+ return 9;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 2))) {
+ return 10;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 3))) {
+ return 11;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 4))) {
+ return 12;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 5))) {
+ return 13;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 6))) {
+ return 14;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 7))) {
+ return 15;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 8))) {
return 16;
}
- else if (idx == 1) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 9))) {
return 17;
}
- else if (idx == 2) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 10))) {
return 18;
}
- else if (idx == 3) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 11))) {
return 19;
}
- else if (idx == 4) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 12))) {
return 20;
}
- else if (idx == 5) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 13))) {
return 21;
}
- else if (idx == 6) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 14))) {
return 22;
}
- else if (idx == 7) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 15))) {
return 23;
}
- else if (idx == 8) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 16))) {
return 24;
}
- else if (idx == 9) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 17))) {
return 25;
}
- else if (idx == 10) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 18))) {
return 26;
}
- else if (idx == 11) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 19))) {
return 27;
}
- else if (idx == 12) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 20))) {
return 28;
}
- else if (idx == 13) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 21))) {
return 29;
}
- else if (idx == 14) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 22))) {
return 30;
}
- else if (idx == 15) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 23))) {
return 31;
}
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 24))) {
+ return 32;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 25))) {
+ return 33;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 26))) {
+ return 34;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 27))) {
+ return 35;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 28))) {
+ return 36;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 29))) {
+ return 27;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 30))) {
+ return 28;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 31))) {
+ return 29;
+ }
else {
return 0;
}
@@ -421,203 +571,487 @@ static inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lin
-/* --------------------- sifive_global_external_interrupts0 ------------ */
+/* --------------------- sifive_gpio_button ------------ */
-/* --------------------- sifive_gpio0 ------------ */
-static inline unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio)
+/* --------------------- sifive_gpio_led ------------ */
+static __inline__ struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_SIFIVE_GPIO0_10012000_BASE_ADDRESS;
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_gpio_led_pin(struct metal_led *led)
+{
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return 22;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return 19;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return 21;
}
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio)
+static __inline__ char * __metal_driver_sifive_gpio_led_label(struct metal_led *led)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_SIFIVE_GPIO0_10012000_SIZE;
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return "LD0red";
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return "LD0green";
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return "LD0blue";
+ }
+ else {
+ return "";
+ }
+}
+
+
+
+/* --------------------- sifive_gpio_switch ------------ */
+
+
+/* --------------------- sifive_i2c0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_i2c0_control_base(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return METAL_SIFIVE_I2C0_10016000_BASE_ADDRESS;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio)
+static __inline__ unsigned long __metal_driver_sifive_i2c0_control_size(struct metal_i2c *i2c)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_MAX_GPIO_INTERRUPTS;
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return METAL_SIFIVE_I2C0_10016000_SIZE;
}
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio)
+static __inline__ struct metal_clock * __metal_driver_sifive_i2c0_clock(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_i2c0_pinmux(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_output_selector(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_source_selector(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 12288;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_i2c0_num_interrupts(struct metal_i2c *i2c)
+{
+ return METAL_MAX_I2C0_INTERRUPTS;
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_i2c0_interrupt_parent(struct metal_i2c *i2c)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+}
+
+static __inline__ int __metal_driver_sifive_i2c0_interrupt_line(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 52;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx)
+
+
+/* --------------------- sifive_pwm0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_pwm0_control_base(struct metal_pwm *pwm)
{
- if (((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 0)) {
- return 7;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return METAL_SIFIVE_PWM0_10015000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 1))) {
- return 8;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return METAL_SIFIVE_PWM0_10025000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 2))) {
- return 9;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return METAL_SIFIVE_PWM0_10035000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 3))) {
- return 10;
+ else {
+ return 0;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 4))) {
- return 11;
+}
+
+static __inline__ unsigned long __metal_driver_sifive_pwm0_control_size(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return METAL_SIFIVE_PWM0_10015000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 5))) {
- return 12;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return METAL_SIFIVE_PWM0_10025000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 6))) {
- return 13;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return METAL_SIFIVE_PWM0_10035000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 7))) {
- return 14;
+ else {
+ return 0;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 8))) {
- return 15;
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_pwm0_clock(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 9))) {
- return 16;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 10))) {
- return 17;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 11))) {
- return 18;
+ else {
+ return NULL;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 12))) {
- return 19;
+}
+
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_pwm0_pinmux(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 13))) {
- return 20;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 14))) {
- return 21;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 15))) {
- return 22;
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_output_selector(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 15;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 7864320;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 15360;
}
else {
return 0;
}
}
+static __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_source_selector(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 15;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 7864320;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 15360;
+ }
+ else {
+ return 0;
+ }
+}
+static __inline__ int __metal_driver_sifive_pwm0_num_interrupts(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return __METAL_PWM_10015000_INTERRUPTS;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return __METAL_PWM_10025000_INTERRUPTS;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return __METAL_PWM_10035000_INTERRUPTS;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_button ------------ */
+static __inline__ struct metal_interrupt * __metal_driver_sifive_pwm0_interrupt_parent(struct metal_pwm *pwm)
+{
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+}
+static __inline__ int __metal_driver_sifive_pwm0_interrupt_lines(struct metal_pwm *pwm, int idx)
+{
+ if (((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 0)) {
+ return 40;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 1))) {
+ return 41;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 2))) {
+ return 42;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 3))) {
+ return 43;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 0))) {
+ return 44;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 1))) {
+ return 45;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 2))) {
+ return 46;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 3))) {
+ return 47;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 0))) {
+ return 48;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 1))) {
+ return 49;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 2))) {
+ return 50;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 3))) {
+ return 51;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_led ------------ */
-static inline struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led)
+static __inline__ int __metal_driver_sifive_pwm0_compare_width(struct metal_pwm *pwm)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 8;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 16;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 16;
}
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_gpio_led_pin(struct metal_led *led)
+static __inline__ int __metal_driver_sifive_pwm0_comparator_count(struct metal_pwm *pwm)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return 22;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 4;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return 19;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 4;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return 21;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 4;
}
else {
return 0;
}
}
-static inline char * __metal_driver_sifive_gpio_led_label(struct metal_led *led)
+
+
+/* --------------------- sifive_rtc0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_rtc0_control_base(const struct metal_rtc *const rtc)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return "LD0red";
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return METAL_SIFIVE_AON0_10000000_BASE_ADDRESS;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return "LD0green";
+ else {
+ return 0;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return "LD0blue";
+}
+
+static __inline__ unsigned long __metal_driver_sifive_rtc0_control_size(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return METAL_SIFIVE_AON0_10000000_SIZE;
}
else {
- return "";
+ return 0;
}
}
+static __inline__ struct metal_interrupt * __metal_driver_sifive_rtc0_interrupt_parent(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+static __inline__ int __metal_driver_sifive_rtc0_interrupt_line(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return 2;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_switch ------------ */
+static __inline__ struct metal_clock * __metal_driver_sifive_rtc0_clock(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return (struct metal_clock *)&__metal_dt_clock_7.clock;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_spi0 ------------ */
-static inline unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi)
{
if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
return METAL_SIFIVE_SPI0_10014000_BASE_ADDRESS;
}
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return METAL_SIFIVE_SPI0_10024000_BASE_ADDRESS;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return METAL_SIFIVE_SPI0_10034000_BASE_ADDRESS;
+ }
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi)
{
if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
return METAL_SIFIVE_SPI0_10014000_SIZE;
}
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return METAL_SIFIVE_SPI0_10024000_SIZE;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return METAL_SIFIVE_SPI0_10034000_SIZE;
+ }
else {
return 0;
}
}
-static inline struct metal_clock * __metal_driver_sifive_spi0_clock(struct metal_spi *spi)
+static __inline__ struct metal_clock * __metal_driver_sifive_spi0_clock(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi)
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi)
{
- return 60;
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
return 60;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return 4227858432;
+ }
+ else {
+ return 0;
+ }
}
@@ -625,91 +1059,201 @@ static inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(st
/* --------------------- sifive_test0 ------------ */
+/* --------------------- sifive_trace ------------ */
+
/* --------------------- sifive_uart0 ------------ */
-static inline unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_SIFIVE_UART0_10013000_BASE_ADDRESS;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_SIFIVE_UART0_10023000_BASE_ADDRESS;
+ }
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_SIFIVE_UART0_10013000_SIZE;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_SIFIVE_UART0_10023000_SIZE;
+ }
else {
return 0;
}
}
-static inline int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart)
+static __inline__ int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_MAX_UART_INTERRUPTS;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_MAX_UART_INTERRUPTS;
+ }
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart)
+static __inline__ int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart)
{
- return 5;
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return 3;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 4;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart)
+static __inline__ struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart)
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart)
{
- return 196608;
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return 0;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return 196608;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 8650752;
+ }
+ else {
+ return 0;
+ }
+}
+
+
+
+/* --------------------- sifive_simuart0 ------------ */
+
+
+/* --------------------- sifive_wdog0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_wdog0_control_base(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return METAL_SIFIVE_AON0_10000000_BASE_ADDRESS;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_wdog0_control_size(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return METAL_SIFIVE_AON0_10000000_SIZE;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_wdog0_interrupt_parent(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_wdog0_interrupt_line(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return 1;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_wdog0_clock(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return (struct metal_clock *)&__metal_dt_clock_7.clock;
+ }
+ else {
+ return 0;
+ }
}
/* --------------------- sifive_fe310_g000_hfrosc ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_2.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock)
+static __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock)
{
return &__metal_driver_vtable_sifive_fe310_g000_prci;
}
-static inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_HFROSCCFG;
}
@@ -717,55 +1261,98 @@ static inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const s
/* --------------------- sifive_fe310_g000_hfxosc ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_0.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_HFXOSCCFG;
}
+/* --------------------- sifive_fe310_g000_lfrosc ------------ */
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return (struct metal_clock *)&__metal_dt_clock_5.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return (struct metal_clock *)&__metal_dt_clock_6.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_config_reg(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return 112;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return 124;
+ }
+ else {
+ return 0;
+ }
+}
+
+
+
/* --------------------- sifive_fe310_g000_pll ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_3.clock;
}
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_1.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_PLLOUTDIV;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( )
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( )
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_config_offset( )
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_config_offset( )
{
return METAL_SIFIVE_FE310_G000_PRCI_PLLCFG;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_init_rate( )
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_init_rate( )
{
return 16000000;
}
@@ -773,31 +1360,29 @@ static inline long __metal_driver_sifive_fe310_g000_pll_init_rate( )
/* --------------------- sifive_fe310_g000_prci ------------ */
-static inline long __metal_driver_sifive_fe310_g000_prci_base( )
+static __inline__ long __metal_driver_sifive_fe310_g000_prci_base( )
{
return METAL_SIFIVE_FE310_G000_PRCI_10008000_BASE_ADDRESS;
}
-static inline long __metal_driver_sifive_fe310_g000_prci_size( )
+static __inline__ long __metal_driver_sifive_fe310_g000_prci_size( )
{
return METAL_SIFIVE_FE310_G000_PRCI_10008000_SIZE;
}
-static inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( )
+static __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( )
{
return &__metal_driver_vtable_sifive_fe310_g000_prci;
}
-/* --------------------- sifive_fu540_c000_l2 ------------ */
-
+#define __METAL_DT_MAX_MEMORIES 3
-#define __METAL_DT_MAX_MEMORIES 2
-
-asm (".weak __metal_memory_table");
+__asm__ (".weak __metal_memory_table");
struct metal_memory *__metal_memory_table[] = {
&__metal_dt_mem_dtim_80000000,
+ &__metal_dt_mem_itim_8000000,
&__metal_dt_mem_spi_10014000};
/* From serial@10013000 */
@@ -814,7 +1399,9 @@ struct metal_memory *__metal_memory_table[] = {
#define __METAL_DT_MAX_HARTS 1
-asm (".weak __metal_cpu_table");
+#define __METAL_CPU_0_ICACHE_HANDLE 1
+
+__asm__ (".weak __metal_cpu_table");
struct __metal_driver_cpu *__metal_cpu_table[] = {
&__metal_dt_cpu_0};
@@ -825,47 +1412,82 @@ struct __metal_driver_cpu *__metal_cpu_table[] = {
#define __METAL_DT_PMP_HANDLE (&__metal_dt_pmp)
-/* From local_external_interrupts_0 */
-#define __METAL_DT_SIFIVE_LOCAL_EXINTR0_HANDLE (&__metal_dt_local_external_interrupts_0.irc)
-
-#define __METAL_DT_LOCAL_EXTERNAL_INTERRUPTS_0_HANDLE (&__metal_dt_local_external_interrupts_0.irc)
-
#define __MEE_DT_MAX_GPIOS 1
-asm (".weak __metal_gpio_table");
+__asm__ (".weak __metal_gpio_table");
struct __metal_driver_sifive_gpio0 *__metal_gpio_table[] = {
&__metal_dt_gpio_10012000};
#define __METAL_DT_MAX_BUTTONS 0
-asm (".weak __metal_button_table");
+__asm__ (".weak __metal_button_table");
struct __metal_driver_sifive_gpio_button *__metal_button_table[] = {
NULL };
#define __METAL_DT_MAX_LEDS 3
-asm (".weak __metal_led_table");
+__asm__ (".weak __metal_led_table");
struct __metal_driver_sifive_gpio_led *__metal_led_table[] = {
- &__metal_dt_led_0red,
- &__metal_dt_led_0green,
- &__metal_dt_led_0blue};
+ &__metal_dt_led_0,
+ &__metal_dt_led_1,
+ &__metal_dt_led_2};
#define __METAL_DT_MAX_SWITCHES 0
-asm (".weak __metal_switch_table");
+__asm__ (".weak __metal_switch_table");
struct __metal_driver_sifive_gpio_switch *__metal_switch_table[] = {
NULL };
-#define __METAL_DT_MAX_SPIS 1
+#define __METAL_DT_MAX_I2CS 1
+
+__asm__ (".weak __metal_i2c_table");
+struct __metal_driver_sifive_i2c0 *__metal_i2c_table[] = {
+ &__metal_dt_i2c_10016000};
+
+#define __METAL_DT_MAX_PWMS 3
+
+__asm__ (".weak __metal_pwm_table");
+struct __metal_driver_sifive_pwm0 *__metal_pwm_table[] = {
+ &__metal_dt_pwm_10015000,
+ &__metal_dt_pwm_10025000,
+ &__metal_dt_pwm_10035000};
+
+#define __METAL_DT_MAX_RTCS 1
-asm (".weak __metal_spi_table");
+__asm__ (".weak __metal_rtc_table");
+struct __metal_driver_sifive_rtc0 *__metal_rtc_table[] = {
+ &__metal_dt_rtc_10000000};
+
+#define __METAL_DT_MAX_SPIS 3
+
+__asm__ (".weak __metal_spi_table");
struct __metal_driver_sifive_spi0 *__metal_spi_table[] = {
- &__metal_dt_spi_10014000};
+ &__metal_dt_spi_10014000,
+ &__metal_dt_spi_10024000,
+ &__metal_dt_spi_10034000};
+
+#define __METAL_DT_MAX_UARTS 2
+
+__asm__ (".weak __metal_uart_table");
+struct __metal_driver_sifive_uart0 *__metal_uart_table[] = {
+ &__metal_dt_serial_10013000,
+ &__metal_dt_serial_10023000};
+
+#define __METAL_DT_MAX_SIMUARTS 0
+
+__asm__ (".weak __metal_simuart_table");
+struct __metal_driver_sifive_simuart0 *__metal_simuart_table[] = {
+ NULL };
+#define __METAL_DT_MAX_WDOGS 1
+
+__asm__ (".weak __metal_wdog_table");
+struct __metal_driver_sifive_wdog0 *__metal_wdog_table[] = {
+ &__metal_dt_aon_10000000};
/* From clock@4 */
#define __METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE (&__metal_dt_clock_4)
#define __METAL_DT_CLOCK_4_HANDLE (&__metal_dt_clock_4)
-#endif /* MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H*/
+#endif /* MACROS_ELSE_METAL_H*/
#endif /* ! __METAL_MACHINE_MACROS */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/inline.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/inline.h
index 8c0cd048b..fd05ab065 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/inline.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/inline.h
@@ -5,128 +5,181 @@
#ifndef ASSEMBLY
-#ifndef SIFIVE_HIFIVE1_REVB____METAL_INLINE_H
-#define SIFIVE_HIFIVE1_REVB____METAL_INLINE_H
+#ifndef METAL_INLINE_H
+#define METAL_INLINE_H
#include <metal/machine.h>
/* --------------------- fixed_clock ------------ */
-extern inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock);
+extern __inline__ unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock);
/* --------------------- fixed_factor_clock ------------ */
/* --------------------- sifive_clint0 ------------ */
-extern inline unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller);
-extern inline unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller);
-extern inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx);
-extern inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller);
+extern __inline__ unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx);
/* --------------------- cpu ------------ */
-extern inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu);
-extern inline int __metal_driver_cpu_timebase(struct metal_cpu *cpu);
-extern inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu);
-extern inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_hartid(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_timebase(struct metal_cpu *cpu);
+extern __inline__ struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu);
+extern __inline__ struct metal_buserror * __metal_driver_cpu_buserror(struct metal_cpu *cpu);
/* --------------------- sifive_plic0 ------------ */
-extern inline unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller);
-extern inline unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller);
-extern inline struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx);
-extern inline int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller);
+extern __inline__ unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_plic0_context_ids(int hartid);
+
+
+/* --------------------- sifive_buserror0 ------------ */
/* --------------------- sifive_clic0 ------------ */
/* --------------------- sifive_local_external_interrupts0 ------------ */
-extern inline struct metal_interrupt * __metal_driver_sifive_local_external_interrupts0_interrupt_parent(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_local_external_interrupts0_num_interrupts(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lines(struct metal_interrupt *controller, int idx);
/* --------------------- sifive_global_external_interrupts0 ------------ */
/* --------------------- sifive_gpio0 ------------ */
-extern inline unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio);
-extern inline unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio);
-extern inline int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio);
-extern inline struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio);
-extern inline int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio);
+extern __inline__ unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio);
+extern __inline__ int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio);
+extern __inline__ int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx);
/* --------------------- sifive_gpio_button ------------ */
/* --------------------- sifive_gpio_led ------------ */
-extern inline struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led);
-extern inline int __metal_driver_sifive_gpio_led_pin(struct metal_led *led);
-extern inline char * __metal_driver_sifive_gpio_led_label(struct metal_led *led);
+extern __inline__ struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led);
+extern __inline__ int __metal_driver_sifive_gpio_led_pin(struct metal_led *led);
+extern __inline__ char * __metal_driver_sifive_gpio_led_label(struct metal_led *led);
/* --------------------- sifive_gpio_switch ------------ */
+/* --------------------- sifive_i2c0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_control_base(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_control_size(struct metal_i2c *i2c);
+extern __inline__ int __metal_driver_sifive_i2c0_num_interrupts(struct metal_i2c *i2c);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_i2c0_interrupt_parent(struct metal_i2c *i2c);
+extern __inline__ int __metal_driver_sifive_i2c0_interrupt_line(struct metal_i2c *i2c);
+extern __inline__ struct metal_clock * __metal_driver_sifive_i2c0_clock(struct metal_i2c *i2c);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_i2c0_pinmux(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_output_selector(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_source_selector(struct metal_i2c *i2c);
+
+
+/* --------------------- sifive_pwm0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_control_base(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_control_size(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_num_interrupts(struct metal_pwm *pwm);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_pwm0_interrupt_parent(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_interrupt_lines(struct metal_pwm *pwm, int idx);
+extern __inline__ struct metal_clock * __metal_driver_sifive_pwm0_clock(struct metal_pwm *pwm);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_pwm0_pinmux(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_output_selector(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_source_selector(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_compare_width(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_comparator_count(struct metal_pwm *pwm);
+
+
+/* --------------------- sifive_rtc0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_rtc0_control_base(const struct metal_rtc *const rtc);
+extern __inline__ unsigned long __metal_driver_sifive_rtc0_control_size(const struct metal_rtc *const rtc);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_rtc0_interrupt_parent(const struct metal_rtc *const rtc);
+extern __inline__ int __metal_driver_sifive_rtc0_interrupt_line(const struct metal_rtc *const rtc);
+extern __inline__ struct metal_clock * __metal_driver_sifive_rtc0_clock(const struct metal_rtc *const rtc);
+
+
/* --------------------- sifive_spi0 ------------ */
-extern inline unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi);
-extern inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi);
/* --------------------- sifive_test0 ------------ */
+/* --------------------- sifive_trace ------------ */
+
/* --------------------- sifive_uart0 ------------ */
-extern inline unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart);
-extern inline int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart);
-extern inline struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart);
-extern inline int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart);
-extern inline struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart);
-extern inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart);
+extern __inline__ int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart);
+extern __inline__ int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart);
+extern __inline__ struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart);
+
+
+/* --------------------- sifive_simuart0 ------------ */
+
+
+/* --------------------- sifive_wdog0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_wdog0_control_base(const struct metal_watchdog *const watchdog);
+extern __inline__ unsigned long __metal_driver_sifive_wdog0_control_size(const struct metal_watchdog *const watchdog);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_wdog0_interrupt_parent(const struct metal_watchdog *const watchdog);
+extern __inline__ int __metal_driver_sifive_wdog0_interrupt_line(const struct metal_watchdog *const watchdog);
+extern __inline__ struct metal_clock * __metal_driver_sifive_wdog0_clock(const struct metal_watchdog *const watchdog);
/* --------------------- sifive_fe310_g000_hfrosc ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock);
-extern inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock);
+extern __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock);
/* --------------------- sifive_fe310_g000_hfxosc ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock);
-/* --------------------- sifive_fe310_g000_pll ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock);
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( );
-extern inline long __metal_driver_sifive_fe310_g000_pll_config_offset( );
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_pll_init_rate( );
+/* --------------------- sifive_fe310_g000_lfrosc ------------ */
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(const struct metal_clock *clock);
+extern __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_config_reg(const struct metal_clock *clock);
+extern __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(const struct metal_clock *clock);
-/* --------------------- fe310_g000_prci ------------ */
-extern inline long __metal_driver_sifive_fe310_g000_prci_base( );
-extern inline long __metal_driver_sifive_fe310_g000_prci_size( );
-extern inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( );
+/* --------------------- sifive_fe310_g000_pll ------------ */
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( );
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_config_offset( );
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_init_rate( );
-/* --------------------- sifive_fu540_c000_l2 ------------ */
+/* --------------------- fe310_g000_prci ------------ */
+extern __inline__ long __metal_driver_sifive_fe310_g000_prci_base( );
+extern __inline__ long __metal_driver_sifive_fe310_g000_prci_size( );
+extern __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( );
/* From clock@0 */
@@ -144,6 +197,11 @@ struct __metal_driver_fixed_clock __metal_dt_clock_5 = {
.clock.vtable = &__metal_driver_vtable_fixed_clock.clock,
};
+/* From clock@6 */
+struct __metal_driver_fixed_clock __metal_dt_clock_6 = {
+ .clock.vtable = &__metal_driver_vtable_fixed_clock.clock,
+};
+
struct metal_memory __metal_dt_mem_dtim_80000000 = {
._base_address = 2147483648UL,
._size = 16384UL,
@@ -155,6 +213,17 @@ struct metal_memory __metal_dt_mem_dtim_80000000 = {
.A = 1},
};
+struct metal_memory __metal_dt_mem_itim_8000000 = {
+ ._base_address = 134217728UL,
+ ._size = 8192UL,
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
struct metal_memory __metal_dt_mem_spi_10014000 = {
._base_address = 536870912UL,
._size = 500000UL,
@@ -166,6 +235,24 @@ struct metal_memory __metal_dt_mem_spi_10014000 = {
.A = 1},
};
+struct metal_memory __metal_dt_mem_spi_10024000 = {
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
+struct metal_memory __metal_dt_mem_spi_10034000 = {
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
/* From clint@2000000 */
struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000 = {
.controller.vtable = &__metal_driver_vtable_riscv_clint0.clint_vtable,
@@ -175,6 +262,7 @@ struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000 = {
/* From cpu@0 */
struct __metal_driver_cpu __metal_dt_cpu_0 = {
.cpu.vtable = &__metal_driver_vtable_cpu.cpu_vtable,
+ .hpm_count = 0,
};
/* From interrupt_controller */
@@ -189,42 +277,83 @@ struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000 = {
.init_done = 0,
};
-/* From local_external_interrupts_0 */
-struct __metal_driver_sifive_local_external_interrupts0 __metal_dt_local_external_interrupts_0 = {
- .irc.vtable = &__metal_driver_vtable_sifive_local_external_interrupts0.local0_vtable,
- .init_done = 0,
-};
+struct metal_pmp __metal_dt_pmp;
/* From gpio@10012000 */
struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000 = {
.gpio.vtable = &__metal_driver_vtable_sifive_gpio0.gpio,
};
-/* From led@0red */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0red = {
+/* From led@0 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_0 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
-/* From led@0green */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0green = {
+/* From led@1 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_1 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
-/* From led@0blue */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0blue = {
+/* From led@2 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_2 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
+/* From i2c@10016000 */
+struct __metal_driver_sifive_i2c0 __metal_dt_i2c_10016000 = {
+ .i2c.vtable = &__metal_driver_vtable_sifive_i2c0.i2c,
+};
+
+/* From pwm@10015000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10015000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From pwm@10025000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10025000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From pwm@10035000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10035000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From aon@10000000 */
+struct __metal_driver_sifive_rtc0 __metal_dt_rtc_10000000 = {
+ .rtc.vtable = &__metal_driver_vtable_sifive_rtc0.rtc,
+};
+
/* From spi@10014000 */
struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000 = {
.spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
};
+/* From spi@10024000 */
+struct __metal_driver_sifive_spi0 __metal_dt_spi_10024000 = {
+ .spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
+};
+
+/* From spi@10034000 */
+struct __metal_driver_sifive_spi0 __metal_dt_spi_10034000 = {
+ .spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
+};
+
/* From serial@10013000 */
struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000 = {
.uart.vtable = &__metal_driver_vtable_sifive_uart0.uart,
};
+/* From serial@10023000 */
+struct __metal_driver_sifive_uart0 __metal_dt_serial_10023000 = {
+ .uart.vtable = &__metal_driver_vtable_sifive_uart0.uart,
+};
+
+/* From aon@10000000 */
+struct __metal_driver_sifive_wdog0 __metal_dt_aon_10000000 = {
+ .watchdog.vtable = &__metal_driver_vtable_sifive_wdog0.watchdog,
+};
+
/* From clock@3 */
struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_hfrosc.clock,
@@ -235,6 +364,11 @@ struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_hfxosc.clock,
};
+/* From clock@7 */
+struct __metal_driver_sifive_fe310_g000_lfrosc __metal_dt_clock_7 = {
+ .clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_lfrosc.clock,
+};
+
/* From clock@4 */
struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_pll.clock,
@@ -242,8 +376,9 @@ struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4 = {
/* From prci@10008000 */
struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000 = {
+ .vtable = &__metal_driver_vtable_sifive_fe310_g000_prci,
};
-#endif /* SIFIVE_HIFIVE1_REVB____METAL_INLINE_H*/
+#endif /* METAL_INLINE_H*/
#endif /* ! ASSEMBLY */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/platform.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/platform.h
index 4ecd3e336..d517b5859 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/platform.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/machine/platform.h
@@ -3,8 +3,8 @@
/* ----------------------------------- */
/* ----------------------------------- */
-#ifndef SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H
-#define SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H
+#ifndef METAL_PLATFORM_H
+#define METAL_PLATFORM_H
/* From clock@0 */
#define METAL_FIXED_CLOCK_0_CLOCK_FREQUENCY 16000000UL
@@ -13,7 +13,10 @@
#define METAL_FIXED_CLOCK_2_CLOCK_FREQUENCY 72000000UL
/* From clock@5 */
-#define METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY 32000000UL
+#define METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY 32768UL
+
+/* From clock@6 */
+#define METAL_FIXED_CLOCK_6_CLOCK_FREQUENCY 32768UL
#define METAL_FIXED_CLOCK
@@ -35,15 +38,18 @@
#define METAL_RISCV_PLIC0_0_SIZE 67108864UL
#define METAL_RISCV_PLIC0_C000000_RISCV_MAX_PRIORITY 7UL
#define METAL_RISCV_PLIC0_0_RISCV_MAX_PRIORITY 7UL
-#define METAL_RISCV_PLIC0_C000000_RISCV_NDEV 27UL
-#define METAL_RISCV_PLIC0_0_RISCV_NDEV 27UL
+#define METAL_RISCV_PLIC0_C000000_RISCV_NDEV 53UL
+#define METAL_RISCV_PLIC0_0_RISCV_NDEV 53UL
#define METAL_RISCV_PLIC0
#define METAL_RISCV_PLIC0_PRIORITY_BASE 0UL
#define METAL_RISCV_PLIC0_PENDING_BASE 4096UL
#define METAL_RISCV_PLIC0_ENABLE_BASE 8192UL
-#define METAL_RISCV_PLIC0_THRESHOLD 2097152UL
-#define METAL_RISCV_PLIC0_CLAIM 2097156UL
+#define METAL_RISCV_PLIC0_ENABLE_PER_HART 128UL
+#define METAL_RISCV_PLIC0_CONTEXT_BASE 2097152UL
+#define METAL_RISCV_PLIC0_CONTEXT_PER_HART 4096UL
+#define METAL_RISCV_PLIC0_CONTEXT_THRESHOLD 0UL
+#define METAL_RISCV_PLIC0_CONTEXT_CLAIM 4UL
/* From aon@10000000 */
#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
@@ -111,6 +117,10 @@
#define METAL_SIFIVE_FE310_G000_HFXOSC
+/* From clock@7 */
+
+#define METAL_SIFIVE_FE310_G000_LFROSC
+
/* From prci@10008000 */
#define METAL_SIFIVE_FE310_G000_PRCI_10008000_BASE_ADDRESS 268468224UL
#define METAL_SIFIVE_FE310_G000_PRCI_0_BASE_ADDRESS 268468224UL
@@ -153,11 +163,11 @@
#define METAL_SIFIVE_GPIO0_IOF_SEL 60UL
#define METAL_SIFIVE_GPIO0_OUT_XOR 64UL
-/* From led@0red */
+/* From led@0 */
-/* From led@0green */
+/* From led@1 */
-/* From led@0blue */
+/* From led@2 */
#define METAL_SIFIVE_GPIO_LEDS
@@ -176,16 +186,24 @@
#define METAL_SIFIVE_I2C0_COMMAND 16UL
#define METAL_SIFIVE_I2C0_STATUS 16UL
-/* From local_external_interrupts_0 */
-
-#define METAL_SIFIVE_LOCAL_EXTERNAL_INTERRUPTS0
-
/* From pwm@10015000 */
#define METAL_SIFIVE_PWM0_10015000_BASE_ADDRESS 268521472UL
#define METAL_SIFIVE_PWM0_0_BASE_ADDRESS 268521472UL
#define METAL_SIFIVE_PWM0_10015000_SIZE 4096UL
#define METAL_SIFIVE_PWM0_0_SIZE 4096UL
+/* From pwm@10025000 */
+#define METAL_SIFIVE_PWM0_10025000_BASE_ADDRESS 268587008UL
+#define METAL_SIFIVE_PWM0_1_BASE_ADDRESS 268587008UL
+#define METAL_SIFIVE_PWM0_10025000_SIZE 4096UL
+#define METAL_SIFIVE_PWM0_1_SIZE 4096UL
+
+/* From pwm@10035000 */
+#define METAL_SIFIVE_PWM0_10035000_BASE_ADDRESS 268652544UL
+#define METAL_SIFIVE_PWM0_2_BASE_ADDRESS 268652544UL
+#define METAL_SIFIVE_PWM0_10035000_SIZE 4096UL
+#define METAL_SIFIVE_PWM0_2_SIZE 4096UL
+
#define METAL_SIFIVE_PWM0
#define METAL_SIFIVE_PWM0_PWMCFG 0UL
#define METAL_SIFIVE_PWM0_PWMCOUNT 8UL
@@ -195,12 +213,37 @@
#define METAL_SIFIVE_PWM0_PWMCMP2 40UL
#define METAL_SIFIVE_PWM0_PWMCMP3 44UL
+/* From aon@10000000 */
+#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_0_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_10000000_SIZE 32768UL
+#define METAL_SIFIVE_AON0_0_SIZE 32768UL
+
+#define METAL_SIFIVE_RTC0
+#define METAL_SIFIVE_RTC0_RTCCFG 64UL
+#define METAL_SIFIVE_RTC0_RTCCOUNTLO 72UL
+#define METAL_SIFIVE_RTC0_RTCCOUNTHI 76UL
+#define METAL_SIFIVE_RTC0_RTCS 80UL
+#define METAL_SIFIVE_RTC0_RTCCMP0 96UL
+
/* From spi@10014000 */
#define METAL_SIFIVE_SPI0_10014000_BASE_ADDRESS 268517376UL
#define METAL_SIFIVE_SPI0_0_BASE_ADDRESS 268517376UL
#define METAL_SIFIVE_SPI0_10014000_SIZE 4096UL
#define METAL_SIFIVE_SPI0_0_SIZE 4096UL
+/* From spi@10024000 */
+#define METAL_SIFIVE_SPI0_10024000_BASE_ADDRESS 268582912UL
+#define METAL_SIFIVE_SPI0_1_BASE_ADDRESS 268582912UL
+#define METAL_SIFIVE_SPI0_10024000_SIZE 4096UL
+#define METAL_SIFIVE_SPI0_1_SIZE 4096UL
+
+/* From spi@10034000 */
+#define METAL_SIFIVE_SPI0_10034000_BASE_ADDRESS 268648448UL
+#define METAL_SIFIVE_SPI0_2_BASE_ADDRESS 268648448UL
+#define METAL_SIFIVE_SPI0_10034000_SIZE 4096UL
+#define METAL_SIFIVE_SPI0_2_SIZE 4096UL
+
#define METAL_SIFIVE_SPI0
#define METAL_SIFIVE_SPI0_SCKDIV 0UL
#define METAL_SIFIVE_SPI0_SCKMODE 4UL
@@ -225,6 +268,12 @@
#define METAL_SIFIVE_UART0_10013000_SIZE 4096UL
#define METAL_SIFIVE_UART0_0_SIZE 4096UL
+/* From serial@10023000 */
+#define METAL_SIFIVE_UART0_10023000_BASE_ADDRESS 268578816UL
+#define METAL_SIFIVE_UART0_1_BASE_ADDRESS 268578816UL
+#define METAL_SIFIVE_UART0_10023000_SIZE 4096UL
+#define METAL_SIFIVE_UART0_1_SIZE 4096UL
+
#define METAL_SIFIVE_UART0
#define METAL_SIFIVE_UART0_TXDATA 0UL
#define METAL_SIFIVE_UART0_RXDATA 4UL
@@ -234,4 +283,20 @@
#define METAL_SIFIVE_UART0_IP 20UL
#define METAL_SIFIVE_UART0_DIV 24UL
-#endif /* SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H*/
+/* From aon@10000000 */
+#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_0_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_10000000_SIZE 32768UL
+#define METAL_SIFIVE_AON0_0_SIZE 32768UL
+
+#define METAL_SIFIVE_WDOG0
+#define METAL_SIFIVE_WDOG0_MAGIC_KEY 5370206UL
+#define METAL_SIFIVE_WDOG0_MAGIC_FOOD 218755085UL
+#define METAL_SIFIVE_WDOG0_WDOGCFG 0UL
+#define METAL_SIFIVE_WDOG0_WDOGCOUNT 8UL
+#define METAL_SIFIVE_WDOG0_WDOGS 16UL
+#define METAL_SIFIVE_WDOG0_WDOGFEED 24UL
+#define METAL_SIFIVE_WDOG0_WDOGKEY 28UL
+#define METAL_SIFIVE_WDOG0_WDOGCMP 32UL
+
+#endif /* METAL_PLATFORM_H*/
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/memory.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/memory.h
index b62d8b25a..f009e9ecc 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/memory.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/memory.h
@@ -4,8 +4,8 @@
#ifndef METAL__MEMORY_H
#define METAL__MEMORY_H
-#include <stdint.h>
#include <stddef.h>
+#include <stdint.h>
/*!
* @file memory.h
@@ -14,20 +14,20 @@
*/
struct _metal_memory_attributes {
- int R : 1;
- int W : 1;
- int X : 1;
- int C : 1;
- int A : 1;
+ unsigned int R : 1;
+ unsigned int W : 1;
+ unsigned int X : 1;
+ unsigned int C : 1;
+ unsigned int A : 1;
};
/*!
* @brief A handle for a memory block
*/
struct metal_memory {
- const uintptr_t _base_address;
- const size_t _size;
- const struct _metal_memory_attributes _attrs;
+ const uintptr_t _base_address;
+ const size_t _size;
+ const struct _metal_memory_attributes _attrs;
};
/*!
@@ -37,7 +37,8 @@ struct metal_memory {
* that address is mapped.
*
* @param address The address to query
- * @return The memory block handle, or NULL if the address is not mapped to a memory block
+ * @return The memory block handle, or NULL if the address is not mapped to a
+ * memory block
*/
struct metal_memory *metal_get_memory_from_address(const uintptr_t address);
@@ -46,8 +47,9 @@ struct metal_memory *metal_get_memory_from_address(const uintptr_t address);
* @param memory The handle for the memory block
* @return The base address of the memory block
*/
-inline uintptr_t metal_memory_get_base_address(const struct metal_memory *memory) {
- return memory->_base_address;
+__inline__ uintptr_t
+metal_memory_get_base_address(const struct metal_memory *memory) {
+ return memory->_base_address;
}
/*!
@@ -55,8 +57,8 @@ inline uintptr_t metal_memory_get_base_address(const struct metal_memory *memory
* @param memory The handle for the memory block
* @return The size of the memory block
*/
-inline size_t metal_memory_get_size(const struct metal_memory *memory) {
- return memory->_size;
+__inline__ size_t metal_memory_get_size(const struct metal_memory *memory) {
+ return memory->_size;
}
/*!
@@ -64,8 +66,9 @@ inline size_t metal_memory_get_size(const struct metal_memory *memory) {
* @param memory The handle for the memory block
* @return nonzero if the memory block supports atomic operations
*/
-inline int metal_memory_supports_atomics(const struct metal_memory *memory) {
- return memory->_attrs.A;
+__inline__ int
+metal_memory_supports_atomics(const struct metal_memory *memory) {
+ return memory->_attrs.A;
}
/*!
@@ -73,9 +76,8 @@ inline int metal_memory_supports_atomics(const struct metal_memory *memory) {
* @param memory The handle for the memory block
* @return nonzero if the memory block is cachable
*/
-inline int metal_memory_is_cachable(const struct metal_memory *memory) {
- return memory->_attrs.C;
+__inline__ int metal_memory_is_cachable(const struct metal_memory *memory) {
+ return memory->_attrs.C;
}
#endif /* METAL__MEMORY_H */
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pmp.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pmp.h
index 9121b10a1..38ab1b9a4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pmp.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pmp.h
@@ -12,14 +12,14 @@
* The Physical Memory Protection (PMP) interface on RISC-V cores
* is a form of memory protection unit which allows for a finite number
* of physical memory regions to be configured with certain access
- * permissions.
+ * permissions.
*
* Additional information about the use and configuration rules for PMPs
* can be found by reading the RISC-V Privileged Architecture Specification.
*/
-#include <stddef.h>
#include <metal/machine.h>
+#include <stddef.h>
struct metal_pmp;
@@ -28,11 +28,11 @@ struct metal_pmp;
*/
enum metal_pmp_address_mode {
/*! @brief Disable the PMP region */
- METAL_PMP_OFF = 0,
+ METAL_PMP_OFF = 0,
/*! @brief Use Top-of-Range mode */
- METAL_PMP_TOR = 1,
+ METAL_PMP_TOR = 1,
/*! @brief Use naturally-aligned 4-byte region mode */
- METAL_PMP_NA4 = 2,
+ METAL_PMP_NA4 = 2,
/*! @brief Use naturally-aligned power-of-two mode */
METAL_PMP_NAPOT = 3
};
@@ -42,11 +42,11 @@ enum metal_pmp_address_mode {
*/
struct metal_pmp_config {
/*! @brief Sets whether reads to the PMP region succeed */
- int R : 1;
+ unsigned int R : 1;
/*! @brief Sets whether writes to the PMP region succeed */
- int W : 1;
+ unsigned int W : 1;
/*! @brief Sets whether the PMP region is executable */
- int X : 1;
+ unsigned int X : 1;
/*! @brief Sets the addressing mode of the PMP region */
enum metal_pmp_address_mode A : 2;
@@ -56,7 +56,7 @@ struct metal_pmp_config {
/*! @brief Sets whether the PMP region is locked */
enum metal_pmp_locked {
METAL_PMP_UNLOCKED = 0,
- METAL_PMP_LOCKED = 1
+ METAL_PMP_LOCKED = 1
} L : 1;
};
@@ -74,6 +74,11 @@ struct metal_pmp {
struct metal_pmp *metal_pmp_get_device(void);
/*!
+ * @brief Get the number of pmp regions for the hartid
+ */
+int metal_pmp_num_regions(int hartid);
+
+/*!
* @brief Initialize the PMP
* @param pmp The PMP device handle to be initialized
*
@@ -96,9 +101,10 @@ void metal_pmp_init(struct metal_pmp *pmp);
* @param address The desired address of the PMP region
* @return 0 upon success
*/
-int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region, struct metal_pmp_config config, size_t address);
+int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config config, size_t address);
-/*!
+/*!
* @brief Get the configuration for a PMP region
* @param pmp The PMP device handle
* @param region The PMP region to read
@@ -106,7 +112,8 @@ int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region, struct meta
* @param address Variable to store the PMP region address
* @return 0 if the region is read successfully
*/
-int metal_pmp_get_region(struct metal_pmp *pmp, unsigned int region, struct metal_pmp_config *config, size_t *address);
+int metal_pmp_get_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config *config, size_t *address);
/*!
* @brief Lock a PMP region
@@ -123,7 +130,8 @@ int metal_pmp_lock(struct metal_pmp *pmp, unsigned int region);
* @param address The desired address of the PMP region
* @return 0 if the address is successfully set
*/
-int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region, size_t address);
+int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region,
+ size_t address);
/*!
* @brief Get the address of a PMP region
@@ -140,7 +148,8 @@ size_t metal_pmp_get_address(struct metal_pmp *pmp, unsigned int region);
* @param mode The PMP addressing mode to set
* @return 0 if the addressing mode is successfully set
*/
-int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum metal_pmp_address_mode mode);
+int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region,
+ enum metal_pmp_address_mode mode);
/*!
* @brief Get the addressing mode of a PMP region
@@ -148,7 +157,8 @@ int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum
* @param region The PMP region to read
* @return The address mode of the PMP region
*/
-enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp, unsigned int region);
+enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp,
+ unsigned int region);
/*!
* @brief Set the executable bit for a PMP region
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/privilege.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/privilege.h
index c5212e5d1..522e7efe0 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/privilege.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/privilege.h
@@ -16,9 +16,9 @@
#include <stdint.h>
enum metal_privilege_mode {
- METAL_PRIVILEGE_USER = 0,
- METAL_PRIVILEGE_SUPERVISOR = 1,
- METAL_PRIVELEGE_MACHINE = 3,
+ METAL_PRIVILEGE_USER = 0,
+ METAL_PRIVILEGE_SUPERVISOR = 1,
+ METAL_PRIVILEGE_MACHINE = 3,
};
#if __riscv_xlen == 32
@@ -34,89 +34,89 @@ typedef uint64_t metal_freg_t;
#endif
struct metal_register_file {
- metal_xreg_t ra;
- metal_xreg_t sp;
- metal_xreg_t gp;
- metal_xreg_t tp;
-
- metal_xreg_t t0;
- metal_xreg_t t1;
- metal_xreg_t t2;
-
- metal_xreg_t s0;
- metal_xreg_t s1;
-
- metal_xreg_t a0;
- metal_xreg_t a1;
- metal_xreg_t a2;
- metal_xreg_t a3;
- metal_xreg_t a4;
- metal_xreg_t a5;
+ metal_xreg_t ra;
+ metal_xreg_t sp;
+ metal_xreg_t gp;
+ metal_xreg_t tp;
+
+ metal_xreg_t t0;
+ metal_xreg_t t1;
+ metal_xreg_t t2;
+
+ metal_xreg_t s0;
+ metal_xreg_t s1;
+
+ metal_xreg_t a0;
+ metal_xreg_t a1;
+ metal_xreg_t a2;
+ metal_xreg_t a3;
+ metal_xreg_t a4;
+ metal_xreg_t a5;
#ifndef __riscv_32e
- metal_xreg_t a6;
- metal_xreg_t a7;
-
- metal_xreg_t s2;
- metal_xreg_t s3;
- metal_xreg_t s4;
- metal_xreg_t s5;
- metal_xreg_t s6;
- metal_xreg_t s7;
- metal_xreg_t s8;
- metal_xreg_t s9;
- metal_xreg_t s10;
- metal_xreg_t s11;
-
- metal_xreg_t t3;
- metal_xreg_t t4;
- metal_xreg_t t5;
- metal_xreg_t t6;
+ metal_xreg_t a6;
+ metal_xreg_t a7;
+
+ metal_xreg_t s2;
+ metal_xreg_t s3;
+ metal_xreg_t s4;
+ metal_xreg_t s5;
+ metal_xreg_t s6;
+ metal_xreg_t s7;
+ metal_xreg_t s8;
+ metal_xreg_t s9;
+ metal_xreg_t s10;
+ metal_xreg_t s11;
+
+ metal_xreg_t t3;
+ metal_xreg_t t4;
+ metal_xreg_t t5;
+ metal_xreg_t t6;
#endif /* __riscv_32e */
#ifdef __riscv_flen
- metal_freg_t ft0;
- metal_freg_t ft1;
- metal_freg_t ft2;
- metal_freg_t ft3;
- metal_freg_t ft4;
- metal_freg_t ft5;
- metal_freg_t ft6;
- metal_freg_t ft7;
-
- metal_freg_t fs0;
- metal_freg_t fs1;
-
- metal_freg_t fa0;
- metal_freg_t fa1;
- metal_freg_t fa2;
- metal_freg_t fa3;
- metal_freg_t fa4;
- metal_freg_t fa5;
- metal_freg_t fa6;
- metal_freg_t fa7;
-
- metal_freg_t fs2;
- metal_freg_t fs3;
- metal_freg_t fs4;
- metal_freg_t fs5;
- metal_freg_t fs6;
- metal_freg_t fs7;
- metal_freg_t fs8;
- metal_freg_t fs9;
- metal_freg_t fs10;
- metal_freg_t fs11;
-
- metal_freg_t ft8;
- metal_freg_t ft9;
- metal_freg_t ft10;
- metal_freg_t ft11;
+ metal_freg_t ft0;
+ metal_freg_t ft1;
+ metal_freg_t ft2;
+ metal_freg_t ft3;
+ metal_freg_t ft4;
+ metal_freg_t ft5;
+ metal_freg_t ft6;
+ metal_freg_t ft7;
+
+ metal_freg_t fs0;
+ metal_freg_t fs1;
+
+ metal_freg_t fa0;
+ metal_freg_t fa1;
+ metal_freg_t fa2;
+ metal_freg_t fa3;
+ metal_freg_t fa4;
+ metal_freg_t fa5;
+ metal_freg_t fa6;
+ metal_freg_t fa7;
+
+ metal_freg_t fs2;
+ metal_freg_t fs3;
+ metal_freg_t fs4;
+ metal_freg_t fs5;
+ metal_freg_t fs6;
+ metal_freg_t fs7;
+ metal_freg_t fs8;
+ metal_freg_t fs9;
+ metal_freg_t fs10;
+ metal_freg_t fs11;
+
+ metal_freg_t ft8;
+ metal_freg_t ft9;
+ metal_freg_t ft10;
+ metal_freg_t ft11;
#endif /* __riscv_flen */
};
-typedef void (*metal_privilege_entry_point_t)();
+typedef void (*metal_privilege_entry_point_t)(void);
void metal_privilege_drop_to_mode(enum metal_privilege_mode mode,
- struct metal_register_file regfile,
- metal_privilege_entry_point_t entry_point);
+ struct metal_register_file regfile,
+ metal_privilege_entry_point_t entry_point);
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pwm.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pwm.h
new file mode 100644
index 000000000..600d5a02b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/pwm.h
@@ -0,0 +1,162 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__PWM_H
+#define METAL__PWM_H
+
+/*! @brief Enums for PWM running modes. */
+typedef enum {
+ METAL_PWM_CONTINUOUS = 0,
+ METAL_PWM_ONE_SHOT = 1
+} metal_pwm_run_mode_t;
+
+/*! @brief Enums for Phase correct PWM. */
+typedef enum {
+ METAL_PWM_PHASE_CORRECT_DISABLE = 0,
+ METAL_PWM_PHASE_CORRECT_ENABLE = 1,
+} metal_pwm_phase_correct_t;
+
+/*! @brief Enums for Interrupts enable/disable. */
+typedef enum {
+ METAL_PWM_INTERRUPT_DISABLE = 0,
+ METAL_PWM_INTERRUPT_ENABLE = 1,
+} metal_pwm_interrupt_t;
+
+struct metal_pwm;
+
+/*! @brief vtable for PWM. */
+struct metal_pwm_vtable {
+ int (*enable)(struct metal_pwm *pwm);
+ int (*disable)(struct metal_pwm *pwm);
+ int (*set_freq)(struct metal_pwm *pwm, unsigned int idx, unsigned int freq);
+ int (*set_duty)(struct metal_pwm *pwm, unsigned int idx, unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr);
+ unsigned int (*get_duty)(struct metal_pwm *pwm, unsigned int idx);
+ unsigned int (*get_freq)(struct metal_pwm *pwm, unsigned int idx);
+ int (*trigger)(struct metal_pwm *pwm, unsigned int idx,
+ metal_pwm_run_mode_t mode);
+ int (*stop)(struct metal_pwm *pwm, unsigned int idx);
+ int (*cfg_interrupt)(struct metal_pwm *pwm, metal_pwm_interrupt_t flag);
+ int (*clr_interrupt)(struct metal_pwm *pwm, unsigned int idx);
+ struct metal_interrupt *(*get_interrupt_controller)(struct metal_pwm *pwm);
+ int (*get_interrupt_id)(struct metal_pwm *pwm, unsigned int idx);
+};
+
+/*! @brief A handle for a PWM device. */
+struct metal_pwm {
+ const struct metal_pwm_vtable *vtable;
+};
+
+/*! @brief Gets a PWM device handle.
+ * @param device_num The index of the desired PWM device.
+ * @return A handle to the PWM device, or NULL if the device does not exist.*/
+struct metal_pwm *metal_pwm_get_device(unsigned int device_num);
+
+/*! @brief Enables PWM operation.
+ * @param pwm The handle for the PWM device to initialize.
+ * @return 0 If no error.*/
+inline int metal_pwm_enable(struct metal_pwm *pwm) {
+ return pwm->vtable->enable(pwm);
+}
+
+/*! @brief Disables PWM operation.
+ * @param pwm The handle for the PWM device to be disabled.
+ * @return 0 If no error.*/
+inline int metal_pwm_disable(struct metal_pwm *pwm) {
+ return pwm->vtable->disable(pwm);
+}
+
+/*! @brief Sets frequency in Hz for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @param freq PWM frequency in Hz.
+ * @return 0 If no error.*/
+inline int metal_pwm_set_freq(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int freq) {
+ return pwm->vtable->set_freq(pwm, idx, freq);
+}
+
+/*! @brief Sets duty cycle in percent values [0 - 100] for a given PWM instance.
+ * Phase correct mode provides center aligned PWM waveform output.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @param duty PWM duty cycle value.
+ * @param phase_corr Enable / Disable phase correct mode.
+ * @return 0 If no error.*/
+inline int metal_pwm_set_duty(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr) {
+ return pwm->vtable->set_duty(pwm, idx, duty, phase_corr);
+}
+
+/*! @brief Gets duty cycle in percent values [0 - 100] for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return PWM duty cycle value.*/
+inline unsigned int metal_pwm_get_duty(struct metal_pwm *pwm,
+ unsigned int idx) {
+ return pwm->vtable->get_duty(pwm, idx);
+}
+
+/*! @brief Gets frequency in Hz for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return PWM frequency in Hz.*/
+inline unsigned int metal_pwm_get_freq(struct metal_pwm *pwm,
+ unsigned int idx) {
+ return pwm->vtable->get_freq(pwm, idx);
+}
+
+/*! @brief Starts a PWM instance in selected run mode (continuous/one shot).
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_trigger(struct metal_pwm *pwm, unsigned int idx,
+ metal_pwm_run_mode_t mode) {
+ return pwm->vtable->trigger(pwm, idx, mode);
+}
+
+/*! @brief Stops a running PWM instance in continuous mode.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_stop(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->stop(pwm, idx);
+}
+
+/*! @brief Enable or Disable PWM interrupts.
+ * @param pwm PWM device handle.
+ * @param flag PWM interrupt enable flag.
+ * @return 0 If no error.*/
+inline int metal_pwm_cfg_interrupt(struct metal_pwm *pwm,
+ metal_pwm_interrupt_t flag) {
+ return pwm->vtable->cfg_interrupt(pwm, flag);
+}
+
+/*! @brief Clears pending interrupt flags.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_clr_interrupt(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->clr_interrupt(pwm, idx);
+}
+
+/*! @brief Get the interrupt controller of the PWM peripheral.
+ * The interrupt controller must be initialized before any interrupts can be
+ * registered or enabled with it.
+ * @param pwm PWM device handle.
+ * @return The handle for the PWM interrupt controller.*/
+inline struct metal_interrupt *
+metal_pwm_interrupt_controller(struct metal_pwm *pwm) {
+ return pwm->vtable->get_interrupt_controller(pwm);
+}
+
+/*! @brief Get the interrupt ID of the PWM peripheral.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return The PWM interrupt id.*/
+inline int metal_pwm_get_interrupt_id(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->get_interrupt_id(pwm, idx);
+}
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/rtc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/rtc.h
new file mode 100644
index 000000000..e1b798268
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/rtc.h
@@ -0,0 +1,137 @@
+/* Copyright 2019 SiFive, Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__RTC_H
+#define METAL__RTC_H
+
+#include <stdint.h>
+
+/*!
+ * @file rtc.h
+ * @brief API for Real-Time Clocks
+ */
+
+struct metal_rtc;
+
+/*!
+ * @brief List of RTC run behaviors
+ */
+enum metal_rtc_run_option {
+ METAL_RTC_STOP = 0,
+ METAL_RTC_RUN,
+};
+
+struct metal_rtc_vtable {
+ uint64_t (*get_rate)(const struct metal_rtc *const rtc);
+ uint64_t (*set_rate)(const struct metal_rtc *const rtc,
+ const uint64_t rate);
+ uint64_t (*get_compare)(const struct metal_rtc *const rtc);
+ uint64_t (*set_compare)(const struct metal_rtc *const rtc,
+ const uint64_t compare);
+ uint64_t (*get_count)(const struct metal_rtc *const rtc);
+ uint64_t (*set_count)(const struct metal_rtc *const rtc,
+ const uint64_t count);
+ int (*run)(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option);
+ struct metal_interrupt *(*get_interrupt)(const struct metal_rtc *const rtc);
+ int (*get_interrupt_id)(const struct metal_rtc *const rtc);
+};
+
+/*!
+ * @brief Handle for a Real-Time Clock
+ */
+struct metal_rtc {
+ const struct metal_rtc_vtable *vtable;
+};
+
+/*!
+ * @brief Get the rate of the RTC
+ * @return The rate in Hz
+ */
+inline uint64_t metal_rtc_get_rate(const struct metal_rtc *const rtc) {
+ return rtc->vtable->get_rate(rtc);
+}
+
+/*!
+ * @brief Set (if possible) the rate of the RTC
+ * @return The new rate of the RTC (not guaranteed to be the same as requested)
+ */
+inline uint64_t metal_rtc_set_rate(const struct metal_rtc *const rtc,
+ const uint64_t rate) {
+ return rtc->vtable->set_rate(rtc, rate);
+}
+
+/*!
+ * @brief Get the compare value of the RTC
+ * @return The compare value
+ */
+inline uint64_t metal_rtc_get_compare(const struct metal_rtc *const rtc) {
+ return rtc->vtable->get_compare(rtc);
+}
+
+/*!
+ * @brief Set the compare value of the RTC
+ * @return The set compare value (not guaranteed to be exactly the requested
+ * value)
+ *
+ * The RTC device might impose limits on the maximum compare value or the
+ * granularity of the compare value.
+ */
+inline uint64_t metal_rtc_set_compare(const struct metal_rtc *const rtc,
+ const uint64_t compare) {
+ return rtc->vtable->set_compare(rtc, compare);
+}
+
+/*!
+ * @brief Get the current count of the RTC
+ * @return The count
+ */
+inline uint64_t metal_rtc_get_count(const struct metal_rtc *const rtc) {
+ return rtc->vtable->get_count(rtc);
+}
+
+/*!
+ * @brief Set the current count of the RTC
+ * @return The set value of the count (not guaranteed to be exactly the
+ * requested value)
+ *
+ * The RTC device might impose limits on the maximum value of the count
+ */
+inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc,
+ const uint64_t count) {
+ return rtc->vtable->set_count(rtc, count);
+}
+
+/*!
+ * @brief Start or stop the RTC
+ * @return 0 if the RTC was successfully started/stopped
+ */
+inline int metal_rtc_run(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option) {
+ return rtc->vtable->run(rtc, option);
+}
+
+/*!
+ * @brief Get the interrupt handle for the RTC compare
+ * @return The interrupt handle
+ */
+inline struct metal_interrupt *
+metal_rtc_get_interrupt(const struct metal_rtc *const rtc) {
+ return rtc->vtable->get_interrupt(rtc);
+}
+
+/*!
+ * @brief Get the interrupt ID for the RTC compare
+ * @return The interrupt ID
+ */
+inline int metal_rtc_get_interrupt_id(const struct metal_rtc *const rtc) {
+ return rtc->vtable->get_interrupt_id(rtc);
+}
+
+/*!
+ * @brief Get the handle for an RTC by index
+ * @return The RTC handle, or NULL if none is available at that index
+ */
+struct metal_rtc *metal_rtc_get_device(int index);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/scrub.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/scrub.h
new file mode 100644
index 000000000..51683cc76
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/scrub.h
@@ -0,0 +1,13 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__SCRUB_H
+#define METAL__SCRUB_H
+
+/*! @brief Writes specified memory region with zeros.
+ * @param address Start memory address for zero-scrub.
+ * @param size Memory region size in bytes.
+ * @return None.*/
+void metal_mem_scrub(void *address, int size);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/shutdown.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/shutdown.h
index 3bebfa742..7a43437b7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/shutdown.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/shutdown.h
@@ -12,15 +12,20 @@
struct __metal_shutdown;
struct __metal_shutdown_vtable {
- void (*exit)(const struct __metal_shutdown *sd, int code) __attribute__((noreturn));
+ void (*exit)(const struct __metal_shutdown *sd, int code)
+ __attribute__((noreturn));
};
struct __metal_shutdown {
const struct __metal_shutdown_vtable *vtable;
};
-inline void __metal_shutdown_exit(const struct __metal_shutdown *sd, int code) __attribute__((noreturn));
-inline void __metal_shutdown_exit(const struct __metal_shutdown *sd, int code) { sd->vtable->exit(sd, code); }
+__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd,
+ int code) __attribute__((noreturn));
+__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd,
+ int code) {
+ sd->vtable->exit(sd, code);
+}
/*!
* @brief The public METAL shutdown interface
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/spi.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/spi.h
index b011fe3ce..7e4b04ae2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/spi.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/spi.h
@@ -9,11 +9,7 @@ struct metal_spi;
/*! @brief The configuration for a SPI transfer */
struct metal_spi_config {
/*! @brief The protocol for the SPI transfer */
- enum {
- METAL_SPI_SINGLE,
- METAL_SPI_DUAL,
- METAL_SPI_QUAD
- } protocol;
+ enum { METAL_SPI_SINGLE, METAL_SPI_DUAL, METAL_SPI_QUAD } protocol;
/*! @brief The polarity of the SPI transfer, equivalent to CPOL */
unsigned int polarity : 1;
@@ -25,11 +21,24 @@ struct metal_spi_config {
unsigned int cs_active_high : 1;
/*! @brief The chip select ID to activate for the SPI transfer */
unsigned int csid;
+ /*! @brief The spi command frame number (cycles = num * frame_len) */
+ unsigned int cmd_num;
+ /*! @brief The spi address frame number */
+ unsigned int addr_num;
+ /*! @brief The spi dummy frame number */
+ unsigned int dummy_num;
+ /*! @brief The Dual/Quad spi mode selection.*/
+ enum {
+ MULTI_WIRE_ALL,
+ MULTI_WIRE_DATA_ONLY,
+ MULTI_WIRE_ADDR_DATA
+ } multi_wire;
};
struct metal_spi_vtable {
void (*init)(struct metal_spi *spi, int baud_rate);
- int (*transfer)(struct metal_spi *spi, struct metal_spi_config *config, size_t len, char *tx_buf, char *rx_buf);
+ int (*transfer)(struct metal_spi *spi, struct metal_spi_config *config,
+ size_t len, char *tx_buf, char *rx_buf);
int (*get_baud_rate)(struct metal_spi *spi);
int (*set_baud_rate)(struct metal_spi *spi, int baud_rate);
};
@@ -42,23 +51,29 @@ struct metal_spi {
/*! @brief Get a handle for a SPI device
* @param device_num The index of the desired SPI device
* @return A handle to the SPI device, or NULL if the device does not exist*/
-struct metal_spi *metal_spi_get_device(int device_num);
+struct metal_spi *metal_spi_get_device(unsigned int device_num);
/*! @brief Initialize a SPI device with a certain baud rate
* @param spi The handle for the SPI device to initialize
* @param baud_rate The baud rate to set the SPI device to
*/
-inline void metal_spi_init(struct metal_spi *spi, int baud_rate) { spi->vtable->init(spi, baud_rate); }
+__inline__ void metal_spi_init(struct metal_spi *spi, int baud_rate) {
+ spi->vtable->init(spi, baud_rate);
+}
/*! @brief Perform a SPI transfer
* @param spi The handle for the SPI device to perform the transfer
* @param config The configuration for the SPI transfer.
* @param len The number of bytes to transfer
- * @param tx_buf The buffer to send over the SPI bus. Must be len bytes long. If NULL, the SPI will transfer the value 0.
- * @param rx_buf The buffer to receive data into. Must be len bytes long. If NULL, the SPI will ignore received bytes.
+ * @param tx_buf The buffer to send over the SPI bus. Must be len bytes long. If
+ * NULL, the SPI will transfer the value 0.
+ * @param rx_buf The buffer to receive data into. Must be len bytes long. If
+ * NULL, the SPI will ignore received bytes.
* @return 0 if the transfer succeeds
*/
-inline int metal_spi_transfer(struct metal_spi *spi, struct metal_spi_config *config, size_t len, char *tx_buf, char *rx_buf) {
+__inline__ int metal_spi_transfer(struct metal_spi *spi,
+ struct metal_spi_config *config, size_t len,
+ char *tx_buf, char *rx_buf) {
return spi->vtable->transfer(spi, config, len, tx_buf, rx_buf);
}
@@ -66,13 +81,17 @@ inline int metal_spi_transfer(struct metal_spi *spi, struct metal_spi_config *co
* @param spi The handle for the SPI device
* @return The baud rate in Hz
*/
-inline int metal_spi_get_baud_rate(struct metal_spi *spi) { return spi->vtable->get_baud_rate(spi); }
+__inline__ int metal_spi_get_baud_rate(struct metal_spi *spi) {
+ return spi->vtable->get_baud_rate(spi);
+}
/*! @brief Set the current baud rate of the SPI device
* @param spi The handle for the SPI device
* @param baud_rate The desired baud rate of the SPI device
* @return 0 if the baud rate is successfully changed
*/
-inline int metal_spi_set_baud_rate(struct metal_spi *spi, int baud_rate) { return spi->vtable->set_baud_rate(spi, baud_rate); }
+__inline__ int metal_spi_set_baud_rate(struct metal_spi *spi, int baud_rate) {
+ return spi->vtable->set_baud_rate(spi, baud_rate);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/switch.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/switch.h
index d1c35bc93..695b21ae3 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/switch.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/switch.h
@@ -15,7 +15,7 @@ struct metal_switch;
struct metal_switch_vtable {
int (*switch_exist)(struct metal_switch *sw, char *label);
- struct metal_interrupt* (*interrupt_controller)(struct metal_switch *sw);
+ struct metal_interrupt *(*interrupt_controller)(struct metal_switch *sw);
int (*get_interrupt_id)(struct metal_switch *sw);
};
@@ -29,23 +29,28 @@ struct metal_switch {
/*!
* @brief Get a handle for a switch
* @param label The DeviceTree label for the desired switch
- * @return A handle to the switch, or NULL if none is found for the requested label
+ * @return A handle to the switch, or NULL if none is found for the requested
+ * label
*/
-struct metal_switch* metal_switch_get(char *label);
+struct metal_switch *metal_switch_get(char *label);
/*!
* @brief Get the interrupt controller for a switch
* @param sw The handle for the switch
* @return The interrupt controller handle
*/
-inline struct metal_interrupt*
- metal_switch_interrupt_controller(struct metal_switch *sw) { return sw->vtable->interrupt_controller(sw); }
+__inline__ struct metal_interrupt *
+metal_switch_interrupt_controller(struct metal_switch *sw) {
+ return sw->vtable->interrupt_controller(sw);
+}
/*!
* @brief Get the interrupt id for a switch
* @param sw The handle for the switch
* @return The interrupt ID for the switch
*/
-inline int metal_switch_get_interrupt_id(struct metal_switch *sw) { return sw->vtable->get_interrupt_id(sw); }
+__inline__ int metal_switch_get_interrupt_id(struct metal_switch *sw) {
+ return sw->vtable->get_interrupt_id(sw);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/time.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/time.h
new file mode 100644
index 000000000..a5a880f0d
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/time.h
@@ -0,0 +1,21 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__TIME_H
+#define METAL__TIME_H
+
+#include <time.h>
+#ifndef __SEGGER_LIBC__
+#include <sys/time.h>
+#endif
+
+/*!
+ * @file time.h
+ * @brief API for dealing with time
+ */
+
+int metal_gettimeofday(struct timeval *tp, void *tzp);
+
+time_t metal_time(void);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/timer.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/timer.h
index eeae1f60b..5d5132de5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/timer.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/timer.h
@@ -23,9 +23,10 @@ int metal_timer_get_cyclecount(int hartid, unsigned long long *cyclecount);
* @param timebase The variable to hold the value
* @return 0 upon success
*/
-int metal_timer_get_timebase_frequency(int hartid, unsigned long long *timebase);
+int metal_timer_get_timebase_frequency(int hartid,
+ unsigned long long *timebase);
-/*!
+/*!
* @brief Set the machine timer tick interval in seconds
* @param hartid The hart ID to read the timebase of
* @param second The number of seconds to set the tick interval to
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/tty.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/tty.h
index d2583e3be..5d41783ae 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/tty.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/tty.h
@@ -14,10 +14,22 @@
*
* Write a character to the default output device, which for most
* targets is the UART serial port.
- *
+ *
* @param c The character to write to the terminal
* @return 0 on success, or -1 on failure.
*/
-int metal_tty_putc(unsigned char c);
+int metal_tty_putc(int c);
+
+/*!
+ * @brief Get a byte from the default output device
+ *
+ * The default output device, is typically the UART serial port.
+ *
+ * This call is non-blocking, if nothing is ready c==-1
+ * if something is ready, then c=[0x00 to 0xff] byte value.
+ *
+ * @return 0 on success, or -1 on failure.
+ */
+int metal_tty_getc(int *c);
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/uart.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/uart.h
index 611792a6c..856970ac2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/uart.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/uart.h
@@ -12,15 +12,25 @@
#include <metal/interrupt.h>
struct metal_uart;
-
+#undef getc
+#undef putc
struct metal_uart_vtable {
void (*init)(struct metal_uart *uart, int baud_rate);
- int (*putc)(struct metal_uart *uart, unsigned char c);
- int (*getc)(struct metal_uart *uart, unsigned char *c);
+ int (*putc)(struct metal_uart *uart, int c);
+ int (*txready)(struct metal_uart *uart);
+ int (*getc)(struct metal_uart *uart, int *c);
int (*get_baud_rate)(struct metal_uart *uart);
int (*set_baud_rate)(struct metal_uart *uart, int baud_rate);
- struct metal_interrupt* (*controller_interrupt)(struct metal_uart *uart);
+ struct metal_interrupt *(*controller_interrupt)(struct metal_uart *uart);
int (*get_interrupt_id)(struct metal_uart *uart);
+ int (*tx_interrupt_enable)(struct metal_uart *uart);
+ int (*tx_interrupt_disable)(struct metal_uart *uart);
+ int (*rx_interrupt_enable)(struct metal_uart *uart);
+ int (*rx_interrupt_disable)(struct metal_uart *uart);
+ int (*set_tx_watermark)(struct metal_uart *uart, size_t length);
+ size_t (*get_tx_watermark)(struct metal_uart *uart);
+ int (*set_rx_watermark)(struct metal_uart *uart, size_t length);
+ size_t (*get_rx_watermark)(struct metal_uart *uart);
};
/*!
@@ -30,16 +40,25 @@ struct metal_uart {
const struct metal_uart_vtable *vtable;
};
+/*! @brief Get a handle for a UART device
+ * @param device_num The index of the desired UART device
+ * @return A handle to the UART device, or NULL if the device does not exist*/
+struct metal_uart *metal_uart_get_device(unsigned int device_num);
+
/*!
* @brief Initialize UART device
-
- * Initialize the UART device described by the UART handle. This function must be called before any
- * other method on the UART can be invoked. It is invalid to initialize a UART more than once.
+
+ * Initialize the UART device described by the UART handle. This function must
+ be called before any
+ * other method on the UART can be invoked. It is invalid to initialize a UART
+ more than once.
*
* @param uart The UART device handle
* @param baud_rate the baud rate to set the UART to
*/
-inline void metal_uart_init(struct metal_uart *uart, int baud_rate) { return uart->vtable->init(uart, baud_rate); }
+__inline__ void metal_uart_init(struct metal_uart *uart, int baud_rate) {
+ uart->vtable->init(uart, baud_rate);
+}
/*!
* @brief Output a character over the UART
@@ -47,22 +66,40 @@ inline void metal_uart_init(struct metal_uart *uart, int baud_rate) { return uar
* @param c The character to send over the UART
* @return 0 upon success
*/
-inline int metal_uart_putc(struct metal_uart *uart, unsigned char c) { return uart->vtable->putc(uart, c); }
+__inline__ int metal_uart_putc(struct metal_uart *uart, int c) {
+ return uart->vtable->putc(uart, c);
+}
+
+/*!
+ * @brief Test, determine if tx output is blocked(full/busy)
+ * @param uart The UART device handle
+ * @return 0 not blocked
+ */
+__inline__ int metal_uart_txready(struct metal_uart *uart) {
+ return uart->vtable->txready(uart);
+}
/*!
* @brief Read a character sent over the UART
* @param uart The UART device handle
* @param c The varible to hold the read character
* @return 0 upon success
+ *
+ * If "c == -1" no char was ready.
+ * If "c != -1" then C == byte value (0x00 to 0xff)
*/
-inline int metal_uart_getc(struct metal_uart *uart, unsigned char *c) { return uart->vtable->getc(uart, c); }
+__inline__ int metal_uart_getc(struct metal_uart *uart, int *c) {
+ return uart->vtable->getc(uart, c);
+}
/*!
* @brief Get the baud rate of the UART peripheral
* @param uart The UART device handle
* @return The current baud rate of the UART
*/
-inline int metal_uart_get_baud_rate(struct metal_uart *uart) { return uart->vtable->get_baud_rate(uart); }
+__inline__ int metal_uart_get_baud_rate(struct metal_uart *uart) {
+ return uart->vtable->get_baud_rate(uart);
+}
/*!
* @brief Set the baud rate of the UART peripheral
@@ -70,7 +107,10 @@ inline int metal_uart_get_baud_rate(struct metal_uart *uart) { return uart->vtab
* @param baud_rate The baud rate to configure
* @return the new baud rate of the UART
*/
-inline int metal_uart_set_baud_rate(struct metal_uart *uart, int baud_rate) { return uart->vtable->set_baud_rate(uart, baud_rate); }
+__inline__ int metal_uart_set_baud_rate(struct metal_uart *uart,
+ int baud_rate) {
+ return uart->vtable->set_baud_rate(uart, baud_rate);
+}
/*!
* @brief Get the interrupt controller of the UART peripheral
@@ -82,13 +122,94 @@ inline int metal_uart_set_baud_rate(struct metal_uart *uart, int baud_rate) { re
* @param uart The UART device handle
* @return The handle for the UART interrupt controller
*/
-inline struct metal_interrupt* metal_uart_interrupt_controller(struct metal_uart *uart) { return uart->vtable->controller_interrupt(uart); }
+__inline__ struct metal_interrupt *
+metal_uart_interrupt_controller(struct metal_uart *uart) {
+ return uart->vtable->controller_interrupt(uart);
+}
/*!
* @brief Get the interrupt ID of the UART controller
* @param uart The UART device handle
* @return The UART interrupt id
*/
-inline int metal_uart_get_interrupt_id(struct metal_uart *uart) { return uart->vtable->get_interrupt_id(uart); }
+__inline__ int metal_uart_get_interrupt_id(struct metal_uart *uart) {
+ return uart->vtable->get_interrupt_id(uart);
+}
+
+/*!
+ * @brief Enable the UART transmit interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_transmit_interrupt_enable(struct metal_uart *uart) {
+ return uart->vtable->tx_interrupt_enable(uart);
+}
+
+/*!
+ * @brief Disable the UART transmit interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_transmit_interrupt_disable(struct metal_uart *uart) {
+ return uart->vtable->tx_interrupt_disable(uart);
+}
+
+/*!
+ * @brief Enable the UART receive interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_receive_interrupt_enable(struct metal_uart *uart) {
+ return uart->vtable->rx_interrupt_enable(uart);
+}
+
+/*!
+ * @brief Disable the UART receive interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_receive_interrupt_disable(struct metal_uart *uart) {
+ return uart->vtable->rx_interrupt_disable(uart);
+}
+
+/*!
+ * @brief Set the transmit watermark level of the UART controller
+ * @param uart The UART device handle
+ * @param level The UART transmit watermark level
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_set_transmit_watermark(struct metal_uart *uart,
+ size_t level) {
+ return uart->vtable->set_tx_watermark(uart, level);
+}
+
+/*!
+ * @brief Get the transmit watermark level of the UART controller
+ * @param uart The UART device handle
+ * @return The UART transmit watermark level
+ */
+__inline__ size_t metal_uart_get_transmit_watermark(struct metal_uart *uart) {
+ return uart->vtable->get_tx_watermark(uart);
+}
+
+/*!
+ * @brief Set the receive watermark level of the UART controller
+ * @param uart The UART device handle
+ * @param level The UART transmit watermark level
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_set_receive_watermark(struct metal_uart *uart,
+ size_t level) {
+ return uart->vtable->set_rx_watermark(uart, level);
+}
+
+/*!
+ * @brief Get the receive watermark level of the UART controller
+ * @param uart The UART device handle
+ * @return The UART transmit watermark level
+ */
+__inline__ size_t metal_uart_get_receive_watermark(struct metal_uart *uart) {
+ return uart->vtable->get_rx_watermark(uart);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/watchdog.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/watchdog.h
new file mode 100644
index 000000000..2f84d3b49
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/install/include/metal/watchdog.h
@@ -0,0 +1,168 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__WATCHDOG_H
+#define METAL__WATCHDOG_H
+
+/*!
+ * @file watchdog.h
+ *
+ * @brief API for configuring watchdog timers
+ */
+
+#include <metal/interrupt.h>
+
+struct metal_watchdog;
+
+/*!
+ * @brief List of watchdog timer count behaviors
+ */
+enum metal_watchdog_run_option {
+ METAL_WATCHDOG_STOP = 0, /*!< Stop the watchdog */
+ METAL_WATCHDOG_RUN_ALWAYS, /*!< Run the watchdog continuously, even during
+ sleep */
+ METAL_WATCHDOG_RUN_AWAKE, /*!< Run the watchdog only while the CPU is awake
+ */
+};
+
+/*!
+ * @brief List of behaviors when a watchdog triggers
+ */
+enum metal_watchdog_result {
+ METAL_WATCHDOG_NO_RESULT = 0, /*!< When the watchdog triggers, do nothing */
+ METAL_WATCHDOG_INTERRUPT, /*!< When the watchdog triggers, fire an interrupt
+ */
+ METAL_WATCHDOG_FULL_RESET, /*!< When the watchdog triggers, cause a full
+ system reset */
+};
+
+struct metal_watchdog_vtable {
+ int (*feed)(const struct metal_watchdog *const wdog);
+ long int (*get_rate)(const struct metal_watchdog *const wdog);
+ long int (*set_rate)(const struct metal_watchdog *const wdog,
+ const long int rate);
+ long int (*get_timeout)(const struct metal_watchdog *const wdog);
+ long int (*set_timeout)(const struct metal_watchdog *const wdog,
+ const long int timeout);
+ int (*set_result)(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_result result);
+ int (*run)(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_run_option option);
+ struct metal_interrupt *(*get_interrupt)(
+ const struct metal_watchdog *const wdog);
+ int (*get_interrupt_id)(const struct metal_watchdog *const wdog);
+ int (*clear_interrupt)(const struct metal_watchdog *const wdog);
+};
+
+/*!
+ * @brief Handle for a Watchdog Timer
+ */
+struct metal_watchdog {
+ const struct metal_watchdog_vtable *vtable;
+};
+
+/*!
+ * @brief Feed the watchdog timer
+ */
+inline int metal_watchdog_feed(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->feed(wdog);
+}
+
+/*!
+ * @brief Get the rate of the watchdog timer in Hz
+ *
+ * @return the rate of the watchdog timer
+ */
+inline long int
+metal_watchdog_get_rate(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_rate(wdog);
+}
+
+/*!
+ * @brief Set the rate of the watchdog timer in Hz
+ *
+ * There is no guarantee that the new rate will match the requested rate.
+ *
+ * @return the new rate of the watchdog timer
+ */
+inline long int metal_watchdog_set_rate(const struct metal_watchdog *const wdog,
+ const long int rate) {
+ return wdog->vtable->set_rate(wdog, rate);
+}
+
+/*!
+ * @brief Get the timeout of the watchdog timer
+ *
+ * @return the watchdog timeout value
+ */
+inline long int
+metal_watchdog_get_timeout(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_timeout(wdog);
+}
+
+/*!
+ * @brief Set the timeout of the watchdog timer
+ *
+ * The set rate will be the minimimum of the requested and maximum supported
+ * rates.
+ *
+ * @return the new watchdog timeout value
+ */
+inline long int
+metal_watchdog_set_timeout(const struct metal_watchdog *const wdog,
+ const long int timeout) {
+ return wdog->vtable->set_timeout(wdog, timeout);
+}
+
+/*!
+ * @brief Sets the result behavior of a watchdog timer timeout
+ *
+ * @return 0 if the requested result behavior is supported
+ */
+inline int metal_watchdog_set_result(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_result result) {
+ return wdog->vtable->set_result(wdog, result);
+}
+
+/*!
+ * @brief Set the run behavior of the watchdog
+ *
+ * Used to enable/disable the watchdog timer
+ *
+ * @return 0 if the watchdog was successfully started/stopped
+ */
+inline int metal_watchdog_run(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_run_option option) {
+ return wdog->vtable->run(wdog, option);
+}
+
+/*!
+ * @brief Get the interrupt controller for the watchdog interrupt
+ */
+inline struct metal_interrupt *
+metal_watchdog_get_interrupt(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_interrupt(wdog);
+}
+
+/*!
+ * @Brief Get the interrupt id for the watchdog interrupt
+ */
+inline int
+metal_watchdog_get_interrupt_id(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_interrupt_id(wdog);
+}
+
+/*!
+ * @brief Clear the watchdog interrupt
+ */
+inline int
+metal_watchdog_clear_interrupt(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->clear_interrupt(wdog);
+}
+
+/*!
+ * @brief Get a watchdog handle
+ */
+struct metal_watchdog *metal_watchdog_get_device(const int index);
+
+#endif /* METAL__WATCHDOG_H */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-inline.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-inline.h
index 8c0cd048b..fd05ab065 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-inline.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-inline.h
@@ -5,128 +5,181 @@
#ifndef ASSEMBLY
-#ifndef SIFIVE_HIFIVE1_REVB____METAL_INLINE_H
-#define SIFIVE_HIFIVE1_REVB____METAL_INLINE_H
+#ifndef METAL_INLINE_H
+#define METAL_INLINE_H
#include <metal/machine.h>
/* --------------------- fixed_clock ------------ */
-extern inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock);
+extern __inline__ unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock);
/* --------------------- fixed_factor_clock ------------ */
/* --------------------- sifive_clint0 ------------ */
-extern inline unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller);
-extern inline unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller);
-extern inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx);
-extern inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller);
+extern __inline__ unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx);
/* --------------------- cpu ------------ */
-extern inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu);
-extern inline int __metal_driver_cpu_timebase(struct metal_cpu *cpu);
-extern inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu);
-extern inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_hartid(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_timebase(struct metal_cpu *cpu);
+extern __inline__ struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu);
+extern __inline__ int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu);
+extern __inline__ struct metal_buserror * __metal_driver_cpu_buserror(struct metal_cpu *cpu);
/* --------------------- sifive_plic0 ------------ */
-extern inline unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller);
-extern inline unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller);
-extern inline struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx);
-extern inline int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller);
+extern __inline__ unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller);
+extern __inline__ int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx);
+extern __inline__ int __metal_driver_sifive_plic0_context_ids(int hartid);
+
+
+/* --------------------- sifive_buserror0 ------------ */
/* --------------------- sifive_clic0 ------------ */
/* --------------------- sifive_local_external_interrupts0 ------------ */
-extern inline struct metal_interrupt * __metal_driver_sifive_local_external_interrupts0_interrupt_parent(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_local_external_interrupts0_num_interrupts(struct metal_interrupt *controller);
-extern inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lines(struct metal_interrupt *controller, int idx);
/* --------------------- sifive_global_external_interrupts0 ------------ */
/* --------------------- sifive_gpio0 ------------ */
-extern inline unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio);
-extern inline unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio);
-extern inline int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio);
-extern inline struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio);
-extern inline int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx);
+extern __inline__ unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio);
+extern __inline__ unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio);
+extern __inline__ int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio);
+extern __inline__ int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx);
/* --------------------- sifive_gpio_button ------------ */
/* --------------------- sifive_gpio_led ------------ */
-extern inline struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led);
-extern inline int __metal_driver_sifive_gpio_led_pin(struct metal_led *led);
-extern inline char * __metal_driver_sifive_gpio_led_label(struct metal_led *led);
+extern __inline__ struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led);
+extern __inline__ int __metal_driver_sifive_gpio_led_pin(struct metal_led *led);
+extern __inline__ char * __metal_driver_sifive_gpio_led_label(struct metal_led *led);
/* --------------------- sifive_gpio_switch ------------ */
+/* --------------------- sifive_i2c0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_control_base(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_control_size(struct metal_i2c *i2c);
+extern __inline__ int __metal_driver_sifive_i2c0_num_interrupts(struct metal_i2c *i2c);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_i2c0_interrupt_parent(struct metal_i2c *i2c);
+extern __inline__ int __metal_driver_sifive_i2c0_interrupt_line(struct metal_i2c *i2c);
+extern __inline__ struct metal_clock * __metal_driver_sifive_i2c0_clock(struct metal_i2c *i2c);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_i2c0_pinmux(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_output_selector(struct metal_i2c *i2c);
+extern __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_source_selector(struct metal_i2c *i2c);
+
+
+/* --------------------- sifive_pwm0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_control_base(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_control_size(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_num_interrupts(struct metal_pwm *pwm);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_pwm0_interrupt_parent(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_interrupt_lines(struct metal_pwm *pwm, int idx);
+extern __inline__ struct metal_clock * __metal_driver_sifive_pwm0_clock(struct metal_pwm *pwm);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_pwm0_pinmux(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_output_selector(struct metal_pwm *pwm);
+extern __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_source_selector(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_compare_width(struct metal_pwm *pwm);
+extern __inline__ int __metal_driver_sifive_pwm0_comparator_count(struct metal_pwm *pwm);
+
+
+/* --------------------- sifive_rtc0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_rtc0_control_base(const struct metal_rtc *const rtc);
+extern __inline__ unsigned long __metal_driver_sifive_rtc0_control_size(const struct metal_rtc *const rtc);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_rtc0_interrupt_parent(const struct metal_rtc *const rtc);
+extern __inline__ int __metal_driver_sifive_rtc0_interrupt_line(const struct metal_rtc *const rtc);
+extern __inline__ struct metal_clock * __metal_driver_sifive_rtc0_clock(const struct metal_rtc *const rtc);
+
+
/* --------------------- sifive_spi0 ------------ */
-extern inline unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi);
-extern inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi);
-extern inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi);
+extern __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi);
/* --------------------- sifive_test0 ------------ */
+/* --------------------- sifive_trace ------------ */
+
/* --------------------- sifive_uart0 ------------ */
-extern inline unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart);
-extern inline int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart);
-extern inline struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart);
-extern inline int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart);
-extern inline struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart);
-extern inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart);
-extern inline unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart);
+extern __inline__ int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart);
+extern __inline__ int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart);
+extern __inline__ struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart);
+extern __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart);
+extern __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart);
+
+
+/* --------------------- sifive_simuart0 ------------ */
+
+
+/* --------------------- sifive_wdog0 ------------ */
+extern __inline__ unsigned long __metal_driver_sifive_wdog0_control_base(const struct metal_watchdog *const watchdog);
+extern __inline__ unsigned long __metal_driver_sifive_wdog0_control_size(const struct metal_watchdog *const watchdog);
+extern __inline__ struct metal_interrupt * __metal_driver_sifive_wdog0_interrupt_parent(const struct metal_watchdog *const watchdog);
+extern __inline__ int __metal_driver_sifive_wdog0_interrupt_line(const struct metal_watchdog *const watchdog);
+extern __inline__ struct metal_clock * __metal_driver_sifive_wdog0_clock(const struct metal_watchdog *const watchdog);
/* --------------------- sifive_fe310_g000_hfrosc ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock);
-extern inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock);
+extern __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock);
/* --------------------- sifive_fe310_g000_hfxosc ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock);
-/* --------------------- sifive_fe310_g000_pll ------------ */
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock);
-extern inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock);
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( );
-extern inline long __metal_driver_sifive_fe310_g000_pll_config_offset( );
-extern inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock);
-extern inline long __metal_driver_sifive_fe310_g000_pll_init_rate( );
+/* --------------------- sifive_fe310_g000_lfrosc ------------ */
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(const struct metal_clock *clock);
+extern __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_config_reg(const struct metal_clock *clock);
+extern __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(const struct metal_clock *clock);
-/* --------------------- fe310_g000_prci ------------ */
-extern inline long __metal_driver_sifive_fe310_g000_prci_base( );
-extern inline long __metal_driver_sifive_fe310_g000_prci_size( );
-extern inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( );
+/* --------------------- sifive_fe310_g000_pll ------------ */
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock);
+extern __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock);
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( );
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_config_offset( );
+extern __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock);
+extern __inline__ long __metal_driver_sifive_fe310_g000_pll_init_rate( );
-/* --------------------- sifive_fu540_c000_l2 ------------ */
+/* --------------------- fe310_g000_prci ------------ */
+extern __inline__ long __metal_driver_sifive_fe310_g000_prci_base( );
+extern __inline__ long __metal_driver_sifive_fe310_g000_prci_size( );
+extern __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( );
/* From clock@0 */
@@ -144,6 +197,11 @@ struct __metal_driver_fixed_clock __metal_dt_clock_5 = {
.clock.vtable = &__metal_driver_vtable_fixed_clock.clock,
};
+/* From clock@6 */
+struct __metal_driver_fixed_clock __metal_dt_clock_6 = {
+ .clock.vtable = &__metal_driver_vtable_fixed_clock.clock,
+};
+
struct metal_memory __metal_dt_mem_dtim_80000000 = {
._base_address = 2147483648UL,
._size = 16384UL,
@@ -155,6 +213,17 @@ struct metal_memory __metal_dt_mem_dtim_80000000 = {
.A = 1},
};
+struct metal_memory __metal_dt_mem_itim_8000000 = {
+ ._base_address = 134217728UL,
+ ._size = 8192UL,
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
struct metal_memory __metal_dt_mem_spi_10014000 = {
._base_address = 536870912UL,
._size = 500000UL,
@@ -166,6 +235,24 @@ struct metal_memory __metal_dt_mem_spi_10014000 = {
.A = 1},
};
+struct metal_memory __metal_dt_mem_spi_10024000 = {
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
+struct metal_memory __metal_dt_mem_spi_10034000 = {
+ ._attrs = {
+ .R = 1,
+ .W = 1,
+ .X = 1,
+ .C = 1,
+ .A = 1},
+};
+
/* From clint@2000000 */
struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000 = {
.controller.vtable = &__metal_driver_vtable_riscv_clint0.clint_vtable,
@@ -175,6 +262,7 @@ struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000 = {
/* From cpu@0 */
struct __metal_driver_cpu __metal_dt_cpu_0 = {
.cpu.vtable = &__metal_driver_vtable_cpu.cpu_vtable,
+ .hpm_count = 0,
};
/* From interrupt_controller */
@@ -189,42 +277,83 @@ struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000 = {
.init_done = 0,
};
-/* From local_external_interrupts_0 */
-struct __metal_driver_sifive_local_external_interrupts0 __metal_dt_local_external_interrupts_0 = {
- .irc.vtable = &__metal_driver_vtable_sifive_local_external_interrupts0.local0_vtable,
- .init_done = 0,
-};
+struct metal_pmp __metal_dt_pmp;
/* From gpio@10012000 */
struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000 = {
.gpio.vtable = &__metal_driver_vtable_sifive_gpio0.gpio,
};
-/* From led@0red */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0red = {
+/* From led@0 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_0 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
-/* From led@0green */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0green = {
+/* From led@1 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_1 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
-/* From led@0blue */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0blue = {
+/* From led@2 */
+struct __metal_driver_sifive_gpio_led __metal_dt_led_2 = {
.led.vtable = &__metal_driver_vtable_sifive_led.led_vtable,
};
+/* From i2c@10016000 */
+struct __metal_driver_sifive_i2c0 __metal_dt_i2c_10016000 = {
+ .i2c.vtable = &__metal_driver_vtable_sifive_i2c0.i2c,
+};
+
+/* From pwm@10015000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10015000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From pwm@10025000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10025000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From pwm@10035000 */
+struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10035000 = {
+ .pwm.vtable = &__metal_driver_vtable_sifive_pwm0.pwm,
+};
+
+/* From aon@10000000 */
+struct __metal_driver_sifive_rtc0 __metal_dt_rtc_10000000 = {
+ .rtc.vtable = &__metal_driver_vtable_sifive_rtc0.rtc,
+};
+
/* From spi@10014000 */
struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000 = {
.spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
};
+/* From spi@10024000 */
+struct __metal_driver_sifive_spi0 __metal_dt_spi_10024000 = {
+ .spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
+};
+
+/* From spi@10034000 */
+struct __metal_driver_sifive_spi0 __metal_dt_spi_10034000 = {
+ .spi.vtable = &__metal_driver_vtable_sifive_spi0.spi,
+};
+
/* From serial@10013000 */
struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000 = {
.uart.vtable = &__metal_driver_vtable_sifive_uart0.uart,
};
+/* From serial@10023000 */
+struct __metal_driver_sifive_uart0 __metal_dt_serial_10023000 = {
+ .uart.vtable = &__metal_driver_vtable_sifive_uart0.uart,
+};
+
+/* From aon@10000000 */
+struct __metal_driver_sifive_wdog0 __metal_dt_aon_10000000 = {
+ .watchdog.vtable = &__metal_driver_vtable_sifive_wdog0.watchdog,
+};
+
/* From clock@3 */
struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_hfrosc.clock,
@@ -235,6 +364,11 @@ struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_hfxosc.clock,
};
+/* From clock@7 */
+struct __metal_driver_sifive_fe310_g000_lfrosc __metal_dt_clock_7 = {
+ .clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_lfrosc.clock,
+};
+
/* From clock@4 */
struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4 = {
.clock.vtable = &__metal_driver_vtable_sifive_fe310_g000_pll.clock,
@@ -242,8 +376,9 @@ struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4 = {
/* From prci@10008000 */
struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000 = {
+ .vtable = &__metal_driver_vtable_sifive_fe310_g000_prci,
};
-#endif /* SIFIVE_HIFIVE1_REVB____METAL_INLINE_H*/
+#endif /* METAL_INLINE_H*/
#endif /* ! ASSEMBLY */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-platform.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-platform.h
index 4ecd3e336..d517b5859 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-platform.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal-platform.h
@@ -3,8 +3,8 @@
/* ----------------------------------- */
/* ----------------------------------- */
-#ifndef SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H
-#define SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H
+#ifndef METAL_PLATFORM_H
+#define METAL_PLATFORM_H
/* From clock@0 */
#define METAL_FIXED_CLOCK_0_CLOCK_FREQUENCY 16000000UL
@@ -13,7 +13,10 @@
#define METAL_FIXED_CLOCK_2_CLOCK_FREQUENCY 72000000UL
/* From clock@5 */
-#define METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY 32000000UL
+#define METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY 32768UL
+
+/* From clock@6 */
+#define METAL_FIXED_CLOCK_6_CLOCK_FREQUENCY 32768UL
#define METAL_FIXED_CLOCK
@@ -35,15 +38,18 @@
#define METAL_RISCV_PLIC0_0_SIZE 67108864UL
#define METAL_RISCV_PLIC0_C000000_RISCV_MAX_PRIORITY 7UL
#define METAL_RISCV_PLIC0_0_RISCV_MAX_PRIORITY 7UL
-#define METAL_RISCV_PLIC0_C000000_RISCV_NDEV 27UL
-#define METAL_RISCV_PLIC0_0_RISCV_NDEV 27UL
+#define METAL_RISCV_PLIC0_C000000_RISCV_NDEV 53UL
+#define METAL_RISCV_PLIC0_0_RISCV_NDEV 53UL
#define METAL_RISCV_PLIC0
#define METAL_RISCV_PLIC0_PRIORITY_BASE 0UL
#define METAL_RISCV_PLIC0_PENDING_BASE 4096UL
#define METAL_RISCV_PLIC0_ENABLE_BASE 8192UL
-#define METAL_RISCV_PLIC0_THRESHOLD 2097152UL
-#define METAL_RISCV_PLIC0_CLAIM 2097156UL
+#define METAL_RISCV_PLIC0_ENABLE_PER_HART 128UL
+#define METAL_RISCV_PLIC0_CONTEXT_BASE 2097152UL
+#define METAL_RISCV_PLIC0_CONTEXT_PER_HART 4096UL
+#define METAL_RISCV_PLIC0_CONTEXT_THRESHOLD 0UL
+#define METAL_RISCV_PLIC0_CONTEXT_CLAIM 4UL
/* From aon@10000000 */
#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
@@ -111,6 +117,10 @@
#define METAL_SIFIVE_FE310_G000_HFXOSC
+/* From clock@7 */
+
+#define METAL_SIFIVE_FE310_G000_LFROSC
+
/* From prci@10008000 */
#define METAL_SIFIVE_FE310_G000_PRCI_10008000_BASE_ADDRESS 268468224UL
#define METAL_SIFIVE_FE310_G000_PRCI_0_BASE_ADDRESS 268468224UL
@@ -153,11 +163,11 @@
#define METAL_SIFIVE_GPIO0_IOF_SEL 60UL
#define METAL_SIFIVE_GPIO0_OUT_XOR 64UL
-/* From led@0red */
+/* From led@0 */
-/* From led@0green */
+/* From led@1 */
-/* From led@0blue */
+/* From led@2 */
#define METAL_SIFIVE_GPIO_LEDS
@@ -176,16 +186,24 @@
#define METAL_SIFIVE_I2C0_COMMAND 16UL
#define METAL_SIFIVE_I2C0_STATUS 16UL
-/* From local_external_interrupts_0 */
-
-#define METAL_SIFIVE_LOCAL_EXTERNAL_INTERRUPTS0
-
/* From pwm@10015000 */
#define METAL_SIFIVE_PWM0_10015000_BASE_ADDRESS 268521472UL
#define METAL_SIFIVE_PWM0_0_BASE_ADDRESS 268521472UL
#define METAL_SIFIVE_PWM0_10015000_SIZE 4096UL
#define METAL_SIFIVE_PWM0_0_SIZE 4096UL
+/* From pwm@10025000 */
+#define METAL_SIFIVE_PWM0_10025000_BASE_ADDRESS 268587008UL
+#define METAL_SIFIVE_PWM0_1_BASE_ADDRESS 268587008UL
+#define METAL_SIFIVE_PWM0_10025000_SIZE 4096UL
+#define METAL_SIFIVE_PWM0_1_SIZE 4096UL
+
+/* From pwm@10035000 */
+#define METAL_SIFIVE_PWM0_10035000_BASE_ADDRESS 268652544UL
+#define METAL_SIFIVE_PWM0_2_BASE_ADDRESS 268652544UL
+#define METAL_SIFIVE_PWM0_10035000_SIZE 4096UL
+#define METAL_SIFIVE_PWM0_2_SIZE 4096UL
+
#define METAL_SIFIVE_PWM0
#define METAL_SIFIVE_PWM0_PWMCFG 0UL
#define METAL_SIFIVE_PWM0_PWMCOUNT 8UL
@@ -195,12 +213,37 @@
#define METAL_SIFIVE_PWM0_PWMCMP2 40UL
#define METAL_SIFIVE_PWM0_PWMCMP3 44UL
+/* From aon@10000000 */
+#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_0_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_10000000_SIZE 32768UL
+#define METAL_SIFIVE_AON0_0_SIZE 32768UL
+
+#define METAL_SIFIVE_RTC0
+#define METAL_SIFIVE_RTC0_RTCCFG 64UL
+#define METAL_SIFIVE_RTC0_RTCCOUNTLO 72UL
+#define METAL_SIFIVE_RTC0_RTCCOUNTHI 76UL
+#define METAL_SIFIVE_RTC0_RTCS 80UL
+#define METAL_SIFIVE_RTC0_RTCCMP0 96UL
+
/* From spi@10014000 */
#define METAL_SIFIVE_SPI0_10014000_BASE_ADDRESS 268517376UL
#define METAL_SIFIVE_SPI0_0_BASE_ADDRESS 268517376UL
#define METAL_SIFIVE_SPI0_10014000_SIZE 4096UL
#define METAL_SIFIVE_SPI0_0_SIZE 4096UL
+/* From spi@10024000 */
+#define METAL_SIFIVE_SPI0_10024000_BASE_ADDRESS 268582912UL
+#define METAL_SIFIVE_SPI0_1_BASE_ADDRESS 268582912UL
+#define METAL_SIFIVE_SPI0_10024000_SIZE 4096UL
+#define METAL_SIFIVE_SPI0_1_SIZE 4096UL
+
+/* From spi@10034000 */
+#define METAL_SIFIVE_SPI0_10034000_BASE_ADDRESS 268648448UL
+#define METAL_SIFIVE_SPI0_2_BASE_ADDRESS 268648448UL
+#define METAL_SIFIVE_SPI0_10034000_SIZE 4096UL
+#define METAL_SIFIVE_SPI0_2_SIZE 4096UL
+
#define METAL_SIFIVE_SPI0
#define METAL_SIFIVE_SPI0_SCKDIV 0UL
#define METAL_SIFIVE_SPI0_SCKMODE 4UL
@@ -225,6 +268,12 @@
#define METAL_SIFIVE_UART0_10013000_SIZE 4096UL
#define METAL_SIFIVE_UART0_0_SIZE 4096UL
+/* From serial@10023000 */
+#define METAL_SIFIVE_UART0_10023000_BASE_ADDRESS 268578816UL
+#define METAL_SIFIVE_UART0_1_BASE_ADDRESS 268578816UL
+#define METAL_SIFIVE_UART0_10023000_SIZE 4096UL
+#define METAL_SIFIVE_UART0_1_SIZE 4096UL
+
#define METAL_SIFIVE_UART0
#define METAL_SIFIVE_UART0_TXDATA 0UL
#define METAL_SIFIVE_UART0_RXDATA 4UL
@@ -234,4 +283,20 @@
#define METAL_SIFIVE_UART0_IP 20UL
#define METAL_SIFIVE_UART0_DIV 24UL
-#endif /* SIFIVE_HIFIVE1_REVB____METAL_PLATFORM_H*/
+/* From aon@10000000 */
+#define METAL_SIFIVE_AON0_10000000_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_0_BASE_ADDRESS 268435456UL
+#define METAL_SIFIVE_AON0_10000000_SIZE 32768UL
+#define METAL_SIFIVE_AON0_0_SIZE 32768UL
+
+#define METAL_SIFIVE_WDOG0
+#define METAL_SIFIVE_WDOG0_MAGIC_KEY 5370206UL
+#define METAL_SIFIVE_WDOG0_MAGIC_FOOD 218755085UL
+#define METAL_SIFIVE_WDOG0_WDOGCFG 0UL
+#define METAL_SIFIVE_WDOG0_WDOGCOUNT 8UL
+#define METAL_SIFIVE_WDOG0_WDOGS 16UL
+#define METAL_SIFIVE_WDOG0_WDOGFEED 24UL
+#define METAL_SIFIVE_WDOG0_WDOGKEY 28UL
+#define METAL_SIFIVE_WDOG0_WDOGCMP 32UL
+
+#endif /* METAL_PLATFORM_H*/
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.default.lds b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.default.lds
index 7070af7e8..be7f84c71 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.default.lds
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.default.lds
@@ -1,236 +1,302 @@
-/* Copyright 2019 SiFive, Inc */
+/* Copyright (c) 2020 SiFive Inc. */
/* SPDX-License-Identifier: Apache-2.0 */
-/* ----------------------------------- */
-/* ----------------------------------- */
-
OUTPUT_ARCH("riscv")
+/* Default Linker Script
+ *
+ * This is the default linker script for all Freedom Metal applications.
+ */
+
ENTRY(_enter)
MEMORY
{
- ram (wxa!ri) : ORIGIN = 0x80000000, LENGTH = 0x4000
- flash (rxai!w) : ORIGIN = 0x20010000, LENGTH = 0x6a120
+ itim (airwx) : ORIGIN = 0x8000000, LENGTH = 0x2000
+ ram (arw!xi) : ORIGIN = 0x80000000, LENGTH = 0x4000
+ rom (irx!wa) : ORIGIN = 0x20010000, LENGTH = 0x6a120
}
PHDRS
{
- flash PT_LOAD;
- ram_init PT_LOAD;
- itim_init PT_LOAD;
- ram PT_NULL;
- itim PT_NULL;
+ rom PT_LOAD;
+ ram_init PT_LOAD;
+ tls PT_TLS;
+ ram PT_LOAD;
+ itim_init PT_LOAD;
+ text PT_LOAD;
+ lim_init PT_LOAD;
}
SECTIONS
{
- __stack_size = DEFINED(__stack_size) ? __stack_size : 0x400;
- PROVIDE(__stack_size = __stack_size);
- __heap_size = DEFINED(__heap_size) ? __heap_size : 0x4;
- PROVIDE(__metal_boot_hart = 0);
- PROVIDE(__metal_chicken_bit = 0);
-
-
- .init :
- {
- KEEP (*(.text.metal.init.enter))
- KEEP (*(SORT_NONE(.init)))
- KEEP (*(.text.libgloss.start))
- } >flash AT>flash :flash
-
-
- .text :
- {
- *(.text.unlikely .text.unlikely.*)
- *(.text.startup .text.startup.*)
- *(.text .text.*)
- *(.itim .itim.*)
- *(.gnu.linkonce.t.*)
- } >flash AT>flash :flash
-
-
- .fini :
- {
- KEEP (*(SORT_NONE(.fini)))
- } >flash AT>flash :flash
-
-
- PROVIDE (__etext = .);
- PROVIDE (_etext = .);
- PROVIDE (etext = .);
-
-
- .rodata :
- {
- *(.rdata)
- *(.rodata .rodata.*)
- *(.gnu.linkonce.r.*)
- . = ALIGN(8);
- *(.srodata.cst16)
- *(.srodata.cst8)
- *(.srodata.cst4)
- *(.srodata.cst2)
- *(.srodata .srodata.*)
- } >flash AT>flash :flash
-
-
- . = ALIGN(4);
-
-
- .preinit_array :
- {
- PROVIDE_HIDDEN (__preinit_array_start = .);
- KEEP (*(.preinit_array))
- PROVIDE_HIDDEN (__preinit_array_end = .);
- } >flash AT>flash :flash
-
-
- .init_array :
- {
- PROVIDE_HIDDEN (__init_array_start = .);
- KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
- KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
- PROVIDE_HIDDEN (__init_array_end = .);
- } >flash AT>flash :flash
-
-
- .fini_array :
- {
- PROVIDE_HIDDEN (__fini_array_start = .);
- KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
- KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
- PROVIDE_HIDDEN (__fini_array_end = .);
- } >flash AT>flash :flash
-
-
- .ctors :
- {
- /* gcc uses crtbegin.o to find the start of
- the constructors, so we make sure it is
- first. Because this is a wildcard, it
- doesn't matter if the user does not
- actually link against crtbegin.o; the
- linker won't look for a file to match a
- wildcard. The wildcard also means that it
- doesn't matter which directory crtbegin.o
- is in. */
- KEEP (*crtbegin.o(.ctors))
- KEEP (*crtbegin?.o(.ctors))
- /* We don't want to include the .ctor section from
- the crtend.o file until after the sorted ctors.
- The .ctor section from the crtend file contains the
- end of ctors marker and it must be last */
- KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
- KEEP (*(SORT(.ctors.*)))
- KEEP (*(.ctors))
- } >flash AT>flash :flash
-
-
- .dtors :
- {
- KEEP (*crtbegin.o(.dtors))
- KEEP (*crtbegin?.o(.dtors))
- KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
- KEEP (*(SORT(.dtors.*)))
- KEEP (*(.dtors))
- } >flash AT>flash :flash
-
-
- .litimalign :
- {
- . = ALIGN(4);
- PROVIDE( metal_segment_itim_source_start = . );
- } >flash AT>flash :flash
-
-
- .ditimalign :
- {
- . = ALIGN(4);
- PROVIDE( metal_segment_itim_target_start = . );
- } >ram AT>flash :ram_init
-
-
- .itim :
- {
- *(.itim .itim.*)
- } >flash AT>flash :flash
-
-
- . = ALIGN(8);
- PROVIDE( metal_segment_itim_target_end = . );
-
-
- .lalign :
- {
- . = ALIGN(4);
- PROVIDE( _data_lma = . );
- PROVIDE( metal_segment_data_source_start = . );
- } >flash AT>flash :flash
-
-
- .dalign :
- {
- . = ALIGN(4);
- PROVIDE( metal_segment_data_target_start = . );
- } >ram AT>flash :ram_init
-
-
- .data :
- {
- *(.data .data.*)
- *(.gnu.linkonce.d.*)
- . = ALIGN(8);
- PROVIDE( __global_pointer$ = . + 0x800 );
- *(.sdata .sdata.* .sdata2.*)
- *(.gnu.linkonce.s.*)
- } >ram AT>flash :ram_init
-
-
- . = ALIGN(4);
- PROVIDE( _edata = . );
- PROVIDE( edata = . );
- PROVIDE( metal_segment_data_target_end = . );
- PROVIDE( _fbss = . );
- PROVIDE( __bss_start = . );
- PROVIDE( metal_segment_bss_target_start = . );
-
-
- .bss :
- {
- *(.sbss*)
- *(.gnu.linkonce.sb.*)
- *(.bss .bss.*)
- *(.gnu.linkonce.b.*)
- *(COMMON)
- . = ALIGN(4);
- } >ram AT>ram :ram
-
-
- . = ALIGN(8);
- PROVIDE( _end = . );
- PROVIDE( end = . );
- PROVIDE( metal_segment_bss_target_end = . );
-
- .stack :
- {
- . = ALIGN(16);
- metal_segment_stack_begin = .;
- . += __stack_size;
- . = ALIGN(16);
- _sp = .;
- PROVIDE(metal_segment_stack_end = .);
- __freertos_irq_stack_top = .;
- } >ram AT>ram :ram
-
-
- .heap :
- {
- PROVIDE( metal_segment_heap_target_start = . );
- . = __heap_size;
- PROVIDE( metal_segment_heap_target_end = . );
- PROVIDE( _heap_end = . );
- } >ram AT>ram :ram
-
-
-}
-
+ /* Each hart is allocated its own stack of size __stack_size. This value
+ * can be overriden at build-time by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__stack_size=0xf00
+ *
+ * where 0xf00 can be replaced with a multiple of 16 of your choice.
+ *
+ * __stack_size is PROVIDE-ed as a symbol so that initialization code
+ * initializes the stack pointers for each hart at the right offset from
+ * the _sp symbol.
+ */
+ __stack_size = DEFINED(__stack_size) ? __stack_size : 0x400;
+ PROVIDE(__stack_size = __stack_size);
+
+ /* The size of the heap can be overriden at build-time by adding the
+ * following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_size=0xf00
+ *
+ * where 0xf00 can be replaced with the value of your choice.
+ *
+ * Altertatively, the heap can be grown to fill the entire remaining region
+ * of RAM by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_max=1
+ *
+ * Note that depending on the memory layout, the bitness (32/64bit) of the
+ * target, and the code model in use, this might cause a relocation error.
+ */
+ __heap_size = DEFINED(__heap_size) ? __heap_size : 0x800;
+
+ /* The boot hart sets which hart runs the pre-main initialization routines,
+ * including copying .data into RAM, zeroing the BSS region, running
+ * constructors, etc. After initialization, the boot hart is also the only
+ * hart which runs application code unless the application overrides the
+ * secondary_main() function to start execution on secondary harts.
+ */
+ PROVIDE(__metal_boot_hart = 0);
+
+ /* The chicken bit is used by pre-main initialization to enable/disable
+ * certain core features */
+ PROVIDE(__metal_chicken_bit = 1);
+
+ /* The memory_ecc_scrub bit is used by _entry code to enable/disable
+ * memories scrubbing to zero */
+ PROVIDE(__metal_eccscrub_bit = 0);
+
+ /* The RAM memories map for ECC scrubbing */
+ PROVIDE( metal_dtim_0_memory_start = 0x80000000 );
+ PROVIDE( metal_dtim_0_memory_end = 0x80000000 + 0x4000 );
+ PROVIDE( metal_itim_0_memory_start = 0x8000000 );
+ PROVIDE( metal_itim_0_memory_end = 0x8000000 + 0x2000 );
+
+ /* ROM SECTION
+ *
+ * The following sections contain data which lives in read-only memory, if
+ * such memory is present in the design, for the entire duration of program
+ * execution.
+ */
+
+ .init : {
+ /* The _enter symbol is placed in the .text.metal.init.enter section
+ * and must be placed at the beginning of the program */
+ KEEP (*(.text.metal.init.enter))
+ KEEP (*(.text.metal.init.*))
+ KEEP (*(SORT_NONE(.init)))
+ KEEP (*(.text.libgloss.start))
+ } >rom :rom
+
+ .fini : {
+ KEEP (*(SORT_NONE(.fini)))
+ } >rom :rom
+
+ .preinit_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__preinit_array_start = .);
+ KEEP (*(.preinit_array))
+ PROVIDE_HIDDEN (__preinit_array_end = .);
+ } >rom :rom
+
+ .init_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__init_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
+ KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
+ PROVIDE_HIDDEN (__init_array_end = .);
+ PROVIDE_HIDDEN ( metal_constructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.init_array.*)));
+ KEEP (*(.metal.init_array));
+ PROVIDE_HIDDEN ( metal_constructors_end = .);
+ } >rom :rom
+
+ .fini_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__fini_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
+ KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
+ PROVIDE_HIDDEN (__fini_array_end = .);
+ PROVIDE_HIDDEN ( metal_destructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.fini_array.*)));
+ KEEP (*(.metal.fini_array));
+ PROVIDE_HIDDEN ( metal_destructors_end = .);
+ } >rom :rom
+
+
+
+ .ctors : {
+ KEEP (*crtbegin.o(.ctors))
+ KEEP (*crtbegin?.o(.ctors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
+ KEEP (*(SORT(.ctors.*)))
+ KEEP (*(.ctors))
+ KEEP (*(.metal.ctors .metal.ctors.*))
+ } >rom :rom
+
+ .dtors : {
+ KEEP (*crtbegin.o(.dtors))
+ KEEP (*crtbegin?.o(.dtors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
+ KEEP (*(SORT(.dtors.*)))
+ KEEP (*(.dtors))
+ KEEP (*(.metal.dtors .metal.dtors.*))
+ } >rom : rom
+
+ .rodata : {
+ *(.rdata)
+ *(.rodata .rodata.*)
+ *(.gnu.linkonce.r.*)
+ . = ALIGN(8);
+ *(.srodata.cst16)
+ *(.srodata.cst8)
+ *(.srodata.cst4)
+ *(.srodata.cst2)
+ *(.srodata .srodata.*)
+ } >rom :rom
+
+ /* ITIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into an instruction tightly-integrated memory (ITIM), if one
+ * is present in the design, during pre-main program initialization.
+ *
+ * Generally, the data copied into the ITIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .itim : ALIGN(8) {
+ *(.itim .itim.*)
+ } >itim AT>rom :itim_init
+
+ PROVIDE( metal_segment_itim_source_start = LOADADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_start = ADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_end = ADDR(.itim) + SIZEOF(.itim) );
+
+ /* LIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a loosely integrated memory (LIM), which is shared with L2
+ * cache, during pre-main program initialization.
+ *
+ * Generally, the data copied into the LIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .lim : ALIGN(8) {
+ *(.lim .lim.*)
+ } >ram AT>rom :lim_init
+
+ PROVIDE( metal_segment_lim_source_start = LOADADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_start = ADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_end = ADDR(.lim) + SIZEOF(.lim) );
+
+ /* TEXT SECTION
+ *
+ * The following section contains the code of the program, excluding
+ * everything that's been allocated into the ITIM/LIM already
+ */
+
+ .text : {
+ *(.text.unlikely .text.unlikely.*)
+ *(.text.startup .text.startup.*)
+ *(.text .text.*)
+ *(.gnu.linkonce.t.*)
+ } >rom :text
+
+ /* RAM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a read-write-capable memory such as data tightly-integrated
+ * memory (DTIM) or another main memory, as well as the BSS, stack, and
+ * heap.
+ *
+ * You might notice that .data, .tdata, .tbss, .tbss_space, and .bss all
+ * have an apparently unnecessary ALIGN at their top. This is because
+ * the implementation of _start in Freedom Metal libgloss depends on the
+ * ADDR and LOADADDR being 8-byte aligned.
+ */
+
+ .data : ALIGN(8) {
+ *(.data .data.*)
+ *(.gnu.linkonce.d.*)
+ . = ALIGN(8);
+ PROVIDE( __global_pointer$ = . + 0x800 );
+ *(.sdata .sdata.* .sdata2.*)
+ *(.gnu.linkonce.s.*)
+ } >ram AT>rom :ram_init
+
+ .tdata : ALIGN(8) {
+ PROVIDE( __tls_base = . );
+ *(.tdata .tdata.* .gnu.linkonce.td.*)
+ } >ram AT>rom :tls :ram_init
+
+ PROVIDE( __tdata_source = LOADADDR(.tdata) );
+ PROVIDE( __tdata_size = SIZEOF(.tdata) );
+
+ PROVIDE( metal_segment_data_source_start = LOADADDR(.data) );
+ PROVIDE( metal_segment_data_target_start = ADDR(.data) );
+ PROVIDE( metal_segment_data_target_end = ADDR(.tdata) + SIZEOF(.tdata) );
+
+ .tbss : ALIGN(8) {
+ *(.tbss .tbss.* .gnu.linkonce.tb.*)
+ *(.tcommon .tcommon.*)
+ PROVIDE( __tls_end = . );
+ } >ram AT>ram :tls :ram
+ PROVIDE( __tbss_size = SIZEOF(.tbss) );
+ PROVIDE( __tls_size = __tls_end - __tls_base );
+
+ .tbss_space : ALIGN(8) {
+ . = . + __tbss_size;
+ } >ram :ram
+
+ .bss (NOLOAD): ALIGN(8) {
+ *(.sbss*)
+ *(.gnu.linkonce.sb.*)
+ *(.bss .bss.*)
+ *(.gnu.linkonce.b.*)
+ *(COMMON)
+ } >ram :ram
+
+ PROVIDE( metal_segment_bss_source_start = LOADADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_start = ADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_end = ADDR(.bss) + SIZEOF(.bss) );
+
+
+
+ .stack (NOLOAD) : ALIGN(16) {
+ PROVIDE(metal_segment_stack_begin = .);
+ . += __stack_size; /* Hart 0 */
+ PROVIDE( _sp = . );
+ __freertos_irq_stack_top = .;
+ PROVIDE(metal_segment_stack_end = .);
+ } >ram :ram
+
+ .heap (NOLOAD) : ALIGN(8) {
+ PROVIDE( __end = . );
+ PROVIDE( __heap_start = . );
+ PROVIDE( metal_segment_heap_target_start = . );
+ /* If __heap_max is defined, grow the heap to use the rest of RAM,
+ * otherwise set the heap size to __heap_size */
+ . = DEFINED(__heap_max) ? MIN( LENGTH(ram) - ( . - ORIGIN(ram)) , 0x10000000) : __heap_size;
+ PROVIDE( metal_segment_heap_target_end = . );
+ PROVIDE( _heap_end = . );
+ PROVIDE( __heap_end = . );
+ } >ram :ram
+
+ /* C++ exception handling information is
+ * not useful with our current runtime environment,
+ * and it consumes flash space. Discard it until
+ * we have something that can use it
+ */
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+} \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.freertos.lds b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.freertos.lds
new file mode 100644
index 000000000..4798504ed
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.freertos.lds
@@ -0,0 +1,327 @@
+/* Copyright (c) 2020 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+OUTPUT_ARCH("riscv")
+
+/* Privileged mode Linker Script
+ *
+ * This linker script is based on metal.default.lds. It introduce specific
+ * section to isolate (acessible only from machine mode) and others that can be
+ * used in every execution mode. This linker script it tailored for FreeRTOS
+ * applications.
+ */
+
+ENTRY(_enter)
+
+MEMORY
+{
+ itim (airwx) : ORIGIN = 0x8000000, LENGTH = 0x2000
+ ram (arw!xi) : ORIGIN = 0x80000000, LENGTH = 0x4000
+ rom (irx!wa) : ORIGIN = 0x20010000, LENGTH = 0x6a120
+}
+
+PHDRS
+{
+ rom PT_LOAD;
+ ram_init PT_LOAD;
+ tls PT_TLS;
+ ram PT_LOAD;
+ itim_init PT_LOAD;
+ text PT_LOAD;
+ lim_init PT_LOAD;
+}
+
+SECTIONS
+{
+ /* Each hart is allocated its own stack of size __stack_size. This value
+ * can be overriden at build-time by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__stack_size=0xf00
+ *
+ * where 0xf00 can be replaced with a multiple of 16 of your choice.
+ *
+ * __stack_size is PROVIDE-ed as a symbol so that initialization code
+ * initializes the stack pointers for each hart at the right offset from
+ * the _sp symbol.
+ */
+ __stack_size = DEFINED(__stack_size) ? __stack_size : 0x400;
+ PROVIDE(__stack_size = __stack_size);
+
+ /* The size of the heap can be overriden at build-time by adding the
+ * following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_size=0xf00
+ *
+ * where 0xf00 can be replaced with the value of your choice.
+ *
+ * Altertatively, the heap can be grown to fill the entire remaining region
+ * of RAM by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_max=1
+ *
+ * Note that depending on the memory layout, the bitness (32/64bit) of the
+ * target, and the code model in use, this might cause a relocation error.
+ */
+ __heap_size = DEFINED(__heap_size) ? __heap_size : 0x800;
+
+ /* The boot hart sets which hart runs the pre-main initialization routines,
+ * including copying .data into RAM, zeroing the BSS region, running
+ * constructors, etc. After initialization, the boot hart is also the only
+ * hart which runs application code unless the application overrides the
+ * secondary_main() function to start execution on secondary harts.
+ */
+ PROVIDE(__metal_boot_hart = 0);
+
+ /* The chicken bit is used by pre-main initialization to enable/disable
+ * certain core features */
+ PROVIDE(__metal_chicken_bit = 1);
+
+ /* The memory_ecc_scrub bit is used by _entry code to enable/disable
+ * memories scrubbing to zero */
+ PROVIDE(__metal_eccscrub_bit = 0);
+
+ /* The RAM memories map for ECC scrubbing */
+ PROVIDE( metal_dtim_0_memory_start = 0x80000000 );
+ PROVIDE( metal_dtim_0_memory_end = 0x80000000 + 0x4000 );
+ PROVIDE( metal_itim_0_memory_start = 0x8000000 );
+ PROVIDE( metal_itim_0_memory_end = 0x8000000 + 0x2000 );
+
+ /* ROM SECTION
+ *
+ * The following sections contain data which lives in read-only memory, if
+ * such memory is present in the design, for the entire duration of program
+ * execution.
+ */
+
+ .init : {
+ /* The _enter symbol is placed in the .text.metal.init.enter section
+ * and must be placed at the beginning of the program */
+ KEEP (*(.text.metal.init.enter))
+ KEEP (*(.text.metal.init.*))
+ KEEP (*(SORT_NONE(.init)))
+ KEEP (*(.text.libgloss.start))
+ } >rom :rom
+
+ .fini : {
+ KEEP (*(SORT_NONE(.fini)))
+ } >rom :rom
+
+ .preinit_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__preinit_array_start = .);
+ KEEP (*(.preinit_array))
+ PROVIDE_HIDDEN (__preinit_array_end = .);
+ } >rom :rom
+
+ .init_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__init_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
+ KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
+ PROVIDE_HIDDEN (__init_array_end = .);
+ PROVIDE_HIDDEN ( metal_constructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.init_array.*)));
+ KEEP (*(.metal.init_array));
+ PROVIDE_HIDDEN ( metal_constructors_end = .);
+ } >rom :rom
+
+ .fini_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__fini_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
+ KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
+ PROVIDE_HIDDEN (__fini_array_end = .);
+ PROVIDE_HIDDEN ( metal_destructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.fini_array.*)));
+ KEEP (*(.metal.fini_array));
+ PROVIDE_HIDDEN ( metal_destructors_end = .);
+ } >rom :rom
+
+ .privileged_functions : ALIGN (32) {
+ __privileged_functions_start__ = .;
+ KEEP(*(privileged_functions))
+ . = ALIGN(32);
+ __privileged_functions_end__ = .;
+ } >rom
+
+
+ .ctors : {
+ . = ALIGN(32);
+ __unprivileged_section_start__ = .;
+ KEEP (*crtbegin.o(.ctors))
+ KEEP (*crtbegin?.o(.ctors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
+ KEEP (*(SORT(.ctors.*)))
+ KEEP (*(.ctors))
+ KEEP (*(.metal.ctors .metal.ctors.*))
+ } >rom :rom
+
+ .dtors : {
+ KEEP (*crtbegin.o(.dtors))
+ KEEP (*crtbegin?.o(.dtors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
+ KEEP (*(SORT(.dtors.*)))
+ KEEP (*(.dtors))
+ KEEP (*(.metal.dtors .metal.dtors.*))
+ } >rom : rom
+
+ .rodata : {
+ *(.rdata)
+ *(.rodata .rodata.*)
+ *(.gnu.linkonce.r.*)
+ . = ALIGN(8);
+ *(.srodata.cst16)
+ *(.srodata.cst8)
+ *(.srodata.cst4)
+ *(.srodata.cst2)
+ *(.srodata .srodata.*)
+ } >rom :rom
+
+ /* ITIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into an instruction tightly-integrated memory (ITIM), if one
+ * is present in the design, during pre-main program initialization.
+ *
+ * Generally, the data copied into the ITIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .itim : ALIGN(8) {
+ *(.itim .itim.*)
+ } >itim AT>rom :itim_init
+
+ PROVIDE( metal_segment_itim_source_start = LOADADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_start = ADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_end = ADDR(.itim) + SIZEOF(.itim) );
+
+ /* LIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a loosely integrated memory (LIM), which is shared with L2
+ * cache, during pre-main program initialization.
+ *
+ * Generally, the data copied into the LIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .lim : ALIGN(8) {
+ *(.lim .lim.*)
+ } >ram AT>rom :lim_init
+
+ PROVIDE( metal_segment_lim_source_start = LOADADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_start = ADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_end = ADDR(.lim) + SIZEOF(.lim) );
+
+ /* TEXT SECTION
+ *
+ * The following section contains the code of the program, excluding
+ * everything that's been allocated into the ITIM/LIM already
+ */
+
+ .text : {
+ *(.text.unlikely .text.unlikely.*)
+ *(.text.startup .text.startup.*)
+ *(.text .text.*)
+ *(.gnu.linkonce.t.*)
+ *(freertos_system_calls)
+ . = ALIGN(32);
+ __unprivileged_section_end__ = .;
+ } >rom :text
+
+ /* RAM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a read-write-capable memory such as data tightly-integrated
+ * memory (DTIM) or another main memory, as well as the BSS, stack, and
+ * heap.
+ *
+ * You might notice that .data, .tdata, .tbss, .tbss_space, and .bss all
+ * have an apparently unnecessary ALIGN at their top. This is because
+ * the implementation of _start in Freedom Metal libgloss depends on the
+ * ADDR and LOADADDR being 8-byte aligned.
+ */
+
+ .data : ALIGN(8) {
+ . = ALIGN(32);
+ __unprivileged_data_section_start__ = .;
+ *(.data .data.*)
+ *(.gnu.linkonce.d.*)
+ . = ALIGN(8);
+ PROVIDE( __global_pointer$ = . + 0x800 );
+ *(.sdata .sdata.* .sdata2.*)
+ *(.gnu.linkonce.s.*)
+ } >ram AT>rom :ram_init
+
+ .tdata : ALIGN(8) {
+ PROVIDE( __tls_base = . );
+ *(.tdata .tdata.* .gnu.linkonce.td.*)
+ } >ram AT>rom :tls :ram_init
+
+ PROVIDE( __tdata_source = LOADADDR(.tdata) );
+ PROVIDE( __tdata_size = SIZEOF(.tdata) );
+
+ PROVIDE( metal_segment_data_source_start = LOADADDR(.data) );
+ PROVIDE( metal_segment_data_target_start = ADDR(.data) );
+ PROVIDE( metal_segment_data_target_end = ADDR(.tdata) + SIZEOF(.tdata) );
+
+ .tbss : ALIGN(8) {
+ *(.tbss .tbss.* .gnu.linkonce.tb.*)
+ *(.tcommon .tcommon.*)
+ PROVIDE( __tls_end = . );
+ } >ram AT>ram :tls :ram
+ PROVIDE( __tbss_size = SIZEOF(.tbss) );
+ PROVIDE( __tls_size = __tls_end - __tls_base );
+
+ .tbss_space : ALIGN(8) {
+ . = . + __tbss_size;
+ } >ram :ram
+
+ .bss (NOLOAD): ALIGN(8) {
+ *(.sbss*)
+ *(.gnu.linkonce.sb.*)
+ *(.bss .bss.*)
+ *(.gnu.linkonce.b.*)
+ *(COMMON)
+ . = ALIGN(32);
+ __unprivileged_data_section_end__ = .;
+ } >ram :ram
+
+ PROVIDE( metal_segment_bss_source_start = LOADADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_start = ADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_end = ADDR(.bss) + SIZEOF(.bss) );
+
+ .privileged_data (NOLOAD) : ALIGN(32) {
+ __privileged_data_start__ = .;
+ *(privileged_data)
+ /* Non kernel data is kept out of the first _Privileged_Data_Region_Size
+ bytes of SRAM. */
+ . = ALIGN(32);
+ __privileged_data_end__ = .;
+ } >ram
+
+
+ .stack (NOLOAD) : ALIGN(16) {
+ PROVIDE(metal_segment_stack_begin = .);
+ . += __stack_size; /* Hart 0 */
+ PROVIDE( _sp = . );
+ PROVIDE(metal_segment_stack_end = .);
+ } >ram :ram
+
+ .heap (NOLOAD) : ALIGN(8) {
+ PROVIDE( __end = . );
+ PROVIDE( __heap_start = . );
+ PROVIDE( metal_segment_heap_target_start = . );
+ /* If __heap_max is defined, grow the heap to use the rest of RAM,
+ * otherwise set the heap size to __heap_size */
+ . = DEFINED(__heap_max) ? MIN( LENGTH(ram) - ( . - ORIGIN(ram)) , 0x10000000) : __heap_size;
+ PROVIDE( metal_segment_heap_target_end = . );
+ PROVIDE( _heap_end = . );
+ PROVIDE( __heap_end = . );
+ } >ram :ram
+
+ /* C++ exception handling information is
+ * not useful with our current runtime environment,
+ * and it consumes flash space. Discard it until
+ * we have something that can use it
+ */
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+} \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.h
index f76dbd632..74c361b4b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.h
@@ -9,15 +9,15 @@
#ifdef __METAL_MACHINE_MACROS
-#ifndef MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H
-#define MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H
+#ifndef MACROS_IF_METAL_H
+#define MACROS_IF_METAL_H
#define __METAL_CLINT_NUM_PARENTS 2
#ifndef __METAL_CLINT_NUM_PARENTS
#define __METAL_CLINT_NUM_PARENTS 0
#endif
-#define __METAL_PLIC_SUBINTERRUPTS 27
+#define __METAL_PLIC_SUBINTERRUPTS 53
#define __METAL_PLIC_NUM_PARENTS 1
@@ -31,12 +31,12 @@
#define __METAL_CLIC_SUBINTERRUPTS 0
#endif
-#endif /* MACROS_IF_SIFIVE_HIFIVE1_REVB____METAL_H*/
+#endif /* MACROS_IF_METAL_H*/
#else /* ! __METAL_MACHINE_MACROS */
-#ifndef MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H
-#define MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H
+#ifndef MACROS_ELSE_METAL_H
+#define MACROS_ELSE_METAL_H
#define __METAL_CLINT_2000000_INTERRUPTS 2
@@ -46,7 +46,7 @@
#define __METAL_INTERRUPT_CONTROLLER_C000000_INTERRUPTS 1
-#define __METAL_PLIC_SUBINTERRUPTS 27
+#define __METAL_PLIC_SUBINTERRUPTS 53
#define METAL_MAX_PLIC_INTERRUPTS 1
@@ -55,20 +55,36 @@
#define __METAL_CLIC_SUBINTERRUPTS 0
#define METAL_MAX_CLIC_INTERRUPTS 0
-#define __METAL_LOCAL_EXTERNAL_INTERRUPTS_0_INTERRUPTS 16
-
-#define METAL_MAX_LOCAL_EXT_INTERRUPTS 16
+#define METAL_MAX_LOCAL_EXT_INTERRUPTS 0
#define METAL_MAX_GLOBAL_EXT_INTERRUPTS 0
-#define __METAL_GPIO_10012000_INTERRUPTS 16
+#define __METAL_GPIO_10012000_INTERRUPTS 32
+
+#define METAL_MAX_GPIO_INTERRUPTS 32
+
+#define __METAL_I2C_10016000_INTERRUPTS 1
+
+#define METAL_MAX_I2C0_INTERRUPTS 1
+
+#define __METAL_PWM_10015000_INTERRUPTS 4
-#define METAL_MAX_GPIO_INTERRUPTS 16
+#define __METAL_PWM_10025000_INTERRUPTS 4
+
+#define __METAL_PWM_10035000_INTERRUPTS 4
+
+#define METAL_MAX_PWM0_INTERRUPTS 4
+
+#define METAL_MAX_PWM0_NCMP 4
#define __METAL_SERIAL_10013000_INTERRUPTS 1
+#define __METAL_SERIAL_10023000_INTERRUPTS 1
+
#define METAL_MAX_UART_INTERRUPTS 1
+#define METAL_MAX_SIMUART_INTERRUPTS 0
+
#include <metal/drivers/fixed-clock.h>
#include <metal/memory.h>
@@ -76,79 +92,119 @@
#include <metal/drivers/riscv_cpu.h>
#include <metal/drivers/riscv_plic0.h>
#include <metal/pmp.h>
-#include <metal/drivers/sifive_local-external-interrupts0.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/drivers/sifive_gpio-leds.h>
+#include <metal/drivers/sifive_i2c0.h>
+#include <metal/drivers/sifive_pwm0.h>
+#include <metal/drivers/sifive_rtc0.h>
#include <metal/drivers/sifive_spi0.h>
#include <metal/drivers/sifive_uart0.h>
+#include <metal/drivers/sifive_wdog0.h>
#include <metal/drivers/sifive_fe310-g000_hfrosc.h>
#include <metal/drivers/sifive_fe310-g000_hfxosc.h>
+#include <metal/drivers/sifive_fe310-g000_lfrosc.h>
#include <metal/drivers/sifive_fe310-g000_pll.h>
#include <metal/drivers/sifive_fe310-g000_prci.h>
/* From clock@0 */
-struct __metal_driver_fixed_clock __metal_dt_clock_0;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_0;
/* From clock@2 */
-struct __metal_driver_fixed_clock __metal_dt_clock_2;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_2;
/* From clock@5 */
-struct __metal_driver_fixed_clock __metal_dt_clock_5;
+extern struct __metal_driver_fixed_clock __metal_dt_clock_5;
+
+/* From clock@6 */
+extern struct __metal_driver_fixed_clock __metal_dt_clock_6;
+
+extern struct metal_memory __metal_dt_mem_dtim_80000000;
+
+extern struct metal_memory __metal_dt_mem_itim_8000000;
-struct metal_memory __metal_dt_mem_dtim_80000000;
+extern struct metal_memory __metal_dt_mem_spi_10014000;
-struct metal_memory __metal_dt_mem_spi_10014000;
+extern struct metal_memory __metal_dt_mem_spi_10024000;
+
+extern struct metal_memory __metal_dt_mem_spi_10034000;
/* From clint@2000000 */
-struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000;
+extern struct __metal_driver_riscv_clint0 __metal_dt_clint_2000000;
/* From cpu@0 */
-struct __metal_driver_cpu __metal_dt_cpu_0;
+extern struct __metal_driver_cpu __metal_dt_cpu_0;
-struct __metal_driver_riscv_cpu_intc __metal_dt_cpu_0_interrupt_controller;
+extern struct __metal_driver_riscv_cpu_intc __metal_dt_cpu_0_interrupt_controller;
/* From interrupt_controller@c000000 */
-struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000;
-
-struct metal_pmp __metal_dt_pmp;
+extern struct __metal_driver_riscv_plic0 __metal_dt_interrupt_controller_c000000;
-/* From local_external_interrupts_0 */
-struct __metal_driver_sifive_local_external_interrupts0 __metal_dt_local_external_interrupts_0;
+extern struct metal_pmp __metal_dt_pmp;
/* From gpio@10012000 */
-struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000;
+extern struct __metal_driver_sifive_gpio0 __metal_dt_gpio_10012000;
+
+/* From led@0 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_0;
+
+/* From led@1 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_1;
-/* From led@0red */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0red;
+/* From led@2 */
+extern struct __metal_driver_sifive_gpio_led __metal_dt_led_2;
-/* From led@0green */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0green;
+/* From i2c@10016000 */
+extern struct __metal_driver_sifive_i2c0 __metal_dt_i2c_10016000;
-/* From led@0blue */
-struct __metal_driver_sifive_gpio_led __metal_dt_led_0blue;
+/* From pwm@10015000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10015000;
+
+/* From pwm@10025000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10025000;
+
+/* From pwm@10035000 */
+extern struct __metal_driver_sifive_pwm0 __metal_dt_pwm_10035000;
+
+/* From aon@10000000 */
+extern struct __metal_driver_sifive_rtc0 __metal_dt_rtc_10000000;
/* From spi@10014000 */
-struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000;
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10014000;
+
+/* From spi@10024000 */
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10024000;
+
+/* From spi@10034000 */
+extern struct __metal_driver_sifive_spi0 __metal_dt_spi_10034000;
/* From serial@10013000 */
-struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000;
+extern struct __metal_driver_sifive_uart0 __metal_dt_serial_10013000;
+
+/* From serial@10023000 */
+extern struct __metal_driver_sifive_uart0 __metal_dt_serial_10023000;
+
+/* From aon@10000000 */
+extern struct __metal_driver_sifive_wdog0 __metal_dt_aon_10000000;
/* From clock@3 */
-struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3;
+extern struct __metal_driver_sifive_fe310_g000_hfrosc __metal_dt_clock_3;
/* From clock@1 */
-struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1;
+extern struct __metal_driver_sifive_fe310_g000_hfxosc __metal_dt_clock_1;
+
+/* From clock@7 */
+extern struct __metal_driver_sifive_fe310_g000_lfrosc __metal_dt_clock_7;
/* From clock@4 */
-struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4;
+extern struct __metal_driver_sifive_fe310_g000_pll __metal_dt_clock_4;
/* From prci@10008000 */
-struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000;
+extern struct __metal_driver_sifive_fe310_g000_prci __metal_dt_prci_10008000;
/* --------------------- fixed_clock ------------ */
-static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock)
+static __inline__ unsigned long __metal_driver_fixed_clock_rate(const struct metal_clock *clock)
{
if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_0) {
return METAL_FIXED_CLOCK_0_CLOCK_FREQUENCY;
@@ -159,6 +215,9 @@ static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_c
else if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_5) {
return METAL_FIXED_CLOCK_5_CLOCK_FREQUENCY;
}
+ else if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_6) {
+ return METAL_FIXED_CLOCK_6_CLOCK_FREQUENCY;
+ }
else {
return 0;
}
@@ -170,7 +229,7 @@ static inline unsigned long __metal_driver_fixed_clock_rate(const struct metal_c
/* --------------------- sifive_clint0 ------------ */
-static inline unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_clint0_control_base(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_RISCV_CLINT0_2000000_BASE_ADDRESS;
@@ -180,7 +239,7 @@ static inline unsigned long __metal_driver_sifive_clint0_control_base(struct met
}
}
-static inline unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_clint0_control_size(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_RISCV_CLINT0_2000000_SIZE;
@@ -190,7 +249,7 @@ static inline unsigned long __metal_driver_sifive_clint0_control_size(struct met
}
}
-static inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_clint0_num_interrupts(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_clint_2000000) {
return METAL_MAX_CLINT_INTERRUPTS;
@@ -200,7 +259,7 @@ static inline int __metal_driver_sifive_clint0_num_interrupts(struct metal_inter
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_parents(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
@@ -213,7 +272,7 @@ static inline struct metal_interrupt * __metal_driver_sifive_clint0_interrupt_pa
}
}
-static inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_clint0_interrupt_lines(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return 3;
@@ -229,7 +288,7 @@ static inline int __metal_driver_sifive_clint0_interrupt_lines(struct metal_inte
/* --------------------- cpu ------------ */
-static inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return 0;
@@ -239,17 +298,17 @@ static inline int __metal_driver_cpu_hartid(struct metal_cpu *cpu)
}
}
-static inline int __metal_driver_cpu_timebase(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_timebase(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
- return 1000000;
+ return 16000000;
}
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu)
+static __inline__ struct metal_interrupt * __metal_driver_cpu_interrupt_controller(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return &__metal_dt_cpu_0_interrupt_controller.controller;
@@ -259,7 +318,7 @@ static inline struct metal_interrupt * __metal_driver_cpu_interrupt_controller(s
}
}
-static inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
+static __inline__ int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
{
if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
return 8;
@@ -269,10 +328,20 @@ static inline int __metal_driver_cpu_num_pmp_regions(struct metal_cpu *cpu)
}
}
+static __inline__ struct metal_buserror * __metal_driver_cpu_buserror(struct metal_cpu *cpu)
+{
+ if ((uintptr_t)cpu == (uintptr_t)&__metal_dt_cpu_0) {
+ return NULL;
+ }
+ else {
+ return NULL;
+ }
+}
+
/* --------------------- sifive_plic0 ------------ */
-static inline unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_plic0_control_base(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_BASE_ADDRESS;
@@ -282,7 +351,7 @@ static inline unsigned long __metal_driver_sifive_plic0_control_base(struct meta
}
}
-static inline unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_plic0_control_size(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_SIZE;
@@ -292,7 +361,7 @@ static inline unsigned long __metal_driver_sifive_plic0_control_size(struct meta
}
}
-static inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_plic0_num_interrupts(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_RISCV_NDEV;
@@ -302,7 +371,7 @@ static inline int __metal_driver_sifive_plic0_num_interrupts(struct metal_interr
}
}
-static inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller)
+static __inline__ int __metal_driver_sifive_plic0_max_priority(struct metal_interrupt *controller)
{
if ((uintptr_t)controller == (uintptr_t)&__metal_dt_interrupt_controller_c000000) {
return METAL_RISCV_PLIC0_C000000_RISCV_MAX_PRIORITY;
@@ -312,108 +381,189 @@ static inline int __metal_driver_sifive_plic0_max_priority(struct metal_interrup
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_plic0_interrupt_parents(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
}
- else if (idx == 0) {
- return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
- }
else {
return NULL;
}
}
-static inline int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_plic0_interrupt_lines(struct metal_interrupt *controller, int idx)
{
if (idx == 0) {
return 11;
}
- else if (idx == 0) {
- return 11;
- }
else {
return 0;
}
}
+static __inline__ int __metal_driver_sifive_plic0_context_ids(int hartid)
+{
+ if (hartid == 0) {
+ return 0;
+ }
+ else {
+ return -1;
+ }
+}
+
+
+
+/* --------------------- sifive_buserror0 ------------ */
/* --------------------- sifive_clic0 ------------ */
/* --------------------- sifive_local_external_interrupts0 ------------ */
-static inline struct metal_interrupt * __metal_driver_sifive_local_external_interrupts0_interrupt_parent(struct metal_interrupt *controller)
+
+
+/* --------------------- sifive_global_external_interrupts0 ------------ */
+
+
+/* --------------------- sifive_gpio0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio)
{
- if ((uintptr_t)controller == (uintptr_t)&__metal_dt_local_external_interrupts_0) {
- return (struct metal_interrupt *)&__metal_dt_cpu_0_interrupt_controller.controller;
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_SIFIVE_GPIO0_10012000_BASE_ADDRESS;
}
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_local_external_interrupts0_num_interrupts(struct metal_interrupt *controller)
+static __inline__ unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio)
{
- if ((uintptr_t)controller == (uintptr_t)&__metal_dt_local_external_interrupts_0) {
- return METAL_MAX_LOCAL_EXT_INTERRUPTS;
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_SIFIVE_GPIO0_10012000_SIZE;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lines(struct metal_interrupt *controller, int idx)
+static __inline__ int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio)
{
- if (idx == 0) {
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return METAL_MAX_GPIO_INTERRUPTS;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio)
+{
+ if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx)
+{
+ if (((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 0)) {
+ return 8;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 1))) {
+ return 9;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 2))) {
+ return 10;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 3))) {
+ return 11;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 4))) {
+ return 12;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 5))) {
+ return 13;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 6))) {
+ return 14;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 7))) {
+ return 15;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 8))) {
return 16;
}
- else if (idx == 1) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 9))) {
return 17;
}
- else if (idx == 2) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 10))) {
return 18;
}
- else if (idx == 3) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 11))) {
return 19;
}
- else if (idx == 4) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 12))) {
return 20;
}
- else if (idx == 5) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 13))) {
return 21;
}
- else if (idx == 6) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 14))) {
return 22;
}
- else if (idx == 7) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 15))) {
return 23;
}
- else if (idx == 8) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 16))) {
return 24;
}
- else if (idx == 9) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 17))) {
return 25;
}
- else if (idx == 10) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 18))) {
return 26;
}
- else if (idx == 11) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 19))) {
return 27;
}
- else if (idx == 12) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 20))) {
return 28;
}
- else if (idx == 13) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 21))) {
return 29;
}
- else if (idx == 14) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 22))) {
return 30;
}
- else if (idx == 15) {
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 23))) {
return 31;
}
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 24))) {
+ return 32;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 25))) {
+ return 33;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 26))) {
+ return 34;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 27))) {
+ return 35;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 28))) {
+ return 36;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 29))) {
+ return 27;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 30))) {
+ return 28;
+ }
+ else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 31))) {
+ return 29;
+ }
else {
return 0;
}
@@ -421,203 +571,487 @@ static inline int __metal_driver_sifive_local_external_interrupts0_interrupt_lin
-/* --------------------- sifive_global_external_interrupts0 ------------ */
+/* --------------------- sifive_gpio_button ------------ */
-/* --------------------- sifive_gpio0 ------------ */
-static inline unsigned long __metal_driver_sifive_gpio0_base(struct metal_gpio *gpio)
+/* --------------------- sifive_gpio_led ------------ */
+static __inline__ struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_SIFIVE_GPIO0_10012000_BASE_ADDRESS;
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_gpio_led_pin(struct metal_led *led)
+{
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return 22;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return 19;
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return 21;
}
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_gpio0_size(struct metal_gpio *gpio)
+static __inline__ char * __metal_driver_sifive_gpio_led_label(struct metal_led *led)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_SIFIVE_GPIO0_10012000_SIZE;
+ if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0) {
+ return "LD0red";
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_1) {
+ return "LD0green";
+ }
+ else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_2) {
+ return "LD0blue";
+ }
+ else {
+ return "";
+ }
+}
+
+
+
+/* --------------------- sifive_gpio_switch ------------ */
+
+
+/* --------------------- sifive_i2c0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_i2c0_control_base(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return METAL_SIFIVE_I2C0_10016000_BASE_ADDRESS;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_gpio0_num_interrupts(struct metal_gpio *gpio)
+static __inline__ unsigned long __metal_driver_sifive_i2c0_control_size(struct metal_i2c *i2c)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
- return METAL_MAX_GPIO_INTERRUPTS;
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return METAL_SIFIVE_I2C0_10016000_SIZE;
}
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_gpio0_interrupt_parent(struct metal_gpio *gpio)
+static __inline__ struct metal_clock * __metal_driver_sifive_i2c0_clock(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_i2c0_pinmux(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_output_selector(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_i2c0_pinmux_source_selector(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 12288;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_i2c0_num_interrupts(struct metal_i2c *i2c)
+{
+ return METAL_MAX_I2C0_INTERRUPTS;
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_i2c0_interrupt_parent(struct metal_i2c *i2c)
{
- if ((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) {
return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+}
+
+static __inline__ int __metal_driver_sifive_i2c0_interrupt_line(struct metal_i2c *i2c)
+{
+ if ((uintptr_t)i2c == (uintptr_t)&__metal_dt_i2c_10016000) {
+ return 52;
}
else {
return 0;
}
}
-static inline int __metal_driver_sifive_gpio0_interrupt_lines(struct metal_gpio *gpio, int idx)
+
+
+/* --------------------- sifive_pwm0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_pwm0_control_base(struct metal_pwm *pwm)
{
- if (((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 0)) {
- return 7;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return METAL_SIFIVE_PWM0_10015000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 1))) {
- return 8;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return METAL_SIFIVE_PWM0_10025000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 2))) {
- return 9;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return METAL_SIFIVE_PWM0_10035000_BASE_ADDRESS;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 3))) {
- return 10;
+ else {
+ return 0;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 4))) {
- return 11;
+}
+
+static __inline__ unsigned long __metal_driver_sifive_pwm0_control_size(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return METAL_SIFIVE_PWM0_10015000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 5))) {
- return 12;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return METAL_SIFIVE_PWM0_10025000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 6))) {
- return 13;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return METAL_SIFIVE_PWM0_10035000_SIZE;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 7))) {
- return 14;
+ else {
+ return 0;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 8))) {
- return 15;
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_pwm0_clock(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 9))) {
- return 16;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 10))) {
- return 17;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 11))) {
- return 18;
+ else {
+ return NULL;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 12))) {
- return 19;
+}
+
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_pwm0_pinmux(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 13))) {
- return 20;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 14))) {
- return 21;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
}
- else if ((((uintptr_t)gpio == (uintptr_t)&__metal_dt_gpio_10012000) && (idx == 15))) {
- return 22;
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_output_selector(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 15;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 7864320;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 15360;
}
else {
return 0;
}
}
+static __inline__ unsigned long __metal_driver_sifive_pwm0_pinmux_source_selector(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 15;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 7864320;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 15360;
+ }
+ else {
+ return 0;
+ }
+}
+static __inline__ int __metal_driver_sifive_pwm0_num_interrupts(struct metal_pwm *pwm)
+{
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return __METAL_PWM_10015000_INTERRUPTS;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return __METAL_PWM_10025000_INTERRUPTS;
+ }
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return __METAL_PWM_10035000_INTERRUPTS;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_button ------------ */
+static __inline__ struct metal_interrupt * __metal_driver_sifive_pwm0_interrupt_parent(struct metal_pwm *pwm)
+{
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+}
+static __inline__ int __metal_driver_sifive_pwm0_interrupt_lines(struct metal_pwm *pwm, int idx)
+{
+ if (((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 0)) {
+ return 40;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 1))) {
+ return 41;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 2))) {
+ return 42;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) && (idx == 3))) {
+ return 43;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 0))) {
+ return 44;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 1))) {
+ return 45;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 2))) {
+ return 46;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) && (idx == 3))) {
+ return 47;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 0))) {
+ return 48;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 1))) {
+ return 49;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 2))) {
+ return 50;
+ }
+ else if ((((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) && (idx == 3))) {
+ return 51;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_led ------------ */
-static inline struct metal_gpio * __metal_driver_sifive_gpio_led_gpio(struct metal_led *led)
+static __inline__ int __metal_driver_sifive_pwm0_compare_width(struct metal_pwm *pwm)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 8;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 16;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return (struct metal_gpio *)&__metal_dt_gpio_10012000;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 16;
}
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_gpio_led_pin(struct metal_led *led)
+static __inline__ int __metal_driver_sifive_pwm0_comparator_count(struct metal_pwm *pwm)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return 22;
+ if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10015000) {
+ return 4;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return 19;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10025000) {
+ return 4;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return 21;
+ else if ((uintptr_t)pwm == (uintptr_t)&__metal_dt_pwm_10035000) {
+ return 4;
}
else {
return 0;
}
}
-static inline char * __metal_driver_sifive_gpio_led_label(struct metal_led *led)
+
+
+/* --------------------- sifive_rtc0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_rtc0_control_base(const struct metal_rtc *const rtc)
{
- if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0red) {
- return "LD0red";
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return METAL_SIFIVE_AON0_10000000_BASE_ADDRESS;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0green) {
- return "LD0green";
+ else {
+ return 0;
}
- else if ((uintptr_t)led == (uintptr_t)&__metal_dt_led_0blue) {
- return "LD0blue";
+}
+
+static __inline__ unsigned long __metal_driver_sifive_rtc0_control_size(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return METAL_SIFIVE_AON0_10000000_SIZE;
}
else {
- return "";
+ return 0;
}
}
+static __inline__ struct metal_interrupt * __metal_driver_sifive_rtc0_interrupt_parent(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+static __inline__ int __metal_driver_sifive_rtc0_interrupt_line(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return 2;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_gpio_switch ------------ */
+static __inline__ struct metal_clock * __metal_driver_sifive_rtc0_clock(const struct metal_rtc *const rtc)
+{
+ if ((uintptr_t)rtc == (uintptr_t)&__metal_dt_rtc_10000000) {
+ return (struct metal_clock *)&__metal_dt_clock_7.clock;
+ }
+ else {
+ return 0;
+ }
+}
-/* --------------------- sifive_spi0 ------------ */
-static inline unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_control_base(struct metal_spi *spi)
{
if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
return METAL_SIFIVE_SPI0_10014000_BASE_ADDRESS;
}
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return METAL_SIFIVE_SPI0_10024000_BASE_ADDRESS;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return METAL_SIFIVE_SPI0_10034000_BASE_ADDRESS;
+ }
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_control_size(struct metal_spi *spi)
{
if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
return METAL_SIFIVE_SPI0_10014000_SIZE;
}
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return METAL_SIFIVE_SPI0_10024000_SIZE;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return METAL_SIFIVE_SPI0_10034000_SIZE;
+ }
else {
return 0;
}
}
-static inline struct metal_clock * __metal_driver_sifive_spi0_clock(struct metal_spi *spi)
+static __inline__ struct metal_clock * __metal_driver_sifive_spi0_clock(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi)
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_spi0_pinmux(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_output_selector(struct metal_spi *spi)
{
- return 60;
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi)
+static __inline__ unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(struct metal_spi *spi)
{
+ if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10014000) {
+ return 0;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10024000) {
return 60;
+ }
+ else if ((uintptr_t)spi == (uintptr_t)&__metal_dt_spi_10034000) {
+ return 4227858432;
+ }
+ else {
+ return 0;
+ }
}
@@ -625,91 +1059,201 @@ static inline unsigned long __metal_driver_sifive_spi0_pinmux_source_selector(st
/* --------------------- sifive_test0 ------------ */
+/* --------------------- sifive_trace ------------ */
+
/* --------------------- sifive_uart0 ------------ */
-static inline unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_control_base(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_SIFIVE_UART0_10013000_BASE_ADDRESS;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_SIFIVE_UART0_10023000_BASE_ADDRESS;
+ }
else {
return 0;
}
}
-static inline unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_control_size(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_SIFIVE_UART0_10013000_SIZE;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_SIFIVE_UART0_10023000_SIZE;
+ }
else {
return 0;
}
}
-static inline int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart)
+static __inline__ int __metal_driver_sifive_uart0_num_interrupts(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return METAL_MAX_UART_INTERRUPTS;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return METAL_MAX_UART_INTERRUPTS;
+ }
else {
return 0;
}
}
-static inline struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart)
+static __inline__ struct metal_interrupt * __metal_driver_sifive_uart0_interrupt_parent(struct metal_uart *uart)
{
if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
}
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
else {
- return NULL;
+ return 0;
}
}
-static inline int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart)
+static __inline__ int __metal_driver_sifive_uart0_interrupt_line(struct metal_uart *uart)
{
- return 5;
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return 3;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 4;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart)
+static __inline__ struct metal_clock * __metal_driver_sifive_uart0_clock(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return (struct metal_clock *)&__metal_dt_clock_4.clock;
+ }
+ else {
+ return 0;
+ }
}
-static inline struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart)
+static __inline__ struct __metal_driver_sifive_gpio0 * __metal_driver_sifive_uart0_pinmux(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
return (struct __metal_driver_sifive_gpio0 *)&__metal_dt_gpio_10012000;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_output_selector(struct metal_uart *uart)
{
- return 196608;
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
+ return 0;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 0;
+ }
+ else {
+ return 0;
+ }
}
-static inline unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart)
+static __inline__ unsigned long __metal_driver_sifive_uart0_pinmux_source_selector(struct metal_uart *uart)
{
+ if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10013000) {
return 196608;
+ }
+ else if ((uintptr_t)uart == (uintptr_t)&__metal_dt_serial_10023000) {
+ return 8650752;
+ }
+ else {
+ return 0;
+ }
+}
+
+
+
+/* --------------------- sifive_simuart0 ------------ */
+
+
+/* --------------------- sifive_wdog0 ------------ */
+static __inline__ unsigned long __metal_driver_sifive_wdog0_control_base(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return METAL_SIFIVE_AON0_10000000_BASE_ADDRESS;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long __metal_driver_sifive_wdog0_control_size(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return METAL_SIFIVE_AON0_10000000_SIZE;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_interrupt * __metal_driver_sifive_wdog0_interrupt_parent(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return (struct metal_interrupt *)&__metal_dt_interrupt_controller_c000000.controller;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ int __metal_driver_sifive_wdog0_interrupt_line(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return 1;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_wdog0_clock(const struct metal_watchdog *const watchdog)
+{
+ if ((uintptr_t)watchdog == (uintptr_t)&__metal_dt_aon_10000000) {
+ return (struct metal_clock *)&__metal_dt_clock_7.clock;
+ }
+ else {
+ return 0;
+ }
}
/* --------------------- sifive_fe310_g000_hfrosc ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfrosc_ref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_2.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock)
+static __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfrosc_config_vtable(struct metal_clock *clock)
{
return &__metal_driver_vtable_sifive_fe310_g000_prci;
}
-static inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_HFROSCCFG;
}
@@ -717,55 +1261,98 @@ static inline long __metal_driver_sifive_fe310_g000_hfrosc_config_offset(const s
/* --------------------- sifive_fe310_g000_hfxosc ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_hfxosc_ref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_0.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_hfxosc_config_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_hfxosc_config_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_HFXOSCCFG;
}
+/* --------------------- sifive_fe310_g000_lfrosc ------------ */
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return (struct metal_clock *)&__metal_dt_clock_5.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return (struct metal_clock *)&__metal_dt_clock_6.clock;
+ }
+ else {
+ return NULL;
+ }
+}
+
+static __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_config_reg(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return 112;
+ }
+ else {
+ return 0;
+ }
+}
+
+static __inline__ unsigned long int __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(const struct metal_clock *clock)
+{
+ if ((uintptr_t)clock == (uintptr_t)&__metal_dt_clock_7) {
+ return 124;
+ }
+ else {
+ return 0;
+ }
+}
+
+
+
/* --------------------- sifive_fe310_g000_pll ------------ */
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllsel0(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_3.clock;
}
-static inline struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock)
+static __inline__ struct metal_clock * __metal_driver_sifive_fe310_g000_pll_pllref(const struct metal_clock *clock)
{
return (struct metal_clock *)&__metal_dt_clock_1.clock;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock)
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_divider_base(const struct metal_clock *clock)
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock)
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_divider_offset(const struct metal_clock *clock)
{
return METAL_SIFIVE_FE310_G000_PRCI_PLLOUTDIV;
}
-static inline struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( )
+static __inline__ struct __metal_driver_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_pll_config_base( )
{
return (struct __metal_driver_sifive_fe310_g000_prci *)&__metal_dt_prci_10008000;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_config_offset( )
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_config_offset( )
{
return METAL_SIFIVE_FE310_G000_PRCI_PLLCFG;
}
-static inline long __metal_driver_sifive_fe310_g000_pll_init_rate( )
+static __inline__ long __metal_driver_sifive_fe310_g000_pll_init_rate( )
{
return 16000000;
}
@@ -773,31 +1360,29 @@ static inline long __metal_driver_sifive_fe310_g000_pll_init_rate( )
/* --------------------- sifive_fe310_g000_prci ------------ */
-static inline long __metal_driver_sifive_fe310_g000_prci_base( )
+static __inline__ long __metal_driver_sifive_fe310_g000_prci_base( )
{
return METAL_SIFIVE_FE310_G000_PRCI_10008000_BASE_ADDRESS;
}
-static inline long __metal_driver_sifive_fe310_g000_prci_size( )
+static __inline__ long __metal_driver_sifive_fe310_g000_prci_size( )
{
return METAL_SIFIVE_FE310_G000_PRCI_10008000_SIZE;
}
-static inline const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( )
+static __inline__ const struct __metal_driver_vtable_sifive_fe310_g000_prci * __metal_driver_sifive_fe310_g000_prci_vtable( )
{
return &__metal_driver_vtable_sifive_fe310_g000_prci;
}
-/* --------------------- sifive_fu540_c000_l2 ------------ */
-
+#define __METAL_DT_MAX_MEMORIES 3
-#define __METAL_DT_MAX_MEMORIES 2
-
-asm (".weak __metal_memory_table");
+__asm__ (".weak __metal_memory_table");
struct metal_memory *__metal_memory_table[] = {
&__metal_dt_mem_dtim_80000000,
+ &__metal_dt_mem_itim_8000000,
&__metal_dt_mem_spi_10014000};
/* From serial@10013000 */
@@ -814,7 +1399,9 @@ struct metal_memory *__metal_memory_table[] = {
#define __METAL_DT_MAX_HARTS 1
-asm (".weak __metal_cpu_table");
+#define __METAL_CPU_0_ICACHE_HANDLE 1
+
+__asm__ (".weak __metal_cpu_table");
struct __metal_driver_cpu *__metal_cpu_table[] = {
&__metal_dt_cpu_0};
@@ -825,47 +1412,82 @@ struct __metal_driver_cpu *__metal_cpu_table[] = {
#define __METAL_DT_PMP_HANDLE (&__metal_dt_pmp)
-/* From local_external_interrupts_0 */
-#define __METAL_DT_SIFIVE_LOCAL_EXINTR0_HANDLE (&__metal_dt_local_external_interrupts_0.irc)
-
-#define __METAL_DT_LOCAL_EXTERNAL_INTERRUPTS_0_HANDLE (&__metal_dt_local_external_interrupts_0.irc)
-
#define __MEE_DT_MAX_GPIOS 1
-asm (".weak __metal_gpio_table");
+__asm__ (".weak __metal_gpio_table");
struct __metal_driver_sifive_gpio0 *__metal_gpio_table[] = {
&__metal_dt_gpio_10012000};
#define __METAL_DT_MAX_BUTTONS 0
-asm (".weak __metal_button_table");
+__asm__ (".weak __metal_button_table");
struct __metal_driver_sifive_gpio_button *__metal_button_table[] = {
NULL };
#define __METAL_DT_MAX_LEDS 3
-asm (".weak __metal_led_table");
+__asm__ (".weak __metal_led_table");
struct __metal_driver_sifive_gpio_led *__metal_led_table[] = {
- &__metal_dt_led_0red,
- &__metal_dt_led_0green,
- &__metal_dt_led_0blue};
+ &__metal_dt_led_0,
+ &__metal_dt_led_1,
+ &__metal_dt_led_2};
#define __METAL_DT_MAX_SWITCHES 0
-asm (".weak __metal_switch_table");
+__asm__ (".weak __metal_switch_table");
struct __metal_driver_sifive_gpio_switch *__metal_switch_table[] = {
NULL };
-#define __METAL_DT_MAX_SPIS 1
+#define __METAL_DT_MAX_I2CS 1
+
+__asm__ (".weak __metal_i2c_table");
+struct __metal_driver_sifive_i2c0 *__metal_i2c_table[] = {
+ &__metal_dt_i2c_10016000};
+
+#define __METAL_DT_MAX_PWMS 3
+
+__asm__ (".weak __metal_pwm_table");
+struct __metal_driver_sifive_pwm0 *__metal_pwm_table[] = {
+ &__metal_dt_pwm_10015000,
+ &__metal_dt_pwm_10025000,
+ &__metal_dt_pwm_10035000};
+
+#define __METAL_DT_MAX_RTCS 1
-asm (".weak __metal_spi_table");
+__asm__ (".weak __metal_rtc_table");
+struct __metal_driver_sifive_rtc0 *__metal_rtc_table[] = {
+ &__metal_dt_rtc_10000000};
+
+#define __METAL_DT_MAX_SPIS 3
+
+__asm__ (".weak __metal_spi_table");
struct __metal_driver_sifive_spi0 *__metal_spi_table[] = {
- &__metal_dt_spi_10014000};
+ &__metal_dt_spi_10014000,
+ &__metal_dt_spi_10024000,
+ &__metal_dt_spi_10034000};
+
+#define __METAL_DT_MAX_UARTS 2
+
+__asm__ (".weak __metal_uart_table");
+struct __metal_driver_sifive_uart0 *__metal_uart_table[] = {
+ &__metal_dt_serial_10013000,
+ &__metal_dt_serial_10023000};
+
+#define __METAL_DT_MAX_SIMUARTS 0
+
+__asm__ (".weak __metal_simuart_table");
+struct __metal_driver_sifive_simuart0 *__metal_simuart_table[] = {
+ NULL };
+#define __METAL_DT_MAX_WDOGS 1
+
+__asm__ (".weak __metal_wdog_table");
+struct __metal_driver_sifive_wdog0 *__metal_wdog_table[] = {
+ &__metal_dt_aon_10000000};
/* From clock@4 */
#define __METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE (&__metal_dt_clock_4)
#define __METAL_DT_CLOCK_4_HANDLE (&__metal_dt_clock_4)
-#endif /* MACROS_ELSE_SIFIVE_HIFIVE1_REVB____METAL_H*/
+#endif /* MACROS_ELSE_METAL_H*/
#endif /* ! __METAL_MACHINE_MACROS */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.ramrodata.lds b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.ramrodata.lds
new file mode 100644
index 000000000..6803873ce
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.ramrodata.lds
@@ -0,0 +1,306 @@
+/* Copyright (c) 2020 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+OUTPUT_ARCH("riscv")
+
+/* RAM Read-Only Data Linker Script
+ *
+ * This linker script places application code and read-only data into writable
+ * memories in an attempt to improve performance, since writable memories
+ * are generally lower-latency. This linker script may cause your application
+ * to overflow RAM, since it dramatically increases the quantity of data vying
+ * for space there.
+ */
+
+ENTRY(_enter)
+
+MEMORY
+{
+ itim (airwx) : ORIGIN = 0x8000000, LENGTH = 0x2000
+ ram (arw!xi) : ORIGIN = 0x80000000, LENGTH = 0x4000
+ rom (irx!wa) : ORIGIN = 0x20010000, LENGTH = 0x6a120
+}
+
+PHDRS
+{
+ rom PT_LOAD;
+ ram_init PT_LOAD;
+ tls PT_TLS;
+ ram PT_LOAD;
+ itim_init PT_LOAD;
+ text PT_LOAD;
+ lim_init PT_LOAD;
+}
+
+SECTIONS
+{
+ /* Each hart is allocated its own stack of size __stack_size. This value
+ * can be overriden at build-time by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__stack_size=0xf00
+ *
+ * where 0xf00 can be replaced with a multiple of 16 of your choice.
+ *
+ * __stack_size is PROVIDE-ed as a symbol so that initialization code
+ * initializes the stack pointers for each hart at the right offset from
+ * the _sp symbol.
+ */
+ __stack_size = DEFINED(__stack_size) ? __stack_size : 0x400;
+ PROVIDE(__stack_size = __stack_size);
+
+ /* The size of the heap can be overriden at build-time by adding the
+ * following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_size=0xf00
+ *
+ * where 0xf00 can be replaced with the value of your choice.
+ *
+ * Altertatively, the heap can be grown to fill the entire remaining region
+ * of RAM by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_max=1
+ *
+ * Note that depending on the memory layout, the bitness (32/64bit) of the
+ * target, and the code model in use, this might cause a relocation error.
+ */
+ __heap_size = DEFINED(__heap_size) ? __heap_size : 0x800;
+
+ /* The boot hart sets which hart runs the pre-main initialization routines,
+ * including copying .data into RAM, zeroing the BSS region, running
+ * constructors, etc. After initialization, the boot hart is also the only
+ * hart which runs application code unless the application overrides the
+ * secondary_main() function to start execution on secondary harts.
+ */
+ PROVIDE(__metal_boot_hart = 0);
+
+ /* The chicken bit is used by pre-main initialization to enable/disable
+ * certain core features */
+ PROVIDE(__metal_chicken_bit = 1);
+
+ /* The memory_ecc_scrub bit is used by _entry code to enable/disable
+ * memories scrubbing to zero */
+ PROVIDE(__metal_eccscrub_bit = 0);
+
+ /* The RAM memories map for ECC scrubbing */
+ PROVIDE( metal_dtim_0_memory_start = 0x80000000 );
+ PROVIDE( metal_dtim_0_memory_end = 0x80000000 + 0x4000 );
+ PROVIDE( metal_itim_0_memory_start = 0x8000000 );
+ PROVIDE( metal_itim_0_memory_end = 0x8000000 + 0x2000 );
+
+ /* ROM SECTION
+ *
+ * The following sections contain data which lives in read-only memory, if
+ * such memory is present in the design, for the entire duration of program
+ * execution.
+ */
+
+ .init : {
+ /* The _enter symbol is placed in the .text.metal.init.enter section
+ * and must be placed at the beginning of the program */
+ KEEP (*(.text.metal.init.enter))
+ KEEP (*(.text.metal.init.*))
+ KEEP (*(SORT_NONE(.init)))
+ KEEP (*(.text.libgloss.start))
+ } >rom :rom
+
+ .fini : {
+ KEEP (*(SORT_NONE(.fini)))
+ } >rom :rom
+
+ .preinit_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__preinit_array_start = .);
+ KEEP (*(.preinit_array))
+ PROVIDE_HIDDEN (__preinit_array_end = .);
+ } >rom :rom
+
+ .init_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__init_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
+ KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
+ PROVIDE_HIDDEN (__init_array_end = .);
+ PROVIDE_HIDDEN ( metal_constructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.init_array.*)));
+ KEEP (*(.metal.init_array));
+ PROVIDE_HIDDEN ( metal_constructors_end = .);
+ } >rom :rom
+
+ .fini_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__fini_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
+ KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
+ PROVIDE_HIDDEN (__fini_array_end = .);
+ PROVIDE_HIDDEN ( metal_destructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.fini_array.*)));
+ KEEP (*(.metal.fini_array));
+ PROVIDE_HIDDEN ( metal_destructors_end = .);
+ } >rom :rom
+
+
+
+ .ctors : {
+ KEEP (*crtbegin.o(.ctors))
+ KEEP (*crtbegin?.o(.ctors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
+ KEEP (*(SORT(.ctors.*)))
+ KEEP (*(.ctors))
+ KEEP (*(.metal.ctors .metal.ctors.*))
+ } >rom :rom
+
+ .dtors : {
+ KEEP (*crtbegin.o(.dtors))
+ KEEP (*crtbegin?.o(.dtors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
+ KEEP (*(SORT(.dtors.*)))
+ KEEP (*(.dtors))
+ KEEP (*(.metal.dtors .metal.dtors.*))
+ } >rom : rom
+
+
+ /* ITIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into an instruction tightly-integrated memory (ITIM), if one
+ * is present in the design, during pre-main program initialization.
+ *
+ * Generally, the data copied into the ITIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .itim : ALIGN(8) {
+ *(.itim .itim.*)
+ } >itim AT>rom :itim_init
+
+ PROVIDE( metal_segment_itim_source_start = LOADADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_start = ADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_end = ADDR(.itim) + SIZEOF(.itim) );
+
+ /* LIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a loosely integrated memory (LIM), which is shared with L2
+ * cache, during pre-main program initialization.
+ *
+ * Generally, the data copied into the LIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .lim : ALIGN(8) {
+ *(.lim .lim.*)
+ } >ram AT>rom :lim_init
+
+ PROVIDE( metal_segment_lim_source_start = LOADADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_start = ADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_end = ADDR(.lim) + SIZEOF(.lim) );
+
+ /* TEXT SECTION
+ *
+ * The following section contains the code of the program, excluding
+ * everything that's been allocated into the ITIM/LIM already
+ */
+
+ .text : {
+ *(.text.unlikely .text.unlikely.*)
+ *(.text.startup .text.startup.*)
+ *(.text .text.*)
+ *(.gnu.linkonce.t.*)
+ } >rom :text
+
+ /* RAM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a read-write-capable memory such as data tightly-integrated
+ * memory (DTIM) or another main memory, as well as the BSS, stack, and
+ * heap.
+ *
+ * You might notice that .data, .tdata, .tbss, .tbss_space, and .bss all
+ * have an apparently unnecessary ALIGN at their top. This is because
+ * the implementation of _start in Freedom Metal libgloss depends on the
+ * ADDR and LOADADDR being 8-byte aligned.
+ */
+
+ .data : ALIGN(8) {
+ *(.data .data.*)
+ *(.gnu.linkonce.d.*)
+ . = ALIGN(8);
+ PROVIDE( __global_pointer$ = . + 0x800 );
+ *(.sdata .sdata.* .sdata2.*)
+ *(.gnu.linkonce.s.*)
+ /* Read-only data is placed in RAM to improve performance, since
+ * read-only memory generally has higher latency than RAM */
+ . = ALIGN(8);
+ *(.srodata.cst16)
+ *(.srodata.cst8)
+ *(.srodata.cst4)
+ *(.srodata.cst2)
+ *(.srodata .srodata.*)
+ . = ALIGN(8);
+ *(.rdata)
+ *(.rodata .rodata.*)
+ *(.gnu.linkonce.r.*)
+ } >ram AT>rom :ram_init
+
+ .tdata : ALIGN(8) {
+ PROVIDE( __tls_base = . );
+ *(.tdata .tdata.* .gnu.linkonce.td.*)
+ } >ram AT>rom :tls :ram_init
+
+ PROVIDE( __tdata_source = LOADADDR(.tdata) );
+ PROVIDE( __tdata_size = SIZEOF(.tdata) );
+
+ PROVIDE( metal_segment_data_source_start = LOADADDR(.data) );
+ PROVIDE( metal_segment_data_target_start = ADDR(.data) );
+ PROVIDE( metal_segment_data_target_end = ADDR(.tdata) + SIZEOF(.tdata) );
+
+ .tbss : ALIGN(8) {
+ *(.tbss .tbss.* .gnu.linkonce.tb.*)
+ *(.tcommon .tcommon.*)
+ PROVIDE( __tls_end = . );
+ } >ram AT>ram :tls :ram
+ PROVIDE( __tbss_size = SIZEOF(.tbss) );
+ PROVIDE( __tls_size = __tls_end - __tls_base );
+
+ .tbss_space : ALIGN(8) {
+ . = . + __tbss_size;
+ } >ram :ram
+
+ .bss (NOLOAD): ALIGN(8) {
+ *(.sbss*)
+ *(.gnu.linkonce.sb.*)
+ *(.bss .bss.*)
+ *(.gnu.linkonce.b.*)
+ *(COMMON)
+ } >ram :ram
+
+ PROVIDE( metal_segment_bss_source_start = LOADADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_start = ADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_end = ADDR(.bss) + SIZEOF(.bss) );
+
+
+
+ .stack (NOLOAD) : ALIGN(16) {
+ PROVIDE(metal_segment_stack_begin = .);
+ . += __stack_size; /* Hart 0 */
+ PROVIDE( _sp = . );
+ PROVIDE(metal_segment_stack_end = .);
+ } >ram :ram
+
+ .heap (NOLOAD) : ALIGN(8) {
+ PROVIDE( __end = . );
+ PROVIDE( __heap_start = . );
+ PROVIDE( metal_segment_heap_target_start = . );
+ /* If __heap_max is defined, grow the heap to use the rest of RAM,
+ * otherwise set the heap size to __heap_size */
+ . = DEFINED(__heap_max) ? MIN( LENGTH(ram) - ( . - ORIGIN(ram)) , 0x10000000) : __heap_size;
+ PROVIDE( metal_segment_heap_target_end = . );
+ PROVIDE( _heap_end = . );
+ PROVIDE( __heap_end = . );
+ } >ram :ram
+
+ /* C++ exception handling information is
+ * not useful with our current runtime environment,
+ * and it consumes flash space. Discard it until
+ * we have something that can use it
+ */
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+} \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.scratchpad.lds b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.scratchpad.lds
new file mode 100644
index 000000000..356726912
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/metal.scratchpad.lds
@@ -0,0 +1,294 @@
+/* Copyright (c) 2020 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+OUTPUT_ARCH("riscv")
+
+/* Scratchpad Linker Script
+ *
+ * This linker script is for executing in "scratchpad" mode, where all
+ * application code and data is placed in writable memory.
+ */
+
+ENTRY(_enter)
+
+MEMORY
+{
+ itim (airwx) : ORIGIN = 0x8000000, LENGTH = 0x2000
+ ram (arw!xi) : ORIGIN = 0x80000000, LENGTH = 0x4000
+ rom (irx!wa) : ORIGIN = 0x20010000, LENGTH = 0x6a120
+}
+
+PHDRS
+{
+ rom PT_LOAD;
+ ram_init PT_LOAD;
+ tls PT_TLS;
+ ram PT_LOAD;
+ itim_init PT_LOAD;
+ text PT_LOAD;
+ lim_init PT_LOAD;
+}
+
+SECTIONS
+{
+ /* Each hart is allocated its own stack of size __stack_size. This value
+ * can be overriden at build-time by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__stack_size=0xf00
+ *
+ * where 0xf00 can be replaced with a multiple of 16 of your choice.
+ *
+ * __stack_size is PROVIDE-ed as a symbol so that initialization code
+ * initializes the stack pointers for each hart at the right offset from
+ * the _sp symbol.
+ */
+ __stack_size = DEFINED(__stack_size) ? __stack_size : 0x400;
+ PROVIDE(__stack_size = __stack_size);
+
+ /* The size of the heap can be overriden at build-time by adding the
+ * following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_size=0xf00
+ *
+ * where 0xf00 can be replaced with the value of your choice.
+ *
+ * Altertatively, the heap can be grown to fill the entire remaining region
+ * of RAM by adding the following to CFLAGS:
+ *
+ * -Xlinker --defsym=__heap_max=1
+ *
+ * Note that depending on the memory layout, the bitness (32/64bit) of the
+ * target, and the code model in use, this might cause a relocation error.
+ */
+ __heap_size = DEFINED(__heap_size) ? __heap_size : 0x800;
+
+ /* The boot hart sets which hart runs the pre-main initialization routines,
+ * including copying .data into RAM, zeroing the BSS region, running
+ * constructors, etc. After initialization, the boot hart is also the only
+ * hart which runs application code unless the application overrides the
+ * secondary_main() function to start execution on secondary harts.
+ */
+ PROVIDE(__metal_boot_hart = 0);
+
+ /* The chicken bit is used by pre-main initialization to enable/disable
+ * certain core features */
+ PROVIDE(__metal_chicken_bit = 1);
+
+ PROVIDE(__metal_eccscrub_bit = 0);
+
+ /* ROM SECTION
+ *
+ * The following sections contain data which lives in read-only memory, if
+ * such memory is present in the design, for the entire duration of program
+ * execution.
+ */
+
+ .init : {
+ /* The _enter symbol is placed in the .text.metal.init.enter section
+ * and must be placed at the beginning of the program */
+ KEEP (*(.text.metal.init.enter))
+ KEEP (*(.text.metal.init.*))
+ KEEP (*(SORT_NONE(.init)))
+ KEEP (*(.text.libgloss.start))
+ } >ram :rom
+
+ .fini : {
+ KEEP (*(SORT_NONE(.fini)))
+ } >ram :rom
+
+ .preinit_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__preinit_array_start = .);
+ KEEP (*(.preinit_array))
+ PROVIDE_HIDDEN (__preinit_array_end = .);
+ } >ram :rom
+
+ .init_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__init_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.init_array.*) SORT_BY_INIT_PRIORITY(.ctors.*)))
+ KEEP (*(.init_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .ctors))
+ PROVIDE_HIDDEN (__init_array_end = .);
+ PROVIDE_HIDDEN ( metal_constructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.init_array.*)));
+ KEEP (*(.metal.init_array));
+ PROVIDE_HIDDEN ( metal_constructors_end = .);
+ } >ram :rom
+
+ .fini_array : ALIGN(8) {
+ PROVIDE_HIDDEN (__fini_array_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.fini_array.*) SORT_BY_INIT_PRIORITY(.dtors.*)))
+ KEEP (*(.fini_array EXCLUDE_FILE (*crtbegin.o *crtbegin?.o *crtend.o *crtend?.o ) .dtors))
+ PROVIDE_HIDDEN (__fini_array_end = .);
+ PROVIDE_HIDDEN ( metal_destructors_start = .);
+ KEEP (*(SORT_BY_INIT_PRIORITY(.metal.fini_array.*)));
+ KEEP (*(.metal.fini_array));
+ PROVIDE_HIDDEN ( metal_destructors_end = .);
+ } >ram :rom
+
+
+
+ .ctors : {
+ KEEP (*crtbegin.o(.ctors))
+ KEEP (*crtbegin?.o(.ctors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors))
+ KEEP (*(SORT(.ctors.*)))
+ KEEP (*(.ctors))
+ KEEP (*(.metal.ctors .metal.ctors.*))
+ } >ram :rom
+
+ .dtors : {
+ KEEP (*crtbegin.o(.dtors))
+ KEEP (*crtbegin?.o(.dtors))
+ KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors))
+ KEEP (*(SORT(.dtors.*)))
+ KEEP (*(.dtors))
+ KEEP (*(.metal.dtors .metal.dtors.*))
+ } >ram : rom
+
+ .rodata : {
+ *(.rdata)
+ *(.rodata .rodata.*)
+ *(.gnu.linkonce.r.*)
+ . = ALIGN(8);
+ *(.srodata.cst16)
+ *(.srodata.cst8)
+ *(.srodata.cst4)
+ *(.srodata.cst2)
+ *(.srodata .srodata.*)
+ } >ram :rom
+
+ /* ITIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into an instruction tightly-integrated memory (ITIM), if one
+ * is present in the design, during pre-main program initialization.
+ *
+ * Generally, the data copied into the ITIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .itim : ALIGN(8) {
+ *(.itim .itim.*)
+ } >itim AT>ram :itim_init
+
+ PROVIDE( metal_segment_itim_source_start = LOADADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_start = ADDR(.itim) );
+ PROVIDE( metal_segment_itim_target_end = ADDR(.itim) + SIZEOF(.itim) );
+
+ /* LIM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a loosely integrated memory (LIM), which is shared with L2
+ * cache, during pre-main program initialization.
+ *
+ * Generally, the data copied into the LIM should be performance-critical
+ * functions which benefit from low instruction-fetch latency.
+ */
+
+ .lim : ALIGN(8) {
+ *(.lim .lim.*)
+ } >ram AT>ram :lim_init
+
+ PROVIDE( metal_segment_lim_source_start = LOADADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_start = ADDR(.lim) );
+ PROVIDE( metal_segment_lim_target_end = ADDR(.lim) + SIZEOF(.lim) );
+
+ /* TEXT SECTION
+ *
+ * The following section contains the code of the program, excluding
+ * everything that's been allocated into the ITIM/LIM already
+ */
+
+ .text : {
+ *(.text.unlikely .text.unlikely.*)
+ *(.text.startup .text.startup.*)
+ *(.text .text.*)
+ *(.gnu.linkonce.t.*)
+ } >ram :text
+
+ /* RAM SECTION
+ *
+ * The following sections contain data which is copied from read-only
+ * memory into a read-write-capable memory such as data tightly-integrated
+ * memory (DTIM) or another main memory, as well as the BSS, stack, and
+ * heap.
+ *
+ * You might notice that .data, .tdata, .tbss, .tbss_space, and .bss all
+ * have an apparently unnecessary ALIGN at their top. This is because
+ * the implementation of _start in Freedom Metal libgloss depends on the
+ * ADDR and LOADADDR being 8-byte aligned.
+ */
+
+ .data : ALIGN(8) {
+ *(.data .data.*)
+ *(.gnu.linkonce.d.*)
+ . = ALIGN(8);
+ PROVIDE( __global_pointer$ = . + 0x800 );
+ *(.sdata .sdata.* .sdata2.*)
+ *(.gnu.linkonce.s.*)
+ } >ram AT>ram :ram_init
+
+ .tdata : ALIGN(8) {
+ PROVIDE( __tls_base = . );
+ *(.tdata .tdata.* .gnu.linkonce.td.*)
+ } >ram AT>ram :tls :ram_init
+
+ PROVIDE( __tdata_source = LOADADDR(.tdata) );
+ PROVIDE( __tdata_size = SIZEOF(.tdata) );
+
+ PROVIDE( metal_segment_data_source_start = LOADADDR(.data) );
+ PROVIDE( metal_segment_data_target_start = ADDR(.data) );
+ PROVIDE( metal_segment_data_target_end = ADDR(.tdata) + SIZEOF(.tdata) );
+
+ .tbss : ALIGN(8) {
+ *(.tbss .tbss.* .gnu.linkonce.tb.*)
+ *(.tcommon .tcommon.*)
+ PROVIDE( __tls_end = . );
+ } >ram AT>ram :tls :ram
+ PROVIDE( __tbss_size = SIZEOF(.tbss) );
+ PROVIDE( __tls_size = __tls_end - __tls_base );
+
+ .tbss_space : ALIGN(8) {
+ . = . + __tbss_size;
+ } >ram :ram
+
+ .bss (NOLOAD): ALIGN(8) {
+ *(.sbss*)
+ *(.gnu.linkonce.sb.*)
+ *(.bss .bss.*)
+ *(.gnu.linkonce.b.*)
+ *(COMMON)
+ } >ram :ram
+
+ PROVIDE( metal_segment_bss_source_start = LOADADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_start = ADDR(.tbss) );
+ PROVIDE( metal_segment_bss_target_end = ADDR(.bss) + SIZEOF(.bss) );
+
+
+
+ .stack (NOLOAD) : ALIGN(16) {
+ PROVIDE(metal_segment_stack_begin = .);
+ . += __stack_size; /* Hart 0 */
+ PROVIDE( _sp = . );
+ PROVIDE(metal_segment_stack_end = .);
+ } >ram :ram
+
+ .heap (NOLOAD) : ALIGN(8) {
+ PROVIDE( __end = . );
+ PROVIDE( __heap_start = . );
+ PROVIDE( metal_segment_heap_target_start = . );
+ /* If __heap_max is defined, grow the heap to use the rest of RAM,
+ * otherwise set the heap size to __heap_size */
+ . = DEFINED(__heap_max) ? MIN( LENGTH(ram) - ( . - ORIGIN(ram)) , 0x10000000) : __heap_size;
+ PROVIDE( metal_segment_heap_target_end = . );
+ PROVIDE( _heap_end = . );
+ PROVIDE( __heap_end = . );
+ } >ram :ram
+
+ /* C++ exception handling information is
+ * not useful with our current runtime environment,
+ * and it consumes flash space. Discard it until
+ * we have something that can use it
+ */
+ /DISCARD/ : {
+ *(.eh_frame .eh_frame.*)
+ }
+} \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/settings.mk b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/settings.mk
new file mode 100644
index 000000000..a8ddd99f2
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/bsp/settings.mk
@@ -0,0 +1,13 @@
+# Copyright (C) 2020 SiFive Inc
+# SPDX-License-Identifier: Apache-2.0
+
+RISCV_ARCH = rv32imac
+RISCV_ABI = ilp32
+RISCV_CMODEL = medlow
+RISCV_SERIES = sifive-3-series
+
+TARGET_TAGS = board jlink
+TARGET_DHRY_ITERS = 20000000
+TARGET_CORE_ITERS = 5000
+TARGET_FREERTOS_WAIT_MS = 1000
+TARGET_INTR_WAIT_CYCLE = 0 \ No newline at end of file
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.clang-format b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.clang-format
new file mode 100644
index 000000000..f9d627fe6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.clang-format
@@ -0,0 +1,5 @@
+BasedOnStyle: LLVM
+Language: Cpp
+
+IndentWidth: 4
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.travis.yml b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.travis.yml
new file mode 100644
index 000000000..04ce26935
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/.travis.yml
@@ -0,0 +1,35 @@
+sudo: required
+
+# Travis doesn't provide a wide variety of host environments to run on, so we
+# rely on Docker to provide these instead.
+services:
+ - docker
+
+# It is not really needed, other than for showing correct language tag in
+# Travis CI build log.
+language: c
+
+# The matrix of targets that we're interested in.
+env:
+ - HOST="ubuntu:16.04"
+
+# Before running the install phase we need to set up docker container that runs
+# the target machine.
+before_install:
+ - docker run -d --name host -v $(pwd):/travis $HOST tail -f /dev/null
+ - docker ps
+
+# Update the container and install dependencies
+install:
+ - docker exec -t host bash -c "yes | apt-get update"
+ - docker exec -t host bash -c "yes | apt-get upgrade"
+ - docker exec -t host bash -c "yes | apt-get install git clang-format-6.0"
+ - sudo curl -L -o /tmp/wake.deb https://github.com/sifive/wake/releases/download/v0.19.0/ubuntu-16-04-wake_0.19.0-1_amd64.deb
+ - sudo apt install /tmp/wake.deb
+
+# Here's where we actually run the test.
+script:
+# Check source code formatting
+ - docker exec -t host bash -c "cd /travis && ./scripts/check-format"
+# Run dummy Wake program in order to run Wake type checker.
+ - wake --init . && wake -x Unit
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Doxyfile b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Doxyfile
new file mode 100644
index 000000000..22c8f7845
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Doxyfile
@@ -0,0 +1,2537 @@
+# Doxyfile 1.8.15
+
+# This file describes the settings to be used by the documentation system
+# doxygen (www.doxygen.org) for a project.
+#
+# All text after a double hash (##) is considered a comment and is placed in
+# front of the TAG it is preceding.
+#
+# All text after a single hash (#) is considered a comment and will be ignored.
+# The format is:
+# TAG = value [value, ...]
+# For lists, items can also be appended using:
+# TAG += value [value, ...]
+# Values that contain spaces should be placed between quotes (\" \").
+
+#---------------------------------------------------------------------------
+# Project related configuration options
+#---------------------------------------------------------------------------
+
+# This tag specifies the encoding used for all characters in the configuration
+# file that follow. The default is UTF-8 which is also the encoding used for all
+# text before the first occurrence of this tag. Doxygen uses libiconv (or the
+# iconv built into libc) for the transcoding. See
+# https://www.gnu.org/software/libiconv/ for the list of possible encodings.
+# The default value is: UTF-8.
+
+DOXYFILE_ENCODING = UTF-8
+
+# The PROJECT_NAME tag is a single word (or a sequence of words surrounded by
+# double-quotes, unless you are using Doxywizard) that should identify the
+# project for which the documentation is generated. This name is used in the
+# title of most generated pages and in a few other places.
+# The default value is: My Project.
+
+PROJECT_NAME = "Freedom Metal"
+
+# The PROJECT_NUMBER tag can be used to enter a project or revision number. This
+# could be handy for archiving the generated documentation or if some version
+# control system is used.
+
+PROJECT_NUMBER =
+
+# Using the PROJECT_BRIEF tag one can provide an optional one line description
+# for a project that appears at the top of each page and should give viewer a
+# quick idea about the purpose of the project. Keep the description short.
+
+PROJECT_BRIEF = "Bare Metal Compatibility Library for the Freedom Platform"
+
+# With the PROJECT_LOGO tag one can specify a logo or an icon that is included
+# in the documentation. The maximum height of the logo should not exceed 55
+# pixels and the maximum width should not exceed 200 pixels. Doxygen will copy
+# the logo to the output directory.
+
+PROJECT_LOGO =
+
+# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) path
+# into which the generated documentation will be written. If a relative path is
+# entered, it will be relative to the location where doxygen was started. If
+# left blank the current directory will be used.
+
+OUTPUT_DIRECTORY = "doc"
+
+# If the CREATE_SUBDIRS tag is set to YES then doxygen will create 4096 sub-
+# directories (in 2 levels) under the output directory of each output format and
+# will distribute the generated files over these directories. Enabling this
+# option can be useful when feeding doxygen a huge amount of source files, where
+# putting all generated files in the same directory would otherwise causes
+# performance problems for the file system.
+# The default value is: NO.
+
+CREATE_SUBDIRS = NO
+
+# If the ALLOW_UNICODE_NAMES tag is set to YES, doxygen will allow non-ASCII
+# characters to appear in the names of generated files. If set to NO, non-ASCII
+# characters will be escaped, for example _xE3_x81_x84 will be used for Unicode
+# U+3044.
+# The default value is: NO.
+
+ALLOW_UNICODE_NAMES = NO
+
+# The OUTPUT_LANGUAGE tag is used to specify the language in which all
+# documentation generated by doxygen is written. Doxygen will use this
+# information to generate all constant output in the proper language.
+# Possible values are: Afrikaans, Arabic, Armenian, Brazilian, Catalan, Chinese,
+# Chinese-Traditional, Croatian, Czech, Danish, Dutch, English (United States),
+# Esperanto, Farsi (Persian), Finnish, French, German, Greek, Hungarian,
+# Indonesian, Italian, Japanese, Japanese-en (Japanese with English messages),
+# Korean, Korean-en (Korean with English messages), Latvian, Lithuanian,
+# Macedonian, Norwegian, Persian (Farsi), Polish, Portuguese, Romanian, Russian,
+# Serbian, Serbian-Cyrillic, Slovak, Slovene, Spanish, Swedish, Turkish,
+# Ukrainian and Vietnamese.
+# The default value is: English.
+
+OUTPUT_LANGUAGE = English
+
+# The OUTPUT_TEXT_DIRECTION tag is used to specify the direction in which all
+# documentation generated by doxygen is written. Doxygen will use this
+# information to generate all generated output in the proper direction.
+# Possible values are: None, LTR, RTL and Context.
+# The default value is: None.
+
+OUTPUT_TEXT_DIRECTION = None
+
+# If the BRIEF_MEMBER_DESC tag is set to YES, doxygen will include brief member
+# descriptions after the members that are listed in the file and class
+# documentation (similar to Javadoc). Set to NO to disable this.
+# The default value is: YES.
+
+BRIEF_MEMBER_DESC = YES
+
+# If the REPEAT_BRIEF tag is set to YES, doxygen will prepend the brief
+# description of a member or function before the detailed description
+#
+# Note: If both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the
+# brief descriptions will be completely suppressed.
+# The default value is: YES.
+
+REPEAT_BRIEF = YES
+
+# This tag implements a quasi-intelligent brief description abbreviator that is
+# used to form the text in various listings. Each string in this list, if found
+# as the leading text of the brief description, will be stripped from the text
+# and the result, after processing the whole list, is used as the annotated
+# text. Otherwise, the brief description is used as-is. If left blank, the
+# following values are used ($name is automatically replaced with the name of
+# the entity):The $name class, The $name widget, The $name file, is, provides,
+# specifies, contains, represents, a, an and the.
+
+ABBREVIATE_BRIEF = "The $name class" \
+ "The $name widget" \
+ "The $name file" \
+ is \
+ provides \
+ specifies \
+ contains \
+ represents \
+ a \
+ an \
+ the
+
+# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then
+# doxygen will generate a detailed section even if there is only a brief
+# description.
+# The default value is: NO.
+
+ALWAYS_DETAILED_SEC = NO
+
+# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all
+# inherited members of a class in the documentation of that class as if those
+# members were ordinary class members. Constructors, destructors and assignment
+# operators of the base classes will not be shown.
+# The default value is: NO.
+
+INLINE_INHERITED_MEMB = NO
+
+# If the FULL_PATH_NAMES tag is set to YES, doxygen will prepend the full path
+# before files name in the file list and in the header files. If set to NO the
+# shortest path that makes the file name unique will be used
+# The default value is: YES.
+
+FULL_PATH_NAMES = YES
+
+# The STRIP_FROM_PATH tag can be used to strip a user-defined part of the path.
+# Stripping is only done if one of the specified strings matches the left-hand
+# part of the path. The tag can be used to show relative paths in the file list.
+# If left blank the directory from which doxygen is run is used as the path to
+# strip.
+#
+# Note that you can specify absolute paths here, but also relative paths, which
+# will be relative from the directory where doxygen is started.
+# This tag requires that the tag FULL_PATH_NAMES is set to YES.
+
+STRIP_FROM_PATH =
+
+# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of the
+# path mentioned in the documentation of a class, which tells the reader which
+# header file to include in order to use a class. If left blank only the name of
+# the header file containing the class definition is used. Otherwise one should
+# specify the list of include paths that are normally passed to the compiler
+# using the -I flag.
+
+STRIP_FROM_INC_PATH =
+
+# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter (but
+# less readable) file names. This can be useful is your file systems doesn't
+# support long names like on DOS, Mac, or CD-ROM.
+# The default value is: NO.
+
+SHORT_NAMES = NO
+
+# If the JAVADOC_AUTOBRIEF tag is set to YES then doxygen will interpret the
+# first line (until the first dot) of a Javadoc-style comment as the brief
+# description. If set to NO, the Javadoc-style will behave just like regular Qt-
+# style comments (thus requiring an explicit @brief command for a brief
+# description.)
+# The default value is: NO.
+
+JAVADOC_AUTOBRIEF = NO
+
+# If the QT_AUTOBRIEF tag is set to YES then doxygen will interpret the first
+# line (until the first dot) of a Qt-style comment as the brief description. If
+# set to NO, the Qt-style will behave just like regular Qt-style comments (thus
+# requiring an explicit \brief command for a brief description.)
+# The default value is: NO.
+
+QT_AUTOBRIEF = NO
+
+# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make doxygen treat a
+# multi-line C++ special comment block (i.e. a block of //! or /// comments) as
+# a brief description. This used to be the default behavior. The new default is
+# to treat a multi-line C++ comment block as a detailed description. Set this
+# tag to YES if you prefer the old behavior instead.
+#
+# Note that setting this tag to YES also means that rational rose comments are
+# not recognized any more.
+# The default value is: NO.
+
+MULTILINE_CPP_IS_BRIEF = NO
+
+# If the INHERIT_DOCS tag is set to YES then an undocumented member inherits the
+# documentation from any documented member that it re-implements.
+# The default value is: YES.
+
+INHERIT_DOCS = YES
+
+# If the SEPARATE_MEMBER_PAGES tag is set to YES then doxygen will produce a new
+# page for each member. If set to NO, the documentation of a member will be part
+# of the file/class/namespace that contains it.
+# The default value is: NO.
+
+SEPARATE_MEMBER_PAGES = NO
+
+# The TAB_SIZE tag can be used to set the number of spaces in a tab. Doxygen
+# uses this value to replace tabs by spaces in code fragments.
+# Minimum value: 1, maximum value: 16, default value: 4.
+
+TAB_SIZE = 4
+
+# This tag can be used to specify a number of aliases that act as commands in
+# the documentation. An alias has the form:
+# name=value
+# For example adding
+# "sideeffect=@par Side Effects:\n"
+# will allow you to put the command \sideeffect (or @sideeffect) in the
+# documentation, which will result in a user-defined paragraph with heading
+# "Side Effects:". You can put \n's in the value part of an alias to insert
+# newlines (in the resulting output). You can put ^^ in the value part of an
+# alias to insert a newline as if a physical newline was in the original file.
+# When you need a literal { or } or , in the value part of an alias you have to
+# escape them by means of a backslash (\), this can lead to conflicts with the
+# commands \{ and \} for these it is advised to use the version @{ and @} or use
+# a double escape (\\{ and \\})
+
+ALIASES =
+
+# This tag can be used to specify a number of word-keyword mappings (TCL only).
+# A mapping has the form "name=value". For example adding "class=itcl::class"
+# will allow you to use the command class in the itcl::class meaning.
+
+TCL_SUBST =
+
+# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources
+# only. Doxygen will then generate output that is more tailored for C. For
+# instance, some of the names that are used will be different. The list of all
+# members will be omitted, etc.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_FOR_C = NO
+
+# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java or
+# Python sources only. Doxygen will then generate output that is more tailored
+# for that language. For instance, namespaces will be presented as packages,
+# qualified scopes will look different, etc.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_JAVA = NO
+
+# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran
+# sources. Doxygen will then generate output that is tailored for Fortran.
+# The default value is: NO.
+
+OPTIMIZE_FOR_FORTRAN = NO
+
+# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL
+# sources. Doxygen will then generate output that is tailored for VHDL.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_VHDL = NO
+
+# Set the OPTIMIZE_OUTPUT_SLICE tag to YES if your project consists of Slice
+# sources only. Doxygen will then generate output that is more tailored for that
+# language. For instance, namespaces will be presented as modules, types will be
+# separated into more groups, etc.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_SLICE = NO
+
+# Doxygen selects the parser to use depending on the extension of the files it
+# parses. With this tag you can assign which parser to use for a given
+# extension. Doxygen has a built-in mapping, but you can override or extend it
+# using this tag. The format is ext=language, where ext is a file extension, and
+# language is one of the parsers supported by doxygen: IDL, Java, Javascript,
+# Csharp (C#), C, C++, D, PHP, md (Markdown), Objective-C, Python, Slice,
+# Fortran (fixed format Fortran: FortranFixed, free formatted Fortran:
+# FortranFree, unknown formatted Fortran: Fortran. In the later case the parser
+# tries to guess whether the code is fixed or free formatted code, this is the
+# default for Fortran type files), VHDL, tcl. For instance to make doxygen treat
+# .inc files as Fortran files (default is PHP), and .f files as C (default is
+# Fortran), use: inc=Fortran f=C.
+#
+# Note: For files without extension you can use no_extension as a placeholder.
+#
+# Note that for custom extensions you also need to set FILE_PATTERNS otherwise
+# the files are not read by doxygen.
+
+EXTENSION_MAPPING =
+
+# If the MARKDOWN_SUPPORT tag is enabled then doxygen pre-processes all comments
+# according to the Markdown format, which allows for more readable
+# documentation. See https://daringfireball.net/projects/markdown/ for details.
+# The output of markdown processing is further processed by doxygen, so you can
+# mix doxygen, HTML, and XML commands with Markdown formatting. Disable only in
+# case of backward compatibilities issues.
+# The default value is: YES.
+
+MARKDOWN_SUPPORT = YES
+
+# When the TOC_INCLUDE_HEADINGS tag is set to a non-zero value, all headings up
+# to that level are automatically included in the table of contents, even if
+# they do not have an id attribute.
+# Note: This feature currently applies only to Markdown headings.
+# Minimum value: 0, maximum value: 99, default value: 0.
+# This tag requires that the tag MARKDOWN_SUPPORT is set to YES.
+
+TOC_INCLUDE_HEADINGS = 0
+
+# When enabled doxygen tries to link words that correspond to documented
+# classes, or namespaces to their corresponding documentation. Such a link can
+# be prevented in individual cases by putting a % sign in front of the word or
+# globally by setting AUTOLINK_SUPPORT to NO.
+# The default value is: YES.
+
+AUTOLINK_SUPPORT = YES
+
+# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want
+# to include (a tag file for) the STL sources as input, then you should set this
+# tag to YES in order to let doxygen match functions declarations and
+# definitions whose arguments contain STL classes (e.g. func(std::string);
+# versus func(std::string) {}). This also make the inheritance and collaboration
+# diagrams that involve STL classes more complete and accurate.
+# The default value is: NO.
+
+BUILTIN_STL_SUPPORT = NO
+
+# If you use Microsoft's C++/CLI language, you should set this option to YES to
+# enable parsing support.
+# The default value is: NO.
+
+CPP_CLI_SUPPORT = NO
+
+# Set the SIP_SUPPORT tag to YES if your project consists of sip (see:
+# https://www.riverbankcomputing.com/software/sip/intro) sources only. Doxygen
+# will parse them like normal C++ but will assume all classes use public instead
+# of private inheritance when no explicit protection keyword is present.
+# The default value is: NO.
+
+SIP_SUPPORT = NO
+
+# For Microsoft's IDL there are propget and propput attributes to indicate
+# getter and setter methods for a property. Setting this option to YES will make
+# doxygen to replace the get and set methods by a property in the documentation.
+# This will only work if the methods are indeed getting or setting a simple
+# type. If this is not the case, or you want to show the methods anyway, you
+# should set this option to NO.
+# The default value is: YES.
+
+IDL_PROPERTY_SUPPORT = YES
+
+# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC
+# tag is set to YES then doxygen will reuse the documentation of the first
+# member in the group (if any) for the other members of the group. By default
+# all members of a group must be documented explicitly.
+# The default value is: NO.
+
+DISTRIBUTE_GROUP_DOC = NO
+
+# If one adds a struct or class to a group and this option is enabled, then also
+# any nested class or struct is added to the same group. By default this option
+# is disabled and one has to add nested compounds explicitly via \ingroup.
+# The default value is: NO.
+
+GROUP_NESTED_COMPOUNDS = NO
+
+# Set the SUBGROUPING tag to YES to allow class member groups of the same type
+# (for instance a group of public functions) to be put as a subgroup of that
+# type (e.g. under the Public Functions section). Set it to NO to prevent
+# subgrouping. Alternatively, this can be done per class using the
+# \nosubgrouping command.
+# The default value is: YES.
+
+SUBGROUPING = YES
+
+# When the INLINE_GROUPED_CLASSES tag is set to YES, classes, structs and unions
+# are shown inside the group in which they are included (e.g. using \ingroup)
+# instead of on a separate page (for HTML and Man pages) or section (for LaTeX
+# and RTF).
+#
+# Note that this feature does not work in combination with
+# SEPARATE_MEMBER_PAGES.
+# The default value is: NO.
+
+INLINE_GROUPED_CLASSES = NO
+
+# When the INLINE_SIMPLE_STRUCTS tag is set to YES, structs, classes, and unions
+# with only public data fields or simple typedef fields will be shown inline in
+# the documentation of the scope in which they are defined (i.e. file,
+# namespace, or group documentation), provided this scope is documented. If set
+# to NO, structs, classes, and unions are shown on a separate page (for HTML and
+# Man pages) or section (for LaTeX and RTF).
+# The default value is: NO.
+
+INLINE_SIMPLE_STRUCTS = NO
+
+# When TYPEDEF_HIDES_STRUCT tag is enabled, a typedef of a struct, union, or
+# enum is documented as struct, union, or enum with the name of the typedef. So
+# typedef struct TypeS {} TypeT, will appear in the documentation as a struct
+# with name TypeT. When disabled the typedef will appear as a member of a file,
+# namespace, or class. And the struct will be named TypeS. This can typically be
+# useful for C code in case the coding convention dictates that all compound
+# types are typedef'ed and only the typedef is referenced, never the tag name.
+# The default value is: NO.
+
+TYPEDEF_HIDES_STRUCT = NO
+
+# The size of the symbol lookup cache can be set using LOOKUP_CACHE_SIZE. This
+# cache is used to resolve symbols given their name and scope. Since this can be
+# an expensive process and often the same symbol appears multiple times in the
+# code, doxygen keeps a cache of pre-resolved symbols. If the cache is too small
+# doxygen will become slower. If the cache is too large, memory is wasted. The
+# cache size is given by this formula: 2^(16+LOOKUP_CACHE_SIZE). The valid range
+# is 0..9, the default is 0, corresponding to a cache size of 2^16=65536
+# symbols. At the end of a run doxygen will report the cache usage and suggest
+# the optimal cache size from a speed point of view.
+# Minimum value: 0, maximum value: 9, default value: 0.
+
+LOOKUP_CACHE_SIZE = 0
+
+#---------------------------------------------------------------------------
+# Build related configuration options
+#---------------------------------------------------------------------------
+
+# If the EXTRACT_ALL tag is set to YES, doxygen will assume all entities in
+# documentation are documented, even if no documentation was available. Private
+# class members and static file members will be hidden unless the
+# EXTRACT_PRIVATE respectively EXTRACT_STATIC tags are set to YES.
+# Note: This will also disable the warnings about undocumented members that are
+# normally produced when WARNINGS is set to YES.
+# The default value is: NO.
+
+EXTRACT_ALL = NO
+
+# If the EXTRACT_PRIVATE tag is set to YES, all private members of a class will
+# be included in the documentation.
+# The default value is: NO.
+
+EXTRACT_PRIVATE = NO
+
+# If the EXTRACT_PACKAGE tag is set to YES, all members with package or internal
+# scope will be included in the documentation.
+# The default value is: NO.
+
+EXTRACT_PACKAGE = NO
+
+# If the EXTRACT_STATIC tag is set to YES, all static members of a file will be
+# included in the documentation.
+# The default value is: NO.
+
+EXTRACT_STATIC = NO
+
+# If the EXTRACT_LOCAL_CLASSES tag is set to YES, classes (and structs) defined
+# locally in source files will be included in the documentation. If set to NO,
+# only classes defined in header files are included. Does not have any effect
+# for Java sources.
+# The default value is: YES.
+
+EXTRACT_LOCAL_CLASSES = YES
+
+# This flag is only useful for Objective-C code. If set to YES, local methods,
+# which are defined in the implementation section but not in the interface are
+# included in the documentation. If set to NO, only methods in the interface are
+# included.
+# The default value is: NO.
+
+EXTRACT_LOCAL_METHODS = NO
+
+# If this flag is set to YES, the members of anonymous namespaces will be
+# extracted and appear in the documentation as a namespace called
+# 'anonymous_namespace{file}', where file will be replaced with the base name of
+# the file that contains the anonymous namespace. By default anonymous namespace
+# are hidden.
+# The default value is: NO.
+
+EXTRACT_ANON_NSPACES = NO
+
+# If the HIDE_UNDOC_MEMBERS tag is set to YES, doxygen will hide all
+# undocumented members inside documented classes or files. If set to NO these
+# members will be included in the various overviews, but no documentation
+# section is generated. This option has no effect if EXTRACT_ALL is enabled.
+# The default value is: NO.
+
+HIDE_UNDOC_MEMBERS = NO
+
+# If the HIDE_UNDOC_CLASSES tag is set to YES, doxygen will hide all
+# undocumented classes that are normally visible in the class hierarchy. If set
+# to NO, these classes will be included in the various overviews. This option
+# has no effect if EXTRACT_ALL is enabled.
+# The default value is: NO.
+
+HIDE_UNDOC_CLASSES = NO
+
+# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, doxygen will hide all friend
+# (class|struct|union) declarations. If set to NO, these declarations will be
+# included in the documentation.
+# The default value is: NO.
+
+HIDE_FRIEND_COMPOUNDS = NO
+
+# If the HIDE_IN_BODY_DOCS tag is set to YES, doxygen will hide any
+# documentation blocks found inside the body of a function. If set to NO, these
+# blocks will be appended to the function's detailed documentation block.
+# The default value is: NO.
+
+HIDE_IN_BODY_DOCS = NO
+
+# The INTERNAL_DOCS tag determines if documentation that is typed after a
+# \internal command is included. If the tag is set to NO then the documentation
+# will be excluded. Set it to YES to include the internal documentation.
+# The default value is: NO.
+
+INTERNAL_DOCS = NO
+
+# If the CASE_SENSE_NAMES tag is set to NO then doxygen will only generate file
+# names in lower-case letters. If set to YES, upper-case letters are also
+# allowed. This is useful if you have classes or files whose names only differ
+# in case and if your file system supports case sensitive file names. Windows
+# and Mac users are advised to set this option to NO.
+# The default value is: system dependent.
+
+CASE_SENSE_NAMES = NO
+
+# If the HIDE_SCOPE_NAMES tag is set to NO then doxygen will show members with
+# their full class and namespace scopes in the documentation. If set to YES, the
+# scope will be hidden.
+# The default value is: NO.
+
+HIDE_SCOPE_NAMES = NO
+
+# If the HIDE_COMPOUND_REFERENCE tag is set to NO (default) then doxygen will
+# append additional text to a page's title, such as Class Reference. If set to
+# YES the compound reference will be hidden.
+# The default value is: NO.
+
+HIDE_COMPOUND_REFERENCE= NO
+
+# If the SHOW_INCLUDE_FILES tag is set to YES then doxygen will put a list of
+# the files that are included by a file in the documentation of that file.
+# The default value is: YES.
+
+SHOW_INCLUDE_FILES = YES
+
+# If the SHOW_GROUPED_MEMB_INC tag is set to YES then Doxygen will add for each
+# grouped member an include statement to the documentation, telling the reader
+# which file to include in order to use the member.
+# The default value is: NO.
+
+SHOW_GROUPED_MEMB_INC = NO
+
+# If the FORCE_LOCAL_INCLUDES tag is set to YES then doxygen will list include
+# files with double quotes in the documentation rather than with sharp brackets.
+# The default value is: NO.
+
+FORCE_LOCAL_INCLUDES = NO
+
+# If the INLINE_INFO tag is set to YES then a tag [inline] is inserted in the
+# documentation for inline members.
+# The default value is: YES.
+
+INLINE_INFO = YES
+
+# If the SORT_MEMBER_DOCS tag is set to YES then doxygen will sort the
+# (detailed) documentation of file and class members alphabetically by member
+# name. If set to NO, the members will appear in declaration order.
+# The default value is: YES.
+
+SORT_MEMBER_DOCS = YES
+
+# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the brief
+# descriptions of file, namespace and class members alphabetically by member
+# name. If set to NO, the members will appear in declaration order. Note that
+# this will also influence the order of the classes in the class list.
+# The default value is: NO.
+
+SORT_BRIEF_DOCS = NO
+
+# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the
+# (brief and detailed) documentation of class members so that constructors and
+# destructors are listed first. If set to NO the constructors will appear in the
+# respective orders defined by SORT_BRIEF_DOCS and SORT_MEMBER_DOCS.
+# Note: If SORT_BRIEF_DOCS is set to NO this option is ignored for sorting brief
+# member documentation.
+# Note: If SORT_MEMBER_DOCS is set to NO this option is ignored for sorting
+# detailed member documentation.
+# The default value is: NO.
+
+SORT_MEMBERS_CTORS_1ST = NO
+
+# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the hierarchy
+# of group names into alphabetical order. If set to NO the group names will
+# appear in their defined order.
+# The default value is: NO.
+
+SORT_GROUP_NAMES = NO
+
+# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be sorted by
+# fully-qualified names, including namespaces. If set to NO, the class list will
+# be sorted only by class name, not including the namespace part.
+# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES.
+# Note: This option applies only to the class list, not to the alphabetical
+# list.
+# The default value is: NO.
+
+SORT_BY_SCOPE_NAME = NO
+
+# If the STRICT_PROTO_MATCHING option is enabled and doxygen fails to do proper
+# type resolution of all parameters of a function it will reject a match between
+# the prototype and the implementation of a member function even if there is
+# only one candidate or it is obvious which candidate to choose by doing a
+# simple string match. By disabling STRICT_PROTO_MATCHING doxygen will still
+# accept a match between prototype and implementation in such cases.
+# The default value is: NO.
+
+STRICT_PROTO_MATCHING = NO
+
+# The GENERATE_TODOLIST tag can be used to enable (YES) or disable (NO) the todo
+# list. This list is created by putting \todo commands in the documentation.
+# The default value is: YES.
+
+GENERATE_TODOLIST = YES
+
+# The GENERATE_TESTLIST tag can be used to enable (YES) or disable (NO) the test
+# list. This list is created by putting \test commands in the documentation.
+# The default value is: YES.
+
+GENERATE_TESTLIST = YES
+
+# The GENERATE_BUGLIST tag can be used to enable (YES) or disable (NO) the bug
+# list. This list is created by putting \bug commands in the documentation.
+# The default value is: YES.
+
+GENERATE_BUGLIST = YES
+
+# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or disable (NO)
+# the deprecated list. This list is created by putting \deprecated commands in
+# the documentation.
+# The default value is: YES.
+
+GENERATE_DEPRECATEDLIST= YES
+
+# The ENABLED_SECTIONS tag can be used to enable conditional documentation
+# sections, marked by \if <section_label> ... \endif and \cond <section_label>
+# ... \endcond blocks.
+
+ENABLED_SECTIONS =
+
+# The MAX_INITIALIZER_LINES tag determines the maximum number of lines that the
+# initial value of a variable or macro / define can have for it to appear in the
+# documentation. If the initializer consists of more lines than specified here
+# it will be hidden. Use a value of 0 to hide initializers completely. The
+# appearance of the value of individual variables and macros / defines can be
+# controlled using \showinitializer or \hideinitializer command in the
+# documentation regardless of this setting.
+# Minimum value: 0, maximum value: 10000, default value: 30.
+
+MAX_INITIALIZER_LINES = 30
+
+# Set the SHOW_USED_FILES tag to NO to disable the list of files generated at
+# the bottom of the documentation of classes and structs. If set to YES, the
+# list will mention the files that were used to generate the documentation.
+# The default value is: YES.
+
+SHOW_USED_FILES = YES
+
+# Set the SHOW_FILES tag to NO to disable the generation of the Files page. This
+# will remove the Files entry from the Quick Index and from the Folder Tree View
+# (if specified).
+# The default value is: YES.
+
+SHOW_FILES = YES
+
+# Set the SHOW_NAMESPACES tag to NO to disable the generation of the Namespaces
+# page. This will remove the Namespaces entry from the Quick Index and from the
+# Folder Tree View (if specified).
+# The default value is: YES.
+
+SHOW_NAMESPACES = YES
+
+# The FILE_VERSION_FILTER tag can be used to specify a program or script that
+# doxygen should invoke to get the current version for each file (typically from
+# the version control system). Doxygen will invoke the program by executing (via
+# popen()) the command command input-file, where command is the value of the
+# FILE_VERSION_FILTER tag, and input-file is the name of an input file provided
+# by doxygen. Whatever the program writes to standard output is used as the file
+# version. For an example see the documentation.
+
+FILE_VERSION_FILTER =
+
+# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed
+# by doxygen. The layout file controls the global structure of the generated
+# output files in an output format independent way. To create the layout file
+# that represents doxygen's defaults, run doxygen with the -l option. You can
+# optionally specify a file name after the option, if omitted DoxygenLayout.xml
+# will be used as the name of the layout file.
+#
+# Note that if you run doxygen from a directory containing a file called
+# DoxygenLayout.xml, doxygen will parse it automatically even if the LAYOUT_FILE
+# tag is left empty.
+
+LAYOUT_FILE =
+
+# The CITE_BIB_FILES tag can be used to specify one or more bib files containing
+# the reference definitions. This must be a list of .bib files. The .bib
+# extension is automatically appended if omitted. This requires the bibtex tool
+# to be installed. See also https://en.wikipedia.org/wiki/BibTeX for more info.
+# For LaTeX the style of the bibliography can be controlled using
+# LATEX_BIB_STYLE. To use this feature you need bibtex and perl available in the
+# search path. See also \cite for info how to create references.
+
+CITE_BIB_FILES =
+
+#---------------------------------------------------------------------------
+# Configuration options related to warning and progress messages
+#---------------------------------------------------------------------------
+
+# The QUIET tag can be used to turn on/off the messages that are generated to
+# standard output by doxygen. If QUIET is set to YES this implies that the
+# messages are off.
+# The default value is: NO.
+
+QUIET = NO
+
+# The WARNINGS tag can be used to turn on/off the warning messages that are
+# generated to standard error (stderr) by doxygen. If WARNINGS is set to YES
+# this implies that the warnings are on.
+#
+# Tip: Turn warnings on while writing the documentation.
+# The default value is: YES.
+
+WARNINGS = YES
+
+# If the WARN_IF_UNDOCUMENTED tag is set to YES then doxygen will generate
+# warnings for undocumented members. If EXTRACT_ALL is set to YES then this flag
+# will automatically be disabled.
+# The default value is: YES.
+
+WARN_IF_UNDOCUMENTED = YES
+
+# If the WARN_IF_DOC_ERROR tag is set to YES, doxygen will generate warnings for
+# potential errors in the documentation, such as not documenting some parameters
+# in a documented function, or documenting parameters that don't exist or using
+# markup commands wrongly.
+# The default value is: YES.
+
+WARN_IF_DOC_ERROR = YES
+
+# This WARN_NO_PARAMDOC option can be enabled to get warnings for functions that
+# are documented, but have no documentation for their parameters or return
+# value. If set to NO, doxygen will only warn about wrong or incomplete
+# parameter documentation, but not about the absence of documentation. If
+# EXTRACT_ALL is set to YES then this flag will automatically be disabled.
+# The default value is: NO.
+
+WARN_NO_PARAMDOC = NO
+
+# If the WARN_AS_ERROR tag is set to YES then doxygen will immediately stop when
+# a warning is encountered.
+# The default value is: NO.
+
+WARN_AS_ERROR = NO
+
+# The WARN_FORMAT tag determines the format of the warning messages that doxygen
+# can produce. The string should contain the $file, $line, and $text tags, which
+# will be replaced by the file and line number from which the warning originated
+# and the warning text. Optionally the format may contain $version, which will
+# be replaced by the version of the file (if it could be obtained via
+# FILE_VERSION_FILTER)
+# The default value is: $file:$line: $text.
+
+WARN_FORMAT = "$file:$line: $text"
+
+# The WARN_LOGFILE tag can be used to specify a file to which warning and error
+# messages should be written. If left blank the output is written to standard
+# error (stderr).
+
+WARN_LOGFILE =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the input files
+#---------------------------------------------------------------------------
+
+# The INPUT tag is used to specify the files and/or directories that contain
+# documented source files. You may enter file names like myfile.cpp or
+# directories like /usr/src/myproject. Separate the files or directories with
+# spaces. See also FILE_PATTERNS and EXTENSION_MAPPING
+# Note: If this tag is empty the current directory is searched.
+
+INPUT = metal
+
+# This tag can be used to specify the character encoding of the source files
+# that doxygen parses. Internally doxygen uses the UTF-8 encoding. Doxygen uses
+# libiconv (or the iconv built into libc) for the transcoding. See the libiconv
+# documentation (see: https://www.gnu.org/software/libiconv/) for the list of
+# possible encodings.
+# The default value is: UTF-8.
+
+INPUT_ENCODING = UTF-8
+
+# If the value of the INPUT tag contains directories, you can use the
+# FILE_PATTERNS tag to specify one or more wildcard patterns (like *.cpp and
+# *.h) to filter out the source-files in the directories.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# read by doxygen.
+#
+# If left blank the following patterns are tested:*.c, *.cc, *.cxx, *.cpp,
+# *.c++, *.java, *.ii, *.ixx, *.ipp, *.i++, *.inl, *.idl, *.ddl, *.odl, *.h,
+# *.hh, *.hxx, *.hpp, *.h++, *.cs, *.d, *.php, *.php4, *.php5, *.phtml, *.inc,
+# *.m, *.markdown, *.md, *.mm, *.dox, *.py, *.pyw, *.f90, *.f95, *.f03, *.f08,
+# *.f, *.for, *.tcl, *.vhd, *.vhdl, *.ucf, *.qsf and *.ice.
+
+FILE_PATTERNS = *.c \
+ *.cc \
+ *.cxx \
+ *.cpp \
+ *.c++ \
+ *.java \
+ *.ii \
+ *.ixx \
+ *.ipp \
+ *.i++ \
+ *.inl \
+ *.idl \
+ *.ddl \
+ *.odl \
+ *.h \
+ *.hh \
+ *.hxx \
+ *.hpp \
+ *.h++ \
+ *.cs \
+ *.d \
+ *.php \
+ *.php4 \
+ *.php5 \
+ *.phtml \
+ *.inc \
+ *.m \
+ *.markdown \
+ *.md \
+ *.mm \
+ *.dox \
+ *.py \
+ *.pyw \
+ *.f90 \
+ *.f95 \
+ *.f03 \
+ *.f08 \
+ *.f \
+ *.for \
+ *.tcl \
+ *.vhd \
+ *.vhdl \
+ *.ucf \
+ *.qsf \
+ *.ice
+
+# The RECURSIVE tag can be used to specify whether or not subdirectories should
+# be searched for input files as well.
+# The default value is: NO.
+
+RECURSIVE = NO
+
+# The EXCLUDE tag can be used to specify files and/or directories that should be
+# excluded from the INPUT source files. This way you can easily exclude a
+# subdirectory from a directory tree whose root is specified with the INPUT tag.
+#
+# Note that relative paths are relative to the directory from which doxygen is
+# run.
+
+EXCLUDE = metal/compiler.h metal/io.h metal/machine.h
+
+# The EXCLUDE_SYMLINKS tag can be used to select whether or not files or
+# directories that are symbolic links (a Unix file system feature) are excluded
+# from the input.
+# The default value is: NO.
+
+EXCLUDE_SYMLINKS = NO
+
+# If the value of the INPUT tag contains directories, you can use the
+# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude
+# certain files from those directories.
+#
+# Note that the wildcards are matched against the file with absolute path, so to
+# exclude all test directories for example use the pattern */test/*
+
+EXCLUDE_PATTERNS =
+
+# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names
+# (namespaces, classes, functions, etc.) that should be excluded from the
+# output. The symbol name can be a fully qualified name, a word, or if the
+# wildcard * is used, a substring. Examples: ANamespace, AClass,
+# AClass::ANamespace, ANamespace::*Test
+#
+# Note that the wildcards are matched against the file with absolute path, so to
+# exclude all test directories use the pattern */test/*
+
+EXCLUDE_SYMBOLS = _* __* *vtable
+
+# The EXAMPLE_PATH tag can be used to specify one or more files or directories
+# that contain example code fragments that are included (see the \include
+# command).
+
+EXAMPLE_PATH =
+
+# If the value of the EXAMPLE_PATH tag contains directories, you can use the
+# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp and
+# *.h) to filter out the source-files in the directories. If left blank all
+# files are included.
+
+EXAMPLE_PATTERNS = *
+
+# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be
+# searched for input files to be used with the \include or \dontinclude commands
+# irrespective of the value of the RECURSIVE tag.
+# The default value is: NO.
+
+EXAMPLE_RECURSIVE = NO
+
+# The IMAGE_PATH tag can be used to specify one or more files or directories
+# that contain images that are to be included in the documentation (see the
+# \image command).
+
+IMAGE_PATH =
+
+# The INPUT_FILTER tag can be used to specify a program that doxygen should
+# invoke to filter for each input file. Doxygen will invoke the filter program
+# by executing (via popen()) the command:
+#
+# <filter> <input-file>
+#
+# where <filter> is the value of the INPUT_FILTER tag, and <input-file> is the
+# name of an input file. Doxygen will then use the output that the filter
+# program writes to standard output. If FILTER_PATTERNS is specified, this tag
+# will be ignored.
+#
+# Note that the filter must not add or remove lines; it is applied before the
+# code is scanned, but not when the output code is generated. If lines are added
+# or removed, the anchors will not be placed correctly.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# properly processed by doxygen.
+
+INPUT_FILTER =
+
+# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern
+# basis. Doxygen will compare the file name with each pattern and apply the
+# filter if there is a match. The filters are a list of the form: pattern=filter
+# (like *.cpp=my_cpp_filter). See INPUT_FILTER for further information on how
+# filters are used. If the FILTER_PATTERNS tag is empty or if none of the
+# patterns match the file name, INPUT_FILTER is applied.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# properly processed by doxygen.
+
+FILTER_PATTERNS =
+
+# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using
+# INPUT_FILTER) will also be used to filter the input files that are used for
+# producing the source files to browse (i.e. when SOURCE_BROWSER is set to YES).
+# The default value is: NO.
+
+FILTER_SOURCE_FILES = NO
+
+# The FILTER_SOURCE_PATTERNS tag can be used to specify source filters per file
+# pattern. A pattern will override the setting for FILTER_PATTERN (if any) and
+# it is also possible to disable source filtering for a specific pattern using
+# *.ext= (so without naming a filter).
+# This tag requires that the tag FILTER_SOURCE_FILES is set to YES.
+
+FILTER_SOURCE_PATTERNS =
+
+# If the USE_MDFILE_AS_MAINPAGE tag refers to the name of a markdown file that
+# is part of the input, its contents will be placed on the main page
+# (index.html). This can be useful if you have a project on for instance GitHub
+# and want to reuse the introduction page also for the doxygen output.
+
+USE_MDFILE_AS_MAINPAGE =
+
+#---------------------------------------------------------------------------
+# Configuration options related to source browsing
+#---------------------------------------------------------------------------
+
+# If the SOURCE_BROWSER tag is set to YES then a list of source files will be
+# generated. Documented entities will be cross-referenced with these sources.
+#
+# Note: To get rid of all source code in the generated output, make sure that
+# also VERBATIM_HEADERS is set to NO.
+# The default value is: NO.
+
+SOURCE_BROWSER = NO
+
+# Setting the INLINE_SOURCES tag to YES will include the body of functions,
+# classes and enums directly into the documentation.
+# The default value is: NO.
+
+INLINE_SOURCES = NO
+
+# Setting the STRIP_CODE_COMMENTS tag to YES will instruct doxygen to hide any
+# special comment blocks from generated source code fragments. Normal C, C++ and
+# Fortran comments will always remain visible.
+# The default value is: YES.
+
+STRIP_CODE_COMMENTS = YES
+
+# If the REFERENCED_BY_RELATION tag is set to YES then for each documented
+# entity all documented functions referencing it will be listed.
+# The default value is: NO.
+
+REFERENCED_BY_RELATION = NO
+
+# If the REFERENCES_RELATION tag is set to YES then for each documented function
+# all documented entities called/used by that function will be listed.
+# The default value is: NO.
+
+REFERENCES_RELATION = NO
+
+# If the REFERENCES_LINK_SOURCE tag is set to YES and SOURCE_BROWSER tag is set
+# to YES then the hyperlinks from functions in REFERENCES_RELATION and
+# REFERENCED_BY_RELATION lists will link to the source code. Otherwise they will
+# link to the documentation.
+# The default value is: YES.
+
+REFERENCES_LINK_SOURCE = YES
+
+# If SOURCE_TOOLTIPS is enabled (the default) then hovering a hyperlink in the
+# source code will show a tooltip with additional information such as prototype,
+# brief description and links to the definition and documentation. Since this
+# will make the HTML file larger and loading of large files a bit slower, you
+# can opt to disable this feature.
+# The default value is: YES.
+# This tag requires that the tag SOURCE_BROWSER is set to YES.
+
+SOURCE_TOOLTIPS = YES
+
+# If the USE_HTAGS tag is set to YES then the references to source code will
+# point to the HTML generated by the htags(1) tool instead of doxygen built-in
+# source browser. The htags tool is part of GNU's global source tagging system
+# (see https://www.gnu.org/software/global/global.html). You will need version
+# 4.8.6 or higher.
+#
+# To use it do the following:
+# - Install the latest version of global
+# - Enable SOURCE_BROWSER and USE_HTAGS in the configuration file
+# - Make sure the INPUT points to the root of the source tree
+# - Run doxygen as normal
+#
+# Doxygen will invoke htags (and that will in turn invoke gtags), so these
+# tools must be available from the command line (i.e. in the search path).
+#
+# The result: instead of the source browser generated by doxygen, the links to
+# source code will now point to the output of htags.
+# The default value is: NO.
+# This tag requires that the tag SOURCE_BROWSER is set to YES.
+
+USE_HTAGS = NO
+
+# If the VERBATIM_HEADERS tag is set the YES then doxygen will generate a
+# verbatim copy of the header file for each class for which an include is
+# specified. Set to NO to disable this.
+# See also: Section \class.
+# The default value is: YES.
+
+VERBATIM_HEADERS = YES
+
+#---------------------------------------------------------------------------
+# Configuration options related to the alphabetical class index
+#---------------------------------------------------------------------------
+
+# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index of all
+# compounds will be generated. Enable this if the project contains a lot of
+# classes, structs, unions or interfaces.
+# The default value is: YES.
+
+ALPHABETICAL_INDEX = YES
+
+# The COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns in
+# which the alphabetical index list will be split.
+# Minimum value: 1, maximum value: 20, default value: 5.
+# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.
+
+COLS_IN_ALPHA_INDEX = 5
+
+# In case all classes in a project start with a common prefix, all classes will
+# be put under the same header in the alphabetical index. The IGNORE_PREFIX tag
+# can be used to specify a prefix (or a list of prefixes) that should be ignored
+# while generating the index headers.
+# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.
+
+IGNORE_PREFIX =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the HTML output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_HTML tag is set to YES, doxygen will generate HTML output
+# The default value is: YES.
+
+GENERATE_HTML = NO
+
+# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: html.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_OUTPUT = html
+
+# The HTML_FILE_EXTENSION tag can be used to specify the file extension for each
+# generated HTML page (for example: .htm, .php, .asp).
+# The default value is: .html.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_FILE_EXTENSION = .html
+
+# The HTML_HEADER tag can be used to specify a user-defined HTML header file for
+# each generated HTML page. If the tag is left blank doxygen will generate a
+# standard header.
+#
+# To get valid HTML the header file that includes any scripts and style sheets
+# that doxygen needs, which is dependent on the configuration options used (e.g.
+# the setting GENERATE_TREEVIEW). It is highly recommended to start with a
+# default header using
+# doxygen -w html new_header.html new_footer.html new_stylesheet.css
+# YourConfigFile
+# and then modify the file new_header.html. See also section "Doxygen usage"
+# for information on how to generate the default header that doxygen normally
+# uses.
+# Note: The header is subject to change so you typically have to regenerate the
+# default header when upgrading to a newer version of doxygen. For a description
+# of the possible markers and block names see the documentation.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_HEADER =
+
+# The HTML_FOOTER tag can be used to specify a user-defined HTML footer for each
+# generated HTML page. If the tag is left blank doxygen will generate a standard
+# footer. See HTML_HEADER for more information on how to generate a default
+# footer and what special commands can be used inside the footer. See also
+# section "Doxygen usage" for information on how to generate the default footer
+# that doxygen normally uses.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_FOOTER =
+
+# The HTML_STYLESHEET tag can be used to specify a user-defined cascading style
+# sheet that is used by each HTML page. It can be used to fine-tune the look of
+# the HTML output. If left blank doxygen will generate a default style sheet.
+# See also section "Doxygen usage" for information on how to generate the style
+# sheet that doxygen normally uses.
+# Note: It is recommended to use HTML_EXTRA_STYLESHEET instead of this tag, as
+# it is more robust and this tag (HTML_STYLESHEET) will in the future become
+# obsolete.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_STYLESHEET =
+
+# The HTML_EXTRA_STYLESHEET tag can be used to specify additional user-defined
+# cascading style sheets that are included after the standard style sheets
+# created by doxygen. Using this option one can overrule certain style aspects.
+# This is preferred over using HTML_STYLESHEET since it does not replace the
+# standard style sheet and is therefore more robust against future updates.
+# Doxygen will copy the style sheet files to the output directory.
+# Note: The order of the extra style sheet files is of importance (e.g. the last
+# style sheet in the list overrules the setting of the previous ones in the
+# list). For an example see the documentation.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_EXTRA_STYLESHEET =
+
+# The HTML_EXTRA_FILES tag can be used to specify one or more extra images or
+# other source files which should be copied to the HTML output directory. Note
+# that these files will be copied to the base HTML output directory. Use the
+# $relpath^ marker in the HTML_HEADER and/or HTML_FOOTER files to load these
+# files. In the HTML_STYLESHEET file, use the file name only. Also note that the
+# files will be copied as-is; there are no commands or markers available.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_EXTRA_FILES =
+
+# The HTML_COLORSTYLE_HUE tag controls the color of the HTML output. Doxygen
+# will adjust the colors in the style sheet and background images according to
+# this color. Hue is specified as an angle on a colorwheel, see
+# https://en.wikipedia.org/wiki/Hue for more information. For instance the value
+# 0 represents red, 60 is yellow, 120 is green, 180 is cyan, 240 is blue, 300
+# purple, and 360 is red again.
+# Minimum value: 0, maximum value: 359, default value: 220.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_HUE = 220
+
+# The HTML_COLORSTYLE_SAT tag controls the purity (or saturation) of the colors
+# in the HTML output. For a value of 0 the output will use grayscales only. A
+# value of 255 will produce the most vivid colors.
+# Minimum value: 0, maximum value: 255, default value: 100.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_SAT = 100
+
+# The HTML_COLORSTYLE_GAMMA tag controls the gamma correction applied to the
+# luminance component of the colors in the HTML output. Values below 100
+# gradually make the output lighter, whereas values above 100 make the output
+# darker. The value divided by 100 is the actual gamma applied, so 80 represents
+# a gamma of 0.8, The value 220 represents a gamma of 2.2, and 100 does not
+# change the gamma.
+# Minimum value: 40, maximum value: 240, default value: 80.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_GAMMA = 80
+
+# If the HTML_TIMESTAMP tag is set to YES then the footer of each generated HTML
+# page will contain the date and time when the page was generated. Setting this
+# to YES can help to show when doxygen was last run and thus if the
+# documentation is up to date.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_TIMESTAMP = NO
+
+# If the HTML_DYNAMIC_MENUS tag is set to YES then the generated HTML
+# documentation will contain a main index with vertical navigation menus that
+# are dynamically created via Javascript. If disabled, the navigation index will
+# consists of multiple levels of tabs that are statically embedded in every HTML
+# page. Disable this option to support browsers that do not have Javascript,
+# like the Qt help browser.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_DYNAMIC_MENUS = YES
+
+# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
+# documentation will contain sections that can be hidden and shown after the
+# page has loaded.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_DYNAMIC_SECTIONS = NO
+
+# With HTML_INDEX_NUM_ENTRIES one can control the preferred number of entries
+# shown in the various tree structured indices initially; the user can expand
+# and collapse entries dynamically later on. Doxygen will expand the tree to
+# such a level that at most the specified number of entries are visible (unless
+# a fully collapsed tree already exceeds this amount). So setting the number of
+# entries 1 will produce a full collapsed tree by default. 0 is a special value
+# representing an infinite number of entries and will result in a full expanded
+# tree by default.
+# Minimum value: 0, maximum value: 9999, default value: 100.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_INDEX_NUM_ENTRIES = 100
+
+# If the GENERATE_DOCSET tag is set to YES, additional index files will be
+# generated that can be used as input for Apple's Xcode 3 integrated development
+# environment (see: https://developer.apple.com/xcode/), introduced with OSX
+# 10.5 (Leopard). To create a documentation set, doxygen will generate a
+# Makefile in the HTML output directory. Running make will produce the docset in
+# that directory and running make install will install the docset in
+# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find it at
+# startup. See https://developer.apple.com/library/archive/featuredarticles/Doxy
+# genXcode/_index.html for more information.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_DOCSET = NO
+
+# This tag determines the name of the docset feed. A documentation feed provides
+# an umbrella under which multiple documentation sets from a single provider
+# (such as a company or product suite) can be grouped.
+# The default value is: Doxygen generated docs.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_FEEDNAME = "Doxygen generated docs"
+
+# This tag specifies a string that should uniquely identify the documentation
+# set bundle. This should be a reverse domain-name style string, e.g.
+# com.mycompany.MyDocSet. Doxygen will append .docset to the name.
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_BUNDLE_ID = org.doxygen.Project
+
+# The DOCSET_PUBLISHER_ID tag specifies a string that should uniquely identify
+# the documentation publisher. This should be a reverse domain-name style
+# string, e.g. com.mycompany.MyDocSet.documentation.
+# The default value is: org.doxygen.Publisher.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_PUBLISHER_ID = org.doxygen.Publisher
+
+# The DOCSET_PUBLISHER_NAME tag identifies the documentation publisher.
+# The default value is: Publisher.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_PUBLISHER_NAME = Publisher
+
+# If the GENERATE_HTMLHELP tag is set to YES then doxygen generates three
+# additional HTML index files: index.hhp, index.hhc, and index.hhk. The
+# index.hhp is a project file that can be read by Microsoft's HTML Help Workshop
+# (see: https://www.microsoft.com/en-us/download/details.aspx?id=21138) on
+# Windows.
+#
+# The HTML Help Workshop contains a compiler that can convert all HTML output
+# generated by doxygen into a single compiled HTML file (.chm). Compiled HTML
+# files are now used as the Windows 98 help format, and will replace the old
+# Windows help format (.hlp) on all Windows platforms in the future. Compressed
+# HTML files also contain an index, a table of contents, and you can search for
+# words in the documentation. The HTML workshop also contains a viewer for
+# compressed HTML files.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_HTMLHELP = NO
+
+# The CHM_FILE tag can be used to specify the file name of the resulting .chm
+# file. You can add a path in front of the file if the result should not be
+# written to the html output directory.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+CHM_FILE =
+
+# The HHC_LOCATION tag can be used to specify the location (absolute path
+# including file name) of the HTML help compiler (hhc.exe). If non-empty,
+# doxygen will try to run the HTML help compiler on the generated index.hhp.
+# The file has to be specified with full path.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+HHC_LOCATION =
+
+# The GENERATE_CHI flag controls if a separate .chi index file is generated
+# (YES) or that it should be included in the master .chm file (NO).
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+GENERATE_CHI = NO
+
+# The CHM_INDEX_ENCODING is used to encode HtmlHelp index (hhk), content (hhc)
+# and project file content.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+CHM_INDEX_ENCODING =
+
+# The BINARY_TOC flag controls whether a binary table of contents is generated
+# (YES) or a normal table of contents (NO) in the .chm file. Furthermore it
+# enables the Previous and Next buttons.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+BINARY_TOC = NO
+
+# The TOC_EXPAND flag can be set to YES to add extra items for group members to
+# the table of contents of the HTML help documentation and to the tree view.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+TOC_EXPAND = NO
+
+# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and
+# QHP_VIRTUAL_FOLDER are set, an additional index file will be generated that
+# can be used as input for Qt's qhelpgenerator to generate a Qt Compressed Help
+# (.qch) of the generated HTML documentation.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_QHP = NO
+
+# If the QHG_LOCATION tag is specified, the QCH_FILE tag can be used to specify
+# the file name of the resulting .qch file. The path specified is relative to
+# the HTML output folder.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QCH_FILE =
+
+# The QHP_NAMESPACE tag specifies the namespace to use when generating Qt Help
+# Project output. For more information please see Qt Help Project / Namespace
+# (see: http://doc.qt.io/archives/qt-4.8/qthelpproject.html#namespace).
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_NAMESPACE = org.doxygen.Project
+
+# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating Qt
+# Help Project output. For more information please see Qt Help Project / Virtual
+# Folders (see: http://doc.qt.io/archives/qt-4.8/qthelpproject.html#virtual-
+# folders).
+# The default value is: doc.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_VIRTUAL_FOLDER = doc
+
+# If the QHP_CUST_FILTER_NAME tag is set, it specifies the name of a custom
+# filter to add. For more information please see Qt Help Project / Custom
+# Filters (see: http://doc.qt.io/archives/qt-4.8/qthelpproject.html#custom-
+# filters).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_CUST_FILTER_NAME =
+
+# The QHP_CUST_FILTER_ATTRS tag specifies the list of the attributes of the
+# custom filter to add. For more information please see Qt Help Project / Custom
+# Filters (see: http://doc.qt.io/archives/qt-4.8/qthelpproject.html#custom-
+# filters).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_CUST_FILTER_ATTRS =
+
+# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this
+# project's filter section matches. Qt Help Project / Filter Attributes (see:
+# http://doc.qt.io/archives/qt-4.8/qthelpproject.html#filter-attributes).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_SECT_FILTER_ATTRS =
+
+# The QHG_LOCATION tag can be used to specify the location of Qt's
+# qhelpgenerator. If non-empty doxygen will try to run qhelpgenerator on the
+# generated .qhp file.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHG_LOCATION =
+
+# If the GENERATE_ECLIPSEHELP tag is set to YES, additional index files will be
+# generated, together with the HTML files, they form an Eclipse help plugin. To
+# install this plugin and make it available under the help contents menu in
+# Eclipse, the contents of the directory containing the HTML and XML files needs
+# to be copied into the plugins directory of eclipse. The name of the directory
+# within the plugins directory should be the same as the ECLIPSE_DOC_ID value.
+# After copying Eclipse needs to be restarted before the help appears.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_ECLIPSEHELP = NO
+
+# A unique identifier for the Eclipse help plugin. When installing the plugin
+# the directory name containing the HTML and XML files should also have this
+# name. Each documentation set should have its own identifier.
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_ECLIPSEHELP is set to YES.
+
+ECLIPSE_DOC_ID = org.doxygen.Project
+
+# If you want full control over the layout of the generated HTML pages it might
+# be necessary to disable the index and replace it with your own. The
+# DISABLE_INDEX tag can be used to turn on/off the condensed index (tabs) at top
+# of each HTML page. A value of NO enables the index and the value YES disables
+# it. Since the tabs in the index contain the same information as the navigation
+# tree, you can set this option to YES if you also set GENERATE_TREEVIEW to YES.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+DISABLE_INDEX = NO
+
+# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index
+# structure should be generated to display hierarchical information. If the tag
+# value is set to YES, a side panel will be generated containing a tree-like
+# index structure (just like the one that is generated for HTML Help). For this
+# to work a browser that supports JavaScript, DHTML, CSS and frames is required
+# (i.e. any modern browser). Windows users are probably better off using the
+# HTML help feature. Via custom style sheets (see HTML_EXTRA_STYLESHEET) one can
+# further fine-tune the look of the index. As an example, the default style
+# sheet generated by doxygen has an example that shows how to put an image at
+# the root of the tree instead of the PROJECT_NAME. Since the tree basically has
+# the same information as the tab index, you could consider setting
+# DISABLE_INDEX to YES when enabling this option.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_TREEVIEW = NO
+
+# The ENUM_VALUES_PER_LINE tag can be used to set the number of enum values that
+# doxygen will group on one line in the generated HTML documentation.
+#
+# Note that a value of 0 will completely suppress the enum values from appearing
+# in the overview section.
+# Minimum value: 0, maximum value: 20, default value: 4.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+ENUM_VALUES_PER_LINE = 4
+
+# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be used
+# to set the initial width (in pixels) of the frame in which the tree is shown.
+# Minimum value: 0, maximum value: 1500, default value: 250.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+TREEVIEW_WIDTH = 250
+
+# If the EXT_LINKS_IN_WINDOW option is set to YES, doxygen will open links to
+# external symbols imported via tag files in a separate window.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+EXT_LINKS_IN_WINDOW = NO
+
+# Use this tag to change the font size of LaTeX formulas included as images in
+# the HTML documentation. When you change the font size after a successful
+# doxygen run you need to manually remove any form_*.png images from the HTML
+# output directory to force them to be regenerated.
+# Minimum value: 8, maximum value: 50, default value: 10.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+FORMULA_FONTSIZE = 10
+
+# Use the FORMULA_TRANSPARENT tag to determine whether or not the images
+# generated for formulas are transparent PNGs. Transparent PNGs are not
+# supported properly for IE 6.0, but are supported on all modern browsers.
+#
+# Note that when changing this option you need to delete any form_*.png files in
+# the HTML output directory before the changes have effect.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+FORMULA_TRANSPARENT = YES
+
+# Enable the USE_MATHJAX option to render LaTeX formulas using MathJax (see
+# https://www.mathjax.org) which uses client side Javascript for the rendering
+# instead of using pre-rendered bitmaps. Use this if you do not have LaTeX
+# installed or if you want to formulas look prettier in the HTML output. When
+# enabled you may also need to install MathJax separately and configure the path
+# to it using the MATHJAX_RELPATH option.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+USE_MATHJAX = NO
+
+# When MathJax is enabled you can set the default output format to be used for
+# the MathJax output. See the MathJax site (see:
+# http://docs.mathjax.org/en/latest/output.html) for more details.
+# Possible values are: HTML-CSS (which is slower, but has the best
+# compatibility), NativeMML (i.e. MathML) and SVG.
+# The default value is: HTML-CSS.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_FORMAT = HTML-CSS
+
+# When MathJax is enabled you need to specify the location relative to the HTML
+# output directory using the MATHJAX_RELPATH option. The destination directory
+# should contain the MathJax.js script. For instance, if the mathjax directory
+# is located at the same level as the HTML output directory, then
+# MATHJAX_RELPATH should be ../mathjax. The default value points to the MathJax
+# Content Delivery Network so you can quickly see the result without installing
+# MathJax. However, it is strongly recommended to install a local copy of
+# MathJax from https://www.mathjax.org before deployment.
+# The default value is: https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_RELPATH = https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/
+
+# The MATHJAX_EXTENSIONS tag can be used to specify one or more MathJax
+# extension names that should be enabled during MathJax rendering. For example
+# MATHJAX_EXTENSIONS = TeX/AMSmath TeX/AMSsymbols
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_EXTENSIONS =
+
+# The MATHJAX_CODEFILE tag can be used to specify a file with javascript pieces
+# of code that will be used on startup of the MathJax code. See the MathJax site
+# (see: http://docs.mathjax.org/en/latest/output.html) for more details. For an
+# example see the documentation.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_CODEFILE =
+
+# When the SEARCHENGINE tag is enabled doxygen will generate a search box for
+# the HTML output. The underlying search engine uses javascript and DHTML and
+# should work on any modern browser. Note that when using HTML help
+# (GENERATE_HTMLHELP), Qt help (GENERATE_QHP), or docsets (GENERATE_DOCSET)
+# there is already a search function so this one should typically be disabled.
+# For large projects the javascript based search engine can be slow, then
+# enabling SERVER_BASED_SEARCH may provide a better solution. It is possible to
+# search using the keyboard; to jump to the search box use <access key> + S
+# (what the <access key> is depends on the OS and browser, but it is typically
+# <CTRL>, <ALT>/<option>, or both). Inside the search box use the <cursor down
+# key> to jump into the search results window, the results can be navigated
+# using the <cursor keys>. Press <Enter> to select an item or <escape> to cancel
+# the search. The filter options can be selected when the cursor is inside the
+# search box by pressing <Shift>+<cursor down>. Also here use the <cursor keys>
+# to select a filter and <Enter> or <escape> to activate or cancel the filter
+# option.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+SEARCHENGINE = YES
+
+# When the SERVER_BASED_SEARCH tag is enabled the search engine will be
+# implemented using a web server instead of a web client using Javascript. There
+# are two flavors of web server based searching depending on the EXTERNAL_SEARCH
+# setting. When disabled, doxygen will generate a PHP script for searching and
+# an index file used by the script. When EXTERNAL_SEARCH is enabled the indexing
+# and searching needs to be provided by external tools. See the section
+# "External Indexing and Searching" for details.
+# The default value is: NO.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SERVER_BASED_SEARCH = NO
+
+# When EXTERNAL_SEARCH tag is enabled doxygen will no longer generate the PHP
+# script for searching. Instead the search results are written to an XML file
+# which needs to be processed by an external indexer. Doxygen will invoke an
+# external search engine pointed to by the SEARCHENGINE_URL option to obtain the
+# search results.
+#
+# Doxygen ships with an example indexer (doxyindexer) and search engine
+# (doxysearch.cgi) which are based on the open source search engine library
+# Xapian (see: https://xapian.org/).
+#
+# See the section "External Indexing and Searching" for details.
+# The default value is: NO.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTERNAL_SEARCH = NO
+
+# The SEARCHENGINE_URL should point to a search engine hosted by a web server
+# which will return the search results when EXTERNAL_SEARCH is enabled.
+#
+# Doxygen ships with an example indexer (doxyindexer) and search engine
+# (doxysearch.cgi) which are based on the open source search engine library
+# Xapian (see: https://xapian.org/). See the section "External Indexing and
+# Searching" for details.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SEARCHENGINE_URL =
+
+# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the unindexed
+# search data is written to a file for indexing by an external tool. With the
+# SEARCHDATA_FILE tag the name of this file can be specified.
+# The default file is: searchdata.xml.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SEARCHDATA_FILE = searchdata.xml
+
+# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the
+# EXTERNAL_SEARCH_ID tag can be used as an identifier for the project. This is
+# useful in combination with EXTRA_SEARCH_MAPPINGS to search through multiple
+# projects and redirect the results back to the right project.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTERNAL_SEARCH_ID =
+
+# The EXTRA_SEARCH_MAPPINGS tag can be used to enable searching through doxygen
+# projects other than the one defined by this configuration file, but that are
+# all added to the same external search index. Each project needs to have a
+# unique id set via EXTERNAL_SEARCH_ID. The search mapping then maps the id of
+# to a relative location where the documentation can be found. The format is:
+# EXTRA_SEARCH_MAPPINGS = tagname1=loc1 tagname2=loc2 ...
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTRA_SEARCH_MAPPINGS =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the LaTeX output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_LATEX tag is set to YES, doxygen will generate LaTeX output.
+# The default value is: YES.
+
+GENERATE_LATEX = NO
+
+# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: latex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_OUTPUT = latex
+
+# The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be
+# invoked.
+#
+# Note that when not enabling USE_PDFLATEX the default is latex when enabling
+# USE_PDFLATEX the default is pdflatex and when in the later case latex is
+# chosen this is overwritten by pdflatex. For specific output languages the
+# default can have been set differently, this depends on the implementation of
+# the output language.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_CMD_NAME =
+
+# The MAKEINDEX_CMD_NAME tag can be used to specify the command name to generate
+# index for LaTeX.
+# Note: This tag is used in the Makefile / make.bat.
+# See also: LATEX_MAKEINDEX_CMD for the part in the generated output file
+# (.tex).
+# The default file is: makeindex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+MAKEINDEX_CMD_NAME = makeindex
+
+# The LATEX_MAKEINDEX_CMD tag can be used to specify the command name to
+# generate index for LaTeX. In case there is no backslash (\) as first character
+# it will be automatically added in the LaTeX code.
+# Note: This tag is used in the generated output file (.tex).
+# See also: MAKEINDEX_CMD_NAME for the part in the Makefile / make.bat.
+# The default value is: makeindex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_MAKEINDEX_CMD = makeindex
+
+# If the COMPACT_LATEX tag is set to YES, doxygen generates more compact LaTeX
+# documents. This may be useful for small projects and may help to save some
+# trees in general.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+COMPACT_LATEX = NO
+
+# The PAPER_TYPE tag can be used to set the paper type that is used by the
+# printer.
+# Possible values are: a4 (210 x 297 mm), letter (8.5 x 11 inches), legal (8.5 x
+# 14 inches) and executive (7.25 x 10.5 inches).
+# The default value is: a4.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+PAPER_TYPE = a4
+
+# The EXTRA_PACKAGES tag can be used to specify one or more LaTeX package names
+# that should be included in the LaTeX output. The package can be specified just
+# by its name or with the correct syntax as to be used with the LaTeX
+# \usepackage command. To get the times font for instance you can specify :
+# EXTRA_PACKAGES=times or EXTRA_PACKAGES={times}
+# To use the option intlimits with the amsmath package you can specify:
+# EXTRA_PACKAGES=[intlimits]{amsmath}
+# If left blank no extra packages will be included.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+EXTRA_PACKAGES =
+
+# The LATEX_HEADER tag can be used to specify a personal LaTeX header for the
+# generated LaTeX document. The header should contain everything until the first
+# chapter. If it is left blank doxygen will generate a standard header. See
+# section "Doxygen usage" for information on how to let doxygen write the
+# default header to a separate file.
+#
+# Note: Only use a user-defined header if you know what you are doing! The
+# following commands have a special meaning inside the header: $title,
+# $datetime, $date, $doxygenversion, $projectname, $projectnumber,
+# $projectbrief, $projectlogo. Doxygen will replace $title with the empty
+# string, for the replacement values of the other commands the user is referred
+# to HTML_HEADER.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_HEADER =
+
+# The LATEX_FOOTER tag can be used to specify a personal LaTeX footer for the
+# generated LaTeX document. The footer should contain everything after the last
+# chapter. If it is left blank doxygen will generate a standard footer. See
+# LATEX_HEADER for more information on how to generate a default footer and what
+# special commands can be used inside the footer.
+#
+# Note: Only use a user-defined footer if you know what you are doing!
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_FOOTER =
+
+# The LATEX_EXTRA_STYLESHEET tag can be used to specify additional user-defined
+# LaTeX style sheets that are included after the standard style sheets created
+# by doxygen. Using this option one can overrule certain style aspects. Doxygen
+# will copy the style sheet files to the output directory.
+# Note: The order of the extra style sheet files is of importance (e.g. the last
+# style sheet in the list overrules the setting of the previous ones in the
+# list).
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_EXTRA_STYLESHEET =
+
+# The LATEX_EXTRA_FILES tag can be used to specify one or more extra images or
+# other source files which should be copied to the LATEX_OUTPUT output
+# directory. Note that the files will be copied as-is; there are no commands or
+# markers available.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_EXTRA_FILES =
+
+# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated is
+# prepared for conversion to PDF (using ps2pdf or pdflatex). The PDF file will
+# contain links (just like the HTML output) instead of page references. This
+# makes the output suitable for online browsing using a PDF viewer.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+PDF_HYPERLINKS = YES
+
+# If the USE_PDFLATEX tag is set to YES, doxygen will use pdflatex to generate
+# the PDF file directly from the LaTeX files. Set this option to YES, to get a
+# higher quality PDF documentation.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+USE_PDFLATEX = YES
+
+# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \batchmode
+# command to the generated LaTeX files. This will instruct LaTeX to keep running
+# if errors occur, instead of asking the user for help. This option is also used
+# when generating formulas in HTML.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_BATCHMODE = NO
+
+# If the LATEX_HIDE_INDICES tag is set to YES then doxygen will not include the
+# index chapters (such as File Index, Compound Index, etc.) in the output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_HIDE_INDICES = NO
+
+# If the LATEX_SOURCE_CODE tag is set to YES then doxygen will include source
+# code with syntax highlighting in the LaTeX output.
+#
+# Note that which sources are shown also depends on other settings such as
+# SOURCE_BROWSER.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_SOURCE_CODE = NO
+
+# The LATEX_BIB_STYLE tag can be used to specify the style to use for the
+# bibliography, e.g. plainnat, or ieeetr. See
+# https://en.wikipedia.org/wiki/BibTeX and \cite for more info.
+# The default value is: plain.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_BIB_STYLE = plain
+
+# If the LATEX_TIMESTAMP tag is set to YES then the footer of each generated
+# page will contain the date and time when the page was generated. Setting this
+# to NO can help when comparing the output of multiple runs.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_TIMESTAMP = NO
+
+# The LATEX_EMOJI_DIRECTORY tag is used to specify the (relative or absolute)
+# path from which the emoji images will be read. If a relative path is entered,
+# it will be relative to the LATEX_OUTPUT directory. If left blank the
+# LATEX_OUTPUT directory will be used.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_EMOJI_DIRECTORY =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the RTF output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_RTF tag is set to YES, doxygen will generate RTF output. The
+# RTF output is optimized for Word 97 and may not look too pretty with other RTF
+# readers/editors.
+# The default value is: NO.
+
+GENERATE_RTF = NO
+
+# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: rtf.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_OUTPUT = rtf
+
+# If the COMPACT_RTF tag is set to YES, doxygen generates more compact RTF
+# documents. This may be useful for small projects and may help to save some
+# trees in general.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+COMPACT_RTF = NO
+
+# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated will
+# contain hyperlink fields. The RTF file will contain links (just like the HTML
+# output) instead of page references. This makes the output suitable for online
+# browsing using Word or some other Word compatible readers that support those
+# fields.
+#
+# Note: WordPad (write) and others do not support links.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_HYPERLINKS = NO
+
+# Load stylesheet definitions from file. Syntax is similar to doxygen's
+# configuration file, i.e. a series of assignments. You only have to provide
+# replacements, missing definitions are set to their default value.
+#
+# See also section "Doxygen usage" for information on how to generate the
+# default style sheet that doxygen normally uses.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_STYLESHEET_FILE =
+
+# Set optional variables used in the generation of an RTF document. Syntax is
+# similar to doxygen's configuration file. A template extensions file can be
+# generated using doxygen -e rtf extensionFile.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_EXTENSIONS_FILE =
+
+# If the RTF_SOURCE_CODE tag is set to YES then doxygen will include source code
+# with syntax highlighting in the RTF output.
+#
+# Note that which sources are shown also depends on other settings such as
+# SOURCE_BROWSER.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_SOURCE_CODE = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the man page output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_MAN tag is set to YES, doxygen will generate man pages for
+# classes and files.
+# The default value is: NO.
+
+GENERATE_MAN = NO
+
+# The MAN_OUTPUT tag is used to specify where the man pages will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it. A directory man3 will be created inside the directory specified by
+# MAN_OUTPUT.
+# The default directory is: man.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_OUTPUT = man
+
+# The MAN_EXTENSION tag determines the extension that is added to the generated
+# man pages. In case the manual section does not start with a number, the number
+# 3 is prepended. The dot (.) at the beginning of the MAN_EXTENSION tag is
+# optional.
+# The default value is: .3.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_EXTENSION = .3
+
+# The MAN_SUBDIR tag determines the name of the directory created within
+# MAN_OUTPUT in which the man pages are placed. If defaults to man followed by
+# MAN_EXTENSION with the initial . removed.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_SUBDIR =
+
+# If the MAN_LINKS tag is set to YES and doxygen generates man output, then it
+# will generate one additional man file for each entity documented in the real
+# man page(s). These additional files only source the real man page, but without
+# them the man command would be unable to find the correct page.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_LINKS = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the XML output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_XML tag is set to YES, doxygen will generate an XML file that
+# captures the structure of the code including all documentation.
+# The default value is: NO.
+
+GENERATE_XML = YES
+
+# The XML_OUTPUT tag is used to specify where the XML pages will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: xml.
+# This tag requires that the tag GENERATE_XML is set to YES.
+
+XML_OUTPUT = xml
+
+# If the XML_PROGRAMLISTING tag is set to YES, doxygen will dump the program
+# listings (including syntax highlighting and cross-referencing information) to
+# the XML output. Note that enabling this will significantly increase the size
+# of the XML output.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_XML is set to YES.
+
+XML_PROGRAMLISTING = YES
+
+# If the XML_NS_MEMB_FILE_SCOPE tag is set to YES, doxygen will include
+# namespace members in file scope as well, matching the HTML output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_XML is set to YES.
+
+XML_NS_MEMB_FILE_SCOPE = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the DOCBOOK output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_DOCBOOK tag is set to YES, doxygen will generate Docbook files
+# that can be used to generate PDF.
+# The default value is: NO.
+
+GENERATE_DOCBOOK = NO
+
+# The DOCBOOK_OUTPUT tag is used to specify where the Docbook pages will be put.
+# If a relative path is entered the value of OUTPUT_DIRECTORY will be put in
+# front of it.
+# The default directory is: docbook.
+# This tag requires that the tag GENERATE_DOCBOOK is set to YES.
+
+DOCBOOK_OUTPUT = docbook
+
+# If the DOCBOOK_PROGRAMLISTING tag is set to YES, doxygen will include the
+# program listings (including syntax highlighting and cross-referencing
+# information) to the DOCBOOK output. Note that enabling this will significantly
+# increase the size of the DOCBOOK output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_DOCBOOK is set to YES.
+
+DOCBOOK_PROGRAMLISTING = NO
+
+#---------------------------------------------------------------------------
+# Configuration options for the AutoGen Definitions output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_AUTOGEN_DEF tag is set to YES, doxygen will generate an
+# AutoGen Definitions (see http://autogen.sourceforge.net/) file that captures
+# the structure of the code including all documentation. Note that this feature
+# is still experimental and incomplete at the moment.
+# The default value is: NO.
+
+GENERATE_AUTOGEN_DEF = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the Perl module output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_PERLMOD tag is set to YES, doxygen will generate a Perl module
+# file that captures the structure of the code including all documentation.
+#
+# Note that this feature is still experimental and incomplete at the moment.
+# The default value is: NO.
+
+GENERATE_PERLMOD = NO
+
+# If the PERLMOD_LATEX tag is set to YES, doxygen will generate the necessary
+# Makefile rules, Perl scripts and LaTeX code to be able to generate PDF and DVI
+# output from the Perl module output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_LATEX = NO
+
+# If the PERLMOD_PRETTY tag is set to YES, the Perl module output will be nicely
+# formatted so it can be parsed by a human reader. This is useful if you want to
+# understand what is going on. On the other hand, if this tag is set to NO, the
+# size of the Perl module output will be much smaller and Perl will parse it
+# just the same.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_PRETTY = YES
+
+# The names of the make variables in the generated doxyrules.make file are
+# prefixed with the string contained in PERLMOD_MAKEVAR_PREFIX. This is useful
+# so different doxyrules.make files included by the same Makefile don't
+# overwrite each other's variables.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_MAKEVAR_PREFIX =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the preprocessor
+#---------------------------------------------------------------------------
+
+# If the ENABLE_PREPROCESSING tag is set to YES, doxygen will evaluate all
+# C-preprocessor directives found in the sources and include files.
+# The default value is: YES.
+
+ENABLE_PREPROCESSING = YES
+
+# If the MACRO_EXPANSION tag is set to YES, doxygen will expand all macro names
+# in the source code. If set to NO, only conditional compilation will be
+# performed. Macro expansion can be done in a controlled way by setting
+# EXPAND_ONLY_PREDEF to YES.
+# The default value is: NO.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+MACRO_EXPANSION = NO
+
+# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES then
+# the macro expansion is limited to the macros specified with the PREDEFINED and
+# EXPAND_AS_DEFINED tags.
+# The default value is: NO.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+EXPAND_ONLY_PREDEF = NO
+
+# If the SEARCH_INCLUDES tag is set to YES, the include files in the
+# INCLUDE_PATH will be searched if a #include is found.
+# The default value is: YES.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+SEARCH_INCLUDES = YES
+
+# The INCLUDE_PATH tag can be used to specify one or more directories that
+# contain include files that are not input files but should be processed by the
+# preprocessor.
+# This tag requires that the tag SEARCH_INCLUDES is set to YES.
+
+INCLUDE_PATH =
+
+# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard
+# patterns (like *.h and *.hpp) to filter out the header-files in the
+# directories. If left blank, the patterns specified with FILE_PATTERNS will be
+# used.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+INCLUDE_FILE_PATTERNS =
+
+# The PREDEFINED tag can be used to specify one or more macro names that are
+# defined before the preprocessor is started (similar to the -D option of e.g.
+# gcc). The argument of the tag is a list of macros of the form: name or
+# name=definition (no spaces). If the definition and the "=" are omitted, "=1"
+# is assumed. To prevent a macro definition from being undefined via #undef or
+# recursively expanded use the := operator instead of the = operator.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+PREDEFINED =
+
+# If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then this
+# tag can be used to specify a list of macro names that should be expanded. The
+# macro definition that is found in the sources will be used. Use the PREDEFINED
+# tag if you want to use a different macro definition that overrules the
+# definition found in the source code.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+EXPAND_AS_DEFINED =
+
+# If the SKIP_FUNCTION_MACROS tag is set to YES then doxygen's preprocessor will
+# remove all references to function-like macros that are alone on a line, have
+# an all uppercase name, and do not end with a semicolon. Such function macros
+# are typically used for boiler-plate code, and will confuse the parser if not
+# removed.
+# The default value is: YES.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+SKIP_FUNCTION_MACROS = YES
+
+#---------------------------------------------------------------------------
+# Configuration options related to external references
+#---------------------------------------------------------------------------
+
+# The TAGFILES tag can be used to specify one or more tag files. For each tag
+# file the location of the external documentation should be added. The format of
+# a tag file without this location is as follows:
+# TAGFILES = file1 file2 ...
+# Adding location for the tag files is done as follows:
+# TAGFILES = file1=loc1 "file2 = loc2" ...
+# where loc1 and loc2 can be relative or absolute paths or URLs. See the
+# section "Linking to external documentation" for more information about the use
+# of tag files.
+# Note: Each tag file must have a unique name (where the name does NOT include
+# the path). If a tag file is not located in the directory in which doxygen is
+# run, you must also specify the path to the tagfile here.
+
+TAGFILES =
+
+# When a file name is specified after GENERATE_TAGFILE, doxygen will create a
+# tag file that is based on the input files it reads. See section "Linking to
+# external documentation" for more information about the usage of tag files.
+
+GENERATE_TAGFILE =
+
+# If the ALLEXTERNALS tag is set to YES, all external class will be listed in
+# the class index. If set to NO, only the inherited external classes will be
+# listed.
+# The default value is: NO.
+
+ALLEXTERNALS = NO
+
+# If the EXTERNAL_GROUPS tag is set to YES, all external groups will be listed
+# in the modules index. If set to NO, only the current project's groups will be
+# listed.
+# The default value is: YES.
+
+EXTERNAL_GROUPS = YES
+
+# If the EXTERNAL_PAGES tag is set to YES, all external pages will be listed in
+# the related pages index. If set to NO, only the current project's pages will
+# be listed.
+# The default value is: YES.
+
+EXTERNAL_PAGES = YES
+
+# The PERL_PATH should be the absolute path and name of the perl script
+# interpreter (i.e. the result of 'which perl').
+# The default file (with absolute path) is: /usr/bin/perl.
+
+PERL_PATH = /usr/bin/perl
+
+#---------------------------------------------------------------------------
+# Configuration options related to the dot tool
+#---------------------------------------------------------------------------
+
+# If the CLASS_DIAGRAMS tag is set to YES, doxygen will generate a class diagram
+# (in HTML and LaTeX) for classes with base or super classes. Setting the tag to
+# NO turns the diagrams off. Note that this option also works with HAVE_DOT
+# disabled, but it is recommended to install and use dot, since it yields more
+# powerful graphs.
+# The default value is: YES.
+
+CLASS_DIAGRAMS = YES
+
+# You can define message sequence charts within doxygen comments using the \msc
+# command. Doxygen will then run the mscgen tool (see:
+# http://www.mcternan.me.uk/mscgen/)) to produce the chart and insert it in the
+# documentation. The MSCGEN_PATH tag allows you to specify the directory where
+# the mscgen tool resides. If left empty the tool is assumed to be found in the
+# default search path.
+
+MSCGEN_PATH =
+
+# You can include diagrams made with dia in doxygen documentation. Doxygen will
+# then run dia to produce the diagram and insert it in the documentation. The
+# DIA_PATH tag allows you to specify the directory where the dia binary resides.
+# If left empty dia is assumed to be found in the default search path.
+
+DIA_PATH =
+
+# If set to YES the inheritance and collaboration graphs will hide inheritance
+# and usage relations if the target is undocumented or is not a class.
+# The default value is: YES.
+
+HIDE_UNDOC_RELATIONS = YES
+
+# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is
+# available from the path. This tool is part of Graphviz (see:
+# http://www.graphviz.org/), a graph visualization toolkit from AT&T and Lucent
+# Bell Labs. The other options in this section have no effect if this option is
+# set to NO
+# The default value is: NO.
+
+HAVE_DOT = NO
+
+# The DOT_NUM_THREADS specifies the number of dot invocations doxygen is allowed
+# to run in parallel. When set to 0 doxygen will base this on the number of
+# processors available in the system. You can set it explicitly to a value
+# larger than 0 to get control over the balance between CPU load and processing
+# speed.
+# Minimum value: 0, maximum value: 32, default value: 0.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_NUM_THREADS = 0
+
+# When you want a differently looking font in the dot files that doxygen
+# generates you can specify the font name using DOT_FONTNAME. You need to make
+# sure dot is able to find the font, which can be done by putting it in a
+# standard location or by setting the DOTFONTPATH environment variable or by
+# setting DOT_FONTPATH to the directory containing the font.
+# The default value is: Helvetica.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTNAME = Helvetica
+
+# The DOT_FONTSIZE tag can be used to set the size (in points) of the font of
+# dot graphs.
+# Minimum value: 4, maximum value: 24, default value: 10.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTSIZE = 10
+
+# By default doxygen will tell dot to use the default font as specified with
+# DOT_FONTNAME. If you specify a different font using DOT_FONTNAME you can set
+# the path where dot can find it using this tag.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTPATH =
+
+# If the CLASS_GRAPH tag is set to YES then doxygen will generate a graph for
+# each documented class showing the direct and indirect inheritance relations.
+# Setting this tag to YES will force the CLASS_DIAGRAMS tag to NO.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CLASS_GRAPH = YES
+
+# If the COLLABORATION_GRAPH tag is set to YES then doxygen will generate a
+# graph for each documented class showing the direct and indirect implementation
+# dependencies (inheritance, containment, and class references variables) of the
+# class with other documented classes.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+COLLABORATION_GRAPH = YES
+
+# If the GROUP_GRAPHS tag is set to YES then doxygen will generate a graph for
+# groups, showing the direct groups dependencies.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GROUP_GRAPHS = YES
+
+# If the UML_LOOK tag is set to YES, doxygen will generate inheritance and
+# collaboration diagrams in a style similar to the OMG's Unified Modeling
+# Language.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+UML_LOOK = NO
+
+# If the UML_LOOK tag is enabled, the fields and methods are shown inside the
+# class node. If there are many fields or methods and many nodes the graph may
+# become too big to be useful. The UML_LIMIT_NUM_FIELDS threshold limits the
+# number of items for each type to make the size more manageable. Set this to 0
+# for no limit. Note that the threshold may be exceeded by 50% before the limit
+# is enforced. So when you set the threshold to 10, up to 15 fields may appear,
+# but if the number exceeds 15, the total amount of fields shown is limited to
+# 10.
+# Minimum value: 0, maximum value: 100, default value: 10.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+UML_LIMIT_NUM_FIELDS = 10
+
+# If the TEMPLATE_RELATIONS tag is set to YES then the inheritance and
+# collaboration graphs will show the relations between templates and their
+# instances.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+TEMPLATE_RELATIONS = NO
+
+# If the INCLUDE_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are set to
+# YES then doxygen will generate a graph for each documented file showing the
+# direct and indirect include dependencies of the file with other documented
+# files.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INCLUDE_GRAPH = YES
+
+# If the INCLUDED_BY_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are
+# set to YES then doxygen will generate a graph for each documented file showing
+# the direct and indirect include dependencies of the file with other documented
+# files.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INCLUDED_BY_GRAPH = YES
+
+# If the CALL_GRAPH tag is set to YES then doxygen will generate a call
+# dependency graph for every global function or class method.
+#
+# Note that enabling this option will significantly increase the time of a run.
+# So in most cases it will be better to enable call graphs for selected
+# functions only using the \callgraph command. Disabling a call graph can be
+# accomplished by means of the command \hidecallgraph.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CALL_GRAPH = NO
+
+# If the CALLER_GRAPH tag is set to YES then doxygen will generate a caller
+# dependency graph for every global function or class method.
+#
+# Note that enabling this option will significantly increase the time of a run.
+# So in most cases it will be better to enable caller graphs for selected
+# functions only using the \callergraph command. Disabling a caller graph can be
+# accomplished by means of the command \hidecallergraph.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CALLER_GRAPH = NO
+
+# If the GRAPHICAL_HIERARCHY tag is set to YES then doxygen will graphical
+# hierarchy of all classes instead of a textual one.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GRAPHICAL_HIERARCHY = YES
+
+# If the DIRECTORY_GRAPH tag is set to YES then doxygen will show the
+# dependencies a directory has on other directories in a graphical way. The
+# dependency relations are determined by the #include relations between the
+# files in the directories.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DIRECTORY_GRAPH = YES
+
+# The DOT_IMAGE_FORMAT tag can be used to set the image format of the images
+# generated by dot. For an explanation of the image formats see the section
+# output formats in the documentation of the dot tool (Graphviz (see:
+# http://www.graphviz.org/)).
+# Note: If you choose svg you need to set HTML_FILE_EXTENSION to xhtml in order
+# to make the SVG files visible in IE 9+ (other browsers do not have this
+# requirement).
+# Possible values are: png, jpg, gif, svg, png:gd, png:gd:gd, png:cairo,
+# png:cairo:gd, png:cairo:cairo, png:cairo:gdiplus, png:gdiplus and
+# png:gdiplus:gdiplus.
+# The default value is: png.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_IMAGE_FORMAT = png
+
+# If DOT_IMAGE_FORMAT is set to svg, then this option can be set to YES to
+# enable generation of interactive SVG images that allow zooming and panning.
+#
+# Note that this requires a modern browser other than Internet Explorer. Tested
+# and working are Firefox, Chrome, Safari, and Opera.
+# Note: For IE 9+ you need to set HTML_FILE_EXTENSION to xhtml in order to make
+# the SVG files visible. Older versions of IE do not have SVG support.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INTERACTIVE_SVG = NO
+
+# The DOT_PATH tag can be used to specify the path where the dot tool can be
+# found. If left blank, it is assumed the dot tool can be found in the path.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_PATH =
+
+# The DOTFILE_DIRS tag can be used to specify one or more directories that
+# contain dot files that are included in the documentation (see the \dotfile
+# command).
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOTFILE_DIRS =
+
+# The MSCFILE_DIRS tag can be used to specify one or more directories that
+# contain msc files that are included in the documentation (see the \mscfile
+# command).
+
+MSCFILE_DIRS =
+
+# The DIAFILE_DIRS tag can be used to specify one or more directories that
+# contain dia files that are included in the documentation (see the \diafile
+# command).
+
+DIAFILE_DIRS =
+
+# When using plantuml, the PLANTUML_JAR_PATH tag should be used to specify the
+# path where java can find the plantuml.jar file. If left blank, it is assumed
+# PlantUML is not used or called during a preprocessing step. Doxygen will
+# generate a warning when it encounters a \startuml command in this case and
+# will not generate output for the diagram.
+
+PLANTUML_JAR_PATH =
+
+# When using plantuml, the PLANTUML_CFG_FILE tag can be used to specify a
+# configuration file for plantuml.
+
+PLANTUML_CFG_FILE =
+
+# When using plantuml, the specified paths are searched for files specified by
+# the !include statement in a plantuml block.
+
+PLANTUML_INCLUDE_PATH =
+
+# The DOT_GRAPH_MAX_NODES tag can be used to set the maximum number of nodes
+# that will be shown in the graph. If the number of nodes in a graph becomes
+# larger than this value, doxygen will truncate the graph, which is visualized
+# by representing a node as a red box. Note that doxygen if the number of direct
+# children of the root node in a graph is already larger than
+# DOT_GRAPH_MAX_NODES then the graph will not be shown at all. Also note that
+# the size of a graph can be further restricted by MAX_DOT_GRAPH_DEPTH.
+# Minimum value: 0, maximum value: 10000, default value: 50.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_GRAPH_MAX_NODES = 50
+
+# The MAX_DOT_GRAPH_DEPTH tag can be used to set the maximum depth of the graphs
+# generated by dot. A depth value of 3 means that only nodes reachable from the
+# root by following a path via at most 3 edges will be shown. Nodes that lay
+# further from the root node will be omitted. Note that setting this option to 1
+# or 2 may greatly reduce the computation time needed for large code bases. Also
+# note that the size of a graph can be further restricted by
+# DOT_GRAPH_MAX_NODES. Using a depth of 0 means no depth restriction.
+# Minimum value: 0, maximum value: 1000, default value: 0.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+MAX_DOT_GRAPH_DEPTH = 0
+
+# Set the DOT_TRANSPARENT tag to YES to generate images with a transparent
+# background. This is disabled by default, because dot on Windows does not seem
+# to support this out of the box.
+#
+# Warning: Depending on the platform used, enabling this option may lead to
+# badly anti-aliased labels on the edges of a graph (i.e. they become hard to
+# read).
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_TRANSPARENT = NO
+
+# Set the DOT_MULTI_TARGETS tag to YES to allow dot to generate multiple output
+# files in one run (i.e. multiple -o and -T options on the command line). This
+# makes dot run faster, but since only newer versions of dot (>1.8.10) support
+# this, this feature is disabled by default.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_MULTI_TARGETS = NO
+
+# If the GENERATE_LEGEND tag is set to YES doxygen will generate a legend page
+# explaining the meaning of the various boxes and arrows in the dot generated
+# graphs.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GENERATE_LEGEND = YES
+
+# If the DOT_CLEANUP tag is set to YES, doxygen will remove the intermediate dot
+# files that are used to generate the various graphs.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_CLEANUP = YES
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE
new file mode 100644
index 000000000..201a5c0fd
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE
@@ -0,0 +1,3 @@
+This source repository is release under Apache2 and MIT licenses.
+
+See LICENSE.Apache2 and LICENSE.MIT for details.
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.Apache2 b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.Apache2
new file mode 100644
index 000000000..d64569567
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.Apache2
@@ -0,0 +1,202 @@
+
+ Apache License
+ Version 2.0, January 2004
+ http://www.apache.org/licenses/
+
+ TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+ 1. Definitions.
+
+ "License" shall mean the terms and conditions for use, reproduction,
+ and distribution as defined by Sections 1 through 9 of this document.
+
+ "Licensor" shall mean the copyright owner or entity authorized by
+ the copyright owner that is granting the License.
+
+ "Legal Entity" shall mean the union of the acting entity and all
+ other entities that control, are controlled by, or are under common
+ control with that entity. For the purposes of this definition,
+ "control" means (i) the power, direct or indirect, to cause the
+ direction or management of such entity, whether by contract or
+ otherwise, or (ii) ownership of fifty percent (50%) or more of the
+ outstanding shares, or (iii) beneficial ownership of such entity.
+
+ "You" (or "Your") shall mean an individual or Legal Entity
+ exercising permissions granted by this License.
+
+ "Source" form shall mean the preferred form for making modifications,
+ including but not limited to software source code, documentation
+ source, and configuration files.
+
+ "Object" form shall mean any form resulting from mechanical
+ transformation or translation of a Source form, including but
+ not limited to compiled object code, generated documentation,
+ and conversions to other media types.
+
+ "Work" shall mean the work of authorship, whether in Source or
+ Object form, made available under the License, as indicated by a
+ copyright notice that is included in or attached to the work
+ (an example is provided in the Appendix below).
+
+ "Derivative Works" shall mean any work, whether in Source or Object
+ form, that is based on (or derived from) the Work and for which the
+ editorial revisions, annotations, elaborations, or other modifications
+ represent, as a whole, an original work of authorship. For the purposes
+ of this License, Derivative Works shall not include works that remain
+ separable from, or merely link (or bind by name) to the interfaces of,
+ the Work and Derivative Works thereof.
+
+ "Contribution" shall mean any work of authorship, including
+ the original version of the Work and any modifications or additions
+ to that Work or Derivative Works thereof, that is intentionally
+ submitted to Licensor for inclusion in the Work by the copyright owner
+ or by an individual or Legal Entity authorized to submit on behalf of
+ the copyright owner. For the purposes of this definition, "submitted"
+ means any form of electronic, verbal, or written communication sent
+ to the Licensor or its representatives, including but not limited to
+ communication on electronic mailing lists, source code control systems,
+ and issue tracking systems that are managed by, or on behalf of, the
+ Licensor for the purpose of discussing and improving the Work, but
+ excluding communication that is conspicuously marked or otherwise
+ designated in writing by the copyright owner as "Not a Contribution."
+
+ "Contributor" shall mean Licensor and any individual or Legal Entity
+ on behalf of whom a Contribution has been received by Licensor and
+ subsequently incorporated within the Work.
+
+ 2. Grant of Copyright License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ copyright license to reproduce, prepare Derivative Works of,
+ publicly display, publicly perform, sublicense, and distribute the
+ Work and such Derivative Works in Source or Object form.
+
+ 3. Grant of Patent License. Subject to the terms and conditions of
+ this License, each Contributor hereby grants to You a perpetual,
+ worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+ (except as stated in this section) patent license to make, have made,
+ use, offer to sell, sell, import, and otherwise transfer the Work,
+ where such license applies only to those patent claims licensable
+ by such Contributor that are necessarily infringed by their
+ Contribution(s) alone or by combination of their Contribution(s)
+ with the Work to which such Contribution(s) was submitted. If You
+ institute patent litigation against any entity (including a
+ cross-claim or counterclaim in a lawsuit) alleging that the Work
+ or a Contribution incorporated within the Work constitutes direct
+ or contributory patent infringement, then any patent licenses
+ granted to You under this License for that Work shall terminate
+ as of the date such litigation is filed.
+
+ 4. Redistribution. You may reproduce and distribute copies of the
+ Work or Derivative Works thereof in any medium, with or without
+ modifications, and in Source or Object form, provided that You
+ meet the following conditions:
+
+ (a) You must give any other recipients of the Work or
+ Derivative Works a copy of this License; and
+
+ (b) You must cause any modified files to carry prominent notices
+ stating that You changed the files; and
+
+ (c) You must retain, in the Source form of any Derivative Works
+ that You distribute, all copyright, patent, trademark, and
+ attribution notices from the Source form of the Work,
+ excluding those notices that do not pertain to any part of
+ the Derivative Works; and
+
+ (d) If the Work includes a "NOTICE" text file as part of its
+ distribution, then any Derivative Works that You distribute must
+ include a readable copy of the attribution notices contained
+ within such NOTICE file, excluding those notices that do not
+ pertain to any part of the Derivative Works, in at least one
+ of the following places: within a NOTICE text file distributed
+ as part of the Derivative Works; within the Source form or
+ documentation, if provided along with the Derivative Works; or,
+ within a display generated by the Derivative Works, if and
+ wherever such third-party notices normally appear. The contents
+ of the NOTICE file are for informational purposes only and
+ do not modify the License. You may add Your own attribution
+ notices within Derivative Works that You distribute, alongside
+ or as an addendum to the NOTICE text from the Work, provided
+ that such additional attribution notices cannot be construed
+ as modifying the License.
+
+ You may add Your own copyright statement to Your modifications and
+ may provide additional or different license terms and conditions
+ for use, reproduction, or distribution of Your modifications, or
+ for any such Derivative Works as a whole, provided Your use,
+ reproduction, and distribution of the Work otherwise complies with
+ the conditions stated in this License.
+
+ 5. Submission of Contributions. Unless You explicitly state otherwise,
+ any Contribution intentionally submitted for inclusion in the Work
+ by You to the Licensor shall be under the terms and conditions of
+ this License, without any additional terms or conditions.
+ Notwithstanding the above, nothing herein shall supersede or modify
+ the terms of any separate license agreement you may have executed
+ with Licensor regarding such Contributions.
+
+ 6. Trademarks. This License does not grant permission to use the trade
+ names, trademarks, service marks, or product names of the Licensor,
+ except as required for reasonable and customary use in describing the
+ origin of the Work and reproducing the content of the NOTICE file.
+
+ 7. Disclaimer of Warranty. Unless required by applicable law or
+ agreed to in writing, Licensor provides the Work (and each
+ Contributor provides its Contributions) on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+ implied, including, without limitation, any warranties or conditions
+ of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+ PARTICULAR PURPOSE. You are solely responsible for determining the
+ appropriateness of using or redistributing the Work and assume any
+ risks associated with Your exercise of permissions under this License.
+
+ 8. Limitation of Liability. In no event and under no legal theory,
+ whether in tort (including negligence), contract, or otherwise,
+ unless required by applicable law (such as deliberate and grossly
+ negligent acts) or agreed to in writing, shall any Contributor be
+ liable to You for damages, including any direct, indirect, special,
+ incidental, or consequential damages of any character arising as a
+ result of this License or out of the use or inability to use the
+ Work (including but not limited to damages for loss of goodwill,
+ work stoppage, computer failure or malfunction, or any and all
+ other commercial damages or losses), even if such Contributor
+ has been advised of the possibility of such damages.
+
+ 9. Accepting Warranty or Additional Liability. While redistributing
+ the Work or Derivative Works thereof, You may choose to offer,
+ and charge a fee for, acceptance of support, warranty, indemnity,
+ or other liability obligations and/or rights consistent with this
+ License. However, in accepting such obligations, You may act only
+ on Your own behalf and on Your sole responsibility, not on behalf
+ of any other Contributor, and only if You agree to indemnify,
+ defend, and hold each Contributor harmless for any liability
+ incurred by, or claims asserted against, such Contributor by reason
+ of your accepting any such warranty or additional liability.
+
+ END OF TERMS AND CONDITIONS
+
+ APPENDIX: How to apply the Apache License to your work.
+
+ To apply the Apache License to your work, attach the following
+ boilerplate notice, with the fields enclosed by brackets "[]"
+ replaced with your own identifying information. (Don't include
+ the brackets!) The text should be enclosed in the appropriate
+ comment syntax for the file format. We also recommend that a
+ file or class name and description of purpose be included on the
+ same "printed page" as the copyright notice for easier
+ identification within third-party archives.
+
+ Copyright [yyyy] [name of copyright owner]
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.MIT b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.MIT
new file mode 100644
index 000000000..3a7e422b6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/LICENSE.MIT
@@ -0,0 +1,21 @@
+The MIT License
+
+Copyright (c) 2019 SiFive, Inc.
+
+Permission is hereby granted, free of charge, to any person obtaining a
+copy of this software and associated documentation files (the "Software"),
+to deal in the Software without restriction, including without limitation
+the rights to use, copy, modify, merge, publish, distribute, sublicense,
+and/or sell copies of the Software, and to permit persons to whom the
+Software is furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+DEALINGS IN THE SOFTWARE.
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.am b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.am
new file mode 100644
index 000000000..0166e2828
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.am
@@ -0,0 +1,238 @@
+# Copyright 2018-2019 SiFive, Inc
+# SPDX-License-Identifier: Apache-2.0
+
+########################################################
+# Sources passed in by configure
+########################################################
+
+metal/machine.h: @MACHINE_HEADER@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+metal/machine/inline.h: @MACHINE_INLINE@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+metal/machine/platform.h: @PLATFORM_HEADER@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+nobase_include_HEADERS = \
+ metal/machine.h \
+ metal/machine/inline.h \
+ metal/machine/platform.h
+
+# This will generate these sources before the compilation step
+BUILT_SOURCES = \
+ metal/machine.h \
+ metal/machine/inline.h \
+ metal/machine/platform.h
+
+########################################################
+# Metal header files
+########################################################
+
+nobase_include_HEADERS += \
+ metal/drivers/fixed-clock.h \
+ metal/drivers/fixed-factor-clock.h \
+ metal/drivers/riscv_clint0.h \
+ metal/drivers/riscv_cpu.h \
+ metal/drivers/riscv_plic0.h \
+ metal/drivers/sifive_buserror0.h \
+ metal/drivers/sifive_ccache0.h \
+ metal/drivers/sifive_clic0.h \
+ metal/drivers/sifive_fe310-g000_hfrosc.h \
+ metal/drivers/sifive_fe310-g000_hfxosc.h \
+ metal/drivers/sifive_fe310-g000_lfrosc.h \
+ metal/drivers/sifive_fe310-g000_pll.h \
+ metal/drivers/sifive_fe310-g000_prci.h \
+ metal/drivers/sifive_global-external-interrupts0.h \
+ metal/drivers/sifive_gpio-buttons.h \
+ metal/drivers/sifive_gpio-leds.h \
+ metal/drivers/sifive_gpio-switches.h \
+ metal/drivers/sifive_gpio0.h \
+ metal/drivers/sifive_i2c0.h \
+ metal/drivers/sifive_l2pf0.h \
+ metal/drivers/sifive_local-external-interrupts0.h \
+ metal/drivers/sifive_pwm0.h \
+ metal/drivers/sifive_rtc0.h \
+ metal/drivers/sifive_spi0.h \
+ metal/drivers/sifive_test0.h \
+ metal/drivers/sifive_trace.h \
+ metal/drivers/sifive_uart0.h \
+ metal/drivers/sifive_simuart0.h \
+ metal/drivers/sifive_wdog0.h \
+ metal/drivers/ucb_htif0.h \
+ metal/atomic.h \
+ metal/button.h \
+ metal/cache.h \
+ metal/clock.h \
+ metal/compiler.h \
+ metal/cpu.h \
+ metal/csr.h \
+ metal/gpio.h \
+ metal/hpm.h \
+ metal/i2c.h \
+ metal/init.h \
+ metal/interrupt.h \
+ metal/io.h \
+ metal/itim.h \
+ metal/led.h \
+ metal/lim.h \
+ metal/lock.h \
+ metal/memory.h \
+ metal/pmp.h \
+ metal/privilege.h \
+ metal/pwm.h\
+ metal/rtc.h \
+ metal/shutdown.h \
+ metal/scrub.h \
+ metal/spi.h \
+ metal/switch.h \
+ metal/timer.h \
+ metal/time.h \
+ metal/tty.h \
+ metal/uart.h \
+ metal/watchdog.h
+
+########################################################
+# libmetal
+########################################################
+
+lib_LIBRARIES = libmetal.a
+
+libmetal_a_SOURCES = \
+ src/drivers/fixed-clock.c \
+ src/drivers/fixed-factor-clock.c \
+ src/drivers/inline.c \
+ src/drivers/riscv_clint0.c \
+ src/drivers/riscv_cpu.c \
+ src/drivers/riscv_plic0.c \
+ src/drivers/sifive_buserror0.c \
+ src/drivers/sifive_ccache0.c \
+ src/drivers/sifive_clic0.c \
+ src/drivers/sifive_fe310-g000_hfrosc.c \
+ src/drivers/sifive_fe310-g000_hfxosc.c \
+ src/drivers/sifive_fe310-g000_lfrosc.c \
+ src/drivers/sifive_fe310-g000_pll.c \
+ src/drivers/sifive_fe310-g000_prci.c \
+ src/drivers/sifive_global-external-interrupts0.c \
+ src/drivers/sifive_gpio-buttons.c \
+ src/drivers/sifive_gpio-leds.c \
+ src/drivers/sifive_gpio-switches.c \
+ src/drivers/sifive_gpio0.c \
+ src/drivers/sifive_i2c0.c \
+ src/drivers/sifive_l2pf0.c \
+ src/drivers/sifive_local-external-interrupts0.c \
+ src/drivers/sifive_pwm0.c \
+ src/drivers/sifive_rtc0.c \
+ src/drivers/sifive_spi0.c \
+ src/drivers/sifive_test0.c \
+ src/drivers/sifive_trace.c \
+ src/drivers/sifive_uart0.c \
+ src/drivers/sifive_simuart0.c \
+ src/drivers/sifive_wdog0.c \
+ src/drivers/ucb_htif0.c \
+ src/atomic.c \
+ src/button.c \
+ src/cache.c \
+ src/clock.c \
+ src/cpu.c \
+ src/entry.S \
+ src/scrub.S \
+ src/trap.S \
+ src/gpio.c \
+ src/hpm.c \
+ src/i2c.c \
+ src/init.c \
+ src/interrupt.c \
+ src/led.c \
+ src/lock.c \
+ src/memory.c \
+ src/pmp.c \
+ src/privilege.c \
+ src/pwm.c\
+ src/rtc.c \
+ src/shutdown.c \
+ src/spi.c \
+ src/switch.c \
+ src/synchronize_harts.c \
+ src/timer.c \
+ src/time.c \
+ src/trap.S \
+ src/tty.c \
+ src/uart.c \
+ src/vector.S \
+ src/watchdog.c
+
+########################################################
+# libsegger
+########################################################
+
+# Provide segger hook with Freedom Metal that is built when
+# --with-builtin-libmetal-segger is passed to configure
+if WITH_BUILTIN_LIBMETAL_SEGGER
+
+lib_LIBRARIES += libmetal-segger.a
+
+libmetal_segger_a_SOURCES = \
+ gloss/crt0.S \
+ segger/SEGGER_target_metal.c
+
+endif # WITH_BUILTIN_LIBMETAL_SEGGER
+
+########################################################
+# libgloss
+########################################################
+
+# Freedom Metal has its own libgloss implementation that is only built when
+# --with-builtin-libgloss is passed to configure.
+if WITH_BUILTIN_LIBGLOSS
+
+lib_LIBRARIES += libmetal-gloss.a
+
+libmetal_gloss_a_SOURCES = \
+ gloss/crt0.S \
+ gloss/nanosleep.c \
+ gloss/sys_access.c \
+ gloss/sys_chdir.c \
+ gloss/sys_chmod.c \
+ gloss/sys_chown.c \
+ gloss/sys_clock_gettime.c \
+ gloss/sys_close.c \
+ gloss/sys_execve.c \
+ gloss/sys_exit.c \
+ gloss/sys_faccessat.c \
+ gloss/sys_fork.c \
+ gloss/sys_fstat.c \
+ gloss/sys_fstatat.c \
+ gloss/sys_ftime.c \
+ gloss/sys_getcwd.c \
+ gloss/sys_getpid.c \
+ gloss/sys_gettimeofday.c \
+ gloss/sys_isatty.c \
+ gloss/sys_kill.c \
+ gloss/sys_link.c \
+ gloss/sys_lseek.c \
+ gloss/sys_lstat.c \
+ gloss/sys_open.c \
+ gloss/sys_openat.c \
+ gloss/sys_read.c \
+ gloss/sys_sbrk.c \
+ gloss/sys_stat.c \
+ gloss/sys_sysconf.c \
+ gloss/sys_times.c \
+ gloss/sys_unlink.c \
+ gloss/sys_utime.c \
+ gloss/sys_wait.c \
+ gloss/sys_write.c
+
+endif
+
+########################################################
+# Clean
+########################################################
+
+clean-local:
+ -rm -rf metal/machine.h metal/machine/inline.h
+ -rm -rf metal/machine/platform.h
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.in b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.in
new file mode 100644
index 000000000..8bba3983b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/Makefile.in
@@ -0,0 +1,1443 @@
+# Makefile.in generated by automake 1.15 from Makefile.am.
+# @configure_input@
+
+# Copyright (C) 1994-2014 Free Software Foundation, Inc.
+
+# This Makefile.in is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
+# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+# PARTICULAR PURPOSE.
+
+@SET_MAKE@
+
+# Copyright 2018-2019 SiFive, Inc
+# SPDX-License-Identifier: Apache-2.0
+
+########################################################
+# Sources passed in by configure
+########################################################
+
+
+VPATH = @srcdir@
+am__is_gnu_make = { \
+ if test -z '$(MAKELEVEL)'; then \
+ false; \
+ elif test -n '$(MAKE_HOST)'; then \
+ true; \
+ elif test -n '$(MAKE_VERSION)' && test -n '$(CURDIR)'; then \
+ true; \
+ else \
+ false; \
+ fi; \
+}
+am__make_running_with_option = \
+ case $${target_option-} in \
+ ?) ;; \
+ *) echo "am__make_running_with_option: internal error: invalid" \
+ "target option '$${target_option-}' specified" >&2; \
+ exit 1;; \
+ esac; \
+ has_opt=no; \
+ sane_makeflags=$$MAKEFLAGS; \
+ if $(am__is_gnu_make); then \
+ sane_makeflags=$$MFLAGS; \
+ else \
+ case $$MAKEFLAGS in \
+ *\\[\ \ ]*) \
+ bs=\\; \
+ sane_makeflags=`printf '%s\n' "$$MAKEFLAGS" \
+ | sed "s/$$bs$$bs[$$bs $$bs ]*//g"`;; \
+ esac; \
+ fi; \
+ skip_next=no; \
+ strip_trailopt () \
+ { \
+ flg=`printf '%s\n' "$$flg" | sed "s/$$1.*$$//"`; \
+ }; \
+ for flg in $$sane_makeflags; do \
+ test $$skip_next = yes && { skip_next=no; continue; }; \
+ case $$flg in \
+ *=*|--*) continue;; \
+ -*I) strip_trailopt 'I'; skip_next=yes;; \
+ -*I?*) strip_trailopt 'I';; \
+ -*O) strip_trailopt 'O'; skip_next=yes;; \
+ -*O?*) strip_trailopt 'O';; \
+ -*l) strip_trailopt 'l'; skip_next=yes;; \
+ -*l?*) strip_trailopt 'l';; \
+ -[dEDm]) skip_next=yes;; \
+ -[JT]) skip_next=yes;; \
+ esac; \
+ case $$flg in \
+ *$$target_option*) has_opt=yes; break;; \
+ esac; \
+ done; \
+ test $$has_opt = yes
+am__make_dryrun = (target_option=n; $(am__make_running_with_option))
+am__make_keepgoing = (target_option=k; $(am__make_running_with_option))
+pkgdatadir = $(datadir)/@PACKAGE@
+pkgincludedir = $(includedir)/@PACKAGE@
+pkglibdir = $(libdir)/@PACKAGE@
+pkglibexecdir = $(libexecdir)/@PACKAGE@
+am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
+install_sh_DATA = $(install_sh) -c -m 644
+install_sh_PROGRAM = $(install_sh) -c
+install_sh_SCRIPT = $(install_sh) -c
+INSTALL_HEADER = $(INSTALL_DATA)
+transform = $(program_transform_name)
+NORMAL_INSTALL = :
+PRE_INSTALL = :
+POST_INSTALL = :
+NORMAL_UNINSTALL = :
+PRE_UNINSTALL = :
+POST_UNINSTALL = :
+build_triplet = @build@
+host_triplet = @host@
+
+########################################################
+# libsegger
+########################################################
+
+# Provide segger hook with Freedom Metal that is built when
+# --with-builtin-libmetal-segger is passed to configure
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@am__append_1 = libmetal-segger.a
+
+########################################################
+# libgloss
+########################################################
+
+# Freedom Metal has its own libgloss implementation that is only built when
+# --with-builtin-libgloss is passed to configure.
+@WITH_BUILTIN_LIBGLOSS_TRUE@am__append_2 = libmetal-gloss.a
+subdir = .
+ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
+am__aclocal_m4_deps = $(top_srcdir)/configure.ac
+am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
+ $(ACLOCAL_M4)
+DIST_COMMON = $(srcdir)/Makefile.am $(top_srcdir)/configure \
+ $(am__configure_deps) $(nobase_include_HEADERS) \
+ $(am__DIST_COMMON)
+am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \
+ configure.lineno config.status.lineno
+mkinstalldirs = $(install_sh) -d
+CONFIG_CLEAN_FILES =
+CONFIG_CLEAN_VPATH_FILES =
+am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
+am__vpath_adj = case $$p in \
+ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
+ *) f=$$p;; \
+ esac;
+am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`;
+am__install_max = 40
+am__nobase_strip_setup = \
+ srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'`
+am__nobase_strip = \
+ for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||"
+am__nobase_list = $(am__nobase_strip_setup); \
+ for p in $$list; do echo "$$p $$p"; done | \
+ sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \
+ $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \
+ if (++n[$$2] == $(am__install_max)) \
+ { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \
+ END { for (dir in files) print dir, files[dir] }'
+am__base_list = \
+ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \
+ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g'
+am__uninstall_files_from_dir = { \
+ test -z "$$files" \
+ || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \
+ || { echo " ( cd '$$dir' && rm -f" $$files ")"; \
+ $(am__cd) "$$dir" && rm -f $$files; }; \
+ }
+am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(includedir)"
+LIBRARIES = $(lib_LIBRARIES)
+ARFLAGS = cru
+AM_V_AR = $(am__v_AR_@AM_V@)
+am__v_AR_ = $(am__v_AR_@AM_DEFAULT_V@)
+am__v_AR_0 = @echo " AR " $@;
+am__v_AR_1 =
+libmetal_gloss_a_AR = $(AR) $(ARFLAGS)
+libmetal_gloss_a_LIBADD =
+am__libmetal_gloss_a_SOURCES_DIST = gloss/crt0.S gloss/nanosleep.c \
+ gloss/sys_access.c gloss/sys_chdir.c gloss/sys_chmod.c \
+ gloss/sys_chown.c gloss/sys_clock_gettime.c gloss/sys_close.c \
+ gloss/sys_execve.c gloss/sys_exit.c gloss/sys_faccessat.c \
+ gloss/sys_fork.c gloss/sys_fstat.c gloss/sys_fstatat.c \
+ gloss/sys_ftime.c gloss/sys_getcwd.c gloss/sys_getpid.c \
+ gloss/sys_gettimeofday.c gloss/sys_isatty.c gloss/sys_kill.c \
+ gloss/sys_link.c gloss/sys_lseek.c gloss/sys_lstat.c \
+ gloss/sys_open.c gloss/sys_openat.c gloss/sys_read.c \
+ gloss/sys_sbrk.c gloss/sys_stat.c gloss/sys_sysconf.c \
+ gloss/sys_times.c gloss/sys_unlink.c gloss/sys_utime.c \
+ gloss/sys_wait.c gloss/sys_write.c
+am__dirstamp = $(am__leading_dot)dirstamp
+@WITH_BUILTIN_LIBGLOSS_TRUE@am_libmetal_gloss_a_OBJECTS = \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/crt0.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/nanosleep.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_access.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chdir.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chmod.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chown.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_clock_gettime.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_close.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_execve.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_exit.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_faccessat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fork.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fstat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fstatat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_ftime.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_getcwd.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_getpid.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_gettimeofday.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_isatty.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_kill.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_link.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_lseek.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_lstat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_open.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_openat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_read.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_sbrk.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_stat.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_sysconf.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_times.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_unlink.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_utime.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_wait.$(OBJEXT) \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_write.$(OBJEXT)
+libmetal_gloss_a_OBJECTS = $(am_libmetal_gloss_a_OBJECTS)
+libmetal_segger_a_AR = $(AR) $(ARFLAGS)
+libmetal_segger_a_LIBADD =
+am__libmetal_segger_a_SOURCES_DIST = gloss/crt0.S \
+ segger/SEGGER_target_metal.c
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@am_libmetal_segger_a_OBJECTS = \
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@ gloss/crt0.$(OBJEXT) \
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@ segger/SEGGER_target_metal.$(OBJEXT)
+libmetal_segger_a_OBJECTS = $(am_libmetal_segger_a_OBJECTS)
+libmetal_a_AR = $(AR) $(ARFLAGS)
+libmetal_a_LIBADD =
+am_libmetal_a_OBJECTS = src/drivers/fixed-clock.$(OBJEXT) \
+ src/drivers/fixed-factor-clock.$(OBJEXT) \
+ src/drivers/inline.$(OBJEXT) \
+ src/drivers/riscv_clint0.$(OBJEXT) \
+ src/drivers/riscv_cpu.$(OBJEXT) \
+ src/drivers/riscv_plic0.$(OBJEXT) \
+ src/drivers/sifive_buserror0.$(OBJEXT) \
+ src/drivers/sifive_ccache0.$(OBJEXT) \
+ src/drivers/sifive_clic0.$(OBJEXT) \
+ src/drivers/sifive_fe310-g000_hfrosc.$(OBJEXT) \
+ src/drivers/sifive_fe310-g000_hfxosc.$(OBJEXT) \
+ src/drivers/sifive_fe310-g000_lfrosc.$(OBJEXT) \
+ src/drivers/sifive_fe310-g000_pll.$(OBJEXT) \
+ src/drivers/sifive_fe310-g000_prci.$(OBJEXT) \
+ src/drivers/sifive_global-external-interrupts0.$(OBJEXT) \
+ src/drivers/sifive_gpio-buttons.$(OBJEXT) \
+ src/drivers/sifive_gpio-leds.$(OBJEXT) \
+ src/drivers/sifive_gpio-switches.$(OBJEXT) \
+ src/drivers/sifive_gpio0.$(OBJEXT) \
+ src/drivers/sifive_i2c0.$(OBJEXT) \
+ src/drivers/sifive_l2pf0.$(OBJEXT) \
+ src/drivers/sifive_local-external-interrupts0.$(OBJEXT) \
+ src/drivers/sifive_pwm0.$(OBJEXT) \
+ src/drivers/sifive_rtc0.$(OBJEXT) \
+ src/drivers/sifive_spi0.$(OBJEXT) \
+ src/drivers/sifive_test0.$(OBJEXT) \
+ src/drivers/sifive_trace.$(OBJEXT) \
+ src/drivers/sifive_uart0.$(OBJEXT) \
+ src/drivers/sifive_simuart0.$(OBJEXT) \
+ src/drivers/sifive_wdog0.$(OBJEXT) \
+ src/drivers/ucb_htif0.$(OBJEXT) src/atomic.$(OBJEXT) \
+ src/button.$(OBJEXT) src/cache.$(OBJEXT) src/clock.$(OBJEXT) \
+ src/cpu.$(OBJEXT) src/entry.$(OBJEXT) src/scrub.$(OBJEXT) \
+ src/trap.$(OBJEXT) src/gpio.$(OBJEXT) src/hpm.$(OBJEXT) \
+ src/i2c.$(OBJEXT) src/init.$(OBJEXT) src/interrupt.$(OBJEXT) \
+ src/led.$(OBJEXT) src/lock.$(OBJEXT) src/memory.$(OBJEXT) \
+ src/pmp.$(OBJEXT) src/privilege.$(OBJEXT) src/pwm.$(OBJEXT) \
+ src/rtc.$(OBJEXT) src/shutdown.$(OBJEXT) src/spi.$(OBJEXT) \
+ src/switch.$(OBJEXT) src/synchronize_harts.$(OBJEXT) \
+ src/timer.$(OBJEXT) src/time.$(OBJEXT) src/trap.$(OBJEXT) \
+ src/tty.$(OBJEXT) src/uart.$(OBJEXT) src/vector.$(OBJEXT) \
+ src/watchdog.$(OBJEXT)
+libmetal_a_OBJECTS = $(am_libmetal_a_OBJECTS)
+AM_V_P = $(am__v_P_@AM_V@)
+am__v_P_ = $(am__v_P_@AM_DEFAULT_V@)
+am__v_P_0 = false
+am__v_P_1 = :
+AM_V_GEN = $(am__v_GEN_@AM_V@)
+am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@)
+am__v_GEN_0 = @echo " GEN " $@;
+am__v_GEN_1 =
+AM_V_at = $(am__v_at_@AM_V@)
+am__v_at_ = $(am__v_at_@AM_DEFAULT_V@)
+am__v_at_0 = @
+am__v_at_1 =
+DEFAULT_INCLUDES = -I.@am__isrc@
+depcomp = $(SHELL) $(top_srcdir)/depcomp
+am__depfiles_maybe = depfiles
+am__mv = mv -f
+CPPASCOMPILE = $(CCAS) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \
+ $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CCASFLAGS) $(CCASFLAGS)
+AM_V_CPPAS = $(am__v_CPPAS_@AM_V@)
+am__v_CPPAS_ = $(am__v_CPPAS_@AM_DEFAULT_V@)
+am__v_CPPAS_0 = @echo " CPPAS " $@;
+am__v_CPPAS_1 =
+COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
+ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
+AM_V_CC = $(am__v_CC_@AM_V@)
+am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@)
+am__v_CC_0 = @echo " CC " $@;
+am__v_CC_1 =
+CCLD = $(CC)
+LINK = $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@
+AM_V_CCLD = $(am__v_CCLD_@AM_V@)
+am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@)
+am__v_CCLD_0 = @echo " CCLD " $@;
+am__v_CCLD_1 =
+SOURCES = $(libmetal_gloss_a_SOURCES) $(libmetal_segger_a_SOURCES) \
+ $(libmetal_a_SOURCES)
+DIST_SOURCES = $(am__libmetal_gloss_a_SOURCES_DIST) \
+ $(am__libmetal_segger_a_SOURCES_DIST) $(libmetal_a_SOURCES)
+am__can_run_installinfo = \
+ case $$AM_UPDATE_INFO_DIR in \
+ n|no|NO) false;; \
+ *) (install-info --version) >/dev/null 2>&1;; \
+ esac
+HEADERS = $(nobase_include_HEADERS)
+am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) $(LISP)
+# Read a list of newline-separated strings from the standard input,
+# and print each of them once, without duplicates. Input order is
+# *not* preserved.
+am__uniquify_input = $(AWK) '\
+ BEGIN { nonempty = 0; } \
+ { items[$$0] = 1; nonempty = 1; } \
+ END { if (nonempty) { for (i in items) print i; }; } \
+'
+# Make sure the list of sources is unique. This is necessary because,
+# e.g., the same source file might be shared among _SOURCES variables
+# for different programs/libraries.
+am__define_uniq_tagged_files = \
+ list='$(am__tagged_files)'; \
+ unique=`for i in $$list; do \
+ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
+ done | $(am__uniquify_input)`
+ETAGS = etags
+CTAGS = ctags
+CSCOPE = cscope
+AM_RECURSIVE_TARGETS = cscope
+am__DIST_COMMON = $(srcdir)/Makefile.in ar-lib compile config.guess \
+ config.sub depcomp install-sh missing
+DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
+distdir = $(PACKAGE)-$(VERSION)
+top_distdir = $(distdir)
+am__remove_distdir = \
+ if test -d "$(distdir)"; then \
+ find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \
+ && rm -rf "$(distdir)" \
+ || { sleep 5 && rm -rf "$(distdir)"; }; \
+ else :; fi
+am__post_remove_distdir = $(am__remove_distdir)
+DIST_ARCHIVES = $(distdir).tar.gz
+GZIP_ENV = --best
+DIST_TARGETS = dist-gzip
+distuninstallcheck_listfiles = find . -type f -print
+am__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \
+ | sed 's|^\./|$(prefix)/|' | grep -v '$(infodir)/dir$$'
+distcleancheck_listfiles = find . -type f -print
+ACLOCAL = @ACLOCAL@
+AMTAR = @AMTAR@
+AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@
+AR = @AR@
+AUTOCONF = @AUTOCONF@
+AUTOHEADER = @AUTOHEADER@
+AUTOMAKE = @AUTOMAKE@
+AWK = @AWK@
+CC = @CC@
+CCAS = @CCAS@
+CCASDEPMODE = @CCASDEPMODE@
+CCASFLAGS = @CCASFLAGS@
+CCDEPMODE = @CCDEPMODE@
+CFLAGS = @CFLAGS@
+CPPFLAGS = @CPPFLAGS@
+CYGPATH_W = @CYGPATH_W@
+DEFS = @DEFS@
+DEPDIR = @DEPDIR@
+ECHO_C = @ECHO_C@
+ECHO_N = @ECHO_N@
+ECHO_T = @ECHO_T@
+EXEEXT = @EXEEXT@
+INSTALL = @INSTALL@
+INSTALL_DATA = @INSTALL_DATA@
+INSTALL_PROGRAM = @INSTALL_PROGRAM@
+INSTALL_SCRIPT = @INSTALL_SCRIPT@
+INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
+LDFLAGS = @LDFLAGS@
+LIBOBJS = @LIBOBJS@
+LIBS = @LIBS@
+LTLIBOBJS = @LTLIBOBJS@
+MACHINE_HEADER = @MACHINE_HEADER@
+MACHINE_INLINE = @MACHINE_INLINE@
+MAINT = @MAINT@
+MAKEINFO = @MAKEINFO@
+MKDIR_P = @MKDIR_P@
+OBJEXT = @OBJEXT@
+PACKAGE = @PACKAGE@
+PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
+PACKAGE_NAME = @PACKAGE_NAME@
+PACKAGE_STRING = @PACKAGE_STRING@
+PACKAGE_TARNAME = @PACKAGE_TARNAME@
+PACKAGE_URL = @PACKAGE_URL@
+PACKAGE_VERSION = @PACKAGE_VERSION@
+PATH_SEPARATOR = @PATH_SEPARATOR@
+PLATFORM_HEADER = @PLATFORM_HEADER@
+RANLIB = @RANLIB@
+SET_MAKE = @SET_MAKE@
+SHELL = @SHELL@
+STRIP = @STRIP@
+VERSION = @VERSION@
+abs_builddir = @abs_builddir@
+abs_srcdir = @abs_srcdir@
+abs_top_builddir = @abs_top_builddir@
+abs_top_srcdir = @abs_top_srcdir@
+ac_ct_AR = @ac_ct_AR@
+ac_ct_CC = @ac_ct_CC@
+am__include = @am__include@
+am__leading_dot = @am__leading_dot@
+am__quote = @am__quote@
+am__tar = @am__tar@
+am__untar = @am__untar@
+bindir = @bindir@
+build = @build@
+build_alias = @build_alias@
+build_cpu = @build_cpu@
+build_os = @build_os@
+build_vendor = @build_vendor@
+builddir = @builddir@
+datadir = @datadir@
+datarootdir = @datarootdir@
+docdir = @docdir@
+dvidir = @dvidir@
+exec_prefix = @exec_prefix@
+host = @host@
+host_alias = @host_alias@
+host_cpu = @host_cpu@
+host_os = @host_os@
+host_vendor = @host_vendor@
+htmldir = @htmldir@
+includedir = @includedir@
+infodir = @infodir@
+install_sh = @install_sh@
+libdir = @libdir@
+libexecdir = @libexecdir@
+localedir = @localedir@
+localstatedir = @localstatedir@
+mandir = @mandir@
+mkdir_p = @mkdir_p@
+oldincludedir = @oldincludedir@
+pdfdir = @pdfdir@
+prefix = @prefix@
+program_transform_name = @program_transform_name@
+psdir = @psdir@
+runstatedir = @runstatedir@
+sbindir = @sbindir@
+sharedstatedir = @sharedstatedir@
+srcdir = @srcdir@
+sysconfdir = @sysconfdir@
+target_alias = @target_alias@
+top_build_prefix = @top_build_prefix@
+top_builddir = @top_builddir@
+top_srcdir = @top_srcdir@
+
+########################################################
+# Metal header files
+########################################################
+nobase_include_HEADERS = metal/machine.h metal/machine/inline.h \
+ metal/machine/platform.h metal/drivers/fixed-clock.h \
+ metal/drivers/fixed-factor-clock.h \
+ metal/drivers/riscv_clint0.h metal/drivers/riscv_cpu.h \
+ metal/drivers/riscv_plic0.h metal/drivers/sifive_buserror0.h \
+ metal/drivers/sifive_ccache0.h metal/drivers/sifive_clic0.h \
+ metal/drivers/sifive_fe310-g000_hfrosc.h \
+ metal/drivers/sifive_fe310-g000_hfxosc.h \
+ metal/drivers/sifive_fe310-g000_lfrosc.h \
+ metal/drivers/sifive_fe310-g000_pll.h \
+ metal/drivers/sifive_fe310-g000_prci.h \
+ metal/drivers/sifive_global-external-interrupts0.h \
+ metal/drivers/sifive_gpio-buttons.h \
+ metal/drivers/sifive_gpio-leds.h \
+ metal/drivers/sifive_gpio-switches.h \
+ metal/drivers/sifive_gpio0.h metal/drivers/sifive_i2c0.h \
+ metal/drivers/sifive_l2pf0.h \
+ metal/drivers/sifive_local-external-interrupts0.h \
+ metal/drivers/sifive_pwm0.h metal/drivers/sifive_rtc0.h \
+ metal/drivers/sifive_spi0.h metal/drivers/sifive_test0.h \
+ metal/drivers/sifive_trace.h metal/drivers/sifive_uart0.h \
+ metal/drivers/sifive_simuart0.h metal/drivers/sifive_wdog0.h \
+ metal/drivers/ucb_htif0.h metal/atomic.h metal/button.h \
+ metal/cache.h metal/clock.h metal/compiler.h metal/cpu.h \
+ metal/csr.h metal/gpio.h metal/hpm.h metal/i2c.h metal/init.h \
+ metal/interrupt.h metal/io.h metal/itim.h metal/led.h \
+ metal/lim.h metal/lock.h metal/memory.h metal/pmp.h \
+ metal/privilege.h metal/pwm.h metal/rtc.h metal/shutdown.h \
+ metal/scrub.h metal/spi.h metal/switch.h metal/timer.h \
+ metal/time.h metal/tty.h metal/uart.h metal/watchdog.h
+
+# This will generate these sources before the compilation step
+BUILT_SOURCES = \
+ metal/machine.h \
+ metal/machine/inline.h \
+ metal/machine/platform.h
+
+
+########################################################
+# libmetal
+########################################################
+lib_LIBRARIES = libmetal.a $(am__append_1) $(am__append_2)
+libmetal_a_SOURCES = \
+ src/drivers/fixed-clock.c \
+ src/drivers/fixed-factor-clock.c \
+ src/drivers/inline.c \
+ src/drivers/riscv_clint0.c \
+ src/drivers/riscv_cpu.c \
+ src/drivers/riscv_plic0.c \
+ src/drivers/sifive_buserror0.c \
+ src/drivers/sifive_ccache0.c \
+ src/drivers/sifive_clic0.c \
+ src/drivers/sifive_fe310-g000_hfrosc.c \
+ src/drivers/sifive_fe310-g000_hfxosc.c \
+ src/drivers/sifive_fe310-g000_lfrosc.c \
+ src/drivers/sifive_fe310-g000_pll.c \
+ src/drivers/sifive_fe310-g000_prci.c \
+ src/drivers/sifive_global-external-interrupts0.c \
+ src/drivers/sifive_gpio-buttons.c \
+ src/drivers/sifive_gpio-leds.c \
+ src/drivers/sifive_gpio-switches.c \
+ src/drivers/sifive_gpio0.c \
+ src/drivers/sifive_i2c0.c \
+ src/drivers/sifive_l2pf0.c \
+ src/drivers/sifive_local-external-interrupts0.c \
+ src/drivers/sifive_pwm0.c \
+ src/drivers/sifive_rtc0.c \
+ src/drivers/sifive_spi0.c \
+ src/drivers/sifive_test0.c \
+ src/drivers/sifive_trace.c \
+ src/drivers/sifive_uart0.c \
+ src/drivers/sifive_simuart0.c \
+ src/drivers/sifive_wdog0.c \
+ src/drivers/ucb_htif0.c \
+ src/atomic.c \
+ src/button.c \
+ src/cache.c \
+ src/clock.c \
+ src/cpu.c \
+ src/entry.S \
+ src/scrub.S \
+ src/trap.S \
+ src/gpio.c \
+ src/hpm.c \
+ src/i2c.c \
+ src/init.c \
+ src/interrupt.c \
+ src/led.c \
+ src/lock.c \
+ src/memory.c \
+ src/pmp.c \
+ src/privilege.c \
+ src/pwm.c\
+ src/rtc.c \
+ src/shutdown.c \
+ src/spi.c \
+ src/switch.c \
+ src/synchronize_harts.c \
+ src/timer.c \
+ src/time.c \
+ src/trap.S \
+ src/tty.c \
+ src/uart.c \
+ src/vector.S \
+ src/watchdog.c
+
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@libmetal_segger_a_SOURCES = \
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@ gloss/crt0.S \
+@WITH_BUILTIN_LIBMETAL_SEGGER_TRUE@ segger/SEGGER_target_metal.c
+
+@WITH_BUILTIN_LIBGLOSS_TRUE@libmetal_gloss_a_SOURCES = \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/crt0.S \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/nanosleep.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_access.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chdir.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chmod.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_chown.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_clock_gettime.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_close.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_execve.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_exit.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_faccessat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fork.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fstat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_fstatat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_ftime.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_getcwd.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_getpid.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_gettimeofday.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_isatty.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_kill.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_link.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_lseek.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_lstat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_open.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_openat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_read.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_sbrk.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_stat.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_sysconf.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_times.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_unlink.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_utime.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_wait.c \
+@WITH_BUILTIN_LIBGLOSS_TRUE@ gloss/sys_write.c
+
+all: $(BUILT_SOURCES)
+ $(MAKE) $(AM_MAKEFLAGS) all-am
+
+.SUFFIXES:
+.SUFFIXES: .S .c .o .obj
+am--refresh: Makefile
+ @:
+$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
+ @for dep in $?; do \
+ case '$(am__configure_deps)' in \
+ *$$dep*) \
+ echo ' cd $(srcdir) && $(AUTOMAKE) --foreign'; \
+ $(am__cd) $(srcdir) && $(AUTOMAKE) --foreign \
+ && exit 0; \
+ exit 1;; \
+ esac; \
+ done; \
+ echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign Makefile'; \
+ $(am__cd) $(top_srcdir) && \
+ $(AUTOMAKE) --foreign Makefile
+Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
+ @case '$?' in \
+ *config.status*) \
+ echo ' $(SHELL) ./config.status'; \
+ $(SHELL) ./config.status;; \
+ *) \
+ echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe)'; \
+ cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe);; \
+ esac;
+
+$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
+ $(SHELL) ./config.status --recheck
+
+$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
+ $(am__cd) $(srcdir) && $(AUTOCONF)
+$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
+ $(am__cd) $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS)
+$(am__aclocal_m4_deps):
+install-libLIBRARIES: $(lib_LIBRARIES)
+ @$(NORMAL_INSTALL)
+ @list='$(lib_LIBRARIES)'; test -n "$(libdir)" || list=; \
+ list2=; for p in $$list; do \
+ if test -f $$p; then \
+ list2="$$list2 $$p"; \
+ else :; fi; \
+ done; \
+ test -z "$$list2" || { \
+ echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \
+ $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \
+ echo " $(INSTALL_DATA) $$list2 '$(DESTDIR)$(libdir)'"; \
+ $(INSTALL_DATA) $$list2 "$(DESTDIR)$(libdir)" || exit $$?; }
+ @$(POST_INSTALL)
+ @list='$(lib_LIBRARIES)'; test -n "$(libdir)" || list=; \
+ for p in $$list; do \
+ if test -f $$p; then \
+ $(am__strip_dir) \
+ echo " ( cd '$(DESTDIR)$(libdir)' && $(RANLIB) $$f )"; \
+ ( cd "$(DESTDIR)$(libdir)" && $(RANLIB) $$f ) || exit $$?; \
+ else :; fi; \
+ done
+
+uninstall-libLIBRARIES:
+ @$(NORMAL_UNINSTALL)
+ @list='$(lib_LIBRARIES)'; test -n "$(libdir)" || list=; \
+ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \
+ dir='$(DESTDIR)$(libdir)'; $(am__uninstall_files_from_dir)
+
+clean-libLIBRARIES:
+ -test -z "$(lib_LIBRARIES)" || rm -f $(lib_LIBRARIES)
+gloss/$(am__dirstamp):
+ @$(MKDIR_P) gloss
+ @: > gloss/$(am__dirstamp)
+gloss/$(DEPDIR)/$(am__dirstamp):
+ @$(MKDIR_P) gloss/$(DEPDIR)
+ @: > gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/crt0.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/nanosleep.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_access.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_chdir.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_chmod.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_chown.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_clock_gettime.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_close.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_execve.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_exit.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_faccessat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_fork.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_fstat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_fstatat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_ftime.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_getcwd.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_getpid.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_gettimeofday.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_isatty.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_kill.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_link.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_lseek.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_lstat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_open.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_openat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_read.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_sbrk.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_stat.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_sysconf.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_times.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_unlink.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_utime.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_wait.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+gloss/sys_write.$(OBJEXT): gloss/$(am__dirstamp) \
+ gloss/$(DEPDIR)/$(am__dirstamp)
+
+libmetal-gloss.a: $(libmetal_gloss_a_OBJECTS) $(libmetal_gloss_a_DEPENDENCIES) $(EXTRA_libmetal_gloss_a_DEPENDENCIES)
+ $(AM_V_at)-rm -f libmetal-gloss.a
+ $(AM_V_AR)$(libmetal_gloss_a_AR) libmetal-gloss.a $(libmetal_gloss_a_OBJECTS) $(libmetal_gloss_a_LIBADD)
+ $(AM_V_at)$(RANLIB) libmetal-gloss.a
+segger/$(am__dirstamp):
+ @$(MKDIR_P) segger
+ @: > segger/$(am__dirstamp)
+segger/$(DEPDIR)/$(am__dirstamp):
+ @$(MKDIR_P) segger/$(DEPDIR)
+ @: > segger/$(DEPDIR)/$(am__dirstamp)
+segger/SEGGER_target_metal.$(OBJEXT): segger/$(am__dirstamp) \
+ segger/$(DEPDIR)/$(am__dirstamp)
+
+libmetal-segger.a: $(libmetal_segger_a_OBJECTS) $(libmetal_segger_a_DEPENDENCIES) $(EXTRA_libmetal_segger_a_DEPENDENCIES)
+ $(AM_V_at)-rm -f libmetal-segger.a
+ $(AM_V_AR)$(libmetal_segger_a_AR) libmetal-segger.a $(libmetal_segger_a_OBJECTS) $(libmetal_segger_a_LIBADD)
+ $(AM_V_at)$(RANLIB) libmetal-segger.a
+src/drivers/$(am__dirstamp):
+ @$(MKDIR_P) src/drivers
+ @: > src/drivers/$(am__dirstamp)
+src/drivers/$(DEPDIR)/$(am__dirstamp):
+ @$(MKDIR_P) src/drivers/$(DEPDIR)
+ @: > src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/fixed-clock.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/fixed-factor-clock.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/inline.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/riscv_clint0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/riscv_cpu.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/riscv_plic0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_buserror0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_ccache0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_clic0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_fe310-g000_hfrosc.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_fe310-g000_hfxosc.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_fe310-g000_lfrosc.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_fe310-g000_pll.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_fe310-g000_prci.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_global-external-interrupts0.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_gpio-buttons.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_gpio-leds.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_gpio-switches.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_gpio0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_i2c0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_l2pf0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_local-external-interrupts0.$(OBJEXT): \
+ src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_pwm0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_rtc0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_spi0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_test0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_trace.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_uart0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_simuart0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/sifive_wdog0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/drivers/ucb_htif0.$(OBJEXT): src/drivers/$(am__dirstamp) \
+ src/drivers/$(DEPDIR)/$(am__dirstamp)
+src/$(am__dirstamp):
+ @$(MKDIR_P) src
+ @: > src/$(am__dirstamp)
+src/$(DEPDIR)/$(am__dirstamp):
+ @$(MKDIR_P) src/$(DEPDIR)
+ @: > src/$(DEPDIR)/$(am__dirstamp)
+src/atomic.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/button.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/cache.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/clock.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/cpu.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/entry.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/scrub.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/trap.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/gpio.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/hpm.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/i2c.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/init.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/interrupt.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/led.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/lock.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/memory.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/pmp.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/privilege.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/pwm.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/rtc.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/shutdown.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/spi.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/switch.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/synchronize_harts.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/timer.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/time.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/tty.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/uart.$(OBJEXT): src/$(am__dirstamp) src/$(DEPDIR)/$(am__dirstamp)
+src/vector.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+src/watchdog.$(OBJEXT): src/$(am__dirstamp) \
+ src/$(DEPDIR)/$(am__dirstamp)
+
+libmetal.a: $(libmetal_a_OBJECTS) $(libmetal_a_DEPENDENCIES) $(EXTRA_libmetal_a_DEPENDENCIES)
+ $(AM_V_at)-rm -f libmetal.a
+ $(AM_V_AR)$(libmetal_a_AR) libmetal.a $(libmetal_a_OBJECTS) $(libmetal_a_LIBADD)
+ $(AM_V_at)$(RANLIB) libmetal.a
+
+mostlyclean-compile:
+ -rm -f *.$(OBJEXT)
+ -rm -f gloss/*.$(OBJEXT)
+ -rm -f segger/*.$(OBJEXT)
+ -rm -f src/*.$(OBJEXT)
+ -rm -f src/drivers/*.$(OBJEXT)
+
+distclean-compile:
+ -rm -f *.tab.c
+
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/crt0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/nanosleep.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_access.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_chdir.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_chmod.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_chown.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_clock_gettime.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_close.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_execve.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_exit.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_faccessat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_fork.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_fstat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_fstatat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_ftime.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_getcwd.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_getpid.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_gettimeofday.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_isatty.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_kill.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_link.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_lseek.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_lstat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_open.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_openat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_read.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_sbrk.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_stat.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_sysconf.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_times.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_unlink.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_utime.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_wait.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@gloss/$(DEPDIR)/sys_write.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@segger/$(DEPDIR)/SEGGER_target_metal.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/atomic.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/button.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/cache.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/clock.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/cpu.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/entry.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/gpio.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/hpm.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/i2c.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/init.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/interrupt.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/led.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/lock.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/memory.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/pmp.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/privilege.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/pwm.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/rtc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/scrub.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/shutdown.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/spi.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/switch.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/synchronize_harts.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/time.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/timer.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/trap.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/tty.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/uart.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/vector.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/$(DEPDIR)/watchdog.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/fixed-clock.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/fixed-factor-clock.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/inline.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/riscv_clint0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/riscv_cpu.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/riscv_plic0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_buserror0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_ccache0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_clic0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_fe310-g000_hfrosc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_fe310-g000_hfxosc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_fe310-g000_lfrosc.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_fe310-g000_pll.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_fe310-g000_prci.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_global-external-interrupts0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_gpio-buttons.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_gpio-leds.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_gpio-switches.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_gpio0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_i2c0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_l2pf0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_local-external-interrupts0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_pwm0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_rtc0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_simuart0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_spi0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_test0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_trace.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_uart0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/sifive_wdog0.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/drivers/$(DEPDIR)/ucb_htif0.Po@am__quote@
+
+.S.o:
+@am__fastdepCCAS_TRUE@ $(AM_V_CPPAS)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.o$$||'`;\
+@am__fastdepCCAS_TRUE@ $(CPPASCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\
+@am__fastdepCCAS_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po
+@AMDEP_TRUE@@am__fastdepCCAS_FALSE@ $(AM_V_CPPAS)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCCAS_FALSE@ DEPDIR=$(DEPDIR) $(CCASDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCCAS_FALSE@ $(AM_V_CPPAS@am__nodep@)$(CPPASCOMPILE) -c -o $@ $<
+
+.S.obj:
+@am__fastdepCCAS_TRUE@ $(AM_V_CPPAS)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.obj$$||'`;\
+@am__fastdepCCAS_TRUE@ $(CPPASCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ `$(CYGPATH_W) '$<'` &&\
+@am__fastdepCCAS_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po
+@AMDEP_TRUE@@am__fastdepCCAS_FALSE@ $(AM_V_CPPAS)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCCAS_FALSE@ DEPDIR=$(DEPDIR) $(CCASDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCCAS_FALSE@ $(AM_V_CPPAS@am__nodep@)$(CPPASCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
+
+.c.o:
+@am__fastdepCC_TRUE@ $(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.o$$||'`;\
+@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\
+@am__fastdepCC_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $<
+
+.c.obj:
+@am__fastdepCC_TRUE@ $(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.obj$$||'`;\
+@am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ `$(CYGPATH_W) '$<'` &&\
+@am__fastdepCC_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
+install-nobase_includeHEADERS: $(nobase_include_HEADERS)
+ @$(NORMAL_INSTALL)
+ @list='$(nobase_include_HEADERS)'; test -n "$(includedir)" || list=; \
+ if test -n "$$list"; then \
+ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)'"; \
+ $(MKDIR_P) "$(DESTDIR)$(includedir)" || exit 1; \
+ fi; \
+ $(am__nobase_list) | while read dir files; do \
+ xfiles=; for file in $$files; do \
+ if test -f "$$file"; then xfiles="$$xfiles $$file"; \
+ else xfiles="$$xfiles $(srcdir)/$$file"; fi; done; \
+ test -z "$$xfiles" || { \
+ test "x$$dir" = x. || { \
+ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)/$$dir'"; \
+ $(MKDIR_P) "$(DESTDIR)$(includedir)/$$dir"; }; \
+ echo " $(INSTALL_HEADER) $$xfiles '$(DESTDIR)$(includedir)/$$dir'"; \
+ $(INSTALL_HEADER) $$xfiles "$(DESTDIR)$(includedir)/$$dir" || exit $$?; }; \
+ done
+
+uninstall-nobase_includeHEADERS:
+ @$(NORMAL_UNINSTALL)
+ @list='$(nobase_include_HEADERS)'; test -n "$(includedir)" || list=; \
+ $(am__nobase_strip_setup); files=`$(am__nobase_strip)`; \
+ dir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir)
+
+ID: $(am__tagged_files)
+ $(am__define_uniq_tagged_files); mkid -fID $$unique
+tags: tags-am
+TAGS: tags
+
+tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)
+ set x; \
+ here=`pwd`; \
+ $(am__define_uniq_tagged_files); \
+ shift; \
+ if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \
+ test -n "$$unique" || unique=$$empty_fix; \
+ if test $$# -gt 0; then \
+ $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
+ "$$@" $$unique; \
+ else \
+ $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
+ $$unique; \
+ fi; \
+ fi
+ctags: ctags-am
+
+CTAGS: ctags
+ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)
+ $(am__define_uniq_tagged_files); \
+ test -z "$(CTAGS_ARGS)$$unique" \
+ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
+ $$unique
+
+GTAGS:
+ here=`$(am__cd) $(top_builddir) && pwd` \
+ && $(am__cd) $(top_srcdir) \
+ && gtags -i $(GTAGS_ARGS) "$$here"
+cscope: cscope.files
+ test ! -s cscope.files \
+ || $(CSCOPE) -b -q $(AM_CSCOPEFLAGS) $(CSCOPEFLAGS) -i cscope.files $(CSCOPE_ARGS)
+clean-cscope:
+ -rm -f cscope.files
+cscope.files: clean-cscope cscopelist
+cscopelist: cscopelist-am
+
+cscopelist-am: $(am__tagged_files)
+ list='$(am__tagged_files)'; \
+ case "$(srcdir)" in \
+ [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \
+ *) sdir=$(subdir)/$(srcdir) ;; \
+ esac; \
+ for i in $$list; do \
+ if test -f "$$i"; then \
+ echo "$(subdir)/$$i"; \
+ else \
+ echo "$$sdir/$$i"; \
+ fi; \
+ done >> $(top_builddir)/cscope.files
+
+distclean-tags:
+ -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
+ -rm -f cscope.out cscope.in.out cscope.po.out cscope.files
+
+distdir: $(DISTFILES)
+ $(am__remove_distdir)
+ test -d "$(distdir)" || mkdir "$(distdir)"
+ @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
+ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
+ list='$(DISTFILES)'; \
+ dist_files=`for file in $$list; do echo $$file; done | \
+ sed -e "s|^$$srcdirstrip/||;t" \
+ -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \
+ case $$dist_files in \
+ */*) $(MKDIR_P) `echo "$$dist_files" | \
+ sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \
+ sort -u` ;; \
+ esac; \
+ for file in $$dist_files; do \
+ if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
+ if test -d $$d/$$file; then \
+ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \
+ if test -d "$(distdir)/$$file"; then \
+ find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \
+ fi; \
+ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
+ cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \
+ find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \
+ fi; \
+ cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \
+ else \
+ test -f "$(distdir)/$$file" \
+ || cp -p $$d/$$file "$(distdir)/$$file" \
+ || exit 1; \
+ fi; \
+ done
+ -test -n "$(am__skip_mode_fix)" \
+ || find "$(distdir)" -type d ! -perm -755 \
+ -exec chmod u+rwx,go+rx {} \; -o \
+ ! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \
+ ! -type d ! -perm -400 -exec chmod a+r {} \; -o \
+ ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \
+ || chmod -R a+r "$(distdir)"
+dist-gzip: distdir
+ tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz
+ $(am__post_remove_distdir)
+
+dist-bzip2: distdir
+ tardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2
+ $(am__post_remove_distdir)
+
+dist-lzip: distdir
+ tardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz
+ $(am__post_remove_distdir)
+
+dist-xz: distdir
+ tardir=$(distdir) && $(am__tar) | XZ_OPT=$${XZ_OPT--e} xz -c >$(distdir).tar.xz
+ $(am__post_remove_distdir)
+
+dist-tarZ: distdir
+ @echo WARNING: "Support for distribution archives compressed with" \
+ "legacy program 'compress' is deprecated." >&2
+ @echo WARNING: "It will be removed altogether in Automake 2.0" >&2
+ tardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z
+ $(am__post_remove_distdir)
+
+dist-shar: distdir
+ @echo WARNING: "Support for shar distribution archives is" \
+ "deprecated." >&2
+ @echo WARNING: "It will be removed altogether in Automake 2.0" >&2
+ shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz
+ $(am__post_remove_distdir)
+
+dist-zip: distdir
+ -rm -f $(distdir).zip
+ zip -rq $(distdir).zip $(distdir)
+ $(am__post_remove_distdir)
+
+dist dist-all:
+ $(MAKE) $(AM_MAKEFLAGS) $(DIST_TARGETS) am__post_remove_distdir='@:'
+ $(am__post_remove_distdir)
+
+# This target untars the dist file and tries a VPATH configuration. Then
+# it guarantees that the distribution is self-contained by making another
+# tarfile.
+distcheck: dist
+ case '$(DIST_ARCHIVES)' in \
+ *.tar.gz*) \
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
+ *.tar.bz2*) \
+ bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
+ *.tar.lz*) \
+ lzip -dc $(distdir).tar.lz | $(am__untar) ;;\
+ *.tar.xz*) \
+ xz -dc $(distdir).tar.xz | $(am__untar) ;;\
+ *.tar.Z*) \
+ uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
+ *.shar.gz*) \
+ GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\
+ *.zip*) \
+ unzip $(distdir).zip ;;\
+ esac
+ chmod -R a-w $(distdir)
+ chmod u+w $(distdir)
+ mkdir $(distdir)/_build $(distdir)/_build/sub $(distdir)/_inst
+ chmod a-w $(distdir)
+ test -d $(distdir)/_build || exit 0; \
+ dc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\/]:[\\/],/,'` \
+ && dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \
+ && am__cwd=`pwd` \
+ && $(am__cd) $(distdir)/_build/sub \
+ && ../../configure \
+ $(AM_DISTCHECK_CONFIGURE_FLAGS) \
+ $(DISTCHECK_CONFIGURE_FLAGS) \
+ --srcdir=../.. --prefix="$$dc_install_base" \
+ && $(MAKE) $(AM_MAKEFLAGS) \
+ && $(MAKE) $(AM_MAKEFLAGS) dvi \
+ && $(MAKE) $(AM_MAKEFLAGS) check \
+ && $(MAKE) $(AM_MAKEFLAGS) install \
+ && $(MAKE) $(AM_MAKEFLAGS) installcheck \
+ && $(MAKE) $(AM_MAKEFLAGS) uninstall \
+ && $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir="$$dc_install_base" \
+ distuninstallcheck \
+ && chmod -R a-w "$$dc_install_base" \
+ && ({ \
+ (cd ../.. && umask 077 && mkdir "$$dc_destdir") \
+ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" install \
+ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" uninstall \
+ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" \
+ distuninstallcheck_dir="$$dc_destdir" distuninstallcheck; \
+ } || { rm -rf "$$dc_destdir"; exit 1; }) \
+ && rm -rf "$$dc_destdir" \
+ && $(MAKE) $(AM_MAKEFLAGS) dist \
+ && rm -rf $(DIST_ARCHIVES) \
+ && $(MAKE) $(AM_MAKEFLAGS) distcleancheck \
+ && cd "$$am__cwd" \
+ || exit 1
+ $(am__post_remove_distdir)
+ @(echo "$(distdir) archives ready for distribution: "; \
+ list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \
+ sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x'
+distuninstallcheck:
+ @test -n '$(distuninstallcheck_dir)' || { \
+ echo 'ERROR: trying to run $@ with an empty' \
+ '$$(distuninstallcheck_dir)' >&2; \
+ exit 1; \
+ }; \
+ $(am__cd) '$(distuninstallcheck_dir)' || { \
+ echo 'ERROR: cannot chdir into $(distuninstallcheck_dir)' >&2; \
+ exit 1; \
+ }; \
+ test `$(am__distuninstallcheck_listfiles) | wc -l` -eq 0 \
+ || { echo "ERROR: files left after uninstall:" ; \
+ if test -n "$(DESTDIR)"; then \
+ echo " (check DESTDIR support)"; \
+ fi ; \
+ $(distuninstallcheck_listfiles) ; \
+ exit 1; } >&2
+distcleancheck: distclean
+ @if test '$(srcdir)' = . ; then \
+ echo "ERROR: distcleancheck can only run from a VPATH build" ; \
+ exit 1 ; \
+ fi
+ @test `$(distcleancheck_listfiles) | wc -l` -eq 0 \
+ || { echo "ERROR: files left in build directory after distclean:" ; \
+ $(distcleancheck_listfiles) ; \
+ exit 1; } >&2
+check-am: all-am
+check: $(BUILT_SOURCES)
+ $(MAKE) $(AM_MAKEFLAGS) check-am
+all-am: Makefile $(LIBRARIES) $(HEADERS)
+installdirs:
+ for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(includedir)"; do \
+ test -z "$$dir" || $(MKDIR_P) "$$dir"; \
+ done
+install: $(BUILT_SOURCES)
+ $(MAKE) $(AM_MAKEFLAGS) install-am
+install-exec: install-exec-am
+install-data: install-data-am
+uninstall: uninstall-am
+
+install-am: all-am
+ @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
+
+installcheck: installcheck-am
+install-strip:
+ if test -z '$(STRIP)'; then \
+ $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
+ install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
+ install; \
+ else \
+ $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
+ install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
+ "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \
+ fi
+mostlyclean-generic:
+
+clean-generic:
+
+distclean-generic:
+ -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
+ -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES)
+ -rm -f gloss/$(DEPDIR)/$(am__dirstamp)
+ -rm -f gloss/$(am__dirstamp)
+ -rm -f segger/$(DEPDIR)/$(am__dirstamp)
+ -rm -f segger/$(am__dirstamp)
+ -rm -f src/$(DEPDIR)/$(am__dirstamp)
+ -rm -f src/$(am__dirstamp)
+ -rm -f src/drivers/$(DEPDIR)/$(am__dirstamp)
+ -rm -f src/drivers/$(am__dirstamp)
+
+maintainer-clean-generic:
+ @echo "This command is intended for maintainers to use"
+ @echo "it deletes files that may require special tools to rebuild."
+ -test -z "$(BUILT_SOURCES)" || rm -f $(BUILT_SOURCES)
+clean: clean-am
+
+clean-am: clean-generic clean-libLIBRARIES clean-local mostlyclean-am
+
+distclean: distclean-am
+ -rm -f $(am__CONFIG_DISTCLEAN_FILES)
+ -rm -rf gloss/$(DEPDIR) segger/$(DEPDIR) src/$(DEPDIR) src/drivers/$(DEPDIR)
+ -rm -f Makefile
+distclean-am: clean-am distclean-compile distclean-generic \
+ distclean-tags
+
+dvi: dvi-am
+
+dvi-am:
+
+html: html-am
+
+html-am:
+
+info: info-am
+
+info-am:
+
+install-data-am: install-nobase_includeHEADERS
+
+install-dvi: install-dvi-am
+
+install-dvi-am:
+
+install-exec-am: install-libLIBRARIES
+
+install-html: install-html-am
+
+install-html-am:
+
+install-info: install-info-am
+
+install-info-am:
+
+install-man:
+
+install-pdf: install-pdf-am
+
+install-pdf-am:
+
+install-ps: install-ps-am
+
+install-ps-am:
+
+installcheck-am:
+
+maintainer-clean: maintainer-clean-am
+ -rm -f $(am__CONFIG_DISTCLEAN_FILES)
+ -rm -rf $(top_srcdir)/autom4te.cache
+ -rm -rf gloss/$(DEPDIR) segger/$(DEPDIR) src/$(DEPDIR) src/drivers/$(DEPDIR)
+ -rm -f Makefile
+maintainer-clean-am: distclean-am maintainer-clean-generic
+
+mostlyclean: mostlyclean-am
+
+mostlyclean-am: mostlyclean-compile mostlyclean-generic
+
+pdf: pdf-am
+
+pdf-am:
+
+ps: ps-am
+
+ps-am:
+
+uninstall-am: uninstall-libLIBRARIES uninstall-nobase_includeHEADERS
+
+.MAKE: all check install install-am install-strip
+
+.PHONY: CTAGS GTAGS TAGS all all-am am--refresh check check-am clean \
+ clean-cscope clean-generic clean-libLIBRARIES clean-local \
+ cscope cscopelist-am ctags ctags-am dist dist-all dist-bzip2 \
+ dist-gzip dist-lzip dist-shar dist-tarZ dist-xz dist-zip \
+ distcheck distclean distclean-compile distclean-generic \
+ distclean-tags distcleancheck distdir distuninstallcheck dvi \
+ dvi-am html html-am info info-am install install-am \
+ install-data install-data-am install-dvi install-dvi-am \
+ install-exec install-exec-am install-html install-html-am \
+ install-info install-info-am install-libLIBRARIES install-man \
+ install-nobase_includeHEADERS install-pdf install-pdf-am \
+ install-ps install-ps-am install-strip installcheck \
+ installcheck-am installdirs maintainer-clean \
+ maintainer-clean-generic mostlyclean mostlyclean-compile \
+ mostlyclean-generic pdf pdf-am ps ps-am tags tags-am uninstall \
+ uninstall-am uninstall-libLIBRARIES \
+ uninstall-nobase_includeHEADERS
+
+.PRECIOUS: Makefile
+
+
+metal/machine.h: @MACHINE_HEADER@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+metal/machine/inline.h: @MACHINE_INLINE@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+metal/machine/platform.h: @PLATFORM_HEADER@
+ @mkdir -p $(dir $@)
+ cp $< $@
+
+########################################################
+# Clean
+########################################################
+
+clean-local:
+ -rm -rf metal/machine.h metal/machine/inline.h
+ -rm -rf metal/machine/platform.h
+
+# Tell versions [3.59,3.63) of GNU make to not export all variables.
+# Otherwise a system limit (for SysV at least) may be exceeded.
+.NOEXPORT:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/README.md b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/README.md
new file mode 100644
index 000000000..e8237d04c
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/README.md
@@ -0,0 +1,4 @@
+# Freedom Metal Machine Compatibility Library
+
+Documentation for the Freedom Metal library [can be found here](https://sifive.github.io/freedom-metal-docs/).
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/aclocal.m4 b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/aclocal.m4
new file mode 100644
index 000000000..42ec7eedc
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/aclocal.m4
@@ -0,0 +1,1268 @@
+# generated automatically by aclocal 1.15 -*- Autoconf -*-
+
+# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
+# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+# PARTICULAR PURPOSE.
+
+m4_ifndef([AC_CONFIG_MACRO_DIRS], [m4_defun([_AM_CONFIG_MACRO_DIRS], [])m4_defun([AC_CONFIG_MACRO_DIRS], [_AM_CONFIG_MACRO_DIRS($@)])])
+m4_ifndef([AC_AUTOCONF_VERSION],
+ [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
+m4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.69],,
+[m4_warning([this file was generated for autoconf 2.69.
+You have another version of autoconf. It may work, but is not guaranteed to.
+If you have problems, you may need to regenerate the build system entirely.
+To do so, use the procedure documented by the package, typically 'autoreconf'.])])
+
+# Copyright (C) 2002-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_AUTOMAKE_VERSION(VERSION)
+# ----------------------------
+# Automake X.Y traces this macro to ensure aclocal.m4 has been
+# generated from the m4 files accompanying Automake X.Y.
+# (This private macro should not be called outside this file.)
+AC_DEFUN([AM_AUTOMAKE_VERSION],
+[am__api_version='1.15'
+dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
+dnl require some minimum version. Point them to the right macro.
+m4_if([$1], [1.15], [],
+ [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
+])
+
+# _AM_AUTOCONF_VERSION(VERSION)
+# -----------------------------
+# aclocal traces this macro to find the Autoconf version.
+# This is a private macro too. Using m4_define simplifies
+# the logic in aclocal, which can simply ignore this definition.
+m4_define([_AM_AUTOCONF_VERSION], [])
+
+# AM_SET_CURRENT_AUTOMAKE_VERSION
+# -------------------------------
+# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
+# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
+AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
+[AM_AUTOMAKE_VERSION([1.15])dnl
+m4_ifndef([AC_AUTOCONF_VERSION],
+ [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
+_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
+
+# Copyright (C) 2011-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_AR([ACT-IF-FAIL])
+# -------------------------
+# Try to determine the archiver interface, and trigger the ar-lib wrapper
+# if it is needed. If the detection of archiver interface fails, run
+# ACT-IF-FAIL (default is to abort configure with a proper error message).
+AC_DEFUN([AM_PROG_AR],
+[AC_BEFORE([$0], [LT_INIT])dnl
+AC_BEFORE([$0], [AC_PROG_LIBTOOL])dnl
+AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+AC_REQUIRE_AUX_FILE([ar-lib])dnl
+AC_CHECK_TOOLS([AR], [ar lib "link -lib"], [false])
+: ${AR=ar}
+
+AC_CACHE_CHECK([the archiver ($AR) interface], [am_cv_ar_interface],
+ [AC_LANG_PUSH([C])
+ am_cv_ar_interface=ar
+ AC_COMPILE_IFELSE([AC_LANG_SOURCE([[int some_variable = 0;]])],
+ [am_ar_try='$AR cru libconftest.a conftest.$ac_objext >&AS_MESSAGE_LOG_FD'
+ AC_TRY_EVAL([am_ar_try])
+ if test "$ac_status" -eq 0; then
+ am_cv_ar_interface=ar
+ else
+ am_ar_try='$AR -NOLOGO -OUT:conftest.lib conftest.$ac_objext >&AS_MESSAGE_LOG_FD'
+ AC_TRY_EVAL([am_ar_try])
+ if test "$ac_status" -eq 0; then
+ am_cv_ar_interface=lib
+ else
+ am_cv_ar_interface=unknown
+ fi
+ fi
+ rm -f conftest.lib libconftest.a
+ ])
+ AC_LANG_POP([C])])
+
+case $am_cv_ar_interface in
+ar)
+ ;;
+lib)
+ # Microsoft lib, so override with the ar-lib wrapper script.
+ # FIXME: It is wrong to rewrite AR.
+ # But if we don't then we get into trouble of one sort or another.
+ # A longer-term fix would be to have automake use am__AR in this case,
+ # and then we could set am__AR="$am_aux_dir/ar-lib \$(AR)" or something
+ # similar.
+ AR="$am_aux_dir/ar-lib $AR"
+ ;;
+unknown)
+ m4_default([$1],
+ [AC_MSG_ERROR([could not determine $AR interface])])
+ ;;
+esac
+AC_SUBST([AR])dnl
+])
+
+# Figure out how to run the assembler. -*- Autoconf -*-
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_AS
+# ----------
+AC_DEFUN([AM_PROG_AS],
+[# By default we simply use the C compiler to build assembly code.
+AC_REQUIRE([AC_PROG_CC])
+test "${CCAS+set}" = set || CCAS=$CC
+test "${CCASFLAGS+set}" = set || CCASFLAGS=$CFLAGS
+AC_ARG_VAR([CCAS], [assembler compiler command (defaults to CC)])
+AC_ARG_VAR([CCASFLAGS], [assembler compiler flags (defaults to CFLAGS)])
+_AM_IF_OPTION([no-dependencies],, [_AM_DEPENDENCIES([CCAS])])dnl
+])
+
+# AM_AUX_DIR_EXPAND -*- Autoconf -*-
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets
+# $ac_aux_dir to '$srcdir/foo'. In other projects, it is set to
+# '$srcdir', '$srcdir/..', or '$srcdir/../..'.
+#
+# Of course, Automake must honor this variable whenever it calls a
+# tool from the auxiliary directory. The problem is that $srcdir (and
+# therefore $ac_aux_dir as well) can be either absolute or relative,
+# depending on how configure is run. This is pretty annoying, since
+# it makes $ac_aux_dir quite unusable in subdirectories: in the top
+# source directory, any form will work fine, but in subdirectories a
+# relative path needs to be adjusted first.
+#
+# $ac_aux_dir/missing
+# fails when called from a subdirectory if $ac_aux_dir is relative
+# $top_srcdir/$ac_aux_dir/missing
+# fails if $ac_aux_dir is absolute,
+# fails when called from a subdirectory in a VPATH build with
+# a relative $ac_aux_dir
+#
+# The reason of the latter failure is that $top_srcdir and $ac_aux_dir
+# are both prefixed by $srcdir. In an in-source build this is usually
+# harmless because $srcdir is '.', but things will broke when you
+# start a VPATH build or use an absolute $srcdir.
+#
+# So we could use something similar to $top_srcdir/$ac_aux_dir/missing,
+# iff we strip the leading $srcdir from $ac_aux_dir. That would be:
+# am_aux_dir='\$(top_srcdir)/'`expr "$ac_aux_dir" : "$srcdir//*\(.*\)"`
+# and then we would define $MISSING as
+# MISSING="\${SHELL} $am_aux_dir/missing"
+# This will work as long as MISSING is not called from configure, because
+# unfortunately $(top_srcdir) has no meaning in configure.
+# However there are other variables, like CC, which are often used in
+# configure, and could therefore not use this "fixed" $ac_aux_dir.
+#
+# Another solution, used here, is to always expand $ac_aux_dir to an
+# absolute PATH. The drawback is that using absolute paths prevent a
+# configured tree to be moved without reconfiguration.
+
+AC_DEFUN([AM_AUX_DIR_EXPAND],
+[AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl
+# Expand $ac_aux_dir to an absolute path.
+am_aux_dir=`cd "$ac_aux_dir" && pwd`
+])
+
+# AM_CONDITIONAL -*- Autoconf -*-
+
+# Copyright (C) 1997-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_CONDITIONAL(NAME, SHELL-CONDITION)
+# -------------------------------------
+# Define a conditional.
+AC_DEFUN([AM_CONDITIONAL],
+[AC_PREREQ([2.52])dnl
+ m4_if([$1], [TRUE], [AC_FATAL([$0: invalid condition: $1])],
+ [$1], [FALSE], [AC_FATAL([$0: invalid condition: $1])])dnl
+AC_SUBST([$1_TRUE])dnl
+AC_SUBST([$1_FALSE])dnl
+_AM_SUBST_NOTMAKE([$1_TRUE])dnl
+_AM_SUBST_NOTMAKE([$1_FALSE])dnl
+m4_define([_AM_COND_VALUE_$1], [$2])dnl
+if $2; then
+ $1_TRUE=
+ $1_FALSE='#'
+else
+ $1_TRUE='#'
+ $1_FALSE=
+fi
+AC_CONFIG_COMMANDS_PRE(
+[if test -z "${$1_TRUE}" && test -z "${$1_FALSE}"; then
+ AC_MSG_ERROR([[conditional "$1" was never defined.
+Usually this means the macro was only invoked conditionally.]])
+fi])])
+
+# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+
+# There are a few dirty hacks below to avoid letting 'AC_PROG_CC' be
+# written in clear, in which case automake, when reading aclocal.m4,
+# will think it sees a *use*, and therefore will trigger all it's
+# C support machinery. Also note that it means that autoscan, seeing
+# CC etc. in the Makefile, will ask for an AC_PROG_CC use...
+
+
+# _AM_DEPENDENCIES(NAME)
+# ----------------------
+# See how the compiler implements dependency checking.
+# NAME is "CC", "CXX", "OBJC", "OBJCXX", "UPC", or "GJC".
+# We try a few techniques and use that to set a single cache variable.
+#
+# We don't AC_REQUIRE the corresponding AC_PROG_CC since the latter was
+# modified to invoke _AM_DEPENDENCIES(CC); we would have a circular
+# dependency, and given that the user is not expected to run this macro,
+# just rely on AC_PROG_CC.
+AC_DEFUN([_AM_DEPENDENCIES],
+[AC_REQUIRE([AM_SET_DEPDIR])dnl
+AC_REQUIRE([AM_OUTPUT_DEPENDENCY_COMMANDS])dnl
+AC_REQUIRE([AM_MAKE_INCLUDE])dnl
+AC_REQUIRE([AM_DEP_TRACK])dnl
+
+m4_if([$1], [CC], [depcc="$CC" am_compiler_list=],
+ [$1], [CXX], [depcc="$CXX" am_compiler_list=],
+ [$1], [OBJC], [depcc="$OBJC" am_compiler_list='gcc3 gcc'],
+ [$1], [OBJCXX], [depcc="$OBJCXX" am_compiler_list='gcc3 gcc'],
+ [$1], [UPC], [depcc="$UPC" am_compiler_list=],
+ [$1], [GCJ], [depcc="$GCJ" am_compiler_list='gcc3 gcc'],
+ [depcc="$$1" am_compiler_list=])
+
+AC_CACHE_CHECK([dependency style of $depcc],
+ [am_cv_$1_dependencies_compiler_type],
+[if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then
+ # We make a subdir and do the tests there. Otherwise we can end up
+ # making bogus files that we don't know about and never remove. For
+ # instance it was reported that on HP-UX the gcc test will end up
+ # making a dummy file named 'D' -- because '-MD' means "put the output
+ # in D".
+ rm -rf conftest.dir
+ mkdir conftest.dir
+ # Copy depcomp to subdir because otherwise we won't find it if we're
+ # using a relative directory.
+ cp "$am_depcomp" conftest.dir
+ cd conftest.dir
+ # We will build objects and dependencies in a subdirectory because
+ # it helps to detect inapplicable dependency modes. For instance
+ # both Tru64's cc and ICC support -MD to output dependencies as a
+ # side effect of compilation, but ICC will put the dependencies in
+ # the current directory while Tru64 will put them in the object
+ # directory.
+ mkdir sub
+
+ am_cv_$1_dependencies_compiler_type=none
+ if test "$am_compiler_list" = ""; then
+ am_compiler_list=`sed -n ['s/^#*\([a-zA-Z0-9]*\))$/\1/p'] < ./depcomp`
+ fi
+ am__universal=false
+ m4_case([$1], [CC],
+ [case " $depcc " in #(
+ *\ -arch\ *\ -arch\ *) am__universal=true ;;
+ esac],
+ [CXX],
+ [case " $depcc " in #(
+ *\ -arch\ *\ -arch\ *) am__universal=true ;;
+ esac])
+
+ for depmode in $am_compiler_list; do
+ # Setup a source with many dependencies, because some compilers
+ # like to wrap large dependency lists on column 80 (with \), and
+ # we should not choose a depcomp mode which is confused by this.
+ #
+ # We need to recreate these files for each test, as the compiler may
+ # overwrite some of them when testing with obscure command lines.
+ # This happens at least with the AIX C compiler.
+ : > sub/conftest.c
+ for i in 1 2 3 4 5 6; do
+ echo '#include "conftst'$i'.h"' >> sub/conftest.c
+ # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with
+ # Solaris 10 /bin/sh.
+ echo '/* dummy */' > sub/conftst$i.h
+ done
+ echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf
+
+ # We check with '-c' and '-o' for the sake of the "dashmstdout"
+ # mode. It turns out that the SunPro C++ compiler does not properly
+ # handle '-M -o', and we need to detect this. Also, some Intel
+ # versions had trouble with output in subdirs.
+ am__obj=sub/conftest.${OBJEXT-o}
+ am__minus_obj="-o $am__obj"
+ case $depmode in
+ gcc)
+ # This depmode causes a compiler race in universal mode.
+ test "$am__universal" = false || continue
+ ;;
+ nosideeffect)
+ # After this tag, mechanisms are not by side-effect, so they'll
+ # only be used when explicitly requested.
+ if test "x$enable_dependency_tracking" = xyes; then
+ continue
+ else
+ break
+ fi
+ ;;
+ msvc7 | msvc7msys | msvisualcpp | msvcmsys)
+ # This compiler won't grok '-c -o', but also, the minuso test has
+ # not run yet. These depmodes are late enough in the game, and
+ # so weak that their functioning should not be impacted.
+ am__obj=conftest.${OBJEXT-o}
+ am__minus_obj=
+ ;;
+ none) break ;;
+ esac
+ if depmode=$depmode \
+ source=sub/conftest.c object=$am__obj \
+ depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \
+ $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \
+ >/dev/null 2>conftest.err &&
+ grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&
+ ${MAKE-make} -s -f confmf > /dev/null 2>&1; then
+ # icc doesn't choke on unknown options, it will just issue warnings
+ # or remarks (even with -Werror). So we grep stderr for any message
+ # that says an option was ignored or not supported.
+ # When given -MP, icc 7.0 and 7.1 complain thusly:
+ # icc: Command line warning: ignoring option '-M'; no argument required
+ # The diagnosis changed in icc 8.0:
+ # icc: Command line remark: option '-MP' not supported
+ if (grep 'ignoring option' conftest.err ||
+ grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else
+ am_cv_$1_dependencies_compiler_type=$depmode
+ break
+ fi
+ fi
+ done
+
+ cd ..
+ rm -rf conftest.dir
+else
+ am_cv_$1_dependencies_compiler_type=none
+fi
+])
+AC_SUBST([$1DEPMODE], [depmode=$am_cv_$1_dependencies_compiler_type])
+AM_CONDITIONAL([am__fastdep$1], [
+ test "x$enable_dependency_tracking" != xno \
+ && test "$am_cv_$1_dependencies_compiler_type" = gcc3])
+])
+
+
+# AM_SET_DEPDIR
+# -------------
+# Choose a directory name for dependency files.
+# This macro is AC_REQUIREd in _AM_DEPENDENCIES.
+AC_DEFUN([AM_SET_DEPDIR],
+[AC_REQUIRE([AM_SET_LEADING_DOT])dnl
+AC_SUBST([DEPDIR], ["${am__leading_dot}deps"])dnl
+])
+
+
+# AM_DEP_TRACK
+# ------------
+AC_DEFUN([AM_DEP_TRACK],
+[AC_ARG_ENABLE([dependency-tracking], [dnl
+AS_HELP_STRING(
+ [--enable-dependency-tracking],
+ [do not reject slow dependency extractors])
+AS_HELP_STRING(
+ [--disable-dependency-tracking],
+ [speeds up one-time build])])
+if test "x$enable_dependency_tracking" != xno; then
+ am_depcomp="$ac_aux_dir/depcomp"
+ AMDEPBACKSLASH='\'
+ am__nodep='_no'
+fi
+AM_CONDITIONAL([AMDEP], [test "x$enable_dependency_tracking" != xno])
+AC_SUBST([AMDEPBACKSLASH])dnl
+_AM_SUBST_NOTMAKE([AMDEPBACKSLASH])dnl
+AC_SUBST([am__nodep])dnl
+_AM_SUBST_NOTMAKE([am__nodep])dnl
+])
+
+# Generate code to set up dependency tracking. -*- Autoconf -*-
+
+# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+
+# _AM_OUTPUT_DEPENDENCY_COMMANDS
+# ------------------------------
+AC_DEFUN([_AM_OUTPUT_DEPENDENCY_COMMANDS],
+[{
+ # Older Autoconf quotes --file arguments for eval, but not when files
+ # are listed without --file. Let's play safe and only enable the eval
+ # if we detect the quoting.
+ case $CONFIG_FILES in
+ *\'*) eval set x "$CONFIG_FILES" ;;
+ *) set x $CONFIG_FILES ;;
+ esac
+ shift
+ for mf
+ do
+ # Strip MF so we end up with the name of the file.
+ mf=`echo "$mf" | sed -e 's/:.*$//'`
+ # Check whether this is an Automake generated Makefile or not.
+ # We used to match only the files named 'Makefile.in', but
+ # some people rename them; so instead we look at the file content.
+ # Grep'ing the first line is not enough: some people post-process
+ # each Makefile.in and add a new line on top of each file to say so.
+ # Grep'ing the whole file is not good either: AIX grep has a line
+ # limit of 2048, but all sed's we know have understand at least 4000.
+ if sed -n 's,^#.*generated by automake.*,X,p' "$mf" | grep X >/dev/null 2>&1; then
+ dirpart=`AS_DIRNAME("$mf")`
+ else
+ continue
+ fi
+ # Extract the definition of DEPDIR, am__include, and am__quote
+ # from the Makefile without running 'make'.
+ DEPDIR=`sed -n 's/^DEPDIR = //p' < "$mf"`
+ test -z "$DEPDIR" && continue
+ am__include=`sed -n 's/^am__include = //p' < "$mf"`
+ test -z "$am__include" && continue
+ am__quote=`sed -n 's/^am__quote = //p' < "$mf"`
+ # Find all dependency output files, they are included files with
+ # $(DEPDIR) in their names. We invoke sed twice because it is the
+ # simplest approach to changing $(DEPDIR) to its actual value in the
+ # expansion.
+ for file in `sed -n "
+ s/^$am__include $am__quote\(.*(DEPDIR).*\)$am__quote"'$/\1/p' <"$mf" | \
+ sed -e 's/\$(DEPDIR)/'"$DEPDIR"'/g'`; do
+ # Make sure the directory exists.
+ test -f "$dirpart/$file" && continue
+ fdir=`AS_DIRNAME(["$file"])`
+ AS_MKDIR_P([$dirpart/$fdir])
+ # echo "creating $dirpart/$file"
+ echo '# dummy' > "$dirpart/$file"
+ done
+ done
+}
+])# _AM_OUTPUT_DEPENDENCY_COMMANDS
+
+
+# AM_OUTPUT_DEPENDENCY_COMMANDS
+# -----------------------------
+# This macro should only be invoked once -- use via AC_REQUIRE.
+#
+# This code is only required when automatic dependency tracking
+# is enabled. FIXME. This creates each '.P' file that we will
+# need in order to bootstrap the dependency handling code.
+AC_DEFUN([AM_OUTPUT_DEPENDENCY_COMMANDS],
+[AC_CONFIG_COMMANDS([depfiles],
+ [test x"$AMDEP_TRUE" != x"" || _AM_OUTPUT_DEPENDENCY_COMMANDS],
+ [AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"])
+])
+
+# Do all the work for Automake. -*- Autoconf -*-
+
+# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# This macro actually does too much. Some checks are only needed if
+# your package does certain things. But this isn't really a big deal.
+
+dnl Redefine AC_PROG_CC to automatically invoke _AM_PROG_CC_C_O.
+m4_define([AC_PROG_CC],
+m4_defn([AC_PROG_CC])
+[_AM_PROG_CC_C_O
+])
+
+# AM_INIT_AUTOMAKE(PACKAGE, VERSION, [NO-DEFINE])
+# AM_INIT_AUTOMAKE([OPTIONS])
+# -----------------------------------------------
+# The call with PACKAGE and VERSION arguments is the old style
+# call (pre autoconf-2.50), which is being phased out. PACKAGE
+# and VERSION should now be passed to AC_INIT and removed from
+# the call to AM_INIT_AUTOMAKE.
+# We support both call styles for the transition. After
+# the next Automake release, Autoconf can make the AC_INIT
+# arguments mandatory, and then we can depend on a new Autoconf
+# release and drop the old call support.
+AC_DEFUN([AM_INIT_AUTOMAKE],
+[AC_PREREQ([2.65])dnl
+dnl Autoconf wants to disallow AM_ names. We explicitly allow
+dnl the ones we care about.
+m4_pattern_allow([^AM_[A-Z]+FLAGS$])dnl
+AC_REQUIRE([AM_SET_CURRENT_AUTOMAKE_VERSION])dnl
+AC_REQUIRE([AC_PROG_INSTALL])dnl
+if test "`cd $srcdir && pwd`" != "`pwd`"; then
+ # Use -I$(srcdir) only when $(srcdir) != ., so that make's output
+ # is not polluted with repeated "-I."
+ AC_SUBST([am__isrc], [' -I$(srcdir)'])_AM_SUBST_NOTMAKE([am__isrc])dnl
+ # test to see if srcdir already configured
+ if test -f $srcdir/config.status; then
+ AC_MSG_ERROR([source directory already configured; run "make distclean" there first])
+ fi
+fi
+
+# test whether we have cygpath
+if test -z "$CYGPATH_W"; then
+ if (cygpath --version) >/dev/null 2>/dev/null; then
+ CYGPATH_W='cygpath -w'
+ else
+ CYGPATH_W=echo
+ fi
+fi
+AC_SUBST([CYGPATH_W])
+
+# Define the identity of the package.
+dnl Distinguish between old-style and new-style calls.
+m4_ifval([$2],
+[AC_DIAGNOSE([obsolete],
+ [$0: two- and three-arguments forms are deprecated.])
+m4_ifval([$3], [_AM_SET_OPTION([no-define])])dnl
+ AC_SUBST([PACKAGE], [$1])dnl
+ AC_SUBST([VERSION], [$2])],
+[_AM_SET_OPTIONS([$1])dnl
+dnl Diagnose old-style AC_INIT with new-style AM_AUTOMAKE_INIT.
+m4_if(
+ m4_ifdef([AC_PACKAGE_NAME], [ok]):m4_ifdef([AC_PACKAGE_VERSION], [ok]),
+ [ok:ok],,
+ [m4_fatal([AC_INIT should be called with package and version arguments])])dnl
+ AC_SUBST([PACKAGE], ['AC_PACKAGE_TARNAME'])dnl
+ AC_SUBST([VERSION], ['AC_PACKAGE_VERSION'])])dnl
+
+_AM_IF_OPTION([no-define],,
+[AC_DEFINE_UNQUOTED([PACKAGE], ["$PACKAGE"], [Name of package])
+ AC_DEFINE_UNQUOTED([VERSION], ["$VERSION"], [Version number of package])])dnl
+
+# Some tools Automake needs.
+AC_REQUIRE([AM_SANITY_CHECK])dnl
+AC_REQUIRE([AC_ARG_PROGRAM])dnl
+AM_MISSING_PROG([ACLOCAL], [aclocal-${am__api_version}])
+AM_MISSING_PROG([AUTOCONF], [autoconf])
+AM_MISSING_PROG([AUTOMAKE], [automake-${am__api_version}])
+AM_MISSING_PROG([AUTOHEADER], [autoheader])
+AM_MISSING_PROG([MAKEINFO], [makeinfo])
+AC_REQUIRE([AM_PROG_INSTALL_SH])dnl
+AC_REQUIRE([AM_PROG_INSTALL_STRIP])dnl
+AC_REQUIRE([AC_PROG_MKDIR_P])dnl
+# For better backward compatibility. To be removed once Automake 1.9.x
+# dies out for good. For more background, see:
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>
+AC_SUBST([mkdir_p], ['$(MKDIR_P)'])
+# We need awk for the "check" target (and possibly the TAP driver). The
+# system "awk" is bad on some platforms.
+AC_REQUIRE([AC_PROG_AWK])dnl
+AC_REQUIRE([AC_PROG_MAKE_SET])dnl
+AC_REQUIRE([AM_SET_LEADING_DOT])dnl
+_AM_IF_OPTION([tar-ustar], [_AM_PROG_TAR([ustar])],
+ [_AM_IF_OPTION([tar-pax], [_AM_PROG_TAR([pax])],
+ [_AM_PROG_TAR([v7])])])
+_AM_IF_OPTION([no-dependencies],,
+[AC_PROVIDE_IFELSE([AC_PROG_CC],
+ [_AM_DEPENDENCIES([CC])],
+ [m4_define([AC_PROG_CC],
+ m4_defn([AC_PROG_CC])[_AM_DEPENDENCIES([CC])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_CXX],
+ [_AM_DEPENDENCIES([CXX])],
+ [m4_define([AC_PROG_CXX],
+ m4_defn([AC_PROG_CXX])[_AM_DEPENDENCIES([CXX])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_OBJC],
+ [_AM_DEPENDENCIES([OBJC])],
+ [m4_define([AC_PROG_OBJC],
+ m4_defn([AC_PROG_OBJC])[_AM_DEPENDENCIES([OBJC])])])dnl
+AC_PROVIDE_IFELSE([AC_PROG_OBJCXX],
+ [_AM_DEPENDENCIES([OBJCXX])],
+ [m4_define([AC_PROG_OBJCXX],
+ m4_defn([AC_PROG_OBJCXX])[_AM_DEPENDENCIES([OBJCXX])])])dnl
+])
+AC_REQUIRE([AM_SILENT_RULES])dnl
+dnl The testsuite driver may need to know about EXEEXT, so add the
+dnl 'am__EXEEXT' conditional if _AM_COMPILER_EXEEXT was seen. This
+dnl macro is hooked onto _AC_COMPILER_EXEEXT early, see below.
+AC_CONFIG_COMMANDS_PRE(dnl
+[m4_provide_if([_AM_COMPILER_EXEEXT],
+ [AM_CONDITIONAL([am__EXEEXT], [test -n "$EXEEXT"])])])dnl
+
+# POSIX will say in a future version that running "rm -f" with no argument
+# is OK; and we want to be able to make that assumption in our Makefile
+# recipes. So use an aggressive probe to check that the usage we want is
+# actually supported "in the wild" to an acceptable degree.
+# See automake bug#10828.
+# To make any issue more visible, cause the running configure to be aborted
+# by default if the 'rm' program in use doesn't match our expectations; the
+# user can still override this though.
+if rm -f && rm -fr && rm -rf; then : OK; else
+ cat >&2 <<'END'
+Oops!
+
+Your 'rm' program seems unable to run without file operands specified
+on the command line, even when the '-f' option is present. This is contrary
+to the behaviour of most rm programs out there, and not conforming with
+the upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>
+
+Please tell bug-automake@gnu.org about your system, including the value
+of your $PATH and any error possibly output before this message. This
+can help us improve future automake versions.
+
+END
+ if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then
+ echo 'Configuration will proceed anyway, since you have set the' >&2
+ echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2
+ echo >&2
+ else
+ cat >&2 <<'END'
+Aborting the configuration process, to ensure you take notice of the issue.
+
+You can download and install GNU coreutils to get an 'rm' implementation
+that behaves properly: <http://www.gnu.org/software/coreutils/>.
+
+If you want to complete the configuration process using your problematic
+'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM
+to "yes", and re-run configure.
+
+END
+ AC_MSG_ERROR([Your 'rm' program is bad, sorry.])
+ fi
+fi
+dnl The trailing newline in this macro's definition is deliberate, for
+dnl backward compatibility and to allow trailing 'dnl'-style comments
+dnl after the AM_INIT_AUTOMAKE invocation. See automake bug#16841.
+])
+
+dnl Hook into '_AC_COMPILER_EXEEXT' early to learn its expansion. Do not
+dnl add the conditional right here, as _AC_COMPILER_EXEEXT may be further
+dnl mangled by Autoconf and run in a shell conditional statement.
+m4_define([_AC_COMPILER_EXEEXT],
+m4_defn([_AC_COMPILER_EXEEXT])[m4_provide([_AM_COMPILER_EXEEXT])])
+
+# When config.status generates a header, we must update the stamp-h file.
+# This file resides in the same directory as the config header
+# that is generated. The stamp files are numbered to have different names.
+
+# Autoconf calls _AC_AM_CONFIG_HEADER_HOOK (when defined) in the
+# loop where config.status creates the headers, so we can generate
+# our stamp files there.
+AC_DEFUN([_AC_AM_CONFIG_HEADER_HOOK],
+[# Compute $1's index in $config_headers.
+_am_arg=$1
+_am_stamp_count=1
+for _am_header in $config_headers :; do
+ case $_am_header in
+ $_am_arg | $_am_arg:* )
+ break ;;
+ * )
+ _am_stamp_count=`expr $_am_stamp_count + 1` ;;
+ esac
+done
+echo "timestamp for $_am_arg" >`AS_DIRNAME(["$_am_arg"])`/stamp-h[]$_am_stamp_count])
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_INSTALL_SH
+# ------------------
+# Define $install_sh.
+AC_DEFUN([AM_PROG_INSTALL_SH],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+if test x"${install_sh+set}" != xset; then
+ case $am_aux_dir in
+ *\ * | *\ *)
+ install_sh="\${SHELL} '$am_aux_dir/install-sh'" ;;
+ *)
+ install_sh="\${SHELL} $am_aux_dir/install-sh"
+ esac
+fi
+AC_SUBST([install_sh])])
+
+# Copyright (C) 2003-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# Check whether the underlying file-system supports filenames
+# with a leading dot. For instance MS-DOS doesn't.
+AC_DEFUN([AM_SET_LEADING_DOT],
+[rm -rf .tst 2>/dev/null
+mkdir .tst 2>/dev/null
+if test -d .tst; then
+ am__leading_dot=.
+else
+ am__leading_dot=_
+fi
+rmdir .tst 2>/dev/null
+AC_SUBST([am__leading_dot])])
+
+# Add --enable-maintainer-mode option to configure. -*- Autoconf -*-
+# From Jim Meyering
+
+# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_MAINTAINER_MODE([DEFAULT-MODE])
+# ----------------------------------
+# Control maintainer-specific portions of Makefiles.
+# Default is to disable them, unless 'enable' is passed literally.
+# For symmetry, 'disable' may be passed as well. Anyway, the user
+# can override the default with the --enable/--disable switch.
+AC_DEFUN([AM_MAINTAINER_MODE],
+[m4_case(m4_default([$1], [disable]),
+ [enable], [m4_define([am_maintainer_other], [disable])],
+ [disable], [m4_define([am_maintainer_other], [enable])],
+ [m4_define([am_maintainer_other], [enable])
+ m4_warn([syntax], [unexpected argument to AM@&t@_MAINTAINER_MODE: $1])])
+AC_MSG_CHECKING([whether to enable maintainer-specific portions of Makefiles])
+ dnl maintainer-mode's default is 'disable' unless 'enable' is passed
+ AC_ARG_ENABLE([maintainer-mode],
+ [AS_HELP_STRING([--]am_maintainer_other[-maintainer-mode],
+ am_maintainer_other[ make rules and dependencies not useful
+ (and sometimes confusing) to the casual installer])],
+ [USE_MAINTAINER_MODE=$enableval],
+ [USE_MAINTAINER_MODE=]m4_if(am_maintainer_other, [enable], [no], [yes]))
+ AC_MSG_RESULT([$USE_MAINTAINER_MODE])
+ AM_CONDITIONAL([MAINTAINER_MODE], [test $USE_MAINTAINER_MODE = yes])
+ MAINT=$MAINTAINER_MODE_TRUE
+ AC_SUBST([MAINT])dnl
+]
+)
+
+# Check to see how 'make' treats includes. -*- Autoconf -*-
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_MAKE_INCLUDE()
+# -----------------
+# Check to see how make treats includes.
+AC_DEFUN([AM_MAKE_INCLUDE],
+[am_make=${MAKE-make}
+cat > confinc << 'END'
+am__doit:
+ @echo this is the am__doit target
+.PHONY: am__doit
+END
+# If we don't find an include directive, just comment out the code.
+AC_MSG_CHECKING([for style of include used by $am_make])
+am__include="#"
+am__quote=
+_am_result=none
+# First try GNU make style include.
+echo "include confinc" > confmf
+# Ignore all kinds of additional output from 'make'.
+case `$am_make -s -f confmf 2> /dev/null` in #(
+*the\ am__doit\ target*)
+ am__include=include
+ am__quote=
+ _am_result=GNU
+ ;;
+esac
+# Now try BSD make style include.
+if test "$am__include" = "#"; then
+ echo '.include "confinc"' > confmf
+ case `$am_make -s -f confmf 2> /dev/null` in #(
+ *the\ am__doit\ target*)
+ am__include=.include
+ am__quote="\""
+ _am_result=BSD
+ ;;
+ esac
+fi
+AC_SUBST([am__include])
+AC_SUBST([am__quote])
+AC_MSG_RESULT([$_am_result])
+rm -f confinc confmf
+])
+
+# Fake the existence of programs that GNU maintainers use. -*- Autoconf -*-
+
+# Copyright (C) 1997-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_MISSING_PROG(NAME, PROGRAM)
+# ------------------------------
+AC_DEFUN([AM_MISSING_PROG],
+[AC_REQUIRE([AM_MISSING_HAS_RUN])
+$1=${$1-"${am_missing_run}$2"}
+AC_SUBST($1)])
+
+# AM_MISSING_HAS_RUN
+# ------------------
+# Define MISSING if not defined so far and test if it is modern enough.
+# If it is, set am_missing_run to use it, otherwise, to nothing.
+AC_DEFUN([AM_MISSING_HAS_RUN],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+AC_REQUIRE_AUX_FILE([missing])dnl
+if test x"${MISSING+set}" != xset; then
+ case $am_aux_dir in
+ *\ * | *\ *)
+ MISSING="\${SHELL} \"$am_aux_dir/missing\"" ;;
+ *)
+ MISSING="\${SHELL} $am_aux_dir/missing" ;;
+ esac
+fi
+# Use eval to expand $SHELL
+if eval "$MISSING --is-lightweight"; then
+ am_missing_run="$MISSING "
+else
+ am_missing_run=
+ AC_MSG_WARN(['missing' script is too old or missing])
+fi
+])
+
+# Helper functions for option handling. -*- Autoconf -*-
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_MANGLE_OPTION(NAME)
+# -----------------------
+AC_DEFUN([_AM_MANGLE_OPTION],
+[[_AM_OPTION_]m4_bpatsubst($1, [[^a-zA-Z0-9_]], [_])])
+
+# _AM_SET_OPTION(NAME)
+# --------------------
+# Set option NAME. Presently that only means defining a flag for this option.
+AC_DEFUN([_AM_SET_OPTION],
+[m4_define(_AM_MANGLE_OPTION([$1]), [1])])
+
+# _AM_SET_OPTIONS(OPTIONS)
+# ------------------------
+# OPTIONS is a space-separated list of Automake options.
+AC_DEFUN([_AM_SET_OPTIONS],
+[m4_foreach_w([_AM_Option], [$1], [_AM_SET_OPTION(_AM_Option)])])
+
+# _AM_IF_OPTION(OPTION, IF-SET, [IF-NOT-SET])
+# -------------------------------------------
+# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise.
+AC_DEFUN([_AM_IF_OPTION],
+[m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])])
+
+# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_CC_C_O
+# ---------------
+# Like AC_PROG_CC_C_O, but changed for automake. We rewrite AC_PROG_CC
+# to automatically call this.
+AC_DEFUN([_AM_PROG_CC_C_O],
+[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl
+AC_REQUIRE_AUX_FILE([compile])dnl
+AC_LANG_PUSH([C])dnl
+AC_CACHE_CHECK(
+ [whether $CC understands -c and -o together],
+ [am_cv_prog_cc_c_o],
+ [AC_LANG_CONFTEST([AC_LANG_PROGRAM([])])
+ # Make sure it works both with $CC and with simple cc.
+ # Following AC_PROG_CC_C_O, we do the test twice because some
+ # compilers refuse to overwrite an existing .o file with -o,
+ # though they will create one.
+ am_cv_prog_cc_c_o=yes
+ for am_i in 1 2; do
+ if AM_RUN_LOG([$CC -c conftest.$ac_ext -o conftest2.$ac_objext]) \
+ && test -f conftest2.$ac_objext; then
+ : OK
+ else
+ am_cv_prog_cc_c_o=no
+ break
+ fi
+ done
+ rm -f core conftest*
+ unset am_i])
+if test "$am_cv_prog_cc_c_o" != yes; then
+ # Losing compiler, so override with the script.
+ # FIXME: It is wrong to rewrite CC.
+ # But if we don't then we get into trouble of one sort or another.
+ # A longer-term fix would be to have automake use am__CC in this case,
+ # and then we could set am__CC="\$(top_srcdir)/compile \$(CC)"
+ CC="$am_aux_dir/compile $CC"
+fi
+AC_LANG_POP([C])])
+
+# For backward compatibility.
+AC_DEFUN_ONCE([AM_PROG_CC_C_O], [AC_REQUIRE([AC_PROG_CC])])
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_RUN_LOG(COMMAND)
+# -------------------
+# Run COMMAND, save the exit status in ac_status, and log it.
+# (This has been adapted from Autoconf's _AC_RUN_LOG macro.)
+AC_DEFUN([AM_RUN_LOG],
+[{ echo "$as_me:$LINENO: $1" >&AS_MESSAGE_LOG_FD
+ ($1) >&AS_MESSAGE_LOG_FD 2>&AS_MESSAGE_LOG_FD
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD
+ (exit $ac_status); }])
+
+# Check to make sure that the build environment is sane. -*- Autoconf -*-
+
+# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_SANITY_CHECK
+# ---------------
+AC_DEFUN([AM_SANITY_CHECK],
+[AC_MSG_CHECKING([whether build environment is sane])
+# Reject unsafe characters in $srcdir or the absolute working directory
+# name. Accept space and tab only in the latter.
+am_lf='
+'
+case `pwd` in
+ *[[\\\"\#\$\&\'\`$am_lf]]*)
+ AC_MSG_ERROR([unsafe absolute working directory name]);;
+esac
+case $srcdir in
+ *[[\\\"\#\$\&\'\`$am_lf\ \ ]]*)
+ AC_MSG_ERROR([unsafe srcdir value: '$srcdir']);;
+esac
+
+# Do 'set' in a subshell so we don't clobber the current shell's
+# arguments. Must try -L first in case configure is actually a
+# symlink; some systems play weird games with the mod time of symlinks
+# (eg FreeBSD returns the mod time of the symlink's containing
+# directory).
+if (
+ am_has_slept=no
+ for am_try in 1 2; do
+ echo "timestamp, slept: $am_has_slept" > conftest.file
+ set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
+ if test "$[*]" = "X"; then
+ # -L didn't work.
+ set X `ls -t "$srcdir/configure" conftest.file`
+ fi
+ if test "$[*]" != "X $srcdir/configure conftest.file" \
+ && test "$[*]" != "X conftest.file $srcdir/configure"; then
+
+ # If neither matched, then we have a broken ls. This can happen
+ # if, for instance, CONFIG_SHELL is bash and it inherits a
+ # broken ls alias from the environment. This has actually
+ # happened. Such a system could not be considered "sane".
+ AC_MSG_ERROR([ls -t appears to fail. Make sure there is not a broken
+ alias in your environment])
+ fi
+ if test "$[2]" = conftest.file || test $am_try -eq 2; then
+ break
+ fi
+ # Just in case.
+ sleep 1
+ am_has_slept=yes
+ done
+ test "$[2]" = conftest.file
+ )
+then
+ # Ok.
+ :
+else
+ AC_MSG_ERROR([newly created file is older than distributed files!
+Check your system clock])
+fi
+AC_MSG_RESULT([yes])
+# If we didn't sleep, we still need to ensure time stamps of config.status and
+# generated files are strictly newer.
+am_sleep_pid=
+if grep 'slept: no' conftest.file >/dev/null 2>&1; then
+ ( sleep 1 ) &
+ am_sleep_pid=$!
+fi
+AC_CONFIG_COMMANDS_PRE(
+ [AC_MSG_CHECKING([that generated files are newer than configure])
+ if test -n "$am_sleep_pid"; then
+ # Hide warnings about reused PIDs.
+ wait $am_sleep_pid 2>/dev/null
+ fi
+ AC_MSG_RESULT([done])])
+rm -f conftest.file
+])
+
+# Copyright (C) 2009-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_SILENT_RULES([DEFAULT])
+# --------------------------
+# Enable less verbose build rules; with the default set to DEFAULT
+# ("yes" being less verbose, "no" or empty being verbose).
+AC_DEFUN([AM_SILENT_RULES],
+[AC_ARG_ENABLE([silent-rules], [dnl
+AS_HELP_STRING(
+ [--enable-silent-rules],
+ [less verbose build output (undo: "make V=1")])
+AS_HELP_STRING(
+ [--disable-silent-rules],
+ [verbose build output (undo: "make V=0")])dnl
+])
+case $enable_silent_rules in @%:@ (((
+ yes) AM_DEFAULT_VERBOSITY=0;;
+ no) AM_DEFAULT_VERBOSITY=1;;
+ *) AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1]);;
+esac
+dnl
+dnl A few 'make' implementations (e.g., NonStop OS and NextStep)
+dnl do not support nested variable expansions.
+dnl See automake bug#9928 and bug#10237.
+am_make=${MAKE-make}
+AC_CACHE_CHECK([whether $am_make supports nested variables],
+ [am_cv_make_support_nested_variables],
+ [if AS_ECHO([['TRUE=$(BAR$(V))
+BAR0=false
+BAR1=true
+V=1
+am__doit:
+ @$(TRUE)
+.PHONY: am__doit']]) | $am_make -f - >/dev/null 2>&1; then
+ am_cv_make_support_nested_variables=yes
+else
+ am_cv_make_support_nested_variables=no
+fi])
+if test $am_cv_make_support_nested_variables = yes; then
+ dnl Using '$V' instead of '$(V)' breaks IRIX make.
+ AM_V='$(V)'
+ AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
+else
+ AM_V=$AM_DEFAULT_VERBOSITY
+ AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
+fi
+AC_SUBST([AM_V])dnl
+AM_SUBST_NOTMAKE([AM_V])dnl
+AC_SUBST([AM_DEFAULT_V])dnl
+AM_SUBST_NOTMAKE([AM_DEFAULT_V])dnl
+AC_SUBST([AM_DEFAULT_VERBOSITY])dnl
+AM_BACKSLASH='\'
+AC_SUBST([AM_BACKSLASH])dnl
+_AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl
+])
+
+# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# AM_PROG_INSTALL_STRIP
+# ---------------------
+# One issue with vendor 'install' (even GNU) is that you can't
+# specify the program used to strip binaries. This is especially
+# annoying in cross-compiling environments, where the build's strip
+# is unlikely to handle the host's binaries.
+# Fortunately install-sh will honor a STRIPPROG variable, so we
+# always use install-sh in "make install-strip", and initialize
+# STRIPPROG with the value of the STRIP variable (set by the user).
+AC_DEFUN([AM_PROG_INSTALL_STRIP],
+[AC_REQUIRE([AM_PROG_INSTALL_SH])dnl
+# Installed binaries are usually stripped using 'strip' when the user
+# run "make install-strip". However 'strip' might not be the right
+# tool to use in cross-compilation environments, therefore Automake
+# will honor the 'STRIP' environment variable to overrule this program.
+dnl Don't test for $cross_compiling = yes, because it might be 'maybe'.
+if test "$cross_compiling" != no; then
+ AC_CHECK_TOOL([STRIP], [strip], :)
+fi
+INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
+AC_SUBST([INSTALL_STRIP_PROGRAM])])
+
+# Copyright (C) 2006-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_SUBST_NOTMAKE(VARIABLE)
+# ---------------------------
+# Prevent Automake from outputting VARIABLE = @VARIABLE@ in Makefile.in.
+# This macro is traced by Automake.
+AC_DEFUN([_AM_SUBST_NOTMAKE])
+
+# AM_SUBST_NOTMAKE(VARIABLE)
+# --------------------------
+# Public sister of _AM_SUBST_NOTMAKE.
+AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)])
+
+# Check how to create a tarball. -*- Autoconf -*-
+
+# Copyright (C) 2004-2014 Free Software Foundation, Inc.
+#
+# This file is free software; the Free Software Foundation
+# gives unlimited permission to copy and/or distribute it,
+# with or without modifications, as long as this notice is preserved.
+
+# _AM_PROG_TAR(FORMAT)
+# --------------------
+# Check how to create a tarball in format FORMAT.
+# FORMAT should be one of 'v7', 'ustar', or 'pax'.
+#
+# Substitute a variable $(am__tar) that is a command
+# writing to stdout a FORMAT-tarball containing the directory
+# $tardir.
+# tardir=directory && $(am__tar) > result.tar
+#
+# Substitute a variable $(am__untar) that extract such
+# a tarball read from stdin.
+# $(am__untar) < result.tar
+#
+AC_DEFUN([_AM_PROG_TAR],
+[# Always define AMTAR for backward compatibility. Yes, it's still used
+# in the wild :-( We should find a proper way to deprecate it ...
+AC_SUBST([AMTAR], ['$${TAR-tar}'])
+
+# We'll loop over all known methods to create a tar archive until one works.
+_am_tools='gnutar m4_if([$1], [ustar], [plaintar]) pax cpio none'
+
+m4_if([$1], [v7],
+ [am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -'],
+
+ [m4_case([$1],
+ [ustar],
+ [# The POSIX 1988 'ustar' format is defined with fixed-size fields.
+ # There is notably a 21 bits limit for the UID and the GID. In fact,
+ # the 'pax' utility can hang on bigger UID/GID (see automake bug#8343
+ # and bug#13588).
+ am_max_uid=2097151 # 2^21 - 1
+ am_max_gid=$am_max_uid
+ # The $UID and $GID variables are not portable, so we need to resort
+ # to the POSIX-mandated id(1) utility. Errors in the 'id' calls
+ # below are definitely unexpected, so allow the users to see them
+ # (that is, avoid stderr redirection).
+ am_uid=`id -u || echo unknown`
+ am_gid=`id -g || echo unknown`
+ AC_MSG_CHECKING([whether UID '$am_uid' is supported by ustar format])
+ if test $am_uid -le $am_max_uid; then
+ AC_MSG_RESULT([yes])
+ else
+ AC_MSG_RESULT([no])
+ _am_tools=none
+ fi
+ AC_MSG_CHECKING([whether GID '$am_gid' is supported by ustar format])
+ if test $am_gid -le $am_max_gid; then
+ AC_MSG_RESULT([yes])
+ else
+ AC_MSG_RESULT([no])
+ _am_tools=none
+ fi],
+
+ [pax],
+ [],
+
+ [m4_fatal([Unknown tar format])])
+
+ AC_MSG_CHECKING([how to create a $1 tar archive])
+
+ # Go ahead even if we have the value already cached. We do so because we
+ # need to set the values for the 'am__tar' and 'am__untar' variables.
+ _am_tools=${am_cv_prog_tar_$1-$_am_tools}
+
+ for _am_tool in $_am_tools; do
+ case $_am_tool in
+ gnutar)
+ for _am_tar in tar gnutar gtar; do
+ AM_RUN_LOG([$_am_tar --version]) && break
+ done
+ am__tar="$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - "'"$$tardir"'
+ am__tar_="$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - "'"$tardir"'
+ am__untar="$_am_tar -xf -"
+ ;;
+ plaintar)
+ # Must skip GNU tar: if it does not support --format= it doesn't create
+ # ustar tarball either.
+ (tar --version) >/dev/null 2>&1 && continue
+ am__tar='tar chf - "$$tardir"'
+ am__tar_='tar chf - "$tardir"'
+ am__untar='tar xf -'
+ ;;
+ pax)
+ am__tar='pax -L -x $1 -w "$$tardir"'
+ am__tar_='pax -L -x $1 -w "$tardir"'
+ am__untar='pax -r'
+ ;;
+ cpio)
+ am__tar='find "$$tardir" -print | cpio -o -H $1 -L'
+ am__tar_='find "$tardir" -print | cpio -o -H $1 -L'
+ am__untar='cpio -i -H $1 -d'
+ ;;
+ none)
+ am__tar=false
+ am__tar_=false
+ am__untar=false
+ ;;
+ esac
+
+ # If the value was cached, stop now. We just wanted to have am__tar
+ # and am__untar set.
+ test -n "${am_cv_prog_tar_$1}" && break
+
+ # tar/untar a dummy directory, and stop if the command works.
+ rm -rf conftest.dir
+ mkdir conftest.dir
+ echo GrepMe > conftest.dir/file
+ AM_RUN_LOG([tardir=conftest.dir && eval $am__tar_ >conftest.tar])
+ rm -rf conftest.dir
+ if test -s conftest.tar; then
+ AM_RUN_LOG([$am__untar <conftest.tar])
+ AM_RUN_LOG([cat conftest.dir/file])
+ grep GrepMe conftest.dir/file >/dev/null 2>&1 && break
+ fi
+ done
+ rm -rf conftest.dir
+
+ AC_CACHE_VAL([am_cv_prog_tar_$1], [am_cv_prog_tar_$1=$_am_tool])
+ AC_MSG_RESULT([$am_cv_prog_tar_$1])])
+
+AC_SUBST([am__tar])
+AC_SUBST([am__untar])
+]) # _AM_PROG_TAR
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/ar-lib b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/ar-lib
new file mode 100755
index 000000000..463b9ec02
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/ar-lib
@@ -0,0 +1,270 @@
+#! /bin/sh
+# Wrapper for Microsoft lib.exe
+
+me=ar-lib
+scriptversion=2012-03-01.08; # UTC
+
+# Copyright (C) 2010-2014 Free Software Foundation, Inc.
+# Written by Peter Rosin <peda@lysator.liu.se>.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# This file is maintained in Automake, please report
+# bugs to <bug-automake@gnu.org> or send patches to
+# <automake-patches@gnu.org>.
+
+
+# func_error message
+func_error ()
+{
+ echo "$me: $1" 1>&2
+ exit 1
+}
+
+file_conv=
+
+# func_file_conv build_file
+# Convert a $build file to $host form and store it in $file
+# Currently only supports Windows hosts.
+func_file_conv ()
+{
+ file=$1
+ case $file in
+ / | /[!/]*) # absolute file, and not a UNC file
+ if test -z "$file_conv"; then
+ # lazily determine how to convert abs files
+ case `uname -s` in
+ MINGW*)
+ file_conv=mingw
+ ;;
+ CYGWIN*)
+ file_conv=cygwin
+ ;;
+ *)
+ file_conv=wine
+ ;;
+ esac
+ fi
+ case $file_conv in
+ mingw)
+ file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'`
+ ;;
+ cygwin)
+ file=`cygpath -m "$file" || echo "$file"`
+ ;;
+ wine)
+ file=`winepath -w "$file" || echo "$file"`
+ ;;
+ esac
+ ;;
+ esac
+}
+
+# func_at_file at_file operation archive
+# Iterate over all members in AT_FILE performing OPERATION on ARCHIVE
+# for each of them.
+# When interpreting the content of the @FILE, do NOT use func_file_conv,
+# since the user would need to supply preconverted file names to
+# binutils ar, at least for MinGW.
+func_at_file ()
+{
+ operation=$2
+ archive=$3
+ at_file_contents=`cat "$1"`
+ eval set x "$at_file_contents"
+ shift
+
+ for member
+ do
+ $AR -NOLOGO $operation:"$member" "$archive" || exit $?
+ done
+}
+
+case $1 in
+ '')
+ func_error "no command. Try '$0 --help' for more information."
+ ;;
+ -h | --h*)
+ cat <<EOF
+Usage: $me [--help] [--version] PROGRAM ACTION ARCHIVE [MEMBER...]
+
+Members may be specified in a file named with @FILE.
+EOF
+ exit $?
+ ;;
+ -v | --v*)
+ echo "$me, version $scriptversion"
+ exit $?
+ ;;
+esac
+
+if test $# -lt 3; then
+ func_error "you must specify a program, an action and an archive"
+fi
+
+AR=$1
+shift
+while :
+do
+ if test $# -lt 2; then
+ func_error "you must specify a program, an action and an archive"
+ fi
+ case $1 in
+ -lib | -LIB \
+ | -ltcg | -LTCG \
+ | -machine* | -MACHINE* \
+ | -subsystem* | -SUBSYSTEM* \
+ | -verbose | -VERBOSE \
+ | -wx* | -WX* )
+ AR="$AR $1"
+ shift
+ ;;
+ *)
+ action=$1
+ shift
+ break
+ ;;
+ esac
+done
+orig_archive=$1
+shift
+func_file_conv "$orig_archive"
+archive=$file
+
+# strip leading dash in $action
+action=${action#-}
+
+delete=
+extract=
+list=
+quick=
+replace=
+index=
+create=
+
+while test -n "$action"
+do
+ case $action in
+ d*) delete=yes ;;
+ x*) extract=yes ;;
+ t*) list=yes ;;
+ q*) quick=yes ;;
+ r*) replace=yes ;;
+ s*) index=yes ;;
+ S*) ;; # the index is always updated implicitly
+ c*) create=yes ;;
+ u*) ;; # TODO: don't ignore the update modifier
+ v*) ;; # TODO: don't ignore the verbose modifier
+ *)
+ func_error "unknown action specified"
+ ;;
+ esac
+ action=${action#?}
+done
+
+case $delete$extract$list$quick$replace,$index in
+ yes,* | ,yes)
+ ;;
+ yesyes*)
+ func_error "more than one action specified"
+ ;;
+ *)
+ func_error "no action specified"
+ ;;
+esac
+
+if test -n "$delete"; then
+ if test ! -f "$orig_archive"; then
+ func_error "archive not found"
+ fi
+ for member
+ do
+ case $1 in
+ @*)
+ func_at_file "${1#@}" -REMOVE "$archive"
+ ;;
+ *)
+ func_file_conv "$1"
+ $AR -NOLOGO -REMOVE:"$file" "$archive" || exit $?
+ ;;
+ esac
+ done
+
+elif test -n "$extract"; then
+ if test ! -f "$orig_archive"; then
+ func_error "archive not found"
+ fi
+ if test $# -gt 0; then
+ for member
+ do
+ case $1 in
+ @*)
+ func_at_file "${1#@}" -EXTRACT "$archive"
+ ;;
+ *)
+ func_file_conv "$1"
+ $AR -NOLOGO -EXTRACT:"$file" "$archive" || exit $?
+ ;;
+ esac
+ done
+ else
+ $AR -NOLOGO -LIST "$archive" | sed -e 's/\\/\\\\/g' | while read member
+ do
+ $AR -NOLOGO -EXTRACT:"$member" "$archive" || exit $?
+ done
+ fi
+
+elif test -n "$quick$replace"; then
+ if test ! -f "$orig_archive"; then
+ if test -z "$create"; then
+ echo "$me: creating $orig_archive"
+ fi
+ orig_archive=
+ else
+ orig_archive=$archive
+ fi
+
+ for member
+ do
+ case $1 in
+ @*)
+ func_file_conv "${1#@}"
+ set x "$@" "@$file"
+ ;;
+ *)
+ func_file_conv "$1"
+ set x "$@" "$file"
+ ;;
+ esac
+ shift
+ shift
+ done
+
+ if test -n "$orig_archive"; then
+ $AR -NOLOGO -OUT:"$archive" "$orig_archive" "$@" || exit $?
+ else
+ $AR -NOLOGO -OUT:"$archive" "$@" || exit $?
+ fi
+
+elif test -n "$list"; then
+ if test ! -f "$orig_archive"; then
+ func_error "archive not found"
+ fi
+ $AR -NOLOGO -LIST "$archive" || exit $?
+fi
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/build.wake b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/build.wake
new file mode 100644
index 000000000..21edd636f
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/build.wake
@@ -0,0 +1,150 @@
+tuple MachineExecutionEnvironment =
+ Job_: Job
+ IncludeDir_: String
+ LibDir_: String
+ LibMetal_: Path
+ LibMetalGloss_: Path
+ ConfigOptions: FreedomMetalConfigureOptions
+ AllOutputs_: List Path
+
+global def getMachineExecutionEnvironmentJob = getMachineExecutionEnvironmentJob_
+global def getMachineExecutionEnvironmentLibMetal = getMachineExecutionEnvironmentLibMetal_
+global def getMachineExecutionEnvironmentLibMetalGloss = getMachineExecutionEnvironmentLibMetalGloss_
+global def getMachineExecutionEnvironmentIncludeDir = getMachineExecutionEnvironmentIncludeDir_
+global def getMachineExecutionEnvironmentLibDir = getMachineExecutionEnvironmentLibDir_
+global def getMachineExecutionEnvironmentAllOutputs = getMachineExecutionEnvironmentAllOutputs_
+
+global def getMachineExecutionEnvironmentRISCV_ARCH = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsRISCV_ARCH
+global def getMachineExecutionEnvironmentRISCV_ABI = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsRISCV_ABI
+global def getMachineExecutionEnvironmentRISCV_CMODEL = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsRISCV_CMODEL
+global def getMachineExecutionEnvironmentHost = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsHost
+global def getMachineExecutionEnvironmentPrefix = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsOutputDir
+global def getMachineExecutionEnvironmentName = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsMachineName
+global def getMachineExecutionEnvironmentHeader = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsMachineHeader
+global def getMachineExecutionEnvironmentLdScript = _.getMachineExecutionEnvironmentConfigOptions.getFreedomMetalConfigureOptionsMachineLdScript
+
+tuple FreedomMetalConfigureOptions =
+ global Resources: List String
+ global RISCV_ARCH: String
+ global RISCV_ABI: String
+ global RISCV_CMODEL: String
+ global Host: String
+ global OutputDir: String
+ global MachineName: String
+ global MachineHeader: Path
+ global MachineInlineHeader: Path
+ global PlatformHeader: Path
+ global MachineLdScript: Path
+
+global def defaultSiFiveRISCVResources = "riscv-tools/2019.05.0", Nil
+
+global def makeFreedomMetalConfigureOptions arch abi cmodel host outputDir name header inlineHeader platformHeader ldScript =
+ def resources = defaultSiFiveRISCVResources
+ FreedomMetalConfigureOptions resources arch abi cmodel host outputDir name header inlineHeader platformHeader ldScript
+
+global tuple MakeElfOptions =
+ global MEE: MachineExecutionEnvironment
+ global ProgramSrcs: List Path
+ global CFlags: List String
+ global LFlags: List String
+ global IncludeDirs: List String
+ global ElfFile: String
+
+global def runFreedomMetalInstall options =
+ def outputDir = options.getFreedomMetalConfigureOptionsOutputDir
+ def metalHeader = options.getFreedomMetalConfigureOptionsMachineHeader
+ def metalInline = options.getFreedomMetalConfigureOptionsMachineInlineHeader
+ def platformHeader = options.getFreedomMetalConfigureOptionsPlatformHeader
+
+ def metalInstallDir = outputDir
+
+ def installedFreedomMetal =
+ def inputs =
+ sources "freedom-metal" `.*`
+ | filter (!matches `freedom-metal/doc/.*` _.getPathName)
+ def cmdline =
+ "rsync",
+ "-r",
+ "--exclude", "freedom-metal/doc",
+ "--exclude", "freedom-metal/.git",
+ "--exclude", "*.wake",
+ "freedom-metal",
+ outputDir,
+ Nil
+ def fnOutputs _ =
+ files "freedom-metal" `.*`
+ | filter (!matches `freedom-metal/(\.git|doc)/.*` _)
+ | filter (!matches `.*\.(in|am|m4|wake)` _) # exclude these because autoconf modfies them
+ | filter (!matches `(.*/)?(configure)` _)
+ | map ("{metalInstallDir}/{_}")
+
+ makePlan cmdline inputs
+ | setPlanFnOutputs fnOutputs
+ | setPlanLocalOnly True
+ | runJob
+ | getJobOutputs
+
+
+ def runDir = "{metalInstallDir}/freedom-metal"
+ def cmdline = "bash", "-c", "%
+ set -eo pipefail
+ machine_header=$(pwd)/%{metalHeader.getPathName}
+ machine_inline=$(pwd)/%{metalInline.getPathName}
+ platform_header=$(pwd)/%{platformHeader.getPathName}
+ install_dir=$(pwd)/%{outputDir}
+ export RISCV_PATH=$RISCV
+ cd %{runDir}
+ ./configure \
+ --host=%{options.getFreedomMetalConfigureOptionsHost} \
+ --with-builtin-libgloss \
+ --with-machine-header=$machine_header \
+ --with-machine-inline=$machine_inline \
+ --with-platform-header=$platform_header \
+ --prefix=
+ make \
+ RANLIB="riscv64-unknown-elf-ranlib -D" \
+ ARFLAGS=Dcr
+ make \
+ RANLIB="riscv64-unknown-elf-ranlib -D" \
+ ARFLAGS=Dcr \
+ DESTDIR=$install_dir \
+ install
+ %", Nil
+
+ def inputs = mkdir outputDir, metalHeader, installedFreedomMetal
+ def foutputs _ =
+ files "{outputDir}/include" `.*`
+ ++ files "{outputDir}/lib" `.*`
+ def withCFlags =
+ def march = options.getFreedomMetalConfigureOptionsRISCV_ARCH
+ def mabi = options.getFreedomMetalConfigureOptionsRISCV_ABI
+ def cmodel = options.getFreedomMetalConfigureOptionsRISCV_CMODEL
+ "CFLAGS=-march={march} -mabi={mabi} -g -mcmodel={cmodel}", _
+
+ def job =
+ makePlan cmdline inputs
+ | setPlanLocalOnly True
+ | setPlanFnOutputs foutputs
+ | setPlanResources options.getFreedomMetalConfigureOptionsResources
+ | editPlanEnvironment withCFlags
+ | runJob
+ def makeOutputs = job.getJobOutputs
+
+ def getFile f msg = match (makeOutputs | map getPathResult | findFail)
+ Fail e = makeBadPath e
+ Pass _ =
+ filter (simplify f ==~ _.getPathName) makeOutputs
+ | head
+ | getOrElse msg.makeError.makeBadPath
+
+ def libmetal =
+ def fileName = "{outputDir}/lib/libmetal.a"
+ getFile fileName "Failed to compile libmetal: {fileName}"
+
+ def libmetalGloss =
+ def fileName = "{outputDir}/lib/libmetal-gloss.a"
+ getFile fileName "Failed to compile libgloss: {fileName}"
+
+ def includeDir = "{outputDir}/include"
+ def libDir = "{outputDir}/lib"
+ MachineExecutionEnvironment job includeDir libDir libmetal libmetalGloss options makeOutputs
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/compile b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/compile
new file mode 100755
index 000000000..a85b723c7
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/compile
@@ -0,0 +1,347 @@
+#! /bin/sh
+# Wrapper for compilers which do not understand '-c -o'.
+
+scriptversion=2012-10-14.11; # UTC
+
+# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Written by Tom Tromey <tromey@cygnus.com>.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# This file is maintained in Automake, please report
+# bugs to <bug-automake@gnu.org> or send patches to
+# <automake-patches@gnu.org>.
+
+nl='
+'
+
+# We need space, tab and new line, in precisely that order. Quoting is
+# there to prevent tools from complaining about whitespace usage.
+IFS=" "" $nl"
+
+file_conv=
+
+# func_file_conv build_file lazy
+# Convert a $build file to $host form and store it in $file
+# Currently only supports Windows hosts. If the determined conversion
+# type is listed in (the comma separated) LAZY, no conversion will
+# take place.
+func_file_conv ()
+{
+ file=$1
+ case $file in
+ / | /[!/]*) # absolute file, and not a UNC file
+ if test -z "$file_conv"; then
+ # lazily determine how to convert abs files
+ case `uname -s` in
+ MINGW*)
+ file_conv=mingw
+ ;;
+ CYGWIN*)
+ file_conv=cygwin
+ ;;
+ *)
+ file_conv=wine
+ ;;
+ esac
+ fi
+ case $file_conv/,$2, in
+ *,$file_conv,*)
+ ;;
+ mingw/*)
+ file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'`
+ ;;
+ cygwin/*)
+ file=`cygpath -m "$file" || echo "$file"`
+ ;;
+ wine/*)
+ file=`winepath -w "$file" || echo "$file"`
+ ;;
+ esac
+ ;;
+ esac
+}
+
+# func_cl_dashL linkdir
+# Make cl look for libraries in LINKDIR
+func_cl_dashL ()
+{
+ func_file_conv "$1"
+ if test -z "$lib_path"; then
+ lib_path=$file
+ else
+ lib_path="$lib_path;$file"
+ fi
+ linker_opts="$linker_opts -LIBPATH:$file"
+}
+
+# func_cl_dashl library
+# Do a library search-path lookup for cl
+func_cl_dashl ()
+{
+ lib=$1
+ found=no
+ save_IFS=$IFS
+ IFS=';'
+ for dir in $lib_path $LIB
+ do
+ IFS=$save_IFS
+ if $shared && test -f "$dir/$lib.dll.lib"; then
+ found=yes
+ lib=$dir/$lib.dll.lib
+ break
+ fi
+ if test -f "$dir/$lib.lib"; then
+ found=yes
+ lib=$dir/$lib.lib
+ break
+ fi
+ if test -f "$dir/lib$lib.a"; then
+ found=yes
+ lib=$dir/lib$lib.a
+ break
+ fi
+ done
+ IFS=$save_IFS
+
+ if test "$found" != yes; then
+ lib=$lib.lib
+ fi
+}
+
+# func_cl_wrapper cl arg...
+# Adjust compile command to suit cl
+func_cl_wrapper ()
+{
+ # Assume a capable shell
+ lib_path=
+ shared=:
+ linker_opts=
+ for arg
+ do
+ if test -n "$eat"; then
+ eat=
+ else
+ case $1 in
+ -o)
+ # configure might choose to run compile as 'compile cc -o foo foo.c'.
+ eat=1
+ case $2 in
+ *.o | *.[oO][bB][jJ])
+ func_file_conv "$2"
+ set x "$@" -Fo"$file"
+ shift
+ ;;
+ *)
+ func_file_conv "$2"
+ set x "$@" -Fe"$file"
+ shift
+ ;;
+ esac
+ ;;
+ -I)
+ eat=1
+ func_file_conv "$2" mingw
+ set x "$@" -I"$file"
+ shift
+ ;;
+ -I*)
+ func_file_conv "${1#-I}" mingw
+ set x "$@" -I"$file"
+ shift
+ ;;
+ -l)
+ eat=1
+ func_cl_dashl "$2"
+ set x "$@" "$lib"
+ shift
+ ;;
+ -l*)
+ func_cl_dashl "${1#-l}"
+ set x "$@" "$lib"
+ shift
+ ;;
+ -L)
+ eat=1
+ func_cl_dashL "$2"
+ ;;
+ -L*)
+ func_cl_dashL "${1#-L}"
+ ;;
+ -static)
+ shared=false
+ ;;
+ -Wl,*)
+ arg=${1#-Wl,}
+ save_ifs="$IFS"; IFS=','
+ for flag in $arg; do
+ IFS="$save_ifs"
+ linker_opts="$linker_opts $flag"
+ done
+ IFS="$save_ifs"
+ ;;
+ -Xlinker)
+ eat=1
+ linker_opts="$linker_opts $2"
+ ;;
+ -*)
+ set x "$@" "$1"
+ shift
+ ;;
+ *.cc | *.CC | *.cxx | *.CXX | *.[cC]++)
+ func_file_conv "$1"
+ set x "$@" -Tp"$file"
+ shift
+ ;;
+ *.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO])
+ func_file_conv "$1" mingw
+ set x "$@" "$file"
+ shift
+ ;;
+ *)
+ set x "$@" "$1"
+ shift
+ ;;
+ esac
+ fi
+ shift
+ done
+ if test -n "$linker_opts"; then
+ linker_opts="-link$linker_opts"
+ fi
+ exec "$@" $linker_opts
+ exit 1
+}
+
+eat=
+
+case $1 in
+ '')
+ echo "$0: No command. Try '$0 --help' for more information." 1>&2
+ exit 1;
+ ;;
+ -h | --h*)
+ cat <<\EOF
+Usage: compile [--help] [--version] PROGRAM [ARGS]
+
+Wrapper for compilers which do not understand '-c -o'.
+Remove '-o dest.o' from ARGS, run PROGRAM with the remaining
+arguments, and rename the output as expected.
+
+If you are trying to build a whole package this is not the
+right script to run: please start by reading the file 'INSTALL'.
+
+Report bugs to <bug-automake@gnu.org>.
+EOF
+ exit $?
+ ;;
+ -v | --v*)
+ echo "compile $scriptversion"
+ exit $?
+ ;;
+ cl | *[/\\]cl | cl.exe | *[/\\]cl.exe )
+ func_cl_wrapper "$@" # Doesn't return...
+ ;;
+esac
+
+ofile=
+cfile=
+
+for arg
+do
+ if test -n "$eat"; then
+ eat=
+ else
+ case $1 in
+ -o)
+ # configure might choose to run compile as 'compile cc -o foo foo.c'.
+ # So we strip '-o arg' only if arg is an object.
+ eat=1
+ case $2 in
+ *.o | *.obj)
+ ofile=$2
+ ;;
+ *)
+ set x "$@" -o "$2"
+ shift
+ ;;
+ esac
+ ;;
+ *.c)
+ cfile=$1
+ set x "$@" "$1"
+ shift
+ ;;
+ *)
+ set x "$@" "$1"
+ shift
+ ;;
+ esac
+ fi
+ shift
+done
+
+if test -z "$ofile" || test -z "$cfile"; then
+ # If no '-o' option was seen then we might have been invoked from a
+ # pattern rule where we don't need one. That is ok -- this is a
+ # normal compilation that the losing compiler can handle. If no
+ # '.c' file was seen then we are probably linking. That is also
+ # ok.
+ exec "$@"
+fi
+
+# Name of file we expect compiler to create.
+cofile=`echo "$cfile" | sed 's|^.*[\\/]||; s|^[a-zA-Z]:||; s/\.c$/.o/'`
+
+# Create the lock directory.
+# Note: use '[/\\:.-]' here to ensure that we don't use the same name
+# that we are using for the .o file. Also, base the name on the expected
+# object file name, since that is what matters with a parallel build.
+lockdir=`echo "$cofile" | sed -e 's|[/\\:.-]|_|g'`.d
+while true; do
+ if mkdir "$lockdir" >/dev/null 2>&1; then
+ break
+ fi
+ sleep 1
+done
+# FIXME: race condition here if user kills between mkdir and trap.
+trap "rmdir '$lockdir'; exit 1" 1 2 15
+
+# Run the compile.
+"$@"
+ret=$?
+
+if test -f "$cofile"; then
+ test "$cofile" = "$ofile" || mv "$cofile" "$ofile"
+elif test -f "${cofile}bj"; then
+ test "${cofile}bj" = "$ofile" || mv "${cofile}bj" "$ofile"
+fi
+
+rmdir "$lockdir"
+exit $ret
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.guess b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.guess
new file mode 100755
index 000000000..16592509d
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.guess
@@ -0,0 +1,1441 @@
+#! /bin/sh
+# Attempt to guess a canonical system name.
+# Copyright 1992-2015 Free Software Foundation, Inc.
+
+timestamp='2015-08-20'
+
+# This file is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, see <http://www.gnu.org/licenses/>.
+#
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that
+# program. This Exception is an additional permission under section 7
+# of the GNU General Public License, version 3 ("GPLv3").
+#
+# Originally written by Per Bothner; maintained since 2000 by Ben Elliston.
+#
+# You can get the latest version of this script from:
+# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD
+#
+# Please send patches to <config-patches@gnu.org>.
+
+
+me=`echo "$0" | sed -e 's,.*/,,'`
+
+usage="\
+Usage: $0 [OPTION]
+
+Output the configuration name of the system \`$me' is run on.
+
+Operation modes:
+ -h, --help print this help, then exit
+ -t, --time-stamp print date of last modification, then exit
+ -v, --version print version number, then exit
+
+Report bugs and patches to <config-patches@gnu.org>."
+
+version="\
+GNU config.guess ($timestamp)
+
+Originally written by Per Bothner.
+Copyright 1992-2015 Free Software Foundation, Inc.
+
+This is free software; see the source for copying conditions. There is NO
+warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
+
+help="
+Try \`$me --help' for more information."
+
+# Parse command line
+while test $# -gt 0 ; do
+ case $1 in
+ --time-stamp | --time* | -t )
+ echo "$timestamp" ; exit ;;
+ --version | -v )
+ echo "$version" ; exit ;;
+ --help | --h* | -h )
+ echo "$usage"; exit ;;
+ -- ) # Stop option processing
+ shift; break ;;
+ - ) # Use stdin as input.
+ break ;;
+ -* )
+ echo "$me: invalid option $1$help" >&2
+ exit 1 ;;
+ * )
+ break ;;
+ esac
+done
+
+if test $# != 0; then
+ echo "$me: too many arguments$help" >&2
+ exit 1
+fi
+
+trap 'exit 1' 1 2 15
+
+# CC_FOR_BUILD -- compiler used by this script. Note that the use of a
+# compiler to aid in system detection is discouraged as it requires
+# temporary files to be created and, as you can see below, it is a
+# headache to deal with in a portable fashion.
+
+# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still
+# use `HOST_CC' if defined, but it is deprecated.
+
+# Portable tmp directory creation inspired by the Autoconf team.
+
+set_cc_for_build='
+trap "exitcode=\$?; (rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null) && exit \$exitcode" 0 ;
+trap "rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null; exit 1" 1 2 13 15 ;
+: ${TMPDIR=/tmp} ;
+ { tmp=`(umask 077 && mktemp -d "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } ||
+ { test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } ||
+ { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo "Warning: creating insecure temp directory" >&2 ; } ||
+ { echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } ;
+dummy=$tmp/dummy ;
+tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ;
+case $CC_FOR_BUILD,$HOST_CC,$CC in
+ ,,) echo "int x;" > $dummy.c ;
+ for c in cc gcc c89 c99 ; do
+ if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then
+ CC_FOR_BUILD="$c"; break ;
+ fi ;
+ done ;
+ if test x"$CC_FOR_BUILD" = x ; then
+ CC_FOR_BUILD=no_compiler_found ;
+ fi
+ ;;
+ ,,*) CC_FOR_BUILD=$CC ;;
+ ,*,*) CC_FOR_BUILD=$HOST_CC ;;
+esac ; set_cc_for_build= ;'
+
+# This is needed to find uname on a Pyramid OSx when run in the BSD universe.
+# (ghazi@noc.rutgers.edu 1994-08-24)
+if (test -f /.attbin/uname) >/dev/null 2>&1 ; then
+ PATH=$PATH:/.attbin ; export PATH
+fi
+
+UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown
+UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown
+UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown
+UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
+
+case "${UNAME_SYSTEM}" in
+Linux|GNU|GNU/*)
+ # If the system lacks a compiler, then just pick glibc.
+ # We could probably try harder.
+ LIBC=gnu
+
+ eval $set_cc_for_build
+ cat <<-EOF > $dummy.c
+ #include <features.h>
+ #if defined(__UCLIBC__)
+ LIBC=uclibc
+ #elif defined(__dietlibc__)
+ LIBC=dietlibc
+ #else
+ LIBC=gnu
+ #endif
+ EOF
+ eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC' | sed 's, ,,g'`
+ ;;
+esac
+
+# Note: order is significant - the case branches are not exclusive.
+
+case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
+ *:NetBSD:*:*)
+ # NetBSD (nbsd) targets should (where applicable) match one or
+ # more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*,
+ # *-*-netbsdecoff* and *-*-netbsd*. For targets that recently
+ # switched to ELF, *-*-netbsd* would select the old
+ # object file format. This provides both forward
+ # compatibility and a consistent mechanism for selecting the
+ # object file format.
+ #
+ # Note: NetBSD doesn't particularly care about the vendor
+ # portion of the name. We always set it to "unknown".
+ sysctl="sysctl -n hw.machine_arch"
+ UNAME_MACHINE_ARCH=`(uname -p 2>/dev/null || \
+ /sbin/$sysctl 2>/dev/null || \
+ /usr/sbin/$sysctl 2>/dev/null || \
+ echo unknown)`
+ case "${UNAME_MACHINE_ARCH}" in
+ armeb) machine=armeb-unknown ;;
+ arm*) machine=arm-unknown ;;
+ sh3el) machine=shl-unknown ;;
+ sh3eb) machine=sh-unknown ;;
+ sh5el) machine=sh5le-unknown ;;
+ earmv*)
+ arch=`echo ${UNAME_MACHINE_ARCH} | sed -e 's,^e\(armv[0-9]\).*$,\1,'`
+ endian=`echo ${UNAME_MACHINE_ARCH} | sed -ne 's,^.*\(eb\)$,\1,p'`
+ machine=${arch}${endian}-unknown
+ ;;
+ *) machine=${UNAME_MACHINE_ARCH}-unknown ;;
+ esac
+ # The Operating System including object format, if it has switched
+ # to ELF recently, or will in the future.
+ case "${UNAME_MACHINE_ARCH}" in
+ arm*|earm*|i386|m68k|ns32k|sh3*|sparc|vax)
+ eval $set_cc_for_build
+ if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \
+ | grep -q __ELF__
+ then
+ # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout).
+ # Return netbsd for either. FIX?
+ os=netbsd
+ else
+ os=netbsdelf
+ fi
+ ;;
+ *)
+ os=netbsd
+ ;;
+ esac
+ # Determine ABI tags.
+ case "${UNAME_MACHINE_ARCH}" in
+ earm*)
+ expr='s/^earmv[0-9]/-eabi/;s/eb$//'
+ abi=`echo ${UNAME_MACHINE_ARCH} | sed -e "$expr"`
+ ;;
+ esac
+ # The OS release
+ # Debian GNU/NetBSD machines have a different userland, and
+ # thus, need a distinct triplet. However, they do not need
+ # kernel version information, so it can be replaced with a
+ # suitable tag, in the style of linux-gnu.
+ case "${UNAME_VERSION}" in
+ Debian*)
+ release='-gnu'
+ ;;
+ *)
+ release=`echo ${UNAME_RELEASE} | sed -e 's/[-_].*//' | cut -d. -f1,2`
+ ;;
+ esac
+ # Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:
+ # contains redundant information, the shorter form:
+ # CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
+ echo "${machine}-${os}${release}${abi}"
+ exit ;;
+ *:Bitrig:*:*)
+ UNAME_MACHINE_ARCH=`arch | sed 's/Bitrig.//'`
+ echo ${UNAME_MACHINE_ARCH}-unknown-bitrig${UNAME_RELEASE}
+ exit ;;
+ *:OpenBSD:*:*)
+ UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'`
+ echo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE}
+ exit ;;
+ *:ekkoBSD:*:*)
+ echo ${UNAME_MACHINE}-unknown-ekkobsd${UNAME_RELEASE}
+ exit ;;
+ *:SolidBSD:*:*)
+ echo ${UNAME_MACHINE}-unknown-solidbsd${UNAME_RELEASE}
+ exit ;;
+ macppc:MirBSD:*:*)
+ echo powerpc-unknown-mirbsd${UNAME_RELEASE}
+ exit ;;
+ *:MirBSD:*:*)
+ echo ${UNAME_MACHINE}-unknown-mirbsd${UNAME_RELEASE}
+ exit ;;
+ *:Sortix:*:*)
+ echo ${UNAME_MACHINE}-unknown-sortix
+ exit ;;
+ alpha:OSF1:*:*)
+ case $UNAME_RELEASE in
+ *4.0)
+ UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`
+ ;;
+ *5.*)
+ UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'`
+ ;;
+ esac
+ # According to Compaq, /usr/sbin/psrinfo has been available on
+ # OSF/1 and Tru64 systems produced since 1995. I hope that
+ # covers most systems running today. This code pipes the CPU
+ # types through head -n 1, so we only detect the type of CPU 0.
+ ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^ The alpha \(.*\) processor.*$/\1/p' | head -n 1`
+ case "$ALPHA_CPU_TYPE" in
+ "EV4 (21064)")
+ UNAME_MACHINE="alpha" ;;
+ "EV4.5 (21064)")
+ UNAME_MACHINE="alpha" ;;
+ "LCA4 (21066/21068)")
+ UNAME_MACHINE="alpha" ;;
+ "EV5 (21164)")
+ UNAME_MACHINE="alphaev5" ;;
+ "EV5.6 (21164A)")
+ UNAME_MACHINE="alphaev56" ;;
+ "EV5.6 (21164PC)")
+ UNAME_MACHINE="alphapca56" ;;
+ "EV5.7 (21164PC)")
+ UNAME_MACHINE="alphapca57" ;;
+ "EV6 (21264)")
+ UNAME_MACHINE="alphaev6" ;;
+ "EV6.7 (21264A)")
+ UNAME_MACHINE="alphaev67" ;;
+ "EV6.8CB (21264C)")
+ UNAME_MACHINE="alphaev68" ;;
+ "EV6.8AL (21264B)")
+ UNAME_MACHINE="alphaev68" ;;
+ "EV6.8CX (21264D)")
+ UNAME_MACHINE="alphaev68" ;;
+ "EV6.9A (21264/EV69A)")
+ UNAME_MACHINE="alphaev69" ;;
+ "EV7 (21364)")
+ UNAME_MACHINE="alphaev7" ;;
+ "EV7.9 (21364A)")
+ UNAME_MACHINE="alphaev79" ;;
+ esac
+ # A Pn.n version is a patched version.
+ # A Vn.n version is a released version.
+ # A Tn.n version is a released field test version.
+ # A Xn.n version is an unreleased experimental baselevel.
+ # 1.2 uses "1.2" for uname -r.
+ echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
+ # Reset EXIT trap before exiting to avoid spurious non-zero exit code.
+ exitcode=$?
+ trap '' 0
+ exit $exitcode ;;
+ Alpha\ *:Windows_NT*:*)
+ # How do we know it's Interix rather than the generic POSIX subsystem?
+ # Should we change UNAME_MACHINE based on the output of uname instead
+ # of the specific Alpha model?
+ echo alpha-pc-interix
+ exit ;;
+ 21064:Windows_NT:50:3)
+ echo alpha-dec-winnt3.5
+ exit ;;
+ Amiga*:UNIX_System_V:4.0:*)
+ echo m68k-unknown-sysv4
+ exit ;;
+ *:[Aa]miga[Oo][Ss]:*:*)
+ echo ${UNAME_MACHINE}-unknown-amigaos
+ exit ;;
+ *:[Mm]orph[Oo][Ss]:*:*)
+ echo ${UNAME_MACHINE}-unknown-morphos
+ exit ;;
+ *:OS/390:*:*)
+ echo i370-ibm-openedition
+ exit ;;
+ *:z/VM:*:*)
+ echo s390-ibm-zvmoe
+ exit ;;
+ *:OS400:*:*)
+ echo powerpc-ibm-os400
+ exit ;;
+ arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
+ echo arm-acorn-riscix${UNAME_RELEASE}
+ exit ;;
+ arm*:riscos:*:*|arm*:RISCOS:*:*)
+ echo arm-unknown-riscos
+ exit ;;
+ SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)
+ echo hppa1.1-hitachi-hiuxmpp
+ exit ;;
+ Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*)
+ # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE.
+ if test "`(/bin/universe) 2>/dev/null`" = att ; then
+ echo pyramid-pyramid-sysv3
+ else
+ echo pyramid-pyramid-bsd
+ fi
+ exit ;;
+ NILE*:*:*:dcosx)
+ echo pyramid-pyramid-svr4
+ exit ;;
+ DRS?6000:unix:4.0:6*)
+ echo sparc-icl-nx6
+ exit ;;
+ DRS?6000:UNIX_SV:4.2*:7* | DRS?6000:isis:4.2*:7*)
+ case `/usr/bin/uname -p` in
+ sparc) echo sparc-icl-nx7; exit ;;
+ esac ;;
+ s390x:SunOS:*:*)
+ echo ${UNAME_MACHINE}-ibm-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ sun4H:SunOS:5.*:*)
+ echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)
+ echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ i86pc:AuroraUX:5.*:* | i86xen:AuroraUX:5.*:*)
+ echo i386-pc-auroraux${UNAME_RELEASE}
+ exit ;;
+ i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*)
+ eval $set_cc_for_build
+ SUN_ARCH="i386"
+ # If there is a compiler, see if it is configured for 64-bit objects.
+ # Note that the Sun cc does not turn __LP64__ into 1 like gcc does.
+ # This test works for both compilers.
+ if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
+ if (echo '#ifdef __amd64'; echo IS_64BIT_ARCH; echo '#endif') | \
+ (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
+ grep IS_64BIT_ARCH >/dev/null
+ then
+ SUN_ARCH="x86_64"
+ fi
+ fi
+ echo ${SUN_ARCH}-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ sun4*:SunOS:6*:*)
+ # According to config.sub, this is the proper way to canonicalize
+ # SunOS6. Hard to guess exactly what SunOS6 will be like, but
+ # it's likely to be more like Solaris than SunOS4.
+ echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ sun4*:SunOS:*:*)
+ case "`/usr/bin/arch -k`" in
+ Series*|S4*)
+ UNAME_RELEASE=`uname -v`
+ ;;
+ esac
+ # Japanese Language versions have a version number like `4.1.3-JL'.
+ echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'`
+ exit ;;
+ sun3*:SunOS:*:*)
+ echo m68k-sun-sunos${UNAME_RELEASE}
+ exit ;;
+ sun*:*:4.2BSD:*)
+ UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
+ test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3
+ case "`/bin/arch`" in
+ sun3)
+ echo m68k-sun-sunos${UNAME_RELEASE}
+ ;;
+ sun4)
+ echo sparc-sun-sunos${UNAME_RELEASE}
+ ;;
+ esac
+ exit ;;
+ aushp:SunOS:*:*)
+ echo sparc-auspex-sunos${UNAME_RELEASE}
+ exit ;;
+ # The situation for MiNT is a little confusing. The machine name
+ # can be virtually everything (everything which is not
+ # "atarist" or "atariste" at least should have a processor
+ # > m68000). The system name ranges from "MiNT" over "FreeMiNT"
+ # to the lowercase version "mint" (or "freemint"). Finally
+ # the system name "TOS" denotes a system which is actually not
+ # MiNT. But MiNT is downward compatible to TOS, so this should
+ # be no problem.
+ atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)
+ echo m68k-atari-mint${UNAME_RELEASE}
+ exit ;;
+ atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)
+ echo m68k-atari-mint${UNAME_RELEASE}
+ exit ;;
+ *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)
+ echo m68k-atari-mint${UNAME_RELEASE}
+ exit ;;
+ milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)
+ echo m68k-milan-mint${UNAME_RELEASE}
+ exit ;;
+ hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)
+ echo m68k-hades-mint${UNAME_RELEASE}
+ exit ;;
+ *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
+ echo m68k-unknown-mint${UNAME_RELEASE}
+ exit ;;
+ m68k:machten:*:*)
+ echo m68k-apple-machten${UNAME_RELEASE}
+ exit ;;
+ powerpc:machten:*:*)
+ echo powerpc-apple-machten${UNAME_RELEASE}
+ exit ;;
+ RISC*:Mach:*:*)
+ echo mips-dec-mach_bsd4.3
+ exit ;;
+ RISC*:ULTRIX:*:*)
+ echo mips-dec-ultrix${UNAME_RELEASE}
+ exit ;;
+ VAX*:ULTRIX*:*:*)
+ echo vax-dec-ultrix${UNAME_RELEASE}
+ exit ;;
+ 2020:CLIX:*:* | 2430:CLIX:*:*)
+ echo clipper-intergraph-clix${UNAME_RELEASE}
+ exit ;;
+ mips:*:*:UMIPS | mips:*:*:RISCos)
+ eval $set_cc_for_build
+ sed 's/^ //' << EOF >$dummy.c
+#ifdef __cplusplus
+#include <stdio.h> /* for printf() prototype */
+ int main (int argc, char *argv[]) {
+#else
+ int main (argc, argv) int argc; char *argv[]; {
+#endif
+ #if defined (host_mips) && defined (MIPSEB)
+ #if defined (SYSTYPE_SYSV)
+ printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0);
+ #endif
+ #if defined (SYSTYPE_SVR4)
+ printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0);
+ #endif
+ #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD)
+ printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0);
+ #endif
+ #endif
+ exit (-1);
+ }
+EOF
+ $CC_FOR_BUILD -o $dummy $dummy.c &&
+ dummyarg=`echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` &&
+ SYSTEM_NAME=`$dummy $dummyarg` &&
+ { echo "$SYSTEM_NAME"; exit; }
+ echo mips-mips-riscos${UNAME_RELEASE}
+ exit ;;
+ Motorola:PowerMAX_OS:*:*)
+ echo powerpc-motorola-powermax
+ exit ;;
+ Motorola:*:4.3:PL8-*)
+ echo powerpc-harris-powermax
+ exit ;;
+ Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*)
+ echo powerpc-harris-powermax
+ exit ;;
+ Night_Hawk:Power_UNIX:*:*)
+ echo powerpc-harris-powerunix
+ exit ;;
+ m88k:CX/UX:7*:*)
+ echo m88k-harris-cxux7
+ exit ;;
+ m88k:*:4*:R4*)
+ echo m88k-motorola-sysv4
+ exit ;;
+ m88k:*:3*:R3*)
+ echo m88k-motorola-sysv3
+ exit ;;
+ AViiON:dgux:*:*)
+ # DG/UX returns AViiON for all architectures
+ UNAME_PROCESSOR=`/usr/bin/uname -p`
+ if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]
+ then
+ if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \
+ [ ${TARGET_BINARY_INTERFACE}x = x ]
+ then
+ echo m88k-dg-dgux${UNAME_RELEASE}
+ else
+ echo m88k-dg-dguxbcs${UNAME_RELEASE}
+ fi
+ else
+ echo i586-dg-dgux${UNAME_RELEASE}
+ fi
+ exit ;;
+ M88*:DolphinOS:*:*) # DolphinOS (SVR3)
+ echo m88k-dolphin-sysv3
+ exit ;;
+ M88*:*:R3*:*)
+ # Delta 88k system running SVR3
+ echo m88k-motorola-sysv3
+ exit ;;
+ XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3)
+ echo m88k-tektronix-sysv3
+ exit ;;
+ Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD)
+ echo m68k-tektronix-bsd
+ exit ;;
+ *:IRIX*:*:*)
+ echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'`
+ exit ;;
+ ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.
+ echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id
+ exit ;; # Note that: echo "'`uname -s`'" gives 'AIX '
+ i*86:AIX:*:*)
+ echo i386-ibm-aix
+ exit ;;
+ ia64:AIX:*:*)
+ if [ -x /usr/bin/oslevel ] ; then
+ IBM_REV=`/usr/bin/oslevel`
+ else
+ IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+ fi
+ echo ${UNAME_MACHINE}-ibm-aix${IBM_REV}
+ exit ;;
+ *:AIX:2:3)
+ if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then
+ eval $set_cc_for_build
+ sed 's/^ //' << EOF >$dummy.c
+ #include <sys/systemcfg.h>
+
+ main()
+ {
+ if (!__power_pc())
+ exit(1);
+ puts("powerpc-ibm-aix3.2.5");
+ exit(0);
+ }
+EOF
+ if $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy`
+ then
+ echo "$SYSTEM_NAME"
+ else
+ echo rs6000-ibm-aix3.2.5
+ fi
+ elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then
+ echo rs6000-ibm-aix3.2.4
+ else
+ echo rs6000-ibm-aix3.2
+ fi
+ exit ;;
+ *:AIX:*:[4567])
+ IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
+ if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
+ IBM_ARCH=rs6000
+ else
+ IBM_ARCH=powerpc
+ fi
+ if [ -x /usr/bin/lslpp ] ; then
+ IBM_REV=`/usr/bin/lslpp -Lqc bos.rte.libc |
+ awk -F: '{ print $3 }' | sed s/[0-9]*$/0/`
+ else
+ IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+ fi
+ echo ${IBM_ARCH}-ibm-aix${IBM_REV}
+ exit ;;
+ *:AIX:*:*)
+ echo rs6000-ibm-aix
+ exit ;;
+ ibmrt:4.4BSD:*|romp-ibm:BSD:*)
+ echo romp-ibm-bsd4.4
+ exit ;;
+ ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC BSD and
+ echo romp-ibm-bsd${UNAME_RELEASE} # 4.3 with uname added to
+ exit ;; # report: romp-ibm BSD 4.3
+ *:BOSX:*:*)
+ echo rs6000-bull-bosx
+ exit ;;
+ DPX/2?00:B.O.S.:*:*)
+ echo m68k-bull-sysv3
+ exit ;;
+ 9000/[34]??:4.3bsd:1.*:*)
+ echo m68k-hp-bsd
+ exit ;;
+ hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*)
+ echo m68k-hp-bsd4.4
+ exit ;;
+ 9000/[34678]??:HP-UX:*:*)
+ HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
+ case "${UNAME_MACHINE}" in
+ 9000/31? ) HP_ARCH=m68000 ;;
+ 9000/[34]?? ) HP_ARCH=m68k ;;
+ 9000/[678][0-9][0-9])
+ if [ -x /usr/bin/getconf ]; then
+ sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
+ sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
+ case "${sc_cpu_version}" in
+ 523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
+ 528) HP_ARCH="hppa1.1" ;; # CPU_PA_RISC1_1
+ 532) # CPU_PA_RISC2_0
+ case "${sc_kernel_bits}" in
+ 32) HP_ARCH="hppa2.0n" ;;
+ 64) HP_ARCH="hppa2.0w" ;;
+ '') HP_ARCH="hppa2.0" ;; # HP-UX 10.20
+ esac ;;
+ esac
+ fi
+ if [ "${HP_ARCH}" = "" ]; then
+ eval $set_cc_for_build
+ sed 's/^ //' << EOF >$dummy.c
+
+ #define _HPUX_SOURCE
+ #include <stdlib.h>
+ #include <unistd.h>
+
+ int main ()
+ {
+ #if defined(_SC_KERNEL_BITS)
+ long bits = sysconf(_SC_KERNEL_BITS);
+ #endif
+ long cpu = sysconf (_SC_CPU_VERSION);
+
+ switch (cpu)
+ {
+ case CPU_PA_RISC1_0: puts ("hppa1.0"); break;
+ case CPU_PA_RISC1_1: puts ("hppa1.1"); break;
+ case CPU_PA_RISC2_0:
+ #if defined(_SC_KERNEL_BITS)
+ switch (bits)
+ {
+ case 64: puts ("hppa2.0w"); break;
+ case 32: puts ("hppa2.0n"); break;
+ default: puts ("hppa2.0"); break;
+ } break;
+ #else /* !defined(_SC_KERNEL_BITS) */
+ puts ("hppa2.0"); break;
+ #endif
+ default: puts ("hppa1.0"); break;
+ }
+ exit (0);
+ }
+EOF
+ (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
+ test -z "$HP_ARCH" && HP_ARCH=hppa
+ fi ;;
+ esac
+ if [ ${HP_ARCH} = "hppa2.0w" ]
+ then
+ eval $set_cc_for_build
+
+ # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating
+ # 32-bit code. hppa64-hp-hpux* has the same kernel and a compiler
+ # generating 64-bit code. GNU and HP use different nomenclature:
+ #
+ # $ CC_FOR_BUILD=cc ./config.guess
+ # => hppa2.0w-hp-hpux11.23
+ # $ CC_FOR_BUILD="cc +DA2.0w" ./config.guess
+ # => hppa64-hp-hpux11.23
+
+ if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) |
+ grep -q __LP64__
+ then
+ HP_ARCH="hppa2.0w"
+ else
+ HP_ARCH="hppa64"
+ fi
+ fi
+ echo ${HP_ARCH}-hp-hpux${HPUX_REV}
+ exit ;;
+ ia64:HP-UX:*:*)
+ HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
+ echo ia64-hp-hpux${HPUX_REV}
+ exit ;;
+ 3050*:HI-UX:*:*)
+ eval $set_cc_for_build
+ sed 's/^ //' << EOF >$dummy.c
+ #include <unistd.h>
+ int
+ main ()
+ {
+ long cpu = sysconf (_SC_CPU_VERSION);
+ /* The order matters, because CPU_IS_HP_MC68K erroneously returns
+ true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct
+ results, however. */
+ if (CPU_IS_PA_RISC (cpu))
+ {
+ switch (cpu)
+ {
+ case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break;
+ case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break;
+ case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break;
+ default: puts ("hppa-hitachi-hiuxwe2"); break;
+ }
+ }
+ else if (CPU_IS_HP_MC68K (cpu))
+ puts ("m68k-hitachi-hiuxwe2");
+ else puts ("unknown-hitachi-hiuxwe2");
+ exit (0);
+ }
+EOF
+ $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` &&
+ { echo "$SYSTEM_NAME"; exit; }
+ echo unknown-hitachi-hiuxwe2
+ exit ;;
+ 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )
+ echo hppa1.1-hp-bsd
+ exit ;;
+ 9000/8??:4.3bsd:*:*)
+ echo hppa1.0-hp-bsd
+ exit ;;
+ *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*)
+ echo hppa1.0-hp-mpeix
+ exit ;;
+ hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* )
+ echo hppa1.1-hp-osf
+ exit ;;
+ hp8??:OSF1:*:*)
+ echo hppa1.0-hp-osf
+ exit ;;
+ i*86:OSF1:*:*)
+ if [ -x /usr/sbin/sysversion ] ; then
+ echo ${UNAME_MACHINE}-unknown-osf1mk
+ else
+ echo ${UNAME_MACHINE}-unknown-osf1
+ fi
+ exit ;;
+ parisc*:Lites*:*:*)
+ echo hppa1.1-hp-lites
+ exit ;;
+ C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)
+ echo c1-convex-bsd
+ exit ;;
+ C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*)
+ if getsysinfo -f scalar_acc
+ then echo c32-convex-bsd
+ else echo c2-convex-bsd
+ fi
+ exit ;;
+ C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*)
+ echo c34-convex-bsd
+ exit ;;
+ C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*)
+ echo c38-convex-bsd
+ exit ;;
+ C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)
+ echo c4-convex-bsd
+ exit ;;
+ CRAY*Y-MP:*:*:*)
+ echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+ exit ;;
+ CRAY*[A-Z]90:*:*:*)
+ echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \
+ | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \
+ -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \
+ -e 's/\.[^.]*$/.X/'
+ exit ;;
+ CRAY*TS:*:*:*)
+ echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+ exit ;;
+ CRAY*T3E:*:*:*)
+ echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+ exit ;;
+ CRAY*SV1:*:*:*)
+ echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+ exit ;;
+ *:UNICOS/mp:*:*)
+ echo craynv-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+ exit ;;
+ F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
+ FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
+ FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
+ FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
+ echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+ exit ;;
+ 5000:UNIX_System_V:4.*:*)
+ FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
+ FUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'`
+ echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+ exit ;;
+ i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
+ echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
+ exit ;;
+ sparc*:BSD/OS:*:*)
+ echo sparc-unknown-bsdi${UNAME_RELEASE}
+ exit ;;
+ *:BSD/OS:*:*)
+ echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
+ exit ;;
+ *:FreeBSD:*:*)
+ UNAME_PROCESSOR=`/usr/bin/uname -p`
+ case ${UNAME_PROCESSOR} in
+ amd64)
+ echo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
+ *)
+ echo ${UNAME_PROCESSOR}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
+ esac
+ exit ;;
+ i*:CYGWIN*:*)
+ echo ${UNAME_MACHINE}-pc-cygwin
+ exit ;;
+ *:MINGW64*:*)
+ echo ${UNAME_MACHINE}-pc-mingw64
+ exit ;;
+ *:MINGW*:*)
+ echo ${UNAME_MACHINE}-pc-mingw32
+ exit ;;
+ *:MSYS*:*)
+ echo ${UNAME_MACHINE}-pc-msys
+ exit ;;
+ i*:windows32*:*)
+ # uname -m includes "-pc" on this system.
+ echo ${UNAME_MACHINE}-mingw32
+ exit ;;
+ i*:PW*:*)
+ echo ${UNAME_MACHINE}-pc-pw32
+ exit ;;
+ *:Interix*:*)
+ case ${UNAME_MACHINE} in
+ x86)
+ echo i586-pc-interix${UNAME_RELEASE}
+ exit ;;
+ authenticamd | genuineintel | EM64T)
+ echo x86_64-unknown-interix${UNAME_RELEASE}
+ exit ;;
+ IA64)
+ echo ia64-unknown-interix${UNAME_RELEASE}
+ exit ;;
+ esac ;;
+ [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)
+ echo i${UNAME_MACHINE}-pc-mks
+ exit ;;
+ 8664:Windows_NT:*)
+ echo x86_64-pc-mks
+ exit ;;
+ i*:Windows_NT*:* | Pentium*:Windows_NT*:*)
+ # How do we know it's Interix rather than the generic POSIX subsystem?
+ # It also conflicts with pre-2.0 versions of AT&T UWIN. Should we
+ # UNAME_MACHINE based on the output of uname instead of i386?
+ echo i586-pc-interix
+ exit ;;
+ i*:UWIN*:*)
+ echo ${UNAME_MACHINE}-pc-uwin
+ exit ;;
+ amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*)
+ echo x86_64-unknown-cygwin
+ exit ;;
+ p*:CYGWIN*:*)
+ echo powerpcle-unknown-cygwin
+ exit ;;
+ prep*:SunOS:5.*:*)
+ echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+ exit ;;
+ *:GNU:*:*)
+ # the GNU system
+ echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-${LIBC}`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
+ exit ;;
+ *:GNU/*:*:*)
+ # other systems with GNU libc and userland
+ echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-${LIBC}
+ exit ;;
+ i*86:Minix:*:*)
+ echo ${UNAME_MACHINE}-pc-minix
+ exit ;;
+ aarch64:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ aarch64_be:Linux:*:*)
+ UNAME_MACHINE=aarch64_be
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ alpha:Linux:*:*)
+ case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
+ EV5) UNAME_MACHINE=alphaev5 ;;
+ EV56) UNAME_MACHINE=alphaev56 ;;
+ PCA56) UNAME_MACHINE=alphapca56 ;;
+ PCA57) UNAME_MACHINE=alphapca56 ;;
+ EV6) UNAME_MACHINE=alphaev6 ;;
+ EV67) UNAME_MACHINE=alphaev67 ;;
+ EV68*) UNAME_MACHINE=alphaev68 ;;
+ esac
+ objdump --private-headers /bin/sh | grep -q ld.so.1
+ if test "$?" = 0 ; then LIBC="gnulibc1" ; fi
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ arc:Linux:*:* | arceb:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ arm*:Linux:*:*)
+ eval $set_cc_for_build
+ if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
+ | grep -q __ARM_EABI__
+ then
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ else
+ if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \
+ | grep -q __ARM_PCS_VFP
+ then
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabi
+ else
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabihf
+ fi
+ fi
+ exit ;;
+ avr32*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ cris:Linux:*:*)
+ echo ${UNAME_MACHINE}-axis-linux-${LIBC}
+ exit ;;
+ crisv32:Linux:*:*)
+ echo ${UNAME_MACHINE}-axis-linux-${LIBC}
+ exit ;;
+ e2k:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ frv:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ hexagon:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ i*86:Linux:*:*)
+ echo ${UNAME_MACHINE}-pc-linux-${LIBC}
+ exit ;;
+ ia64:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ m32r*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ m68*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ mips:Linux:*:* | mips64:Linux:*:*)
+ eval $set_cc_for_build
+ sed 's/^ //' << EOF >$dummy.c
+ #undef CPU
+ #undef ${UNAME_MACHINE}
+ #undef ${UNAME_MACHINE}el
+ #if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
+ CPU=${UNAME_MACHINE}el
+ #else
+ #if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
+ CPU=${UNAME_MACHINE}
+ #else
+ CPU=
+ #endif
+ #endif
+EOF
+ eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`
+ test x"${CPU}" != x && { echo "${CPU}-unknown-linux-${LIBC}"; exit; }
+ ;;
+ openrisc*:Linux:*:*)
+ echo or1k-unknown-linux-${LIBC}
+ exit ;;
+ or32:Linux:*:* | or1k*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ padre:Linux:*:*)
+ echo sparc-unknown-linux-${LIBC}
+ exit ;;
+ parisc64:Linux:*:* | hppa64:Linux:*:*)
+ echo hppa64-unknown-linux-${LIBC}
+ exit ;;
+ parisc:Linux:*:* | hppa:Linux:*:*)
+ # Look for CPU level
+ case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
+ PA7*) echo hppa1.1-unknown-linux-${LIBC} ;;
+ PA8*) echo hppa2.0-unknown-linux-${LIBC} ;;
+ *) echo hppa-unknown-linux-${LIBC} ;;
+ esac
+ exit ;;
+ ppc64:Linux:*:*)
+ echo powerpc64-unknown-linux-${LIBC}
+ exit ;;
+ ppc:Linux:*:*)
+ echo powerpc-unknown-linux-${LIBC}
+ exit ;;
+ ppc64le:Linux:*:*)
+ echo powerpc64le-unknown-linux-${LIBC}
+ exit ;;
+ ppcle:Linux:*:*)
+ echo powerpcle-unknown-linux-${LIBC}
+ exit ;;
+ s390:Linux:*:* | s390x:Linux:*:*)
+ echo ${UNAME_MACHINE}-ibm-linux-${LIBC}
+ exit ;;
+ sh64*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ sh*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ sparc:Linux:*:* | sparc64:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ tile*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ vax:Linux:*:*)
+ echo ${UNAME_MACHINE}-dec-linux-${LIBC}
+ exit ;;
+ x86_64:Linux:*:*)
+ echo ${UNAME_MACHINE}-pc-linux-${LIBC}
+ exit ;;
+ xtensa*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+ exit ;;
+ i*86:DYNIX/ptx:4*:*)
+ # ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
+ # earlier versions are messed up and put the nodename in both
+ # sysname and nodename.
+ echo i386-sequent-sysv4
+ exit ;;
+ i*86:UNIX_SV:4.2MP:2.*)
+ # Unixware is an offshoot of SVR4, but it has its own version
+ # number series starting with 2...
+ # I am not positive that other SVR4 systems won't match this,
+ # I just have to hope. -- rms.
+ # Use sysv4.2uw... so that sysv4* matches it.
+ echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
+ exit ;;
+ i*86:OS/2:*:*)
+ # If we were able to find `uname', then EMX Unix compatibility
+ # is probably installed.
+ echo ${UNAME_MACHINE}-pc-os2-emx
+ exit ;;
+ i*86:XTS-300:*:STOP)
+ echo ${UNAME_MACHINE}-unknown-stop
+ exit ;;
+ i*86:atheos:*:*)
+ echo ${UNAME_MACHINE}-unknown-atheos
+ exit ;;
+ i*86:syllable:*:*)
+ echo ${UNAME_MACHINE}-pc-syllable
+ exit ;;
+ i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.[02]*:*)
+ echo i386-unknown-lynxos${UNAME_RELEASE}
+ exit ;;
+ i*86:*DOS:*:*)
+ echo ${UNAME_MACHINE}-pc-msdosdjgpp
+ exit ;;
+ i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
+ UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
+ if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
+ echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}
+ else
+ echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}
+ fi
+ exit ;;
+ i*86:*:5:[678]*)
+ # UnixWare 7.x, OpenUNIX and OpenServer 6.
+ case `/bin/uname -X | grep "^Machine"` in
+ *486*) UNAME_MACHINE=i486 ;;
+ *Pentium) UNAME_MACHINE=i586 ;;
+ *Pent*|*Celeron) UNAME_MACHINE=i686 ;;
+ esac
+ echo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION}
+ exit ;;
+ i*86:*:3.2:*)
+ if test -f /usr/options/cb.name; then
+ UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
+ echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
+ elif /bin/uname -X 2>/dev/null >/dev/null ; then
+ UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`
+ (/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486
+ (/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \
+ && UNAME_MACHINE=i586
+ (/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \
+ && UNAME_MACHINE=i686
+ (/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \
+ && UNAME_MACHINE=i686
+ echo ${UNAME_MACHINE}-pc-sco$UNAME_REL
+ else
+ echo ${UNAME_MACHINE}-pc-sysv32
+ fi
+ exit ;;
+ pc:*:*:*)
+ # Left here for compatibility:
+ # uname -m prints for DJGPP always 'pc', but it prints nothing about
+ # the processor, so we play safe by assuming i586.
+ # Note: whatever this is, it MUST be the same as what config.sub
+ # prints for the "djgpp" host, or else GDB configury will decide that
+ # this is a cross-build.
+ echo i586-pc-msdosdjgpp
+ exit ;;
+ Intel:Mach:3*:*)
+ echo i386-pc-mach3
+ exit ;;
+ paragon:*:*:*)
+ echo i860-intel-osf1
+ exit ;;
+ i860:*:4.*:*) # i860-SVR4
+ if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then
+ echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4
+ else # Add other i860-SVR4 vendors below as they are discovered.
+ echo i860-unknown-sysv${UNAME_RELEASE} # Unknown i860-SVR4
+ fi
+ exit ;;
+ mini*:CTIX:SYS*5:*)
+ # "miniframe"
+ echo m68010-convergent-sysv
+ exit ;;
+ mc68k:UNIX:SYSTEM5:3.51m)
+ echo m68k-convergent-sysv
+ exit ;;
+ M680?0:D-NIX:5.3:*)
+ echo m68k-diab-dnix
+ exit ;;
+ M68*:*:R3V[5678]*:*)
+ test -r /sysV68 && { echo 'm68k-motorola-sysv'; exit; } ;;
+ 3[345]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0 | S7501*:*:4.0:3.0)
+ OS_REL=''
+ test -r /etc/.relid \
+ && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
+ /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+ && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
+ /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
+ && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
+ 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
+ /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+ && { echo i486-ncr-sysv4; exit; } ;;
+ NCR*:*:4.2:* | MPRAS*:*:4.2:*)
+ OS_REL='.3'
+ test -r /etc/.relid \
+ && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
+ /bin/uname -p 2>/dev/null | grep 86 >/dev/null \
+ && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
+ /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
+ && { echo i586-ncr-sysv4.3${OS_REL}; exit; }
+ /bin/uname -p 2>/dev/null | /bin/grep pteron >/dev/null \
+ && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
+ m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)
+ echo m68k-unknown-lynxos${UNAME_RELEASE}
+ exit ;;
+ mc68030:UNIX_System_V:4.*:*)
+ echo m68k-atari-sysv4
+ exit ;;
+ TSUNAMI:LynxOS:2.*:*)
+ echo sparc-unknown-lynxos${UNAME_RELEASE}
+ exit ;;
+ rs6000:LynxOS:2.*:*)
+ echo rs6000-unknown-lynxos${UNAME_RELEASE}
+ exit ;;
+ PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.[02]*:*)
+ echo powerpc-unknown-lynxos${UNAME_RELEASE}
+ exit ;;
+ SM[BE]S:UNIX_SV:*:*)
+ echo mips-dde-sysv${UNAME_RELEASE}
+ exit ;;
+ RM*:ReliantUNIX-*:*:*)
+ echo mips-sni-sysv4
+ exit ;;
+ RM*:SINIX-*:*:*)
+ echo mips-sni-sysv4
+ exit ;;
+ *:SINIX-*:*:*)
+ if uname -p 2>/dev/null >/dev/null ; then
+ UNAME_MACHINE=`(uname -p) 2>/dev/null`
+ echo ${UNAME_MACHINE}-sni-sysv4
+ else
+ echo ns32k-sni-sysv
+ fi
+ exit ;;
+ PENTIUM:*:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort
+ # says <Richard.M.Bartel@ccMail.Census.GOV>
+ echo i586-unisys-sysv4
+ exit ;;
+ *:UNIX_System_V:4*:FTX*)
+ # From Gerald Hewes <hewes@openmarket.com>.
+ # How about differentiating between stratus architectures? -djm
+ echo hppa1.1-stratus-sysv4
+ exit ;;
+ *:*:*:FTX*)
+ # From seanf@swdc.stratus.com.
+ echo i860-stratus-sysv4
+ exit ;;
+ i*86:VOS:*:*)
+ # From Paul.Green@stratus.com.
+ echo ${UNAME_MACHINE}-stratus-vos
+ exit ;;
+ *:VOS:*:*)
+ # From Paul.Green@stratus.com.
+ echo hppa1.1-stratus-vos
+ exit ;;
+ mc68*:A/UX:*:*)
+ echo m68k-apple-aux${UNAME_RELEASE}
+ exit ;;
+ news*:NEWS-OS:6*:*)
+ echo mips-sony-newsos6
+ exit ;;
+ R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)
+ if [ -d /usr/nec ]; then
+ echo mips-nec-sysv${UNAME_RELEASE}
+ else
+ echo mips-unknown-sysv${UNAME_RELEASE}
+ fi
+ exit ;;
+ BeBox:BeOS:*:*) # BeOS running on hardware made by Be, PPC only.
+ echo powerpc-be-beos
+ exit ;;
+ BeMac:BeOS:*:*) # BeOS running on Mac or Mac clone, PPC only.
+ echo powerpc-apple-beos
+ exit ;;
+ BePC:BeOS:*:*) # BeOS running on Intel PC compatible.
+ echo i586-pc-beos
+ exit ;;
+ BePC:Haiku:*:*) # Haiku running on Intel PC compatible.
+ echo i586-pc-haiku
+ exit ;;
+ x86_64:Haiku:*:*)
+ echo x86_64-unknown-haiku
+ exit ;;
+ SX-4:SUPER-UX:*:*)
+ echo sx4-nec-superux${UNAME_RELEASE}
+ exit ;;
+ SX-5:SUPER-UX:*:*)
+ echo sx5-nec-superux${UNAME_RELEASE}
+ exit ;;
+ SX-6:SUPER-UX:*:*)
+ echo sx6-nec-superux${UNAME_RELEASE}
+ exit ;;
+ SX-7:SUPER-UX:*:*)
+ echo sx7-nec-superux${UNAME_RELEASE}
+ exit ;;
+ SX-8:SUPER-UX:*:*)
+ echo sx8-nec-superux${UNAME_RELEASE}
+ exit ;;
+ SX-8R:SUPER-UX:*:*)
+ echo sx8r-nec-superux${UNAME_RELEASE}
+ exit ;;
+ Power*:Rhapsody:*:*)
+ echo powerpc-apple-rhapsody${UNAME_RELEASE}
+ exit ;;
+ *:Rhapsody:*:*)
+ echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}
+ exit ;;
+ *:Darwin:*:*)
+ UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown
+ eval $set_cc_for_build
+ if test "$UNAME_PROCESSOR" = unknown ; then
+ UNAME_PROCESSOR=powerpc
+ fi
+ if test `echo "$UNAME_RELEASE" | sed -e 's/\..*//'` -le 10 ; then
+ if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
+ if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \
+ (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
+ grep IS_64BIT_ARCH >/dev/null
+ then
+ case $UNAME_PROCESSOR in
+ i386) UNAME_PROCESSOR=x86_64 ;;
+ powerpc) UNAME_PROCESSOR=powerpc64 ;;
+ esac
+ fi
+ fi
+ elif test "$UNAME_PROCESSOR" = i386 ; then
+ # Avoid executing cc on OS X 10.9, as it ships with a stub
+ # that puts up a graphical alert prompting to install
+ # developer tools. Any system running Mac OS X 10.7 or
+ # later (Darwin 11 and later) is required to have a 64-bit
+ # processor. This is not true of the ARM version of Darwin
+ # that Apple uses in portable devices.
+ UNAME_PROCESSOR=x86_64
+ fi
+ echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
+ exit ;;
+ *:procnto*:*:* | *:QNX:[0123456789]*:*)
+ UNAME_PROCESSOR=`uname -p`
+ if test "$UNAME_PROCESSOR" = "x86"; then
+ UNAME_PROCESSOR=i386
+ UNAME_MACHINE=pc
+ fi
+ echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}
+ exit ;;
+ *:QNX:*:4*)
+ echo i386-pc-qnx
+ exit ;;
+ NEO-?:NONSTOP_KERNEL:*:*)
+ echo neo-tandem-nsk${UNAME_RELEASE}
+ exit ;;
+ NSE-*:NONSTOP_KERNEL:*:*)
+ echo nse-tandem-nsk${UNAME_RELEASE}
+ exit ;;
+ NSR-?:NONSTOP_KERNEL:*:*)
+ echo nsr-tandem-nsk${UNAME_RELEASE}
+ exit ;;
+ *:NonStop-UX:*:*)
+ echo mips-compaq-nonstopux
+ exit ;;
+ BS2000:POSIX*:*:*)
+ echo bs2000-siemens-sysv
+ exit ;;
+ DS/*:UNIX_System_V:*:*)
+ echo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE}
+ exit ;;
+ *:Plan9:*:*)
+ # "uname -m" is not consistent, so use $cputype instead. 386
+ # is converted to i386 for consistency with other x86
+ # operating systems.
+ if test "$cputype" = "386"; then
+ UNAME_MACHINE=i386
+ else
+ UNAME_MACHINE="$cputype"
+ fi
+ echo ${UNAME_MACHINE}-unknown-plan9
+ exit ;;
+ *:TOPS-10:*:*)
+ echo pdp10-unknown-tops10
+ exit ;;
+ *:TENEX:*:*)
+ echo pdp10-unknown-tenex
+ exit ;;
+ KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*)
+ echo pdp10-dec-tops20
+ exit ;;
+ XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*)
+ echo pdp10-xkl-tops20
+ exit ;;
+ *:TOPS-20:*:*)
+ echo pdp10-unknown-tops20
+ exit ;;
+ *:ITS:*:*)
+ echo pdp10-unknown-its
+ exit ;;
+ SEI:*:*:SEIUX)
+ echo mips-sei-seiux${UNAME_RELEASE}
+ exit ;;
+ *:DragonFly:*:*)
+ echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`
+ exit ;;
+ *:*VMS:*:*)
+ UNAME_MACHINE=`(uname -p) 2>/dev/null`
+ case "${UNAME_MACHINE}" in
+ A*) echo alpha-dec-vms ; exit ;;
+ I*) echo ia64-dec-vms ; exit ;;
+ V*) echo vax-dec-vms ; exit ;;
+ esac ;;
+ *:XENIX:*:SysV)
+ echo i386-pc-xenix
+ exit ;;
+ i*86:skyos:*:*)
+ echo ${UNAME_MACHINE}-pc-skyos`echo ${UNAME_RELEASE}` | sed -e 's/ .*$//'
+ exit ;;
+ i*86:rdos:*:*)
+ echo ${UNAME_MACHINE}-pc-rdos
+ exit ;;
+ i*86:AROS:*:*)
+ echo ${UNAME_MACHINE}-pc-aros
+ exit ;;
+ x86_64:VMkernel:*:*)
+ echo ${UNAME_MACHINE}-unknown-esx
+ exit ;;
+esac
+
+cat >&2 <<EOF
+$0: unable to guess system type
+
+This script, last modified $timestamp, has failed to recognize
+the operating system you are using. It is advised that you
+download the most up to date version of the config scripts from
+
+ http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD
+and
+ http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD
+
+If the version you run ($0) is already up to date, please
+send the following data and any information you think might be
+pertinent to <config-patches@gnu.org> in order to provide the needed
+information to handle your system.
+
+config.guess timestamp = $timestamp
+
+uname -m = `(uname -m) 2>/dev/null || echo unknown`
+uname -r = `(uname -r) 2>/dev/null || echo unknown`
+uname -s = `(uname -s) 2>/dev/null || echo unknown`
+uname -v = `(uname -v) 2>/dev/null || echo unknown`
+
+/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null`
+/bin/uname -X = `(/bin/uname -X) 2>/dev/null`
+
+hostinfo = `(hostinfo) 2>/dev/null`
+/bin/universe = `(/bin/universe) 2>/dev/null`
+/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null`
+/bin/arch = `(/bin/arch) 2>/dev/null`
+/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null`
+/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null`
+
+UNAME_MACHINE = ${UNAME_MACHINE}
+UNAME_RELEASE = ${UNAME_RELEASE}
+UNAME_SYSTEM = ${UNAME_SYSTEM}
+UNAME_VERSION = ${UNAME_VERSION}
+EOF
+
+exit 1
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "timestamp='"
+# time-stamp-format: "%:y-%02m-%02d"
+# time-stamp-end: "'"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.sub b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.sub
new file mode 100755
index 000000000..1acc966a3
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/config.sub
@@ -0,0 +1,1813 @@
+#! /bin/sh
+# Configuration validation subroutine script.
+# Copyright 1992-2015 Free Software Foundation, Inc.
+
+timestamp='2015-08-20'
+
+# This file is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful, but
+# WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, see <http://www.gnu.org/licenses/>.
+#
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that
+# program. This Exception is an additional permission under section 7
+# of the GNU General Public License, version 3 ("GPLv3").
+
+
+# Please send patches to <config-patches@gnu.org>.
+#
+# Configuration subroutine to validate and canonicalize a configuration type.
+# Supply the specified configuration type as an argument.
+# If it is invalid, we print an error message on stderr and exit with code 1.
+# Otherwise, we print the canonical config type on stdout and succeed.
+
+# You can get the latest version of this script from:
+# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD
+
+# This file is supposed to be the same for all GNU packages
+# and recognize all the CPU types, system types and aliases
+# that are meaningful with *any* GNU software.
+# Each package is responsible for reporting which valid configurations
+# it does not support. The user should be able to distinguish
+# a failure to support a valid configuration from a meaningless
+# configuration.
+
+# The goal of this file is to map all the various variations of a given
+# machine specification into a single specification in the form:
+# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM
+# or in some cases, the newer four-part form:
+# CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM
+# It is wrong to echo any other type of specification.
+
+me=`echo "$0" | sed -e 's,.*/,,'`
+
+usage="\
+Usage: $0 [OPTION] CPU-MFR-OPSYS
+ $0 [OPTION] ALIAS
+
+Canonicalize a configuration name.
+
+Operation modes:
+ -h, --help print this help, then exit
+ -t, --time-stamp print date of last modification, then exit
+ -v, --version print version number, then exit
+
+Report bugs and patches to <config-patches@gnu.org>."
+
+version="\
+GNU config.sub ($timestamp)
+
+Copyright 1992-2015 Free Software Foundation, Inc.
+
+This is free software; see the source for copying conditions. There is NO
+warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
+
+help="
+Try \`$me --help' for more information."
+
+# Parse command line
+while test $# -gt 0 ; do
+ case $1 in
+ --time-stamp | --time* | -t )
+ echo "$timestamp" ; exit ;;
+ --version | -v )
+ echo "$version" ; exit ;;
+ --help | --h* | -h )
+ echo "$usage"; exit ;;
+ -- ) # Stop option processing
+ shift; break ;;
+ - ) # Use stdin as input.
+ break ;;
+ -* )
+ echo "$me: invalid option $1$help"
+ exit 1 ;;
+
+ *local*)
+ # First pass through any local machine types.
+ echo $1
+ exit ;;
+
+ * )
+ break ;;
+ esac
+done
+
+case $# in
+ 0) echo "$me: missing argument$help" >&2
+ exit 1;;
+ 1) ;;
+ *) echo "$me: too many arguments$help" >&2
+ exit 1;;
+esac
+
+# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any).
+# Here we must recognize all the valid KERNEL-OS combinations.
+maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
+case $maybe_os in
+ nto-qnx* | linux-gnu* | linux-android* | linux-dietlibc | linux-newlib* | \
+ linux-musl* | linux-uclibc* | uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | \
+ knetbsd*-gnu* | netbsd*-gnu* | netbsd*-eabi* | \
+ kopensolaris*-gnu* | \
+ storm-chaos* | os2-emx* | rtmk-nova*)
+ os=-$maybe_os
+ basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
+ ;;
+ android-linux)
+ os=-linux-android
+ basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`-unknown
+ ;;
+ *)
+ basic_machine=`echo $1 | sed 's/-[^-]*$//'`
+ if [ $basic_machine != $1 ]
+ then os=`echo $1 | sed 's/.*-/-/'`
+ else os=; fi
+ ;;
+esac
+
+### Let's recognize common machines as not being operating systems so
+### that things like config.sub decstation-3100 work. We also
+### recognize some manufacturers as not being operating systems, so we
+### can provide default operating systems below.
+case $os in
+ -sun*os*)
+ # Prevent following clause from handling this invalid input.
+ ;;
+ -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \
+ -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \
+ -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \
+ -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\
+ -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \
+ -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \
+ -apple | -axis | -knuth | -cray | -microblaze*)
+ os=
+ basic_machine=$1
+ ;;
+ -bluegene*)
+ os=-cnk
+ ;;
+ -sim | -cisco | -oki | -wec | -winbond)
+ os=
+ basic_machine=$1
+ ;;
+ -scout)
+ ;;
+ -wrs)
+ os=-vxworks
+ basic_machine=$1
+ ;;
+ -chorusos*)
+ os=-chorusos
+ basic_machine=$1
+ ;;
+ -chorusrdb)
+ os=-chorusrdb
+ basic_machine=$1
+ ;;
+ -hiux*)
+ os=-hiuxwe2
+ ;;
+ -sco6)
+ os=-sco5v6
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco5)
+ os=-sco3.2v5
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco4)
+ os=-sco3.2v4
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco3.2.[4-9]*)
+ os=`echo $os | sed -e 's/sco3.2./sco3.2v/'`
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco3.2v[4-9]*)
+ # Don't forget version if it is 3.2v4 or newer.
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco5v6*)
+ # Don't forget version if it is 3.2v4 or newer.
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -sco*)
+ os=-sco3.2v2
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -udk*)
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -isc)
+ os=-isc2.2
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -clix*)
+ basic_machine=clipper-intergraph
+ ;;
+ -isc*)
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+ ;;
+ -lynx*178)
+ os=-lynxos178
+ ;;
+ -lynx*5)
+ os=-lynxos5
+ ;;
+ -lynx*)
+ os=-lynxos
+ ;;
+ -ptx*)
+ basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'`
+ ;;
+ -windowsnt*)
+ os=`echo $os | sed -e 's/windowsnt/winnt/'`
+ ;;
+ -psos*)
+ os=-psos
+ ;;
+ -mint | -mint[0-9]*)
+ basic_machine=m68k-atari
+ os=-mint
+ ;;
+esac
+
+# Decode aliases for certain CPU-COMPANY combinations.
+case $basic_machine in
+ # Recognize the basic CPU types without company name.
+ # Some are omitted here because they have special meanings below.
+ 1750a | 580 \
+ | a29k \
+ | aarch64 | aarch64_be \
+ | alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
+ | alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
+ | am33_2.0 \
+ | arc | arceb \
+ | arm | arm[bl]e | arme[lb] | armv[2-8] | armv[3-8][lb] | armv7[arm] \
+ | avr | avr32 \
+ | ba \
+ | be32 | be64 \
+ | bfin \
+ | c4x | c8051 | clipper \
+ | d10v | d30v | dlx | dsp16xx \
+ | e2k | epiphany \
+ | fido | fr30 | frv | ft32 \
+ | h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
+ | hexagon \
+ | i370 | i860 | i960 | ia64 \
+ | ip2k | iq2000 \
+ | k1om \
+ | le32 | le64 \
+ | lm32 \
+ | m32c | m32r | m32rle | m68000 | m68k | m88k \
+ | maxq | mb | microblaze | microblazeel | mcore | mep | metag \
+ | mips | mipsbe | mipseb | mipsel | mipsle \
+ | mips16 \
+ | mips64 | mips64el \
+ | mips64octeon | mips64octeonel \
+ | mips64orion | mips64orionel \
+ | mips64r5900 | mips64r5900el \
+ | mips64vr | mips64vrel \
+ | mips64vr4100 | mips64vr4100el \
+ | mips64vr4300 | mips64vr4300el \
+ | mips64vr5000 | mips64vr5000el \
+ | mips64vr5900 | mips64vr5900el \
+ | mipsisa32 | mipsisa32el \
+ | mipsisa32r2 | mipsisa32r2el \
+ | mipsisa32r6 | mipsisa32r6el \
+ | mipsisa64 | mipsisa64el \
+ | mipsisa64r2 | mipsisa64r2el \
+ | mipsisa64r6 | mipsisa64r6el \
+ | mipsisa64sb1 | mipsisa64sb1el \
+ | mipsisa64sr71k | mipsisa64sr71kel \
+ | mipsr5900 | mipsr5900el \
+ | mipstx39 | mipstx39el \
+ | mn10200 | mn10300 \
+ | moxie \
+ | mt \
+ | msp430 \
+ | nds32 | nds32le | nds32be \
+ | nios | nios2 | nios2eb | nios2el \
+ | ns16k | ns32k \
+ | open8 | or1k | or1knd | or32 \
+ | pdp10 | pdp11 | pj | pjl \
+ | powerpc | powerpc64 | powerpc64le | powerpcle \
+ | pyramid \
+ | riscv32 | riscv64 \
+ | rl78 | rx \
+ | score \
+ | sh | sh[1234] | sh[24]a | sh[24]aeb | sh[23]e | sh[234]eb | sheb | shbe | shle | sh[1234]le | sh3ele \
+ | sh64 | sh64le \
+ | sparc | sparc64 | sparc64b | sparc64v | sparc86x | sparclet | sparclite \
+ | sparcv8 | sparcv9 | sparcv9b | sparcv9v \
+ | spu \
+ | tahoe | tic4x | tic54x | tic55x | tic6x | tic80 | tron \
+ | ubicom32 \
+ | v850 | v850e | v850e1 | v850e2 | v850es | v850e2v3 \
+ | visium \
+ | we32k \
+ | x86 | xc16x | xstormy16 | xtensa \
+ | z8k | z80)
+ basic_machine=$basic_machine-unknown
+ ;;
+ c54x)
+ basic_machine=tic54x-unknown
+ ;;
+ c55x)
+ basic_machine=tic55x-unknown
+ ;;
+ c6x)
+ basic_machine=tic6x-unknown
+ ;;
+ leon|leon[3-9])
+ basic_machine=sparc-$basic_machine
+ ;;
+ m6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | nvptx | picochip)
+ basic_machine=$basic_machine-unknown
+ os=-none
+ ;;
+ m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k)
+ ;;
+ ms1)
+ basic_machine=mt-unknown
+ ;;
+
+ strongarm | thumb | xscale)
+ basic_machine=arm-unknown
+ ;;
+ xgate)
+ basic_machine=$basic_machine-unknown
+ os=-none
+ ;;
+ xscaleeb)
+ basic_machine=armeb-unknown
+ ;;
+
+ xscaleel)
+ basic_machine=armel-unknown
+ ;;
+
+ # We use `pc' rather than `unknown'
+ # because (1) that's what they normally are, and
+ # (2) the word "unknown" tends to confuse beginning users.
+ i*86 | x86_64)
+ basic_machine=$basic_machine-pc
+ ;;
+ # Object if more than one company name word.
+ *-*-*)
+ echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+ exit 1
+ ;;
+ # Recognize the basic CPU types with company name.
+ 580-* \
+ | a29k-* \
+ | aarch64-* | aarch64_be-* \
+ | alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
+ | alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
+ | alphapca5[67]-* | alpha64pca5[67]-* | arc-* | arceb-* \
+ | arm-* | armbe-* | armle-* | armeb-* | armv*-* \
+ | avr-* | avr32-* \
+ | ba-* \
+ | be32-* | be64-* \
+ | bfin-* | bs2000-* \
+ | c[123]* | c30-* | [cjt]90-* | c4x-* \
+ | c8051-* | clipper-* | craynv-* | cydra-* \
+ | d10v-* | d30v-* | dlx-* \
+ | e2k-* | elxsi-* \
+ | f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \
+ | h8300-* | h8500-* \
+ | hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
+ | hexagon-* \
+ | i*86-* | i860-* | i960-* | ia64-* \
+ | ip2k-* | iq2000-* \
+ | k1om-* \
+ | le32-* | le64-* \
+ | lm32-* \
+ | m32c-* | m32r-* | m32rle-* \
+ | m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \
+ | m88110-* | m88k-* | maxq-* | mcore-* | metag-* \
+ | microblaze-* | microblazeel-* \
+ | mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \
+ | mips16-* \
+ | mips64-* | mips64el-* \
+ | mips64octeon-* | mips64octeonel-* \
+ | mips64orion-* | mips64orionel-* \
+ | mips64r5900-* | mips64r5900el-* \
+ | mips64vr-* | mips64vrel-* \
+ | mips64vr4100-* | mips64vr4100el-* \
+ | mips64vr4300-* | mips64vr4300el-* \
+ | mips64vr5000-* | mips64vr5000el-* \
+ | mips64vr5900-* | mips64vr5900el-* \
+ | mipsisa32-* | mipsisa32el-* \
+ | mipsisa32r2-* | mipsisa32r2el-* \
+ | mipsisa32r6-* | mipsisa32r6el-* \
+ | mipsisa64-* | mipsisa64el-* \
+ | mipsisa64r2-* | mipsisa64r2el-* \
+ | mipsisa64r6-* | mipsisa64r6el-* \
+ | mipsisa64sb1-* | mipsisa64sb1el-* \
+ | mipsisa64sr71k-* | mipsisa64sr71kel-* \
+ | mipsr5900-* | mipsr5900el-* \
+ | mipstx39-* | mipstx39el-* \
+ | mmix-* \
+ | mt-* \
+ | msp430-* \
+ | nds32-* | nds32le-* | nds32be-* \
+ | nios-* | nios2-* | nios2eb-* | nios2el-* \
+ | none-* | np1-* | ns16k-* | ns32k-* \
+ | open8-* \
+ | or1k*-* \
+ | orion-* \
+ | pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
+ | powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* \
+ | pyramid-* \
+ | riscv32-* | riscv64-* \
+ | rl78-* | romp-* | rs6000-* | rx-* \
+ | sh-* | sh[1234]-* | sh[24]a-* | sh[24]aeb-* | sh[23]e-* | sh[34]eb-* | sheb-* | shbe-* \
+ | shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \
+ | sparc-* | sparc64-* | sparc64b-* | sparc64v-* | sparc86x-* | sparclet-* \
+ | sparclite-* \
+ | sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | sv1-* | sx*-* \
+ | tahoe-* \
+ | tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \
+ | tile*-* \
+ | tron-* \
+ | ubicom32-* \
+ | v850-* | v850e-* | v850e1-* | v850es-* | v850e2-* | v850e2v3-* \
+ | vax-* \
+ | visium-* \
+ | we32k-* \
+ | x86-* | x86_64-* | xc16x-* | xps100-* \
+ | xstormy16-* | xtensa*-* \
+ | ymp-* \
+ | z8k-* | z80-*)
+ ;;
+ # Recognize the basic CPU types without company name, with glob match.
+ xtensa*)
+ basic_machine=$basic_machine-unknown
+ ;;
+ # Recognize the various machine names and aliases which stand
+ # for a CPU type and a company and sometimes even an OS.
+ 386bsd)
+ basic_machine=i386-unknown
+ os=-bsd
+ ;;
+ 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc)
+ basic_machine=m68000-att
+ ;;
+ 3b*)
+ basic_machine=we32k-att
+ ;;
+ a29khif)
+ basic_machine=a29k-amd
+ os=-udi
+ ;;
+ abacus)
+ basic_machine=abacus-unknown
+ ;;
+ adobe68k)
+ basic_machine=m68010-adobe
+ os=-scout
+ ;;
+ alliant | fx80)
+ basic_machine=fx80-alliant
+ ;;
+ altos | altos3068)
+ basic_machine=m68k-altos
+ ;;
+ am29k)
+ basic_machine=a29k-none
+ os=-bsd
+ ;;
+ amd64)
+ basic_machine=x86_64-pc
+ ;;
+ amd64-*)
+ basic_machine=x86_64-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ amdahl)
+ basic_machine=580-amdahl
+ os=-sysv
+ ;;
+ amiga | amiga-*)
+ basic_machine=m68k-unknown
+ ;;
+ amigaos | amigados)
+ basic_machine=m68k-unknown
+ os=-amigaos
+ ;;
+ amigaunix | amix)
+ basic_machine=m68k-unknown
+ os=-sysv4
+ ;;
+ apollo68)
+ basic_machine=m68k-apollo
+ os=-sysv
+ ;;
+ apollo68bsd)
+ basic_machine=m68k-apollo
+ os=-bsd
+ ;;
+ aros)
+ basic_machine=i386-pc
+ os=-aros
+ ;;
+ asmjs)
+ basic_machine=asmjs-unknown
+ ;;
+ aux)
+ basic_machine=m68k-apple
+ os=-aux
+ ;;
+ balance)
+ basic_machine=ns32k-sequent
+ os=-dynix
+ ;;
+ blackfin)
+ basic_machine=bfin-unknown
+ os=-linux
+ ;;
+ blackfin-*)
+ basic_machine=bfin-`echo $basic_machine | sed 's/^[^-]*-//'`
+ os=-linux
+ ;;
+ bluegene*)
+ basic_machine=powerpc-ibm
+ os=-cnk
+ ;;
+ c54x-*)
+ basic_machine=tic54x-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ c55x-*)
+ basic_machine=tic55x-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ c6x-*)
+ basic_machine=tic6x-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ c90)
+ basic_machine=c90-cray
+ os=-unicos
+ ;;
+ cegcc)
+ basic_machine=arm-unknown
+ os=-cegcc
+ ;;
+ convex-c1)
+ basic_machine=c1-convex
+ os=-bsd
+ ;;
+ convex-c2)
+ basic_machine=c2-convex
+ os=-bsd
+ ;;
+ convex-c32)
+ basic_machine=c32-convex
+ os=-bsd
+ ;;
+ convex-c34)
+ basic_machine=c34-convex
+ os=-bsd
+ ;;
+ convex-c38)
+ basic_machine=c38-convex
+ os=-bsd
+ ;;
+ cray | j90)
+ basic_machine=j90-cray
+ os=-unicos
+ ;;
+ craynv)
+ basic_machine=craynv-cray
+ os=-unicosmp
+ ;;
+ cr16 | cr16-*)
+ basic_machine=cr16-unknown
+ os=-elf
+ ;;
+ crds | unos)
+ basic_machine=m68k-crds
+ ;;
+ crisv32 | crisv32-* | etraxfs*)
+ basic_machine=crisv32-axis
+ ;;
+ cris | cris-* | etrax*)
+ basic_machine=cris-axis
+ ;;
+ crx)
+ basic_machine=crx-unknown
+ os=-elf
+ ;;
+ da30 | da30-*)
+ basic_machine=m68k-da30
+ ;;
+ decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn)
+ basic_machine=mips-dec
+ ;;
+ decsystem10* | dec10*)
+ basic_machine=pdp10-dec
+ os=-tops10
+ ;;
+ decsystem20* | dec20*)
+ basic_machine=pdp10-dec
+ os=-tops20
+ ;;
+ delta | 3300 | motorola-3300 | motorola-delta \
+ | 3300-motorola | delta-motorola)
+ basic_machine=m68k-motorola
+ ;;
+ delta88)
+ basic_machine=m88k-motorola
+ os=-sysv3
+ ;;
+ dicos)
+ basic_machine=i686-pc
+ os=-dicos
+ ;;
+ djgpp)
+ basic_machine=i586-pc
+ os=-msdosdjgpp
+ ;;
+ dpx20 | dpx20-*)
+ basic_machine=rs6000-bull
+ os=-bosx
+ ;;
+ dpx2* | dpx2*-bull)
+ basic_machine=m68k-bull
+ os=-sysv3
+ ;;
+ ebmon29k)
+ basic_machine=a29k-amd
+ os=-ebmon
+ ;;
+ elxsi)
+ basic_machine=elxsi-elxsi
+ os=-bsd
+ ;;
+ encore | umax | mmax)
+ basic_machine=ns32k-encore
+ ;;
+ es1800 | OSE68k | ose68k | ose | OSE)
+ basic_machine=m68k-ericsson
+ os=-ose
+ ;;
+ fx2800)
+ basic_machine=i860-alliant
+ ;;
+ genix)
+ basic_machine=ns32k-ns
+ ;;
+ gmicro)
+ basic_machine=tron-gmicro
+ os=-sysv
+ ;;
+ go32)
+ basic_machine=i386-pc
+ os=-go32
+ ;;
+ h3050r* | hiux*)
+ basic_machine=hppa1.1-hitachi
+ os=-hiuxwe2
+ ;;
+ h8300hms)
+ basic_machine=h8300-hitachi
+ os=-hms
+ ;;
+ h8300xray)
+ basic_machine=h8300-hitachi
+ os=-xray
+ ;;
+ h8500hms)
+ basic_machine=h8500-hitachi
+ os=-hms
+ ;;
+ harris)
+ basic_machine=m88k-harris
+ os=-sysv3
+ ;;
+ hp300-*)
+ basic_machine=m68k-hp
+ ;;
+ hp300bsd)
+ basic_machine=m68k-hp
+ os=-bsd
+ ;;
+ hp300hpux)
+ basic_machine=m68k-hp
+ os=-hpux
+ ;;
+ hp3k9[0-9][0-9] | hp9[0-9][0-9])
+ basic_machine=hppa1.0-hp
+ ;;
+ hp9k2[0-9][0-9] | hp9k31[0-9])
+ basic_machine=m68000-hp
+ ;;
+ hp9k3[2-9][0-9])
+ basic_machine=m68k-hp
+ ;;
+ hp9k6[0-9][0-9] | hp6[0-9][0-9])
+ basic_machine=hppa1.0-hp
+ ;;
+ hp9k7[0-79][0-9] | hp7[0-79][0-9])
+ basic_machine=hppa1.1-hp
+ ;;
+ hp9k78[0-9] | hp78[0-9])
+ # FIXME: really hppa2.0-hp
+ basic_machine=hppa1.1-hp
+ ;;
+ hp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893)
+ # FIXME: really hppa2.0-hp
+ basic_machine=hppa1.1-hp
+ ;;
+ hp9k8[0-9][13679] | hp8[0-9][13679])
+ basic_machine=hppa1.1-hp
+ ;;
+ hp9k8[0-9][0-9] | hp8[0-9][0-9])
+ basic_machine=hppa1.0-hp
+ ;;
+ hppa-next)
+ os=-nextstep3
+ ;;
+ hppaosf)
+ basic_machine=hppa1.1-hp
+ os=-osf
+ ;;
+ hppro)
+ basic_machine=hppa1.1-hp
+ os=-proelf
+ ;;
+ i370-ibm* | ibm*)
+ basic_machine=i370-ibm
+ ;;
+ i*86v32)
+ basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+ os=-sysv32
+ ;;
+ i*86v4*)
+ basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+ os=-sysv4
+ ;;
+ i*86v)
+ basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+ os=-sysv
+ ;;
+ i*86sol2)
+ basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+ os=-solaris2
+ ;;
+ i386mach)
+ basic_machine=i386-mach
+ os=-mach
+ ;;
+ i386-vsta | vsta)
+ basic_machine=i386-unknown
+ os=-vsta
+ ;;
+ iris | iris4d)
+ basic_machine=mips-sgi
+ case $os in
+ -irix*)
+ ;;
+ *)
+ os=-irix4
+ ;;
+ esac
+ ;;
+ isi68 | isi)
+ basic_machine=m68k-isi
+ os=-sysv
+ ;;
+ leon-*|leon[3-9]-*)
+ basic_machine=sparc-`echo $basic_machine | sed 's/-.*//'`
+ ;;
+ m68knommu)
+ basic_machine=m68k-unknown
+ os=-linux
+ ;;
+ m68knommu-*)
+ basic_machine=m68k-`echo $basic_machine | sed 's/^[^-]*-//'`
+ os=-linux
+ ;;
+ m88k-omron*)
+ basic_machine=m88k-omron
+ ;;
+ magnum | m3230)
+ basic_machine=mips-mips
+ os=-sysv
+ ;;
+ merlin)
+ basic_machine=ns32k-utek
+ os=-sysv
+ ;;
+ microblaze*)
+ basic_machine=microblaze-xilinx
+ ;;
+ mingw64)
+ basic_machine=x86_64-pc
+ os=-mingw64
+ ;;
+ mingw32)
+ basic_machine=i686-pc
+ os=-mingw32
+ ;;
+ mingw32ce)
+ basic_machine=arm-unknown
+ os=-mingw32ce
+ ;;
+ miniframe)
+ basic_machine=m68000-convergent
+ ;;
+ *mint | -mint[0-9]* | *MiNT | *MiNT[0-9]*)
+ basic_machine=m68k-atari
+ os=-mint
+ ;;
+ mips3*-*)
+ basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`
+ ;;
+ mips3*)
+ basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown
+ ;;
+ monitor)
+ basic_machine=m68k-rom68k
+ os=-coff
+ ;;
+ morphos)
+ basic_machine=powerpc-unknown
+ os=-morphos
+ ;;
+ moxiebox)
+ basic_machine=moxie-unknown
+ os=-moxiebox
+ ;;
+ msdos)
+ basic_machine=i386-pc
+ os=-msdos
+ ;;
+ ms1-*)
+ basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`
+ ;;
+ msys)
+ basic_machine=i686-pc
+ os=-msys
+ ;;
+ mvs)
+ basic_machine=i370-ibm
+ os=-mvs
+ ;;
+ nacl)
+ basic_machine=le32-unknown
+ os=-nacl
+ ;;
+ ncr3000)
+ basic_machine=i486-ncr
+ os=-sysv4
+ ;;
+ netbsd386)
+ basic_machine=i386-unknown
+ os=-netbsd
+ ;;
+ netwinder)
+ basic_machine=armv4l-rebel
+ os=-linux
+ ;;
+ news | news700 | news800 | news900)
+ basic_machine=m68k-sony
+ os=-newsos
+ ;;
+ news1000)
+ basic_machine=m68030-sony
+ os=-newsos
+ ;;
+ news-3600 | risc-news)
+ basic_machine=mips-sony
+ os=-newsos
+ ;;
+ necv70)
+ basic_machine=v70-nec
+ os=-sysv
+ ;;
+ next | m*-next )
+ basic_machine=m68k-next
+ case $os in
+ -nextstep* )
+ ;;
+ -ns2*)
+ os=-nextstep2
+ ;;
+ *)
+ os=-nextstep3
+ ;;
+ esac
+ ;;
+ nh3000)
+ basic_machine=m68k-harris
+ os=-cxux
+ ;;
+ nh[45]000)
+ basic_machine=m88k-harris
+ os=-cxux
+ ;;
+ nindy960)
+ basic_machine=i960-intel
+ os=-nindy
+ ;;
+ mon960)
+ basic_machine=i960-intel
+ os=-mon960
+ ;;
+ nonstopux)
+ basic_machine=mips-compaq
+ os=-nonstopux
+ ;;
+ np1)
+ basic_machine=np1-gould
+ ;;
+ neo-tandem)
+ basic_machine=neo-tandem
+ ;;
+ nse-tandem)
+ basic_machine=nse-tandem
+ ;;
+ nsr-tandem)
+ basic_machine=nsr-tandem
+ ;;
+ op50n-* | op60c-*)
+ basic_machine=hppa1.1-oki
+ os=-proelf
+ ;;
+ openrisc | openrisc-*)
+ basic_machine=or32-unknown
+ ;;
+ os400)
+ basic_machine=powerpc-ibm
+ os=-os400
+ ;;
+ OSE68000 | ose68000)
+ basic_machine=m68000-ericsson
+ os=-ose
+ ;;
+ os68k)
+ basic_machine=m68k-none
+ os=-os68k
+ ;;
+ pa-hitachi)
+ basic_machine=hppa1.1-hitachi
+ os=-hiuxwe2
+ ;;
+ paragon)
+ basic_machine=i860-intel
+ os=-osf
+ ;;
+ parisc)
+ basic_machine=hppa-unknown
+ os=-linux
+ ;;
+ parisc-*)
+ basic_machine=hppa-`echo $basic_machine | sed 's/^[^-]*-//'`
+ os=-linux
+ ;;
+ pbd)
+ basic_machine=sparc-tti
+ ;;
+ pbb)
+ basic_machine=m68k-tti
+ ;;
+ pc532 | pc532-*)
+ basic_machine=ns32k-pc532
+ ;;
+ pc98)
+ basic_machine=i386-pc
+ ;;
+ pc98-*)
+ basic_machine=i386-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ pentium | p5 | k5 | k6 | nexgen | viac3)
+ basic_machine=i586-pc
+ ;;
+ pentiumpro | p6 | 6x86 | athlon | athlon_*)
+ basic_machine=i686-pc
+ ;;
+ pentiumii | pentium2 | pentiumiii | pentium3)
+ basic_machine=i686-pc
+ ;;
+ pentium4)
+ basic_machine=i786-pc
+ ;;
+ pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)
+ basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ pentiumpro-* | p6-* | 6x86-* | athlon-*)
+ basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)
+ basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ pentium4-*)
+ basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ pn)
+ basic_machine=pn-gould
+ ;;
+ power) basic_machine=power-ibm
+ ;;
+ ppc | ppcbe) basic_machine=powerpc-unknown
+ ;;
+ ppc-* | ppcbe-*)
+ basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ ppcle | powerpclittle | ppc-le | powerpc-little)
+ basic_machine=powerpcle-unknown
+ ;;
+ ppcle-* | powerpclittle-*)
+ basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ ppc64) basic_machine=powerpc64-unknown
+ ;;
+ ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ ppc64le | powerpc64little | ppc64-le | powerpc64-little)
+ basic_machine=powerpc64le-unknown
+ ;;
+ ppc64le-* | powerpc64little-*)
+ basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ ps2)
+ basic_machine=i386-ibm
+ ;;
+ pw32)
+ basic_machine=i586-unknown
+ os=-pw32
+ ;;
+ rdos | rdos64)
+ basic_machine=x86_64-pc
+ os=-rdos
+ ;;
+ rdos32)
+ basic_machine=i386-pc
+ os=-rdos
+ ;;
+ rom68k)
+ basic_machine=m68k-rom68k
+ os=-coff
+ ;;
+ rm[46]00)
+ basic_machine=mips-siemens
+ ;;
+ rtpc | rtpc-*)
+ basic_machine=romp-ibm
+ ;;
+ s390 | s390-*)
+ basic_machine=s390-ibm
+ ;;
+ s390x | s390x-*)
+ basic_machine=s390x-ibm
+ ;;
+ sa29200)
+ basic_machine=a29k-amd
+ os=-udi
+ ;;
+ sb1)
+ basic_machine=mipsisa64sb1-unknown
+ ;;
+ sb1el)
+ basic_machine=mipsisa64sb1el-unknown
+ ;;
+ sde)
+ basic_machine=mipsisa32-sde
+ os=-elf
+ ;;
+ sei)
+ basic_machine=mips-sei
+ os=-seiux
+ ;;
+ sequent)
+ basic_machine=i386-sequent
+ ;;
+ sh)
+ basic_machine=sh-hitachi
+ os=-hms
+ ;;
+ sh5el)
+ basic_machine=sh5le-unknown
+ ;;
+ sh64)
+ basic_machine=sh64-unknown
+ ;;
+ sparclite-wrs | simso-wrs)
+ basic_machine=sparclite-wrs
+ os=-vxworks
+ ;;
+ sps7)
+ basic_machine=m68k-bull
+ os=-sysv2
+ ;;
+ spur)
+ basic_machine=spur-unknown
+ ;;
+ st2000)
+ basic_machine=m68k-tandem
+ ;;
+ stratus)
+ basic_machine=i860-stratus
+ os=-sysv4
+ ;;
+ strongarm-* | thumb-*)
+ basic_machine=arm-`echo $basic_machine | sed 's/^[^-]*-//'`
+ ;;
+ sun2)
+ basic_machine=m68000-sun
+ ;;
+ sun2os3)
+ basic_machine=m68000-sun
+ os=-sunos3
+ ;;
+ sun2os4)
+ basic_machine=m68000-sun
+ os=-sunos4
+ ;;
+ sun3os3)
+ basic_machine=m68k-sun
+ os=-sunos3
+ ;;
+ sun3os4)
+ basic_machine=m68k-sun
+ os=-sunos4
+ ;;
+ sun4os3)
+ basic_machine=sparc-sun
+ os=-sunos3
+ ;;
+ sun4os4)
+ basic_machine=sparc-sun
+ os=-sunos4
+ ;;
+ sun4sol2)
+ basic_machine=sparc-sun
+ os=-solaris2
+ ;;
+ sun3 | sun3-*)
+ basic_machine=m68k-sun
+ ;;
+ sun4)
+ basic_machine=sparc-sun
+ ;;
+ sun386 | sun386i | roadrunner)
+ basic_machine=i386-sun
+ ;;
+ sv1)
+ basic_machine=sv1-cray
+ os=-unicos
+ ;;
+ symmetry)
+ basic_machine=i386-sequent
+ os=-dynix
+ ;;
+ t3e)
+ basic_machine=alphaev5-cray
+ os=-unicos
+ ;;
+ t90)
+ basic_machine=t90-cray
+ os=-unicos
+ ;;
+ tile*)
+ basic_machine=$basic_machine-unknown
+ os=-linux-gnu
+ ;;
+ tx39)
+ basic_machine=mipstx39-unknown
+ ;;
+ tx39el)
+ basic_machine=mipstx39el-unknown
+ ;;
+ toad1)
+ basic_machine=pdp10-xkl
+ os=-tops20
+ ;;
+ tower | tower-32)
+ basic_machine=m68k-ncr
+ ;;
+ tpf)
+ basic_machine=s390x-ibm
+ os=-tpf
+ ;;
+ udi29k)
+ basic_machine=a29k-amd
+ os=-udi
+ ;;
+ ultra3)
+ basic_machine=a29k-nyu
+ os=-sym1
+ ;;
+ v810 | necv810)
+ basic_machine=v810-nec
+ os=-none
+ ;;
+ vaxv)
+ basic_machine=vax-dec
+ os=-sysv
+ ;;
+ vms)
+ basic_machine=vax-dec
+ os=-vms
+ ;;
+ vpp*|vx|vx-*)
+ basic_machine=f301-fujitsu
+ ;;
+ vxworks960)
+ basic_machine=i960-wrs
+ os=-vxworks
+ ;;
+ vxworks68)
+ basic_machine=m68k-wrs
+ os=-vxworks
+ ;;
+ vxworks29k)
+ basic_machine=a29k-wrs
+ os=-vxworks
+ ;;
+ w65*)
+ basic_machine=w65-wdc
+ os=-none
+ ;;
+ w89k-*)
+ basic_machine=hppa1.1-winbond
+ os=-proelf
+ ;;
+ xbox)
+ basic_machine=i686-pc
+ os=-mingw32
+ ;;
+ xps | xps100)
+ basic_machine=xps100-honeywell
+ ;;
+ xscale-* | xscalee[bl]-*)
+ basic_machine=`echo $basic_machine | sed 's/^xscale/arm/'`
+ ;;
+ ymp)
+ basic_machine=ymp-cray
+ os=-unicos
+ ;;
+ z8k-*-coff)
+ basic_machine=z8k-unknown
+ os=-sim
+ ;;
+ z80-*-coff)
+ basic_machine=z80-unknown
+ os=-sim
+ ;;
+ none)
+ basic_machine=none-none
+ os=-none
+ ;;
+
+# Here we handle the default manufacturer of certain CPU types. It is in
+# some cases the only manufacturer, in others, it is the most popular.
+ w89k)
+ basic_machine=hppa1.1-winbond
+ ;;
+ op50n)
+ basic_machine=hppa1.1-oki
+ ;;
+ op60c)
+ basic_machine=hppa1.1-oki
+ ;;
+ romp)
+ basic_machine=romp-ibm
+ ;;
+ mmix)
+ basic_machine=mmix-knuth
+ ;;
+ rs6000)
+ basic_machine=rs6000-ibm
+ ;;
+ vax)
+ basic_machine=vax-dec
+ ;;
+ pdp10)
+ # there are many clones, so DEC is not a safe bet
+ basic_machine=pdp10-unknown
+ ;;
+ pdp11)
+ basic_machine=pdp11-dec
+ ;;
+ we32k)
+ basic_machine=we32k-att
+ ;;
+ sh[1234] | sh[24]a | sh[24]aeb | sh[34]eb | sh[1234]le | sh[23]ele)
+ basic_machine=sh-unknown
+ ;;
+ sparc | sparcv8 | sparcv9 | sparcv9b | sparcv9v)
+ basic_machine=sparc-sun
+ ;;
+ cydra)
+ basic_machine=cydra-cydrome
+ ;;
+ orion)
+ basic_machine=orion-highlevel
+ ;;
+ orion105)
+ basic_machine=clipper-highlevel
+ ;;
+ mac | mpw | mac-mpw)
+ basic_machine=m68k-apple
+ ;;
+ pmac | pmac-mpw)
+ basic_machine=powerpc-apple
+ ;;
+ *-unknown)
+ # Make sure to match an already-canonicalized machine name.
+ ;;
+ *)
+ echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+ exit 1
+ ;;
+esac
+
+# Here we canonicalize certain aliases for manufacturers.
+case $basic_machine in
+ *-digital*)
+ basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'`
+ ;;
+ *-commodore*)
+ basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'`
+ ;;
+ *)
+ ;;
+esac
+
+# Decode manufacturer-specific aliases for certain operating systems.
+
+if [ x"$os" != x"" ]
+then
+case $os in
+ # First match some system type aliases
+ # that might get confused with valid system types.
+ # -solaris* is a basic system type, with this one exception.
+ -auroraux)
+ os=-auroraux
+ ;;
+ -solaris1 | -solaris1.*)
+ os=`echo $os | sed -e 's|solaris1|sunos4|'`
+ ;;
+ -solaris)
+ os=-solaris2
+ ;;
+ -svr4*)
+ os=-sysv4
+ ;;
+ -unixware*)
+ os=-sysv4.2uw
+ ;;
+ -gnu/linux*)
+ os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'`
+ ;;
+ # First accept the basic system types.
+ # The portable systems comes first.
+ # Each alternative MUST END IN A *, to match a version number.
+ # -sysv* is not here because it comes later, after sysvr4.
+ -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \
+ | -*vms* | -sco* | -esix* | -isc* | -aix* | -cnk* | -sunos | -sunos[34]*\
+ | -hpux* | -unos* | -osf* | -luna* | -dgux* | -auroraux* | -solaris* \
+ | -sym* | -kopensolaris* | -plan9* \
+ | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \
+ | -aos* | -aros* | -cloudabi* | -sortix* \
+ | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \
+ | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \
+ | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \
+ | -bitrig* | -openbsd* | -solidbsd* \
+ | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \
+ | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \
+ | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \
+ | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \
+ | -chorusos* | -chorusrdb* | -cegcc* \
+ | -cygwin* | -msys* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
+ | -mingw32* | -mingw64* | -linux-gnu* | -linux-android* \
+ | -linux-newlib* | -linux-musl* | -linux-uclibc* \
+ | -uxpv* | -beos* | -mpeix* | -udk* | -moxiebox* \
+ | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
+ | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
+ | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \
+ | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
+ | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
+ | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \
+ | -skyos* | -haiku* | -rdos* | -toppers* | -drops* | -es* | -tirtos*)
+ # Remember, each alternative MUST END IN *, to match a version number.
+ ;;
+ -qnx*)
+ case $basic_machine in
+ x86-* | i*86-*)
+ ;;
+ *)
+ os=-nto$os
+ ;;
+ esac
+ ;;
+ -nto-qnx*)
+ ;;
+ -nto*)
+ os=`echo $os | sed -e 's|nto|nto-qnx|'`
+ ;;
+ -sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \
+ | -windows* | -osx | -abug | -netware* | -os9* | -beos* | -haiku* \
+ | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*)
+ ;;
+ -mac*)
+ os=`echo $os | sed -e 's|mac|macos|'`
+ ;;
+ -linux-dietlibc)
+ os=-linux-dietlibc
+ ;;
+ -linux*)
+ os=`echo $os | sed -e 's|linux|linux-gnu|'`
+ ;;
+ -sunos5*)
+ os=`echo $os | sed -e 's|sunos5|solaris2|'`
+ ;;
+ -sunos6*)
+ os=`echo $os | sed -e 's|sunos6|solaris3|'`
+ ;;
+ -opened*)
+ os=-openedition
+ ;;
+ -os400*)
+ os=-os400
+ ;;
+ -wince*)
+ os=-wince
+ ;;
+ -osfrose*)
+ os=-osfrose
+ ;;
+ -osf*)
+ os=-osf
+ ;;
+ -utek*)
+ os=-bsd
+ ;;
+ -dynix*)
+ os=-bsd
+ ;;
+ -acis*)
+ os=-aos
+ ;;
+ -atheos*)
+ os=-atheos
+ ;;
+ -syllable*)
+ os=-syllable
+ ;;
+ -386bsd)
+ os=-bsd
+ ;;
+ -ctix* | -uts*)
+ os=-sysv
+ ;;
+ -nova*)
+ os=-rtmk-nova
+ ;;
+ -ns2 )
+ os=-nextstep2
+ ;;
+ -nsk*)
+ os=-nsk
+ ;;
+ # Preserve the version number of sinix5.
+ -sinix5.*)
+ os=`echo $os | sed -e 's|sinix|sysv|'`
+ ;;
+ -sinix*)
+ os=-sysv4
+ ;;
+ -tpf*)
+ os=-tpf
+ ;;
+ -triton*)
+ os=-sysv3
+ ;;
+ -oss*)
+ os=-sysv3
+ ;;
+ -svr4)
+ os=-sysv4
+ ;;
+ -svr3)
+ os=-sysv3
+ ;;
+ -sysvr4)
+ os=-sysv4
+ ;;
+ # This must come after -sysvr4.
+ -sysv*)
+ ;;
+ -ose*)
+ os=-ose
+ ;;
+ -es1800*)
+ os=-ose
+ ;;
+ -xenix)
+ os=-xenix
+ ;;
+ -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
+ os=-mint
+ ;;
+ -aros*)
+ os=-aros
+ ;;
+ -zvmoe)
+ os=-zvmoe
+ ;;
+ -dicos*)
+ os=-dicos
+ ;;
+ -nacl*)
+ ;;
+ -none)
+ ;;
+ *)
+ # Get rid of the `-' at the beginning of $os.
+ os=`echo $os | sed 's/[^-]*-//'`
+ echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2
+ exit 1
+ ;;
+esac
+else
+
+# Here we handle the default operating systems that come with various machines.
+# The value should be what the vendor currently ships out the door with their
+# machine or put another way, the most popular os provided with the machine.
+
+# Note that if you're going to try to match "-MANUFACTURER" here (say,
+# "-sun"), then you have to tell the case statement up towards the top
+# that MANUFACTURER isn't an operating system. Otherwise, code above
+# will signal an error saying that MANUFACTURER isn't an operating
+# system, and we'll never get to this point.
+
+case $basic_machine in
+ score-*)
+ os=-elf
+ ;;
+ spu-*)
+ os=-elf
+ ;;
+ *-acorn)
+ os=-riscix1.2
+ ;;
+ arm*-rebel)
+ os=-linux
+ ;;
+ arm*-semi)
+ os=-aout
+ ;;
+ c4x-* | tic4x-*)
+ os=-coff
+ ;;
+ c8051-*)
+ os=-elf
+ ;;
+ hexagon-*)
+ os=-elf
+ ;;
+ tic54x-*)
+ os=-coff
+ ;;
+ tic55x-*)
+ os=-coff
+ ;;
+ tic6x-*)
+ os=-coff
+ ;;
+ # This must come before the *-dec entry.
+ pdp10-*)
+ os=-tops20
+ ;;
+ pdp11-*)
+ os=-none
+ ;;
+ *-dec | vax-*)
+ os=-ultrix4.2
+ ;;
+ m68*-apollo)
+ os=-domain
+ ;;
+ i386-sun)
+ os=-sunos4.0.2
+ ;;
+ m68000-sun)
+ os=-sunos3
+ ;;
+ m68*-cisco)
+ os=-aout
+ ;;
+ mep-*)
+ os=-elf
+ ;;
+ mips*-cisco)
+ os=-elf
+ ;;
+ mips*-*)
+ os=-elf
+ ;;
+ or32-*)
+ os=-coff
+ ;;
+ *-tti) # must be before sparc entry or we get the wrong os.
+ os=-sysv3
+ ;;
+ sparc-* | *-sun)
+ os=-sunos4.1.1
+ ;;
+ *-be)
+ os=-beos
+ ;;
+ *-haiku)
+ os=-haiku
+ ;;
+ *-ibm)
+ os=-aix
+ ;;
+ *-knuth)
+ os=-mmixware
+ ;;
+ *-wec)
+ os=-proelf
+ ;;
+ *-winbond)
+ os=-proelf
+ ;;
+ *-oki)
+ os=-proelf
+ ;;
+ *-hp)
+ os=-hpux
+ ;;
+ *-hitachi)
+ os=-hiux
+ ;;
+ i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent)
+ os=-sysv
+ ;;
+ *-cbm)
+ os=-amigaos
+ ;;
+ *-dg)
+ os=-dgux
+ ;;
+ *-dolphin)
+ os=-sysv3
+ ;;
+ m68k-ccur)
+ os=-rtu
+ ;;
+ m88k-omron*)
+ os=-luna
+ ;;
+ *-next )
+ os=-nextstep
+ ;;
+ *-sequent)
+ os=-ptx
+ ;;
+ *-crds)
+ os=-unos
+ ;;
+ *-ns)
+ os=-genix
+ ;;
+ i370-*)
+ os=-mvs
+ ;;
+ *-next)
+ os=-nextstep3
+ ;;
+ *-gould)
+ os=-sysv
+ ;;
+ *-highlevel)
+ os=-bsd
+ ;;
+ *-encore)
+ os=-bsd
+ ;;
+ *-sgi)
+ os=-irix
+ ;;
+ *-siemens)
+ os=-sysv4
+ ;;
+ *-masscomp)
+ os=-rtu
+ ;;
+ f30[01]-fujitsu | f700-fujitsu)
+ os=-uxpv
+ ;;
+ *-rom68k)
+ os=-coff
+ ;;
+ *-*bug)
+ os=-coff
+ ;;
+ *-apple)
+ os=-macos
+ ;;
+ *-atari*)
+ os=-mint
+ ;;
+ *)
+ os=-none
+ ;;
+esac
+fi
+
+# Here we handle the case where we know the os, and the CPU type, but not the
+# manufacturer. We pick the logical manufacturer.
+vendor=unknown
+case $basic_machine in
+ *-unknown)
+ case $os in
+ -riscix*)
+ vendor=acorn
+ ;;
+ -sunos*)
+ vendor=sun
+ ;;
+ -cnk*|-aix*)
+ vendor=ibm
+ ;;
+ -beos*)
+ vendor=be
+ ;;
+ -hpux*)
+ vendor=hp
+ ;;
+ -mpeix*)
+ vendor=hp
+ ;;
+ -hiux*)
+ vendor=hitachi
+ ;;
+ -unos*)
+ vendor=crds
+ ;;
+ -dgux*)
+ vendor=dg
+ ;;
+ -luna*)
+ vendor=omron
+ ;;
+ -genix*)
+ vendor=ns
+ ;;
+ -mvs* | -opened*)
+ vendor=ibm
+ ;;
+ -os400*)
+ vendor=ibm
+ ;;
+ -ptx*)
+ vendor=sequent
+ ;;
+ -tpf*)
+ vendor=ibm
+ ;;
+ -vxsim* | -vxworks* | -windiss*)
+ vendor=wrs
+ ;;
+ -aux*)
+ vendor=apple
+ ;;
+ -hms*)
+ vendor=hitachi
+ ;;
+ -mpw* | -macos*)
+ vendor=apple
+ ;;
+ -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
+ vendor=atari
+ ;;
+ -vos*)
+ vendor=stratus
+ ;;
+ esac
+ basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"`
+ ;;
+esac
+
+echo $basic_machine$os
+exit
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "timestamp='"
+# time-stamp-format: "%:y-%02m-%02d"
+# time-stamp-end: "'"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure
new file mode 100755
index 000000000..9bf715929
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure
@@ -0,0 +1,5491 @@
+#! /bin/sh
+# Guess values for system-dependent variables and create Makefiles.
+# Generated by GNU Autoconf 2.69 for freedom-metal v0.1.2.
+#
+# Report bugs to <https://github.com/sifive/freedom-metal/issues>.
+#
+#
+# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc.
+#
+#
+# This configure script is free software; the Free Software Foundation
+# gives unlimited permission to copy, distribute and modify it.
+## -------------------- ##
+## M4sh Initialization. ##
+## -------------------- ##
+
+# Be more Bourne compatible
+DUALCASE=1; export DUALCASE # for MKS sh
+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :
+ emulate sh
+ NULLCMD=:
+ # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which
+ # is contrary to our usage. Disable this feature.
+ alias -g '${1+"$@"}'='"$@"'
+ setopt NO_GLOB_SUBST
+else
+ case `(set -o) 2>/dev/null` in #(
+ *posix*) :
+ set -o posix ;; #(
+ *) :
+ ;;
+esac
+fi
+
+
+as_nl='
+'
+export as_nl
+# Printing a long string crashes Solaris 7 /usr/bin/printf.
+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo
+# Prefer a ksh shell builtin over an external printf program on Solaris,
+# but without wasting forks for bash or zsh.
+if test -z "$BASH_VERSION$ZSH_VERSION" \
+ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then
+ as_echo='print -r --'
+ as_echo_n='print -rn --'
+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then
+ as_echo='printf %s\n'
+ as_echo_n='printf %s'
+else
+ if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then
+ as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'
+ as_echo_n='/usr/ucb/echo -n'
+ else
+ as_echo_body='eval expr "X$1" : "X\\(.*\\)"'
+ as_echo_n_body='eval
+ arg=$1;
+ case $arg in #(
+ *"$as_nl"*)
+ expr "X$arg" : "X\\(.*\\)$as_nl";
+ arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;
+ esac;
+ expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"
+ '
+ export as_echo_n_body
+ as_echo_n='sh -c $as_echo_n_body as_echo'
+ fi
+ export as_echo_body
+ as_echo='sh -c $as_echo_body as_echo'
+fi
+
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+ PATH_SEPARATOR=:
+ (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {
+ (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||
+ PATH_SEPARATOR=';'
+ }
+fi
+
+
+# IFS
+# We need space, tab and new line, in precisely that order. Quoting is
+# there to prevent editors from complaining about space-tab.
+# (If _AS_PATH_WALK were called with IFS unset, it would disable word
+# splitting by setting IFS to empty value.)
+IFS=" "" $as_nl"
+
+# Find who we are. Look in the path if we contain no directory separator.
+as_myself=
+case $0 in #((
+ *[\\/]* ) as_myself=$0 ;;
+ *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break
+ done
+IFS=$as_save_IFS
+
+ ;;
+esac
+# We did not find ourselves, most probably we were run as `sh COMMAND'
+# in which case we are not to be found in the path.
+if test "x$as_myself" = x; then
+ as_myself=$0
+fi
+if test ! -f "$as_myself"; then
+ $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2
+ exit 1
+fi
+
+# Unset variables that we do not need and which cause bugs (e.g. in
+# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1"
+# suppresses any "Segmentation fault" message there. '((' could
+# trigger a bug in pdksh 5.2.14.
+for as_var in BASH_ENV ENV MAIL MAILPATH
+do eval test x\${$as_var+set} = xset \
+ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :
+done
+PS1='$ '
+PS2='> '
+PS4='+ '
+
+# NLS nuisances.
+LC_ALL=C
+export LC_ALL
+LANGUAGE=C
+export LANGUAGE
+
+# CDPATH.
+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH
+
+# Use a proper internal environment variable to ensure we don't fall
+ # into an infinite loop, continuously re-executing ourselves.
+ if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then
+ _as_can_reexec=no; export _as_can_reexec;
+ # We cannot yet assume a decent shell, so we have to provide a
+# neutralization value for shells without unset; and this also
+# works around shells that cannot unset nonexistent variables.
+# Preserve -v and -x to the replacement shell.
+BASH_ENV=/dev/null
+ENV=/dev/null
+(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV
+case $- in # ((((
+ *v*x* | *x*v* ) as_opts=-vx ;;
+ *v* ) as_opts=-v ;;
+ *x* ) as_opts=-x ;;
+ * ) as_opts= ;;
+esac
+exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"}
+# Admittedly, this is quite paranoid, since all the known shells bail
+# out after a failed `exec'.
+$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2
+as_fn_exit 255
+ fi
+ # We don't want this to propagate to other subprocesses.
+ { _as_can_reexec=; unset _as_can_reexec;}
+if test "x$CONFIG_SHELL" = x; then
+ as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then :
+ emulate sh
+ NULLCMD=:
+ # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which
+ # is contrary to our usage. Disable this feature.
+ alias -g '\${1+\"\$@\"}'='\"\$@\"'
+ setopt NO_GLOB_SUBST
+else
+ case \`(set -o) 2>/dev/null\` in #(
+ *posix*) :
+ set -o posix ;; #(
+ *) :
+ ;;
+esac
+fi
+"
+ as_required="as_fn_return () { (exit \$1); }
+as_fn_success () { as_fn_return 0; }
+as_fn_failure () { as_fn_return 1; }
+as_fn_ret_success () { return 0; }
+as_fn_ret_failure () { return 1; }
+
+exitcode=0
+as_fn_success || { exitcode=1; echo as_fn_success failed.; }
+as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; }
+as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; }
+as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; }
+if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then :
+
+else
+ exitcode=1; echo positional parameters were not saved.
+fi
+test x\$exitcode = x0 || exit 1
+test -x / || exit 1"
+ as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO
+ as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO
+ eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" &&
+ test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1"
+ if (eval "$as_required") 2>/dev/null; then :
+ as_have_required=yes
+else
+ as_have_required=no
+fi
+ if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then :
+
+else
+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+as_found=false
+for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ as_found=:
+ case $as_dir in #(
+ /*)
+ for as_base in sh bash ksh sh5; do
+ # Try only shells that exist, to save several forks.
+ as_shell=$as_dir/$as_base
+ if { test -f "$as_shell" || test -f "$as_shell.exe"; } &&
+ { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then :
+ CONFIG_SHELL=$as_shell as_have_required=yes
+ if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then :
+ break 2
+fi
+fi
+ done;;
+ esac
+ as_found=false
+done
+$as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } &&
+ { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then :
+ CONFIG_SHELL=$SHELL as_have_required=yes
+fi; }
+IFS=$as_save_IFS
+
+
+ if test "x$CONFIG_SHELL" != x; then :
+ export CONFIG_SHELL
+ # We cannot yet assume a decent shell, so we have to provide a
+# neutralization value for shells without unset; and this also
+# works around shells that cannot unset nonexistent variables.
+# Preserve -v and -x to the replacement shell.
+BASH_ENV=/dev/null
+ENV=/dev/null
+(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV
+case $- in # ((((
+ *v*x* | *x*v* ) as_opts=-vx ;;
+ *v* ) as_opts=-v ;;
+ *x* ) as_opts=-x ;;
+ * ) as_opts= ;;
+esac
+exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"}
+# Admittedly, this is quite paranoid, since all the known shells bail
+# out after a failed `exec'.
+$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2
+exit 255
+fi
+
+ if test x$as_have_required = xno; then :
+ $as_echo "$0: This script requires a shell more modern than all"
+ $as_echo "$0: the shells that I found on your system."
+ if test x${ZSH_VERSION+set} = xset ; then
+ $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should"
+ $as_echo "$0: be upgraded to zsh 4.3.4 or later."
+ else
+ $as_echo "$0: Please tell bug-autoconf@gnu.org and
+$0: https://github.com/sifive/freedom-metal/issues about
+$0: your system, including any error possibly output before
+$0: this message. Then install a modern shell, or manually
+$0: run the script under such a shell if you do have one."
+ fi
+ exit 1
+fi
+fi
+fi
+SHELL=${CONFIG_SHELL-/bin/sh}
+export SHELL
+# Unset more variables known to interfere with behavior of common tools.
+CLICOLOR_FORCE= GREP_OPTIONS=
+unset CLICOLOR_FORCE GREP_OPTIONS
+
+## --------------------- ##
+## M4sh Shell Functions. ##
+## --------------------- ##
+# as_fn_unset VAR
+# ---------------
+# Portably unset VAR.
+as_fn_unset ()
+{
+ { eval $1=; unset $1;}
+}
+as_unset=as_fn_unset
+
+# as_fn_set_status STATUS
+# -----------------------
+# Set $? to STATUS, without forking.
+as_fn_set_status ()
+{
+ return $1
+} # as_fn_set_status
+
+# as_fn_exit STATUS
+# -----------------
+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.
+as_fn_exit ()
+{
+ set +e
+ as_fn_set_status $1
+ exit $1
+} # as_fn_exit
+
+# as_fn_mkdir_p
+# -------------
+# Create "$as_dir" as a directory, including parents if necessary.
+as_fn_mkdir_p ()
+{
+
+ case $as_dir in #(
+ -*) as_dir=./$as_dir;;
+ esac
+ test -d "$as_dir" || eval $as_mkdir_p || {
+ as_dirs=
+ while :; do
+ case $as_dir in #(
+ *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(
+ *) as_qdir=$as_dir;;
+ esac
+ as_dirs="'$as_qdir' $as_dirs"
+ as_dir=`$as_dirname -- "$as_dir" ||
+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$as_dir" : 'X\(//\)[^/]' \| \
+ X"$as_dir" : 'X\(//\)$' \| \
+ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_dir" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ test -d "$as_dir" && break
+ done
+ test -z "$as_dirs" || eval "mkdir $as_dirs"
+ } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"
+
+
+} # as_fn_mkdir_p
+
+# as_fn_executable_p FILE
+# -----------------------
+# Test if FILE is an executable regular file.
+as_fn_executable_p ()
+{
+ test -f "$1" && test -x "$1"
+} # as_fn_executable_p
+# as_fn_append VAR VALUE
+# ----------------------
+# Append the text in VALUE to the end of the definition contained in VAR. Take
+# advantage of any shell optimizations that allow amortized linear growth over
+# repeated appends, instead of the typical quadratic growth present in naive
+# implementations.
+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :
+ eval 'as_fn_append ()
+ {
+ eval $1+=\$2
+ }'
+else
+ as_fn_append ()
+ {
+ eval $1=\$$1\$2
+ }
+fi # as_fn_append
+
+# as_fn_arith ARG...
+# ------------------
+# Perform arithmetic evaluation on the ARGs, and store the result in the
+# global $as_val. Take advantage of shells that can avoid forks. The arguments
+# must be portable across $(()) and expr.
+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :
+ eval 'as_fn_arith ()
+ {
+ as_val=$(( $* ))
+ }'
+else
+ as_fn_arith ()
+ {
+ as_val=`expr "$@" || test $? -eq 1`
+ }
+fi # as_fn_arith
+
+
+# as_fn_error STATUS ERROR [LINENO LOG_FD]
+# ----------------------------------------
+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are
+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the
+# script with STATUS, using 1 if that was 0.
+as_fn_error ()
+{
+ as_status=$1; test $as_status -eq 0 && as_status=1
+ if test "$4"; then
+ as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+ $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4
+ fi
+ $as_echo "$as_me: error: $2" >&2
+ as_fn_exit $as_status
+} # as_fn_error
+
+if expr a : '\(a\)' >/dev/null 2>&1 &&
+ test "X`expr 00001 : '.*\(...\)'`" = X001; then
+ as_expr=expr
+else
+ as_expr=false
+fi
+
+if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then
+ as_basename=basename
+else
+ as_basename=false
+fi
+
+if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then
+ as_dirname=dirname
+else
+ as_dirname=false
+fi
+
+as_me=`$as_basename -- "$0" ||
+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \
+ X"$0" : 'X\(//\)$' \| \
+ X"$0" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X/"$0" |
+ sed '/^.*\/\([^/][^/]*\)\/*$/{
+ s//\1/
+ q
+ }
+ /^X\/\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\/\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+
+# Avoid depending upon Character Ranges.
+as_cr_letters='abcdefghijklmnopqrstuvwxyz'
+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'
+as_cr_Letters=$as_cr_letters$as_cr_LETTERS
+as_cr_digits='0123456789'
+as_cr_alnum=$as_cr_Letters$as_cr_digits
+
+
+ as_lineno_1=$LINENO as_lineno_1a=$LINENO
+ as_lineno_2=$LINENO as_lineno_2a=$LINENO
+ eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" &&
+ test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || {
+ # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-)
+ sed -n '
+ p
+ /[$]LINENO/=
+ ' <$as_myself |
+ sed '
+ s/[$]LINENO.*/&-/
+ t lineno
+ b
+ :lineno
+ N
+ :loop
+ s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/
+ t loop
+ s/-\n.*//
+ ' >$as_me.lineno &&
+ chmod +x "$as_me.lineno" ||
+ { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; }
+
+ # If we had to re-execute with $CONFIG_SHELL, we're ensured to have
+ # already done that, so ensure we don't try to do so again and fall
+ # in an infinite loop. This has already happened in practice.
+ _as_can_reexec=no; export _as_can_reexec
+ # Don't try to exec as it changes $[0], causing all sort of problems
+ # (the dirname of $[0] is not the place where we might find the
+ # original and so on. Autoconf is especially sensitive to this).
+ . "./$as_me.lineno"
+ # Exit status is that of the last command.
+ exit
+}
+
+ECHO_C= ECHO_N= ECHO_T=
+case `echo -n x` in #(((((
+-n*)
+ case `echo 'xy\c'` in
+ *c*) ECHO_T=' ';; # ECHO_T is single tab character.
+ xy) ECHO_C='\c';;
+ *) echo `echo ksh88 bug on AIX 6.1` > /dev/null
+ ECHO_T=' ';;
+ esac;;
+*)
+ ECHO_N='-n';;
+esac
+
+rm -f conf$$ conf$$.exe conf$$.file
+if test -d conf$$.dir; then
+ rm -f conf$$.dir/conf$$.file
+else
+ rm -f conf$$.dir
+ mkdir conf$$.dir 2>/dev/null
+fi
+if (echo >conf$$.file) 2>/dev/null; then
+ if ln -s conf$$.file conf$$ 2>/dev/null; then
+ as_ln_s='ln -s'
+ # ... but there are two gotchas:
+ # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.
+ # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.
+ # In both cases, we have to default to `cp -pR'.
+ ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||
+ as_ln_s='cp -pR'
+ elif ln conf$$.file conf$$ 2>/dev/null; then
+ as_ln_s=ln
+ else
+ as_ln_s='cp -pR'
+ fi
+else
+ as_ln_s='cp -pR'
+fi
+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file
+rmdir conf$$.dir 2>/dev/null
+
+if mkdir -p . 2>/dev/null; then
+ as_mkdir_p='mkdir -p "$as_dir"'
+else
+ test -d ./-p && rmdir ./-p
+ as_mkdir_p=false
+fi
+
+as_test_x='test -x'
+as_executable_p=as_fn_executable_p
+
+# Sed expression to map a string onto a valid CPP name.
+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"
+
+# Sed expression to map a string onto a valid variable name.
+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"
+
+
+test -n "$DJDIR" || exec 7<&0 </dev/null
+exec 6>&1
+
+# Name of the host.
+# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status,
+# so uname gets run too.
+ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q`
+
+#
+# Initializations.
+#
+ac_default_prefix=/usr/local
+ac_clean_files=
+ac_config_libobj_dir=.
+LIBOBJS=
+cross_compiling=no
+subdirs=
+MFLAGS=
+MAKEFLAGS=
+
+# Identity of this package.
+PACKAGE_NAME='freedom-metal'
+PACKAGE_TARNAME='freedom-metal'
+PACKAGE_VERSION='v0.1.2'
+PACKAGE_STRING='freedom-metal v0.1.2'
+PACKAGE_BUGREPORT='https://github.com/sifive/freedom-metal/issues'
+PACKAGE_URL='https://github.com/sifive/freedom-metal'
+
+ac_subst_vars='am__EXEEXT_FALSE
+am__EXEEXT_TRUE
+LTLIBOBJS
+LIBOBJS
+PLATFORM_HEADER
+MACHINE_INLINE
+MACHINE_HEADER
+WITH_BUILTIN_LIBMETAL_SEGGER_FALSE
+WITH_BUILTIN_LIBMETAL_SEGGER_TRUE
+WITH_BUILTIN_LIBMETAL_PICO_FALSE
+WITH_BUILTIN_LIBMETAL_PICO_TRUE
+WITH_BUILTIN_LIBGLOSS_FALSE
+WITH_BUILTIN_LIBGLOSS_TRUE
+am__fastdepCCAS_FALSE
+am__fastdepCCAS_TRUE
+CCASDEPMODE
+CCASFLAGS
+CCAS
+ac_ct_AR
+AR
+RANLIB
+am__fastdepCC_FALSE
+am__fastdepCC_TRUE
+CCDEPMODE
+am__nodep
+AMDEPBACKSLASH
+AMDEP_FALSE
+AMDEP_TRUE
+am__quote
+am__include
+DEPDIR
+OBJEXT
+EXEEXT
+ac_ct_CC
+CPPFLAGS
+LDFLAGS
+CFLAGS
+CC
+host_os
+host_vendor
+host_cpu
+host
+build_os
+build_vendor
+build_cpu
+build
+MAINT
+MAINTAINER_MODE_FALSE
+MAINTAINER_MODE_TRUE
+AM_BACKSLASH
+AM_DEFAULT_VERBOSITY
+AM_DEFAULT_V
+AM_V
+am__untar
+am__tar
+AMTAR
+am__leading_dot
+SET_MAKE
+AWK
+mkdir_p
+MKDIR_P
+INSTALL_STRIP_PROGRAM
+STRIP
+install_sh
+MAKEINFO
+AUTOHEADER
+AUTOMAKE
+AUTOCONF
+ACLOCAL
+VERSION
+PACKAGE
+CYGPATH_W
+am__isrc
+INSTALL_DATA
+INSTALL_SCRIPT
+INSTALL_PROGRAM
+target_alias
+host_alias
+build_alias
+LIBS
+ECHO_T
+ECHO_N
+ECHO_C
+DEFS
+mandir
+localedir
+libdir
+psdir
+pdfdir
+dvidir
+htmldir
+infodir
+docdir
+oldincludedir
+includedir
+runstatedir
+localstatedir
+sharedstatedir
+sysconfdir
+datadir
+datarootdir
+libexecdir
+sbindir
+bindir
+program_transform_name
+prefix
+exec_prefix
+PACKAGE_URL
+PACKAGE_BUGREPORT
+PACKAGE_STRING
+PACKAGE_VERSION
+PACKAGE_TARNAME
+PACKAGE_NAME
+PATH_SEPARATOR
+SHELL'
+ac_subst_files=''
+ac_user_opts='
+enable_option_checking
+enable_silent_rules
+enable_maintainer_mode
+enable_dependency_tracking
+with_builtin_libgloss
+with_builtin_libmetal_pico
+with_builtin_libmetal_segger
+with_machine_header
+with_machine_inline
+with_platform_header
+'
+ ac_precious_vars='build_alias
+host_alias
+target_alias
+CC
+CFLAGS
+LDFLAGS
+LIBS
+CPPFLAGS
+CCAS
+CCASFLAGS'
+
+
+# Initialize some variables set by options.
+ac_init_help=
+ac_init_version=false
+ac_unrecognized_opts=
+ac_unrecognized_sep=
+# The variables have the same names as the options, with
+# dashes changed to underlines.
+cache_file=/dev/null
+exec_prefix=NONE
+no_create=
+no_recursion=
+prefix=NONE
+program_prefix=NONE
+program_suffix=NONE
+program_transform_name=s,x,x,
+silent=
+site=
+srcdir=
+verbose=
+x_includes=NONE
+x_libraries=NONE
+
+# Installation directory options.
+# These are left unexpanded so users can "make install exec_prefix=/foo"
+# and all the variables that are supposed to be based on exec_prefix
+# by default will actually change.
+# Use braces instead of parens because sh, perl, etc. also accept them.
+# (The list follows the same order as the GNU Coding Standards.)
+bindir='${exec_prefix}/bin'
+sbindir='${exec_prefix}/sbin'
+libexecdir='${exec_prefix}/libexec'
+datarootdir='${prefix}/share'
+datadir='${datarootdir}'
+sysconfdir='${prefix}/etc'
+sharedstatedir='${prefix}/com'
+localstatedir='${prefix}/var'
+runstatedir='${localstatedir}/run'
+includedir='${prefix}/include'
+oldincludedir='/usr/include'
+docdir='${datarootdir}/doc/${PACKAGE_TARNAME}'
+infodir='${datarootdir}/info'
+htmldir='${docdir}'
+dvidir='${docdir}'
+pdfdir='${docdir}'
+psdir='${docdir}'
+libdir='${exec_prefix}/lib'
+localedir='${datarootdir}/locale'
+mandir='${datarootdir}/man'
+
+ac_prev=
+ac_dashdash=
+for ac_option
+do
+ # If the previous option needs an argument, assign it.
+ if test -n "$ac_prev"; then
+ eval $ac_prev=\$ac_option
+ ac_prev=
+ continue
+ fi
+
+ case $ac_option in
+ *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;;
+ *=) ac_optarg= ;;
+ *) ac_optarg=yes ;;
+ esac
+
+ # Accept the important Cygnus configure options, so we can diagnose typos.
+
+ case $ac_dashdash$ac_option in
+ --)
+ ac_dashdash=yes ;;
+
+ -bindir | --bindir | --bindi | --bind | --bin | --bi)
+ ac_prev=bindir ;;
+ -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*)
+ bindir=$ac_optarg ;;
+
+ -build | --build | --buil | --bui | --bu)
+ ac_prev=build_alias ;;
+ -build=* | --build=* | --buil=* | --bui=* | --bu=*)
+ build_alias=$ac_optarg ;;
+
+ -cache-file | --cache-file | --cache-fil | --cache-fi \
+ | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c)
+ ac_prev=cache_file ;;
+ -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \
+ | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*)
+ cache_file=$ac_optarg ;;
+
+ --config-cache | -C)
+ cache_file=config.cache ;;
+
+ -datadir | --datadir | --datadi | --datad)
+ ac_prev=datadir ;;
+ -datadir=* | --datadir=* | --datadi=* | --datad=*)
+ datadir=$ac_optarg ;;
+
+ -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \
+ | --dataroo | --dataro | --datar)
+ ac_prev=datarootdir ;;
+ -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \
+ | --dataroot=* | --dataroo=* | --dataro=* | --datar=*)
+ datarootdir=$ac_optarg ;;
+
+ -disable-* | --disable-*)
+ ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'`
+ # Reject names that are not valid shell variable names.
+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+ as_fn_error $? "invalid feature name: $ac_useropt"
+ ac_useropt_orig=$ac_useropt
+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+ case $ac_user_opts in
+ *"
+"enable_$ac_useropt"
+"*) ;;
+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig"
+ ac_unrecognized_sep=', ';;
+ esac
+ eval enable_$ac_useropt=no ;;
+
+ -docdir | --docdir | --docdi | --doc | --do)
+ ac_prev=docdir ;;
+ -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*)
+ docdir=$ac_optarg ;;
+
+ -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv)
+ ac_prev=dvidir ;;
+ -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*)
+ dvidir=$ac_optarg ;;
+
+ -enable-* | --enable-*)
+ ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'`
+ # Reject names that are not valid shell variable names.
+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+ as_fn_error $? "invalid feature name: $ac_useropt"
+ ac_useropt_orig=$ac_useropt
+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+ case $ac_user_opts in
+ *"
+"enable_$ac_useropt"
+"*) ;;
+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig"
+ ac_unrecognized_sep=', ';;
+ esac
+ eval enable_$ac_useropt=\$ac_optarg ;;
+
+ -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \
+ | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \
+ | --exec | --exe | --ex)
+ ac_prev=exec_prefix ;;
+ -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \
+ | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \
+ | --exec=* | --exe=* | --ex=*)
+ exec_prefix=$ac_optarg ;;
+
+ -gas | --gas | --ga | --g)
+ # Obsolete; use --with-gas.
+ with_gas=yes ;;
+
+ -help | --help | --hel | --he | -h)
+ ac_init_help=long ;;
+ -help=r* | --help=r* | --hel=r* | --he=r* | -hr*)
+ ac_init_help=recursive ;;
+ -help=s* | --help=s* | --hel=s* | --he=s* | -hs*)
+ ac_init_help=short ;;
+
+ -host | --host | --hos | --ho)
+ ac_prev=host_alias ;;
+ -host=* | --host=* | --hos=* | --ho=*)
+ host_alias=$ac_optarg ;;
+
+ -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht)
+ ac_prev=htmldir ;;
+ -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \
+ | --ht=*)
+ htmldir=$ac_optarg ;;
+
+ -includedir | --includedir | --includedi | --included | --include \
+ | --includ | --inclu | --incl | --inc)
+ ac_prev=includedir ;;
+ -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \
+ | --includ=* | --inclu=* | --incl=* | --inc=*)
+ includedir=$ac_optarg ;;
+
+ -infodir | --infodir | --infodi | --infod | --info | --inf)
+ ac_prev=infodir ;;
+ -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*)
+ infodir=$ac_optarg ;;
+
+ -libdir | --libdir | --libdi | --libd)
+ ac_prev=libdir ;;
+ -libdir=* | --libdir=* | --libdi=* | --libd=*)
+ libdir=$ac_optarg ;;
+
+ -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \
+ | --libexe | --libex | --libe)
+ ac_prev=libexecdir ;;
+ -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \
+ | --libexe=* | --libex=* | --libe=*)
+ libexecdir=$ac_optarg ;;
+
+ -localedir | --localedir | --localedi | --localed | --locale)
+ ac_prev=localedir ;;
+ -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*)
+ localedir=$ac_optarg ;;
+
+ -localstatedir | --localstatedir | --localstatedi | --localstated \
+ | --localstate | --localstat | --localsta | --localst | --locals)
+ ac_prev=localstatedir ;;
+ -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \
+ | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*)
+ localstatedir=$ac_optarg ;;
+
+ -mandir | --mandir | --mandi | --mand | --man | --ma | --m)
+ ac_prev=mandir ;;
+ -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*)
+ mandir=$ac_optarg ;;
+
+ -nfp | --nfp | --nf)
+ # Obsolete; use --without-fp.
+ with_fp=no ;;
+
+ -no-create | --no-create | --no-creat | --no-crea | --no-cre \
+ | --no-cr | --no-c | -n)
+ no_create=yes ;;
+
+ -no-recursion | --no-recursion | --no-recursio | --no-recursi \
+ | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r)
+ no_recursion=yes ;;
+
+ -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \
+ | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \
+ | --oldin | --oldi | --old | --ol | --o)
+ ac_prev=oldincludedir ;;
+ -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \
+ | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \
+ | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*)
+ oldincludedir=$ac_optarg ;;
+
+ -prefix | --prefix | --prefi | --pref | --pre | --pr | --p)
+ ac_prev=prefix ;;
+ -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*)
+ prefix=$ac_optarg ;;
+
+ -program-prefix | --program-prefix | --program-prefi | --program-pref \
+ | --program-pre | --program-pr | --program-p)
+ ac_prev=program_prefix ;;
+ -program-prefix=* | --program-prefix=* | --program-prefi=* \
+ | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*)
+ program_prefix=$ac_optarg ;;
+
+ -program-suffix | --program-suffix | --program-suffi | --program-suff \
+ | --program-suf | --program-su | --program-s)
+ ac_prev=program_suffix ;;
+ -program-suffix=* | --program-suffix=* | --program-suffi=* \
+ | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*)
+ program_suffix=$ac_optarg ;;
+
+ -program-transform-name | --program-transform-name \
+ | --program-transform-nam | --program-transform-na \
+ | --program-transform-n | --program-transform- \
+ | --program-transform | --program-transfor \
+ | --program-transfo | --program-transf \
+ | --program-trans | --program-tran \
+ | --progr-tra | --program-tr | --program-t)
+ ac_prev=program_transform_name ;;
+ -program-transform-name=* | --program-transform-name=* \
+ | --program-transform-nam=* | --program-transform-na=* \
+ | --program-transform-n=* | --program-transform-=* \
+ | --program-transform=* | --program-transfor=* \
+ | --program-transfo=* | --program-transf=* \
+ | --program-trans=* | --program-tran=* \
+ | --progr-tra=* | --program-tr=* | --program-t=*)
+ program_transform_name=$ac_optarg ;;
+
+ -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd)
+ ac_prev=pdfdir ;;
+ -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*)
+ pdfdir=$ac_optarg ;;
+
+ -psdir | --psdir | --psdi | --psd | --ps)
+ ac_prev=psdir ;;
+ -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*)
+ psdir=$ac_optarg ;;
+
+ -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+ | -silent | --silent | --silen | --sile | --sil)
+ silent=yes ;;
+
+ -runstatedir | --runstatedir | --runstatedi | --runstated \
+ | --runstate | --runstat | --runsta | --runst | --runs \
+ | --run | --ru | --r)
+ ac_prev=runstatedir ;;
+ -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \
+ | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \
+ | --run=* | --ru=* | --r=*)
+ runstatedir=$ac_optarg ;;
+
+ -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)
+ ac_prev=sbindir ;;
+ -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \
+ | --sbi=* | --sb=*)
+ sbindir=$ac_optarg ;;
+
+ -sharedstatedir | --sharedstatedir | --sharedstatedi \
+ | --sharedstated | --sharedstate | --sharedstat | --sharedsta \
+ | --sharedst | --shareds | --shared | --share | --shar \
+ | --sha | --sh)
+ ac_prev=sharedstatedir ;;
+ -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \
+ | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \
+ | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \
+ | --sha=* | --sh=*)
+ sharedstatedir=$ac_optarg ;;
+
+ -site | --site | --sit)
+ ac_prev=site ;;
+ -site=* | --site=* | --sit=*)
+ site=$ac_optarg ;;
+
+ -srcdir | --srcdir | --srcdi | --srcd | --src | --sr)
+ ac_prev=srcdir ;;
+ -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*)
+ srcdir=$ac_optarg ;;
+
+ -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \
+ | --syscon | --sysco | --sysc | --sys | --sy)
+ ac_prev=sysconfdir ;;
+ -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \
+ | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*)
+ sysconfdir=$ac_optarg ;;
+
+ -target | --target | --targe | --targ | --tar | --ta | --t)
+ ac_prev=target_alias ;;
+ -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*)
+ target_alias=$ac_optarg ;;
+
+ -v | -verbose | --verbose | --verbos | --verbo | --verb)
+ verbose=yes ;;
+
+ -version | --version | --versio | --versi | --vers | -V)
+ ac_init_version=: ;;
+
+ -with-* | --with-*)
+ ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'`
+ # Reject names that are not valid shell variable names.
+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+ as_fn_error $? "invalid package name: $ac_useropt"
+ ac_useropt_orig=$ac_useropt
+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+ case $ac_user_opts in
+ *"
+"with_$ac_useropt"
+"*) ;;
+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig"
+ ac_unrecognized_sep=', ';;
+ esac
+ eval with_$ac_useropt=\$ac_optarg ;;
+
+ -without-* | --without-*)
+ ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'`
+ # Reject names that are not valid shell variable names.
+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&
+ as_fn_error $? "invalid package name: $ac_useropt"
+ ac_useropt_orig=$ac_useropt
+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`
+ case $ac_user_opts in
+ *"
+"with_$ac_useropt"
+"*) ;;
+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig"
+ ac_unrecognized_sep=', ';;
+ esac
+ eval with_$ac_useropt=no ;;
+
+ --x)
+ # Obsolete; use --with-x.
+ with_x=yes ;;
+
+ -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \
+ | --x-incl | --x-inc | --x-in | --x-i)
+ ac_prev=x_includes ;;
+ -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \
+ | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*)
+ x_includes=$ac_optarg ;;
+
+ -x-libraries | --x-libraries | --x-librarie | --x-librari \
+ | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l)
+ ac_prev=x_libraries ;;
+ -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \
+ | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*)
+ x_libraries=$ac_optarg ;;
+
+ -*) as_fn_error $? "unrecognized option: \`$ac_option'
+Try \`$0 --help' for more information"
+ ;;
+
+ *=*)
+ ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='`
+ # Reject names that are not valid shell variable names.
+ case $ac_envvar in #(
+ '' | [0-9]* | *[!_$as_cr_alnum]* )
+ as_fn_error $? "invalid variable name: \`$ac_envvar'" ;;
+ esac
+ eval $ac_envvar=\$ac_optarg
+ export $ac_envvar ;;
+
+ *)
+ # FIXME: should be removed in autoconf 3.0.
+ $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2
+ expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null &&
+ $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2
+ : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}"
+ ;;
+
+ esac
+done
+
+if test -n "$ac_prev"; then
+ ac_option=--`echo $ac_prev | sed 's/_/-/g'`
+ as_fn_error $? "missing argument to $ac_option"
+fi
+
+if test -n "$ac_unrecognized_opts"; then
+ case $enable_option_checking in
+ no) ;;
+ fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;;
+ *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;;
+ esac
+fi
+
+# Check all directory arguments for consistency.
+for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \
+ datadir sysconfdir sharedstatedir localstatedir includedir \
+ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \
+ libdir localedir mandir runstatedir
+do
+ eval ac_val=\$$ac_var
+ # Remove trailing slashes.
+ case $ac_val in
+ */ )
+ ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'`
+ eval $ac_var=\$ac_val;;
+ esac
+ # Be sure to have absolute directory names.
+ case $ac_val in
+ [\\/$]* | ?:[\\/]* ) continue;;
+ NONE | '' ) case $ac_var in *prefix ) continue;; esac;;
+ esac
+ as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val"
+done
+
+# There might be people who depend on the old broken behavior: `$host'
+# used to hold the argument of --host etc.
+# FIXME: To remove some day.
+build=$build_alias
+host=$host_alias
+target=$target_alias
+
+# FIXME: To remove some day.
+if test "x$host_alias" != x; then
+ if test "x$build_alias" = x; then
+ cross_compiling=maybe
+ elif test "x$build_alias" != "x$host_alias"; then
+ cross_compiling=yes
+ fi
+fi
+
+ac_tool_prefix=
+test -n "$host_alias" && ac_tool_prefix=$host_alias-
+
+test "$silent" = yes && exec 6>/dev/null
+
+
+ac_pwd=`pwd` && test -n "$ac_pwd" &&
+ac_ls_di=`ls -di .` &&
+ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` ||
+ as_fn_error $? "working directory cannot be determined"
+test "X$ac_ls_di" = "X$ac_pwd_ls_di" ||
+ as_fn_error $? "pwd does not report name of working directory"
+
+
+# Find the source files, if location was not specified.
+if test -z "$srcdir"; then
+ ac_srcdir_defaulted=yes
+ # Try the directory containing this script, then the parent directory.
+ ac_confdir=`$as_dirname -- "$as_myself" ||
+$as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$as_myself" : 'X\(//\)[^/]' \| \
+ X"$as_myself" : 'X\(//\)$' \| \
+ X"$as_myself" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_myself" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ srcdir=$ac_confdir
+ if test ! -r "$srcdir/$ac_unique_file"; then
+ srcdir=..
+ fi
+else
+ ac_srcdir_defaulted=no
+fi
+if test ! -r "$srcdir/$ac_unique_file"; then
+ test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .."
+ as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir"
+fi
+ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work"
+ac_abs_confdir=`(
+ cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg"
+ pwd)`
+# When building in place, set srcdir=.
+if test "$ac_abs_confdir" = "$ac_pwd"; then
+ srcdir=.
+fi
+# Remove unnecessary trailing slashes from srcdir.
+# Double slashes in file names in object file debugging info
+# mess up M-x gdb in Emacs.
+case $srcdir in
+*/) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;;
+esac
+for ac_var in $ac_precious_vars; do
+ eval ac_env_${ac_var}_set=\${${ac_var}+set}
+ eval ac_env_${ac_var}_value=\$${ac_var}
+ eval ac_cv_env_${ac_var}_set=\${${ac_var}+set}
+ eval ac_cv_env_${ac_var}_value=\$${ac_var}
+done
+
+#
+# Report the --help message.
+#
+if test "$ac_init_help" = "long"; then
+ # Omit some internal or obsolete options to make the list less imposing.
+ # This message is too long to be a string in the A/UX 3.1 sh.
+ cat <<_ACEOF
+\`configure' configures freedom-metal v0.1.2 to adapt to many kinds of systems.
+
+Usage: $0 [OPTION]... [VAR=VALUE]...
+
+To assign environment variables (e.g., CC, CFLAGS...), specify them as
+VAR=VALUE. See below for descriptions of some of the useful variables.
+
+Defaults for the options are specified in brackets.
+
+Configuration:
+ -h, --help display this help and exit
+ --help=short display options specific to this package
+ --help=recursive display the short help of all the included packages
+ -V, --version display version information and exit
+ -q, --quiet, --silent do not print \`checking ...' messages
+ --cache-file=FILE cache test results in FILE [disabled]
+ -C, --config-cache alias for \`--cache-file=config.cache'
+ -n, --no-create do not create output files
+ --srcdir=DIR find the sources in DIR [configure dir or \`..']
+
+Installation directories:
+ --prefix=PREFIX install architecture-independent files in PREFIX
+ [$ac_default_prefix]
+ --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX
+ [PREFIX]
+
+By default, \`make install' will install all the files in
+\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify
+an installation prefix other than \`$ac_default_prefix' using \`--prefix',
+for instance \`--prefix=\$HOME'.
+
+For better control, use the options below.
+
+Fine tuning of the installation directories:
+ --bindir=DIR user executables [EPREFIX/bin]
+ --sbindir=DIR system admin executables [EPREFIX/sbin]
+ --libexecdir=DIR program executables [EPREFIX/libexec]
+ --sysconfdir=DIR read-only single-machine data [PREFIX/etc]
+ --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com]
+ --localstatedir=DIR modifiable single-machine data [PREFIX/var]
+ --runstatedir=DIR modifiable per-process data [LOCALSTATEDIR/run]
+ --libdir=DIR object code libraries [EPREFIX/lib]
+ --includedir=DIR C header files [PREFIX/include]
+ --oldincludedir=DIR C header files for non-gcc [/usr/include]
+ --datarootdir=DIR read-only arch.-independent data root [PREFIX/share]
+ --datadir=DIR read-only architecture-independent data [DATAROOTDIR]
+ --infodir=DIR info documentation [DATAROOTDIR/info]
+ --localedir=DIR locale-dependent data [DATAROOTDIR/locale]
+ --mandir=DIR man documentation [DATAROOTDIR/man]
+ --docdir=DIR documentation root [DATAROOTDIR/doc/freedom-metal]
+ --htmldir=DIR html documentation [DOCDIR]
+ --dvidir=DIR dvi documentation [DOCDIR]
+ --pdfdir=DIR pdf documentation [DOCDIR]
+ --psdir=DIR ps documentation [DOCDIR]
+_ACEOF
+
+ cat <<\_ACEOF
+
+Program names:
+ --program-prefix=PREFIX prepend PREFIX to installed program names
+ --program-suffix=SUFFIX append SUFFIX to installed program names
+ --program-transform-name=PROGRAM run sed PROGRAM on installed program names
+
+System types:
+ --build=BUILD configure for building on BUILD [guessed]
+ --host=HOST cross-compile to build programs to run on HOST [BUILD]
+_ACEOF
+fi
+
+if test -n "$ac_init_help"; then
+ case $ac_init_help in
+ short | recursive ) echo "Configuration of freedom-metal v0.1.2:";;
+ esac
+ cat <<\_ACEOF
+
+Optional Features:
+ --disable-option-checking ignore unrecognized --enable/--with options
+ --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no)
+ --enable-FEATURE[=ARG] include FEATURE [ARG=yes]
+ --enable-silent-rules less verbose build output (undo: "make V=1")
+ --disable-silent-rules verbose build output (undo: "make V=0")
+ --enable-maintainer-mode
+ enable make rules and dependencies not useful (and
+ sometimes confusing) to the casual installer
+ --enable-dependency-tracking
+ do not reject slow dependency extractors
+ --disable-dependency-tracking
+ speeds up one-time build
+
+Optional Packages:
+ --with-PACKAGE[=ARG] use PACKAGE [ARG=yes]
+ --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no)
+ --with-bultin-libgloss Build libgloss along with Metal
+ --with-bultin-libmetal-pico
+ Build libmetal-pico along with Metal
+ --with-bultin-libmetal-segger
+ Build libmetal-segger along with Metal
+ --with-machine-header=PATH
+ Path to the machine header file
+ --with-machine-inline=PATH
+ Path to the machine inline file
+ --with-platform-header=PATH
+ Path to the platform header file
+
+Some influential environment variables:
+ CC C compiler command
+ CFLAGS C compiler flags
+ LDFLAGS linker flags, e.g. -L<lib dir> if you have libraries in a
+ nonstandard directory <lib dir>
+ LIBS libraries to pass to the linker, e.g. -l<library>
+ CPPFLAGS (Objective) C/C++ preprocessor flags, e.g. -I<include dir> if
+ you have headers in a nonstandard directory <include dir>
+ CCAS assembler compiler command (defaults to CC)
+ CCASFLAGS assembler compiler flags (defaults to CFLAGS)
+
+Use these variables to override the choices made by `configure' or to help
+it to find libraries and programs with nonstandard names/locations.
+
+Report bugs to <https://github.com/sifive/freedom-metal/issues>.
+freedom-metal home page: <https://github.com/sifive/freedom-metal>.
+_ACEOF
+ac_status=$?
+fi
+
+if test "$ac_init_help" = "recursive"; then
+ # If there are subdirs, report their specific --help.
+ for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue
+ test -d "$ac_dir" ||
+ { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } ||
+ continue
+ ac_builddir=.
+
+case "$ac_dir" in
+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;
+*)
+ ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`
+ # A ".." for each directory in $ac_dir_suffix.
+ ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`
+ case $ac_top_builddir_sub in
+ "") ac_top_builddir_sub=. ac_top_build_prefix= ;;
+ *) ac_top_build_prefix=$ac_top_builddir_sub/ ;;
+ esac ;;
+esac
+ac_abs_top_builddir=$ac_pwd
+ac_abs_builddir=$ac_pwd$ac_dir_suffix
+# for backward compatibility:
+ac_top_builddir=$ac_top_build_prefix
+
+case $srcdir in
+ .) # We are building in place.
+ ac_srcdir=.
+ ac_top_srcdir=$ac_top_builddir_sub
+ ac_abs_top_srcdir=$ac_pwd ;;
+ [\\/]* | ?:[\\/]* ) # Absolute name.
+ ac_srcdir=$srcdir$ac_dir_suffix;
+ ac_top_srcdir=$srcdir
+ ac_abs_top_srcdir=$srcdir ;;
+ *) # Relative name.
+ ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix
+ ac_top_srcdir=$ac_top_build_prefix$srcdir
+ ac_abs_top_srcdir=$ac_pwd/$srcdir ;;
+esac
+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix
+
+ cd "$ac_dir" || { ac_status=$?; continue; }
+ # Check for guested configure.
+ if test -f "$ac_srcdir/configure.gnu"; then
+ echo &&
+ $SHELL "$ac_srcdir/configure.gnu" --help=recursive
+ elif test -f "$ac_srcdir/configure"; then
+ echo &&
+ $SHELL "$ac_srcdir/configure" --help=recursive
+ else
+ $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2
+ fi || ac_status=$?
+ cd "$ac_pwd" || { ac_status=$?; break; }
+ done
+fi
+
+test -n "$ac_init_help" && exit $ac_status
+if $ac_init_version; then
+ cat <<\_ACEOF
+freedom-metal configure v0.1.2
+generated by GNU Autoconf 2.69
+
+Copyright (C) 2012 Free Software Foundation, Inc.
+This configure script is free software; the Free Software Foundation
+gives unlimited permission to copy, distribute and modify it.
+_ACEOF
+ exit
+fi
+
+## ------------------------ ##
+## Autoconf initialization. ##
+## ------------------------ ##
+
+# ac_fn_c_try_compile LINENO
+# --------------------------
+# Try to compile conftest.$ac_ext, and return whether this succeeded.
+ac_fn_c_try_compile ()
+{
+ as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+ rm -f conftest.$ac_objext
+ if { { ac_try="$ac_compile"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_compile") 2>conftest.err
+ ac_status=$?
+ if test -s conftest.err; then
+ grep -v '^ *+' conftest.err >conftest.er1
+ cat conftest.er1 >&5
+ mv -f conftest.er1 conftest.err
+ fi
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; } && {
+ test -z "$ac_c_werror_flag" ||
+ test ! -s conftest.err
+ } && test -s conftest.$ac_objext; then :
+ ac_retval=0
+else
+ $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+ ac_retval=1
+fi
+ eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
+ as_fn_set_status $ac_retval
+
+} # ac_fn_c_try_compile
+cat >config.log <<_ACEOF
+This file contains any messages produced by compilers while
+running configure, to aid debugging if configure makes a mistake.
+
+It was created by freedom-metal $as_me v0.1.2, which was
+generated by GNU Autoconf 2.69. Invocation command line was
+
+ $ $0 $@
+
+_ACEOF
+exec 5>>config.log
+{
+cat <<_ASUNAME
+## --------- ##
+## Platform. ##
+## --------- ##
+
+hostname = `(hostname || uname -n) 2>/dev/null | sed 1q`
+uname -m = `(uname -m) 2>/dev/null || echo unknown`
+uname -r = `(uname -r) 2>/dev/null || echo unknown`
+uname -s = `(uname -s) 2>/dev/null || echo unknown`
+uname -v = `(uname -v) 2>/dev/null || echo unknown`
+
+/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown`
+/bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown`
+
+/bin/arch = `(/bin/arch) 2>/dev/null || echo unknown`
+/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown`
+/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown`
+/usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown`
+/bin/machine = `(/bin/machine) 2>/dev/null || echo unknown`
+/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown`
+/bin/universe = `(/bin/universe) 2>/dev/null || echo unknown`
+
+_ASUNAME
+
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ $as_echo "PATH: $as_dir"
+ done
+IFS=$as_save_IFS
+
+} >&5
+
+cat >&5 <<_ACEOF
+
+
+## ----------- ##
+## Core tests. ##
+## ----------- ##
+
+_ACEOF
+
+
+# Keep a trace of the command line.
+# Strip out --no-create and --no-recursion so they do not pile up.
+# Strip out --silent because we don't want to record it for future runs.
+# Also quote any args containing shell meta-characters.
+# Make two passes to allow for proper duplicate-argument suppression.
+ac_configure_args=
+ac_configure_args0=
+ac_configure_args1=
+ac_must_keep_next=false
+for ac_pass in 1 2
+do
+ for ac_arg
+ do
+ case $ac_arg in
+ -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;;
+ -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+ | -silent | --silent | --silen | --sile | --sil)
+ continue ;;
+ *\'*)
+ ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;;
+ esac
+ case $ac_pass in
+ 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;;
+ 2)
+ as_fn_append ac_configure_args1 " '$ac_arg'"
+ if test $ac_must_keep_next = true; then
+ ac_must_keep_next=false # Got value, back to normal.
+ else
+ case $ac_arg in
+ *=* | --config-cache | -C | -disable-* | --disable-* \
+ | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \
+ | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \
+ | -with-* | --with-* | -without-* | --without-* | --x)
+ case "$ac_configure_args0 " in
+ "$ac_configure_args1"*" '$ac_arg' "* ) continue ;;
+ esac
+ ;;
+ -* ) ac_must_keep_next=true ;;
+ esac
+ fi
+ as_fn_append ac_configure_args " '$ac_arg'"
+ ;;
+ esac
+ done
+done
+{ ac_configure_args0=; unset ac_configure_args0;}
+{ ac_configure_args1=; unset ac_configure_args1;}
+
+# When interrupted or exit'd, cleanup temporary files, and complete
+# config.log. We remove comments because anyway the quotes in there
+# would cause problems or look ugly.
+# WARNING: Use '\'' to represent an apostrophe within the trap.
+# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug.
+trap 'exit_status=$?
+ # Save into config.log some information that might help in debugging.
+ {
+ echo
+
+ $as_echo "## ---------------- ##
+## Cache variables. ##
+## ---------------- ##"
+ echo
+ # The following way of writing the cache mishandles newlines in values,
+(
+ for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do
+ eval ac_val=\$$ac_var
+ case $ac_val in #(
+ *${as_nl}*)
+ case $ac_var in #(
+ *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5
+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;
+ esac
+ case $ac_var in #(
+ _ | IFS | as_nl) ;; #(
+ BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(
+ *) { eval $ac_var=; unset $ac_var;} ;;
+ esac ;;
+ esac
+ done
+ (set) 2>&1 |
+ case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #(
+ *${as_nl}ac_space=\ *)
+ sed -n \
+ "s/'\''/'\''\\\\'\'''\''/g;
+ s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p"
+ ;; #(
+ *)
+ sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"
+ ;;
+ esac |
+ sort
+)
+ echo
+
+ $as_echo "## ----------------- ##
+## Output variables. ##
+## ----------------- ##"
+ echo
+ for ac_var in $ac_subst_vars
+ do
+ eval ac_val=\$$ac_var
+ case $ac_val in
+ *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;
+ esac
+ $as_echo "$ac_var='\''$ac_val'\''"
+ done | sort
+ echo
+
+ if test -n "$ac_subst_files"; then
+ $as_echo "## ------------------- ##
+## File substitutions. ##
+## ------------------- ##"
+ echo
+ for ac_var in $ac_subst_files
+ do
+ eval ac_val=\$$ac_var
+ case $ac_val in
+ *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;
+ esac
+ $as_echo "$ac_var='\''$ac_val'\''"
+ done | sort
+ echo
+ fi
+
+ if test -s confdefs.h; then
+ $as_echo "## ----------- ##
+## confdefs.h. ##
+## ----------- ##"
+ echo
+ cat confdefs.h
+ echo
+ fi
+ test "$ac_signal" != 0 &&
+ $as_echo "$as_me: caught signal $ac_signal"
+ $as_echo "$as_me: exit $exit_status"
+ } >&5
+ rm -f core *.core core.conftest.* &&
+ rm -f -r conftest* confdefs* conf$$* $ac_clean_files &&
+ exit $exit_status
+' 0
+for ac_signal in 1 2 13 15; do
+ trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal
+done
+ac_signal=0
+
+# confdefs.h avoids OS command line length limits that DEFS can exceed.
+rm -f -r conftest* confdefs.h
+
+$as_echo "/* confdefs.h */" > confdefs.h
+
+# Predefined preprocessor variables.
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_NAME "$PACKAGE_NAME"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_TARNAME "$PACKAGE_TARNAME"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_VERSION "$PACKAGE_VERSION"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_STRING "$PACKAGE_STRING"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT"
+_ACEOF
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE_URL "$PACKAGE_URL"
+_ACEOF
+
+
+# Let the site file select an alternate cache file if it wants to.
+# Prefer an explicitly selected file to automatically selected ones.
+ac_site_file1=NONE
+ac_site_file2=NONE
+if test -n "$CONFIG_SITE"; then
+ # We do not want a PATH search for config.site.
+ case $CONFIG_SITE in #((
+ -*) ac_site_file1=./$CONFIG_SITE;;
+ */*) ac_site_file1=$CONFIG_SITE;;
+ *) ac_site_file1=./$CONFIG_SITE;;
+ esac
+elif test "x$prefix" != xNONE; then
+ ac_site_file1=$prefix/share/config.site
+ ac_site_file2=$prefix/etc/config.site
+else
+ ac_site_file1=$ac_default_prefix/share/config.site
+ ac_site_file2=$ac_default_prefix/etc/config.site
+fi
+for ac_site_file in "$ac_site_file1" "$ac_site_file2"
+do
+ test "x$ac_site_file" = xNONE && continue
+ if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5
+$as_echo "$as_me: loading site script $ac_site_file" >&6;}
+ sed 's/^/| /' "$ac_site_file" >&5
+ . "$ac_site_file" \
+ || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "failed to load site script $ac_site_file
+See \`config.log' for more details" "$LINENO" 5; }
+ fi
+done
+
+if test -r "$cache_file"; then
+ # Some versions of bash will fail to source /dev/null (special files
+ # actually), so we avoid doing that. DJGPP emulates it as a regular file.
+ if test /dev/null != "$cache_file" && test -f "$cache_file"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5
+$as_echo "$as_me: loading cache $cache_file" >&6;}
+ case $cache_file in
+ [\\/]* | ?:[\\/]* ) . "$cache_file";;
+ *) . "./$cache_file";;
+ esac
+ fi
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5
+$as_echo "$as_me: creating cache $cache_file" >&6;}
+ >$cache_file
+fi
+
+# Check that the precious variables saved in the cache have kept the same
+# value.
+ac_cache_corrupted=false
+for ac_var in $ac_precious_vars; do
+ eval ac_old_set=\$ac_cv_env_${ac_var}_set
+ eval ac_new_set=\$ac_env_${ac_var}_set
+ eval ac_old_val=\$ac_cv_env_${ac_var}_value
+ eval ac_new_val=\$ac_env_${ac_var}_value
+ case $ac_old_set,$ac_new_set in
+ set,)
+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5
+$as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;}
+ ac_cache_corrupted=: ;;
+ ,set)
+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5
+$as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;}
+ ac_cache_corrupted=: ;;
+ ,);;
+ *)
+ if test "x$ac_old_val" != "x$ac_new_val"; then
+ # differences in whitespace do not lead to failure.
+ ac_old_val_w=`echo x $ac_old_val`
+ ac_new_val_w=`echo x $ac_new_val`
+ if test "$ac_old_val_w" != "$ac_new_val_w"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5
+$as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;}
+ ac_cache_corrupted=:
+ else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5
+$as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;}
+ eval $ac_var=\$ac_old_val
+ fi
+ { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5
+$as_echo "$as_me: former value: \`$ac_old_val'" >&2;}
+ { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5
+$as_echo "$as_me: current value: \`$ac_new_val'" >&2;}
+ fi;;
+ esac
+ # Pass precious variables to config.status.
+ if test "$ac_new_set" = set; then
+ case $ac_new_val in
+ *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;;
+ *) ac_arg=$ac_var=$ac_new_val ;;
+ esac
+ case " $ac_configure_args " in
+ *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy.
+ *) as_fn_append ac_configure_args " '$ac_arg'" ;;
+ esac
+ fi
+done
+if $ac_cache_corrupted; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5
+$as_echo "$as_me: error: changes in the environment can compromise the build" >&2;}
+ as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5
+fi
+## -------------------- ##
+## Main body of script. ##
+## -------------------- ##
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+
+
+# Initializes automake, enabling maintainer mode by default (which should be
+# disabled by the archive generated by "make dist").
+am__api_version='1.15'
+
+ac_aux_dir=
+for ac_dir in "$srcdir" "$srcdir/.." "$srcdir/../.."; do
+ if test -f "$ac_dir/install-sh"; then
+ ac_aux_dir=$ac_dir
+ ac_install_sh="$ac_aux_dir/install-sh -c"
+ break
+ elif test -f "$ac_dir/install.sh"; then
+ ac_aux_dir=$ac_dir
+ ac_install_sh="$ac_aux_dir/install.sh -c"
+ break
+ elif test -f "$ac_dir/shtool"; then
+ ac_aux_dir=$ac_dir
+ ac_install_sh="$ac_aux_dir/shtool install -c"
+ break
+ fi
+done
+if test -z "$ac_aux_dir"; then
+ as_fn_error $? "cannot find install-sh, install.sh, or shtool in \"$srcdir\" \"$srcdir/..\" \"$srcdir/../..\"" "$LINENO" 5
+fi
+
+# These three variables are undocumented and unsupported,
+# and are intended to be withdrawn in a future Autoconf release.
+# They can cause serious problems if a builder's source tree is in a directory
+# whose full name contains unusual characters.
+ac_config_guess="$SHELL $ac_aux_dir/config.guess" # Please don't use this var.
+ac_config_sub="$SHELL $ac_aux_dir/config.sub" # Please don't use this var.
+ac_configure="$SHELL $ac_aux_dir/configure" # Please don't use this var.
+
+
+# Find a good install program. We prefer a C program (faster),
+# so one script is as good as another. But avoid the broken or
+# incompatible versions:
+# SysV /etc/install, /usr/sbin/install
+# SunOS /usr/etc/install
+# IRIX /sbin/install
+# AIX /bin/install
+# AmigaOS /C/install, which installs bootblocks on floppy discs
+# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag
+# AFS /usr/afsws/bin/install, which mishandles nonexistent args
+# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff"
+# OS/2's system install, which has a completely different semantic
+# ./install, which can be erroneously created by make from ./install.sh.
+# Reject install programs that cannot install multiple files.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5
+$as_echo_n "checking for a BSD-compatible install... " >&6; }
+if test -z "$INSTALL"; then
+if ${ac_cv_path_install+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ # Account for people who put trailing slashes in PATH elements.
+case $as_dir/ in #((
+ ./ | .// | /[cC]/* | \
+ /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \
+ ?:[\\/]os2[\\/]install[\\/]* | ?:[\\/]OS2[\\/]INSTALL[\\/]* | \
+ /usr/ucb/* ) ;;
+ *)
+ # OSF1 and SCO ODT 3.0 have their own names for install.
+ # Don't use installbsd from OSF since it installs stuff as root
+ # by default.
+ for ac_prog in ginstall scoinst install; do
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then
+ if test $ac_prog = install &&
+ grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then
+ # AIX install. It has an incompatible calling convention.
+ :
+ elif test $ac_prog = install &&
+ grep pwplus "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then
+ # program-specific install script used by HP pwplus--don't use.
+ :
+ else
+ rm -rf conftest.one conftest.two conftest.dir
+ echo one > conftest.one
+ echo two > conftest.two
+ mkdir conftest.dir
+ if "$as_dir/$ac_prog$ac_exec_ext" -c conftest.one conftest.two "`pwd`/conftest.dir" &&
+ test -s conftest.one && test -s conftest.two &&
+ test -s conftest.dir/conftest.one &&
+ test -s conftest.dir/conftest.two
+ then
+ ac_cv_path_install="$as_dir/$ac_prog$ac_exec_ext -c"
+ break 3
+ fi
+ fi
+ fi
+ done
+ done
+ ;;
+esac
+
+ done
+IFS=$as_save_IFS
+
+rm -rf conftest.one conftest.two conftest.dir
+
+fi
+ if test "${ac_cv_path_install+set}" = set; then
+ INSTALL=$ac_cv_path_install
+ else
+ # As a last resort, use the slow shell script. Don't cache a
+ # value for INSTALL within a source directory, because that will
+ # break other packages using the cache if that directory is
+ # removed, or if the value is a relative name.
+ INSTALL=$ac_install_sh
+ fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $INSTALL" >&5
+$as_echo "$INSTALL" >&6; }
+
+# Use test -z because SunOS4 sh mishandles braces in ${var-val}.
+# It thinks the first close brace ends the variable substitution.
+test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}'
+
+test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}'
+
+test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644'
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether build environment is sane" >&5
+$as_echo_n "checking whether build environment is sane... " >&6; }
+# Reject unsafe characters in $srcdir or the absolute working directory
+# name. Accept space and tab only in the latter.
+am_lf='
+'
+case `pwd` in
+ *[\\\"\#\$\&\'\`$am_lf]*)
+ as_fn_error $? "unsafe absolute working directory name" "$LINENO" 5;;
+esac
+case $srcdir in
+ *[\\\"\#\$\&\'\`$am_lf\ \ ]*)
+ as_fn_error $? "unsafe srcdir value: '$srcdir'" "$LINENO" 5;;
+esac
+
+# Do 'set' in a subshell so we don't clobber the current shell's
+# arguments. Must try -L first in case configure is actually a
+# symlink; some systems play weird games with the mod time of symlinks
+# (eg FreeBSD returns the mod time of the symlink's containing
+# directory).
+if (
+ am_has_slept=no
+ for am_try in 1 2; do
+ echo "timestamp, slept: $am_has_slept" > conftest.file
+ set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null`
+ if test "$*" = "X"; then
+ # -L didn't work.
+ set X `ls -t "$srcdir/configure" conftest.file`
+ fi
+ if test "$*" != "X $srcdir/configure conftest.file" \
+ && test "$*" != "X conftest.file $srcdir/configure"; then
+
+ # If neither matched, then we have a broken ls. This can happen
+ # if, for instance, CONFIG_SHELL is bash and it inherits a
+ # broken ls alias from the environment. This has actually
+ # happened. Such a system could not be considered "sane".
+ as_fn_error $? "ls -t appears to fail. Make sure there is not a broken
+ alias in your environment" "$LINENO" 5
+ fi
+ if test "$2" = conftest.file || test $am_try -eq 2; then
+ break
+ fi
+ # Just in case.
+ sleep 1
+ am_has_slept=yes
+ done
+ test "$2" = conftest.file
+ )
+then
+ # Ok.
+ :
+else
+ as_fn_error $? "newly created file is older than distributed files!
+Check your system clock" "$LINENO" 5
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+# If we didn't sleep, we still need to ensure time stamps of config.status and
+# generated files are strictly newer.
+am_sleep_pid=
+if grep 'slept: no' conftest.file >/dev/null 2>&1; then
+ ( sleep 1 ) &
+ am_sleep_pid=$!
+fi
+
+rm -f conftest.file
+
+test "$program_prefix" != NONE &&
+ program_transform_name="s&^&$program_prefix&;$program_transform_name"
+# Use a double $ so make ignores it.
+test "$program_suffix" != NONE &&
+ program_transform_name="s&\$&$program_suffix&;$program_transform_name"
+# Double any \ or $.
+# By default was `s,x,x', remove it if useless.
+ac_script='s/[\\$]/&&/g;s/;s,x,x,$//'
+program_transform_name=`$as_echo "$program_transform_name" | sed "$ac_script"`
+
+# Expand $ac_aux_dir to an absolute path.
+am_aux_dir=`cd "$ac_aux_dir" && pwd`
+
+if test x"${MISSING+set}" != xset; then
+ case $am_aux_dir in
+ *\ * | *\ *)
+ MISSING="\${SHELL} \"$am_aux_dir/missing\"" ;;
+ *)
+ MISSING="\${SHELL} $am_aux_dir/missing" ;;
+ esac
+fi
+# Use eval to expand $SHELL
+if eval "$MISSING --is-lightweight"; then
+ am_missing_run="$MISSING "
+else
+ am_missing_run=
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: 'missing' script is too old or missing" >&5
+$as_echo "$as_me: WARNING: 'missing' script is too old or missing" >&2;}
+fi
+
+if test x"${install_sh+set}" != xset; then
+ case $am_aux_dir in
+ *\ * | *\ *)
+ install_sh="\${SHELL} '$am_aux_dir/install-sh'" ;;
+ *)
+ install_sh="\${SHELL} $am_aux_dir/install-sh"
+ esac
+fi
+
+# Installed binaries are usually stripped using 'strip' when the user
+# run "make install-strip". However 'strip' might not be the right
+# tool to use in cross-compilation environments, therefore Automake
+# will honor the 'STRIP' environment variable to overrule this program.
+if test "$cross_compiling" != no; then
+ if test -n "$ac_tool_prefix"; then
+ # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args.
+set dummy ${ac_tool_prefix}strip; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_STRIP+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$STRIP"; then
+ ac_cv_prog_STRIP="$STRIP" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_STRIP="${ac_tool_prefix}strip"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+STRIP=$ac_cv_prog_STRIP
+if test -n "$STRIP"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $STRIP" >&5
+$as_echo "$STRIP" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$ac_cv_prog_STRIP"; then
+ ac_ct_STRIP=$STRIP
+ # Extract the first word of "strip", so it can be a program name with args.
+set dummy strip; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_STRIP+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$ac_ct_STRIP"; then
+ ac_cv_prog_ac_ct_STRIP="$ac_ct_STRIP" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_ac_ct_STRIP="strip"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP
+if test -n "$ac_ct_STRIP"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP" >&5
+$as_echo "$ac_ct_STRIP" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+ if test "x$ac_ct_STRIP" = x; then
+ STRIP=":"
+ else
+ case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+ STRIP=$ac_ct_STRIP
+ fi
+else
+ STRIP="$ac_cv_prog_STRIP"
+fi
+
+fi
+INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for a thread-safe mkdir -p" >&5
+$as_echo_n "checking for a thread-safe mkdir -p... " >&6; }
+if test -z "$MKDIR_P"; then
+ if ${ac_cv_path_mkdir+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH$PATH_SEPARATOR/opt/sfw/bin
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_prog in mkdir gmkdir; do
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext" || continue
+ case `"$as_dir/$ac_prog$ac_exec_ext" --version 2>&1` in #(
+ 'mkdir (GNU coreutils) '* | \
+ 'mkdir (coreutils) '* | \
+ 'mkdir (fileutils) '4.1*)
+ ac_cv_path_mkdir=$as_dir/$ac_prog$ac_exec_ext
+ break 3;;
+ esac
+ done
+ done
+ done
+IFS=$as_save_IFS
+
+fi
+
+ test -d ./--version && rmdir ./--version
+ if test "${ac_cv_path_mkdir+set}" = set; then
+ MKDIR_P="$ac_cv_path_mkdir -p"
+ else
+ # As a last resort, use the slow shell script. Don't cache a
+ # value for MKDIR_P within a source directory, because that will
+ # break other packages using the cache if that directory is
+ # removed, or if the value is a relative name.
+ MKDIR_P="$ac_install_sh -d"
+ fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $MKDIR_P" >&5
+$as_echo "$MKDIR_P" >&6; }
+
+for ac_prog in gawk mawk nawk awk
+do
+ # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_AWK+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$AWK"; then
+ ac_cv_prog_AWK="$AWK" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_AWK="$ac_prog"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+AWK=$ac_cv_prog_AWK
+if test -n "$AWK"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AWK" >&5
+$as_echo "$AWK" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ test -n "$AWK" && break
+done
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} sets \$(MAKE)" >&5
+$as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; }
+set x ${MAKE-make}
+ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'`
+if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat >conftest.make <<\_ACEOF
+SHELL = /bin/sh
+all:
+ @echo '@@@%%%=$(MAKE)=@@@%%%'
+_ACEOF
+# GNU make sometimes prints "make[1]: Entering ...", which would confuse us.
+case `${MAKE-make} -f conftest.make 2>/dev/null` in
+ *@@@%%%=?*=@@@%%%*)
+ eval ac_cv_prog_make_${ac_make}_set=yes;;
+ *)
+ eval ac_cv_prog_make_${ac_make}_set=no;;
+esac
+rm -f conftest.make
+fi
+if eval test \$ac_cv_prog_make_${ac_make}_set = yes; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+ SET_MAKE=
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+ SET_MAKE="MAKE=${MAKE-make}"
+fi
+
+rm -rf .tst 2>/dev/null
+mkdir .tst 2>/dev/null
+if test -d .tst; then
+ am__leading_dot=.
+else
+ am__leading_dot=_
+fi
+rmdir .tst 2>/dev/null
+
+# Check whether --enable-silent-rules was given.
+if test "${enable_silent_rules+set}" = set; then :
+ enableval=$enable_silent_rules;
+fi
+
+case $enable_silent_rules in # (((
+ yes) AM_DEFAULT_VERBOSITY=0;;
+ no) AM_DEFAULT_VERBOSITY=1;;
+ *) AM_DEFAULT_VERBOSITY=1;;
+esac
+am_make=${MAKE-make}
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $am_make supports nested variables" >&5
+$as_echo_n "checking whether $am_make supports nested variables... " >&6; }
+if ${am_cv_make_support_nested_variables+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if $as_echo 'TRUE=$(BAR$(V))
+BAR0=false
+BAR1=true
+V=1
+am__doit:
+ @$(TRUE)
+.PHONY: am__doit' | $am_make -f - >/dev/null 2>&1; then
+ am_cv_make_support_nested_variables=yes
+else
+ am_cv_make_support_nested_variables=no
+fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_make_support_nested_variables" >&5
+$as_echo "$am_cv_make_support_nested_variables" >&6; }
+if test $am_cv_make_support_nested_variables = yes; then
+ AM_V='$(V)'
+ AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'
+else
+ AM_V=$AM_DEFAULT_VERBOSITY
+ AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY
+fi
+AM_BACKSLASH='\'
+
+if test "`cd $srcdir && pwd`" != "`pwd`"; then
+ # Use -I$(srcdir) only when $(srcdir) != ., so that make's output
+ # is not polluted with repeated "-I."
+ am__isrc=' -I$(srcdir)'
+ # test to see if srcdir already configured
+ if test -f $srcdir/config.status; then
+ as_fn_error $? "source directory already configured; run \"make distclean\" there first" "$LINENO" 5
+ fi
+fi
+
+# test whether we have cygpath
+if test -z "$CYGPATH_W"; then
+ if (cygpath --version) >/dev/null 2>/dev/null; then
+ CYGPATH_W='cygpath -w'
+ else
+ CYGPATH_W=echo
+ fi
+fi
+
+
+# Define the identity of the package.
+ PACKAGE='freedom-metal'
+ VERSION='v0.1.2'
+
+
+cat >>confdefs.h <<_ACEOF
+#define PACKAGE "$PACKAGE"
+_ACEOF
+
+
+cat >>confdefs.h <<_ACEOF
+#define VERSION "$VERSION"
+_ACEOF
+
+# Some tools Automake needs.
+
+ACLOCAL=${ACLOCAL-"${am_missing_run}aclocal-${am__api_version}"}
+
+
+AUTOCONF=${AUTOCONF-"${am_missing_run}autoconf"}
+
+
+AUTOMAKE=${AUTOMAKE-"${am_missing_run}automake-${am__api_version}"}
+
+
+AUTOHEADER=${AUTOHEADER-"${am_missing_run}autoheader"}
+
+
+MAKEINFO=${MAKEINFO-"${am_missing_run}makeinfo"}
+
+# For better backward compatibility. To be removed once Automake 1.9.x
+# dies out for good. For more background, see:
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>
+# <http://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>
+mkdir_p='$(MKDIR_P)'
+
+# We need awk for the "check" target (and possibly the TAP driver). The
+# system "awk" is bad on some platforms.
+# Always define AMTAR for backward compatibility. Yes, it's still used
+# in the wild :-( We should find a proper way to deprecate it ...
+AMTAR='$${TAR-tar}'
+
+
+# We'll loop over all known methods to create a tar archive until one works.
+_am_tools='gnutar pax cpio none'
+
+am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -'
+
+
+
+
+
+
+# POSIX will say in a future version that running "rm -f" with no argument
+# is OK; and we want to be able to make that assumption in our Makefile
+# recipes. So use an aggressive probe to check that the usage we want is
+# actually supported "in the wild" to an acceptable degree.
+# See automake bug#10828.
+# To make any issue more visible, cause the running configure to be aborted
+# by default if the 'rm' program in use doesn't match our expectations; the
+# user can still override this though.
+if rm -f && rm -fr && rm -rf; then : OK; else
+ cat >&2 <<'END'
+Oops!
+
+Your 'rm' program seems unable to run without file operands specified
+on the command line, even when the '-f' option is present. This is contrary
+to the behaviour of most rm programs out there, and not conforming with
+the upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>
+
+Please tell bug-automake@gnu.org about your system, including the value
+of your $PATH and any error possibly output before this message. This
+can help us improve future automake versions.
+
+END
+ if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then
+ echo 'Configuration will proceed anyway, since you have set the' >&2
+ echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2
+ echo >&2
+ else
+ cat >&2 <<'END'
+Aborting the configuration process, to ensure you take notice of the issue.
+
+You can download and install GNU coreutils to get an 'rm' implementation
+that behaves properly: <http://www.gnu.org/software/coreutils/>.
+
+If you want to complete the configuration process using your problematic
+'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM
+to "yes", and re-run configure.
+
+END
+ as_fn_error $? "Your 'rm' program is bad, sorry." "$LINENO" 5
+ fi
+fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to enable maintainer-specific portions of Makefiles" >&5
+$as_echo_n "checking whether to enable maintainer-specific portions of Makefiles... " >&6; }
+ # Check whether --enable-maintainer-mode was given.
+if test "${enable_maintainer_mode+set}" = set; then :
+ enableval=$enable_maintainer_mode; USE_MAINTAINER_MODE=$enableval
+else
+ USE_MAINTAINER_MODE=no
+fi
+
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $USE_MAINTAINER_MODE" >&5
+$as_echo "$USE_MAINTAINER_MODE" >&6; }
+ if test $USE_MAINTAINER_MODE = yes; then
+ MAINTAINER_MODE_TRUE=
+ MAINTAINER_MODE_FALSE='#'
+else
+ MAINTAINER_MODE_TRUE='#'
+ MAINTAINER_MODE_FALSE=
+fi
+
+ MAINT=$MAINTAINER_MODE_TRUE
+
+
+
+
+# Make sure we can run config.sub.
+$SHELL "$ac_aux_dir/config.sub" sun4 >/dev/null 2>&1 ||
+ as_fn_error $? "cannot run $SHELL $ac_aux_dir/config.sub" "$LINENO" 5
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking build system type" >&5
+$as_echo_n "checking build system type... " >&6; }
+if ${ac_cv_build+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ ac_build_alias=$build_alias
+test "x$ac_build_alias" = x &&
+ ac_build_alias=`$SHELL "$ac_aux_dir/config.guess"`
+test "x$ac_build_alias" = x &&
+ as_fn_error $? "cannot guess build type; you must specify one" "$LINENO" 5
+ac_cv_build=`$SHELL "$ac_aux_dir/config.sub" $ac_build_alias` ||
+ as_fn_error $? "$SHELL $ac_aux_dir/config.sub $ac_build_alias failed" "$LINENO" 5
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_build" >&5
+$as_echo "$ac_cv_build" >&6; }
+case $ac_cv_build in
+*-*-*) ;;
+*) as_fn_error $? "invalid value of canonical build" "$LINENO" 5;;
+esac
+build=$ac_cv_build
+ac_save_IFS=$IFS; IFS='-'
+set x $ac_cv_build
+shift
+build_cpu=$1
+build_vendor=$2
+shift; shift
+# Remember, the first character of IFS is used to create $*,
+# except with old shells:
+build_os=$*
+IFS=$ac_save_IFS
+case $build_os in *\ *) build_os=`echo "$build_os" | sed 's/ /-/g'`;; esac
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking host system type" >&5
+$as_echo_n "checking host system type... " >&6; }
+if ${ac_cv_host+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test "x$host_alias" = x; then
+ ac_cv_host=$ac_cv_build
+else
+ ac_cv_host=`$SHELL "$ac_aux_dir/config.sub" $host_alias` ||
+ as_fn_error $? "$SHELL $ac_aux_dir/config.sub $host_alias failed" "$LINENO" 5
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_host" >&5
+$as_echo "$ac_cv_host" >&6; }
+case $ac_cv_host in
+*-*-*) ;;
+*) as_fn_error $? "invalid value of canonical host" "$LINENO" 5;;
+esac
+host=$ac_cv_host
+ac_save_IFS=$IFS; IFS='-'
+set x $ac_cv_host
+shift
+host_cpu=$1
+host_vendor=$2
+shift; shift
+# Remember, the first character of IFS is used to create $*,
+# except with old shells:
+host_os=$*
+IFS=$ac_save_IFS
+case $host_os in *\ *) host_os=`echo "$host_os" | sed 's/ /-/g'`;; esac
+
+
+
+# Probe for tools that we need in order to build.
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+if test -n "$ac_tool_prefix"; then
+ # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args.
+set dummy ${ac_tool_prefix}gcc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$CC"; then
+ ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_CC="${ac_tool_prefix}gcc"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$ac_cv_prog_CC"; then
+ ac_ct_CC=$CC
+ # Extract the first word of "gcc", so it can be a program name with args.
+set dummy gcc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$ac_ct_CC"; then
+ ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_ac_ct_CC="gcc"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_CC=$ac_cv_prog_ac_ct_CC
+if test -n "$ac_ct_CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5
+$as_echo "$ac_ct_CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+ if test "x$ac_ct_CC" = x; then
+ CC=""
+ else
+ case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+ CC=$ac_ct_CC
+ fi
+else
+ CC="$ac_cv_prog_CC"
+fi
+
+if test -z "$CC"; then
+ if test -n "$ac_tool_prefix"; then
+ # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args.
+set dummy ${ac_tool_prefix}cc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$CC"; then
+ ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_CC="${ac_tool_prefix}cc"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ fi
+fi
+if test -z "$CC"; then
+ # Extract the first word of "cc", so it can be a program name with args.
+set dummy cc; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$CC"; then
+ ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+ ac_prog_rejected=no
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then
+ ac_prog_rejected=yes
+ continue
+ fi
+ ac_cv_prog_CC="cc"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+if test $ac_prog_rejected = yes; then
+ # We found a bogon in the path, so make sure we never use it.
+ set dummy $ac_cv_prog_CC
+ shift
+ if test $# != 0; then
+ # We chose a different compiler from the bogus one.
+ # However, it has the same basename, so the bogon will be chosen
+ # first if we set CC to just the basename; use the full file name.
+ shift
+ ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@"
+ fi
+fi
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$CC"; then
+ if test -n "$ac_tool_prefix"; then
+ for ac_prog in cl.exe
+ do
+ # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args.
+set dummy $ac_tool_prefix$ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$CC"; then
+ ac_cv_prog_CC="$CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_CC="$ac_tool_prefix$ac_prog"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+CC=$ac_cv_prog_CC
+if test -n "$CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5
+$as_echo "$CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ test -n "$CC" && break
+ done
+fi
+if test -z "$CC"; then
+ ac_ct_CC=$CC
+ for ac_prog in cl.exe
+do
+ # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_CC+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$ac_ct_CC"; then
+ ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_ac_ct_CC="$ac_prog"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_CC=$ac_cv_prog_ac_ct_CC
+if test -n "$ac_ct_CC"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5
+$as_echo "$ac_ct_CC" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ test -n "$ac_ct_CC" && break
+done
+
+ if test "x$ac_ct_CC" = x; then
+ CC=""
+ else
+ case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+ CC=$ac_ct_CC
+ fi
+fi
+
+fi
+
+
+test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "no acceptable C compiler found in \$PATH
+See \`config.log' for more details" "$LINENO" 5; }
+
+# Provide some information about the compiler.
+$as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5
+set X $ac_compile
+ac_compiler=$2
+for ac_option in --version -v -V -qversion; do
+ { { ac_try="$ac_compiler $ac_option >&5"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_compiler $ac_option >&5") 2>conftest.err
+ ac_status=$?
+ if test -s conftest.err; then
+ sed '10a\
+... rest of stderr output deleted ...
+ 10q' conftest.err >conftest.er1
+ cat conftest.er1 >&5
+ fi
+ rm -f conftest.er1 conftest.err
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }
+done
+
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+ac_clean_files_save=$ac_clean_files
+ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out"
+# Try to create an executable without -o first, disregard a.out.
+# It will help us diagnose broken compilers, and finding out an intuition
+# of exeext.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler works" >&5
+$as_echo_n "checking whether the C compiler works... " >&6; }
+ac_link_default=`$as_echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'`
+
+# The possible output files:
+ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*"
+
+ac_rmfiles=
+for ac_file in $ac_files
+do
+ case $ac_file in
+ *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;
+ * ) ac_rmfiles="$ac_rmfiles $ac_file";;
+ esac
+done
+rm -f $ac_rmfiles
+
+if { { ac_try="$ac_link_default"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_link_default") 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }; then :
+ # Autoconf-2.13 could set the ac_cv_exeext variable to `no'.
+# So ignore a value of `no', otherwise this would lead to `EXEEXT = no'
+# in a Makefile. We should not override ac_cv_exeext if it was cached,
+# so that the user can short-circuit this test for compilers unknown to
+# Autoconf.
+for ac_file in $ac_files ''
+do
+ test -f "$ac_file" || continue
+ case $ac_file in
+ *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj )
+ ;;
+ [ab].out )
+ # We found the default executable, but exeext='' is most
+ # certainly right.
+ break;;
+ *.* )
+ if test "${ac_cv_exeext+set}" = set && test "$ac_cv_exeext" != no;
+ then :; else
+ ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'`
+ fi
+ # We set ac_cv_exeext here because the later test for it is not
+ # safe: cross compilers may not add the suffix if given an `-o'
+ # argument, so we may need to know it at that point already.
+ # Even if this section looks crufty: it has the advantage of
+ # actually working.
+ break;;
+ * )
+ break;;
+ esac
+done
+test "$ac_cv_exeext" = no && ac_cv_exeext=
+
+else
+ ac_file=''
+fi
+if test -z "$ac_file"; then :
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+$as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error 77 "C compiler cannot create executables
+See \`config.log' for more details" "$LINENO" 5; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name" >&5
+$as_echo_n "checking for C compiler default output file name... " >&6; }
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5
+$as_echo "$ac_file" >&6; }
+ac_exeext=$ac_cv_exeext
+
+rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out
+ac_clean_files=$ac_clean_files_save
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5
+$as_echo_n "checking for suffix of executables... " >&6; }
+if { { ac_try="$ac_link"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_link") 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }; then :
+ # If both `conftest.exe' and `conftest' are `present' (well, observable)
+# catch `conftest.exe'. For instance with Cygwin, `ls conftest' will
+# work properly (i.e., refer to `conftest.exe'), while it won't with
+# `rm'.
+for ac_file in conftest.exe conftest conftest.*; do
+ test -f "$ac_file" || continue
+ case $ac_file in
+ *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;
+ *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'`
+ break;;
+ * ) break;;
+ esac
+done
+else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot compute suffix of executables: cannot compile and link
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+rm -f conftest conftest$ac_cv_exeext
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5
+$as_echo "$ac_cv_exeext" >&6; }
+
+rm -f conftest.$ac_ext
+EXEEXT=$ac_cv_exeext
+ac_exeext=$EXEEXT
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+#include <stdio.h>
+int
+main ()
+{
+FILE *f = fopen ("conftest.out", "w");
+ return ferror (f) || fclose (f) != 0;
+
+ ;
+ return 0;
+}
+_ACEOF
+ac_clean_files="$ac_clean_files conftest.out"
+# Check that the compiler produces executables we can run. If not, either
+# the compiler is broken, or we cross compile.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5
+$as_echo_n "checking whether we are cross compiling... " >&6; }
+if test "$cross_compiling" != yes; then
+ { { ac_try="$ac_link"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_link") 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }
+ if { ac_try='./conftest$ac_cv_exeext'
+ { { case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_try") 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }; }; then
+ cross_compiling=no
+ else
+ if test "$cross_compiling" = maybe; then
+ cross_compiling=yes
+ else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot run C compiled programs.
+If you meant to cross compile, use \`--host'.
+See \`config.log' for more details" "$LINENO" 5; }
+ fi
+ fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5
+$as_echo "$cross_compiling" >&6; }
+
+rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out
+ac_clean_files=$ac_clean_files_save
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5
+$as_echo_n "checking for suffix of object files... " >&6; }
+if ${ac_cv_objext+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+rm -f conftest.o conftest.obj
+if { { ac_try="$ac_compile"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\""
+$as_echo "$ac_try_echo"; } >&5
+ (eval "$ac_compile") 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }; then :
+ for ac_file in conftest.o conftest.obj conftest.*; do
+ test -f "$ac_file" || continue;
+ case $ac_file in
+ *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;;
+ *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'`
+ break;;
+ esac
+done
+else
+ $as_echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "cannot compute suffix of object files: cannot compile
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+rm -f conftest.$ac_cv_objext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5
+$as_echo "$ac_cv_objext" >&6; }
+OBJEXT=$ac_cv_objext
+ac_objext=$OBJEXT
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5
+$as_echo_n "checking whether we are using the GNU C compiler... " >&6; }
+if ${ac_cv_c_compiler_gnu+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+#ifndef __GNUC__
+ choke me
+#endif
+
+ ;
+ return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+ ac_compiler_gnu=yes
+else
+ ac_compiler_gnu=no
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+ac_cv_c_compiler_gnu=$ac_compiler_gnu
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5
+$as_echo "$ac_cv_c_compiler_gnu" >&6; }
+if test $ac_compiler_gnu = yes; then
+ GCC=yes
+else
+ GCC=
+fi
+ac_test_CFLAGS=${CFLAGS+set}
+ac_save_CFLAGS=$CFLAGS
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5
+$as_echo_n "checking whether $CC accepts -g... " >&6; }
+if ${ac_cv_prog_cc_g+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ ac_save_c_werror_flag=$ac_c_werror_flag
+ ac_c_werror_flag=yes
+ ac_cv_prog_cc_g=no
+ CFLAGS="-g"
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+ ac_cv_prog_cc_g=yes
+else
+ CFLAGS=""
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+
+else
+ ac_c_werror_flag=$ac_save_c_werror_flag
+ CFLAGS="-g"
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+ ac_cv_prog_cc_g=yes
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+ ac_c_werror_flag=$ac_save_c_werror_flag
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5
+$as_echo "$ac_cv_prog_cc_g" >&6; }
+if test "$ac_test_CFLAGS" = set; then
+ CFLAGS=$ac_save_CFLAGS
+elif test $ac_cv_prog_cc_g = yes; then
+ if test "$GCC" = yes; then
+ CFLAGS="-g -O2"
+ else
+ CFLAGS="-g"
+ fi
+else
+ if test "$GCC" = yes; then
+ CFLAGS="-O2"
+ else
+ CFLAGS=
+ fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5
+$as_echo_n "checking for $CC option to accept ISO C89... " >&6; }
+if ${ac_cv_prog_cc_c89+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ ac_cv_prog_cc_c89=no
+ac_save_CC=$CC
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+#include <stdarg.h>
+#include <stdio.h>
+struct stat;
+/* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */
+struct buf { int x; };
+FILE * (*rcsopen) (struct buf *, struct stat *, int);
+static char *e (p, i)
+ char **p;
+ int i;
+{
+ return p[i];
+}
+static char *f (char * (*g) (char **, int), char **p, ...)
+{
+ char *s;
+ va_list v;
+ va_start (v,p);
+ s = g (p, va_arg (v,int));
+ va_end (v);
+ return s;
+}
+
+/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has
+ function prototypes and stuff, but not '\xHH' hex character constants.
+ These don't provoke an error unfortunately, instead are silently treated
+ as 'x'. The following induces an error, until -std is added to get
+ proper ANSI mode. Curiously '\x00'!='x' always comes out true, for an
+ array size at least. It's necessary to write '\x00'==0 to get something
+ that's true only with -std. */
+int osf4_cc_array ['\x00' == 0 ? 1 : -1];
+
+/* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters
+ inside strings and character constants. */
+#define FOO(x) 'x'
+int xlc6_cc_array[FOO(a) == 'x' ? 1 : -1];
+
+int test (int i, double x);
+struct s1 {int (*f) (int a);};
+struct s2 {int (*f) (double a);};
+int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int);
+int argc;
+char **argv;
+int
+main ()
+{
+return f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1];
+ ;
+ return 0;
+}
+_ACEOF
+for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std \
+ -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__"
+do
+ CC="$ac_save_CC $ac_arg"
+ if ac_fn_c_try_compile "$LINENO"; then :
+ ac_cv_prog_cc_c89=$ac_arg
+fi
+rm -f core conftest.err conftest.$ac_objext
+ test "x$ac_cv_prog_cc_c89" != "xno" && break
+done
+rm -f conftest.$ac_ext
+CC=$ac_save_CC
+
+fi
+# AC_CACHE_VAL
+case "x$ac_cv_prog_cc_c89" in
+ x)
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5
+$as_echo "none needed" >&6; } ;;
+ xno)
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5
+$as_echo "unsupported" >&6; } ;;
+ *)
+ CC="$CC $ac_cv_prog_cc_c89"
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5
+$as_echo "$ac_cv_prog_cc_c89" >&6; } ;;
+esac
+if test "x$ac_cv_prog_cc_c89" != xno; then :
+
+fi
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC understands -c and -o together" >&5
+$as_echo_n "checking whether $CC understands -c and -o together... " >&6; }
+if ${am_cv_prog_cc_c_o+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+ ;
+ return 0;
+}
+_ACEOF
+ # Make sure it works both with $CC and with simple cc.
+ # Following AC_PROG_CC_C_O, we do the test twice because some
+ # compilers refuse to overwrite an existing .o file with -o,
+ # though they will create one.
+ am_cv_prog_cc_c_o=yes
+ for am_i in 1 2; do
+ if { echo "$as_me:$LINENO: $CC -c conftest.$ac_ext -o conftest2.$ac_objext" >&5
+ ($CC -c conftest.$ac_ext -o conftest2.$ac_objext) >&5 2>&5
+ ac_status=$?
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); } \
+ && test -f conftest2.$ac_objext; then
+ : OK
+ else
+ am_cv_prog_cc_c_o=no
+ break
+ fi
+ done
+ rm -f core conftest*
+ unset am_i
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_prog_cc_c_o" >&5
+$as_echo "$am_cv_prog_cc_c_o" >&6; }
+if test "$am_cv_prog_cc_c_o" != yes; then
+ # Losing compiler, so override with the script.
+ # FIXME: It is wrong to rewrite CC.
+ # But if we don't then we get into trouble of one sort or another.
+ # A longer-term fix would be to have automake use am__CC in this case,
+ # and then we could set am__CC="\$(top_srcdir)/compile \$(CC)"
+ CC="$am_aux_dir/compile $CC"
+fi
+ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+DEPDIR="${am__leading_dot}deps"
+
+ac_config_commands="$ac_config_commands depfiles"
+
+
+am_make=${MAKE-make}
+cat > confinc << 'END'
+am__doit:
+ @echo this is the am__doit target
+.PHONY: am__doit
+END
+# If we don't find an include directive, just comment out the code.
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for style of include used by $am_make" >&5
+$as_echo_n "checking for style of include used by $am_make... " >&6; }
+am__include="#"
+am__quote=
+_am_result=none
+# First try GNU make style include.
+echo "include confinc" > confmf
+# Ignore all kinds of additional output from 'make'.
+case `$am_make -s -f confmf 2> /dev/null` in #(
+*the\ am__doit\ target*)
+ am__include=include
+ am__quote=
+ _am_result=GNU
+ ;;
+esac
+# Now try BSD make style include.
+if test "$am__include" = "#"; then
+ echo '.include "confinc"' > confmf
+ case `$am_make -s -f confmf 2> /dev/null` in #(
+ *the\ am__doit\ target*)
+ am__include=.include
+ am__quote="\""
+ _am_result=BSD
+ ;;
+ esac
+fi
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $_am_result" >&5
+$as_echo "$_am_result" >&6; }
+rm -f confinc confmf
+
+# Check whether --enable-dependency-tracking was given.
+if test "${enable_dependency_tracking+set}" = set; then :
+ enableval=$enable_dependency_tracking;
+fi
+
+if test "x$enable_dependency_tracking" != xno; then
+ am_depcomp="$ac_aux_dir/depcomp"
+ AMDEPBACKSLASH='\'
+ am__nodep='_no'
+fi
+ if test "x$enable_dependency_tracking" != xno; then
+ AMDEP_TRUE=
+ AMDEP_FALSE='#'
+else
+ AMDEP_TRUE='#'
+ AMDEP_FALSE=
+fi
+
+
+
+depcc="$CC" am_compiler_list=
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5
+$as_echo_n "checking dependency style of $depcc... " >&6; }
+if ${am_cv_CC_dependencies_compiler_type+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then
+ # We make a subdir and do the tests there. Otherwise we can end up
+ # making bogus files that we don't know about and never remove. For
+ # instance it was reported that on HP-UX the gcc test will end up
+ # making a dummy file named 'D' -- because '-MD' means "put the output
+ # in D".
+ rm -rf conftest.dir
+ mkdir conftest.dir
+ # Copy depcomp to subdir because otherwise we won't find it if we're
+ # using a relative directory.
+ cp "$am_depcomp" conftest.dir
+ cd conftest.dir
+ # We will build objects and dependencies in a subdirectory because
+ # it helps to detect inapplicable dependency modes. For instance
+ # both Tru64's cc and ICC support -MD to output dependencies as a
+ # side effect of compilation, but ICC will put the dependencies in
+ # the current directory while Tru64 will put them in the object
+ # directory.
+ mkdir sub
+
+ am_cv_CC_dependencies_compiler_type=none
+ if test "$am_compiler_list" = ""; then
+ am_compiler_list=`sed -n 's/^#*\([a-zA-Z0-9]*\))$/\1/p' < ./depcomp`
+ fi
+ am__universal=false
+ case " $depcc " in #(
+ *\ -arch\ *\ -arch\ *) am__universal=true ;;
+ esac
+
+ for depmode in $am_compiler_list; do
+ # Setup a source with many dependencies, because some compilers
+ # like to wrap large dependency lists on column 80 (with \), and
+ # we should not choose a depcomp mode which is confused by this.
+ #
+ # We need to recreate these files for each test, as the compiler may
+ # overwrite some of them when testing with obscure command lines.
+ # This happens at least with the AIX C compiler.
+ : > sub/conftest.c
+ for i in 1 2 3 4 5 6; do
+ echo '#include "conftst'$i'.h"' >> sub/conftest.c
+ # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with
+ # Solaris 10 /bin/sh.
+ echo '/* dummy */' > sub/conftst$i.h
+ done
+ echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf
+
+ # We check with '-c' and '-o' for the sake of the "dashmstdout"
+ # mode. It turns out that the SunPro C++ compiler does not properly
+ # handle '-M -o', and we need to detect this. Also, some Intel
+ # versions had trouble with output in subdirs.
+ am__obj=sub/conftest.${OBJEXT-o}
+ am__minus_obj="-o $am__obj"
+ case $depmode in
+ gcc)
+ # This depmode causes a compiler race in universal mode.
+ test "$am__universal" = false || continue
+ ;;
+ nosideeffect)
+ # After this tag, mechanisms are not by side-effect, so they'll
+ # only be used when explicitly requested.
+ if test "x$enable_dependency_tracking" = xyes; then
+ continue
+ else
+ break
+ fi
+ ;;
+ msvc7 | msvc7msys | msvisualcpp | msvcmsys)
+ # This compiler won't grok '-c -o', but also, the minuso test has
+ # not run yet. These depmodes are late enough in the game, and
+ # so weak that their functioning should not be impacted.
+ am__obj=conftest.${OBJEXT-o}
+ am__minus_obj=
+ ;;
+ none) break ;;
+ esac
+ if depmode=$depmode \
+ source=sub/conftest.c object=$am__obj \
+ depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \
+ $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \
+ >/dev/null 2>conftest.err &&
+ grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&
+ ${MAKE-make} -s -f confmf > /dev/null 2>&1; then
+ # icc doesn't choke on unknown options, it will just issue warnings
+ # or remarks (even with -Werror). So we grep stderr for any message
+ # that says an option was ignored or not supported.
+ # When given -MP, icc 7.0 and 7.1 complain thusly:
+ # icc: Command line warning: ignoring option '-M'; no argument required
+ # The diagnosis changed in icc 8.0:
+ # icc: Command line remark: option '-MP' not supported
+ if (grep 'ignoring option' conftest.err ||
+ grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else
+ am_cv_CC_dependencies_compiler_type=$depmode
+ break
+ fi
+ fi
+ done
+
+ cd ..
+ rm -rf conftest.dir
+else
+ am_cv_CC_dependencies_compiler_type=none
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_CC_dependencies_compiler_type" >&5
+$as_echo "$am_cv_CC_dependencies_compiler_type" >&6; }
+CCDEPMODE=depmode=$am_cv_CC_dependencies_compiler_type
+
+ if
+ test "x$enable_dependency_tracking" != xno \
+ && test "$am_cv_CC_dependencies_compiler_type" = gcc3; then
+ am__fastdepCC_TRUE=
+ am__fastdepCC_FALSE='#'
+else
+ am__fastdepCC_TRUE='#'
+ am__fastdepCC_FALSE=
+fi
+
+
+if test -n "$ac_tool_prefix"; then
+ # Extract the first word of "${ac_tool_prefix}ranlib", so it can be a program name with args.
+set dummy ${ac_tool_prefix}ranlib; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_RANLIB+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$RANLIB"; then
+ ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_RANLIB="${ac_tool_prefix}ranlib"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+RANLIB=$ac_cv_prog_RANLIB
+if test -n "$RANLIB"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $RANLIB" >&5
+$as_echo "$RANLIB" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+fi
+if test -z "$ac_cv_prog_RANLIB"; then
+ ac_ct_RANLIB=$RANLIB
+ # Extract the first word of "ranlib", so it can be a program name with args.
+set dummy ranlib; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_RANLIB+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$ac_ct_RANLIB"; then
+ ac_cv_prog_ac_ct_RANLIB="$ac_ct_RANLIB" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_ac_ct_RANLIB="ranlib"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_RANLIB=$ac_cv_prog_ac_ct_RANLIB
+if test -n "$ac_ct_RANLIB"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_RANLIB" >&5
+$as_echo "$ac_ct_RANLIB" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+ if test "x$ac_ct_RANLIB" = x; then
+ RANLIB=":"
+ else
+ case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+ RANLIB=$ac_ct_RANLIB
+ fi
+else
+ RANLIB="$ac_cv_prog_RANLIB"
+fi
+
+
+if test -n "$ac_tool_prefix"; then
+ for ac_prog in ar lib "link -lib"
+ do
+ # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args.
+set dummy $ac_tool_prefix$ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_AR+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$AR"; then
+ ac_cv_prog_AR="$AR" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_AR="$ac_tool_prefix$ac_prog"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+AR=$ac_cv_prog_AR
+if test -n "$AR"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AR" >&5
+$as_echo "$AR" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ test -n "$AR" && break
+ done
+fi
+if test -z "$AR"; then
+ ac_ct_AR=$AR
+ for ac_prog in ar lib "link -lib"
+do
+ # Extract the first word of "$ac_prog", so it can be a program name with args.
+set dummy $ac_prog; ac_word=$2
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
+$as_echo_n "checking for $ac_word... " >&6; }
+if ${ac_cv_prog_ac_ct_AR+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -n "$ac_ct_AR"; then
+ ac_cv_prog_ac_ct_AR="$ac_ct_AR" # Let the user override the test.
+else
+as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ for ac_exec_ext in '' $ac_executable_extensions; do
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
+ ac_cv_prog_ac_ct_AR="$ac_prog"
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
+ break 2
+ fi
+done
+ done
+IFS=$as_save_IFS
+
+fi
+fi
+ac_ct_AR=$ac_cv_prog_ac_ct_AR
+if test -n "$ac_ct_AR"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR" >&5
+$as_echo "$ac_ct_AR" >&6; }
+else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+fi
+
+
+ test -n "$ac_ct_AR" && break
+done
+
+ if test "x$ac_ct_AR" = x; then
+ AR="false"
+ else
+ case $cross_compiling:$ac_tool_warned in
+yes:)
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
+ac_tool_warned=yes ;;
+esac
+ AR=$ac_ct_AR
+ fi
+fi
+
+: ${AR=ar}
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking the archiver ($AR) interface" >&5
+$as_echo_n "checking the archiver ($AR) interface... " >&6; }
+if ${am_cv_ar_interface+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+ am_cv_ar_interface=ar
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+int some_variable = 0;
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+ am_ar_try='$AR cru libconftest.a conftest.$ac_objext >&5'
+ { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$am_ar_try\""; } >&5
+ (eval $am_ar_try) 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }
+ if test "$ac_status" -eq 0; then
+ am_cv_ar_interface=ar
+ else
+ am_ar_try='$AR -NOLOGO -OUT:conftest.lib conftest.$ac_objext >&5'
+ { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$am_ar_try\""; } >&5
+ (eval $am_ar_try) 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }
+ if test "$ac_status" -eq 0; then
+ am_cv_ar_interface=lib
+ else
+ am_cv_ar_interface=unknown
+ fi
+ fi
+ rm -f conftest.lib libconftest.a
+
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+ ac_ext=c
+ac_cpp='$CPP $CPPFLAGS'
+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'
+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'
+ac_compiler_gnu=$ac_cv_c_compiler_gnu
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_ar_interface" >&5
+$as_echo "$am_cv_ar_interface" >&6; }
+
+case $am_cv_ar_interface in
+ar)
+ ;;
+lib)
+ # Microsoft lib, so override with the ar-lib wrapper script.
+ # FIXME: It is wrong to rewrite AR.
+ # But if we don't then we get into trouble of one sort or another.
+ # A longer-term fix would be to have automake use am__AR in this case,
+ # and then we could set am__AR="$am_aux_dir/ar-lib \$(AR)" or something
+ # similar.
+ AR="$am_aux_dir/ar-lib $AR"
+ ;;
+unknown)
+ as_fn_error $? "could not determine $AR interface" "$LINENO" 5
+ ;;
+esac
+
+# By default we simply use the C compiler to build assembly code.
+
+test "${CCAS+set}" = set || CCAS=$CC
+test "${CCASFLAGS+set}" = set || CCASFLAGS=$CFLAGS
+
+
+
+depcc="$CCAS" am_compiler_list=
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5
+$as_echo_n "checking dependency style of $depcc... " >&6; }
+if ${am_cv_CCAS_dependencies_compiler_type+:} false; then :
+ $as_echo_n "(cached) " >&6
+else
+ if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then
+ # We make a subdir and do the tests there. Otherwise we can end up
+ # making bogus files that we don't know about and never remove. For
+ # instance it was reported that on HP-UX the gcc test will end up
+ # making a dummy file named 'D' -- because '-MD' means "put the output
+ # in D".
+ rm -rf conftest.dir
+ mkdir conftest.dir
+ # Copy depcomp to subdir because otherwise we won't find it if we're
+ # using a relative directory.
+ cp "$am_depcomp" conftest.dir
+ cd conftest.dir
+ # We will build objects and dependencies in a subdirectory because
+ # it helps to detect inapplicable dependency modes. For instance
+ # both Tru64's cc and ICC support -MD to output dependencies as a
+ # side effect of compilation, but ICC will put the dependencies in
+ # the current directory while Tru64 will put them in the object
+ # directory.
+ mkdir sub
+
+ am_cv_CCAS_dependencies_compiler_type=none
+ if test "$am_compiler_list" = ""; then
+ am_compiler_list=`sed -n 's/^#*\([a-zA-Z0-9]*\))$/\1/p' < ./depcomp`
+ fi
+ am__universal=false
+
+
+ for depmode in $am_compiler_list; do
+ # Setup a source with many dependencies, because some compilers
+ # like to wrap large dependency lists on column 80 (with \), and
+ # we should not choose a depcomp mode which is confused by this.
+ #
+ # We need to recreate these files for each test, as the compiler may
+ # overwrite some of them when testing with obscure command lines.
+ # This happens at least with the AIX C compiler.
+ : > sub/conftest.c
+ for i in 1 2 3 4 5 6; do
+ echo '#include "conftst'$i'.h"' >> sub/conftest.c
+ # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with
+ # Solaris 10 /bin/sh.
+ echo '/* dummy */' > sub/conftst$i.h
+ done
+ echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf
+
+ # We check with '-c' and '-o' for the sake of the "dashmstdout"
+ # mode. It turns out that the SunPro C++ compiler does not properly
+ # handle '-M -o', and we need to detect this. Also, some Intel
+ # versions had trouble with output in subdirs.
+ am__obj=sub/conftest.${OBJEXT-o}
+ am__minus_obj="-o $am__obj"
+ case $depmode in
+ gcc)
+ # This depmode causes a compiler race in universal mode.
+ test "$am__universal" = false || continue
+ ;;
+ nosideeffect)
+ # After this tag, mechanisms are not by side-effect, so they'll
+ # only be used when explicitly requested.
+ if test "x$enable_dependency_tracking" = xyes; then
+ continue
+ else
+ break
+ fi
+ ;;
+ msvc7 | msvc7msys | msvisualcpp | msvcmsys)
+ # This compiler won't grok '-c -o', but also, the minuso test has
+ # not run yet. These depmodes are late enough in the game, and
+ # so weak that their functioning should not be impacted.
+ am__obj=conftest.${OBJEXT-o}
+ am__minus_obj=
+ ;;
+ none) break ;;
+ esac
+ if depmode=$depmode \
+ source=sub/conftest.c object=$am__obj \
+ depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \
+ $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \
+ >/dev/null 2>conftest.err &&
+ grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&
+ grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&
+ ${MAKE-make} -s -f confmf > /dev/null 2>&1; then
+ # icc doesn't choke on unknown options, it will just issue warnings
+ # or remarks (even with -Werror). So we grep stderr for any message
+ # that says an option was ignored or not supported.
+ # When given -MP, icc 7.0 and 7.1 complain thusly:
+ # icc: Command line warning: ignoring option '-M'; no argument required
+ # The diagnosis changed in icc 8.0:
+ # icc: Command line remark: option '-MP' not supported
+ if (grep 'ignoring option' conftest.err ||
+ grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else
+ am_cv_CCAS_dependencies_compiler_type=$depmode
+ break
+ fi
+ fi
+ done
+
+ cd ..
+ rm -rf conftest.dir
+else
+ am_cv_CCAS_dependencies_compiler_type=none
+fi
+
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_CCAS_dependencies_compiler_type" >&5
+$as_echo "$am_cv_CCAS_dependencies_compiler_type" >&6; }
+CCASDEPMODE=depmode=$am_cv_CCAS_dependencies_compiler_type
+
+ if
+ test "x$enable_dependency_tracking" != xno \
+ && test "$am_cv_CCAS_dependencies_compiler_type" = gcc3; then
+ am__fastdepCCAS_TRUE=
+ am__fastdepCCAS_FALSE='#'
+else
+ am__fastdepCCAS_TRUE='#'
+ am__fastdepCCAS_FALSE=
+fi
+
+
+
+# autoconf tries very hard to avoid failing, so it'll even go ahead and try to
+# build the project using "gcc" if it can't find a suitable C compiler prefixed
+# by the host system. This doesn't work when cross compiling, but it's a
+# common error for users so we explicitly check for this right here to quickly
+# provide an error message.
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+int
+main ()
+{
+
+#ifndef __riscv
+# error "A RISC-V compiler is required to build Freedom Metal"
+#endif
+
+ ;
+ return 0;
+}
+_ACEOF
+if ac_fn_c_try_compile "$LINENO"; then :
+
+else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "The C compiler doesn't define __riscv, which means it's probably not a RISC-V compiler. You should specify something like --host=riscv64-sifive-elf when building this, as it will only work on RISC-V systems.
+See \`config.log' for more details" "$LINENO" 5; }
+fi
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
+########################################################
+# Options
+########################################################
+
+
+# Check whether --with-builtin-libgloss was given.
+if test "${with_builtin_libgloss+set}" = set; then :
+ withval=$with_builtin_libgloss; with_builtin_libgloss="yes"
+else
+ with_builtin_libgloss="no"
+
+fi
+
+
+
+# Check whether --with-builtin-libmetal-pico was given.
+if test "${with_builtin_libmetal_pico+set}" = set; then :
+ withval=$with_builtin_libmetal_pico; with_builtin_libmetal_pico="yes"
+else
+ with_builtin_libmetal_pico="no"
+
+fi
+
+
+
+# Check whether --with-builtin-libmetal-segger was given.
+if test "${with_builtin_libmetal_segger+set}" = set; then :
+ withval=$with_builtin_libmetal_segger; with_builtin_libmetal_segger="yes"
+else
+ with_builtin_libmetal_segger="no"
+
+fi
+
+
+
+# Check whether --with-machine-header was given.
+if test "${with_machine_header+set}" = set; then :
+ withval=$with_machine_header;
+else
+ with_machine_header="no"
+
+fi
+
+
+
+# Check whether --with-machine-inline was given.
+if test "${with_machine_inline+set}" = set; then :
+ withval=$with_machine_inline;
+else
+ with_machine_inline="no"
+
+fi
+
+
+
+# Check whether --with-platform-header was given.
+if test "${with_platform_header+set}" = set; then :
+ withval=$with_platform_header;
+else
+ with_platform_header="no"
+
+fi
+
+
+########################################################
+# Process Options
+########################################################
+
+ if test "x$with_builtin_libgloss" = "xyes"; then
+ WITH_BUILTIN_LIBGLOSS_TRUE=
+ WITH_BUILTIN_LIBGLOSS_FALSE='#'
+else
+ WITH_BUILTIN_LIBGLOSS_TRUE='#'
+ WITH_BUILTIN_LIBGLOSS_FALSE=
+fi
+
+
+ if test "x$with_builtin_libmetal_pico" = "xyes"; then
+ WITH_BUILTIN_LIBMETAL_PICO_TRUE=
+ WITH_BUILTIN_LIBMETAL_PICO_FALSE='#'
+else
+ WITH_BUILTIN_LIBMETAL_PICO_TRUE='#'
+ WITH_BUILTIN_LIBMETAL_PICO_FALSE=
+fi
+
+
+ if test "x$with_builtin_libmetal_segger" = "xyes"; then
+ WITH_BUILTIN_LIBMETAL_SEGGER_TRUE=
+ WITH_BUILTIN_LIBMETAL_SEGGER_FALSE='#'
+else
+ WITH_BUILTIN_LIBMETAL_SEGGER_TRUE='#'
+ WITH_BUILTIN_LIBMETAL_SEGGER_FALSE=
+fi
+
+
+# Configure the build system to pass in the preconfigured machine support files
+if test "x$with_machine_header" != "xno"; then :
+ MACHINE_HEADER="$with_machine_header"
+
+else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "--with-machine-header is required
+See \`config.log' for more details" "$LINENO" 5; }
+
+fi
+
+if test "x$with_machine_inline" != "xno"; then :
+ MACHINE_INLINE="$with_machine_inline"
+
+else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "--with-machine-inline is required
+See \`config.log' for more details" "$LINENO" 5; }
+
+fi
+
+if test "x$with_platform_header" != "xno"; then :
+ PLATFORM_HEADER="$with_platform_header"
+
+else
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
+as_fn_error $? "--with-platform-header is required
+See \`config.log' for more details" "$LINENO" 5; }
+
+fi
+
+# Generates the remainder of the build system.
+ac_config_files="$ac_config_files Makefile"
+
+cat >confcache <<\_ACEOF
+# This file is a shell script that caches the results of configure
+# tests run on this system so they can be shared between configure
+# scripts and configure runs, see configure's option --config-cache.
+# It is not useful on other systems. If it contains results you don't
+# want to keep, you may remove or edit it.
+#
+# config.status only pays attention to the cache file if you give it
+# the --recheck option to rerun configure.
+#
+# `ac_cv_env_foo' variables (set or unset) will be overridden when
+# loading this file, other *unset* `ac_cv_foo' will be assigned the
+# following values.
+
+_ACEOF
+
+# The following way of writing the cache mishandles newlines in values,
+# but we know of no workaround that is simple, portable, and efficient.
+# So, we kill variables containing newlines.
+# Ultrix sh set writes to stderr and can't be redirected directly,
+# and sets the high bit in the cache file unless we assign to the vars.
+(
+ for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do
+ eval ac_val=\$$ac_var
+ case $ac_val in #(
+ *${as_nl}*)
+ case $ac_var in #(
+ *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5
+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;
+ esac
+ case $ac_var in #(
+ _ | IFS | as_nl) ;; #(
+ BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(
+ *) { eval $ac_var=; unset $ac_var;} ;;
+ esac ;;
+ esac
+ done
+
+ (set) 2>&1 |
+ case $as_nl`(ac_space=' '; set) 2>&1` in #(
+ *${as_nl}ac_space=\ *)
+ # `set' does not quote correctly, so add quotes: double-quote
+ # substitution turns \\\\ into \\, and sed turns \\ into \.
+ sed -n \
+ "s/'/'\\\\''/g;
+ s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p"
+ ;; #(
+ *)
+ # `set' quotes correctly as required by POSIX, so do not add quotes.
+ sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"
+ ;;
+ esac |
+ sort
+) |
+ sed '
+ /^ac_cv_env_/b end
+ t clear
+ :clear
+ s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/
+ t end
+ s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/
+ :end' >>confcache
+if diff "$cache_file" confcache >/dev/null 2>&1; then :; else
+ if test -w "$cache_file"; then
+ if test "x$cache_file" != "x/dev/null"; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5
+$as_echo "$as_me: updating cache $cache_file" >&6;}
+ if test ! -f "$cache_file" || test -h "$cache_file"; then
+ cat confcache >"$cache_file"
+ else
+ case $cache_file in #(
+ */* | ?:*)
+ mv -f confcache "$cache_file"$$ &&
+ mv -f "$cache_file"$$ "$cache_file" ;; #(
+ *)
+ mv -f confcache "$cache_file" ;;
+ esac
+ fi
+ fi
+ else
+ { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5
+$as_echo "$as_me: not updating unwritable cache $cache_file" >&6;}
+ fi
+fi
+rm -f confcache
+
+test "x$prefix" = xNONE && prefix=$ac_default_prefix
+# Let make expand exec_prefix.
+test "x$exec_prefix" = xNONE && exec_prefix='${prefix}'
+
+# Transform confdefs.h into DEFS.
+# Protect against shell expansion while executing Makefile rules.
+# Protect against Makefile macro expansion.
+#
+# If the first sed substitution is executed (which looks for macros that
+# take arguments), then branch to the quote section. Otherwise,
+# look for a macro that doesn't take arguments.
+ac_script='
+:mline
+/\\$/{
+ N
+ s,\\\n,,
+ b mline
+}
+t clear
+:clear
+s/^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*([^)]*)\)[ ]*\(.*\)/-D\1=\2/g
+t quote
+s/^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)/-D\1=\2/g
+t quote
+b any
+:quote
+s/[ `~#$^&*(){}\\|;'\''"<>?]/\\&/g
+s/\[/\\&/g
+s/\]/\\&/g
+s/\$/$$/g
+H
+:any
+${
+ g
+ s/^\n//
+ s/\n/ /g
+ p
+}
+'
+DEFS=`sed -n "$ac_script" confdefs.h`
+
+
+ac_libobjs=
+ac_ltlibobjs=
+U=
+for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue
+ # 1. Remove the extension, and $U if already installed.
+ ac_script='s/\$U\././;s/\.o$//;s/\.obj$//'
+ ac_i=`$as_echo "$ac_i" | sed "$ac_script"`
+ # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR
+ # will be set to the directory where LIBOBJS objects are built.
+ as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext"
+ as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo'
+done
+LIBOBJS=$ac_libobjs
+
+LTLIBOBJS=$ac_ltlibobjs
+
+
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking that generated files are newer than configure" >&5
+$as_echo_n "checking that generated files are newer than configure... " >&6; }
+ if test -n "$am_sleep_pid"; then
+ # Hide warnings about reused PIDs.
+ wait $am_sleep_pid 2>/dev/null
+ fi
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: done" >&5
+$as_echo "done" >&6; }
+ if test -n "$EXEEXT"; then
+ am__EXEEXT_TRUE=
+ am__EXEEXT_FALSE='#'
+else
+ am__EXEEXT_TRUE='#'
+ am__EXEEXT_FALSE=
+fi
+
+if test -z "${MAINTAINER_MODE_TRUE}" && test -z "${MAINTAINER_MODE_FALSE}"; then
+ as_fn_error $? "conditional \"MAINTAINER_MODE\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${AMDEP_TRUE}" && test -z "${AMDEP_FALSE}"; then
+ as_fn_error $? "conditional \"AMDEP\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${am__fastdepCC_TRUE}" && test -z "${am__fastdepCC_FALSE}"; then
+ as_fn_error $? "conditional \"am__fastdepCC\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${am__fastdepCCAS_TRUE}" && test -z "${am__fastdepCCAS_FALSE}"; then
+ as_fn_error $? "conditional \"am__fastdepCCAS\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${WITH_BUILTIN_LIBGLOSS_TRUE}" && test -z "${WITH_BUILTIN_LIBGLOSS_FALSE}"; then
+ as_fn_error $? "conditional \"WITH_BUILTIN_LIBGLOSS\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${WITH_BUILTIN_LIBMETAL_PICO_TRUE}" && test -z "${WITH_BUILTIN_LIBMETAL_PICO_FALSE}"; then
+ as_fn_error $? "conditional \"WITH_BUILTIN_LIBMETAL_PICO\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+if test -z "${WITH_BUILTIN_LIBMETAL_SEGGER_TRUE}" && test -z "${WITH_BUILTIN_LIBMETAL_SEGGER_FALSE}"; then
+ as_fn_error $? "conditional \"WITH_BUILTIN_LIBMETAL_SEGGER\" was never defined.
+Usually this means the macro was only invoked conditionally." "$LINENO" 5
+fi
+
+: "${CONFIG_STATUS=./config.status}"
+ac_write_fail=0
+ac_clean_files_save=$ac_clean_files
+ac_clean_files="$ac_clean_files $CONFIG_STATUS"
+{ $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5
+$as_echo "$as_me: creating $CONFIG_STATUS" >&6;}
+as_write_fail=0
+cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1
+#! $SHELL
+# Generated by $as_me.
+# Run this file to recreate the current configuration.
+# Compiler output produced by configure, useful for debugging
+# configure, is in config.log if it exists.
+
+debug=false
+ac_cs_recheck=false
+ac_cs_silent=false
+
+SHELL=\${CONFIG_SHELL-$SHELL}
+export SHELL
+_ASEOF
+cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1
+## -------------------- ##
+## M4sh Initialization. ##
+## -------------------- ##
+
+# Be more Bourne compatible
+DUALCASE=1; export DUALCASE # for MKS sh
+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :
+ emulate sh
+ NULLCMD=:
+ # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which
+ # is contrary to our usage. Disable this feature.
+ alias -g '${1+"$@"}'='"$@"'
+ setopt NO_GLOB_SUBST
+else
+ case `(set -o) 2>/dev/null` in #(
+ *posix*) :
+ set -o posix ;; #(
+ *) :
+ ;;
+esac
+fi
+
+
+as_nl='
+'
+export as_nl
+# Printing a long string crashes Solaris 7 /usr/bin/printf.
+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo
+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo
+# Prefer a ksh shell builtin over an external printf program on Solaris,
+# but without wasting forks for bash or zsh.
+if test -z "$BASH_VERSION$ZSH_VERSION" \
+ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then
+ as_echo='print -r --'
+ as_echo_n='print -rn --'
+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then
+ as_echo='printf %s\n'
+ as_echo_n='printf %s'
+else
+ if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then
+ as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'
+ as_echo_n='/usr/ucb/echo -n'
+ else
+ as_echo_body='eval expr "X$1" : "X\\(.*\\)"'
+ as_echo_n_body='eval
+ arg=$1;
+ case $arg in #(
+ *"$as_nl"*)
+ expr "X$arg" : "X\\(.*\\)$as_nl";
+ arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;
+ esac;
+ expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"
+ '
+ export as_echo_n_body
+ as_echo_n='sh -c $as_echo_n_body as_echo'
+ fi
+ export as_echo_body
+ as_echo='sh -c $as_echo_body as_echo'
+fi
+
+# The user is always right.
+if test "${PATH_SEPARATOR+set}" != set; then
+ PATH_SEPARATOR=:
+ (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {
+ (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||
+ PATH_SEPARATOR=';'
+ }
+fi
+
+
+# IFS
+# We need space, tab and new line, in precisely that order. Quoting is
+# there to prevent editors from complaining about space-tab.
+# (If _AS_PATH_WALK were called with IFS unset, it would disable word
+# splitting by setting IFS to empty value.)
+IFS=" "" $as_nl"
+
+# Find who we are. Look in the path if we contain no directory separator.
+as_myself=
+case $0 in #((
+ *[\\/]* ) as_myself=$0 ;;
+ *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
+for as_dir in $PATH
+do
+ IFS=$as_save_IFS
+ test -z "$as_dir" && as_dir=.
+ test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break
+ done
+IFS=$as_save_IFS
+
+ ;;
+esac
+# We did not find ourselves, most probably we were run as `sh COMMAND'
+# in which case we are not to be found in the path.
+if test "x$as_myself" = x; then
+ as_myself=$0
+fi
+if test ! -f "$as_myself"; then
+ $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2
+ exit 1
+fi
+
+# Unset variables that we do not need and which cause bugs (e.g. in
+# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1"
+# suppresses any "Segmentation fault" message there. '((' could
+# trigger a bug in pdksh 5.2.14.
+for as_var in BASH_ENV ENV MAIL MAILPATH
+do eval test x\${$as_var+set} = xset \
+ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :
+done
+PS1='$ '
+PS2='> '
+PS4='+ '
+
+# NLS nuisances.
+LC_ALL=C
+export LC_ALL
+LANGUAGE=C
+export LANGUAGE
+
+# CDPATH.
+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH
+
+
+# as_fn_error STATUS ERROR [LINENO LOG_FD]
+# ----------------------------------------
+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are
+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the
+# script with STATUS, using 1 if that was 0.
+as_fn_error ()
+{
+ as_status=$1; test $as_status -eq 0 && as_status=1
+ if test "$4"; then
+ as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
+ $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4
+ fi
+ $as_echo "$as_me: error: $2" >&2
+ as_fn_exit $as_status
+} # as_fn_error
+
+
+# as_fn_set_status STATUS
+# -----------------------
+# Set $? to STATUS, without forking.
+as_fn_set_status ()
+{
+ return $1
+} # as_fn_set_status
+
+# as_fn_exit STATUS
+# -----------------
+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.
+as_fn_exit ()
+{
+ set +e
+ as_fn_set_status $1
+ exit $1
+} # as_fn_exit
+
+# as_fn_unset VAR
+# ---------------
+# Portably unset VAR.
+as_fn_unset ()
+{
+ { eval $1=; unset $1;}
+}
+as_unset=as_fn_unset
+# as_fn_append VAR VALUE
+# ----------------------
+# Append the text in VALUE to the end of the definition contained in VAR. Take
+# advantage of any shell optimizations that allow amortized linear growth over
+# repeated appends, instead of the typical quadratic growth present in naive
+# implementations.
+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :
+ eval 'as_fn_append ()
+ {
+ eval $1+=\$2
+ }'
+else
+ as_fn_append ()
+ {
+ eval $1=\$$1\$2
+ }
+fi # as_fn_append
+
+# as_fn_arith ARG...
+# ------------------
+# Perform arithmetic evaluation on the ARGs, and store the result in the
+# global $as_val. Take advantage of shells that can avoid forks. The arguments
+# must be portable across $(()) and expr.
+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :
+ eval 'as_fn_arith ()
+ {
+ as_val=$(( $* ))
+ }'
+else
+ as_fn_arith ()
+ {
+ as_val=`expr "$@" || test $? -eq 1`
+ }
+fi # as_fn_arith
+
+
+if expr a : '\(a\)' >/dev/null 2>&1 &&
+ test "X`expr 00001 : '.*\(...\)'`" = X001; then
+ as_expr=expr
+else
+ as_expr=false
+fi
+
+if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then
+ as_basename=basename
+else
+ as_basename=false
+fi
+
+if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then
+ as_dirname=dirname
+else
+ as_dirname=false
+fi
+
+as_me=`$as_basename -- "$0" ||
+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \
+ X"$0" : 'X\(//\)$' \| \
+ X"$0" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X/"$0" |
+ sed '/^.*\/\([^/][^/]*\)\/*$/{
+ s//\1/
+ q
+ }
+ /^X\/\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\/\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+
+# Avoid depending upon Character Ranges.
+as_cr_letters='abcdefghijklmnopqrstuvwxyz'
+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'
+as_cr_Letters=$as_cr_letters$as_cr_LETTERS
+as_cr_digits='0123456789'
+as_cr_alnum=$as_cr_Letters$as_cr_digits
+
+ECHO_C= ECHO_N= ECHO_T=
+case `echo -n x` in #(((((
+-n*)
+ case `echo 'xy\c'` in
+ *c*) ECHO_T=' ';; # ECHO_T is single tab character.
+ xy) ECHO_C='\c';;
+ *) echo `echo ksh88 bug on AIX 6.1` > /dev/null
+ ECHO_T=' ';;
+ esac;;
+*)
+ ECHO_N='-n';;
+esac
+
+rm -f conf$$ conf$$.exe conf$$.file
+if test -d conf$$.dir; then
+ rm -f conf$$.dir/conf$$.file
+else
+ rm -f conf$$.dir
+ mkdir conf$$.dir 2>/dev/null
+fi
+if (echo >conf$$.file) 2>/dev/null; then
+ if ln -s conf$$.file conf$$ 2>/dev/null; then
+ as_ln_s='ln -s'
+ # ... but there are two gotchas:
+ # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.
+ # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.
+ # In both cases, we have to default to `cp -pR'.
+ ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||
+ as_ln_s='cp -pR'
+ elif ln conf$$.file conf$$ 2>/dev/null; then
+ as_ln_s=ln
+ else
+ as_ln_s='cp -pR'
+ fi
+else
+ as_ln_s='cp -pR'
+fi
+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file
+rmdir conf$$.dir 2>/dev/null
+
+
+# as_fn_mkdir_p
+# -------------
+# Create "$as_dir" as a directory, including parents if necessary.
+as_fn_mkdir_p ()
+{
+
+ case $as_dir in #(
+ -*) as_dir=./$as_dir;;
+ esac
+ test -d "$as_dir" || eval $as_mkdir_p || {
+ as_dirs=
+ while :; do
+ case $as_dir in #(
+ *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(
+ *) as_qdir=$as_dir;;
+ esac
+ as_dirs="'$as_qdir' $as_dirs"
+ as_dir=`$as_dirname -- "$as_dir" ||
+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$as_dir" : 'X\(//\)[^/]' \| \
+ X"$as_dir" : 'X\(//\)$' \| \
+ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$as_dir" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ test -d "$as_dir" && break
+ done
+ test -z "$as_dirs" || eval "mkdir $as_dirs"
+ } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"
+
+
+} # as_fn_mkdir_p
+if mkdir -p . 2>/dev/null; then
+ as_mkdir_p='mkdir -p "$as_dir"'
+else
+ test -d ./-p && rmdir ./-p
+ as_mkdir_p=false
+fi
+
+
+# as_fn_executable_p FILE
+# -----------------------
+# Test if FILE is an executable regular file.
+as_fn_executable_p ()
+{
+ test -f "$1" && test -x "$1"
+} # as_fn_executable_p
+as_test_x='test -x'
+as_executable_p=as_fn_executable_p
+
+# Sed expression to map a string onto a valid CPP name.
+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"
+
+# Sed expression to map a string onto a valid variable name.
+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"
+
+
+exec 6>&1
+## ----------------------------------- ##
+## Main body of $CONFIG_STATUS script. ##
+## ----------------------------------- ##
+_ASEOF
+test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# Save the log message, to keep $0 and so on meaningful, and to
+# report actual input values of CONFIG_FILES etc. instead of their
+# values after options handling.
+ac_log="
+This file was extended by freedom-metal $as_me v0.1.2, which was
+generated by GNU Autoconf 2.69. Invocation command line was
+
+ CONFIG_FILES = $CONFIG_FILES
+ CONFIG_HEADERS = $CONFIG_HEADERS
+ CONFIG_LINKS = $CONFIG_LINKS
+ CONFIG_COMMANDS = $CONFIG_COMMANDS
+ $ $0 $@
+
+on `(hostname || uname -n) 2>/dev/null | sed 1q`
+"
+
+_ACEOF
+
+case $ac_config_files in *"
+"*) set x $ac_config_files; shift; ac_config_files=$*;;
+esac
+
+
+
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+# Files that config.status was made for.
+config_files="$ac_config_files"
+config_commands="$ac_config_commands"
+
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+ac_cs_usage="\
+\`$as_me' instantiates files and other configuration actions
+from templates according to the current configuration. Unless the files
+and actions are specified as TAGs, all are instantiated by default.
+
+Usage: $0 [OPTION]... [TAG]...
+
+ -h, --help print this help, then exit
+ -V, --version print version number and configuration settings, then exit
+ --config print configuration, then exit
+ -q, --quiet, --silent
+ do not print progress messages
+ -d, --debug don't remove temporary files
+ --recheck update $as_me by reconfiguring in the same conditions
+ --file=FILE[:TEMPLATE]
+ instantiate the configuration file FILE
+
+Configuration files:
+$config_files
+
+Configuration commands:
+$config_commands
+
+Report bugs to <https://github.com/sifive/freedom-metal/issues>.
+freedom-metal home page: <https://github.com/sifive/freedom-metal>."
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
+ac_cs_version="\\
+freedom-metal config.status v0.1.2
+configured by $0, generated by GNU Autoconf 2.69,
+ with options \\"\$ac_cs_config\\"
+
+Copyright (C) 2012 Free Software Foundation, Inc.
+This config.status script is free software; the Free Software Foundation
+gives unlimited permission to copy, distribute and modify it."
+
+ac_pwd='$ac_pwd'
+srcdir='$srcdir'
+INSTALL='$INSTALL'
+MKDIR_P='$MKDIR_P'
+AWK='$AWK'
+test -n "\$AWK" || AWK=awk
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# The default lists apply if the user does not specify any file.
+ac_need_defaults=:
+while test $# != 0
+do
+ case $1 in
+ --*=?*)
+ ac_option=`expr "X$1" : 'X\([^=]*\)='`
+ ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'`
+ ac_shift=:
+ ;;
+ --*=)
+ ac_option=`expr "X$1" : 'X\([^=]*\)='`
+ ac_optarg=
+ ac_shift=:
+ ;;
+ *)
+ ac_option=$1
+ ac_optarg=$2
+ ac_shift=shift
+ ;;
+ esac
+
+ case $ac_option in
+ # Handling of the options.
+ -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r)
+ ac_cs_recheck=: ;;
+ --version | --versio | --versi | --vers | --ver | --ve | --v | -V )
+ $as_echo "$ac_cs_version"; exit ;;
+ --config | --confi | --conf | --con | --co | --c )
+ $as_echo "$ac_cs_config"; exit ;;
+ --debug | --debu | --deb | --de | --d | -d )
+ debug=: ;;
+ --file | --fil | --fi | --f )
+ $ac_shift
+ case $ac_optarg in
+ *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;;
+ '') as_fn_error $? "missing file argument" ;;
+ esac
+ as_fn_append CONFIG_FILES " '$ac_optarg'"
+ ac_need_defaults=false;;
+ --he | --h | --help | --hel | -h )
+ $as_echo "$ac_cs_usage"; exit ;;
+ -q | -quiet | --quiet | --quie | --qui | --qu | --q \
+ | -silent | --silent | --silen | --sile | --sil | --si | --s)
+ ac_cs_silent=: ;;
+
+ # This is an error.
+ -*) as_fn_error $? "unrecognized option: \`$1'
+Try \`$0 --help' for more information." ;;
+
+ *) as_fn_append ac_config_targets " $1"
+ ac_need_defaults=false ;;
+
+ esac
+ shift
+done
+
+ac_configure_extra_args=
+
+if $ac_cs_silent; then
+ exec 6>/dev/null
+ ac_configure_extra_args="$ac_configure_extra_args --silent"
+fi
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+if \$ac_cs_recheck; then
+ set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion
+ shift
+ \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6
+ CONFIG_SHELL='$SHELL'
+ export CONFIG_SHELL
+ exec "\$@"
+fi
+
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+exec 5>>config.log
+{
+ echo
+ sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX
+## Running $as_me. ##
+_ASBOX
+ $as_echo "$ac_log"
+} >&5
+
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+#
+# INIT-COMMANDS
+#
+AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir"
+
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+
+# Handling of arguments.
+for ac_config_target in $ac_config_targets
+do
+ case $ac_config_target in
+ "depfiles") CONFIG_COMMANDS="$CONFIG_COMMANDS depfiles" ;;
+ "Makefile") CONFIG_FILES="$CONFIG_FILES Makefile" ;;
+
+ *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;;
+ esac
+done
+
+
+# If the user did not use the arguments to specify the items to instantiate,
+# then the envvar interface is used. Set only those that are not.
+# We use the long form for the default assignment because of an extremely
+# bizarre bug on SunOS 4.1.3.
+if $ac_need_defaults; then
+ test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files
+ test "${CONFIG_COMMANDS+set}" = set || CONFIG_COMMANDS=$config_commands
+fi
+
+# Have a temporary directory for convenience. Make it in the build tree
+# simply because there is no reason against having it here, and in addition,
+# creating and moving files from /tmp can sometimes cause problems.
+# Hook for its removal unless debugging.
+# Note that there is a small window in which the directory will not be cleaned:
+# after its creation but before its name has been assigned to `$tmp'.
+$debug ||
+{
+ tmp= ac_tmp=
+ trap 'exit_status=$?
+ : "${ac_tmp:=$tmp}"
+ { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status
+' 0
+ trap 'as_fn_exit 1' 1 2 13 15
+}
+# Create a (secure) tmp directory for tmp files.
+
+{
+ tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` &&
+ test -d "$tmp"
+} ||
+{
+ tmp=./conf$$-$RANDOM
+ (umask 077 && mkdir "$tmp")
+} || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5
+ac_tmp=$tmp
+
+# Set up the scripts for CONFIG_FILES section.
+# No need to generate them if there are no CONFIG_FILES.
+# This happens for instance with `./config.status config.h'.
+if test -n "$CONFIG_FILES"; then
+
+
+ac_cr=`echo X | tr X '\015'`
+# On cygwin, bash can eat \r inside `` if the user requested igncr.
+# But we know of no other shell where ac_cr would be empty at this
+# point, so we can use a bashism as a fallback.
+if test "x$ac_cr" = x; then
+ eval ac_cr=\$\'\\r\'
+fi
+ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' </dev/null 2>/dev/null`
+if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then
+ ac_cs_awk_cr='\\r'
+else
+ ac_cs_awk_cr=$ac_cr
+fi
+
+echo 'BEGIN {' >"$ac_tmp/subs1.awk" &&
+_ACEOF
+
+
+{
+ echo "cat >conf$$subs.awk <<_ACEOF" &&
+ echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' &&
+ echo "_ACEOF"
+} >conf$$subs.sh ||
+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'`
+ac_delim='%!_!# '
+for ac_last_try in false false false false false :; do
+ . ./conf$$subs.sh ||
+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+
+ ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X`
+ if test $ac_delim_n = $ac_delim_num; then
+ break
+ elif $ac_last_try; then
+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5
+ else
+ ac_delim="$ac_delim!$ac_delim _$ac_delim!! "
+ fi
+done
+rm -f conf$$subs.sh
+
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK &&
+_ACEOF
+sed -n '
+h
+s/^/S["/; s/!.*/"]=/
+p
+g
+s/^[^!]*!//
+:repl
+t repl
+s/'"$ac_delim"'$//
+t delim
+:nl
+h
+s/\(.\{148\}\)..*/\1/
+t more1
+s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/
+p
+n
+b repl
+:more1
+s/["\\]/\\&/g; s/^/"/; s/$/"\\/
+p
+g
+s/.\{148\}//
+t nl
+:delim
+h
+s/\(.\{148\}\)..*/\1/
+t more2
+s/["\\]/\\&/g; s/^/"/; s/$/"/
+p
+b
+:more2
+s/["\\]/\\&/g; s/^/"/; s/$/"\\/
+p
+g
+s/.\{148\}//
+t delim
+' <conf$$subs.awk | sed '
+/^[^""]/{
+ N
+ s/\n//
+}
+' >>$CONFIG_STATUS || ac_write_fail=1
+rm -f conf$$subs.awk
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+_ACAWK
+cat >>"\$ac_tmp/subs1.awk" <<_ACAWK &&
+ for (key in S) S_is_set[key] = 1
+ FS = ""
+
+}
+{
+ line = $ 0
+ nfields = split(line, field, "@")
+ substed = 0
+ len = length(field[1])
+ for (i = 2; i < nfields; i++) {
+ key = field[i]
+ keylen = length(key)
+ if (S_is_set[key]) {
+ value = S[key]
+ line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3)
+ len += length(value) + length(field[++i])
+ substed = 1
+ } else
+ len += 1 + keylen
+ }
+
+ print line
+}
+
+_ACAWK
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then
+ sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g"
+else
+ cat
+fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \
+ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5
+_ACEOF
+
+# VPATH may cause trouble with some makes, so we remove sole $(srcdir),
+# ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and
+# trailing colons and then remove the whole line if VPATH becomes empty
+# (actually we leave an empty line to preserve line numbers).
+if test "x$srcdir" = x.; then
+ ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{
+h
+s///
+s/^/:/
+s/[ ]*$/:/
+s/:\$(srcdir):/:/g
+s/:\${srcdir}:/:/g
+s/:@srcdir@:/:/g
+s/^:*//
+s/:*$//
+x
+s/\(=[ ]*\).*/\1/
+G
+s/\n//
+s/^[^=]*=[ ]*$//
+}'
+fi
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+fi # test -n "$CONFIG_FILES"
+
+
+eval set X " :F $CONFIG_FILES :C $CONFIG_COMMANDS"
+shift
+for ac_tag
+do
+ case $ac_tag in
+ :[FHLC]) ac_mode=$ac_tag; continue;;
+ esac
+ case $ac_mode$ac_tag in
+ :[FHL]*:*);;
+ :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;;
+ :[FH]-) ac_tag=-:-;;
+ :[FH]*) ac_tag=$ac_tag:$ac_tag.in;;
+ esac
+ ac_save_IFS=$IFS
+ IFS=:
+ set x $ac_tag
+ IFS=$ac_save_IFS
+ shift
+ ac_file=$1
+ shift
+
+ case $ac_mode in
+ :L) ac_source=$1;;
+ :[FH])
+ ac_file_inputs=
+ for ac_f
+ do
+ case $ac_f in
+ -) ac_f="$ac_tmp/stdin";;
+ *) # Look for the file first in the build tree, then in the source tree
+ # (if the path is not absolute). The absolute path cannot be DOS-style,
+ # because $ac_f cannot contain `:'.
+ test -f "$ac_f" ||
+ case $ac_f in
+ [\\/$]*) false;;
+ *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";;
+ esac ||
+ as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;;
+ esac
+ case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac
+ as_fn_append ac_file_inputs " '$ac_f'"
+ done
+
+ # Let's still pretend it is `configure' which instantiates (i.e., don't
+ # use $as_me), people would be surprised to read:
+ # /* config.h. Generated by config.status. */
+ configure_input='Generated from '`
+ $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g'
+ `' by configure.'
+ if test x"$ac_file" != x-; then
+ configure_input="$ac_file. $configure_input"
+ { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5
+$as_echo "$as_me: creating $ac_file" >&6;}
+ fi
+ # Neutralize special characters interpreted by sed in replacement strings.
+ case $configure_input in #(
+ *\&* | *\|* | *\\* )
+ ac_sed_conf_input=`$as_echo "$configure_input" |
+ sed 's/[\\\\&|]/\\\\&/g'`;; #(
+ *) ac_sed_conf_input=$configure_input;;
+ esac
+
+ case $ac_tag in
+ *:-:* | *:-) cat >"$ac_tmp/stdin" \
+ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;;
+ esac
+ ;;
+ esac
+
+ ac_dir=`$as_dirname -- "$ac_file" ||
+$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$ac_file" : 'X\(//\)[^/]' \| \
+ X"$ac_file" : 'X\(//\)$' \| \
+ X"$ac_file" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$ac_file" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ as_dir="$ac_dir"; as_fn_mkdir_p
+ ac_builddir=.
+
+case "$ac_dir" in
+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;
+*)
+ ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`
+ # A ".." for each directory in $ac_dir_suffix.
+ ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`
+ case $ac_top_builddir_sub in
+ "") ac_top_builddir_sub=. ac_top_build_prefix= ;;
+ *) ac_top_build_prefix=$ac_top_builddir_sub/ ;;
+ esac ;;
+esac
+ac_abs_top_builddir=$ac_pwd
+ac_abs_builddir=$ac_pwd$ac_dir_suffix
+# for backward compatibility:
+ac_top_builddir=$ac_top_build_prefix
+
+case $srcdir in
+ .) # We are building in place.
+ ac_srcdir=.
+ ac_top_srcdir=$ac_top_builddir_sub
+ ac_abs_top_srcdir=$ac_pwd ;;
+ [\\/]* | ?:[\\/]* ) # Absolute name.
+ ac_srcdir=$srcdir$ac_dir_suffix;
+ ac_top_srcdir=$srcdir
+ ac_abs_top_srcdir=$srcdir ;;
+ *) # Relative name.
+ ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix
+ ac_top_srcdir=$ac_top_build_prefix$srcdir
+ ac_abs_top_srcdir=$ac_pwd/$srcdir ;;
+esac
+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix
+
+
+ case $ac_mode in
+ :F)
+ #
+ # CONFIG_FILE
+ #
+
+ case $INSTALL in
+ [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;;
+ *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;;
+ esac
+ ac_MKDIR_P=$MKDIR_P
+ case $MKDIR_P in
+ [\\/$]* | ?:[\\/]* ) ;;
+ */*) ac_MKDIR_P=$ac_top_build_prefix$MKDIR_P ;;
+ esac
+_ACEOF
+
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+# If the template does not know about datarootdir, expand it.
+# FIXME: This hack should be removed a few years after 2.60.
+ac_datarootdir_hack=; ac_datarootdir_seen=
+ac_sed_dataroot='
+/datarootdir/ {
+ p
+ q
+}
+/@datadir@/p
+/@docdir@/p
+/@infodir@/p
+/@localedir@/p
+/@mandir@/p'
+case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in
+*datarootdir*) ac_datarootdir_seen=yes;;
+*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*)
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5
+$as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;}
+_ACEOF
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+ ac_datarootdir_hack='
+ s&@datadir@&$datadir&g
+ s&@docdir@&$docdir&g
+ s&@infodir@&$infodir&g
+ s&@localedir@&$localedir&g
+ s&@mandir@&$mandir&g
+ s&\\\${datarootdir}&$datarootdir&g' ;;
+esac
+_ACEOF
+
+# Neutralize VPATH when `$srcdir' = `.'.
+# Shell code in configure.ac might set extrasub.
+# FIXME: do we really want to maintain this feature?
+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
+ac_sed_extra="$ac_vpsub
+$extrasub
+_ACEOF
+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
+:t
+/@[a-zA-Z_][a-zA-Z_0-9]*@/!b
+s|@configure_input@|$ac_sed_conf_input|;t t
+s&@top_builddir@&$ac_top_builddir_sub&;t t
+s&@top_build_prefix@&$ac_top_build_prefix&;t t
+s&@srcdir@&$ac_srcdir&;t t
+s&@abs_srcdir@&$ac_abs_srcdir&;t t
+s&@top_srcdir@&$ac_top_srcdir&;t t
+s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t
+s&@builddir@&$ac_builddir&;t t
+s&@abs_builddir@&$ac_abs_builddir&;t t
+s&@abs_top_builddir@&$ac_abs_top_builddir&;t t
+s&@INSTALL@&$ac_INSTALL&;t t
+s&@MKDIR_P@&$ac_MKDIR_P&;t t
+$ac_datarootdir_hack
+"
+eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \
+ >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+
+test -z "$ac_datarootdir_hack$ac_datarootdir_seen" &&
+ { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } &&
+ { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \
+ "$ac_tmp/out"`; test -z "$ac_out"; } &&
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir'
+which seems to be undefined. Please make sure it is defined" >&5
+$as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir'
+which seems to be undefined. Please make sure it is defined" >&2;}
+
+ rm -f "$ac_tmp/stdin"
+ case $ac_file in
+ -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";;
+ *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";;
+ esac \
+ || as_fn_error $? "could not create $ac_file" "$LINENO" 5
+ ;;
+
+
+ :C) { $as_echo "$as_me:${as_lineno-$LINENO}: executing $ac_file commands" >&5
+$as_echo "$as_me: executing $ac_file commands" >&6;}
+ ;;
+ esac
+
+
+ case $ac_file$ac_mode in
+ "depfiles":C) test x"$AMDEP_TRUE" != x"" || {
+ # Older Autoconf quotes --file arguments for eval, but not when files
+ # are listed without --file. Let's play safe and only enable the eval
+ # if we detect the quoting.
+ case $CONFIG_FILES in
+ *\'*) eval set x "$CONFIG_FILES" ;;
+ *) set x $CONFIG_FILES ;;
+ esac
+ shift
+ for mf
+ do
+ # Strip MF so we end up with the name of the file.
+ mf=`echo "$mf" | sed -e 's/:.*$//'`
+ # Check whether this is an Automake generated Makefile or not.
+ # We used to match only the files named 'Makefile.in', but
+ # some people rename them; so instead we look at the file content.
+ # Grep'ing the first line is not enough: some people post-process
+ # each Makefile.in and add a new line on top of each file to say so.
+ # Grep'ing the whole file is not good either: AIX grep has a line
+ # limit of 2048, but all sed's we know have understand at least 4000.
+ if sed -n 's,^#.*generated by automake.*,X,p' "$mf" | grep X >/dev/null 2>&1; then
+ dirpart=`$as_dirname -- "$mf" ||
+$as_expr X"$mf" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$mf" : 'X\(//\)[^/]' \| \
+ X"$mf" : 'X\(//\)$' \| \
+ X"$mf" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$mf" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ else
+ continue
+ fi
+ # Extract the definition of DEPDIR, am__include, and am__quote
+ # from the Makefile without running 'make'.
+ DEPDIR=`sed -n 's/^DEPDIR = //p' < "$mf"`
+ test -z "$DEPDIR" && continue
+ am__include=`sed -n 's/^am__include = //p' < "$mf"`
+ test -z "$am__include" && continue
+ am__quote=`sed -n 's/^am__quote = //p' < "$mf"`
+ # Find all dependency output files, they are included files with
+ # $(DEPDIR) in their names. We invoke sed twice because it is the
+ # simplest approach to changing $(DEPDIR) to its actual value in the
+ # expansion.
+ for file in `sed -n "
+ s/^$am__include $am__quote\(.*(DEPDIR).*\)$am__quote"'$/\1/p' <"$mf" | \
+ sed -e 's/\$(DEPDIR)/'"$DEPDIR"'/g'`; do
+ # Make sure the directory exists.
+ test -f "$dirpart/$file" && continue
+ fdir=`$as_dirname -- "$file" ||
+$as_expr X"$file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
+ X"$file" : 'X\(//\)[^/]' \| \
+ X"$file" : 'X\(//\)$' \| \
+ X"$file" : 'X\(/\)' \| . 2>/dev/null ||
+$as_echo X"$file" |
+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)[^/].*/{
+ s//\1/
+ q
+ }
+ /^X\(\/\/\)$/{
+ s//\1/
+ q
+ }
+ /^X\(\/\).*/{
+ s//\1/
+ q
+ }
+ s/.*/./; q'`
+ as_dir=$dirpart/$fdir; as_fn_mkdir_p
+ # echo "creating $dirpart/$file"
+ echo '# dummy' > "$dirpart/$file"
+ done
+ done
+}
+ ;;
+
+ esac
+done # for ac_tag
+
+
+as_fn_exit 0
+_ACEOF
+ac_clean_files=$ac_clean_files_save
+
+test $ac_write_fail = 0 ||
+ as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5
+
+
+# configure is writing to config.log, and then calls config.status.
+# config.status does its own redirection, appending to config.log.
+# Unfortunately, on DOS this fails, as config.log is still kept open
+# by configure, so config.status won't be able to write to it; its
+# output is simply discarded. So we exec the FD to /dev/null,
+# effectively closing config.log, so it can be properly (re)opened and
+# appended to by config.status. When coming back to configure, we
+# need to make the FD available again.
+if test "$no_create" != yes; then
+ ac_cs_success=:
+ ac_config_status_args=
+ test "$silent" = yes &&
+ ac_config_status_args="$ac_config_status_args --quiet"
+ exec 5>/dev/null
+ $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false
+ exec 5>>config.log
+ # Use ||, not &&, to avoid exiting from the if with $? = 1, which
+ # would make configure fail if this is the last instruction.
+ $ac_cs_success || as_fn_exit 1
+fi
+if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5
+$as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;}
+fi
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure.ac b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure.ac
new file mode 100644
index 000000000..3feebede0
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/configure.ac
@@ -0,0 +1,97 @@
+# The name, version, and maintainer of this package
+AC_INIT([freedom-metal], [m4_esyscmd_s([./scripts/git-version])], [https://github.com/sifive/freedom-metal/issues], [freedom-metal], [https://github.com/sifive/freedom-metal])
+
+# Initializes automake, enabling maintainer mode by default (which should be
+# disabled by the archive generated by "make dist").
+AM_INIT_AUTOMAKE([foreign subdir-objects])
+AM_MAINTAINER_MODE([disable])
+AC_CONFIG_MACRO_DIRS([m4])
+
+AC_CANONICAL_HOST
+
+# Probe for tools that we need in order to build.
+AC_PROG_CC
+AC_PROG_RANLIB
+AM_PROG_AR
+AM_PROG_AS
+
+# autoconf tries very hard to avoid failing, so it'll even go ahead and try to
+# build the project using "gcc" if it can't find a suitable C compiler prefixed
+# by the host system. This doesn't work when cross compiling, but it's a
+# common error for users so we explicitly check for this right here to quickly
+# provide an error message.
+AC_COMPILE_IFELSE([AC_LANG_PROGRAM([],[
+#ifndef __riscv
+# error "A RISC-V compiler is required to build Freedom Metal"
+#endif
+])], [], [AC_MSG_FAILURE([The C compiler doesn't define __riscv, which means it's probably not a RISC-V compiler. You should specify something like --host=riscv64-sifive-elf when building this, as it will only work on RISC-V systems.])])
+
+########################################################
+# Options
+########################################################
+
+AC_ARG_WITH([builtin-libgloss],
+ [AS_HELP_STRING([--with-bultin-libgloss], [Build libgloss along with Metal])],
+ [with_builtin_libgloss="yes"],
+ [with_builtin_libgloss="no"]
+)
+
+AC_ARG_WITH([builtin-libmetal-pico],
+ [AS_HELP_STRING([--with-bultin-libmetal-pico], [Build libmetal-pico along with Metal])],
+ [with_builtin_libmetal_pico="yes"],
+ [with_builtin_libmetal_pico="no"]
+)
+
+AC_ARG_WITH([builtin-libmetal-segger],
+ [AS_HELP_STRING([--with-bultin-libmetal-segger], [Build libmetal-segger along with Metal])],
+ [with_builtin_libmetal_segger="yes"],
+ [with_builtin_libmetal_segger="no"]
+)
+
+AC_ARG_WITH([machine-header],
+ [AS_HELP_STRING([--with-machine-header=PATH], [Path to the machine header file])],
+ [],
+ [with_machine_header="no"]
+)
+
+AC_ARG_WITH([machine-inline],
+ [AS_HELP_STRING([--with-machine-inline=PATH], [Path to the machine inline file])],
+ [],
+ [with_machine_inline="no"]
+)
+
+AC_ARG_WITH([platform-header],
+ [AS_HELP_STRING([--with-platform-header=PATH], [Path to the platform header file])],
+ [],
+ [with_platform_header="no"]
+)
+
+########################################################
+# Process Options
+########################################################
+
+AM_CONDITIONAL([WITH_BUILTIN_LIBGLOSS], [test "x$with_builtin_libgloss" = "xyes"])
+
+AM_CONDITIONAL([WITH_BUILTIN_LIBMETAL_PICO], [test "x$with_builtin_libmetal_pico" = "xyes"])
+
+AM_CONDITIONAL([WITH_BUILTIN_LIBMETAL_SEGGER], [test "x$with_builtin_libmetal_segger" = "xyes"])
+
+# Configure the build system to pass in the preconfigured machine support files
+AS_IF([test "x$with_machine_header" != "xno"],
+ [AC_SUBST([MACHINE_HEADER], "$with_machine_header")],
+ [AC_MSG_FAILURE([--with-machine-header is required])]
+)
+
+AS_IF([test "x$with_machine_inline" != "xno"],
+ [AC_SUBST([MACHINE_INLINE], "$with_machine_inline")],
+ [AC_MSG_FAILURE([--with-machine-inline is required])]
+)
+
+AS_IF([test "x$with_platform_header" != "xno"],
+ [AC_SUBST([PLATFORM_HEADER], "$with_platform_header")],
+ [AC_MSG_FAILURE([--with-platform-header is required])]
+)
+
+# Generates the remainder of the build system.
+AC_CONFIG_FILES([Makefile])
+AC_OUTPUT
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/depcomp b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/depcomp
new file mode 100755
index 000000000..fc98710e2
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/depcomp
@@ -0,0 +1,791 @@
+#! /bin/sh
+# depcomp - compile a program generating dependencies as side-effects
+
+scriptversion=2013-05-30.07; # UTC
+
+# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+# Originally written by Alexandre Oliva <oliva@dcc.unicamp.br>.
+
+case $1 in
+ '')
+ echo "$0: No command. Try '$0 --help' for more information." 1>&2
+ exit 1;
+ ;;
+ -h | --h*)
+ cat <<\EOF
+Usage: depcomp [--help] [--version] PROGRAM [ARGS]
+
+Run PROGRAMS ARGS to compile a file, generating dependencies
+as side-effects.
+
+Environment variables:
+ depmode Dependency tracking mode.
+ source Source file read by 'PROGRAMS ARGS'.
+ object Object file output by 'PROGRAMS ARGS'.
+ DEPDIR directory where to store dependencies.
+ depfile Dependency file to output.
+ tmpdepfile Temporary file to use when outputting dependencies.
+ libtool Whether libtool is used (yes/no).
+
+Report bugs to <bug-automake@gnu.org>.
+EOF
+ exit $?
+ ;;
+ -v | --v*)
+ echo "depcomp $scriptversion"
+ exit $?
+ ;;
+esac
+
+# Get the directory component of the given path, and save it in the
+# global variables '$dir'. Note that this directory component will
+# be either empty or ending with a '/' character. This is deliberate.
+set_dir_from ()
+{
+ case $1 in
+ */*) dir=`echo "$1" | sed -e 's|/[^/]*$|/|'`;;
+ *) dir=;;
+ esac
+}
+
+# Get the suffix-stripped basename of the given path, and save it the
+# global variable '$base'.
+set_base_from ()
+{
+ base=`echo "$1" | sed -e 's|^.*/||' -e 's/\.[^.]*$//'`
+}
+
+# If no dependency file was actually created by the compiler invocation,
+# we still have to create a dummy depfile, to avoid errors with the
+# Makefile "include basename.Plo" scheme.
+make_dummy_depfile ()
+{
+ echo "#dummy" > "$depfile"
+}
+
+# Factor out some common post-processing of the generated depfile.
+# Requires the auxiliary global variable '$tmpdepfile' to be set.
+aix_post_process_depfile ()
+{
+ # If the compiler actually managed to produce a dependency file,
+ # post-process it.
+ if test -f "$tmpdepfile"; then
+ # Each line is of the form 'foo.o: dependency.h'.
+ # Do two passes, one to just change these to
+ # $object: dependency.h
+ # and one to simply output
+ # dependency.h:
+ # which is needed to avoid the deleted-header problem.
+ { sed -e "s,^.*\.[$lower]*:,$object:," < "$tmpdepfile"
+ sed -e "s,^.*\.[$lower]*:[$tab ]*,," -e 's,$,:,' < "$tmpdepfile"
+ } > "$depfile"
+ rm -f "$tmpdepfile"
+ else
+ make_dummy_depfile
+ fi
+}
+
+# A tabulation character.
+tab=' '
+# A newline character.
+nl='
+'
+# Character ranges might be problematic outside the C locale.
+# These definitions help.
+upper=ABCDEFGHIJKLMNOPQRSTUVWXYZ
+lower=abcdefghijklmnopqrstuvwxyz
+digits=0123456789
+alpha=${upper}${lower}
+
+if test -z "$depmode" || test -z "$source" || test -z "$object"; then
+ echo "depcomp: Variables source, object and depmode must be set" 1>&2
+ exit 1
+fi
+
+# Dependencies for sub/bar.o or sub/bar.obj go into sub/.deps/bar.Po.
+depfile=${depfile-`echo "$object" |
+ sed 's|[^\\/]*$|'${DEPDIR-.deps}'/&|;s|\.\([^.]*\)$|.P\1|;s|Pobj$|Po|'`}
+tmpdepfile=${tmpdepfile-`echo "$depfile" | sed 's/\.\([^.]*\)$/.T\1/'`}
+
+rm -f "$tmpdepfile"
+
+# Avoid interferences from the environment.
+gccflag= dashmflag=
+
+# Some modes work just like other modes, but use different flags. We
+# parameterize here, but still list the modes in the big case below,
+# to make depend.m4 easier to write. Note that we *cannot* use a case
+# here, because this file can only contain one case statement.
+if test "$depmode" = hp; then
+ # HP compiler uses -M and no extra arg.
+ gccflag=-M
+ depmode=gcc
+fi
+
+if test "$depmode" = dashXmstdout; then
+ # This is just like dashmstdout with a different argument.
+ dashmflag=-xM
+ depmode=dashmstdout
+fi
+
+cygpath_u="cygpath -u -f -"
+if test "$depmode" = msvcmsys; then
+ # This is just like msvisualcpp but w/o cygpath translation.
+ # Just convert the backslash-escaped backslashes to single forward
+ # slashes to satisfy depend.m4
+ cygpath_u='sed s,\\\\,/,g'
+ depmode=msvisualcpp
+fi
+
+if test "$depmode" = msvc7msys; then
+ # This is just like msvc7 but w/o cygpath translation.
+ # Just convert the backslash-escaped backslashes to single forward
+ # slashes to satisfy depend.m4
+ cygpath_u='sed s,\\\\,/,g'
+ depmode=msvc7
+fi
+
+if test "$depmode" = xlc; then
+ # IBM C/C++ Compilers xlc/xlC can output gcc-like dependency information.
+ gccflag=-qmakedep=gcc,-MF
+ depmode=gcc
+fi
+
+case "$depmode" in
+gcc3)
+## gcc 3 implements dependency tracking that does exactly what
+## we want. Yay! Note: for some reason libtool 1.4 doesn't like
+## it if -MD -MP comes after the -MF stuff. Hmm.
+## Unfortunately, FreeBSD c89 acceptance of flags depends upon
+## the command line argument order; so add the flags where they
+## appear in depend2.am. Note that the slowdown incurred here
+## affects only configure: in makefiles, %FASTDEP% shortcuts this.
+ for arg
+ do
+ case $arg in
+ -c) set fnord "$@" -MT "$object" -MD -MP -MF "$tmpdepfile" "$arg" ;;
+ *) set fnord "$@" "$arg" ;;
+ esac
+ shift # fnord
+ shift # $arg
+ done
+ "$@"
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ mv "$tmpdepfile" "$depfile"
+ ;;
+
+gcc)
+## Note that this doesn't just cater to obsosete pre-3.x GCC compilers.
+## but also to in-use compilers like IMB xlc/xlC and the HP C compiler.
+## (see the conditional assignment to $gccflag above).
+## There are various ways to get dependency output from gcc. Here's
+## why we pick this rather obscure method:
+## - Don't want to use -MD because we'd like the dependencies to end
+## up in a subdir. Having to rename by hand is ugly.
+## (We might end up doing this anyway to support other compilers.)
+## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like
+## -MM, not -M (despite what the docs say). Also, it might not be
+## supported by the other compilers which use the 'gcc' depmode.
+## - Using -M directly means running the compiler twice (even worse
+## than renaming).
+ if test -z "$gccflag"; then
+ gccflag=-MD,
+ fi
+ "$@" -Wp,"$gccflag$tmpdepfile"
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ rm -f "$depfile"
+ echo "$object : \\" > "$depfile"
+ # The second -e expression handles DOS-style file names with drive
+ # letters.
+ sed -e 's/^[^:]*: / /' \
+ -e 's/^['$alpha']:\/[^:]*: / /' < "$tmpdepfile" >> "$depfile"
+## This next piece of magic avoids the "deleted header file" problem.
+## The problem is that when a header file which appears in a .P file
+## is deleted, the dependency causes make to die (because there is
+## typically no way to rebuild the header). We avoid this by adding
+## dummy dependencies for each header file. Too bad gcc doesn't do
+## this for us directly.
+## Some versions of gcc put a space before the ':'. On the theory
+## that the space means something, we add a space to the output as
+## well. hp depmode also adds that space, but also prefixes the VPATH
+## to the object. Take care to not repeat it in the output.
+## Some versions of the HPUX 10.20 sed can't process this invocation
+## correctly. Breaking it into two sed invocations is a workaround.
+ tr ' ' "$nl" < "$tmpdepfile" \
+ | sed -e 's/^\\$//' -e '/^$/d' -e "s|.*$object$||" -e '/:$/d' \
+ | sed -e 's/$/ :/' >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+hp)
+ # This case exists only to let depend.m4 do its work. It works by
+ # looking at the text of this script. This case will never be run,
+ # since it is checked for above.
+ exit 1
+ ;;
+
+sgi)
+ if test "$libtool" = yes; then
+ "$@" "-Wp,-MDupdate,$tmpdepfile"
+ else
+ "$@" -MDupdate "$tmpdepfile"
+ fi
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ rm -f "$depfile"
+
+ if test -f "$tmpdepfile"; then # yes, the sourcefile depend on other files
+ echo "$object : \\" > "$depfile"
+ # Clip off the initial element (the dependent). Don't try to be
+ # clever and replace this with sed code, as IRIX sed won't handle
+ # lines with more than a fixed number of characters (4096 in
+ # IRIX 6.2 sed, 8192 in IRIX 6.5). We also remove comment lines;
+ # the IRIX cc adds comments like '#:fec' to the end of the
+ # dependency line.
+ tr ' ' "$nl" < "$tmpdepfile" \
+ | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' \
+ | tr "$nl" ' ' >> "$depfile"
+ echo >> "$depfile"
+ # The second pass generates a dummy entry for each header file.
+ tr ' ' "$nl" < "$tmpdepfile" \
+ | sed -e 's/^.*\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \
+ >> "$depfile"
+ else
+ make_dummy_depfile
+ fi
+ rm -f "$tmpdepfile"
+ ;;
+
+xlc)
+ # This case exists only to let depend.m4 do its work. It works by
+ # looking at the text of this script. This case will never be run,
+ # since it is checked for above.
+ exit 1
+ ;;
+
+aix)
+ # The C for AIX Compiler uses -M and outputs the dependencies
+ # in a .u file. In older versions, this file always lives in the
+ # current directory. Also, the AIX compiler puts '$object:' at the
+ # start of each line; $object doesn't have directory information.
+ # Version 6 uses the directory in both cases.
+ set_dir_from "$object"
+ set_base_from "$object"
+ if test "$libtool" = yes; then
+ tmpdepfile1=$dir$base.u
+ tmpdepfile2=$base.u
+ tmpdepfile3=$dir.libs/$base.u
+ "$@" -Wc,-M
+ else
+ tmpdepfile1=$dir$base.u
+ tmpdepfile2=$dir$base.u
+ tmpdepfile3=$dir$base.u
+ "$@" -M
+ fi
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+ exit $stat
+ fi
+
+ for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+ do
+ test -f "$tmpdepfile" && break
+ done
+ aix_post_process_depfile
+ ;;
+
+tcc)
+ # tcc (Tiny C Compiler) understand '-MD -MF file' since version 0.9.26
+ # FIXME: That version still under development at the moment of writing.
+ # Make that this statement remains true also for stable, released
+ # versions.
+ # It will wrap lines (doesn't matter whether long or short) with a
+ # trailing '\', as in:
+ #
+ # foo.o : \
+ # foo.c \
+ # foo.h \
+ #
+ # It will put a trailing '\' even on the last line, and will use leading
+ # spaces rather than leading tabs (at least since its commit 0394caf7
+ # "Emit spaces for -MD").
+ "$@" -MD -MF "$tmpdepfile"
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ rm -f "$depfile"
+ # Each non-empty line is of the form 'foo.o : \' or ' dep.h \'.
+ # We have to change lines of the first kind to '$object: \'.
+ sed -e "s|.*:|$object :|" < "$tmpdepfile" > "$depfile"
+ # And for each line of the second kind, we have to emit a 'dep.h:'
+ # dummy dependency, to avoid the deleted-header problem.
+ sed -n -e 's|^ *\(.*\) *\\$|\1:|p' < "$tmpdepfile" >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+## The order of this option in the case statement is important, since the
+## shell code in configure will try each of these formats in the order
+## listed in this file. A plain '-MD' option would be understood by many
+## compilers, so we must ensure this comes after the gcc and icc options.
+pgcc)
+ # Portland's C compiler understands '-MD'.
+ # Will always output deps to 'file.d' where file is the root name of the
+ # source file under compilation, even if file resides in a subdirectory.
+ # The object file name does not affect the name of the '.d' file.
+ # pgcc 10.2 will output
+ # foo.o: sub/foo.c sub/foo.h
+ # and will wrap long lines using '\' :
+ # foo.o: sub/foo.c ... \
+ # sub/foo.h ... \
+ # ...
+ set_dir_from "$object"
+ # Use the source, not the object, to determine the base name, since
+ # that's sadly what pgcc will do too.
+ set_base_from "$source"
+ tmpdepfile=$base.d
+
+ # For projects that build the same source file twice into different object
+ # files, the pgcc approach of using the *source* file root name can cause
+ # problems in parallel builds. Use a locking strategy to avoid stomping on
+ # the same $tmpdepfile.
+ lockdir=$base.d-lock
+ trap "
+ echo '$0: caught signal, cleaning up...' >&2
+ rmdir '$lockdir'
+ exit 1
+ " 1 2 13 15
+ numtries=100
+ i=$numtries
+ while test $i -gt 0; do
+ # mkdir is a portable test-and-set.
+ if mkdir "$lockdir" 2>/dev/null; then
+ # This process acquired the lock.
+ "$@" -MD
+ stat=$?
+ # Release the lock.
+ rmdir "$lockdir"
+ break
+ else
+ # If the lock is being held by a different process, wait
+ # until the winning process is done or we timeout.
+ while test -d "$lockdir" && test $i -gt 0; do
+ sleep 1
+ i=`expr $i - 1`
+ done
+ fi
+ i=`expr $i - 1`
+ done
+ trap - 1 2 13 15
+ if test $i -le 0; then
+ echo "$0: failed to acquire lock after $numtries attempts" >&2
+ echo "$0: check lockdir '$lockdir'" >&2
+ exit 1
+ fi
+
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ rm -f "$depfile"
+ # Each line is of the form `foo.o: dependent.h',
+ # or `foo.o: dep1.h dep2.h \', or ` dep3.h dep4.h \'.
+ # Do two passes, one to just change these to
+ # `$object: dependent.h' and one to simply `dependent.h:'.
+ sed "s,^[^:]*:,$object :," < "$tmpdepfile" > "$depfile"
+ # Some versions of the HPUX 10.20 sed can't process this invocation
+ # correctly. Breaking it into two sed invocations is a workaround.
+ sed 's,^[^:]*: \(.*\)$,\1,;s/^\\$//;/^$/d;/:$/d' < "$tmpdepfile" \
+ | sed -e 's/$/ :/' >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+hp2)
+ # The "hp" stanza above does not work with aCC (C++) and HP's ia64
+ # compilers, which have integrated preprocessors. The correct option
+ # to use with these is +Maked; it writes dependencies to a file named
+ # 'foo.d', which lands next to the object file, wherever that
+ # happens to be.
+ # Much of this is similar to the tru64 case; see comments there.
+ set_dir_from "$object"
+ set_base_from "$object"
+ if test "$libtool" = yes; then
+ tmpdepfile1=$dir$base.d
+ tmpdepfile2=$dir.libs/$base.d
+ "$@" -Wc,+Maked
+ else
+ tmpdepfile1=$dir$base.d
+ tmpdepfile2=$dir$base.d
+ "$@" +Maked
+ fi
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile1" "$tmpdepfile2"
+ exit $stat
+ fi
+
+ for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2"
+ do
+ test -f "$tmpdepfile" && break
+ done
+ if test -f "$tmpdepfile"; then
+ sed -e "s,^.*\.[$lower]*:,$object:," "$tmpdepfile" > "$depfile"
+ # Add 'dependent.h:' lines.
+ sed -ne '2,${
+ s/^ *//
+ s/ \\*$//
+ s/$/:/
+ p
+ }' "$tmpdepfile" >> "$depfile"
+ else
+ make_dummy_depfile
+ fi
+ rm -f "$tmpdepfile" "$tmpdepfile2"
+ ;;
+
+tru64)
+ # The Tru64 compiler uses -MD to generate dependencies as a side
+ # effect. 'cc -MD -o foo.o ...' puts the dependencies into 'foo.o.d'.
+ # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put
+ # dependencies in 'foo.d' instead, so we check for that too.
+ # Subdirectories are respected.
+ set_dir_from "$object"
+ set_base_from "$object"
+
+ if test "$libtool" = yes; then
+ # Libtool generates 2 separate objects for the 2 libraries. These
+ # two compilations output dependencies in $dir.libs/$base.o.d and
+ # in $dir$base.o.d. We have to check for both files, because
+ # one of the two compilations can be disabled. We should prefer
+ # $dir$base.o.d over $dir.libs/$base.o.d because the latter is
+ # automatically cleaned when .libs/ is deleted, while ignoring
+ # the former would cause a distcleancheck panic.
+ tmpdepfile1=$dir$base.o.d # libtool 1.5
+ tmpdepfile2=$dir.libs/$base.o.d # Likewise.
+ tmpdepfile3=$dir.libs/$base.d # Compaq CCC V6.2-504
+ "$@" -Wc,-MD
+ else
+ tmpdepfile1=$dir$base.d
+ tmpdepfile2=$dir$base.d
+ tmpdepfile3=$dir$base.d
+ "$@" -MD
+ fi
+
+ stat=$?
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+ exit $stat
+ fi
+
+ for tmpdepfile in "$tmpdepfile1" "$tmpdepfile2" "$tmpdepfile3"
+ do
+ test -f "$tmpdepfile" && break
+ done
+ # Same post-processing that is required for AIX mode.
+ aix_post_process_depfile
+ ;;
+
+msvc7)
+ if test "$libtool" = yes; then
+ showIncludes=-Wc,-showIncludes
+ else
+ showIncludes=-showIncludes
+ fi
+ "$@" $showIncludes > "$tmpdepfile"
+ stat=$?
+ grep -v '^Note: including file: ' "$tmpdepfile"
+ if test $stat -ne 0; then
+ rm -f "$tmpdepfile"
+ exit $stat
+ fi
+ rm -f "$depfile"
+ echo "$object : \\" > "$depfile"
+ # The first sed program below extracts the file names and escapes
+ # backslashes for cygpath. The second sed program outputs the file
+ # name when reading, but also accumulates all include files in the
+ # hold buffer in order to output them again at the end. This only
+ # works with sed implementations that can handle large buffers.
+ sed < "$tmpdepfile" -n '
+/^Note: including file: *\(.*\)/ {
+ s//\1/
+ s/\\/\\\\/g
+ p
+}' | $cygpath_u | sort -u | sed -n '
+s/ /\\ /g
+s/\(.*\)/'"$tab"'\1 \\/p
+s/.\(.*\) \\/\1:/
+H
+$ {
+ s/.*/'"$tab"'/
+ G
+ p
+}' >> "$depfile"
+ echo >> "$depfile" # make sure the fragment doesn't end with a backslash
+ rm -f "$tmpdepfile"
+ ;;
+
+msvc7msys)
+ # This case exists only to let depend.m4 do its work. It works by
+ # looking at the text of this script. This case will never be run,
+ # since it is checked for above.
+ exit 1
+ ;;
+
+#nosideeffect)
+ # This comment above is used by automake to tell side-effect
+ # dependency tracking mechanisms from slower ones.
+
+dashmstdout)
+ # Important note: in order to support this mode, a compiler *must*
+ # always write the preprocessed file to stdout, regardless of -o.
+ "$@" || exit $?
+
+ # Remove the call to Libtool.
+ if test "$libtool" = yes; then
+ while test "X$1" != 'X--mode=compile'; do
+ shift
+ done
+ shift
+ fi
+
+ # Remove '-o $object'.
+ IFS=" "
+ for arg
+ do
+ case $arg in
+ -o)
+ shift
+ ;;
+ $object)
+ shift
+ ;;
+ *)
+ set fnord "$@" "$arg"
+ shift # fnord
+ shift # $arg
+ ;;
+ esac
+ done
+
+ test -z "$dashmflag" && dashmflag=-M
+ # Require at least two characters before searching for ':'
+ # in the target name. This is to cope with DOS-style filenames:
+ # a dependency such as 'c:/foo/bar' could be seen as target 'c' otherwise.
+ "$@" $dashmflag |
+ sed "s|^[$tab ]*[^:$tab ][^:][^:]*:[$tab ]*|$object: |" > "$tmpdepfile"
+ rm -f "$depfile"
+ cat < "$tmpdepfile" > "$depfile"
+ # Some versions of the HPUX 10.20 sed can't process this sed invocation
+ # correctly. Breaking it into two sed invocations is a workaround.
+ tr ' ' "$nl" < "$tmpdepfile" \
+ | sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
+ | sed -e 's/$/ :/' >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+dashXmstdout)
+ # This case only exists to satisfy depend.m4. It is never actually
+ # run, as this mode is specially recognized in the preamble.
+ exit 1
+ ;;
+
+makedepend)
+ "$@" || exit $?
+ # Remove any Libtool call
+ if test "$libtool" = yes; then
+ while test "X$1" != 'X--mode=compile'; do
+ shift
+ done
+ shift
+ fi
+ # X makedepend
+ shift
+ cleared=no eat=no
+ for arg
+ do
+ case $cleared in
+ no)
+ set ""; shift
+ cleared=yes ;;
+ esac
+ if test $eat = yes; then
+ eat=no
+ continue
+ fi
+ case "$arg" in
+ -D*|-I*)
+ set fnord "$@" "$arg"; shift ;;
+ # Strip any option that makedepend may not understand. Remove
+ # the object too, otherwise makedepend will parse it as a source file.
+ -arch)
+ eat=yes ;;
+ -*|$object)
+ ;;
+ *)
+ set fnord "$@" "$arg"; shift ;;
+ esac
+ done
+ obj_suffix=`echo "$object" | sed 's/^.*\././'`
+ touch "$tmpdepfile"
+ ${MAKEDEPEND-makedepend} -o"$obj_suffix" -f"$tmpdepfile" "$@"
+ rm -f "$depfile"
+ # makedepend may prepend the VPATH from the source file name to the object.
+ # No need to regex-escape $object, excess matching of '.' is harmless.
+ sed "s|^.*\($object *:\)|\1|" "$tmpdepfile" > "$depfile"
+ # Some versions of the HPUX 10.20 sed can't process the last invocation
+ # correctly. Breaking it into two sed invocations is a workaround.
+ sed '1,2d' "$tmpdepfile" \
+ | tr ' ' "$nl" \
+ | sed -e 's/^\\$//' -e '/^$/d' -e '/:$/d' \
+ | sed -e 's/$/ :/' >> "$depfile"
+ rm -f "$tmpdepfile" "$tmpdepfile".bak
+ ;;
+
+cpp)
+ # Important note: in order to support this mode, a compiler *must*
+ # always write the preprocessed file to stdout.
+ "$@" || exit $?
+
+ # Remove the call to Libtool.
+ if test "$libtool" = yes; then
+ while test "X$1" != 'X--mode=compile'; do
+ shift
+ done
+ shift
+ fi
+
+ # Remove '-o $object'.
+ IFS=" "
+ for arg
+ do
+ case $arg in
+ -o)
+ shift
+ ;;
+ $object)
+ shift
+ ;;
+ *)
+ set fnord "$@" "$arg"
+ shift # fnord
+ shift # $arg
+ ;;
+ esac
+ done
+
+ "$@" -E \
+ | sed -n -e '/^# [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
+ -e '/^#line [0-9][0-9]* "\([^"]*\)".*/ s:: \1 \\:p' \
+ | sed '$ s: \\$::' > "$tmpdepfile"
+ rm -f "$depfile"
+ echo "$object : \\" > "$depfile"
+ cat < "$tmpdepfile" >> "$depfile"
+ sed < "$tmpdepfile" '/^$/d;s/^ //;s/ \\$//;s/$/ :/' >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+msvisualcpp)
+ # Important note: in order to support this mode, a compiler *must*
+ # always write the preprocessed file to stdout.
+ "$@" || exit $?
+
+ # Remove the call to Libtool.
+ if test "$libtool" = yes; then
+ while test "X$1" != 'X--mode=compile'; do
+ shift
+ done
+ shift
+ fi
+
+ IFS=" "
+ for arg
+ do
+ case "$arg" in
+ -o)
+ shift
+ ;;
+ $object)
+ shift
+ ;;
+ "-Gm"|"/Gm"|"-Gi"|"/Gi"|"-ZI"|"/ZI")
+ set fnord "$@"
+ shift
+ shift
+ ;;
+ *)
+ set fnord "$@" "$arg"
+ shift
+ shift
+ ;;
+ esac
+ done
+ "$@" -E 2>/dev/null |
+ sed -n '/^#line [0-9][0-9]* "\([^"]*\)"/ s::\1:p' | $cygpath_u | sort -u > "$tmpdepfile"
+ rm -f "$depfile"
+ echo "$object : \\" > "$depfile"
+ sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::'"$tab"'\1 \\:p' >> "$depfile"
+ echo "$tab" >> "$depfile"
+ sed < "$tmpdepfile" -n -e 's% %\\ %g' -e '/^\(.*\)$/ s::\1\::p' >> "$depfile"
+ rm -f "$tmpdepfile"
+ ;;
+
+msvcmsys)
+ # This case exists only to let depend.m4 do its work. It works by
+ # looking at the text of this script. This case will never be run,
+ # since it is checked for above.
+ exit 1
+ ;;
+
+none)
+ exec "$@"
+ ;;
+
+*)
+ echo "Unknown depmode $depmode" 1>&2
+ exit 1
+ ;;
+esac
+
+exit 0
+
+# Local Variables:
+# mode: shell-script
+# sh-indentation: 2
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/doc/link_to_docs_in_github.url b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/doc/link_to_docs_in_github.url
deleted file mode 100644
index f59b1cedd..000000000
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/doc/link_to_docs_in_github.url
+++ /dev/null
@@ -1,5 +0,0 @@
-[{000214A0-0000-0000-C000-000000000046}]
-Prop3=19,11
-[InternetShortcut]
-IDList=
-URL=https://github.com/sifive/freedom-metal-docs
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/crt0.S b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/crt0.S
index 920ee4b9f..20afcc0c1 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/crt0.S
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/crt0.S
@@ -44,22 +44,7 @@ _start:
la gp, __global_pointer$
.option pop
- /* The METAL is designed for a bare-metal environment and therefor is expected
- * to define its own stack pointer. We also align the stack pointer here
- * because the only RISC-V ABI that's currently defined mandates 16-byte
- * stack alignment. */
- la sp, _sp
-
- /* Increment by hartid number of stack sizes */
- li t0, 0
- la t1, __stack_size
-1:
- beq t0, a0, 1f
- add sp, sp, t1
- addi t0, t0, 1
- j 1b
-1:
- andi sp, sp, -16
+ /* Stack pointer is expected to be initialized before _start */
/* If we're not hart 0, skip the initialization work */
la t0, __metal_boot_hart
@@ -123,6 +108,36 @@ _start:
complete */
fence.i
+2:
+
+ /* Copy the LIM section */
+ la t0, metal_segment_lim_source_start
+ la t1, metal_segment_lim_target_start
+ la t2, metal_segment_lim_target_end
+
+ beq t0, t1, 2f
+ bge t1, t2, 2f
+
+1:
+#if __riscv_xlen == 32
+ lw a0, 0(t0)
+ addi t0, t0, 4
+ sw a0, 0(t1)
+ addi t1, t1, 4
+ blt t1, t2, 1b
+#else
+ ld a0, 0(t0)
+ addi t0, t0, 8
+ sd a0, 0(t1)
+ addi t1, t1, 8
+ blt t1, t2, 1b
+#endif
+2:
+
+ /* Fence all subsequent instruction fetches until after the LIM writes
+ complete */
+ fence.i
+
/* Zero the BSS segment. */
la t1, metal_segment_bss_target_start
la t2, metal_segment_bss_target_end
@@ -141,6 +156,10 @@ _start:
#endif
2:
+ /* Set TLS pointer */
+ .weak __tls_base
+ la tp, __tls_base
+
/* At this point we're in an environment that can execute C code. The first
* thing to do is to make the callback to the parent environment if it's been
* requested to do so. */
@@ -153,14 +172,41 @@ _start:
call atexit
call __libc_init_array
+ /* Register metal_fini_run as a destructor and call metal_init_run to
+ * run and setup Metal constructors */
+ la a0, metal_fini_run
+ call atexit
+ call metal_init_run
+
_skip_init:
/* Synchronize harts so that secondary harts wait until hart 0 finishes
initializing */
call __metal_synchronize_harts
- /* Check RISC-V isa and enable FS bits if Floating Point architecture. */
+ /* Disable and clear all interrupt sources */
+ li a3, -1
+ csrc mie, a3
+ csrc mip, a3
+
+ /* The delegation CSRs exist if user mode interrupts (N extension) or
+ * supervisor mode (S extension) are supported */
csrr a5, misa
+ lui a4, 0x42
+ and a4, a4, a5
+ beqz a4, 1f
+ csrc mideleg, a3
+ csrc medeleg, a3
+1:
+
+ /* The satp CSR exists if supervisor mode (S extension) is supported */
+ lui a4, 0x40
+ and a4, a4, a5
+ beqz a4, 1f
+ csrc satp, a3
+1:
+
+ /* Check RISC-V isa and enable FS bits if Floating Point architecture. */
li a4, 0x10028
and a5, a5, a4
beqz a5, 1f
@@ -171,6 +217,16 @@ _skip_init:
csrwi fcsr, 0
1:
+ /* Check for vector extension support and enable it if found */
+ csrr a5, misa
+ li a4, 0x200000
+ and a5, a5, a4
+ beqz a5, 1f
+ csrr a5, mstatus
+ ori a5, a5, 0x200
+ csrw mstatus, a5
+1:
+
/* This is a C runtime, so main() is defined to have some arguments. Since
* there's nothing sane the METAL can pass we don't bother with that but
* instead just setup as close to a NOP as we can. */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/nanosleep.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/nanosleep.c
index 8be22104e..d40d2f892 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/nanosleep.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/nanosleep.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/time.h>
-int
-nanosleep(const struct timespec *rqtp, struct timespec *rmtp)
-{
- errno = ENOSYS;
- return -1;
+int nanosleep(const struct timespec *rqtp, struct timespec *rmtp) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/synchronize_harts.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/synchronize_harts.c
deleted file mode 100644
index 3e857d1df..000000000
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/synchronize_harts.c
+++ /dev/null
@@ -1,59 +0,0 @@
-/* Copyright 2019 SiFive, Inc */
-/* SPDX-License-Identifier: Apache-2.0 */
-
-#include <metal/machine.h>
-#include <metal/machine/platform.h>
-#include <metal/io.h>
-#include <metal/cpu.h>
-
-#define METAL_REG(base, offset) (((unsigned long)(base) + (offset)))
-#define METAL_REGW(base, offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_REG((base), (offset))))
-#define METAL_MSIP(base, hart) (METAL_REGW((base),4*(hart)))
-
-/*
- * _synchronize_harts() is called by crt0.S to cause harts > 0 to wait for
- * hart 0 to finish copying the datat section, zeroing the BSS, and running
- * the libc contstructors.
- */
-void _synchronize_harts() {
-#if __METAL_DT_MAX_HARTS > 1
-
- int hart = metal_cpu_get_current_hartid();
- uintptr_t msip_base = 0;
-
- /* Get the base address of the MSIP registers */
-#ifdef __METAL_DT_RISCV_CLINT0_HANDLE
- msip_base = __metal_driver_sifive_clint0_control_base(__METAL_DT_RISCV_CLINT0_HANDLE);
- msip_base += METAL_RISCV_CLINT0_MSIP_BASE;
-#elif __METAL_DT_RISCV_CLIC0_HANDLE
- msip_base = __metal_driver_sifive_clic0_control_base(__METAL_DT_RISCV_CLIC0_HANDLE);
- msip_base += METAL_RISCV_CLIC0_MSIP_BASE;
-#else
-#warning No handle for CLINT or CLIC found, harts may be unsynchronized after init!
-#endif
-
- /* Disable machine interrupts as a precaution */
- __asm__ volatile("csrc mstatus, %0" :: "r" (METAL_MSTATUS_MIE));
-
- if (hart == 0) {
- /* Hart 0 waits for all harts to set their MSIP bit */
- for (int i = 1 ; i < __METAL_DT_MAX_HARTS; i++) {
- while (METAL_MSIP(msip_base, i) == 0) ;
- }
-
- /* Hart 0 clears everyone's MSIP bit */
- for (int i = 1 ; i < __METAL_DT_MAX_HARTS; i++) {
- METAL_MSIP(msip_base, i) = 0;
- }
- } else {
- /* Other harts set their MSIP bit to indicate they're ready */
- METAL_MSIP(msip_base, hart) = 1;
- __asm__ volatile ("fence w,rw");
-
- /* Wait for hart 0 to clear the MSIP bit */
- while (METAL_MSIP(msip_base, hart) == 1) ;
- }
-
-#endif /* __METAL_DT_MAX_HARTS > 1 */
-}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_access.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_access.c
index c0bc1534d..6aa5ccbd4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_access.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_access.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_access(const char *file, int mode)
-{
- errno = ENOSYS;
- return -1;
+int _access(const char *file, int mode) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chdir.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chdir.c
index f33d26a44..b1daf1c6c 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chdir.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chdir.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_chdir(const char *path)
-{
- errno = ENOSYS;
- return -1;
+int _chdir(const char *path) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chmod.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chmod.c
index 67412bf7d..1711f582f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chmod.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chmod.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/types.h>
-int
-_chmod(const char *path, mode_t mode)
-{
- errno = ENOSYS;
- return -1;
+int _chmod(const char *path, mode_t mode) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chown.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chown.c
index 302952eb1..f7edc91ce 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chown.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_chown.c
@@ -1,9 +1,7 @@
-#include <sys/types.h>
#include <errno.h>
+#include <sys/types.h>
-int
-_chown(const char *path, uid_t owner, gid_t group)
-{
- errno = ENOSYS;
- return -1;
+int _chown(const char *path, uid_t owner, gid_t group) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_clock_gettime.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_clock_gettime.c
new file mode 100644
index 000000000..7feb695b3
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_clock_gettime.c
@@ -0,0 +1,60 @@
+#define _POSIX_MONOTONIC_CLOCK 200809L
+#define _POSIX_TIMERS
+#include <errno.h>
+#include <metal/drivers/riscv_cpu.h>
+#include <metal/machine.h>
+#include <time.h>
+
+#ifdef MTIME_RATE_HZ_DEF
+#undef MTIME_RATE_HZ
+#define MTIME_RATE_HZ MTIME_RATE_HZ_DEF
+#endif
+
+#ifndef MTIME_RATE_HZ
+#define MTIME_RATE_HZ 32768
+#endif
+
+#if !defined(mtime_interrupt_controller) && \
+ defined(__METAL_DT_RISCV_CLINT0_HANDLE)
+#define mtime_interrupt_controller __METAL_DT_RISCV_CLINT0_HANDLE
+#endif
+
+#if !defined(mtime_interrupt_controller) && \
+ defined(__METAL_DT_SIFIVE_CLIC0_HANDLE)
+#define mtime_interrupt_controller __METAL_DT_SIFIVE_CLIC0_HANDLE
+#endif
+
+int clock_getres(clockid_t clk_id, struct timespec *res) {
+ switch (clk_id) {
+ case CLOCK_MONOTONIC:
+ res->tv_sec = 0;
+ res->tv_nsec = 1000000000 / MTIME_RATE_HZ;
+ return 0;
+ break;
+ default:
+ errno = EINVAL;
+ return -1;
+ }
+}
+
+int clock_gettime(clockid_t clk_id, struct timespec *tp) {
+ unsigned long long ticks;
+
+ switch (clk_id) {
+ case CLOCK_MONOTONIC:
+ mtime_interrupt_controller->vtable->command_request(
+ mtime_interrupt_controller, METAL_TIMER_MTIME_GET, &ticks);
+ tp->tv_sec = ticks / MTIME_RATE_HZ;
+ tp->tv_nsec = ((ticks % (MTIME_RATE_HZ)) * 1000000000) / MTIME_RATE_HZ;
+ return 0;
+ break;
+ default:
+ errno = EINVAL;
+ return -1;
+ }
+}
+
+int clock_settime(clockid_t clk_id, const struct timespec *tp) {
+ errno = EINVAL;
+ return -1;
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_close.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_close.c
index 26dd6a59e..c09e66dc5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_close.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_close.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_close(int file)
-{
- errno = ENOSYS;
- return -1;
+int _close(int file) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_execve.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_execve.c
index 9ae9f7e50..05d87ea77 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_execve.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_execve.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_execve(const char *name, char *const argv[], char *const env[])
-{
- errno = ENOMEM;
- return -1;
+int _execve(const char *name, char *const argv[], char *const env[]) {
+ errno = ENOMEM;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_exit.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_exit.c
index 35f5f1a16..71883a67b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_exit.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_exit.c
@@ -1,8 +1,7 @@
#include <metal/shutdown.h>
-void
-_exit(int exit_status)
-{
- metal_shutdown(exit_status);
- while (1);
+void _exit(int exit_status) {
+ metal_shutdown(exit_status);
+ while (1)
+ ;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_faccessat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_faccessat.c
index 873d52c2e..eb18b04d5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_faccessat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_faccessat.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_faccessat(int dirfd, const char *file, int mode, int flags)
-{
- errno = ENOSYS;
- return -1;
+int _faccessat(int dirfd, const char *file, int mode, int flags) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fork.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fork.c
index 64e67569f..4a7974f48 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fork.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fork.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_fork()
-{
- errno = ENOSYS;
- return -1;
+int _fork() {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstat.c
index fedc28977..bf4ad144b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstat.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/stat.h>
-int
-_fstat(int file, struct stat *st)
-{
- errno = -ENOSYS;
- return -1;
+int _fstat(int file, struct stat *st) {
+ errno = -ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstatat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstatat.c
index f2f43bd9e..22b825594 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstatat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_fstatat.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/stat.h>
-int
-_fstatat(int dirfd, const char *file, struct stat *st, int flags)
-{
- errno = ENOSYS;
- return -1;
+int _fstatat(int dirfd, const char *file, struct stat *st, int flags) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_ftime.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_ftime.c
index 65c156398..b5ffa7c19 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_ftime.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_ftime.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/timeb.h>
-int
-_ftime(struct timeb *tp)
-{
- errno = ENOSYS;
- return -1;
+int _ftime(struct timeb *tp) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getcwd.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getcwd.c
index 82e8404ee..d8e73de6d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getcwd.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getcwd.c
@@ -1,8 +1,7 @@
#include <errno.h>
+#include <stddef.h>
-char *
-_getcwd(char *buf, size_t size)
-{
- errno = -ENOSYS;
- return NULL;
+char *_getcwd(char *buf, size_t size) {
+ errno = -ENOSYS;
+ return NULL;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getpid.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getpid.c
index 589ad117c..13b48e142 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getpid.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_getpid.c
@@ -1,7 +1,3 @@
#include <errno.h>
-int
-_getpid()
-{
- return 1;
-}
+int _getpid() { return 1; }
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_gettimeofday.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_gettimeofday.c
index 409b2ce2f..22ba5c0cd 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_gettimeofday.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_gettimeofday.c
@@ -2,9 +2,7 @@
#include <metal/timer.h>
#include <sys/time.h>
-int
-_gettimeofday(struct timeval *tp, void *tzp)
-{
+int _gettimeofday(struct timeval *tp, void *tzp) {
int rv;
unsigned long long mcc, timebase;
rv = metal_timer_get_cyclecount(0, &mcc);
@@ -19,3 +17,6 @@ _gettimeofday(struct timeval *tp, void *tzp)
tp->tv_usec = mcc % timebase * 1000000 / timebase;
return 0;
}
+
+extern __typeof(_gettimeofday) gettimeofday
+ __attribute__((__weak__, __alias__("_gettimeofday")));
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_isatty.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_isatty.c
index dd4f1461b..851bc1494 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_isatty.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_isatty.c
@@ -1,7 +1,3 @@
#include <unistd.h>
-int
-_isatty(int file)
-{
- return (file == STDOUT_FILENO);
-}
+int _isatty(int file) { return (file == STDOUT_FILENO); }
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_kill.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_kill.c
index 9003f266f..6f439744a 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_kill.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_kill.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_kill(int pid, int sig)
-{
- errno = ENOSYS;
- return -1;
+int _kill(int pid, int sig) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_link.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_link.c
index 40d5912bc..c3d7c2bcb 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_link.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_link.c
@@ -1,7 +1,6 @@
#include <errno.h>
-int _link(const char *old_name, const char *new_name)
-{
- errno = ENOSYS;
- return -1;
+int _link(const char *old_name, const char *new_name) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lseek.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lseek.c
index d28a781f8..6dab8c3f7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lseek.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lseek.c
@@ -1,9 +1,7 @@
-#include <sys/types.h>
#include <errno.h>
+#include <sys/types.h>
-off_t
-_lseek(int file, off_t ptr, int dir)
-{
- errno = ENOSYS;
- return -1;
+off_t _lseek(int file, off_t ptr, int dir) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lstat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lstat.c
index 97a45855f..76b66a9ba 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lstat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_lstat.c
@@ -1,8 +1,7 @@
#include <errno.h>
#include <sys/stat.h>
-int _lstat(const char *file, struct stat *st)
-{
- errno = ENOSYS;
- return -1;
+int _lstat(const char *file, struct stat *st) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_open.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_open.c
index a59f627f0..df13edb11 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_open.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_open.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_open(const char *name, int flags, int mode)
-{
- errno = ENOSYS;
- return -1;
+int _open(const char *name, int flags, int mode) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_openat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_openat.c
index 206de3bde..15fad8f7f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_openat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_openat.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_openat(int dirfd, const char *name, int flags, int mode)
-{
- errno = ENOSYS;
- return -1;
+int _openat(int dirfd, const char *name, int flags, int mode) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_read.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_read.c
index 15833cabb..147ee30d7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_read.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_read.c
@@ -1,9 +1,7 @@
-#include <sys/types.h>
#include <errno.h>
+#include <sys/types.h>
-ssize_t
-_read(int file, void *ptr, size_t len)
-{
- errno = ENOSYS;
- return -1;
+ssize_t _read(int file, void *ptr, size_t len) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sbrk.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sbrk.c
index cc01c8ffb..9cb42aecb 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sbrk.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sbrk.c
@@ -1,39 +1,43 @@
+#include <metal/scrub.h>
#include <sys/types.h>
-/* brk is handled entirely within the C library. This limits METAL programs that
- * use the C library to be disallowed from dynamically allocating memory
+/* brk is handled entirely within the C library. This limits METAL programs
+ * that use the C library to be disallowed from dynamically allocating memory
* without talking to the C library, but that sounds like a sane way to go
* about it. Note that there is no error checking anywhere in this file, users
* will simply get the relevant error when actually trying to use the memory
* that's been allocated. */
extern char metal_segment_heap_target_start;
extern char metal_segment_heap_target_end;
-static char *brk = &metal_segment_heap_target_start;
+static char *__brk = &metal_segment_heap_target_start;
-int
-_brk(void *addr)
-{
- brk = addr;
- return 0;
+#ifdef _PICOLIBC__
+#define _brk brk
+#define _sbrk sbrk
+#endif
+
+int _brk(void *addr) {
+ __brk = addr;
+ return 0;
}
-char *
-_sbrk(ptrdiff_t incr)
-{
- char *old = brk;
+char *_sbrk(ptrdiff_t incr) {
+ char *old = __brk;
- /* If __heap_size == 0, we can't allocate memory on the heap */
- if(&metal_segment_heap_target_start == &metal_segment_heap_target_end) {
- return (void *)-1;
- }
+ /* If __heap_size == 0, we can't allocate memory on the heap */
+ if (&metal_segment_heap_target_start == &metal_segment_heap_target_end) {
+ return (void *)-1;
+ }
- /* Don't move the break past the end of the heap */
- if ((brk + incr) < &metal_segment_heap_target_end) {
- brk += incr;
- } else {
- brk = &metal_segment_heap_target_end;
- return (void *)-1;
- }
+ /* Don't move the break past the end of the heap */
+ if ((__brk + incr) < &metal_segment_heap_target_end) {
+ __brk += incr;
+ } else {
+ __brk = &metal_segment_heap_target_end;
+ return (void *)-1;
+ }
+ /* Scrub out allocated memory to avoid spurious ECC errors */
+ metal_mem_scrub(old, incr);
- return old;
+ return old;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_stat.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_stat.c
index 3c2e41910..89d6b8b42 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_stat.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_stat.c
@@ -1,9 +1,7 @@
#include <errno.h>
#include <sys/stat.h>
-int
-_stat(const char *file, struct stat *st)
-{
- errno = ENOSYS;
- return -1;
+int _stat(const char *file, struct stat *st) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sysconf.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sysconf.c
index 452a252ae..8d7ddcf1b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sysconf.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_sysconf.c
@@ -1,16 +1,16 @@
-#include <unistd.h>
#include <time.h>
+#include <unistd.h>
/* Get configurable system variables. */
-long
-_sysconf(int name)
-{
- switch (name)
- {
+long _sysconf(int name) {
+ switch (name) {
case _SC_CLK_TCK:
- return CLOCKS_PER_SEC;
+ return CLOCKS_PER_SEC;
}
- return -1;
+ return -1;
}
+
+extern __typeof(_sysconf) sysconf
+ __attribute__((__weak__, __alias__("_sysconf")));
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_times.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_times.c
index 6beedcb30..f8f3e140b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_times.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_times.c
@@ -1,9 +1,32 @@
-#include <sys/times.h>
-#include <sys/time.h>
-#include <metal/timer.h>
#include <errno.h>
+#include <metal/cpu.h>
+#include <metal/timer.h>
+#include <sys/time.h>
+#include <sys/times.h>
-extern int _gettimeofday(struct timeval *, void *);
+/* v * num / den while avoiding overflow
+ *
+ * Modulus on unsigned values is defined as:
+ *
+ * v % den = v - (v / den) * den
+ * v = v % den + (v / den) * den
+ *
+ * This lets us break the computation down as follows:
+ *
+ * r = (v * num) / den
+ * = ((v % den + (v / den) * den) * num) / den
+ * = ((v % den) * num) / den + ((v / den) * den) * num / den
+ * = ((v % den) * num) / den + ((v / den) * num
+ *
+ * As long as num * den fits in 64 bits, then this computation will fit
+ * in 64 bits. CLOCKS_PER_SEC is defined as 1,000,000, so we just need
+ * timebase to be less than about 4,000,000,000,000 (4 trillion).
+ */
+
+static inline unsigned long long
+muldiv(unsigned long long v, unsigned long long num, unsigned long long den) {
+ return (((v % den) * num) / den) + ((v / den) * num);
+}
/* Timing information for current process. From
newlib/libc/include/sys/times.h the tms struct fields are as follows:
@@ -17,26 +40,28 @@ extern int _gettimeofday(struct timeval *, void *);
children's times to zero. Eventually we might want to separately
account for user vs system time, but for now we just return the total
number of cycles since starting the program. */
-clock_t
-_times(struct tms *buf)
-{
- int rv;
- // when called for the first time, initialize t0
- static struct timeval t0;
- if (t0.tv_sec == 0 && t0.tv_usec == 0)
- _gettimeofday (&t0, 0);
-
- struct timeval t;
- _gettimeofday (&t, 0);
-
+clock_t _times(struct tms *buf) {
+ unsigned long long mcc;
unsigned long long timebase;
- rv = metal_timer_get_timebase_frequency(0, &timebase);
- if (rv != 0) {
- return -1;
- }
-
- long long utime = (t.tv_sec - t0.tv_sec) * 1000000 + (t.tv_usec - t0.tv_usec);
- buf->tms_utime = utime * timebase / 1000000;
- buf->tms_stime = buf->tms_cstime = buf->tms_cutime = 0;
- return 0;
+ int hartid = metal_cpu_get_current_hartid();
+
+ metal_timer_get_timebase_frequency(hartid, &timebase);
+ metal_timer_get_cyclecount(hartid, &mcc);
+
+ /*
+ * Convert from native resolution to published resolution.
+ *
+ * Truncating this to 64 bits works because a change of 'c' in
+ * cyclecount will change the return value by
+ * c * CLOCKS_PER_SEC / timebase, so applications will see
+ * time marching forward.
+ */
+ mcc = muldiv(mcc, CLOCKS_PER_SEC, timebase);
+
+ buf->tms_stime = 0;
+ buf->tms_cutime = 0;
+ buf->tms_cstime = 0;
+ return buf->tms_utime = mcc;
}
+
+extern __typeof(_times) times __attribute__((__weak__, __alias__("_times")));
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_unlink.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_unlink.c
index b369d2017..546039a61 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_unlink.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_unlink.c
@@ -1,8 +1,6 @@
#include <errno.h>
-int
-_unlink(const char *name)
-{
- errno = ENOSYS;
- return -1;
+int _unlink(const char *name) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_utime.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_utime.c
index 33d557aa7..5e7389cd1 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_utime.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_utime.c
@@ -1,9 +1,7 @@
#include <errno.h>
struct utimbuf;
-int
-_utime(const char *path, const struct utimbuf *times)
-{
- errno = ENOSYS;
- return -1;
+int _utime(const char *path, const struct utimbuf *times) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_wait.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_wait.c
index 9d459f14c..304f941b4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_wait.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_wait.c
@@ -1,7 +1,6 @@
#include <errno.h>
-int _wait(int *status)
-{
- errno = ENOSYS;
- return -1;
+int _wait(int *status) {
+ errno = ENOSYS;
+ return -1;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_write.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_write.c
index bfcf0cb2b..10881023d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_write.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/gloss/sys_write.c
@@ -1,19 +1,20 @@
+#include <errno.h>
#include <metal/tty.h>
#include <sys/types.h>
-#include <errno.h>
#include <unistd.h>
/* Write to a file. */
-ssize_t
-_write(int file, const void *ptr, size_t len)
-{
- if (file != STDOUT_FILENO) {
- errno = ENOSYS;
- return -1;
- }
+ssize_t _write(int file, const void *ptr, size_t len) {
+ if (file != STDOUT_FILENO) {
+ errno = ENOSYS;
+ return -1;
+ }
- const char *bptr = ptr;
- for (size_t i = 0; i < len; ++i)
- metal_tty_putc(bptr[i]);
- return 0;
+ const char *bptr = ptr;
+ for (size_t i = 0; i < len; ++i)
+ metal_tty_putc(bptr[i]);
+ return 0;
}
+
+extern __typeof(_write) write
+ __attribute__((__weak__, __weak__, __alias__("_write")));
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-git-hooks b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-git-hooks
new file mode 100755
index 000000000..bc6df8702
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-git-hooks
@@ -0,0 +1,9 @@
+#!/bin/bash
+
+mkdir -p .git/hooks
+cat >.git/hooks/post-commit <<EOF
+#!/bin/bash
+# Generated by $0
+touch -c configure.ac
+EOF
+chmod +x .git/hooks/post-commit
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-sh b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-sh
new file mode 100755
index 000000000..c143b8655
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/install-sh
@@ -0,0 +1,508 @@
+#!/bin/sh
+# install - install a program, script, or datafile
+
+scriptversion=2016-01-11.22; # UTC
+
+# This originates from X11R5 (mit/util/scripts/install.sh), which was
+# later released in X11R6 (xc/config/util/install.sh) with the
+# following copyright and license.
+#
+# Copyright (C) 1994 X Consortium
+#
+# Permission is hereby granted, free of charge, to any person obtaining a copy
+# of this software and associated documentation files (the "Software"), to
+# deal in the Software without restriction, including without limitation the
+# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+# sell copies of the Software, and to permit persons to whom the Software is
+# furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be included in
+# all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
+# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+# Except as contained in this notice, the name of the X Consortium shall not
+# be used in advertising or otherwise to promote the sale, use or other deal-
+# ings in this Software without prior written authorization from the X Consor-
+# tium.
+#
+#
+# FSF changes to this file are in the public domain.
+#
+# Calling this script install-sh is preferred over install.sh, to prevent
+# 'make' implicit rules from creating a file called install from it
+# when there is no Makefile.
+#
+# This script is compatible with the BSD install script, but was written
+# from scratch.
+
+tab=' '
+nl='
+'
+IFS=" $tab$nl"
+
+# Set DOITPROG to "echo" to test this script.
+
+doit=${DOITPROG-}
+doit_exec=${doit:-exec}
+
+# Put in absolute file names if you don't have them in your path;
+# or use environment vars.
+
+chgrpprog=${CHGRPPROG-chgrp}
+chmodprog=${CHMODPROG-chmod}
+chownprog=${CHOWNPROG-chown}
+cmpprog=${CMPPROG-cmp}
+cpprog=${CPPROG-cp}
+mkdirprog=${MKDIRPROG-mkdir}
+mvprog=${MVPROG-mv}
+rmprog=${RMPROG-rm}
+stripprog=${STRIPPROG-strip}
+
+posix_mkdir=
+
+# Desired mode of installed file.
+mode=0755
+
+chgrpcmd=
+chmodcmd=$chmodprog
+chowncmd=
+mvcmd=$mvprog
+rmcmd="$rmprog -f"
+stripcmd=
+
+src=
+dst=
+dir_arg=
+dst_arg=
+
+copy_on_change=false
+is_target_a_directory=possibly
+
+usage="\
+Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE
+ or: $0 [OPTION]... SRCFILES... DIRECTORY
+ or: $0 [OPTION]... -t DIRECTORY SRCFILES...
+ or: $0 [OPTION]... -d DIRECTORIES...
+
+In the 1st form, copy SRCFILE to DSTFILE.
+In the 2nd and 3rd, copy all SRCFILES to DIRECTORY.
+In the 4th, create DIRECTORIES.
+
+Options:
+ --help display this help and exit.
+ --version display version info and exit.
+
+ -c (ignored)
+ -C install only if different (preserve the last data modification time)
+ -d create directories instead of installing files.
+ -g GROUP $chgrpprog installed files to GROUP.
+ -m MODE $chmodprog installed files to MODE.
+ -o USER $chownprog installed files to USER.
+ -s $stripprog installed files.
+ -t DIRECTORY install into DIRECTORY.
+ -T report an error if DSTFILE is a directory.
+
+Environment variables override the default commands:
+ CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG
+ RMPROG STRIPPROG
+"
+
+while test $# -ne 0; do
+ case $1 in
+ -c) ;;
+
+ -C) copy_on_change=true;;
+
+ -d) dir_arg=true;;
+
+ -g) chgrpcmd="$chgrpprog $2"
+ shift;;
+
+ --help) echo "$usage"; exit $?;;
+
+ -m) mode=$2
+ case $mode in
+ *' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*)
+ echo "$0: invalid mode: $mode" >&2
+ exit 1;;
+ esac
+ shift;;
+
+ -o) chowncmd="$chownprog $2"
+ shift;;
+
+ -s) stripcmd=$stripprog;;
+
+ -t)
+ is_target_a_directory=always
+ dst_arg=$2
+ # Protect names problematic for 'test' and other utilities.
+ case $dst_arg in
+ -* | [=\(\)!]) dst_arg=./$dst_arg;;
+ esac
+ shift;;
+
+ -T) is_target_a_directory=never;;
+
+ --version) echo "$0 $scriptversion"; exit $?;;
+
+ --) shift
+ break;;
+
+ -*) echo "$0: invalid option: $1" >&2
+ exit 1;;
+
+ *) break;;
+ esac
+ shift
+done
+
+# We allow the use of options -d and -T together, by making -d
+# take the precedence; this is for compatibility with GNU install.
+
+if test -n "$dir_arg"; then
+ if test -n "$dst_arg"; then
+ echo "$0: target directory not allowed when installing a directory." >&2
+ exit 1
+ fi
+fi
+
+if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then
+ # When -d is used, all remaining arguments are directories to create.
+ # When -t is used, the destination is already specified.
+ # Otherwise, the last argument is the destination. Remove it from $@.
+ for arg
+ do
+ if test -n "$dst_arg"; then
+ # $@ is not empty: it contains at least $arg.
+ set fnord "$@" "$dst_arg"
+ shift # fnord
+ fi
+ shift # arg
+ dst_arg=$arg
+ # Protect names problematic for 'test' and other utilities.
+ case $dst_arg in
+ -* | [=\(\)!]) dst_arg=./$dst_arg;;
+ esac
+ done
+fi
+
+if test $# -eq 0; then
+ if test -z "$dir_arg"; then
+ echo "$0: no input file specified." >&2
+ exit 1
+ fi
+ # It's OK to call 'install-sh -d' without argument.
+ # This can happen when creating conditional directories.
+ exit 0
+fi
+
+if test -z "$dir_arg"; then
+ if test $# -gt 1 || test "$is_target_a_directory" = always; then
+ if test ! -d "$dst_arg"; then
+ echo "$0: $dst_arg: Is not a directory." >&2
+ exit 1
+ fi
+ fi
+fi
+
+if test -z "$dir_arg"; then
+ do_exit='(exit $ret); exit $ret'
+ trap "ret=129; $do_exit" 1
+ trap "ret=130; $do_exit" 2
+ trap "ret=141; $do_exit" 13
+ trap "ret=143; $do_exit" 15
+
+ # Set umask so as not to create temps with too-generous modes.
+ # However, 'strip' requires both read and write access to temps.
+ case $mode in
+ # Optimize common cases.
+ *644) cp_umask=133;;
+ *755) cp_umask=22;;
+
+ *[0-7])
+ if test -z "$stripcmd"; then
+ u_plus_rw=
+ else
+ u_plus_rw='% 200'
+ fi
+ cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;;
+ *)
+ if test -z "$stripcmd"; then
+ u_plus_rw=
+ else
+ u_plus_rw=,u+rw
+ fi
+ cp_umask=$mode$u_plus_rw;;
+ esac
+fi
+
+for src
+do
+ # Protect names problematic for 'test' and other utilities.
+ case $src in
+ -* | [=\(\)!]) src=./$src;;
+ esac
+
+ if test -n "$dir_arg"; then
+ dst=$src
+ dstdir=$dst
+ test -d "$dstdir"
+ dstdir_status=$?
+ else
+
+ # Waiting for this to be detected by the "$cpprog $src $dsttmp" command
+ # might cause directories to be created, which would be especially bad
+ # if $src (and thus $dsttmp) contains '*'.
+ if test ! -f "$src" && test ! -d "$src"; then
+ echo "$0: $src does not exist." >&2
+ exit 1
+ fi
+
+ if test -z "$dst_arg"; then
+ echo "$0: no destination specified." >&2
+ exit 1
+ fi
+ dst=$dst_arg
+
+ # If destination is a directory, append the input filename; won't work
+ # if double slashes aren't ignored.
+ if test -d "$dst"; then
+ if test "$is_target_a_directory" = never; then
+ echo "$0: $dst_arg: Is a directory" >&2
+ exit 1
+ fi
+ dstdir=$dst
+ dst=$dstdir/`basename "$src"`
+ dstdir_status=0
+ else
+ dstdir=`dirname "$dst"`
+ test -d "$dstdir"
+ dstdir_status=$?
+ fi
+ fi
+
+ obsolete_mkdir_used=false
+
+ if test $dstdir_status != 0; then
+ case $posix_mkdir in
+ '')
+ # Create intermediate dirs using mode 755 as modified by the umask.
+ # This is like FreeBSD 'install' as of 1997-10-28.
+ umask=`umask`
+ case $stripcmd.$umask in
+ # Optimize common cases.
+ *[2367][2367]) mkdir_umask=$umask;;
+ .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;;
+
+ *[0-7])
+ mkdir_umask=`expr $umask + 22 \
+ - $umask % 100 % 40 + $umask % 20 \
+ - $umask % 10 % 4 + $umask % 2
+ `;;
+ *) mkdir_umask=$umask,go-w;;
+ esac
+
+ # With -d, create the new directory with the user-specified mode.
+ # Otherwise, rely on $mkdir_umask.
+ if test -n "$dir_arg"; then
+ mkdir_mode=-m$mode
+ else
+ mkdir_mode=
+ fi
+
+ posix_mkdir=false
+ case $umask in
+ *[123567][0-7][0-7])
+ # POSIX mkdir -p sets u+wx bits regardless of umask, which
+ # is incompatible with FreeBSD 'install' when (umask & 300) != 0.
+ ;;
+ *)
+ # $RANDOM is not portable (e.g. dash); use it when possible to
+ # lower collision chance
+ tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$
+ trap 'ret=$?; rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 2>/dev/null; exit $ret' 0
+
+ # As "mkdir -p" follows symlinks and we work in /tmp possibly; so
+ # create the $tmpdir first (and fail if unsuccessful) to make sure
+ # that nobody tries to guess the $tmpdir name.
+ if (umask $mkdir_umask &&
+ $mkdirprog $mkdir_mode "$tmpdir" &&
+ exec $mkdirprog $mkdir_mode -p -- "$tmpdir/a/b") >/dev/null 2>&1
+ then
+ if test -z "$dir_arg" || {
+ # Check for POSIX incompatibilities with -m.
+ # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or
+ # other-writable bit of parent directory when it shouldn't.
+ # FreeBSD 6.1 mkdir -m -p sets mode of existing directory.
+ test_tmpdir="$tmpdir/a"
+ ls_ld_tmpdir=`ls -ld "$test_tmpdir"`
+ case $ls_ld_tmpdir in
+ d????-?r-*) different_mode=700;;
+ d????-?--*) different_mode=755;;
+ *) false;;
+ esac &&
+ $mkdirprog -m$different_mode -p -- "$test_tmpdir" && {
+ ls_ld_tmpdir_1=`ls -ld "$test_tmpdir"`
+ test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1"
+ }
+ }
+ then posix_mkdir=:
+ fi
+ rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir"
+ else
+ # Remove any dirs left behind by ancient mkdir implementations.
+ rmdir ./$mkdir_mode ./-p ./-- "$tmpdir" 2>/dev/null
+ fi
+ trap '' 0;;
+ esac;;
+ esac
+
+ if
+ $posix_mkdir && (
+ umask $mkdir_umask &&
+ $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir"
+ )
+ then :
+ else
+
+ # The umask is ridiculous, or mkdir does not conform to POSIX,
+ # or it failed possibly due to a race condition. Create the
+ # directory the slow way, step by step, checking for races as we go.
+
+ case $dstdir in
+ /*) prefix='/';;
+ [-=\(\)!]*) prefix='./';;
+ *) prefix='';;
+ esac
+
+ oIFS=$IFS
+ IFS=/
+ set -f
+ set fnord $dstdir
+ shift
+ set +f
+ IFS=$oIFS
+
+ prefixes=
+
+ for d
+ do
+ test X"$d" = X && continue
+
+ prefix=$prefix$d
+ if test -d "$prefix"; then
+ prefixes=
+ else
+ if $posix_mkdir; then
+ (umask=$mkdir_umask &&
+ $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break
+ # Don't fail if two instances are running concurrently.
+ test -d "$prefix" || exit 1
+ else
+ case $prefix in
+ *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;;
+ *) qprefix=$prefix;;
+ esac
+ prefixes="$prefixes '$qprefix'"
+ fi
+ fi
+ prefix=$prefix/
+ done
+
+ if test -n "$prefixes"; then
+ # Don't fail if two instances are running concurrently.
+ (umask $mkdir_umask &&
+ eval "\$doit_exec \$mkdirprog $prefixes") ||
+ test -d "$dstdir" || exit 1
+ obsolete_mkdir_used=true
+ fi
+ fi
+ fi
+
+ if test -n "$dir_arg"; then
+ { test -z "$chowncmd" || $doit $chowncmd "$dst"; } &&
+ { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } &&
+ { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false ||
+ test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1
+ else
+
+ # Make a couple of temp file names in the proper directory.
+ dsttmp=$dstdir/_inst.$$_
+ rmtmp=$dstdir/_rm.$$_
+
+ # Trap to clean up those temp files at exit.
+ trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0
+
+ # Copy the file name to the temp name.
+ (umask $cp_umask && $doit_exec $cpprog "$src" "$dsttmp") &&
+
+ # and set any options; do chmod last to preserve setuid bits.
+ #
+ # If any of these fail, we abort the whole thing. If we want to
+ # ignore errors from any of these, just make sure not to ignore
+ # errors from the above "$doit $cpprog $src $dsttmp" command.
+ #
+ { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } &&
+ { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } &&
+ { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } &&
+ { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } &&
+
+ # If -C, don't bother to copy if it wouldn't change the file.
+ if $copy_on_change &&
+ old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` &&
+ new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` &&
+ set -f &&
+ set X $old && old=:$2:$4:$5:$6 &&
+ set X $new && new=:$2:$4:$5:$6 &&
+ set +f &&
+ test "$old" = "$new" &&
+ $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1
+ then
+ rm -f "$dsttmp"
+ else
+ # Rename the file to the real destination.
+ $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null ||
+
+ # The rename failed, perhaps because mv can't rename something else
+ # to itself, or perhaps because mv is so ancient that it does not
+ # support -f.
+ {
+ # Now remove or move aside any old file at destination location.
+ # We try this two ways since rm can't unlink itself on some
+ # systems and the destination file might be busy for other
+ # reasons. In this case, the final cleanup might fail but the new
+ # file should still install successfully.
+ {
+ test ! -f "$dst" ||
+ $doit $rmcmd -f "$dst" 2>/dev/null ||
+ { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null &&
+ { $doit $rmcmd -f "$rmtmp" 2>/dev/null; :; }
+ } ||
+ { echo "$0: cannot unlink or rename $dst" >&2
+ (exit 1); exit 1
+ }
+ } &&
+
+ # Now rename the file to the real destination.
+ $doit $mvcmd "$dsttmp" "$dst"
+ }
+ fi || exit 1
+
+ trap '' 0
+ fi
+done
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC0"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/m4/ax_check_compile_flag.m4 b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/m4/ax_check_compile_flag.m4
new file mode 100644
index 000000000..bd753b34d
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/m4/ax_check_compile_flag.m4
@@ -0,0 +1,53 @@
+# ===========================================================================
+# https://www.gnu.org/software/autoconf-archive/ax_check_compile_flag.html
+# ===========================================================================
+#
+# SYNOPSIS
+#
+# AX_CHECK_COMPILE_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS], [INPUT])
+#
+# DESCRIPTION
+#
+# Check whether the given FLAG works with the current language's compiler
+# or gives an error. (Warnings, however, are ignored)
+#
+# ACTION-SUCCESS/ACTION-FAILURE are shell commands to execute on
+# success/failure.
+#
+# If EXTRA-FLAGS is defined, it is added to the current language's default
+# flags (e.g. CFLAGS) when the check is done. The check is thus made with
+# the flags: "CFLAGS EXTRA-FLAGS FLAG". This can for example be used to
+# force the compiler to issue an error when a bad flag is given.
+#
+# INPUT gives an alternative input source to AC_COMPILE_IFELSE.
+#
+# NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this
+# macro in sync with AX_CHECK_{PREPROC,LINK}_FLAG.
+#
+# LICENSE
+#
+# Copyright (c) 2008 Guido U. Draheim <guidod@gmx.de>
+# Copyright (c) 2011 Maarten Bosmans <mkbosmans@gmail.com>
+#
+# Copying and distribution of this file, with or without modification, are
+# permitted in any medium without royalty provided the copyright notice
+# and this notice are preserved. This file is offered as-is, without any
+# warranty.
+
+#serial 6
+
+AC_DEFUN([AX_CHECK_COMPILE_FLAG],
+[AC_PREREQ(2.64)dnl for _AC_LANG_PREFIX and AS_VAR_IF
+AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_[]_AC_LANG_ABBREV[]flags_$4_$1])dnl
+AC_CACHE_CHECK([whether _AC_LANG compiler accepts $1], CACHEVAR, [
+ ax_check_save_flags=$[]_AC_LANG_PREFIX[]FLAGS
+ _AC_LANG_PREFIX[]FLAGS="$[]_AC_LANG_PREFIX[]FLAGS $4 $1"
+ AC_COMPILE_IFELSE([m4_default([$5],[AC_LANG_PROGRAM()])],
+ [AS_VAR_SET(CACHEVAR,[yes])],
+ [AS_VAR_SET(CACHEVAR,[no])])
+ _AC_LANG_PREFIX[]FLAGS=$ax_check_save_flags])
+AS_VAR_IF(CACHEVAR,yes,
+ [m4_default([$2], :)],
+ [m4_default([$3], :)])
+AS_VAR_POPDEF([CACHEVAR])dnl
+])dnl AX_CHECK_COMPILE_FLAGS
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/atomic.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/atomic.h
new file mode 100644
index 000000000..32a33abd7
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/atomic.h
@@ -0,0 +1,259 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__ATOMIC_H
+#define METAL__ATOMIC_H
+
+#include <stdint.h>
+
+#include <metal/compiler.h>
+
+typedef volatile int32_t metal_atomic_t;
+
+#define METAL_ATOMIC_DECLARE(name) \
+ __attribute((section(".data.atomics"))) metal_atomic_t name
+
+#define _METAL_STORE_AMO_ACCESS_FAULT 7
+
+/* This macro stores the memory address in mtval like a normal store/amo access
+ * fault, triggers a trap, and then if execution returns, returns 0 as an
+ * arbitrary choice */
+#define _METAL_TRAP_AMO_ACCESS(addr) \
+ __asm__("csrw mtval, %[atomic]" ::[atomic] "r"(a)); \
+ _metal_trap(_METAL_STORE_AMO_ACCESS_FAULT); \
+ return 0;
+
+/*!
+ * @brief Check if the platform supports atomic operations
+ *
+ * @return 1 if atomic operations are supported, 0 if not
+ */
+__inline__ int32_t metal_atomic_available(void) {
+#ifdef __riscv_atomic
+ return 1;
+#else
+ return 0;
+#endif
+}
+
+/*!
+ * @brief Atomically increment a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to increment
+ * @param increment the amount to increment the value
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_add(metal_atomic_t *a, int32_t increment) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoadd.w %[old], %[increment], (%[atomic])"
+ : [old] "=r"(old)
+ : [increment] "r"(increment), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-AND a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-AND
+ * @param mask the bitmask to AND
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_and(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoand.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-OR a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-OR
+ * @param mask the bitmask to OR
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_or(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoor.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically swap a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param new_value the value to store in the metal_atomic_t
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_swap(metal_atomic_t *a, int32_t new_value) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoswap.w %[old], %[newval], (%[atomic])"
+ : [old] "=r"(old)
+ : [newval] "r"(new_value), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically bitwise-XOR a metal_atomic_t and return its old value
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to bitwise-XOR
+ * @param mask the bitmask to XOR
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_xor(metal_atomic_t *a, int32_t mask) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amoxor.w %[old], %[mask], (%[atomic])"
+ : [old] "=r"(old)
+ : [mask] "r"(mask), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the greater of
+ * its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_max(metal_atomic_t *a, int32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomax.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the (unsigned)
+ * greater of its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ uint32_t metal_atomic_max_u(metal_atomic_t *a, uint32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomaxu.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the lesser of
+ * its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ int32_t metal_atomic_min(metal_atomic_t *a, int32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amomin.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+/*!
+ * @brief Atomically set the value of a memory location to the (unsigned) lesser
+ * of its current value or a value to compare it with.
+ *
+ * If atomics are not supported on the platform, this function will trap with
+ * a Store/AMO access fault.
+ *
+ * @param a The pointer to the value to swap
+ * @param compare the value to compare with the value in memory
+ *
+ * @return The previous value of the metal_atomic_t
+ */
+__inline__ uint32_t metal_atomic_min_u(metal_atomic_t *a, uint32_t compare) {
+#ifdef __riscv_atomic
+ int32_t old;
+ __asm__ volatile("amominu.w %[old], %[compare], (%[atomic])"
+ : [old] "=r"(old)
+ : [compare] "r"(compare), [atomic] "r"(a)
+ : "memory");
+ return old;
+#else
+ _METAL_TRAP_AMO_ACCESS(a);
+#endif
+}
+
+#endif /* METAL__ATOMIC_H */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/button.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/button.h
index 3ae1c143e..bef645967 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/button.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/button.h
@@ -15,7 +15,8 @@ struct metal_button;
struct metal_button_vtable {
int (*button_exist)(struct metal_button *button, char *label);
- struct metal_interrupt* (*interrupt_controller)(struct metal_button *button);
+ struct metal_interrupt *(*interrupt_controller)(
+ struct metal_button *button);
int (*get_interrupt_id)(struct metal_button *button);
};
@@ -35,8 +36,7 @@ struct metal_button {
* @param label The DeviceTree label for the button
* @return A handle for the button
*/
-struct metal_button* metal_button_get(char *label);
-
+struct metal_button *metal_button_get(char *label);
/*!
* @brief Get the interrupt controller for a button
@@ -45,8 +45,10 @@ struct metal_button* metal_button_get(char *label);
* @return A pointer to the interrupt controller responsible for handling
* button interrupts.
*/
-__inline__ struct metal_interrupt*
- metal_button_interrupt_controller(struct metal_button *button) { return button->vtable->interrupt_controller(button); }
+__inline__ struct metal_interrupt *
+metal_button_interrupt_controller(struct metal_button *button) {
+ return button->vtable->interrupt_controller(button);
+}
/*!
* @brief Get the interrupt id for a button
@@ -54,6 +56,8 @@ __inline__ struct metal_interrupt*
* @param button The handle for the button
* @return The interrupt id corresponding to a button.
*/
-__inline__ int metal_button_get_interrupt_id(struct metal_button *button) { return button->vtable->get_interrupt_id(button); }
+__inline__ int metal_button_get_interrupt_id(struct metal_button *button) {
+ return button->vtable->get_interrupt_id(button);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cache.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cache.h
index bad026480..673a8b13e 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cache.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cache.h
@@ -1,4 +1,4 @@
-/* Copyright 2018 SiFive, Inc */
+/* Copyright 2020 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
#ifndef METAL__CACHE_H
@@ -11,39 +11,56 @@
*/
#include <stdint.h>
-struct metal_cache;
-
-struct __metal_cache_vtable {
- void (*init)(struct metal_cache *cache, int ways);
- int (*get_enabled_ways)(struct metal_cache *cache);
- int (*set_enabled_ways)(struct metal_cache *cache, int ways);
-};
-
/*!
* @brief a handle for a cache
+ * Note: To be deprecated in next release.
*/
struct metal_cache {
- const struct __metal_cache_vtable *vtable;
+ uint8_t __no_empty_structs;
};
/*!
+ * @brief Initialize L2 cache controller.
+ * Enables all available cache ways.
+ * @param None
+ * @return 0 If no error
+ */
+int metal_l2cache_init(void);
+
+/*!
+ * @brief Get the current number of enabled L2 cache ways
+ * @param None
+ * @return The current number of enabled L2 cache ways
+ */
+int metal_l2cache_get_enabled_ways(void);
+
+/*!
+ * @brief Enable the requested number of L2 cache ways
+ * @param ways Number of ways to enable
+ * @return 0 if the ways are successfully enabled
+ */
+int metal_l2cache_set_enabled_ways(int ways);
+
+/*!
* @brief Initialize a cache
* @param cache The handle for the cache to initialize
* @param ways The number of ways to enable
*
* Initializes a cache with the requested number of ways enabled.
+ * Note: API to be deprecated in next release.
*/
__inline__ void metal_cache_init(struct metal_cache *cache, int ways) {
- cache->vtable->init(cache, ways);
+ metal_l2cache_init();
}
/*!
* @brief Get the current number of enabled cache ways
* @param cache The handle for the cache
* @return The current number of enabled cache ways
+ * Note: API to be deprecated in next release.
*/
__inline__ int metal_cache_get_enabled_ways(struct metal_cache *cache) {
- return cache->vtable->get_enabled_ways(cache);
+ return metal_l2cache_get_enabled_ways();
}
/*!
@@ -51,9 +68,11 @@ __inline__ int metal_cache_get_enabled_ways(struct metal_cache *cache) {
* @param cache The handle for the cache
* @param ways The number of ways to enabled
* @return 0 if the ways are successfully enabled
+ * Note: API to be deprecated in next release.
*/
-__inline__ int metal_cache_set_enabled_ways(struct metal_cache *cache, int ways) {
- return cache->vtable->set_enabled_ways(cache, ways);
+__inline__ int metal_cache_set_enabled_ways(struct metal_cache *cache,
+ int ways) {
+ return metal_l2cache_set_enabled_ways(ways);
}
/*!
@@ -86,11 +105,4 @@ void metal_dcache_l1_discard(int hartid, uintptr_t address);
*/
int metal_icache_l1_available(int hartid);
-/*!
- * @brief Flush icache for L1 on the requested core
- * @param hartid The core to flush
- * @return None
- */
-void metal_icache_l1_flush(int hartid);
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/clock.h
index 622fc9470..cfe29f6b7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/clock.h
@@ -4,11 +4,12 @@
#ifndef METAL__CLOCK_H
#define METAL__CLOCK_H
-/*!
+/*!
* @file clock.h
* @brief API for manipulating clock sources
*
- * The clock interface allows for controlling the rate of various clocks in the system.
+ * The clock interface allows for controlling the rate of various clocks in the
+ * system.
*/
struct metal_clock;
@@ -45,7 +46,8 @@ typedef struct _metal_clock_callback_t metal_clock_callback;
/*!
* @brief Call all callbacks in the linked list, if any are registered
*/
-__inline__ void _metal_clock_call_all_callbacks(const metal_clock_callback *const list) {
+__inline__ void
+_metal_clock_call_all_callbacks(const metal_clock_callback *const list) {
const metal_clock_callback *current = list;
while (current) {
current->callback(current->priv);
@@ -56,7 +58,9 @@ __inline__ void _metal_clock_call_all_callbacks(const metal_clock_callback *cons
/*!
* @brief Append a callback to the linked list and return the head of the list
*/
-__inline__ metal_clock_callback *_metal_clock_append_to_callbacks(metal_clock_callback *list, metal_clock_callback *const cb) {
+__inline__ metal_clock_callback *
+_metal_clock_append_to_callbacks(metal_clock_callback *list,
+ metal_clock_callback *const cb) {
cb->_next = NULL;
if (!list) {
@@ -78,13 +82,14 @@ __inline__ metal_clock_callback *_metal_clock_append_to_callbacks(metal_clock_ca
* @struct metal_clock
* @brief The handle for a clock
*
- * Clocks are defined as a pointer to a `struct metal_clock`, the contents of which
- * are implementation defined. Users of the clock interface must call functions
- * which accept a `struct metal_clock *` as an argument to interract with the clock.
+ * Clocks are defined as a pointer to a `struct metal_clock`, the contents of
+ * which are implementation defined. Users of the clock interface must call
+ * functions which accept a `struct metal_clock *` as an argument to interract
+ * with the clock.
*
- * Note that no mechanism for obtaining a pointer to a `struct metal_clock` has been
- * defined, making it impossible to call any of these functions without invoking
- * implementation-defined behavior.
+ * Note that no mechanism for obtaining a pointer to a `struct metal_clock` has
+ * been defined, making it impossible to call any of these functions without
+ * invoking implementation-defined behavior.
*/
struct metal_clock {
const struct __metal_clock_vtable *vtable;
@@ -102,7 +107,9 @@ struct metal_clock {
* @param clk The handle for the clock
* @return The current rate of the clock in Hz
*/
-__inline__ long metal_clock_get_rate_hz(const struct metal_clock *clk) { return clk->vtable->get_rate_hz(clk); }
+__inline__ long metal_clock_get_rate_hz(const struct metal_clock *clk) {
+ return clk->vtable->get_rate_hz(clk);
+}
/*!
* @brief Set the current rate of a clock
@@ -115,11 +122,10 @@ __inline__ long metal_clock_get_rate_hz(const struct metal_clock *clk) { return
* to the given rate in Hz. Returns the actual value that's been selected, which
* could be anything!
*
- * Prior to and after the rate change of the clock, this will call the registered
- * pre- and post-rate change callbacks.
+ * Prior to and after the rate change of the clock, this will call the
+ * registered pre- and post-rate change callbacks.
*/
-__inline__ long metal_clock_set_rate_hz(struct metal_clock *clk, long hz)
-{
+__inline__ long metal_clock_set_rate_hz(struct metal_clock *clk, long hz) {
_metal_clock_call_all_callbacks(clk->_pre_rate_change_callback);
long out = clk->vtable->set_rate_hz(clk, hz);
@@ -135,9 +141,11 @@ __inline__ long metal_clock_set_rate_hz(struct metal_clock *clk, long hz)
* @param clk The handle for the clock
* @param cb The callback to be registered
*/
-__inline__ void metal_clock_register_pre_rate_change_callback(struct metal_clock *clk, metal_clock_callback *cb)
-{
- clk->_pre_rate_change_callback = _metal_clock_append_to_callbacks(clk->_pre_rate_change_callback, cb);
+__inline__ void
+metal_clock_register_pre_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb) {
+ clk->_pre_rate_change_callback =
+ _metal_clock_append_to_callbacks(clk->_pre_rate_change_callback, cb);
}
/*!
@@ -146,9 +154,11 @@ __inline__ void metal_clock_register_pre_rate_change_callback(struct metal_clock
* @param clk The handle for the clock
* @param cb The callback to be registered
*/
-__inline__ void metal_clock_register_post_rate_change_callback(struct metal_clock *clk, metal_clock_callback *cb)
-{
- clk->_post_rate_change_callback = _metal_clock_append_to_callbacks(clk->_post_rate_change_callback, cb);
+__inline__ void
+metal_clock_register_post_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb) {
+ clk->_post_rate_change_callback =
+ _metal_clock_append_to_callbacks(clk->_post_rate_change_callback, cb);
}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/compiler.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/compiler.h
index 62c0ea975..80ca5fee4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/compiler.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/compiler.h
@@ -4,18 +4,19 @@
#ifndef METAL__COMPILER_H
#define METAL__COMPILER_H
-#define __METAL_DECLARE_VTABLE(type) \
- extern const struct type type;
+#define __METAL_DECLARE_VTABLE(type) extern const struct type type;
-#define __METAL_DEFINE_VTABLE(type) \
- const struct type type
+#define __METAL_DEFINE_VTABLE(type) const struct type type
-#define __METAL_GET_FIELD(reg, mask) \
+#define __METAL_GET_FIELD(reg, mask) \
(((reg) & (mask)) / ((mask) & ~((mask) << 1)))
/* Set field with mask for a given value */
-#define __METAL_SET_FIELD(reg, mask, val) \
- (((reg) & ~(mask)) | (((val) * ((mask) & ~((mask) << 1))) & (mask)))
+#define __METAL_SET_FIELD(reg, mask, val) \
+ (((reg) & ~(mask)) | (((val) * ((mask) & ~((mask) << 1))) & (mask)))
+
+#define __METAL_MIN(a, b) ((a) < (b) ? (a) : (b))
+#define __METAL_MAX(a, b) ((a) > (b) ? (a) : (b))
void _metal_trap(int ecode);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cpu.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cpu.h
index dbd3dbfb5..98d7e6680 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cpu.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/cpu.h
@@ -9,33 +9,35 @@
#ifndef METAL__CPU_H
#define METAL__CPU_H
-#include <stdint.h>
#include <metal/interrupt.h>
+#include <stdint.h>
struct metal_cpu;
/*!
* @brief Function signature for exception handlers
*/
-typedef void (*metal_exception_handler_t) (struct metal_cpu *cpu, int ecode);
+typedef void (*metal_exception_handler_t)(struct metal_cpu *cpu, int ecode);
struct metal_cpu_vtable {
unsigned long long (*mcycle_get)(struct metal_cpu *cpu);
unsigned long long (*timebase_get)(struct metal_cpu *cpu);
unsigned long long (*mtime_get)(struct metal_cpu *cpu);
int (*mtimecmp_set)(struct metal_cpu *cpu, unsigned long long time);
- struct metal_interrupt* (*tmr_controller_interrupt)(struct metal_cpu *cpu);
+ struct metal_interrupt *(*tmr_controller_interrupt)(struct metal_cpu *cpu);
int (*get_tmr_interrupt_id)(struct metal_cpu *cpu);
- struct metal_interrupt* (*sw_controller_interrupt)(struct metal_cpu *cpu);
+ struct metal_interrupt *(*sw_controller_interrupt)(struct metal_cpu *cpu);
int (*get_sw_interrupt_id)(struct metal_cpu *cpu);
int (*set_sw_ipi)(struct metal_cpu *cpu, int hartid);
int (*clear_sw_ipi)(struct metal_cpu *cpu, int hartid);
int (*get_msip)(struct metal_cpu *cpu, int hartid);
- struct metal_interrupt* (*controller_interrupt)(struct metal_cpu *cpu);
- int (*exception_register)(struct metal_cpu *cpu, int ecode, metal_exception_handler_t handler);
+ struct metal_interrupt *(*controller_interrupt)(struct metal_cpu *cpu);
+ int (*exception_register)(struct metal_cpu *cpu, int ecode,
+ metal_exception_handler_t handler);
int (*get_ilen)(struct metal_cpu *cpu, uintptr_t epc);
uintptr_t (*get_epc)(struct metal_cpu *cpu);
int (*set_epc)(struct metal_cpu *cpu, uintptr_t epc);
+ struct metal_buserror *(*get_buserror)(struct metal_cpu *cpu);
};
/*! @brief A device handle for a CPU hart
@@ -49,7 +51,7 @@ struct metal_cpu {
* @param hartid The ID of the desired CPU hart
* @return A pointer to the CPU device handle
*/
-struct metal_cpu* metal_cpu_get(unsigned int hartid);
+struct metal_cpu *metal_cpu_get(unsigned int hartid);
/*! @brief Get the hartid of the CPU hart executing this function
*
@@ -57,7 +59,7 @@ struct metal_cpu* metal_cpu_get(unsigned int hartid);
int metal_cpu_get_current_hartid(void);
/*! @brief Get the number of CPU harts
- *
+ *
* @return The number of CPU harts */
int metal_cpu_get_num_harts(void);
@@ -68,8 +70,9 @@ int metal_cpu_get_num_harts(void);
* @param cpu The CPU device handle
* @return The value of the CPU cycle count timer
*/
-__inline__ unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu)
-{ return cpu->vtable->mcycle_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu) {
+ return cpu->vtable->mcycle_get(cpu);
+}
/*! @brief Get the timebase of the CPU
*
@@ -78,8 +81,9 @@ __inline__ unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu)
* @param cpu The CPU device handle
* @return The value of the cycle count timer timebase
*/
-__inline__ unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu)
-{ return cpu->vtable->timebase_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu) {
+ return cpu->vtable->timebase_get(cpu);
+}
/*! @brief Get the value of the mtime RTC
*
@@ -90,8 +94,9 @@ __inline__ unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu)
* @param cpu The CPU device handle
* @return The value of mtime, or 0 if failure
*/
-__inline__ unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu)
-{ return cpu->vtable->mtime_get(cpu); }
+__inline__ unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu) {
+ return cpu->vtable->mtime_get(cpu);
+}
/*! @brief Set the value of the RTC mtimecmp RTC
*
@@ -103,20 +108,24 @@ __inline__ unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu)
* @param time The value to set the compare register to
* @return The value of mtimecmp or -1 if error
*/
-__inline__ int metal_cpu_set_mtimecmp(struct metal_cpu *cpu, unsigned long long time)
-{ return cpu->vtable->mtimecmp_set(cpu, time); }
+__inline__ int metal_cpu_set_mtimecmp(struct metal_cpu *cpu,
+ unsigned long long time) {
+ return cpu->vtable->mtimecmp_set(cpu, time);
+}
/*! @brief Get a reference to RTC timer interrupt controller
*
- * Get a reference to the interrupt controller for the real-time clock interrupt.
- * The controller returned by this function must be initialized before any interrupts
- * are registered or enabled with it.
+ * Get a reference to the interrupt controller for the real-time clock
+ * interrupt. The controller returned by this function must be initialized
+ * before any interrupts are registered or enabled with it.
*
* @param cpu The CPU device handle
* @return A pointer to the timer interrupt handle
*/
-__inline__ struct metal_interrupt* metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->tmr_controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->tmr_controller_interrupt(cpu);
+}
/*! @brief Get the RTC timer interrupt id
*
@@ -125,20 +134,23 @@ __inline__ struct metal_interrupt* metal_cpu_timer_interrupt_controller(struct m
* @param cpu The CPU device handle
* @return The timer interrupt ID
*/
-__inline__ int metal_cpu_timer_get_interrupt_id(struct metal_cpu *cpu)
-{ return cpu->vtable->get_tmr_interrupt_id(cpu); }
+__inline__ int metal_cpu_timer_get_interrupt_id(struct metal_cpu *cpu) {
+ return cpu->vtable->get_tmr_interrupt_id(cpu);
+}
/*! @brief Get a reference to the software interrupt controller
*
* Get a reference to the interrupt controller for the software/inter-process
- * interrupt. The controller returned by this function must be initialized before
- * any interrupts are registered or enabled with it.
+ * interrupt. The controller returned by this function must be initialized
+ * before any interrupts are registered or enabled with it.
*
* @param cpu The CPU device handle
* @return A pointer to the software interrupt handle
*/
-__inline__ struct metal_interrupt* metal_cpu_software_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->sw_controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_software_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->sw_controller_interrupt(cpu);
+}
/*! @brief Get the software interrupt id
*
@@ -147,8 +159,9 @@ __inline__ struct metal_interrupt* metal_cpu_software_interrupt_controller(struc
* @param cpu The CPU device handle
* @return the software interrupt ID
*/
-__inline__ int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu)
-{ return cpu->vtable->get_sw_interrupt_id(cpu); }
+__inline__ int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu) {
+ return cpu->vtable->get_sw_interrupt_id(cpu);
+}
/*!
* @brief Set the inter-process interrupt for a hart
@@ -161,8 +174,9 @@ __inline__ int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu)
* @param hartid The CPU hart ID to be interrupted
* @return 0 upon success
*/
-__inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->set_sw_ipi(cpu, hartid); }
+__inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->set_sw_ipi(cpu, hartid);
+}
/*!
* @brief Clear the inter-process interrupt for a hart
@@ -175,8 +189,9 @@ __inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid)
* @param hartid The CPU hart ID to clear
* @return 0 upon success
*/
-__inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->clear_sw_ipi(cpu, hartid); }
+__inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->clear_sw_ipi(cpu, hartid);
+}
/*!
* @brief Get the value of MSIP for the given hart
@@ -190,8 +205,9 @@ __inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid)
* @param hartid The CPU hart to read
* @return 0 upon success
*/
-__inline__ int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid)
-{ return cpu->vtable->get_msip(cpu, hartid); }
+__inline__ int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid) {
+ return cpu->vtable->get_msip(cpu, hartid);
+}
/*!
* @brief Get the interrupt controller for the CPU
@@ -204,22 +220,26 @@ __inline__ int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid)
* @param cpu The CPU device handle
* @return The handle for the CPU interrupt controller
*/
-__inline__ struct metal_interrupt* metal_cpu_interrupt_controller(struct metal_cpu *cpu)
-{ return cpu->vtable->controller_interrupt(cpu); }
+__inline__ struct metal_interrupt *
+metal_cpu_interrupt_controller(struct metal_cpu *cpu) {
+ return cpu->vtable->controller_interrupt(cpu);
+}
/*!
* @brief Register an exception handler
- *
- * Register an exception handler for the CPU. The CPU interrupt controller must be initialized
- * before this function is called.
+ *
+ * Register an exception handler for the CPU. The CPU interrupt controller must
+ * be initialized before this function is called.
*
* @param cpu The CPU device handle
* @param ecode The exception code to register a handler for
* @param handler Callback function for the exception handler
* @return 0 upon success
*/
-__inline__ int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode, metal_exception_handler_t handler)
-{ return cpu->vtable->exception_register(cpu, ecode, handler); }
+__inline__ int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode,
+ metal_exception_handler_t handler) {
+ return cpu->vtable->exception_register(cpu, ecode, handler);
+}
/*!
* @brief Get the length of an instruction in bytes
@@ -237,8 +257,10 @@ __inline__ int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode, me
* @param epc The address of the instruction to measure
* @return the length of the instruction in bytes
*/
-__inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t epc)
-{ return cpu->vtable->get_ilen(cpu, epc); }
+__inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu,
+ uintptr_t epc) {
+ return cpu->vtable->get_ilen(cpu, epc);
+}
/*!
* @brief Get the program counter of the current exception.
@@ -249,8 +271,9 @@ __inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t
* @param cpu The CPU device handle
* @return The value of the program counter at the time of the exception
*/
-__inline__ uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu)
-{ return cpu->vtable->get_epc(cpu); }
+__inline__ uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu) {
+ return cpu->vtable->get_epc(cpu);
+}
/*!
* @brief Set the exception program counter
@@ -265,7 +288,20 @@ __inline__ uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu)
* @param epc The address to set the exception program counter to
* @return 0 upon success
*/
-__inline__ int metal_cpu_set_exception_pc(struct metal_cpu *cpu, uintptr_t epc)
-{ return cpu->vtable->set_epc(cpu, epc); }
+__inline__ int metal_cpu_set_exception_pc(struct metal_cpu *cpu,
+ uintptr_t epc) {
+ return cpu->vtable->set_epc(cpu, epc);
+}
+
+/*!
+ * @brief Get the handle for the hart's bus error unit
+ *
+ * @param cpu The CPU device handle
+ * @return A pointer to the bus error unit handle
+ */
+__inline__ struct metal_buserror *
+metal_cpu_get_buserror(struct metal_cpu *cpu) {
+ return cpu->vtable->get_buserror(cpu);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/csr.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/csr.h
new file mode 100644
index 000000000..8375d8a44
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/csr.h
@@ -0,0 +1,32 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__CSR_H
+#define METAL__CSR_H
+
+#include <metal/compiler.h>
+#include <stddef.h>
+#include <stdint.h>
+
+/*!
+ * @file csr.h
+ * @brief A collection of APIs for get and set CSR registers
+ */
+
+/*!
+ * @brief Read a given CSR register without checking validity of CSR offset
+ * @param crs Register label or hex value offset to read from
+ * @param value Variable name of uintprt_t type to get the value
+ */
+#define METAL_CPU_GET_CSR(reg, value) \
+ __asm__ volatile("csrr %0, " #reg : "=r"(value));
+
+/*!
+ * @brief Write to a given CSR register without checking validity of CSR offset
+ * @param crs Register label or hex value offset to write to
+ * @param value Variable name of uintprt_t type to set the value
+ */
+#define METAL_CPU_SET_CSR(reg, value) \
+ __asm__ volatile("csrw " #reg ", %0" : : "r"(value));
+
+#endif // METAL__CSR_H
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-clock.h
index 2647c5981..b25f54144 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-clock.h
@@ -6,8 +6,8 @@
struct __metal_driver_fixed_clock;
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
struct __metal_driver_vtable_fixed_clock {
struct __metal_clock_vtable clock;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-factor-clock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-factor-clock.h
index 936ce8d77..84e4fd580 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-factor-clock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/fixed-factor-clock.h
@@ -6,8 +6,8 @@
struct __metal_driver_fixed_factor_clock;
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
struct __metal_driver_vtable_fixed_factor_clock {
struct __metal_clock_vtable clock;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_clint0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_clint0.h
index 08d571e1c..ceda473e2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_clint0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_clint0.h
@@ -21,4 +21,7 @@ struct __metal_driver_riscv_clint0 {
};
#undef __METAL_MACHINE_MACROS
+int __metal_driver_riscv_clint0_command_request(
+ struct metal_interrupt *controller, int command, void *data);
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_cpu.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_cpu.h
index ca91e0a95..f3005f01f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_cpu.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_cpu.h
@@ -4,152 +4,154 @@
#ifndef METAL__DRIVERS__RISCV_CPU_H
#define METAL__DRIVERS__RISCV_CPU_H
-#include <stdint.h>
-#include <metal/cpu.h>
#include <metal/compiler.h>
+#include <metal/cpu.h>
+#include <stdint.h>
-#define METAL_MAX_CORES 8
-#define METAL_MAX_MI 32 /* Per ISA MCause interrupts 32+ are Reserved */
-#define METAL_MAX_ME 12 /* Per ISA Exception codes 12+ are Reserved */
-#define METAL_DEFAULT_RTC_FREQ 32768
-
-#define METAL_DISABLE 0
-#define METAL_ENABLE 1
-
-#define METAL_ISA_A_EXTENSIONS 0x0001
-#define METAL_ISA_C_EXTENSIONS 0x0004
-#define METAL_ISA_D_EXTENSIONS 0x0008
-#define METAL_ISA_E_EXTENSIONS 0x0010
-#define METAL_ISA_F_EXTENSIONS 0x0020
-#define METAL_ISA_G_EXTENSIONS 0x0040
-#define METAL_ISA_I_EXTENSIONS 0x0100
-#define METAL_ISA_M_EXTENSIONS 0x1000
-#define METAL_ISA_N_EXTENSIONS 0x2000
-#define METAL_ISA_Q_EXTENSIONS 0x10000
-#define METAL_ISA_S_EXTENSIONS 0x40000
-#define METAL_ISA_U_EXTENSIONS 0x100000
-#define METAL_ISA_V_EXTENSIONS 0x200000
-#define METAL_ISA_XL32_EXTENSIONS 0x40000000UL
-#define METAL_ISA_XL64_EXTENSIONS 0x8000000000000000UL
+#define METAL_MAX_CORES 8
+#define METAL_MAX_MI 32 /* Per ISA MCause interrupts 32+ are Reserved */
+#define METAL_MAX_ME 12 /* Per ISA Exception codes 12+ are Reserved */
+#define METAL_DEFAULT_RTC_FREQ 32768
+
+#define METAL_DISABLE 0
+#define METAL_ENABLE 1
+
+#define METAL_ISA_A_EXTENSIONS 0x0001
+#define METAL_ISA_C_EXTENSIONS 0x0004
+#define METAL_ISA_D_EXTENSIONS 0x0008
+#define METAL_ISA_E_EXTENSIONS 0x0010
+#define METAL_ISA_F_EXTENSIONS 0x0020
+#define METAL_ISA_G_EXTENSIONS 0x0040
+#define METAL_ISA_I_EXTENSIONS 0x0100
+#define METAL_ISA_M_EXTENSIONS 0x1000
+#define METAL_ISA_N_EXTENSIONS 0x2000
+#define METAL_ISA_Q_EXTENSIONS 0x10000
+#define METAL_ISA_S_EXTENSIONS 0x40000
+#define METAL_ISA_U_EXTENSIONS 0x100000
+#define METAL_ISA_V_EXTENSIONS 0x200000
+#define METAL_ISA_XL32_EXTENSIONS 0x40000000UL
+#define METAL_ISA_XL64_EXTENSIONS 0x8000000000000000UL
#define METAL_ISA_XL128_EXTENSIONS 0xC000000000000000UL
-#define METAL_MTVEC_DIRECT 0x00
-#define METAL_MTVEC_VECTORED 0x01
-#define METAL_MTVEC_CLIC 0x02
-#define METAL_MTVEC_CLIC_VECTORED 0x03
-#define METAL_MTVEC_CLIC_RESERVED 0x3C
-#define METAL_MTVEC_MASK 0x3F
+#define METAL_MTVEC_DIRECT 0x00
+#define METAL_MTVEC_VECTORED 0x01
+#define METAL_MTVEC_CLIC 0x02
+#define METAL_MTVEC_CLIC_VECTORED 0x03
+#define METAL_MTVEC_CLIC_RESERVED 0x3C
+#define METAL_MTVEC_MASK 0x3F
#if __riscv_xlen == 32
-#define METAL_MCAUSE_INTR 0x80000000UL
-#define METAL_MCAUSE_CAUSE 0x000003FFUL
+#define METAL_MCAUSE_INTR 0x80000000UL
+#define METAL_MCAUSE_CAUSE 0x000003FFUL
#else
-#define METAL_MCAUSE_INTR 0x8000000000000000UL
-#define METAL_MCAUSE_CAUSE 0x00000000000003FFUL
+#define METAL_MCAUSE_INTR 0x8000000000000000UL
+#define METAL_MCAUSE_CAUSE 0x00000000000003FFUL
#endif
-#define METAL_MCAUSE_MINHV 0x40000000UL
-#define METAL_MCAUSE_MPP 0x30000000UL
-#define METAL_MCAUSE_MPIE 0x08000000UL
-#define METAL_MCAUSE_MPIL 0x00FF0000UL
-#define METAL_MSTATUS_MIE 0x00000008UL
-#define METAL_MSTATUS_MPIE 0x00000080UL
-#define METAL_MSTATUS_MPP 0x00001800UL
-#define METAL_MSTATUS_FS_INIT 0x00002000UL
-#define METAL_MSTATUS_FS_CLEAN 0x00004000UL
-#define METAL_MSTATUS_FS_DIRTY 0x00006000UL
-#define METAL_MSTATUS_MPRV 0x00020000UL
-#define METAL_MSTATUS_MXR 0x00080000UL
-#define METAL_MINTSTATUS_MIL 0xFF000000UL
-#define METAL_MINTSTATUS_SIL 0x0000FF00UL
-#define METAL_MINTSTATUS_UIL 0x000000FFUL
-
-#define METAL_LOCAL_INTR(X) (16 + X)
-#define METAL_MCAUSE_EVAL(cause) (cause & METAL_MCAUSE_INTR)
-#define METAL_INTERRUPT(cause) (METAL_MCAUSE_EVAL(cause) ? 1 : 0)
-#define METAL_EXCEPTION(cause) (METAL_MCAUSE_EVAL(cause) ? 0 : 1)
-#define METAL_SW_INTR_EXCEPTION (METAL_MCAUSE_INTR + 3)
-#define METAL_TMR_INTR_EXCEPTION (METAL_MCAUSE_INTR + 7)
-#define METAL_EXT_INTR_EXCEPTION (METAL_MCAUSE_INTR + 11)
+#define METAL_MCAUSE_MINHV 0x40000000UL
+#define METAL_MCAUSE_MPP 0x30000000UL
+#define METAL_MCAUSE_MPIE 0x08000000UL
+#define METAL_MCAUSE_MPIL 0x00FF0000UL
+#define METAL_MSTATUS_MIE 0x00000008UL
+#define METAL_MSTATUS_MPIE 0x00000080UL
+#define METAL_MSTATUS_MPP 0x00001800UL
+#define METAL_MSTATUS_FS_INIT 0x00002000UL
+#define METAL_MSTATUS_FS_CLEAN 0x00004000UL
+#define METAL_MSTATUS_FS_DIRTY 0x00006000UL
+#define METAL_MSTATUS_MPRV 0x00020000UL
+#define METAL_MSTATUS_MXR 0x00080000UL
+#define METAL_MINTSTATUS_MIL 0xFF000000UL
+#define METAL_MINTSTATUS_SIL 0x0000FF00UL
+#define METAL_MINTSTATUS_UIL 0x000000FFUL
+
+#define METAL_LOCAL_INTR(X) (16 + X)
+#define METAL_MCAUSE_EVAL(cause) (cause & METAL_MCAUSE_INTR)
+#define METAL_INTERRUPT(cause) (METAL_MCAUSE_EVAL(cause) ? 1 : 0)
+#define METAL_EXCEPTION(cause) (METAL_MCAUSE_EVAL(cause) ? 0 : 1)
+#define METAL_SW_INTR_EXCEPTION (METAL_MCAUSE_INTR + 3)
+#define METAL_TMR_INTR_EXCEPTION (METAL_MCAUSE_INTR + 7)
+#define METAL_EXT_INTR_EXCEPTION (METAL_MCAUSE_INTR + 11)
#define METAL_LOCAL_INTR_EXCEPTION(X) (METAL_MCAUSE_INTR + METAL_LOCAL_INTR(X))
-#define METAL_LOCAL_INTR_RESERVE0 1
-#define METAL_LOCAL_INTR_RESERVE1 2
-#define METAL_LOCAL_INTR_RESERVE2 4
-#define METAL_LOCAL_INTERRUPT_SW 8 /* Bit3 0x008 */
-#define METAL_LOCAL_INTR_RESERVE4 16
-#define METAL_LOCAL_INTR_RESERVE5 32
-#define METAL_LOCAL_INTR_RESERVE6 64
-#define METAL_LOCAL_INTERRUPT_TMR 128 /* Bit7 0x080 */
-#define METAL_LOCAL_INTR_RESERVE8 256
-#define METAL_LOCAL_INTR_RESERVE9 512
-#define METAL_LOCAL_INTR_RESERVE10 1024
-#define METAL_LOCAL_INTERRUPT_EXT 2048 /* Bit11 0x800 */
+#define METAL_LOCAL_INTR_RESERVE0 1
+#define METAL_LOCAL_INTR_RESERVE1 2
+#define METAL_LOCAL_INTR_RESERVE2 4
+#define METAL_LOCAL_INTERRUPT_SW 8 /* Bit3 0x008 */
+#define METAL_LOCAL_INTR_RESERVE4 16
+#define METAL_LOCAL_INTR_RESERVE5 32
+#define METAL_LOCAL_INTR_RESERVE6 64
+#define METAL_LOCAL_INTERRUPT_TMR 128 /* Bit7 0x080 */
+#define METAL_LOCAL_INTR_RESERVE8 256
+#define METAL_LOCAL_INTR_RESERVE9 512
+#define METAL_LOCAL_INTR_RESERVE10 1024
+#define METAL_LOCAL_INTERRUPT_EXT 2048 /* Bit11 0x800 */
/* Bit12 to Bit15 are Reserved */
-#define METAL_LOCAL_INTERRUPT(X) (0x10000 << X) /* Bit16+ Start of Custom Local Interrupt */
-#define METAL_MIE_INTERRUPT METAL_MSTATUS_MIE
+#define METAL_LOCAL_INTERRUPT(X) \
+ (0x10000 << X) /* Bit16+ Start of Custom Local Interrupt */
+#define METAL_MIE_INTERRUPT METAL_MSTATUS_MIE
-#define METAL_INSN_LENGTH_MASK 3
-#define METAL_INSN_NOT_COMPRESSED 3
+#define METAL_INSN_LENGTH_MASK 3
+#define METAL_INSN_NOT_COMPRESSED 3
typedef enum {
- METAL_MACHINE_PRIVILEGE_MODE,
- METAL_SUPERVISOR_PRIVILEGE_MODE,
- METAL_USER_PRIVILEGE_MODE,
+ METAL_MACHINE_PRIVILEGE_MODE,
+ METAL_SUPERVISOR_PRIVILEGE_MODE,
+ METAL_USER_PRIVILEGE_MODE,
} metal_privilege_mode_e;
typedef enum {
- METAL_INTERRUPT_ID_BASE,
- METAL_INTERRUPT_ID_SW = (METAL_INTERRUPT_ID_BASE + 3),
- METAL_INTERRUPT_ID_TMR = (METAL_INTERRUPT_ID_BASE + 7),
- METAL_INTERRUPT_ID_EXT = (METAL_INTERRUPT_ID_BASE + 11),
- METAL_INTERRUPT_ID_CSW = (METAL_INTERRUPT_ID_BASE + 12),
- METAL_INTERRUPT_ID_LC0 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(0)),
- METAL_INTERRUPT_ID_LC1 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(1)),
- METAL_INTERRUPT_ID_LC2 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(2)),
- METAL_INTERRUPT_ID_LC3 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(3)),
- METAL_INTERRUPT_ID_LC4 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(4)),
- METAL_INTERRUPT_ID_LC5 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(5)),
- METAL_INTERRUPT_ID_LC6 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(6)),
- METAL_INTERRUPT_ID_LC7 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(7)),
- METAL_INTERRUPT_ID_LC8 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(8)),
- METAL_INTERRUPT_ID_LC9 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(9)),
- METAL_INTERRUPT_ID_LC10 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(10)),
- METAL_INTERRUPT_ID_LC11 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(11)),
- METAL_INTERRUPT_ID_LC12 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(12)),
- METAL_INTERRUPT_ID_LC13 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(13)),
- METAL_INTERRUPT_ID_LC14 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(14)),
- METAL_INTERRUPT_ID_LC15 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(15)),
- METAL_INTERRUPT_ID_LCMX,
- METAL_INTERRUPT_ID_GL0 = METAL_INTERRUPT_ID_LCMX,
- METAL_INTERRUPT_ID_GLMX = (METAL_MCAUSE_CAUSE + 1),
+ METAL_INTERRUPT_ID_BASE,
+ METAL_INTERRUPT_ID_SW = (METAL_INTERRUPT_ID_BASE + 3),
+ METAL_INTERRUPT_ID_TMR = (METAL_INTERRUPT_ID_BASE + 7),
+ METAL_INTERRUPT_ID_EXT = (METAL_INTERRUPT_ID_BASE + 11),
+ METAL_INTERRUPT_ID_CSW = (METAL_INTERRUPT_ID_BASE + 12),
+ METAL_INTERRUPT_ID_LC0 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(0)),
+ METAL_INTERRUPT_ID_LC1 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(1)),
+ METAL_INTERRUPT_ID_LC2 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(2)),
+ METAL_INTERRUPT_ID_LC3 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(3)),
+ METAL_INTERRUPT_ID_LC4 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(4)),
+ METAL_INTERRUPT_ID_LC5 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(5)),
+ METAL_INTERRUPT_ID_LC6 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(6)),
+ METAL_INTERRUPT_ID_LC7 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(7)),
+ METAL_INTERRUPT_ID_LC8 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(8)),
+ METAL_INTERRUPT_ID_LC9 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(9)),
+ METAL_INTERRUPT_ID_LC10 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(10)),
+ METAL_INTERRUPT_ID_LC11 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(11)),
+ METAL_INTERRUPT_ID_LC12 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(12)),
+ METAL_INTERRUPT_ID_LC13 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(13)),
+ METAL_INTERRUPT_ID_LC14 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(14)),
+ METAL_INTERRUPT_ID_LC15 = (METAL_INTERRUPT_ID_BASE + METAL_LOCAL_INTR(15)),
+ METAL_INTERRUPT_ID_LCMX,
+ METAL_INTERRUPT_ID_GL0 = METAL_INTERRUPT_ID_LCMX,
+ METAL_INTERRUPT_ID_GLMX = (METAL_MCAUSE_CAUSE + 1),
+ METAL_INTERRUPT_ID_BEU = 128,
} metal_interrupt_id_e;
typedef enum {
- METAL_IAM_EXCEPTION_CODE, /* Instruction address misaligned */
- METAL_IAF_EXCEPTION_CODE, /* Instruction access faultd */
- METAL_II_EXCEPTION_CODE, /* Illegal instruction */
- METAL_BREAK_EXCEPTION_CODE, /* Breakpoint */
- METAL_LAM_EXCEPTION_CODE, /* Load address misaligned */
- METAL_LAF_EXCEPTION_CODE, /* Load access fault */
- METAL_SAMOAM_EXCEPTION_CODE, /* Store/AMO address misaligned */
- METAL_SAMOAF_EXCEPTION_CODE, /* Store/AMO access fault */
- METAL_ECALL_U_EXCEPTION_CODE, /* Environment call from U-mode */
- METAL_R9_EXCEPTION_CODE, /* Reserved */
- METAL_R10_EXCEPTION_CODE, /* Reserved */
- METAL_ECALL_M_EXCEPTION_CODE, /* Environment call from M-mode */
- METAL_MAX_EXCEPTION_CODE,
+ METAL_IAM_EXCEPTION_CODE, /* Instruction address misaligned */
+ METAL_IAF_EXCEPTION_CODE, /* Instruction access faultd */
+ METAL_II_EXCEPTION_CODE, /* Illegal instruction */
+ METAL_BREAK_EXCEPTION_CODE, /* Breakpoint */
+ METAL_LAM_EXCEPTION_CODE, /* Load address misaligned */
+ METAL_LAF_EXCEPTION_CODE, /* Load access fault */
+ METAL_SAMOAM_EXCEPTION_CODE, /* Store/AMO address misaligned */
+ METAL_SAMOAF_EXCEPTION_CODE, /* Store/AMO access fault */
+ METAL_ECALL_U_EXCEPTION_CODE, /* Environment call from U-mode */
+ METAL_R9_EXCEPTION_CODE, /* Reserved */
+ METAL_R10_EXCEPTION_CODE, /* Reserved */
+ METAL_ECALL_M_EXCEPTION_CODE, /* Environment call from M-mode */
+ METAL_MAX_EXCEPTION_CODE,
} metal_exception_code_e;
typedef enum {
- METAL_TIMER_MTIME_GET = 1,
- METAL_SOFTWARE_IPI_CLEAR,
- METAL_SOFTWARE_IPI_SET,
- METAL_SOFTWARE_MSIP_GET,
- METAL_MAX_INTERRUPT_GET,
- METAL_INDEX_INTERRUPT_GET,
+ METAL_TIMER_MTIME_GET = 1,
+ METAL_SOFTWARE_IPI_CLEAR,
+ METAL_SOFTWARE_IPI_SET,
+ METAL_SOFTWARE_MSIP_GET,
+ METAL_MAX_INTERRUPT_GET,
+ METAL_INDEX_INTERRUPT_GET,
} metal_interrup_cmd_e;
typedef struct __metal_interrupt_data {
long long pad : 64;
- metal_interrupt_handler_t handler;
+ metal_interrupt_handler_t handler;
void *sub_int;
void *exint_data;
} __metal_interrupt_data;
@@ -159,14 +161,14 @@ typedef struct __metal_interrupt_data {
uintptr_t __metal_myhart_id(void);
struct __metal_driver_vtable_riscv_cpu_intc {
- struct metal_interrupt_vtable controller_vtable;
+ struct metal_interrupt_vtable controller_vtable;
};
-
void __metal_interrupt_global_enable(void);
void __metal_interrupt_global_disable(void);
metal_vector_mode __metal_controller_interrupt_vector_mode(void);
-void __metal_controller_interrupt_vector(metal_vector_mode mode, void *vec_table);
+void __metal_controller_interrupt_vector(metal_vector_mode mode,
+ void *vec_table);
__METAL_DECLARE_VTABLE(__metal_driver_vtable_riscv_cpu_intc)
@@ -175,18 +177,20 @@ struct __metal_driver_riscv_cpu_intc {
int init_done;
uintptr_t metal_mtvec_table[METAL_MAX_MI];
__metal_interrupt_data metal_int_table[METAL_MAX_MI];
+ __metal_interrupt_data metal_int_beu;
metal_exception_handler_t metal_exception_table[METAL_MAX_ME];
};
/* CPU driver*/
struct __metal_driver_vtable_cpu {
- struct metal_cpu_vtable cpu_vtable;
+ struct metal_cpu_vtable cpu_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_cpu)
struct __metal_driver_cpu {
struct metal_cpu cpu;
+ unsigned int hpm_count; /* Available HPM counters per CPU */
};
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_plic0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_plic0.h
index 159ee6d69..fac76fbc3 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_plic0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/riscv_plic0.h
@@ -7,10 +7,10 @@
#include <metal/compiler.h>
#include <metal/drivers/riscv_cpu.h>
-#define METAL_PLIC_SOURCE_MASK 0x1F
-#define METAL_PLIC_SOURCE_SHIFT 5
-#define METAL_PLIC_SOURCE_PRIORITY_SHIFT 2
-#define METAL_PLIC_SOURCE_PENDING_SHIFT 0
+#define METAL_PLIC_SOURCE_MASK 0x1F
+#define METAL_PLIC_SOURCE_SHIFT 5
+#define METAL_PLIC_SOURCE_PRIORITY_SHIFT 2
+#define METAL_PLIC_SOURCE_PENDING_SHIFT 0
struct __metal_driver_vtable_riscv_plic0 {
struct metal_interrupt_vtable plic_vtable;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_buserror0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_buserror0.h
new file mode 100644
index 000000000..20972109b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_buserror0.h
@@ -0,0 +1,184 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_BUSERROR0_H
+#define METAL__DRIVERS__SIFIVE_BUSERROR0_H
+
+/*!
+ * @file sifive_buserror0.h
+ *
+ * @brief API for configuring the SiFive Bus Error Unit
+ */
+
+#include <metal/compiler.h>
+#include <stdbool.h>
+#include <stdint.h>
+
+/*!
+ * @brief The set of possible events handled by a SiFive Bus Error Unit
+ */
+typedef enum {
+ /*! @brief No event or error has been detected */
+ METAL_BUSERROR_EVENT_NONE = 0,
+
+ /*! @brief A correctable ECC error has occurred in the I$ or ITIM */
+ METAL_BUSERROR_EVENT_INST_CORRECTABLE_ECC_ERROR = (1 << 2),
+ /*! @brief An uncorrectable ECC error has occurred in the I$ or ITIM */
+ METAL_BUSERROR_EVENT_INST_UNCORRECTABLE_ECC_ERROR = (1 << 3),
+ /*! @brief A TileLink load or store bus error has occurred */
+ METAL_BUSERROR_EVENT_LOAD_STORE_ERROR = (1 << 5),
+ /*! @brief A correctable ECC error has occurred in the D$ or DTIM */
+ METAL_BUSERROR_EVENT_DATA_CORRECTABLE_ECC_ERROR = (1 << 6),
+ /*! @brief An uncorrectable ECC error has occurred in the D$ or DTIM */
+ METAL_BUSERROR_EVENT_DATA_UNCORRECTABLE_ECC_ERROR = (1 << 7),
+
+ /*! @brief Used to set/clear all interrupts or query/clear all accrued
+ events */
+ METAL_BUSERROR_EVENT_ALL =
+ METAL_BUSERROR_EVENT_INST_CORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_INST_UNCORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_LOAD_STORE_ERROR |
+ METAL_BUSERROR_EVENT_DATA_CORRECTABLE_ECC_ERROR |
+ METAL_BUSERROR_EVENT_DATA_UNCORRECTABLE_ECC_ERROR,
+ /*! @brief A synonym of METAL_BUSERROR_EVENT_ALL */
+ METAL_BUSERROR_EVENT_ANY = METAL_BUSERROR_EVENT_ALL,
+
+ /*! @brief A value which is impossible for the bus error unit to report.
+ * Indicates an error has occurred if provided as a return value. */
+ METAL_BUSERROR_EVENT_INVALID = (1 << 8),
+} metal_buserror_event_t;
+
+/*!
+ * @brief The handle for a bus error unit
+ */
+struct metal_buserror {
+ uint8_t __no_empty_structs;
+};
+
+/*!
+ * @brief Enable bus error events
+ *
+ * Enabling bus error events causes them to be registered as accrued and,
+ * if the corresponding interrupt is inabled, trigger interrupts.
+ *
+ * @param beu The bus error unit handle
+ * @param events A mask of error events to enable
+ * @param enabled True if the mask should be enabled, false if they should be
+ * disabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_event_enabled(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Get enabled bus error events
+ * @param beu The bus error unit handle
+ * @return A mask of all enabled events
+ */
+metal_buserror_event_t
+metal_buserror_get_event_enabled(struct metal_buserror *beu);
+
+/*!
+ * @brief Enable or disable the platform interrupt
+ *
+ * @param beu The bus error unit handle
+ * @param event The error event which would trigger the interrupt
+ * @param enabled True if the interrupt should be enabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_platform_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Enable or disable the hart-local interrupt
+ *
+ * @param beu The bus error unit handle
+ * @param event The error event which would trigger the interrupt
+ * @param enabled True if the interrupt should be enabled
+ * @return 0 upon success
+ */
+int metal_buserror_set_local_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled);
+
+/*!
+ * @brief Get the error event which caused the most recent interrupt
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The event which caused the interrupt
+ */
+metal_buserror_event_t metal_buserror_get_cause(struct metal_buserror *beu);
+
+/*!
+ * @brief Clear the cause register for the bus error unit
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit to un-latch the cause register for the next event
+ *
+ * @param beu The bus error unit handle
+ * @return 0 upon success
+ */
+int metal_buserror_clear_cause(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the physical address of the error event
+ *
+ * This method should be called from within the interrupt handler for the bus
+ * error unit.
+ *
+ * @param beu The bus error unit handle
+ * @return The address of the error event
+ */
+uintptr_t metal_buserror_get_event_address(struct metal_buserror *beu);
+
+/*!
+ * @brief Returns true if the event is set in the accrued register
+ *
+ * @param beu The bus error unit handle
+ * @param event The event to query
+ * @return True if the event is set in the accrued register
+ */
+bool metal_buserror_is_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events);
+
+/*!
+ * @brief Clear the given event from the accrued register
+ *
+ * @param beu The bus error unit handle
+ * @param event The event to clear
+ * @return 0 upon success
+ */
+int metal_buserror_clear_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events);
+
+/*!
+ * @brief get the platform-level interrupt parent of the bus error unit
+ *
+ * @param beu The bus error unit handle
+ * @return A pointer to the interrupt parent
+ */
+struct metal_interrupt *
+metal_buserror_get_platform_interrupt_parent(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the platform-level interrupt id for the bus error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The interrupt id
+ */
+int metal_buserror_get_platform_interrupt_id(struct metal_buserror *beu);
+
+/*!
+ * @brief Get the hart-local interrupt id for the bus error unit interrupt
+ *
+ * @param beu The bus error unit handle
+ * @return The interrupt id
+ */
+int metal_buserror_get_local_interrupt_id(struct metal_buserror *beu);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_ccache0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_ccache0.h
index 2153cf384..13a47c0b9 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_ccache0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_ccache0.h
@@ -1,23 +1,140 @@
-/* Copyright 2019 SiFive, Inc */
+/* Copyright 2020 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
#ifndef METAL__DRIVERS__SIFIVE_CCACHE0_H
#define METAL__DRIVERS__SIFIVE_CCACHE0_H
-#include <metal/cache.h>
-#include <metal/compiler.h>
+/*!
+ * @file sifive_ccache0.h
+ *
+ * @brief API for configuring the SiFive L2 cache controller
+ */
-struct __metal_driver_vtable_sifive_ccache0 {
- struct __metal_cache_vtable cache;
-};
+#include <metal/interrupt.h>
+#include <stdint.h>
-struct __metal_driver_sifive_ccache0;
+/*! @brief Cache configuration data */
+typedef struct {
+ uint32_t num_bank;
+ uint32_t num_ways;
+ uint32_t num_sets;
+ uint32_t block_size;
+} sifive_ccache0_config;
-__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_ccache0)
+/*! @brief Set of values for ECC error type */
+typedef enum {
+ SIFIVE_CCACHE0_DATA = 0,
+ SIFIVE_CCACHE0_DIR = 1,
+} sifive_ccache0_ecc_errtype_t;
-struct __metal_driver_sifive_ccache0 {
- struct metal_cache cache;
-};
+/*! @brief Initialize cache controller, enables all available
+ * cache-ways.
+ * Note: If LIM is in use, corresponding cache ways are not enabled.
+ * @param None.
+ * @return 0 If no error.*/
+int sifive_ccache0_init(void);
-#endif
+/*! @brief Get cache configuration data.
+ * @param config User specified data buffer.
+ * @return None.*/
+void sifive_ccache0_get_config(sifive_ccache0_config *config);
+
+/*! @brief Get currently active cache ways.
+ * @param None.
+ * @return Number of cache ways enabled.*/
+uint32_t sifive_ccache0_get_enabled_ways(void);
+
+/*! @brief Enable specified cache ways.
+ * @param ways Number of ways to be enabled.
+ * @return 0 If no error.*/
+int sifive_ccache0_set_enabled_ways(uint32_t ways);
+
+/*! @brief Inject ECC error into data or meta-data.
+ * @param bitindex Bit index to be corrupted on next cache operation.
+ * @param type ECC error target location.
+ * @return None.*/
+void sifive_ccache0_inject_ecc_error(uint32_t bitindex,
+ sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Flush out entire cache block containing given address.
+ * @param flush_addr Address for the cache block to be flushed.
+ * @return None.*/
+void sifive_ccache0_flush(uintptr_t flush_addr);
+
+/*! @brief Get most recently ECC corrected address.
+ * @param type ECC error target location.
+ * @return Last corrected ECC address.*/
+uintptr_t sifive_ccache0_get_ecc_fix_addr(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get number of times ECC errors were corrected.
+ * Clears related ECC interrupt signals.
+ * @param type ECC error target location.
+ * @return Corrected ECC error count.*/
+uint32_t sifive_ccache0_get_ecc_fix_count(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get address location of most recent uncorrected ECC error.
+ * @param type ECC error target location.
+ * @return Last uncorrected ECC address.*/
+uintptr_t sifive_ccache0_get_ecc_fail_addr(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get number of times ECC errors were not corrected.
+ * Clears related ECC interrupt signals.
+ * @param type ECC error target location.
+ * @return Uncorrected ECC error count.*/
+uint32_t sifive_ccache0_get_ecc_fail_count(sifive_ccache0_ecc_errtype_t type);
+
+/*! @brief Get currently active way enable mask value for the given master ID.
+ * @param master_id Cache controller master ID.
+ * @return Way enable mask. */
+uint64_t sifive_ccache0_get_way_mask(uint32_t master_id);
+/*! @brief Set way enable mask for the given master ID.
+ * @param master_id Cache controller master ID.
+ * @param waymask Specify ways to be enabled.
+ * @return 0 If no error.*/
+int sifive_ccache0_set_way_mask(uint32_t master_id, uint64_t waymask);
+
+/*! @brief Select cache performance events to be counted.
+ * @param counter Cache performance monitor counter index.
+ * @param mask Event selection mask.
+ * @return None.*/
+void sifive_ccache0_set_pmevent_selector(uint32_t counter, uint64_t mask);
+
+/*! @brief Get currently set events for the given counter index.
+ * @param counter Cache performance monitor counter index.
+ * @return Event selection mask.*/
+uint64_t sifive_ccache0_get_pmevent_selector(uint32_t counter);
+
+/*! @brief Clears specified cache performance counter.
+ * @param counter Cache performance monitor counter index.
+ * @return None.*/
+void sifive_ccache0_clr_pmevent_counter(uint32_t counter);
+
+/*! @brief Reads specified cache performance counter.
+ * @param counter Cache performance monitor counter index.
+ * @return Counter value.*/
+uint64_t sifive_ccache0_get_pmevent_counter(uint32_t counter);
+
+/*! @brief Select cache clients to be excluded from performance monitoring.
+ * @param mask Client disable mask.
+ * @return None.*/
+void sifive_ccache0_set_client_filter(uint64_t mask);
+
+/*! @brief Get currently set cache client disable mask.
+ * @param None.
+ * @return Client disable mask.*/
+uint64_t sifive_ccache0_get_client_filter(void);
+
+/*! @brief Get interrupt IDs for the cache controller.
+ * @param src Interrupt trigger source index.
+ * @return Interrupt id.*/
+int sifive_ccache0_get_interrupt_id(uint32_t src);
+
+/*! @brief Get interrupt controller of the cache.
+ * The interrupt controller must be initialized before any interrupts can be
+ * registered or enabled with it.
+ * @param None.
+ * @return Handle for the interrupt controller.*/
+struct metal_interrupt *sifive_ccache0_interrupt_controller(void);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_clic0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_clic0.h
index 7fef38d19..b8ff82271 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_clic0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_clic0.h
@@ -7,21 +7,21 @@
#include <metal/compiler.h>
#include <metal/drivers/riscv_cpu.h>
-#define METAL_CLIC_MAX_NMBITS 2
-#define METAL_CLIC_MAX_NLBITS 8
-#define METAL_CLIC_MAX_NVBITS 1
+#define METAL_CLIC_MAX_NMBITS 2
+#define METAL_CLIC_MAX_NLBITS 8
+#define METAL_CLIC_MAX_NVBITS 1
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MMODE 0x00
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE1 0x20
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE2 0x40
-#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MASK 0x60
-#define METAL_SIFIVE_CLIC0_CLICCFG_NLBITS_MASK 0x1E
-#define METAL_SIFIVE_CLIC0_CLICCFG_NVBIT_MASK 0x01
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MMODE 0x00
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE1 0x20
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_SMODE2 0x40
+#define METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MASK 0x60
+#define METAL_SIFIVE_CLIC0_CLICCFG_NLBITS_MASK 0x1E
+#define METAL_SIFIVE_CLIC0_CLICCFG_NVBIT_MASK 0x01
-#define METAL_CLIC_ICTRL_SMODE1_MASK 0x7F /* b8 set imply M-mode */
-#define METAL_CLIC_ICTRL_SMODE2_MASK 0x3F /* b8 set M-mode, b7 clear U-mode */
+#define METAL_CLIC_ICTRL_SMODE1_MASK 0x7F /* b8 set imply M-mode */
+#define METAL_CLIC_ICTRL_SMODE2_MASK 0x3F /* b8 set M-mode, b7 clear U-mode */
-#define METAL_MAX_INTERRUPT_LEVEL ((1 << METAL_CLIC_MAX_NLBITS) - 1)
+#define METAL_MAX_INTERRUPT_LEVEL ((1 << METAL_CLIC_MAX_NLBITS) - 1)
struct __metal_driver_vtable_sifive_clic0 {
struct metal_interrupt_vtable clic_vtable;
@@ -34,10 +34,15 @@ __METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_clic0)
struct __metal_driver_sifive_clic0 {
struct metal_interrupt controller;
int init_done;
- int pad[14];
- metal_interrupt_vector_handler_t metal_mtvt_table[__METAL_CLIC_SUBINTERRUPTS];
+ struct {
+ } __attribute__((aligned(64)));
+ metal_interrupt_vector_handler_t
+ metal_mtvt_table[__METAL_CLIC_SUBINTERRUPTS];
__metal_interrupt_data metal_exint_table[__METAL_CLIC_SUBINTERRUPTS];
};
#undef __METAL_MACHINE_MACROS
+int __metal_driver_sifive_clic0_command_request(
+ struct metal_interrupt *controller, int command, void *data);
+
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_hfrosc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_hfrosc.h
index d311f0cf2..d60d3a3bd 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_hfrosc.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_hfrosc.h
@@ -4,9 +4,9 @@
#ifndef METAL__DRIVERS__SIFIVE_FE310_G000_HFROSC_H
#define METAL__DRIVERS__SIFIVE_FE310_G000_HFROSC_H
-#include <metal/drivers/sifive_fe310-g000_prci.h>
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/sifive_fe310-g000_prci.h>
#include <metal/io.h>
struct __metal_driver_vtable_sifive_fe310_g000_hfrosc {
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_lfrosc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_lfrosc.h
index 64985c6bb..2650584ad 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_lfrosc.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_lfrosc.h
@@ -4,8 +4,8 @@
#ifndef METAL__DRIVERS__SIFIVE_FE310_G000_LFROSC_H
#define METAL__DRIVERS__SIFIVE_FE310_G000_LFROSC_H
-#include <metal/compiler.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
#include <metal/io.h>
struct __metal_driver_vtable_sifive_fe310_g000_lfrosc {
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_prci.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_prci.h
index 387130be5..4fca30167 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_prci.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fe310-g000_prci.h
@@ -10,8 +10,10 @@
struct __metal_driver_sifive_fe310_g000_prci;
struct __metal_driver_vtable_sifive_fe310_g000_prci {
- long (*get_reg)(const struct __metal_driver_sifive_fe310_g000_prci *, long offset);
- long (*set_reg)(const struct __metal_driver_sifive_fe310_g000_prci *, long offset, long value);
+ long (*get_reg)(const struct __metal_driver_sifive_fe310_g000_prci *,
+ long offset);
+ long (*set_reg)(const struct __metal_driver_sifive_fe310_g000_prci *,
+ long offset, long value);
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_fe310_g000_prci)
@@ -21,4 +23,3 @@ struct __metal_driver_sifive_fe310_g000_prci {
};
#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fu540-c000_l2.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fu540-c000_l2.h
deleted file mode 100644
index bb98f169e..000000000
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_fu540-c000_l2.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Copyright 2018 SiFive, Inc */
-/* SPDX-License-Identifier: Apache-2.0 */
-
-#ifndef METAL__DRIVERS__SIFIVE_FU540_C000_L2_H
-#define METAL__DRIVERS__SIFIVE_FU540_C000_L2_H
-
-#include <metal/cache.h>
-#include <metal/compiler.h>
-
-struct __metal_driver_vtable_sifive_fu540_c000_l2 {
- struct __metal_cache_vtable cache;
-};
-
-struct __metal_driver_sifive_fu540_c000_l2;
-
-__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_fu540_c000_l2)
-
-struct __metal_driver_sifive_fu540_c000_l2 {
- struct metal_cache cache;
-};
-
-#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-buttons.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-buttons.h
index a0caeaba8..7227eee02 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-buttons.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-buttons.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_BUTTONS_H
#define METAL__DRIVERS__SIFIVE_GPIO_BUTTONS_H
-#include <string.h>
#include <metal/button.h>
#include <metal/compiler.h>
+#include <string.h>
struct __metal_driver_vtable_sifive_button {
- struct metal_button_vtable button_vtable;
+ struct metal_button_vtable button_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_button)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-leds.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-leds.h
index a8dacf116..abfca01c2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-leds.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-leds.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_LEDS_H
#define METAL__DRIVERS__SIFIVE_GPIO_LEDS_H
+#include <metal/compiler.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/led.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_led {
- struct metal_led_vtable led_vtable;
+ struct metal_led_vtable led_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_led)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-switches.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-switches.h
index c9c7839e9..be55a0446 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-switches.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio-switches.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_GPIO_SWITCHES_H
#define METAL__DRIVERS__SIFIVE_GPIO_SWITCHES_H
+#include <metal/compiler.h>
#include <metal/drivers/sifive_gpio0.h>
#include <metal/switch.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_switch {
- struct metal_switch_vtable switch_vtable;
+ struct metal_switch_vtable switch_vtable;
};
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_switch)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio0.h
index cc56dc722..50314222d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_gpio0.h
@@ -11,7 +11,7 @@ struct __metal_driver_vtable_sifive_gpio0 {
const struct __metal_gpio_vtable gpio;
};
-//struct __metal_driver_sifive_gpio0;
+// struct __metal_driver_sifive_gpio0;
__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_gpio0)
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_i2c0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_i2c0.h
new file mode 100644
index 000000000..8fbbe21e1
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_i2c0.h
@@ -0,0 +1,24 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_I2C0_H
+#define METAL__DRIVERS__SIFIVE_I2C0_H
+
+#include <metal/clock.h>
+#include <metal/i2c.h>
+
+struct __metal_driver_vtable_sifive_i2c0 {
+ const struct metal_i2c_vtable i2c;
+};
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_i2c0)
+
+struct __metal_driver_sifive_i2c0 {
+ struct metal_i2c i2c;
+ unsigned int init_done;
+ unsigned int baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_l2pf0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_l2pf0.h
new file mode 100644
index 000000000..63c8e6536
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_l2pf0.h
@@ -0,0 +1,78 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_L2PF0_H
+#define METAL__DRIVERS__SIFIVE_L2PF0_H
+
+/*!
+ * @file sifive_l2pf0.h
+ *
+ * @brief API for configuring the SiFive L2 prefetcher.
+ */
+
+#include <stdint.h>
+
+/*! @brief L2 prefetcher configuration */
+typedef struct {
+ /* Enable L2 hardware prefetcher */
+ uint8_t HwPrefetchEnable;
+
+ /* Only works when CrossPageEn === 0.
+ Cross Page optimization disable:
+ 0 -> Entry goes into Pause state while crossing Page boundary.
+ Next time when the demand miss happens on the same page, it doesn’t need
+ to train again. 1 -> The entry is invalidated in case of a cross page. */
+ uint8_t CrossPageOptmDisable;
+
+ /* Enable prefetches to cross pages */
+ uint8_t CrossPageEn;
+
+ /* Age-out mechanism enable */
+ uint8_t AgeOutEn;
+
+ uint32_t PrefetchDistance;
+
+ uint32_t MaxAllowedDistance;
+
+ /* Linear to exponential threshold */
+ uint32_t LinToExpThreshold;
+
+ /* No. of non-matching loads to edge out an entry */
+ uint32_t NumLdsToAgeOut;
+
+ /* Threshold no. of Fullness (L2 MSHRs used/ total available) to stop
+ * sending hits */
+ uint32_t QFullnessThreshold;
+
+ /* Threshold no. of CacheHits for evicting SPF entry */
+ uint32_t HitCacheThreshold;
+
+ /* Threshold no. of MSHR hits for increasing SPF distance */
+ uint32_t hitMSHRThreshold;
+
+ /* Size of the comparison window for address matching */
+ uint32_t Window;
+
+} sifive_l2pf0_config;
+
+/*! @brief Enable L2 hardware prefetcher unit.
+ * @param None.
+ * @return None.*/
+void sifive_l2pf0_enable(void);
+
+/*! @brief Disable L2 hardware prefetcher unit.
+ * @param None.
+ * @return None.*/
+void sifive_l2pf0_disable(void);
+
+/*! @brief Get currently active L2 prefetcher configuration.
+ * @param config Pointer to user specified configuration structure.
+ * @return None.*/
+void sifive_l2pf0_get_config(sifive_l2pf0_config *config);
+
+/*! @brief Enables fine grain access to L2 prefetcher configuration.
+ * @param config Pointer to user structure with values to be set.
+ * @return None.*/
+void sifive_l2pf0_set_config(sifive_l2pf0_config *config);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_local-external-interrupts0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_local-external-interrupts0.h
index aa8d63078..320ab10d2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_local-external-interrupts0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_local-external-interrupts0.h
@@ -18,5 +18,4 @@ struct __metal_driver_sifive_local_external_interrupts0 {
int init_done;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_pwm0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_pwm0.h
new file mode 100644
index 000000000..caa774401
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_pwm0.h
@@ -0,0 +1,29 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_PWM0_H
+#define METAL__DRIVERS__SIFIVE_PWM0_H
+
+#include <metal/clock.h>
+#include <metal/pwm.h>
+
+struct __metal_driver_vtable_sifive_pwm0 {
+ const struct metal_pwm_vtable pwm;
+};
+
+/* Max possible PWM channel count */
+#define METAL_MAX_PWM_CHANNELS 16
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_pwm0)
+
+struct __metal_driver_sifive_pwm0 {
+ struct metal_pwm pwm;
+ unsigned int max_count;
+ unsigned int count_val;
+ unsigned int freq;
+ unsigned int duty[METAL_MAX_PWM_CHANNELS];
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_rtc0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_rtc0.h
index b0ed143bf..a35ab9a09 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_rtc0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_rtc0.h
@@ -4,8 +4,8 @@
#ifndef METAL__DRIVERS__SIFIVE_RTC0_H
#define METAL__DRIVERS__SIFIVE_RTC0_H
-#include <metal/io.h>
#include <metal/compiler.h>
+#include <metal/io.h>
#include <metal/clock.h>
#include <metal/interrupt.h>
@@ -24,4 +24,3 @@ struct __metal_driver_sifive_rtc0 {
};
#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_simuart0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_simuart0.h
new file mode 100644
index 000000000..f6b739143
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_simuart0.h
@@ -0,0 +1,29 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__SIFIVE_SIMUART0_H
+#define METAL__DRIVERS__SIFIVE_SIMUART0_H
+
+#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/riscv_plic0.h>
+#include <metal/drivers/sifive_gpio0.h>
+#include <metal/io.h>
+#include <metal/uart.h>
+
+struct __metal_driver_vtable_sifive_simuart0 {
+ const struct metal_uart_vtable uart;
+};
+
+struct __metal_driver_sifive_simuart0;
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_sifive_simuart0)
+
+struct __metal_driver_sifive_simuart0 {
+ struct metal_uart uart;
+ unsigned long baud_rate;
+ metal_clock_callback pre_rate_change_callback;
+ metal_clock_callback post_rate_change_callback;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_spi0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_spi0.h
index c4a6848e7..73527944b 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_spi0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_spi0.h
@@ -4,9 +4,9 @@
#ifndef METAL__DRIVERS__SIFIVE_SPI0_H
#define METAL__DRIVERS__SIFIVE_SPI0_H
-#include <metal/drivers/sifive_gpio0.h>
#include <metal/clock.h>
#include <metal/compiler.h>
+#include <metal/drivers/sifive_gpio0.h>
#include <metal/io.h>
#include <metal/spi.h>
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_test0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_test0.h
index e87db2c83..debd3fb9d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_test0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_test0.h
@@ -17,5 +17,4 @@ struct __metal_driver_sifive_test0 {
struct __metal_shutdown shutdown;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_uart0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_uart0.h
index 5d585e783..2b38e4631 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_uart0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_uart0.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_UART0_H
#define METAL__DRIVERS__SIFIVE_UART0_H
-#include <metal/drivers/sifive_gpio0.h>
-#include <metal/drivers/riscv_plic0.h>
#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/riscv_plic0.h>
+#include <metal/drivers/sifive_gpio0.h>
#include <metal/io.h>
#include <metal/uart.h>
-#include <metal/compiler.h>
struct __metal_driver_vtable_sifive_uart0 {
const struct metal_uart_vtable uart;
@@ -26,5 +26,4 @@ struct __metal_driver_sifive_uart0 {
metal_clock_callback post_rate_change_callback;
};
-
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_wdog0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_wdog0.h
index 12b143d58..bb3424584 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_wdog0.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/sifive_wdog0.h
@@ -4,12 +4,12 @@
#ifndef METAL__DRIVERS__SIFIVE_WDOG0_H
#define METAL__DRIVERS__SIFIVE_WDOG0_H
-#include <metal/io.h>
#include <metal/compiler.h>
+#include <metal/io.h>
-#include <metal/watchdog.h>
#include <metal/clock.h>
#include <metal/interrupt.h>
+#include <metal/watchdog.h>
struct __metal_driver_vtable_sifive_wdog0 {
const struct metal_watchdog_vtable watchdog;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/ucb_htif0.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/ucb_htif0.h
new file mode 100644
index 000000000..210d0819b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/drivers/ucb_htif0.h
@@ -0,0 +1,48 @@
+/* Copyright 2018 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__DRIVERS__UCB_HTIF0_H
+#define METAL__DRIVERS__UCB_HTIF0_H
+
+#include <metal/compiler.h>
+#include <metal/shutdown.h>
+#include <metal/uart.h>
+
+struct __metal_driver_vtable_ucb_htif0_shutdown {
+ const struct __metal_shutdown_vtable shutdown;
+};
+
+struct __metal_driver_vtable_ucb_htif0_uart {
+ const struct metal_uart_vtable uart;
+};
+
+struct __metal_driver_ucb_htif0;
+
+void __metal_driver_ucb_htif0_exit(const struct __metal_shutdown *test,
+ int code) __attribute__((noreturn));
+
+void __metal_driver_ucb_htif0_init(struct metal_uart *uart, int baud_rate);
+int __metal_driver_ucb_htif0_putc(struct metal_uart *uart, int c);
+int __metal_driver_ucb_htif0_getc(struct metal_uart *uart, int *c);
+int __metal_driver_ucb_htif0_get_baud_rate(struct metal_uart *guart);
+int __metal_driver_ucb_htif0_set_baud_rate(struct metal_uart *guart,
+ int baud_rate);
+struct metal_interrupt *
+__metal_driver_ucb_htif0_interrupt_controller(struct metal_uart *uart);
+int __metal_driver_ucb_htif0_get_interrupt_id(struct metal_uart *uart);
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_ucb_htif0_shutdown)
+
+__METAL_DECLARE_VTABLE(__metal_driver_vtable_ucb_htif0_uart)
+
+struct __metal_driver_ucb_htif0_shutdown {
+ struct __metal_shutdown shutdown;
+ const struct __metal_driver_vtable_ucb_htif0_shutdown *vtable;
+};
+
+struct __metal_driver_ucb_htif0_uart {
+ struct metal_uart uart;
+ const struct __metal_driver_vtable_ucb_htif0_uart *vtable;
+};
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/gpio.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/gpio.h
index 7645494ff..df9adb451 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/gpio.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/gpio.h
@@ -28,25 +28,25 @@ struct __metal_gpio_vtable {
int (*disable_io)(struct metal_gpio *, long pins);
int (*config_int)(struct metal_gpio *, long pins, int intr_type);
int (*clear_int)(struct metal_gpio *, long pins, int intr_type);
- struct metal_interrupt* (*interrupt_controller)(struct metal_gpio *gpio);
+ struct metal_interrupt *(*interrupt_controller)(struct metal_gpio *gpio);
int (*get_interrupt_id)(struct metal_gpio *gpio, int pin);
};
-#define METAL_GPIO_INT_DISABLE 0
-#define METAL_GPIO_INT_RISING 1
-#define METAL_GPIO_INT_FALLING 2
-#define METAL_GPIO_INT_BOTH_EDGE 3
-#define METAL_GPIO_INT_LOW 4
-#define METAL_GPIO_INT_HIGH 5
-#define METAL_GPIO_INT_BOTH_LEVEL 6
-#define METAL_GPIO_INT_MAX 7
+#define METAL_GPIO_INT_DISABLE 0
+#define METAL_GPIO_INT_RISING 1
+#define METAL_GPIO_INT_FALLING 2
+#define METAL_GPIO_INT_BOTH_EDGE 3
+#define METAL_GPIO_INT_LOW 4
+#define METAL_GPIO_INT_HIGH 5
+#define METAL_GPIO_INT_BOTH_LEVEL 6
+#define METAL_GPIO_INT_MAX 7
/*!
* @struct metal_gpio
* @brief The handle for a GPIO interface
*/
struct metal_gpio {
- const struct __metal_gpio_vtable *vtable;
+ const struct __metal_gpio_vtable *vtable;
};
/*!
@@ -63,8 +63,8 @@ struct metal_gpio *metal_gpio_get_device(unsigned int device_num);
* @return 0 if the input is successfully enabled
*/
__inline__ int metal_gpio_enable_input(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->enable_input(gpio, (1 << pin));
@@ -77,8 +77,8 @@ __inline__ int metal_gpio_enable_input(struct metal_gpio *gpio, int pin) {
* @return 0 if the input is successfully disabled
*/
__inline__ int metal_gpio_disable_input(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->disable_input(gpio, (1 << pin));
@@ -91,8 +91,8 @@ __inline__ int metal_gpio_disable_input(struct metal_gpio *gpio, int pin) {
* @return 0 if the output is successfully enabled
*/
__inline__ int metal_gpio_enable_output(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->enable_output(gpio, (1 << pin));
@@ -105,8 +105,8 @@ __inline__ int metal_gpio_enable_output(struct metal_gpio *gpio, int pin) {
* @return 0 if the output is successfully disabled
*/
__inline__ int metal_gpio_disable_output(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->disable_output(gpio, (1 << pin));
@@ -120,14 +120,14 @@ __inline__ int metal_gpio_disable_output(struct metal_gpio *gpio, int pin) {
* @return 0 if the output is successfully set
*/
__inline__ int metal_gpio_set_pin(struct metal_gpio *gpio, int pin, int value) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
- if(value == 0) {
- return gpio->vtable->output_clear(gpio, (1 << pin));
+ if (value == 0) {
+ return gpio->vtable->output_clear(gpio, (1 << pin));
} else {
- return gpio->vtable->output_set(gpio, (1 << pin));
+ return gpio->vtable->output_set(gpio, (1 << pin));
}
}
@@ -138,16 +138,16 @@ __inline__ int metal_gpio_set_pin(struct metal_gpio *gpio, int pin, int value) {
* @return The value of the GPIO pin
*/
__inline__ int metal_gpio_get_input_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 0;
+ if (!gpio) {
+ return 0;
}
long value = gpio->vtable->input(gpio);
- if(value & (1 << pin)) {
- return 1;
+ if (value & (1 << pin)) {
+ return 1;
} else {
- return 0;
+ return 0;
}
}
@@ -158,16 +158,16 @@ __inline__ int metal_gpio_get_input_pin(struct metal_gpio *gpio, int pin) {
* @return The value of the GPIO pin
*/
__inline__ int metal_gpio_get_output_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 0;
+ if (!gpio) {
+ return 0;
}
long value = gpio->vtable->output(gpio);
- if(value & (1 << pin)) {
- return 1;
+ if (value & (1 << pin)) {
+ return 1;
} else {
- return 0;
+ return 0;
}
}
@@ -178,8 +178,8 @@ __inline__ int metal_gpio_get_output_pin(struct metal_gpio *gpio, int pin) {
* @return 0 if the pin is successfully cleared
*/
__inline__ int metal_gpio_clear_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->output_clear(gpio, (1 << pin));
@@ -192,8 +192,8 @@ __inline__ int metal_gpio_clear_pin(struct metal_gpio *gpio, int pin) {
* @return 0 if the pin is successfully toggled
*/
__inline__ int metal_gpio_toggle_pin(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->output_toggle(gpio, (1 << pin));
@@ -206,9 +206,10 @@ __inline__ int metal_gpio_toggle_pin(struct metal_gpio *gpio, int pin) {
* @param io_function The IO function to set
* @return 0 if the pinmux is successfully set
*/
-__inline__ int metal_gpio_enable_pinmux(struct metal_gpio *gpio, int pin, int io_function) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_enable_pinmux(struct metal_gpio *gpio, int pin,
+ int io_function) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->enable_io(gpio, (1 << pin), (io_function << pin));
@@ -221,8 +222,8 @@ __inline__ int metal_gpio_enable_pinmux(struct metal_gpio *gpio, int pin, int io
* @return 0 if the pinmux is successfully set
*/
__inline__ int metal_gpio_disable_pinmux(struct metal_gpio *gpio, int pin) {
- if(!gpio) {
- return 1;
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->disable_io(gpio, (1 << pin));
@@ -235,9 +236,10 @@ __inline__ int metal_gpio_disable_pinmux(struct metal_gpio *gpio, int pin) {
* @param intr_type The interrupt type
* @return 0 if the interrupt mode is setup properly
*/
-__inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio, int pin, int intr_type) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio, int pin,
+ int intr_type) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->config_int(gpio, (1 << pin), intr_type);
@@ -250,9 +252,10 @@ __inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio, int pin, int
* @param intr_type The interrupt type to be clear
* @return 0 if the interrupt is cleared
*/
-__inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio, int pin, int intr_type) {
- if(!gpio) {
- return 1;
+__inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio, int pin,
+ int intr_type) {
+ if (!gpio) {
+ return 1;
}
return gpio->vtable->clear_int(gpio, (1 << pin), intr_type);
@@ -265,8 +268,8 @@ __inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio, int pin, int
* @return A pointer to the interrupt controller responsible for handling
* gpio interrupts.
*/
-__inline__ struct metal_interrupt*
- metal_gpio_interrupt_controller(struct metal_gpio *gpio) {
+__inline__ struct metal_interrupt *
+metal_gpio_interrupt_controller(struct metal_gpio *gpio) {
return gpio->vtable->interrupt_controller(gpio);
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/hpm.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/hpm.h
new file mode 100644
index 000000000..290f7ec3f
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/hpm.h
@@ -0,0 +1,146 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__HPM_H
+#define METAL__HPM_H
+
+#include <metal/cpu.h>
+
+/*! @brief Macros for valid Event IDs */
+#define METAL_HPM_EVENTID_8 (1UL << 8)
+#define METAL_HPM_EVENTID_9 (1UL << 9)
+#define METAL_HPM_EVENTID_10 (1UL << 10)
+#define METAL_HPM_EVENTID_11 (1UL << 11)
+#define METAL_HPM_EVENTID_12 (1UL << 12)
+#define METAL_HPM_EVENTID_13 (1UL << 13)
+#define METAL_HPM_EVENTID_14 (1UL << 14)
+#define METAL_HPM_EVENTID_15 (1UL << 15)
+#define METAL_HPM_EVENTID_16 (1UL << 16)
+#define METAL_HPM_EVENTID_17 (1UL << 17)
+#define METAL_HPM_EVENTID_18 (1UL << 18)
+#define METAL_HPM_EVENTID_19 (1UL << 19)
+#define METAL_HPM_EVENTID_20 (1UL << 20)
+#define METAL_HPM_EVENTID_21 (1UL << 21)
+#define METAL_HPM_EVENTID_22 (1UL << 22)
+#define METAL_HPM_EVENTID_23 (1UL << 23)
+#define METAL_HPM_EVENTID_24 (1UL << 24)
+#define METAL_HPM_EVENTID_25 (1UL << 25)
+#define METAL_HPM_EVENTID_26 (1UL << 26)
+#define METAL_HPM_EVENTID_27 (1UL << 27)
+#define METAL_HPM_EVENTID_28 (1UL << 28)
+#define METAL_HPM_EVENTID_29 (1UL << 29)
+#define METAL_HPM_EVENTID_30 (1UL << 30)
+#define METAL_HPM_EVENTID_31 (1UL << 31)
+
+/*! @brief Macros for valid Event Class */
+#define METAL_HPM_EVENTCLASS_0 (0UL)
+#define METAL_HPM_EVENTCLASS_1 (1UL)
+#define METAL_HPM_EVENTCLASS_2 (2UL)
+#define METAL_HPM_EVENTCLASS_3 (3UL)
+#define METAL_HPM_EVENTCLASS_4 (4UL)
+#define METAL_HPM_EVENTCLASS_5 (5UL)
+#define METAL_HPM_EVENTCLASS_6 (6UL)
+#define METAL_HPM_EVENTCLASS_7 (7UL)
+#define METAL_HPM_EVENTCLASS_8 (8UL)
+
+/*! @brief Enums for available HPM counters */
+typedef enum {
+ METAL_HPM_CYCLE = 0,
+ METAL_HPM_TIME = 1,
+ METAL_HPM_INSTRET = 2,
+ METAL_HPM_COUNTER_3 = 3,
+ METAL_HPM_COUNTER_4 = 4,
+ METAL_HPM_COUNTER_5 = 5,
+ METAL_HPM_COUNTER_6 = 6,
+ METAL_HPM_COUNTER_7 = 7,
+ METAL_HPM_COUNTER_8 = 8,
+ METAL_HPM_COUNTER_9 = 9,
+ METAL_HPM_COUNTER_10 = 10,
+ METAL_HPM_COUNTER_11 = 11,
+ METAL_HPM_COUNTER_12 = 12,
+ METAL_HPM_COUNTER_13 = 13,
+ METAL_HPM_COUNTER_14 = 14,
+ METAL_HPM_COUNTER_15 = 15,
+ METAL_HPM_COUNTER_16 = 16,
+ METAL_HPM_COUNTER_17 = 17,
+ METAL_HPM_COUNTER_18 = 18,
+ METAL_HPM_COUNTER_19 = 19,
+ METAL_HPM_COUNTER_20 = 20,
+ METAL_HPM_COUNTER_21 = 21,
+ METAL_HPM_COUNTER_22 = 22,
+ METAL_HPM_COUNTER_23 = 23,
+ METAL_HPM_COUNTER_24 = 24,
+ METAL_HPM_COUNTER_25 = 25,
+ METAL_HPM_COUNTER_26 = 26,
+ METAL_HPM_COUNTER_27 = 27,
+ METAL_HPM_COUNTER_28 = 28,
+ METAL_HPM_COUNTER_29 = 29,
+ METAL_HPM_COUNTER_30 = 30,
+ METAL_HPM_COUNTER_31 = 31
+} metal_hpm_counter;
+
+/*! @brief Initialize hardware performance monitor counters.
+ * @param cpu The CPU device handle.
+ * @return 0 If no error.*/
+int metal_hpm_init(struct metal_cpu *cpu);
+
+/*! @brief Disables hardware performance monitor counters.
+ * Note - Disabled HPM counters may reduce power consumption.
+ * @param cpu The CPU device handle.
+ * @return 0 If no error.*/
+int metal_hpm_disable(struct metal_cpu *cpu);
+
+/*! @brief Set events which will cause the specified counter to increment.
+ * Counter will start incrementing from the moment events are set.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter to be incremented by selected events.
+ * @param bitmask Bit-mask to select events for a particular counter,
+ * refer core reference manual for selection of events.
+ * Event bit mask is partitioned as follows:
+ * [XLEN-1:8] - Event selection mask [7:0] - Event class
+ * @return 0 If no error.*/
+int metal_hpm_set_event(struct metal_cpu *cpu, metal_hpm_counter counter,
+ unsigned int bitmask);
+
+/*! @brief Get events selection mask set for specified counter.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return Event selection bit mask. refer core reference manual for details.*/
+unsigned int metal_hpm_get_event(struct metal_cpu *cpu,
+ metal_hpm_counter counter);
+
+/*! @brief Clear event selector bits as per specified bit-mask.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_clr_event(struct metal_cpu *cpu, metal_hpm_counter counter,
+ unsigned int bitmask);
+
+/*! @brief Enable counter access to next lower privilege mode.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_enable_access(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+/*! @brief Disable counter access to next lower privilege mode.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_disable_access(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+/*! @brief Reads current value of specified hardware counter.
+ * Note: 'mtime' register is memory mapped into CLINT block.
+ * Use CLINT APIs to access this register.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return Current value of hardware counter on success, 0 on failure.*/
+unsigned long long metal_hpm_read_counter(struct metal_cpu *cpu,
+ metal_hpm_counter counter);
+
+/*! @brief Clears off specified counter.
+ * @param cpu The CPU device handle.
+ * @param counter Hardware counter.
+ * @return 0 If no error.*/
+int metal_hpm_clear_counter(struct metal_cpu *cpu, metal_hpm_counter counter);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/i2c.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/i2c.h
new file mode 100644
index 000000000..baf62e5d6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/i2c.h
@@ -0,0 +1,112 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__I2C_H
+#define METAL__I2C_H
+
+/*! @brief Enums to enable/disable stop condition. */
+typedef enum {
+ METAL_I2C_STOP_DISABLE = 0,
+ METAL_I2C_STOP_ENABLE = 1
+} metal_i2c_stop_bit_t;
+
+/*! @brief Enums to set up I2C device modes. */
+typedef enum { METAL_I2C_SLAVE = 0, METAL_I2C_MASTER = 1 } metal_i2c_mode_t;
+
+struct metal_i2c;
+
+struct metal_i2c_vtable {
+ void (*init)(struct metal_i2c *i2c, unsigned int baud_rate,
+ metal_i2c_mode_t mode);
+ int (*write)(struct metal_i2c *i2c, unsigned int addr, unsigned int len,
+ unsigned char buf[], metal_i2c_stop_bit_t stop_bit);
+ int (*read)(struct metal_i2c *i2c, unsigned int addr, unsigned int len,
+ unsigned char buf[], metal_i2c_stop_bit_t stop_bit);
+ int (*transfer)(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen);
+ int (*get_baud_rate)(struct metal_i2c *i2c);
+ int (*set_baud_rate)(struct metal_i2c *i2c, unsigned int baud_rate);
+};
+
+/*! @brief A handle for a I2C device. */
+struct metal_i2c {
+ const struct metal_i2c_vtable *vtable;
+};
+
+/*! @brief Get a handle for a I2C device.
+ * @param device_num The index of the desired I2C device.
+ * @return A handle to the I2C device, or NULL if the device does not exist.*/
+struct metal_i2c *metal_i2c_get_device(unsigned int device_num);
+
+/*! @brief Initialize a I2C device with a certain baud rate.
+ * @param i2c The handle for the I2C device to initialize.
+ * @param baud_rate The baud rate for the I2C device to operate at.
+ * @param mode I2C operation mode.
+ */
+inline void metal_i2c_init(struct metal_i2c *i2c, unsigned int baud_rate,
+ metal_i2c_mode_t mode) {
+ i2c->vtable->init(i2c, baud_rate, mode);
+}
+
+/*! @brief Perform a I2C write.
+ * @param i2c The handle for the I2C device to perform the write operation.
+ * @param addr The I2C slave address for the write operation.
+ * @param len The number of bytes to transfer.
+ * @param buf The buffer to send over the I2C bus. Must be len bytes long.
+ * @param stop_bit Enable / Disable STOP condition.
+ * @return 0 if the write succeeds.
+ */
+inline int metal_i2c_write(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ return i2c->vtable->write(i2c, addr, len, buf, stop_bit);
+}
+
+/*! @brief Perform a I2C read.
+ * @param i2c The handle for the I2C device to perform the read operation.
+ * @param addr The I2C slave address for the read operation.
+ * @param len The number of bytes to transfer.
+ * @param buf The buffer to store data from I2C bus. Must be len bytes long.
+ * @param stop_bit Enable / Disable STOP condition.
+ * @return 0 if the read succeeds.
+ */
+inline int metal_i2c_read(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ return i2c->vtable->read(i2c, addr, len, buf, stop_bit);
+}
+
+/*! @brief Performs back to back I2C write and read operations.
+ * @param i2c The handle for the I2C device to perform the transfer operation.
+ * @param addr The I2C slave address for the transfer operation.
+ * @param txbuf The data buffer to be transmitted over I2C bus.
+ * @param txlen The number of bytes to write over I2C.
+ * @param rxbuf The buffer to store data received over I2C bus.
+ * @param rxlen The number of bytes to read over I2C.
+ * @return 0 if the transfer succeeds.
+ */
+inline int metal_i2c_transfer(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen) {
+ return i2c->vtable->transfer(i2c, addr, txbuf, txlen, rxbuf, rxlen);
+}
+
+/*! @brief Get the current baud rate of the I2C device.
+ * @param i2c The handle for the I2C device.
+ * @return The baud rate in Hz.
+ */
+inline int metal_i2c_get_baud_rate(struct metal_i2c *i2c) {
+ return i2c->vtable->get_baud_rate(i2c);
+}
+
+/*! @brief Set the current baud rate of the I2C device.
+ * @param i2c The handle for the I2C device.
+ * @param baud_rate The desired baud rate of the I2C device.
+ * @return 0 If the baud rate is successfully changed.
+ */
+inline int metal_i2c_set_baud_rate(struct metal_i2c *i2c, int baud_rate) {
+ return i2c->vtable->set_baud_rate(i2c, baud_rate);
+}
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/init.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/init.h
new file mode 100644
index 000000000..0214d0add
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/init.h
@@ -0,0 +1,130 @@
+/* Copyright 2019 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL_INIT
+#define METAL_INIT
+
+/*!
+ * @file init.h
+ * API for Metal constructors and destructors
+ */
+
+typedef void (*metal_constructor_t)(void);
+typedef void (*metal_destructor_t)(void);
+
+#define METAL_INIT_HIGHEST_PRIORITY 0
+#define METAL_INIT_DEFAULT_PRIORITY 5000
+#define METAL_INIT_LOWEST_PRIORITY 9999
+
+/*! @def METAL_CONSTRUCTOR
+ * @brief Define a Metal constructor
+ *
+ * Functions defined with METAL_CONSTRUCTOR will be added to the list of
+ * Metal constructors. By default, these functions are called before main by
+ * the metal_init() function.
+ */
+#define METAL_CONSTRUCTOR(function_name) \
+ METAL_CONSTRUCTOR_PRIO(function_name, METAL_INIT_DEFAULT_PRIORITY)
+
+/*! @def METAL_CONSTRUCTOR_PRIO
+ * @brief Define a Metal constructor with a given priority
+ *
+ * The priority argument should be an integer between 0 and 9999, where 0
+ * is the highest priority (runs first) and 9999 is the lowest priority
+ * (runs last).
+ *
+ * Functions defined with METAL_CONSTRUCTOR_PRIO will be added to the list of
+ * Metal constructors. By default, these functions are called before main by
+ * the metal_init() function.
+ */
+#define METAL_CONSTRUCTOR_PRIO(function_name, priority) \
+ __METAL_CONSTRUCTOR_PRIO(function_name, priority)
+
+/* We use this wrapper for METAL_CONSTRUCTOR_PRIORITY so that macros passed
+ * as 'priority' are expanded before being stringified by the # operator.
+ * If we don't do this, then
+ * METAL_CONSTRUCTOR(my_fn_name, METAL_INIT_DEFAULT_PRIORITY)
+ * results in .metal.init_array.METAL_INIT_DEFAULT_PRIORITY instead of
+ * .metal.init_array.5000 */
+#define __METAL_CONSTRUCTOR_PRIO(function_name, priority) \
+ __attribute__((section(".metal.ctors"))) void function_name(void); \
+ __attribute__((section(".metal.init_array." #priority))) \
+ metal_constructor_t _##function_name##_ptr = &function_name; \
+ void function_name(void)
+
+/*! @def METAL_DESTRUCTOR
+ * @brief Define a Metal destructor
+ *
+ * Functions defined with METAL_DESTRUCTOR will be added to the list of
+ * Metal destructors. By default, these functions are called on exit by
+ * the metal_fini() function.
+ */
+#define METAL_DESTRUCTOR(function_name) \
+ METAL_DESTRUCTOR_PRIO(function_name, METAL_INIT_DEFAULT_PRIORITY)
+
+/*! @def METAL_DESTRUCTOR_PRIO
+ * @brief Define a Metal destructor with a given priority
+ *
+ * The priority argument should be an integer between 0 and 9999, where 0
+ * is the highest priority (runs first) and 9999 is the lowest priority
+ * (runs last).
+ *
+ * Functions defined with METAL_DESTRUCTOR_PRIO will be added to the list of
+ * Metal destructors. By default, these functions are called on exit by
+ * the metal_fini() function.
+ */
+#define METAL_DESTRUCTOR_PRIO(function_name, priority) \
+ __METAL_DESTRUCTOR_PRIO(function_name, priority)
+#define __METAL_DESTRUCTOR_PRIO(function_name, priority) \
+ __attribute__((section(".metal.dtors"))) void function_name(void); \
+ __attribute__((section(".metal.fini_array." #priority))) \
+ metal_destructor_t _##function_name##_ptr = &function_name; \
+ void function_name(void)
+
+/*!
+ * @brief Call all Metal constructors
+ *
+ * Devices supported by Metal may define Metal constructors to perform
+ * initialization before main. This function iterates over the constructors
+ * and calls them in turn.
+ *
+ * You can add your own constructors to the functions called by metal_init()
+ * by defining functions with the METAL_CONSTRUCTOR() macro.
+ *
+ * This function is called before main by default by metal_init_run().
+ */
+void metal_init(void);
+
+/*!
+ * @brief Call all Metal destructors
+ *
+ * Devices supported by Metal may define Metal destructors to perform
+ * initialization on exit. This function iterates over the destructors
+ * and calls them in turn.
+ *
+ * You can add your own destructors to the functions called by metal_fini()
+ * by defining functions with the METAL_DESTRUCTOR() macro.
+ *
+ * This function is called on exit by default by metal_fini_run().
+ */
+void metal_fini(void);
+
+/*!
+ * @brief Weak function to call metal_init() before main
+ *
+ * This function calls metal_init() before main by default. If you wish to
+ * replace or augment this call to the Metal constructors, you can redefine
+ * metal_init_run()
+ */
+void metal_init_run(void);
+
+/*!
+ * @brief Weak function to call metal_fini() before main
+ *
+ * This function calls metal_fini() at exit by default. If you wish to
+ * replace or augment this call to the Metal destructors, you can redefine
+ * metal_fini_run()
+ */
+void metal_fini_run(void);
+
+#endif /* METAL_INIT */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/interrupt.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/interrupt.h
index 4f59bd36b..11df019de 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/interrupt.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/interrupt.h
@@ -41,35 +41,74 @@ typedef enum metal_intr_priv_mode_ {
} metal_intr_priv_mode;
/*!
+ * @brief The bitmask of hart context
+ */
+typedef struct metal_affinity_ {
+ unsigned long bitmask;
+} metal_affinity;
+
+#define for_each_metal_affinity(bit, metal_affinity) \
+ for (bit = 0; metal_affinity.bitmask; bit++, metal_affinity.bitmask >>= 1)
+
+#define metal_affinity_set_val(metal_affinity, val) \
+ metal_affinity.bitmask = val;
+
+#define metal_affinity_set_bit(metal_affinity, bit, val) \
+ metal_affinity.bitmask |= ((val & 0x1) << bit);
+
+/*!
* @brief Function signature for interrupt callback handlers
*/
-typedef void (*metal_interrupt_handler_t) (int, void *);
-typedef void (*metal_interrupt_vector_handler_t) (void);
+typedef void (*metal_interrupt_handler_t)(int, void *);
+typedef void (*metal_interrupt_vector_handler_t)(void);
struct metal_interrupt;
struct metal_interrupt_vtable {
void (*interrupt_init)(struct metal_interrupt *controller);
- int (*interrupt_set_vector_mode)(struct metal_interrupt *controller, metal_vector_mode mode);
- metal_vector_mode (*interrupt_get_vector_mode)(struct metal_interrupt *controller);
- int (*interrupt_set_privilege)(struct metal_interrupt *controller, metal_intr_priv_mode priv);
- metal_intr_priv_mode (*interrupt_get_privilege)(struct metal_interrupt *controller);
+ int (*interrupt_set_vector_mode)(struct metal_interrupt *controller,
+ metal_vector_mode mode);
+ metal_vector_mode (*interrupt_get_vector_mode)(
+ struct metal_interrupt *controller);
+ int (*interrupt_set_privilege)(struct metal_interrupt *controller,
+ metal_intr_priv_mode priv);
+ metal_intr_priv_mode (*interrupt_get_privilege)(
+ struct metal_interrupt *controller);
int (*interrupt_clear)(struct metal_interrupt *controller, int id);
int (*interrupt_set)(struct metal_interrupt *controller, int id);
int (*interrupt_register)(struct metal_interrupt *controller, int id,
- metal_interrupt_handler_t isr, void *priv_data);
+ metal_interrupt_handler_t isr, void *priv_data);
int (*interrupt_vector_register)(struct metal_interrupt *controller, int id,
- metal_interrupt_vector_handler_t isr, void *priv_data);
+ metal_interrupt_vector_handler_t isr,
+ void *priv_data);
int (*interrupt_enable)(struct metal_interrupt *controller, int id);
int (*interrupt_disable)(struct metal_interrupt *controller, int id);
int (*interrupt_vector_enable)(struct metal_interrupt *controller, int id);
int (*interrupt_vector_disable)(struct metal_interrupt *controller, int id);
unsigned int (*interrupt_get_threshold)(struct metal_interrupt *controller);
- int (*interrupt_set_threshold)(struct metal_interrupt *controller, unsigned int threshold);
- unsigned int (*interrupt_get_priority)(struct metal_interrupt *controller, int id);
- int (*interrupt_set_priority)(struct metal_interrupt *controller, int id, unsigned int priority);
- int (*command_request)(struct metal_interrupt *controller, int cmd, void *data);
- int (*mtimecmp_set)(struct metal_interrupt *controller, int hartid, unsigned long long time);
+ int (*interrupt_set_threshold)(struct metal_interrupt *controller,
+ unsigned int threshold);
+ unsigned int (*interrupt_get_priority)(struct metal_interrupt *controller,
+ int id);
+ int (*interrupt_set_priority)(struct metal_interrupt *controller, int id,
+ unsigned int priority);
+ unsigned int (*interrupt_get_preemptive_level)(
+ struct metal_interrupt *controller, int id);
+ int (*interrupt_set_preemptive_level)(struct metal_interrupt *controller,
+ int id, unsigned int level);
+ int (*command_request)(struct metal_interrupt *controller, int cmd,
+ void *data);
+ int (*mtimecmp_set)(struct metal_interrupt *controller, int hartid,
+ unsigned long long time);
+ metal_affinity (*interrupt_affinity_enable)(
+ struct metal_interrupt *controller, metal_affinity bitmask, int id);
+ metal_affinity (*interrupt_affinity_disable)(
+ struct metal_interrupt *controller, metal_affinity bitmask, int id);
+ metal_affinity (*interrupt_affinity_set_threshold)(
+ struct metal_interrupt *controller, metal_affinity bitmask,
+ unsigned int threshold);
+ unsigned int (*interrupt_affinity_get_threshold)(
+ struct metal_interrupt *controller, int context_id);
};
/*!
@@ -88,8 +127,7 @@ struct metal_interrupt {
*
* @param controller The handle for the interrupt controller
*/
-__inline__ void metal_interrupt_init(struct metal_interrupt *controller)
-{
+__inline__ void metal_interrupt_init(struct metal_interrupt *controller) {
controller->vtable->interrupt_init(controller);
}
@@ -100,8 +138,8 @@ __inline__ void metal_interrupt_init(struct metal_interrupt *controller)
* @return A handle to the interrupt controller (CLINT, CLIC, PLIC), or
* NULL if none is found for the requested label
*/
-struct metal_interrupt* metal_interrupt_get_controller(metal_intr_cntrl_type cntrl,
- int id);
+struct metal_interrupt *
+metal_interrupt_get_controller(metal_intr_cntrl_type cntrl, int id);
/*!
* @brief Configure vector mode for an interrupt controller
@@ -114,9 +152,9 @@ struct metal_interrupt* metal_interrupt_get_controller(metal_intr_cntrl_type cnt
* @param mode The vector mode of the interrupt controller.
* @return 0 upon success
*/
-__inline__ int metal_interrupt_set_vector_mode(struct metal_interrupt *controller,
- metal_vector_mode mode)
-{
+__inline__ int
+metal_interrupt_set_vector_mode(struct metal_interrupt *controller,
+ metal_vector_mode mode) {
return controller->vtable->interrupt_set_vector_mode(controller, mode);
}
@@ -131,8 +169,8 @@ __inline__ int metal_interrupt_set_vector_mode(struct metal_interrupt *controlle
* @param mode The vector mode of the interrupt controller.
* @return The interrupt vector mode
*/
-__inline__ metal_vector_mode metal_interrupt_get_vector_mode(struct metal_interrupt *controller)
-{
+__inline__ metal_vector_mode
+metal_interrupt_get_vector_mode(struct metal_interrupt *controller) {
return controller->vtable->interrupt_get_vector_mode(controller);
}
@@ -148,8 +186,7 @@ __inline__ metal_vector_mode metal_interrupt_get_vector_mode(struct metal_interr
* @return 0 upon success
*/
__inline__ int metal_interrupt_set_privilege(struct metal_interrupt *controller,
- metal_intr_priv_mode privilege)
-{
+ metal_intr_priv_mode privilege) {
return controller->vtable->interrupt_set_privilege(controller, privilege);
}
@@ -163,8 +200,8 @@ __inline__ int metal_interrupt_set_privilege(struct metal_interrupt *controller,
* @param controller The handle for the interrupt controller
* @return The interrupt privilege mode
*/
-__inline__ metal_intr_priv_mode metal_interrupt_get_privilege(struct metal_interrupt *controller)
-{
+__inline__ metal_intr_priv_mode
+metal_interrupt_get_privilege(struct metal_interrupt *controller) {
return controller->vtable->interrupt_get_privilege(controller);
}
@@ -174,10 +211,10 @@ __inline__ metal_intr_priv_mode metal_interrupt_get_privilege(struct metal_inter
* @param id The interrupt ID to trigger
* @return 0 upon success
*/
-__inline__ int metal_interrupt_clear(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_clear(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_clear(controller, id);
-}
+}
/*!
* @brief Set an interrupt
@@ -185,8 +222,7 @@ __inline__ int metal_interrupt_clear(struct metal_interrupt *controller, int id)
* @param id The interrupt ID to trigger
* @return 0 upon success
*/
-__inline__ int metal_interrupt_set(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_set(struct metal_interrupt *controller, int id) {
return controller->vtable->interrupt_set(controller, id);
}
@@ -198,12 +234,12 @@ __inline__ int metal_interrupt_set(struct metal_interrupt *controller, int id)
* @param priv_data Private data for the interrupt handler
* @return 0 upon success
*/
-__inline__ int metal_interrupt_register_handler(struct metal_interrupt *controller,
- int id,
- metal_interrupt_handler_t handler,
- void *priv_data)
-{
- return controller->vtable->interrupt_register(controller, id, handler, priv_data);
+__inline__ int
+metal_interrupt_register_handler(struct metal_interrupt *controller, int id,
+ metal_interrupt_handler_t handler,
+ void *priv_data) {
+ return controller->vtable->interrupt_register(controller, id, handler,
+ priv_data);
}
/*!
@@ -214,12 +250,11 @@ __inline__ int metal_interrupt_register_handler(struct metal_interrupt *controll
* @param priv_data Private data for the interrupt handler
* @return 0 upon success
*/
-__inline__ int metal_interrupt_register_vector_handler(struct metal_interrupt *controller,
- int id,
- metal_interrupt_vector_handler_t handler,
- void *priv_data)
-{
- return controller->vtable->interrupt_vector_register(controller, id, handler, priv_data);
+__inline__ int metal_interrupt_register_vector_handler(
+ struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t handler, void *priv_data) {
+ return controller->vtable->interrupt_vector_register(controller, id,
+ handler, priv_data);
}
/*!
@@ -228,8 +263,8 @@ __inline__ int metal_interrupt_register_vector_handler(struct metal_interrupt *c
* @param id The interrupt ID to enable
* @return 0 upon success
*/
-__inline__ int metal_interrupt_enable(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_enable(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_enable(controller, id);
}
@@ -239,8 +274,8 @@ __inline__ int metal_interrupt_enable(struct metal_interrupt *controller, int id
* @param id The interrupt ID to disable
* @return 0 upon success
*/
-__inline__ int metal_interrupt_disable(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_disable(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_disable(controller, id);
}
@@ -250,8 +285,8 @@ __inline__ int metal_interrupt_disable(struct metal_interrupt *controller, int i
* @param threshold The interrupt threshold level
* @return 0 upon success
*/
-inline int metal_interrupt_set_threshold(struct metal_interrupt *controller, unsigned int level)
-{
+__inline__ int metal_interrupt_set_threshold(struct metal_interrupt *controller,
+ unsigned int level) {
return controller->vtable->interrupt_set_threshold(controller, level);
}
@@ -260,9 +295,9 @@ inline int metal_interrupt_set_threshold(struct metal_interrupt *controller, uns
* @param controller The handle for the interrupt controller
* @return The interrupt threshold level
*/
-inline unsigned int metal_interrupt_get_threshold(struct metal_interrupt *controller)
-{
- return controller->vtable->interrupt_get_threshold(controller);
+__inline__ unsigned int
+metal_interrupt_get_threshold(struct metal_interrupt *controller) {
+ return controller->vtable->interrupt_get_threshold(controller);
}
/*!
@@ -272,9 +307,8 @@ inline unsigned int metal_interrupt_get_threshold(struct metal_interrupt *contro
* @param priority The interrupt priority level
* @return 0 upon success
*/
-inline int metal_interrupt_set_priority(struct metal_interrupt *controller,
- int id, unsigned int priority)
-{
+__inline__ int metal_interrupt_set_priority(struct metal_interrupt *controller,
+ int id, unsigned int priority) {
return controller->vtable->interrupt_set_priority(controller, id, priority);
}
@@ -284,9 +318,45 @@ inline int metal_interrupt_set_priority(struct metal_interrupt *controller,
* @param id The interrupt ID to enable
* @return The interrupt priority level
*/
-inline unsigned int metal_interrupt_get_priority(struct metal_interrupt *controller, int id)
-{
- return controller->vtable->interrupt_get_priority(controller, id);
+__inline__ unsigned int
+metal_interrupt_get_priority(struct metal_interrupt *controller, int id) {
+ return controller->vtable->interrupt_get_priority(controller, id);
+}
+
+/*!
+ * @brief Set preemptive level and priority for a given interrupt ID
+ *
+ * Set the preemptive level and priority for a given interrupt ID.
+ *
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @param level The interrupt level and priority are encoded together
+ * @return 0 upon success
+ */
+__inline__ int
+metal_interrupt_set_preemptive_level(struct metal_interrupt *controller, int id,
+ unsigned int level) {
+ if (controller->vtable->interrupt_set_preemptive_level)
+ return controller->vtable->interrupt_set_preemptive_level(controller,
+ id, level);
+ else
+ return 0;
+}
+
+/*!
+ * @brief Get an interrupt preemptive level
+ * @param controller The handle for the interrupt controller
+ * @param id The interrupt ID to enable
+ * @return The interrupt level
+ */
+__inline__ unsigned int
+metal_interrupt_get_preemptive_level(struct metal_interrupt *controller,
+ int id) {
+ if (controller->vtable->interrupt_get_preemptive_level)
+ return controller->vtable->interrupt_get_preemptive_level(controller,
+ id);
+ else
+ return 0;
}
/*!
@@ -295,8 +365,8 @@ inline unsigned int metal_interrupt_get_priority(struct metal_interrupt *control
* @param id The interrupt ID to enable
* @return 0 upon success
*/
-__inline__ int metal_interrupt_vector_enable(struct metal_interrupt *controller, int id)
-{
+__inline__ int metal_interrupt_vector_enable(struct metal_interrupt *controller,
+ int id) {
return controller->vtable->interrupt_vector_enable(controller, id);
}
@@ -306,8 +376,8 @@ __inline__ int metal_interrupt_vector_enable(struct metal_interrupt *controller,
* @param id The interrupt ID to disable
* @return 0 upon success
*/
-__inline__ int metal_interrupt_vector_disable(struct metal_interrupt *controller, int id)
-{
+__inline__ int
+metal_interrupt_vector_disable(struct metal_interrupt *controller, int id) {
return controller->vtable->interrupt_vector_disable(controller, id);
}
@@ -323,21 +393,24 @@ void __attribute__((weak, interrupt)) metal_interrupt_vector_handler(void);
* @param None
* @return None
*/
-void __attribute__((weak, interrupt)) metal_software_interrupt_vector_handler(void);
+void __attribute__((weak, interrupt))
+metal_software_interrupt_vector_handler(void);
/*!
* @brief Metal Timer interrupt vector handler, that can be overriden by user
* @param None
* @return None
*/
-void __attribute__((weak, interrupt)) metal_timer_interrupt_vector_handler(void);
+void __attribute__((weak, interrupt))
+metal_timer_interrupt_vector_handler(void);
/*!
* @brief Metal External interrupt vector handler, that can be overriden by user
* @param None
* @return None
*/
-void __attribute__((weak, interrupt)) metal_external_interrupt_vector_handler(void);
+void __attribute__((weak, interrupt))
+metal_external_interrupt_vector_handler(void);
/*!
* @brief Metal Local 0 interrupt vector handler, that can be overriden by user
@@ -387,7 +460,7 @@ void __attribute__((weak, interrupt)) metal_lc5_interrupt_vector_handler(void);
* @return None
*/
void __attribute__((weak, interrupt)) metal_lc6_interrupt_vector_handler(void);
-
+
/*!
* @brief Metal Local 7 interrupt vector handler, that can be overriden by user
* @param None
@@ -451,11 +524,67 @@ void __attribute__((weak, interrupt)) metal_lc14_interrupt_vector_handler(void);
*/
void __attribute__((weak, interrupt)) metal_lc15_interrupt_vector_handler(void);
-/* Utilities function to controll, manages devices via a given interrupt controller */
-__inline__ int _metal_interrupt_command_request(struct metal_interrupt *controller,
- int cmd, void *data)
-{
+/* Utilities function to controll, manages devices via a given interrupt
+ * controller */
+__inline__ int
+_metal_interrupt_command_request(struct metal_interrupt *controller, int cmd,
+ void *data) {
return controller->vtable->command_request(controller, cmd, data);
}
+/*!
+ * @brief Enable an interrupt for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to enable
+ * @param id The interrupt ID to enable
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_enable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ return controller->vtable->interrupt_affinity_enable(controller, bitmask,
+ id);
+}
+
+/*!
+ * @brief Disable an interrupt for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to disable
+ * @param id The interrupt ID to disable
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_disable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ return controller->vtable->interrupt_affinity_disable(controller, bitmask,
+ id);
+}
+
+/*!
+ * @brief Set interrupt threshold level for the hart contexts
+ * @param controller The handle for the interrupt controller
+ * @param bitmask The bit mask of hart contexts to set threshold
+ * @param threshold The interrupt threshold level
+ * @return The result of each hart context. 0 upon success at relevant bit.
+ */
+__inline__ metal_affinity
+metal_interrupt_affinity_set_threshold(struct metal_interrupt *controller,
+ metal_affinity bitmask,
+ unsigned int level) {
+ return controller->vtable->interrupt_affinity_set_threshold(controller,
+ bitmask, level);
+}
+
+/*!
+ * @brief Get an interrupt threshold level from the hart context
+ * @param controller The handle for the interrupt controller
+ * @param context_id The hart context ID to get threshold
+ * @return The interrupt threshold level
+ */
+__inline__ unsigned int
+metal_interrupt_affinity_get_threshold(struct metal_interrupt *controller,
+ int context_id) {
+ return controller->vtable->interrupt_affinity_get_threshold(controller,
+ context_id);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/io.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/io.h
index d55b4520a..f1df85518 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/io.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/io.h
@@ -8,15 +8,16 @@
#define __METAL_ACCESS_ONCE(x) (*(__typeof__(*x) volatile *)(x))
/* Allows users to specify arbitrary fences. */
-#define __METAL_IO_FENCE(pred, succ) __asm__ volatile ("fence " #pred "," #succ ::: "memory");
+#define __METAL_IO_FENCE(pred, succ) \
+ __asm__ volatile("fence " #pred "," #succ ::: "memory");
/* Types that explicitly describe an address as being used for memory-mapped
* IO. These should only be accessed via __METAL_ACCESS_ONCE. */
-typedef unsigned char __metal_io_u8;
+typedef unsigned char __metal_io_u8;
typedef unsigned short __metal_io_u16;
-typedef unsigned int __metal_io_u32;
+typedef unsigned int __metal_io_u32;
#if __riscv_xlen >= 64
-typedef unsigned long __metal_io_u64;
+typedef unsigned long __metal_io_u64;
#endif
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/itim.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/itim.h
index 1a2a05b8b..3decefff2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/itim.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/itim.h
@@ -9,13 +9,12 @@
* API for manipulating ITIM allocation
*/
-
/*! @def METAL_PLACE_IN_ITIM
* @brief Link a function into the ITIM
*
* Link a function into the ITIM (Instruction Tightly Integrated
* Memory) if the ITIM is present on the target device.
*/
-#define METAL_PLACE_IN_ITIM __attribute__((section(".itim")))
+#define METAL_PLACE_IN_ITIM __attribute__((section(".itim")))
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/led.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/led.h
index f2aa39ceb..da2555fb8 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/led.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/led.h
@@ -31,38 +31,47 @@ struct metal_led {
* @param label The DeviceTree label for the desired LED
* @return A handle to the LED, or NULL if none is found for the requested label
*/
-struct metal_led* metal_led_get(char *label);
+struct metal_led *metal_led_get(char *label);
/*!
* @brief Get a handle for a channel of an RGB LED
* @param label The DeviceTree label for the desired LED
* @param color The color for the LED in the DeviceTree
- * @return A handle to the LED, or NULL if none is found for the requested label and color
+ * @return A handle to the LED, or NULL if none is found for the requested label
+ * and color
*/
-struct metal_led* metal_led_get_rgb(char *label, char *color);
+struct metal_led *metal_led_get_rgb(char *label, char *color);
/*!
* @brief Enable an LED
* @param led The handle for the LED
*/
-__inline__ void metal_led_enable(struct metal_led *led) { led->vtable->led_enable(led); }
+__inline__ void metal_led_enable(struct metal_led *led) {
+ led->vtable->led_enable(led);
+}
/*!
* @brief Turn an LED on
* @param led The handle for the LED
*/
-__inline__ void metal_led_on(struct metal_led *led) { led->vtable->led_on(led); }
+__inline__ void metal_led_on(struct metal_led *led) {
+ led->vtable->led_on(led);
+}
/*!
* @brief Turn an LED off
* @param led The handle for the LED
*/
-__inline__ void metal_led_off(struct metal_led *led) { led->vtable->led_off(led); }
+__inline__ void metal_led_off(struct metal_led *led) {
+ led->vtable->led_off(led);
+}
/*!
* @brief Toggle the on/off state of an LED
* @param led The handle for the LED
*/
-__inline__ void metal_led_toggle(struct metal_led *led) { led->vtable->led_toggle(led); }
+__inline__ void metal_led_toggle(struct metal_led *led) {
+ led->vtable->led_toggle(led);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lim.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lim.h
new file mode 100644
index 000000000..1e573cad6
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lim.h
@@ -0,0 +1,20 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__LIM_H
+#define METAL__LIM_H
+
+/*! @file lim.h
+ *
+ * API for manipulating LIM allocation
+ */
+
+/*! @def METAL_PLACE_IN_LIM
+ * @brief Link a function into the LIM
+ *
+ * Link a function into the LIM (Loosely Integrated
+ * Memory) if the LIM is present on the target device.
+ */
+#define METAL_PLACE_IN_LIM __attribute__((section(".lim")))
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lock.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lock.h
index 0702cbf16..e591eaefa 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lock.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/lock.h
@@ -4,9 +4,9 @@
#ifndef METAL__LOCK_H
#define METAL__LOCK_H
+#include <metal/compiler.h>
#include <metal/machine.h>
#include <metal/memory.h>
-#include <metal/compiler.h>
/*!
* @file lock.h
@@ -26,21 +26,21 @@
* Locks must be declared with METAL_LOCK_DECLARE to ensure that the lock
* is linked into a memory region which supports atomic memory operations.
*/
-#define METAL_LOCK_DECLARE(name) \
- __attribute__((section(".data.locks"))) \
- struct metal_lock name
+#define METAL_LOCK_DECLARE(name) \
+ __attribute__((section(".data.locks"))) struct metal_lock name
/*!
* @brief A handle for a lock
*/
struct metal_lock {
- int _state;
+ int _state;
};
/*!
* @brief Initialize a lock
* @param lock The handle for a lock
- * @return 0 if the lock is successfully initialized. A non-zero code indicates failure.
+ * @return 0 if the lock is successfully initialized. A non-zero code indicates
+ * failure.
*
* If the lock cannot be initialized, attempts to take or give the lock
* will result in a Store/AMO access fault.
@@ -48,13 +48,14 @@ struct metal_lock {
__inline__ int metal_lock_init(struct metal_lock *lock) {
#ifdef __riscv_atomic
/* Get a handle for the memory which holds the lock state */
- struct metal_memory *lock_mem = metal_get_memory_from_address((uintptr_t) &(lock->_state));
- if(!lock_mem) {
+ struct metal_memory *lock_mem =
+ metal_get_memory_from_address((uintptr_t) & (lock->_state));
+ if (!lock_mem) {
return 1;
}
/* If the memory doesn't support atomics, report an error */
- if(!metal_memory_supports_atomics(lock_mem)) {
+ if (!metal_memory_supports_atomics(lock_mem)) {
return 2;
}
@@ -82,10 +83,10 @@ __inline__ int metal_lock_take(struct metal_lock *lock) {
int backoff = 1;
const int max_backoff = METAL_LOCK_BACKOFF_CYCLES * METAL_MAX_CORES;
- while(1) {
+ while (1) {
__asm__ volatile("amoswap.w.aq %[old], %[new], (%[state])"
- : [old] "=r" (old)
- : [new] "r" (new), [state] "r" (&(lock->_state))
+ : [old] "=r"(old)
+ : [new] "r"(new), [state] "r"(&(lock->_state))
: "memory");
if (old == 0) {
@@ -104,8 +105,7 @@ __inline__ int metal_lock_take(struct metal_lock *lock) {
return 0;
#else
/* Store the memory address in mtval like a normal store/amo access fault */
- __asm__ ("csrw mtval, %[state]"
- :: [state] "r" (&(lock->_state)));
+ __asm__("csrw mtval, %[state]" ::[state] "r"(&(lock->_state)));
/* Trigger a Store/AMO access fault */
_metal_trap(_METAL_STORE_AMO_ACCESS_FAULT);
@@ -125,15 +125,14 @@ __inline__ int metal_lock_take(struct metal_lock *lock) {
*/
__inline__ int metal_lock_give(struct metal_lock *lock) {
#ifdef __riscv_atomic
- __asm__ volatile("amoswap.w.rl x0, x0, (%[state])"
- :: [state] "r" (&(lock->_state))
- : "memory");
+ __asm__ volatile(
+ "amoswap.w.rl x0, x0, (%[state])" ::[state] "r"(&(lock->_state))
+ : "memory");
return 0;
#else
/* Store the memory address in mtval like a normal store/amo access fault */
- __asm__ ("csrw mtval, %[state]"
- :: [state] "r" (&(lock->_state)));
+ __asm__("csrw mtval, %[state]" ::[state] "r"(&(lock->_state)));
/* Trigger a Store/AMO access fault */
_metal_trap(_METAL_STORE_AMO_ACCESS_FAULT);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/memory.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/memory.h
index 9de7d6162..f009e9ecc 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/memory.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/memory.h
@@ -4,8 +4,8 @@
#ifndef METAL__MEMORY_H
#define METAL__MEMORY_H
-#include <stdint.h>
#include <stddef.h>
+#include <stdint.h>
/*!
* @file memory.h
@@ -14,20 +14,20 @@
*/
struct _metal_memory_attributes {
- unsigned int R : 1;
- unsigned int W : 1;
- unsigned int X : 1;
- unsigned int C : 1;
- unsigned int A : 1;
+ unsigned int R : 1;
+ unsigned int W : 1;
+ unsigned int X : 1;
+ unsigned int C : 1;
+ unsigned int A : 1;
};
/*!
* @brief A handle for a memory block
*/
struct metal_memory {
- const uintptr_t _base_address;
- const size_t _size;
- const struct _metal_memory_attributes _attrs;
+ const uintptr_t _base_address;
+ const size_t _size;
+ const struct _metal_memory_attributes _attrs;
};
/*!
@@ -37,7 +37,8 @@ struct metal_memory {
* that address is mapped.
*
* @param address The address to query
- * @return The memory block handle, or NULL if the address is not mapped to a memory block
+ * @return The memory block handle, or NULL if the address is not mapped to a
+ * memory block
*/
struct metal_memory *metal_get_memory_from_address(const uintptr_t address);
@@ -46,8 +47,9 @@ struct metal_memory *metal_get_memory_from_address(const uintptr_t address);
* @param memory The handle for the memory block
* @return The base address of the memory block
*/
-__inline__ uintptr_t metal_memory_get_base_address(const struct metal_memory *memory) {
- return memory->_base_address;
+__inline__ uintptr_t
+metal_memory_get_base_address(const struct metal_memory *memory) {
+ return memory->_base_address;
}
/*!
@@ -56,7 +58,7 @@ __inline__ uintptr_t metal_memory_get_base_address(const struct metal_memory *me
* @return The size of the memory block
*/
__inline__ size_t metal_memory_get_size(const struct metal_memory *memory) {
- return memory->_size;
+ return memory->_size;
}
/*!
@@ -64,8 +66,9 @@ __inline__ size_t metal_memory_get_size(const struct metal_memory *memory) {
* @param memory The handle for the memory block
* @return nonzero if the memory block supports atomic operations
*/
-__inline__ int metal_memory_supports_atomics(const struct metal_memory *memory) {
- return memory->_attrs.A;
+__inline__ int
+metal_memory_supports_atomics(const struct metal_memory *memory) {
+ return memory->_attrs.A;
}
/*!
@@ -74,8 +77,7 @@ __inline__ int metal_memory_supports_atomics(const struct metal_memory *memory)
* @return nonzero if the memory block is cachable
*/
__inline__ int metal_memory_is_cachable(const struct metal_memory *memory) {
- return memory->_attrs.C;
+ return memory->_attrs.C;
}
#endif /* METAL__MEMORY_H */
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pmp.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pmp.h
index d948656c8..38ab1b9a4 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pmp.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pmp.h
@@ -12,14 +12,14 @@
* The Physical Memory Protection (PMP) interface on RISC-V cores
* is a form of memory protection unit which allows for a finite number
* of physical memory regions to be configured with certain access
- * permissions.
+ * permissions.
*
* Additional information about the use and configuration rules for PMPs
* can be found by reading the RISC-V Privileged Architecture Specification.
*/
-#include <stddef.h>
#include <metal/machine.h>
+#include <stddef.h>
struct metal_pmp;
@@ -28,11 +28,11 @@ struct metal_pmp;
*/
enum metal_pmp_address_mode {
/*! @brief Disable the PMP region */
- METAL_PMP_OFF = 0,
+ METAL_PMP_OFF = 0,
/*! @brief Use Top-of-Range mode */
- METAL_PMP_TOR = 1,
+ METAL_PMP_TOR = 1,
/*! @brief Use naturally-aligned 4-byte region mode */
- METAL_PMP_NA4 = 2,
+ METAL_PMP_NA4 = 2,
/*! @brief Use naturally-aligned power-of-two mode */
METAL_PMP_NAPOT = 3
};
@@ -56,7 +56,7 @@ struct metal_pmp_config {
/*! @brief Sets whether the PMP region is locked */
enum metal_pmp_locked {
METAL_PMP_UNLOCKED = 0,
- METAL_PMP_LOCKED = 1
+ METAL_PMP_LOCKED = 1
} L : 1;
};
@@ -101,9 +101,10 @@ void metal_pmp_init(struct metal_pmp *pmp);
* @param address The desired address of the PMP region
* @return 0 upon success
*/
-int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region, struct metal_pmp_config config, size_t address);
+int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config config, size_t address);
-/*!
+/*!
* @brief Get the configuration for a PMP region
* @param pmp The PMP device handle
* @param region The PMP region to read
@@ -111,7 +112,8 @@ int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region, struct meta
* @param address Variable to store the PMP region address
* @return 0 if the region is read successfully
*/
-int metal_pmp_get_region(struct metal_pmp *pmp, unsigned int region, struct metal_pmp_config *config, size_t *address);
+int metal_pmp_get_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config *config, size_t *address);
/*!
* @brief Lock a PMP region
@@ -128,7 +130,8 @@ int metal_pmp_lock(struct metal_pmp *pmp, unsigned int region);
* @param address The desired address of the PMP region
* @return 0 if the address is successfully set
*/
-int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region, size_t address);
+int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region,
+ size_t address);
/*!
* @brief Get the address of a PMP region
@@ -145,7 +148,8 @@ size_t metal_pmp_get_address(struct metal_pmp *pmp, unsigned int region);
* @param mode The PMP addressing mode to set
* @return 0 if the addressing mode is successfully set
*/
-int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum metal_pmp_address_mode mode);
+int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region,
+ enum metal_pmp_address_mode mode);
/*!
* @brief Get the addressing mode of a PMP region
@@ -153,7 +157,8 @@ int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum
* @param region The PMP region to read
* @return The address mode of the PMP region
*/
-enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp, unsigned int region);
+enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp,
+ unsigned int region);
/*!
* @brief Set the executable bit for a PMP region
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/privilege.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/privilege.h
index 928a936b1..522e7efe0 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/privilege.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/privilege.h
@@ -16,9 +16,9 @@
#include <stdint.h>
enum metal_privilege_mode {
- METAL_PRIVILEGE_USER = 0,
- METAL_PRIVILEGE_SUPERVISOR = 1,
- METAL_PRIVILEGE_MACHINE = 3,
+ METAL_PRIVILEGE_USER = 0,
+ METAL_PRIVILEGE_SUPERVISOR = 1,
+ METAL_PRIVILEGE_MACHINE = 3,
};
#if __riscv_xlen == 32
@@ -34,89 +34,89 @@ typedef uint64_t metal_freg_t;
#endif
struct metal_register_file {
- metal_xreg_t ra;
- metal_xreg_t sp;
- metal_xreg_t gp;
- metal_xreg_t tp;
-
- metal_xreg_t t0;
- metal_xreg_t t1;
- metal_xreg_t t2;
-
- metal_xreg_t s0;
- metal_xreg_t s1;
-
- metal_xreg_t a0;
- metal_xreg_t a1;
- metal_xreg_t a2;
- metal_xreg_t a3;
- metal_xreg_t a4;
- metal_xreg_t a5;
+ metal_xreg_t ra;
+ metal_xreg_t sp;
+ metal_xreg_t gp;
+ metal_xreg_t tp;
+
+ metal_xreg_t t0;
+ metal_xreg_t t1;
+ metal_xreg_t t2;
+
+ metal_xreg_t s0;
+ metal_xreg_t s1;
+
+ metal_xreg_t a0;
+ metal_xreg_t a1;
+ metal_xreg_t a2;
+ metal_xreg_t a3;
+ metal_xreg_t a4;
+ metal_xreg_t a5;
#ifndef __riscv_32e
- metal_xreg_t a6;
- metal_xreg_t a7;
-
- metal_xreg_t s2;
- metal_xreg_t s3;
- metal_xreg_t s4;
- metal_xreg_t s5;
- metal_xreg_t s6;
- metal_xreg_t s7;
- metal_xreg_t s8;
- metal_xreg_t s9;
- metal_xreg_t s10;
- metal_xreg_t s11;
-
- metal_xreg_t t3;
- metal_xreg_t t4;
- metal_xreg_t t5;
- metal_xreg_t t6;
+ metal_xreg_t a6;
+ metal_xreg_t a7;
+
+ metal_xreg_t s2;
+ metal_xreg_t s3;
+ metal_xreg_t s4;
+ metal_xreg_t s5;
+ metal_xreg_t s6;
+ metal_xreg_t s7;
+ metal_xreg_t s8;
+ metal_xreg_t s9;
+ metal_xreg_t s10;
+ metal_xreg_t s11;
+
+ metal_xreg_t t3;
+ metal_xreg_t t4;
+ metal_xreg_t t5;
+ metal_xreg_t t6;
#endif /* __riscv_32e */
#ifdef __riscv_flen
- metal_freg_t ft0;
- metal_freg_t ft1;
- metal_freg_t ft2;
- metal_freg_t ft3;
- metal_freg_t ft4;
- metal_freg_t ft5;
- metal_freg_t ft6;
- metal_freg_t ft7;
-
- metal_freg_t fs0;
- metal_freg_t fs1;
-
- metal_freg_t fa0;
- metal_freg_t fa1;
- metal_freg_t fa2;
- metal_freg_t fa3;
- metal_freg_t fa4;
- metal_freg_t fa5;
- metal_freg_t fa6;
- metal_freg_t fa7;
-
- metal_freg_t fs2;
- metal_freg_t fs3;
- metal_freg_t fs4;
- metal_freg_t fs5;
- metal_freg_t fs6;
- metal_freg_t fs7;
- metal_freg_t fs8;
- metal_freg_t fs9;
- metal_freg_t fs10;
- metal_freg_t fs11;
-
- metal_freg_t ft8;
- metal_freg_t ft9;
- metal_freg_t ft10;
- metal_freg_t ft11;
+ metal_freg_t ft0;
+ metal_freg_t ft1;
+ metal_freg_t ft2;
+ metal_freg_t ft3;
+ metal_freg_t ft4;
+ metal_freg_t ft5;
+ metal_freg_t ft6;
+ metal_freg_t ft7;
+
+ metal_freg_t fs0;
+ metal_freg_t fs1;
+
+ metal_freg_t fa0;
+ metal_freg_t fa1;
+ metal_freg_t fa2;
+ metal_freg_t fa3;
+ metal_freg_t fa4;
+ metal_freg_t fa5;
+ metal_freg_t fa6;
+ metal_freg_t fa7;
+
+ metal_freg_t fs2;
+ metal_freg_t fs3;
+ metal_freg_t fs4;
+ metal_freg_t fs5;
+ metal_freg_t fs6;
+ metal_freg_t fs7;
+ metal_freg_t fs8;
+ metal_freg_t fs9;
+ metal_freg_t fs10;
+ metal_freg_t fs11;
+
+ metal_freg_t ft8;
+ metal_freg_t ft9;
+ metal_freg_t ft10;
+ metal_freg_t ft11;
#endif /* __riscv_flen */
};
typedef void (*metal_privilege_entry_point_t)(void);
void metal_privilege_drop_to_mode(enum metal_privilege_mode mode,
- struct metal_register_file regfile,
- metal_privilege_entry_point_t entry_point);
+ struct metal_register_file regfile,
+ metal_privilege_entry_point_t entry_point);
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pwm.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pwm.h
new file mode 100644
index 000000000..600d5a02b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/pwm.h
@@ -0,0 +1,162 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__PWM_H
+#define METAL__PWM_H
+
+/*! @brief Enums for PWM running modes. */
+typedef enum {
+ METAL_PWM_CONTINUOUS = 0,
+ METAL_PWM_ONE_SHOT = 1
+} metal_pwm_run_mode_t;
+
+/*! @brief Enums for Phase correct PWM. */
+typedef enum {
+ METAL_PWM_PHASE_CORRECT_DISABLE = 0,
+ METAL_PWM_PHASE_CORRECT_ENABLE = 1,
+} metal_pwm_phase_correct_t;
+
+/*! @brief Enums for Interrupts enable/disable. */
+typedef enum {
+ METAL_PWM_INTERRUPT_DISABLE = 0,
+ METAL_PWM_INTERRUPT_ENABLE = 1,
+} metal_pwm_interrupt_t;
+
+struct metal_pwm;
+
+/*! @brief vtable for PWM. */
+struct metal_pwm_vtable {
+ int (*enable)(struct metal_pwm *pwm);
+ int (*disable)(struct metal_pwm *pwm);
+ int (*set_freq)(struct metal_pwm *pwm, unsigned int idx, unsigned int freq);
+ int (*set_duty)(struct metal_pwm *pwm, unsigned int idx, unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr);
+ unsigned int (*get_duty)(struct metal_pwm *pwm, unsigned int idx);
+ unsigned int (*get_freq)(struct metal_pwm *pwm, unsigned int idx);
+ int (*trigger)(struct metal_pwm *pwm, unsigned int idx,
+ metal_pwm_run_mode_t mode);
+ int (*stop)(struct metal_pwm *pwm, unsigned int idx);
+ int (*cfg_interrupt)(struct metal_pwm *pwm, metal_pwm_interrupt_t flag);
+ int (*clr_interrupt)(struct metal_pwm *pwm, unsigned int idx);
+ struct metal_interrupt *(*get_interrupt_controller)(struct metal_pwm *pwm);
+ int (*get_interrupt_id)(struct metal_pwm *pwm, unsigned int idx);
+};
+
+/*! @brief A handle for a PWM device. */
+struct metal_pwm {
+ const struct metal_pwm_vtable *vtable;
+};
+
+/*! @brief Gets a PWM device handle.
+ * @param device_num The index of the desired PWM device.
+ * @return A handle to the PWM device, or NULL if the device does not exist.*/
+struct metal_pwm *metal_pwm_get_device(unsigned int device_num);
+
+/*! @brief Enables PWM operation.
+ * @param pwm The handle for the PWM device to initialize.
+ * @return 0 If no error.*/
+inline int metal_pwm_enable(struct metal_pwm *pwm) {
+ return pwm->vtable->enable(pwm);
+}
+
+/*! @brief Disables PWM operation.
+ * @param pwm The handle for the PWM device to be disabled.
+ * @return 0 If no error.*/
+inline int metal_pwm_disable(struct metal_pwm *pwm) {
+ return pwm->vtable->disable(pwm);
+}
+
+/*! @brief Sets frequency in Hz for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @param freq PWM frequency in Hz.
+ * @return 0 If no error.*/
+inline int metal_pwm_set_freq(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int freq) {
+ return pwm->vtable->set_freq(pwm, idx, freq);
+}
+
+/*! @brief Sets duty cycle in percent values [0 - 100] for a given PWM instance.
+ * Phase correct mode provides center aligned PWM waveform output.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @param duty PWM duty cycle value.
+ * @param phase_corr Enable / Disable phase correct mode.
+ * @return 0 If no error.*/
+inline int metal_pwm_set_duty(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr) {
+ return pwm->vtable->set_duty(pwm, idx, duty, phase_corr);
+}
+
+/*! @brief Gets duty cycle in percent values [0 - 100] for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return PWM duty cycle value.*/
+inline unsigned int metal_pwm_get_duty(struct metal_pwm *pwm,
+ unsigned int idx) {
+ return pwm->vtable->get_duty(pwm, idx);
+}
+
+/*! @brief Gets frequency in Hz for a given PWM instance.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return PWM frequency in Hz.*/
+inline unsigned int metal_pwm_get_freq(struct metal_pwm *pwm,
+ unsigned int idx) {
+ return pwm->vtable->get_freq(pwm, idx);
+}
+
+/*! @brief Starts a PWM instance in selected run mode (continuous/one shot).
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_trigger(struct metal_pwm *pwm, unsigned int idx,
+ metal_pwm_run_mode_t mode) {
+ return pwm->vtable->trigger(pwm, idx, mode);
+}
+
+/*! @brief Stops a running PWM instance in continuous mode.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_stop(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->stop(pwm, idx);
+}
+
+/*! @brief Enable or Disable PWM interrupts.
+ * @param pwm PWM device handle.
+ * @param flag PWM interrupt enable flag.
+ * @return 0 If no error.*/
+inline int metal_pwm_cfg_interrupt(struct metal_pwm *pwm,
+ metal_pwm_interrupt_t flag) {
+ return pwm->vtable->cfg_interrupt(pwm, flag);
+}
+
+/*! @brief Clears pending interrupt flags.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return 0 If no error.*/
+inline int metal_pwm_clr_interrupt(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->clr_interrupt(pwm, idx);
+}
+
+/*! @brief Get the interrupt controller of the PWM peripheral.
+ * The interrupt controller must be initialized before any interrupts can be
+ * registered or enabled with it.
+ * @param pwm PWM device handle.
+ * @return The handle for the PWM interrupt controller.*/
+inline struct metal_interrupt *
+metal_pwm_interrupt_controller(struct metal_pwm *pwm) {
+ return pwm->vtable->get_interrupt_controller(pwm);
+}
+
+/*! @brief Get the interrupt ID of the PWM peripheral.
+ * @param pwm PWM device handle.
+ * @param idx PWM channel id.
+ * @return The PWM interrupt id.*/
+inline int metal_pwm_get_interrupt_id(struct metal_pwm *pwm, unsigned int idx) {
+ return pwm->vtable->get_interrupt_id(pwm, idx);
+}
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/rtc.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/rtc.h
index 2e742ea38..e1b798268 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/rtc.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/rtc.h
@@ -23,12 +23,16 @@ enum metal_rtc_run_option {
struct metal_rtc_vtable {
uint64_t (*get_rate)(const struct metal_rtc *const rtc);
- uint64_t (*set_rate)(const struct metal_rtc *const rtc, const uint64_t rate);
+ uint64_t (*set_rate)(const struct metal_rtc *const rtc,
+ const uint64_t rate);
uint64_t (*get_compare)(const struct metal_rtc *const rtc);
- uint64_t (*set_compare)(const struct metal_rtc *const rtc, const uint64_t compare);
+ uint64_t (*set_compare)(const struct metal_rtc *const rtc,
+ const uint64_t compare);
uint64_t (*get_count)(const struct metal_rtc *const rtc);
- uint64_t (*set_count)(const struct metal_rtc *const rtc, const uint64_t count);
- int (*run)(const struct metal_rtc *const rtc, const enum metal_rtc_run_option option);
+ uint64_t (*set_count)(const struct metal_rtc *const rtc,
+ const uint64_t count);
+ int (*run)(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option);
struct metal_interrupt *(*get_interrupt)(const struct metal_rtc *const rtc);
int (*get_interrupt_id)(const struct metal_rtc *const rtc);
};
@@ -52,7 +56,8 @@ inline uint64_t metal_rtc_get_rate(const struct metal_rtc *const rtc) {
* @brief Set (if possible) the rate of the RTC
* @return The new rate of the RTC (not guaranteed to be the same as requested)
*/
-inline uint64_t metal_rtc_set_rate(const struct metal_rtc *const rtc, const uint64_t rate) {
+inline uint64_t metal_rtc_set_rate(const struct metal_rtc *const rtc,
+ const uint64_t rate) {
return rtc->vtable->set_rate(rtc, rate);
}
@@ -66,12 +71,14 @@ inline uint64_t metal_rtc_get_compare(const struct metal_rtc *const rtc) {
/*!
* @brief Set the compare value of the RTC
- * @return The set compare value (not guaranteed to be exactly the requested value)
+ * @return The set compare value (not guaranteed to be exactly the requested
+ * value)
*
- * The RTC device might impose limits on the maximum compare value or the granularity
- * of the compare value.
+ * The RTC device might impose limits on the maximum compare value or the
+ * granularity of the compare value.
*/
-inline uint64_t metal_rtc_set_compare(const struct metal_rtc *const rtc, const uint64_t compare) {
+inline uint64_t metal_rtc_set_compare(const struct metal_rtc *const rtc,
+ const uint64_t compare) {
return rtc->vtable->set_compare(rtc, compare);
}
@@ -85,11 +92,13 @@ inline uint64_t metal_rtc_get_count(const struct metal_rtc *const rtc) {
/*!
* @brief Set the current count of the RTC
- * @return The set value of the count (not guaranteed to be exactly the requested value)
+ * @return The set value of the count (not guaranteed to be exactly the
+ * requested value)
*
* The RTC device might impose limits on the maximum value of the count
*/
-inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc, const uint64_t count) {
+inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc,
+ const uint64_t count) {
return rtc->vtable->set_count(rtc, count);
}
@@ -97,7 +106,8 @@ inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc, const uin
* @brief Start or stop the RTC
* @return 0 if the RTC was successfully started/stopped
*/
-inline int metal_rtc_run(const struct metal_rtc *const rtc, const enum metal_rtc_run_option option) {
+inline int metal_rtc_run(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option) {
return rtc->vtable->run(rtc, option);
}
@@ -105,7 +115,8 @@ inline int metal_rtc_run(const struct metal_rtc *const rtc, const enum metal_rtc
* @brief Get the interrupt handle for the RTC compare
* @return The interrupt handle
*/
-inline struct metal_interrupt *metal_rtc_get_interrupt(const struct metal_rtc *const rtc) {
+inline struct metal_interrupt *
+metal_rtc_get_interrupt(const struct metal_rtc *const rtc) {
return rtc->vtable->get_interrupt(rtc);
}
@@ -124,4 +135,3 @@ inline int metal_rtc_get_interrupt_id(const struct metal_rtc *const rtc) {
struct metal_rtc *metal_rtc_get_device(int index);
#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/scrub.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/scrub.h
new file mode 100644
index 000000000..51683cc76
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/scrub.h
@@ -0,0 +1,13 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#ifndef METAL__SCRUB_H
+#define METAL__SCRUB_H
+
+/*! @brief Writes specified memory region with zeros.
+ * @param address Start memory address for zero-scrub.
+ * @param size Memory region size in bytes.
+ * @return None.*/
+void metal_mem_scrub(void *address, int size);
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/shutdown.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/shutdown.h
index 8d4020b5c..7a43437b7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/shutdown.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/shutdown.h
@@ -12,15 +12,20 @@
struct __metal_shutdown;
struct __metal_shutdown_vtable {
- void (*exit)(const struct __metal_shutdown *sd, int code) __attribute__((noreturn));
+ void (*exit)(const struct __metal_shutdown *sd, int code)
+ __attribute__((noreturn));
};
struct __metal_shutdown {
const struct __metal_shutdown_vtable *vtable;
};
-__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd, int code) __attribute__((noreturn));
-__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd, int code) { sd->vtable->exit(sd, code); }
+__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd,
+ int code) __attribute__((noreturn));
+__inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd,
+ int code) {
+ sd->vtable->exit(sd, code);
+}
/*!
* @brief The public METAL shutdown interface
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/spi.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/spi.h
index 635e3c151..7e4b04ae2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/spi.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/spi.h
@@ -9,11 +9,7 @@ struct metal_spi;
/*! @brief The configuration for a SPI transfer */
struct metal_spi_config {
/*! @brief The protocol for the SPI transfer */
- enum {
- METAL_SPI_SINGLE,
- METAL_SPI_DUAL,
- METAL_SPI_QUAD
- } protocol;
+ enum { METAL_SPI_SINGLE, METAL_SPI_DUAL, METAL_SPI_QUAD } protocol;
/*! @brief The polarity of the SPI transfer, equivalent to CPOL */
unsigned int polarity : 1;
@@ -41,7 +37,8 @@ struct metal_spi_config {
struct metal_spi_vtable {
void (*init)(struct metal_spi *spi, int baud_rate);
- int (*transfer)(struct metal_spi *spi, struct metal_spi_config *config, size_t len, char *tx_buf, char *rx_buf);
+ int (*transfer)(struct metal_spi *spi, struct metal_spi_config *config,
+ size_t len, char *tx_buf, char *rx_buf);
int (*get_baud_rate)(struct metal_spi *spi);
int (*set_baud_rate)(struct metal_spi *spi, int baud_rate);
};
@@ -60,17 +57,23 @@ struct metal_spi *metal_spi_get_device(unsigned int device_num);
* @param spi The handle for the SPI device to initialize
* @param baud_rate The baud rate to set the SPI device to
*/
-__inline__ void metal_spi_init(struct metal_spi *spi, int baud_rate) { spi->vtable->init(spi, baud_rate); }
+__inline__ void metal_spi_init(struct metal_spi *spi, int baud_rate) {
+ spi->vtable->init(spi, baud_rate);
+}
/*! @brief Perform a SPI transfer
* @param spi The handle for the SPI device to perform the transfer
* @param config The configuration for the SPI transfer.
* @param len The number of bytes to transfer
- * @param tx_buf The buffer to send over the SPI bus. Must be len bytes long. If NULL, the SPI will transfer the value 0.
- * @param rx_buf The buffer to receive data into. Must be len bytes long. If NULL, the SPI will ignore received bytes.
+ * @param tx_buf The buffer to send over the SPI bus. Must be len bytes long. If
+ * NULL, the SPI will transfer the value 0.
+ * @param rx_buf The buffer to receive data into. Must be len bytes long. If
+ * NULL, the SPI will ignore received bytes.
* @return 0 if the transfer succeeds
*/
-__inline__ int metal_spi_transfer(struct metal_spi *spi, struct metal_spi_config *config, size_t len, char *tx_buf, char *rx_buf) {
+__inline__ int metal_spi_transfer(struct metal_spi *spi,
+ struct metal_spi_config *config, size_t len,
+ char *tx_buf, char *rx_buf) {
return spi->vtable->transfer(spi, config, len, tx_buf, rx_buf);
}
@@ -78,13 +81,17 @@ __inline__ int metal_spi_transfer(struct metal_spi *spi, struct metal_spi_config
* @param spi The handle for the SPI device
* @return The baud rate in Hz
*/
-__inline__ int metal_spi_get_baud_rate(struct metal_spi *spi) { return spi->vtable->get_baud_rate(spi); }
+__inline__ int metal_spi_get_baud_rate(struct metal_spi *spi) {
+ return spi->vtable->get_baud_rate(spi);
+}
/*! @brief Set the current baud rate of the SPI device
* @param spi The handle for the SPI device
* @param baud_rate The desired baud rate of the SPI device
* @return 0 if the baud rate is successfully changed
*/
-__inline__ int metal_spi_set_baud_rate(struct metal_spi *spi, int baud_rate) { return spi->vtable->set_baud_rate(spi, baud_rate); }
+__inline__ int metal_spi_set_baud_rate(struct metal_spi *spi, int baud_rate) {
+ return spi->vtable->set_baud_rate(spi, baud_rate);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/switch.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/switch.h
index 61f0efe56..695b21ae3 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/switch.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/switch.h
@@ -15,7 +15,7 @@ struct metal_switch;
struct metal_switch_vtable {
int (*switch_exist)(struct metal_switch *sw, char *label);
- struct metal_interrupt* (*interrupt_controller)(struct metal_switch *sw);
+ struct metal_interrupt *(*interrupt_controller)(struct metal_switch *sw);
int (*get_interrupt_id)(struct metal_switch *sw);
};
@@ -29,23 +29,28 @@ struct metal_switch {
/*!
* @brief Get a handle for a switch
* @param label The DeviceTree label for the desired switch
- * @return A handle to the switch, or NULL if none is found for the requested label
+ * @return A handle to the switch, or NULL if none is found for the requested
+ * label
*/
-struct metal_switch* metal_switch_get(char *label);
+struct metal_switch *metal_switch_get(char *label);
/*!
* @brief Get the interrupt controller for a switch
* @param sw The handle for the switch
* @return The interrupt controller handle
*/
-__inline__ struct metal_interrupt*
- metal_switch_interrupt_controller(struct metal_switch *sw) { return sw->vtable->interrupt_controller(sw); }
+__inline__ struct metal_interrupt *
+metal_switch_interrupt_controller(struct metal_switch *sw) {
+ return sw->vtable->interrupt_controller(sw);
+}
/*!
* @brief Get the interrupt id for a switch
* @param sw The handle for the switch
* @return The interrupt ID for the switch
*/
-__inline__ int metal_switch_get_interrupt_id(struct metal_switch *sw) { return sw->vtable->get_interrupt_id(sw); }
+__inline__ int metal_switch_get_interrupt_id(struct metal_switch *sw) {
+ return sw->vtable->get_interrupt_id(sw);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/time.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/time.h
index 5c33b6f1b..a5a880f0d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/time.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/time.h
@@ -5,6 +5,9 @@
#define METAL__TIME_H
#include <time.h>
+#ifndef __SEGGER_LIBC__
+#include <sys/time.h>
+#endif
/*!
* @file time.h
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/timer.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/timer.h
index eeae1f60b..5d5132de5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/timer.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/timer.h
@@ -23,9 +23,10 @@ int metal_timer_get_cyclecount(int hartid, unsigned long long *cyclecount);
* @param timebase The variable to hold the value
* @return 0 upon success
*/
-int metal_timer_get_timebase_frequency(int hartid, unsigned long long *timebase);
+int metal_timer_get_timebase_frequency(int hartid,
+ unsigned long long *timebase);
-/*!
+/*!
* @brief Set the machine timer tick interval in seconds
* @param hartid The hart ID to read the timebase of
* @param second The number of seconds to set the tick interval to
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/tty.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/tty.h
index fe4c000db..5d41783ae 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/tty.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/tty.h
@@ -15,29 +15,12 @@
* Write a character to the default output device, which for most
* targets is the UART serial port.
*
- * putc() does CR/LF mapping.
- * putc_raw() does not.
- *
* @param c The character to write to the terminal
* @return 0 on success, or -1 on failure.
*/
int metal_tty_putc(int c);
/*!
- * @brief Write a raw character to the default output device
- *
- * Write a character to the default output device, which for most
- * targets is the UART serial port.
- *
- * putc() does CR/LF mapping.
- * putc_raw() does not.
- *
- * @param c The character to write to the terminal
- * @return 0 on success, or -1 on failure.
- */
-int metal_tty_putc_raw(int c);
-
-/*!
* @brief Get a byte from the default output device
*
* The default output device, is typically the UART serial port.
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/uart.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/uart.h
index e9e4d0436..856970ac2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/uart.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/uart.h
@@ -21,8 +21,16 @@ struct metal_uart_vtable {
int (*getc)(struct metal_uart *uart, int *c);
int (*get_baud_rate)(struct metal_uart *uart);
int (*set_baud_rate)(struct metal_uart *uart, int baud_rate);
- struct metal_interrupt* (*controller_interrupt)(struct metal_uart *uart);
+ struct metal_interrupt *(*controller_interrupt)(struct metal_uart *uart);
int (*get_interrupt_id)(struct metal_uart *uart);
+ int (*tx_interrupt_enable)(struct metal_uart *uart);
+ int (*tx_interrupt_disable)(struct metal_uart *uart);
+ int (*rx_interrupt_enable)(struct metal_uart *uart);
+ int (*rx_interrupt_disable)(struct metal_uart *uart);
+ int (*set_tx_watermark)(struct metal_uart *uart, size_t length);
+ size_t (*get_tx_watermark)(struct metal_uart *uart);
+ int (*set_rx_watermark)(struct metal_uart *uart, size_t length);
+ size_t (*get_rx_watermark)(struct metal_uart *uart);
};
/*!
@@ -32,16 +40,25 @@ struct metal_uart {
const struct metal_uart_vtable *vtable;
};
+/*! @brief Get a handle for a UART device
+ * @param device_num The index of the desired UART device
+ * @return A handle to the UART device, or NULL if the device does not exist*/
+struct metal_uart *metal_uart_get_device(unsigned int device_num);
+
/*!
* @brief Initialize UART device
-
- * Initialize the UART device described by the UART handle. This function must be called before any
- * other method on the UART can be invoked. It is invalid to initialize a UART more than once.
+
+ * Initialize the UART device described by the UART handle. This function must
+ be called before any
+ * other method on the UART can be invoked. It is invalid to initialize a UART
+ more than once.
*
* @param uart The UART device handle
* @param baud_rate the baud rate to set the UART to
*/
-__inline__ void metal_uart_init(struct metal_uart *uart, int baud_rate) { uart->vtable->init(uart, baud_rate); }
+__inline__ void metal_uart_init(struct metal_uart *uart, int baud_rate) {
+ uart->vtable->init(uart, baud_rate);
+}
/*!
* @brief Output a character over the UART
@@ -49,14 +66,18 @@ __inline__ void metal_uart_init(struct metal_uart *uart, int baud_rate) { uart->
* @param c The character to send over the UART
* @return 0 upon success
*/
-__inline__ int metal_uart_putc(struct metal_uart *uart, int c) { return uart->vtable->putc(uart, c); }
+__inline__ int metal_uart_putc(struct metal_uart *uart, int c) {
+ return uart->vtable->putc(uart, c);
+}
/*!
* @brief Test, determine if tx output is blocked(full/busy)
* @param uart The UART device handle
* @return 0 not blocked
*/
-__inline__ int metal_uart_txready(struct metal_uart *uart) { return uart->vtable->txready(uart); }
+__inline__ int metal_uart_txready(struct metal_uart *uart) {
+ return uart->vtable->txready(uart);
+}
/*!
* @brief Read a character sent over the UART
@@ -67,14 +88,18 @@ __inline__ int metal_uart_txready(struct metal_uart *uart) { return uart->vtable
* If "c == -1" no char was ready.
* If "c != -1" then C == byte value (0x00 to 0xff)
*/
-__inline__ int metal_uart_getc(struct metal_uart *uart, int *c) { return uart->vtable->getc(uart, c); }
+__inline__ int metal_uart_getc(struct metal_uart *uart, int *c) {
+ return uart->vtable->getc(uart, c);
+}
/*!
* @brief Get the baud rate of the UART peripheral
* @param uart The UART device handle
* @return The current baud rate of the UART
*/
-__inline__ int metal_uart_get_baud_rate(struct metal_uart *uart) { return uart->vtable->get_baud_rate(uart); }
+__inline__ int metal_uart_get_baud_rate(struct metal_uart *uart) {
+ return uart->vtable->get_baud_rate(uart);
+}
/*!
* @brief Set the baud rate of the UART peripheral
@@ -82,7 +107,10 @@ __inline__ int metal_uart_get_baud_rate(struct metal_uart *uart) { return uart->
* @param baud_rate The baud rate to configure
* @return the new baud rate of the UART
*/
-__inline__ int metal_uart_set_baud_rate(struct metal_uart *uart, int baud_rate) { return uart->vtable->set_baud_rate(uart, baud_rate); }
+__inline__ int metal_uart_set_baud_rate(struct metal_uart *uart,
+ int baud_rate) {
+ return uart->vtable->set_baud_rate(uart, baud_rate);
+}
/*!
* @brief Get the interrupt controller of the UART peripheral
@@ -94,13 +122,94 @@ __inline__ int metal_uart_set_baud_rate(struct metal_uart *uart, int baud_rate)
* @param uart The UART device handle
* @return The handle for the UART interrupt controller
*/
-__inline__ struct metal_interrupt* metal_uart_interrupt_controller(struct metal_uart *uart) { return uart->vtable->controller_interrupt(uart); }
+__inline__ struct metal_interrupt *
+metal_uart_interrupt_controller(struct metal_uart *uart) {
+ return uart->vtable->controller_interrupt(uart);
+}
/*!
* @brief Get the interrupt ID of the UART controller
* @param uart The UART device handle
* @return The UART interrupt id
*/
-__inline__ int metal_uart_get_interrupt_id(struct metal_uart *uart) { return uart->vtable->get_interrupt_id(uart); }
+__inline__ int metal_uart_get_interrupt_id(struct metal_uart *uart) {
+ return uart->vtable->get_interrupt_id(uart);
+}
+
+/*!
+ * @brief Enable the UART transmit interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_transmit_interrupt_enable(struct metal_uart *uart) {
+ return uart->vtable->tx_interrupt_enable(uart);
+}
+
+/*!
+ * @brief Disable the UART transmit interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_transmit_interrupt_disable(struct metal_uart *uart) {
+ return uart->vtable->tx_interrupt_disable(uart);
+}
+
+/*!
+ * @brief Enable the UART receive interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_receive_interrupt_enable(struct metal_uart *uart) {
+ return uart->vtable->rx_interrupt_enable(uart);
+}
+
+/*!
+ * @brief Disable the UART receive interrupt
+ * @param uart The UART device handle
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_receive_interrupt_disable(struct metal_uart *uart) {
+ return uart->vtable->rx_interrupt_disable(uart);
+}
+
+/*!
+ * @brief Set the transmit watermark level of the UART controller
+ * @param uart The UART device handle
+ * @param level The UART transmit watermark level
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_set_transmit_watermark(struct metal_uart *uart,
+ size_t level) {
+ return uart->vtable->set_tx_watermark(uart, level);
+}
+
+/*!
+ * @brief Get the transmit watermark level of the UART controller
+ * @param uart The UART device handle
+ * @return The UART transmit watermark level
+ */
+__inline__ size_t metal_uart_get_transmit_watermark(struct metal_uart *uart) {
+ return uart->vtable->get_tx_watermark(uart);
+}
+
+/*!
+ * @brief Set the receive watermark level of the UART controller
+ * @param uart The UART device handle
+ * @param level The UART transmit watermark level
+ * @return 0 upon success
+ */
+__inline__ int metal_uart_set_receive_watermark(struct metal_uart *uart,
+ size_t level) {
+ return uart->vtable->set_rx_watermark(uart, level);
+}
+
+/*!
+ * @brief Get the receive watermark level of the UART controller
+ * @param uart The UART device handle
+ * @return The UART transmit watermark level
+ */
+__inline__ size_t metal_uart_get_receive_watermark(struct metal_uart *uart) {
+ return uart->vtable->get_rx_watermark(uart);
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/watchdog.h b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/watchdog.h
index b5ff48697..2f84d3b49 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/watchdog.h
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/metal/watchdog.h
@@ -18,49 +18,54 @@ struct metal_watchdog;
* @brief List of watchdog timer count behaviors
*/
enum metal_watchdog_run_option {
- METAL_WATCHDOG_STOP = 0, /*!< Stop the watchdog */
- METAL_WATCHDOG_RUN_ALWAYS, /*!< Run the watchdog continuously, even during sleep */
- METAL_WATCHDOG_RUN_AWAKE, /*!< Run the watchdog only while the CPU is awake */
+ METAL_WATCHDOG_STOP = 0, /*!< Stop the watchdog */
+ METAL_WATCHDOG_RUN_ALWAYS, /*!< Run the watchdog continuously, even during
+ sleep */
+ METAL_WATCHDOG_RUN_AWAKE, /*!< Run the watchdog only while the CPU is awake
+ */
};
/*!
* @brief List of behaviors when a watchdog triggers
*/
enum metal_watchdog_result {
- METAL_WATCHDOG_NO_RESULT = 0, /*!< When the watchdog triggers, do nothing */
- METAL_WATCHDOG_INTERRUPT, /*!< When the watchdog triggers, fire an interrupt */
- METAL_WATCHDOG_FULL_RESET, /*!< When the watchdog triggers, cause a full system reset */
+ METAL_WATCHDOG_NO_RESULT = 0, /*!< When the watchdog triggers, do nothing */
+ METAL_WATCHDOG_INTERRUPT, /*!< When the watchdog triggers, fire an interrupt
+ */
+ METAL_WATCHDOG_FULL_RESET, /*!< When the watchdog triggers, cause a full
+ system reset */
};
-
struct metal_watchdog_vtable {
- int (*feed)(const struct metal_watchdog *const wdog);
- long int (*get_rate)(const struct metal_watchdog *const wdog);
- long int (*set_rate)(const struct metal_watchdog *const wdog, const long int rate);
- long int (*get_timeout)(const struct metal_watchdog *const wdog);
- long int (*set_timeout)(const struct metal_watchdog *const wdog, const long int timeout);
- int (*set_result)(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_result result);
- int (*run)(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_run_option option);
- struct metal_interrupt *(*get_interrupt)(const struct metal_watchdog *const wdog);
- int (*get_interrupt_id)(const struct metal_watchdog *const wdog);
- int (*clear_interrupt)(const struct metal_watchdog *const wdog);
+ int (*feed)(const struct metal_watchdog *const wdog);
+ long int (*get_rate)(const struct metal_watchdog *const wdog);
+ long int (*set_rate)(const struct metal_watchdog *const wdog,
+ const long int rate);
+ long int (*get_timeout)(const struct metal_watchdog *const wdog);
+ long int (*set_timeout)(const struct metal_watchdog *const wdog,
+ const long int timeout);
+ int (*set_result)(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_result result);
+ int (*run)(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_run_option option);
+ struct metal_interrupt *(*get_interrupt)(
+ const struct metal_watchdog *const wdog);
+ int (*get_interrupt_id)(const struct metal_watchdog *const wdog);
+ int (*clear_interrupt)(const struct metal_watchdog *const wdog);
};
/*!
* @brief Handle for a Watchdog Timer
*/
struct metal_watchdog {
- const struct metal_watchdog_vtable *vtable;
+ const struct metal_watchdog_vtable *vtable;
};
/*!
* @brief Feed the watchdog timer
*/
-inline int metal_watchdog_feed(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->feed(wdog);
+inline int metal_watchdog_feed(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->feed(wdog);
}
/*!
@@ -68,9 +73,9 @@ inline int metal_watchdog_feed(const struct metal_watchdog *const wdog)
*
* @return the rate of the watchdog timer
*/
-inline long int metal_watchdog_get_rate(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->get_rate(wdog);
+inline long int
+metal_watchdog_get_rate(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_rate(wdog);
}
/*!
@@ -80,9 +85,9 @@ inline long int metal_watchdog_get_rate(const struct metal_watchdog *const wdog)
*
* @return the new rate of the watchdog timer
*/
-inline long int metal_watchdog_set_rate(const struct metal_watchdog *const wdog, const long int rate)
-{
- return wdog->vtable->set_rate(wdog, rate);
+inline long int metal_watchdog_set_rate(const struct metal_watchdog *const wdog,
+ const long int rate) {
+ return wdog->vtable->set_rate(wdog, rate);
}
/*!
@@ -90,21 +95,23 @@ inline long int metal_watchdog_set_rate(const struct metal_watchdog *const wdog,
*
* @return the watchdog timeout value
*/
-inline long int metal_watchdog_get_timeout(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->get_timeout(wdog);
+inline long int
+metal_watchdog_get_timeout(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_timeout(wdog);
}
/*!
* @brief Set the timeout of the watchdog timer
*
- * The set rate will be the minimimum of the requested and maximum supported rates.
+ * The set rate will be the minimimum of the requested and maximum supported
+ * rates.
*
* @return the new watchdog timeout value
*/
-inline long int metal_watchdog_set_timeout(const struct metal_watchdog *const wdog, const long int timeout)
-{
- return wdog->vtable->set_timeout(wdog, timeout);
+inline long int
+metal_watchdog_set_timeout(const struct metal_watchdog *const wdog,
+ const long int timeout) {
+ return wdog->vtable->set_timeout(wdog, timeout);
}
/*!
@@ -113,9 +120,8 @@ inline long int metal_watchdog_set_timeout(const struct metal_watchdog *const wd
* @return 0 if the requested result behavior is supported
*/
inline int metal_watchdog_set_result(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_result result)
-{
- return wdog->vtable->set_result(wdog, result);
+ const enum metal_watchdog_result result) {
+ return wdog->vtable->set_result(wdog, result);
}
/*!
@@ -126,33 +132,32 @@ inline int metal_watchdog_set_result(const struct metal_watchdog *const wdog,
* @return 0 if the watchdog was successfully started/stopped
*/
inline int metal_watchdog_run(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_run_option option)
-{
- return wdog->vtable->run(wdog, option);
+ const enum metal_watchdog_run_option option) {
+ return wdog->vtable->run(wdog, option);
}
/*!
* @brief Get the interrupt controller for the watchdog interrupt
*/
-inline struct metal_interrupt *metal_watchdog_get_interrupt(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->get_interrupt(wdog);
+inline struct metal_interrupt *
+metal_watchdog_get_interrupt(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_interrupt(wdog);
}
/*!
* @Brief Get the interrupt id for the watchdog interrupt
*/
-inline int metal_watchdog_get_interrupt_id(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->get_interrupt_id(wdog);
+inline int
+metal_watchdog_get_interrupt_id(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->get_interrupt_id(wdog);
}
/*!
* @brief Clear the watchdog interrupt
*/
-inline int metal_watchdog_clear_interrupt(const struct metal_watchdog *const wdog)
-{
- return wdog->vtable->clear_interrupt(wdog);
+inline int
+metal_watchdog_clear_interrupt(const struct metal_watchdog *const wdog) {
+ return wdog->vtable->clear_interrupt(wdog);
}
/*!
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/missing b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/missing
new file mode 100755
index 000000000..f62bbae30
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/missing
@@ -0,0 +1,215 @@
+#! /bin/sh
+# Common wrapper for a few potentially missing GNU programs.
+
+scriptversion=2013-10-28.13; # UTC
+
+# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
+
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+# As a special exception to the GNU General Public License, if you
+# distribute this file as part of a program that contains a
+# configuration script generated by Autoconf, you may include it under
+# the same distribution terms that you use for the rest of that program.
+
+if test $# -eq 0; then
+ echo 1>&2 "Try '$0 --help' for more information"
+ exit 1
+fi
+
+case $1 in
+
+ --is-lightweight)
+ # Used by our autoconf macros to check whether the available missing
+ # script is modern enough.
+ exit 0
+ ;;
+
+ --run)
+ # Back-compat with the calling convention used by older automake.
+ shift
+ ;;
+
+ -h|--h|--he|--hel|--help)
+ echo "\
+$0 [OPTION]... PROGRAM [ARGUMENT]...
+
+Run 'PROGRAM [ARGUMENT]...', returning a proper advice when this fails due
+to PROGRAM being missing or too old.
+
+Options:
+ -h, --help display this help and exit
+ -v, --version output version information and exit
+
+Supported PROGRAM values:
+ aclocal autoconf autoheader autom4te automake makeinfo
+ bison yacc flex lex help2man
+
+Version suffixes to PROGRAM as well as the prefixes 'gnu-', 'gnu', and
+'g' are ignored when checking the name.
+
+Send bug reports to <bug-automake@gnu.org>."
+ exit $?
+ ;;
+
+ -v|--v|--ve|--ver|--vers|--versi|--versio|--version)
+ echo "missing $scriptversion (GNU Automake)"
+ exit $?
+ ;;
+
+ -*)
+ echo 1>&2 "$0: unknown '$1' option"
+ echo 1>&2 "Try '$0 --help' for more information"
+ exit 1
+ ;;
+
+esac
+
+# Run the given program, remember its exit status.
+"$@"; st=$?
+
+# If it succeeded, we are done.
+test $st -eq 0 && exit 0
+
+# Also exit now if we it failed (or wasn't found), and '--version' was
+# passed; such an option is passed most likely to detect whether the
+# program is present and works.
+case $2 in --version|--help) exit $st;; esac
+
+# Exit code 63 means version mismatch. This often happens when the user
+# tries to use an ancient version of a tool on a file that requires a
+# minimum version.
+if test $st -eq 63; then
+ msg="probably too old"
+elif test $st -eq 127; then
+ # Program was missing.
+ msg="missing on your system"
+else
+ # Program was found and executed, but failed. Give up.
+ exit $st
+fi
+
+perl_URL=http://www.perl.org/
+flex_URL=http://flex.sourceforge.net/
+gnu_software_URL=http://www.gnu.org/software
+
+program_details ()
+{
+ case $1 in
+ aclocal|automake)
+ echo "The '$1' program is part of the GNU Automake package:"
+ echo "<$gnu_software_URL/automake>"
+ echo "It also requires GNU Autoconf, GNU m4 and Perl in order to run:"
+ echo "<$gnu_software_URL/autoconf>"
+ echo "<$gnu_software_URL/m4/>"
+ echo "<$perl_URL>"
+ ;;
+ autoconf|autom4te|autoheader)
+ echo "The '$1' program is part of the GNU Autoconf package:"
+ echo "<$gnu_software_URL/autoconf/>"
+ echo "It also requires GNU m4 and Perl in order to run:"
+ echo "<$gnu_software_URL/m4/>"
+ echo "<$perl_URL>"
+ ;;
+ esac
+}
+
+give_advice ()
+{
+ # Normalize program name to check for.
+ normalized_program=`echo "$1" | sed '
+ s/^gnu-//; t
+ s/^gnu//; t
+ s/^g//; t'`
+
+ printf '%s\n' "'$1' is $msg."
+
+ configure_deps="'configure.ac' or m4 files included by 'configure.ac'"
+ case $normalized_program in
+ autoconf*)
+ echo "You should only need it if you modified 'configure.ac',"
+ echo "or m4 files included by it."
+ program_details 'autoconf'
+ ;;
+ autoheader*)
+ echo "You should only need it if you modified 'acconfig.h' or"
+ echo "$configure_deps."
+ program_details 'autoheader'
+ ;;
+ automake*)
+ echo "You should only need it if you modified 'Makefile.am' or"
+ echo "$configure_deps."
+ program_details 'automake'
+ ;;
+ aclocal*)
+ echo "You should only need it if you modified 'acinclude.m4' or"
+ echo "$configure_deps."
+ program_details 'aclocal'
+ ;;
+ autom4te*)
+ echo "You might have modified some maintainer files that require"
+ echo "the 'autom4te' program to be rebuilt."
+ program_details 'autom4te'
+ ;;
+ bison*|yacc*)
+ echo "You should only need it if you modified a '.y' file."
+ echo "You may want to install the GNU Bison package:"
+ echo "<$gnu_software_URL/bison/>"
+ ;;
+ lex*|flex*)
+ echo "You should only need it if you modified a '.l' file."
+ echo "You may want to install the Fast Lexical Analyzer package:"
+ echo "<$flex_URL>"
+ ;;
+ help2man*)
+ echo "You should only need it if you modified a dependency" \
+ "of a man page."
+ echo "You may want to install the GNU Help2man package:"
+ echo "<$gnu_software_URL/help2man/>"
+ ;;
+ makeinfo*)
+ echo "You should only need it if you modified a '.texi' file, or"
+ echo "any other file indirectly affecting the aspect of the manual."
+ echo "You might want to install the Texinfo package:"
+ echo "<$gnu_software_URL/texinfo/>"
+ echo "The spurious makeinfo call might also be the consequence of"
+ echo "using a buggy 'make' (AIX, DU, IRIX), in which case you might"
+ echo "want to install GNU make:"
+ echo "<$gnu_software_URL/make/>"
+ ;;
+ *)
+ echo "You might have modified some files without having the proper"
+ echo "tools for further handling them. Check the 'README' file, it"
+ echo "often tells you about the needed prerequisites for installing"
+ echo "this package. You may also peek at any GNU archive site, in"
+ echo "case some other package contains this missing '$1' program."
+ ;;
+ esac
+}
+
+give_advice "$1" | sed -e '1s/^/WARNING: /' \
+ -e '2,$s/^/ /' >&2
+
+# Propagate the correct exit status (expected to be 127 for a program
+# not found, 63 for a program that failed due to version mismatch).
+exit $st
+
+# Local variables:
+# eval: (add-hook 'write-file-hooks 'time-stamp)
+# time-stamp-start: "scriptversion="
+# time-stamp-format: "%:y-%02m-%02d.%02H"
+# time-stamp-time-zone: "UTC"
+# time-stamp-end: "; # UTC"
+# End:
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/check-format b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/check-format
new file mode 100755
index 000000000..1447fe43c
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/check-format
@@ -0,0 +1,19 @@
+#!/bin/sh
+
+CLANG_FORMAT=clang-format-6.0
+
+TOP_LEVEL=$(git rev-parse --show-toplevel)
+
+# Run clang-format in-place on all *.c and *.h files in the repository
+cd $TOP_LEVEL && $CLANG_FORMAT -i $(git ls-tree -r HEAD --name-only | grep -E "^\S+\.[ch]*$")
+
+DIFF=$(git diff)
+
+if [ "${DIFF}" != "" ] ; then
+ echo "Formatting errors found! Please run ./scripts/format or apply the"
+ echo "following diff to fix them!"
+ echo ""
+ echo "${DIFF}"
+ exit 1
+fi
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/format b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/format
new file mode 100755
index 000000000..a07c363da
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/format
@@ -0,0 +1,8 @@
+#!/bin/sh
+
+CLANG_FORMAT=clang-format-6.0
+
+TOP_LEVEL=$(git rev-parse --show-toplevel)
+
+# Run clang-format in-place on all *.c and *.h files in the repository
+cd $TOP_LEVEL && $CLANG_FORMAT -i $(git ls-tree -r HEAD --name-only | grep -E "^\S+\.[ch]$")
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/git-version b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/git-version
new file mode 100755
index 000000000..de0529b9d
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/scripts/git-version
@@ -0,0 +1,21 @@
+#!/bin/bash
+
+version='v0.1.2'
+
+if test -d .git
+then
+ gv=`git describe`
+ if [[ "$?" == "0" ]]
+ then
+ if [[ "$(echo "${gv}" | cut -d'-' -f1)" != "$version" ]]
+ then
+ echo "$0 has mismatched version" >&2
+ echo "${gv}-ERROR"
+ exit 1
+ fi
+
+ version="$(echo ${gv} | cut -c2-)"
+ fi
+fi
+
+echo "${version}"
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/atomic.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/atomic.c
new file mode 100644
index 000000000..326568e37
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/atomic.c
@@ -0,0 +1,19 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/atomic.h>
+
+extern __inline__ int32_t metal_atomic_available(void);
+extern __inline__ int32_t metal_atomic_add(metal_atomic_t *a,
+ int32_t increment);
+extern __inline__ int32_t metal_atomic_and(metal_atomic_t *a, int32_t mask);
+extern __inline__ int32_t metal_atomic_or(metal_atomic_t *a, int32_t mask);
+extern __inline__ int32_t metal_atomic_swap(metal_atomic_t *a,
+ int32_t new_value);
+extern __inline__ int32_t metal_atomic_xor(metal_atomic_t *a, int32_t mask);
+extern __inline__ int32_t metal_atomic_max(metal_atomic_t *a, int32_t compare);
+extern __inline__ uint32_t metal_atomic_max_u(metal_atomic_t *a,
+ uint32_t compare);
+extern __inline__ int32_t metal_atomic_min(metal_atomic_t *a, int32_t compare);
+extern __inline__ uint32_t metal_atomic_min_u(metal_atomic_t *a,
+ uint32_t compare);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/button.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/button.c
index efd645334..5831945c2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/button.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/button.c
@@ -4,8 +4,7 @@
#include <metal/button.h>
#include <metal/machine.h>
-struct metal_button* metal_button_get (char *label)
-{
+struct metal_button *metal_button_get(char *label) {
int i;
struct metal_button *button;
@@ -14,7 +13,7 @@ struct metal_button* metal_button_get (char *label)
}
for (i = 0; i < __METAL_DT_MAX_BUTTONS; i++) {
- button = (struct metal_button*)__metal_button_table[i];
+ button = (struct metal_button *)__metal_button_table[i];
if (button->vtable->button_exist(button, label)) {
return button;
}
@@ -22,6 +21,7 @@ struct metal_button* metal_button_get (char *label)
return NULL;
}
-extern __inline__ struct metal_interrupt*
- metal_button_interrupt_controller(struct metal_button *button);
-extern __inline__ int metal_button_get_interrupt_id(struct metal_button *button);
+extern __inline__ struct metal_interrupt *
+metal_button_interrupt_controller(struct metal_button *button);
+extern __inline__ int
+metal_button_get_interrupt_id(struct metal_button *button);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cache.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cache.c
index 024ba52ad..09c270e47 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cache.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cache.c
@@ -1,19 +1,51 @@
-/* Copyright 2018 SiFive, Inc */
+/* Copyright 2020 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
#include <metal/cache.h>
#include <metal/machine.h>
+/* Macros to generate driver prefix string */
+#ifdef METAL_CACHE_DRIVER_PREFIX
+#define METAL_FUNC_STR(a, b) a##_##b
+#define METAL_FUNC_STR_(a, b) METAL_FUNC_STR(a, b)
+#define METAL_FUNC(x) METAL_FUNC_STR_(METAL_CACHE_DRIVER_PREFIX, x)
+#endif
+
extern __inline__ void metal_cache_init(struct metal_cache *cache, int ways);
extern __inline__ int metal_cache_get_enabled_ways(struct metal_cache *cache);
-extern __inline__ int metal_cache_set_enabled_ways(struct metal_cache *cache, int ways);
+extern __inline__ int metal_cache_set_enabled_ways(struct metal_cache *cache,
+ int ways);
+
+int metal_l2cache_init(void) {
+#ifdef METAL_CACHE_DRIVER_PREFIX
+ return METAL_FUNC(init)();
+#else
+ return -1;
+#endif
+}
+
+int metal_l2cache_get_enabled_ways(void) {
+#ifdef METAL_CACHE_DRIVER_PREFIX
+ return METAL_FUNC(get_enabled_ways)();
+#else
+ return -1;
+#endif
+}
+
+int metal_l2cache_set_enabled_ways(int ways) {
+#ifdef METAL_CACHE_DRIVER_PREFIX
+ return METAL_FUNC(set_enabled_ways)(ways);
+#else
+ return -1;
+#endif
+}
int metal_dcache_l1_available(int hartid) {
switch (hartid) {
case 0:
#ifdef __METAL_CPU_0_DCACHE_HANDLE
return __METAL_CPU_0_DCACHE_HANDLE;
-#endif
+#endif
break;
case 1:
#ifdef __METAL_CPU_1_DCACHE_HANDLE
@@ -112,76 +144,78 @@ int metal_icache_l1_available(int hartid) {
/*!
* @brief CFlush.D.L1 instruction is a custom instruction implemented as a
- * state machine in L1 Data Cache (D$) with funct3=0, (for core with data caches)
- * It is an I type: .insn i opcode, func3, rd, rs1, simm12(signed immediate 12bs)
- * 31 28 27 24 23 20 19 16 15 12 11 8 7 4 3 0
+ * state machine in L1 Data Cache (D$) with funct3=0, (for core with data
+ * caches) It is an I type: .insn i opcode, func3, rd, rs1, simm12(signed
+ * immediate 12bs)
+ * 31 28 27 24 23 20 19 16 15 12 11 8 7 4 3 0
* |--------|--------|--------|--------|--------|--------|--------|--------|
* +-------------+------------+----------+------+--------+-----------------+
* |sign immediate12b (simm12)| rs1 | func3| rd | opcode |
* |-1-1-1-1 -1-1-0-0 -0-0-0-0|-x-x-x-x-x|0-0-0-|-0-0-0-0|-0-1-1-1 -0-0-1-1|
* +--------------------------+----------+------+--------+-----------------+
- * 31 -0x40 20 15 0 12 x0 7 0x73 0
+ * 31 -0x40 20 15 0 12 x0 7 0x73 0
* +--------+--------+--------+----------+------+--------+--------+--------+
* where,
- * rs1 = 0x0, CFLUSH.D.L1 writes back and invalidates all lines in the L1 D$
+ * rs1 = x0, CFLUSH.D.L1 writes back and invalidates all lines in the L1 D$
* rs1 != x0, CFLUSH.D.L1 writes back and invalidates the L1 D$ line containing
* the virtual address in integer register rs1.
*/
-void metal_dcache_l1_flush(int hartid, uintptr_t address)
-{
- if (metal_dcache_l1_available(hartid)) {
- // Using ‘.insn’ pseudo directive: '.insn i opcode, func3, rd, rs1, simm12'
- __asm__ __volatile__ (".insn i 0x73, 0, x0, %0, -0x40" : : "r" (address));
- __asm__ __volatile__ ("fence.i"); // FENCE
+void metal_dcache_l1_flush(int hartid, uintptr_t address) {
+ if (metal_dcache_l1_available(hartid)) {
+ if (address) {
+ uintptr_t ms1 = 0, ms2 = 0;
+ __asm__ __volatile__("csrr %0, mtvec \n\t"
+ "la %1, 1f \n\t"
+ "csrw mtvec, %1 \n\t"
+ ".insn i 0x73, 0, x0, %2, -0x40 \n\t"
+ ".align 2\n\t"
+ "1: \n\t"
+ "csrw mtvec, %0 \n\t"
+ : "+r"(ms1), "+r"(ms2)
+ : "r"(address));
+ // Using ‘.insn’ pseudo directive:
+ // '.insn i opcode, func3, rd, rs1, simm12'
+ } else {
+ __asm__ __volatile__(".word 0xfc000073" : : : "memory");
+ }
}
}
/*!
* @brief CDiscard.D.L1 instruction is a custom instruction implemented as a
- * state machine in L1 Data Cache (D$) with funct3=0, (for core with data caches)
- * It is an I type: .insn i opcode, func3, rd, rs1, simm12(signed immediate 12bs)
- * 31 28 27 24 23 20 19 16 15 12 11 8 7 4 3 0
+ * state machine in L1 Data Cache (D$) with funct3=0, (for core with data
+ * caches) It is an I type: .insn i opcode, func3, rd, rs1, simm12(signed
+ * immediate 12bs)
+ * 31 28 27 24 23 20 19 16 15 12 11 8 7 4 3 0
* |--------|--------|--------|--------|--------|--------|--------|--------|
* +-------------+------------+----------+------+--------+-----------------+
* |sign immediate12b (simm12)| rs1 | func3| rd | opcode |
- * |-1-1-1-1 -1-1-0-0 -0-0-0-0|-x-x-x-x-x|0-0-0-|-0-0-0-0|-0-1-1-1 -0-0-1-1|
+ * |-1-1-1-1 -1-1-0-0 -0-0-1-0|-x-x-x-x-x|0-0-0-|-0-0-0-0|-0-1-1-1 -0-0-1-1|
* +--------------------------+----------+------+--------+-----------------+
- * 31 -0x3E 20 15 0 12 x0 7 0x73 0
+ * 31 -0x3E 20 15 0 12 x0 7 0x73 0
* +--------+--------+--------+----------+------+--------+--------+--------+
* where,
- * rs1 = 0x0, CDISCARD.D.L1 invalidates all lines in the L1 D$ with no writes back.
- * rs1 != x0, CDISCARD.D.L1 invalidates the L1 D$ line containing the virtual address
- * in integer register rs1, with no writes back.
- */
-void metal_dcache_l1_discard(int hartid, uintptr_t address)
-{
- if (metal_dcache_l1_available(hartid)) {
- // Using ‘.insn’ pseudo directive: '.insn i opcode, func3, rd, rs1, simm12'
- __asm__ __volatile__ (".insn i 0x73, 0, x0, %0, -0x3E" : : "r" (address));
- __asm__ __volatile__ ("fence.i"); // FENCE
- }
-}
-
-/*!
- * @brief CFlush.I.L1 instruction is a custom instruction implemented as a state
- * machine in L1 Instruction Cache (I$) with funct3=0, (for core with data caches)
- * It is an I type: .insn i opcode, func3, rd, rs1, simm12(signed immediate 12bs)
- * 31 28 27 24 23 20 19 16 15 12 11 8 7 4 3 0
- * |--------|--------|--------|--------|--------|--------|--------|--------|
- * +-------------+------------+----------+------+--------+-----------------+
- * |sign immediate12b (simm12)| rs1 | func3| rd | opcode |
- * |-1-1-1-1 -1-1-0-0 -0-0-0-0|-0-0-0-0-0|0-0-0-|-0-0-0-0|-0-1-1-1 -0-0-1-1|
- * +--------------------------+----------+------+--------+-----------------+
- * 31 -0x3F 20 15 0 12 x0 7 0x73 0
- * +--------+--------+--------+----------+------+--------+--------+--------+
- * CFLUSH.I.L1 invalidates all lines in the L1 I$.
+ * rs1 = x0, CDISCARD.D.L1 invalidates all lines in the L1 D$ with no writes
+ * back. rs1 != x0, CDISCARD.D.L1 invalidates the L1 D$ line containing the
+ * virtual address in integer register rs1, with no writes back.
*/
-void metal_icache_l1_flush(int hartid)
-{
- if (metal_icache_l1_available(hartid)) {
- // Using ‘.insn’ pseudo directive: '.insn i opcode, func3, rd, rs1, simm12'
- __asm__ __volatile__ (".insn i 0x73, 0, x0, x0, -0x3F" : : );
- __asm__ __volatile__ ("fence.i"); // FENCE
+void metal_dcache_l1_discard(int hartid, uintptr_t address) {
+ if (metal_dcache_l1_available(hartid)) {
+ if (address) {
+ uintptr_t ms1 = 0, ms2 = 0;
+ __asm__ __volatile__("csrr %0, mtvec \n\t"
+ "la %1, 1f \n\t"
+ "csrw mtvec, %1 \n\t"
+ ".insn i 0x73, 0, x0, %2, -0x3E \n\t"
+ ".align 2\n\t"
+ "1: \n\t"
+ "csrw mtvec, %0 \n\t"
+ : "+r"(ms1), "+r"(ms2)
+ : "r"(address));
+ // Using ‘.insn’ pseudo directive:
+ // '.insn i opcode, func3, rd, rs1, simm12'
+ } else {
+ __asm__ __volatile__(".word 0xfc200073" : : : "memory");
+ }
}
}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/clock.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/clock.c
index cc3f4dcf3..a2a11231c 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/clock.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/clock.c
@@ -3,10 +3,18 @@
#include <metal/clock.h>
-extern __inline__ void _metal_clock_call_all_callbacks(const metal_clock_callback *const list);
-extern __inline__ metal_clock_callback *_metal_clock_append_to_callbacks(metal_clock_callback *list, metal_clock_callback *const cb);
+extern __inline__ void
+_metal_clock_call_all_callbacks(const metal_clock_callback *const list);
+extern __inline__ metal_clock_callback *
+_metal_clock_append_to_callbacks(metal_clock_callback *list,
+ metal_clock_callback *const cb);
extern __inline__ long metal_clock_get_rate_hz(const struct metal_clock *clk);
-extern __inline__ long metal_clock_set_rate_hz(struct metal_clock *clk, long hz);
-extern __inline__ void metal_clock_register_post_rate_change_callback(struct metal_clock *clk, metal_clock_callback *cb);
-extern __inline__ void metal_clock_register_pre_rate_change_callback(struct metal_clock *clk, metal_clock_callback *cb);
+extern __inline__ long metal_clock_set_rate_hz(struct metal_clock *clk,
+ long hz);
+extern __inline__ void
+metal_clock_register_post_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb);
+extern __inline__ void
+metal_clock_register_pre_rate_change_callback(struct metal_clock *clk,
+ metal_clock_callback *cb);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cpu.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cpu.c
index 25fda5de7..8e28c8979 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cpu.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/cpu.c
@@ -4,56 +4,66 @@
#include <metal/cpu.h>
#include <metal/machine.h>
-struct metal_cpu* metal_cpu_get(unsigned int hartid)
-{
+struct metal_cpu *metal_cpu_get(unsigned int hartid) {
if (hartid < __METAL_DT_MAX_HARTS) {
return (struct metal_cpu *)__metal_cpu_table[hartid];
- }
+ }
return NULL;
}
-int metal_cpu_get_current_hartid()
-{
+int metal_cpu_get_current_hartid() {
#ifdef __riscv
int mhartid;
- __asm__ volatile("csrr %0, mhartid" : "=r" (mhartid));
+ __asm__ volatile("csrr %0, mhartid" : "=r"(mhartid));
return mhartid;
#endif
}
-int metal_cpu_get_num_harts()
-{
- return __METAL_DT_MAX_HARTS;
-}
+int metal_cpu_get_num_harts() { return __METAL_DT_MAX_HARTS; }
extern __inline__ unsigned long long metal_cpu_get_timer(struct metal_cpu *cpu);
-extern __inline__ unsigned long long metal_cpu_get_timebase(struct metal_cpu *cpu);
+extern __inline__ unsigned long long
+metal_cpu_get_timebase(struct metal_cpu *cpu);
extern __inline__ unsigned long long metal_cpu_get_mtime(struct metal_cpu *cpu);
-extern __inline__ int metal_cpu_set_mtimecmp(struct metal_cpu *cpu, unsigned long long time);
+extern __inline__ int metal_cpu_set_mtimecmp(struct metal_cpu *cpu,
+ unsigned long long time);
-extern __inline__ struct metal_interrupt* metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu);
+extern __inline__ struct metal_interrupt *
+metal_cpu_timer_interrupt_controller(struct metal_cpu *cpu);
extern __inline__ int metal_cpu_timer_get_interrupt_id(struct metal_cpu *cpu);
-extern __inline__ struct metal_interrupt* metal_cpu_software_interrupt_controller(struct metal_cpu *cpu);
+extern __inline__ struct metal_interrupt *
+metal_cpu_software_interrupt_controller(struct metal_cpu *cpu);
-extern __inline__ int metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu);
+extern __inline__ int
+metal_cpu_software_get_interrupt_id(struct metal_cpu *cpu);
-extern __inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu, int hartid);
+extern __inline__ int metal_cpu_software_set_ipi(struct metal_cpu *cpu,
+ int hartid);
-extern __inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu, int hartid);
+extern __inline__ int metal_cpu_software_clear_ipi(struct metal_cpu *cpu,
+ int hartid);
extern __inline__ int metal_cpu_get_msip(struct metal_cpu *cpu, int hartid);
-extern __inline__ struct metal_interrupt* metal_cpu_interrupt_controller(struct metal_cpu *cpu);
+extern __inline__ struct metal_interrupt *
+metal_cpu_interrupt_controller(struct metal_cpu *cpu);
-extern __inline__ int metal_cpu_exception_register(struct metal_cpu *cpu, int ecode, metal_exception_handler_t handler);
+extern __inline__ int
+metal_cpu_exception_register(struct metal_cpu *cpu, int ecode,
+ metal_exception_handler_t handler);
-extern __inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t epc);
+extern __inline__ int metal_cpu_get_instruction_length(struct metal_cpu *cpu,
+ uintptr_t epc);
extern __inline__ uintptr_t metal_cpu_get_exception_pc(struct metal_cpu *cpu);
-extern __inline__ int metal_cpu_set_exception_pc(struct metal_cpu *cpu, uintptr_t epc);
+extern __inline__ int metal_cpu_set_exception_pc(struct metal_cpu *cpu,
+ uintptr_t epc);
+
+extern __inline__ struct metal_buserror *
+metal_cpu_get_buserror(struct metal_cpu *cpu);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-clock.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-clock.c
index 92c61d023..395197071 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-clock.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-clock.c
@@ -6,16 +6,15 @@
#ifdef METAL_FIXED_CLOCK
#include <metal/drivers/fixed-clock.h>
-#include <stddef.h>
#include <metal/machine.h>
+#include <stddef.h>
-long __metal_driver_fixed_clock_get_rate_hz(const struct metal_clock *gclk)
-{
+long __metal_driver_fixed_clock_get_rate_hz(const struct metal_clock *gclk) {
return __metal_driver_fixed_clock_rate(gclk);
}
-long __metal_driver_fixed_clock_set_rate_hz(struct metal_clock *gclk, long target_hz)
-{
+long __metal_driver_fixed_clock_set_rate_hz(struct metal_clock *gclk,
+ long target_hz) {
return __metal_driver_fixed_clock_get_rate_hz(gclk);
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-factor-clock.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-factor-clock.c
index 57d83af87..4e8223bf5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-factor-clock.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/fixed-factor-clock.c
@@ -6,22 +6,23 @@
#ifdef METAL_FIXED_FACTOR_CLOCK
#include <metal/drivers/fixed-factor-clock.h>
-#include <stddef.h>
#include <metal/machine.h>
+#include <stddef.h>
-long __metal_driver_fixed_factor_clock_get_rate_hz(const struct metal_clock *gclk)
-{
+long __metal_driver_fixed_factor_clock_get_rate_hz(
+ const struct metal_clock *gclk) {
struct metal_clock *parent = __metal_driver_fixed_factor_clock_parent(gclk);
long parent_rate = 1;
- if(parent) {
+ if (parent) {
parent_rate = parent->vtable->get_rate_hz(parent);
}
- return __metal_driver_fixed_factor_clock_mult(gclk) * parent_rate / __metal_driver_fixed_factor_clock_div(gclk);
+ return __metal_driver_fixed_factor_clock_mult(gclk) * parent_rate /
+ __metal_driver_fixed_factor_clock_div(gclk);
}
-long __metal_driver_fixed_factor_clock_set_rate_hz(struct metal_clock *gclk, long target_hz)
-{
+long __metal_driver_fixed_factor_clock_set_rate_hz(struct metal_clock *gclk,
+ long target_hz) {
return __metal_driver_fixed_factor_clock_get_rate_hz(gclk);
}
@@ -31,4 +32,4 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_fixed_factor_clock) = {
};
#endif /* METAL_FIXED_FACTOR_CLOCK */
-typedef int no_empty_translation_units;
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/inline.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/inline.c
index 50c0c5c21..a87c056ba 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/inline.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/inline.c
@@ -2,4 +2,3 @@
/* SPDX-License-Identifier: Apache-2.0 */
#include <metal/machine/inline.h>
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_clint0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_clint0.c
index d0488b317..3dd7c0eb1 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_clint0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_clint0.c
@@ -5,93 +5,106 @@
#ifdef METAL_RISCV_CLINT0
-#include <metal/io.h>
#include <metal/cpu.h>
#include <metal/drivers/riscv_clint0.h>
+#include <metal/io.h>
#include <metal/machine.h>
-unsigned long long __metal_clint0_mtime_get (struct __metal_driver_riscv_clint0 *clint)
-{
+unsigned long long
+__metal_clint0_mtime_get(struct __metal_driver_riscv_clint0 *clint) {
__metal_io_u32 lo, hi;
- unsigned long control_base = __metal_driver_sifive_clint0_control_base(&clint->controller);
+ unsigned long control_base =
+ __metal_driver_sifive_clint0_control_base(&clint->controller);
/* Guard against rollover when reading */
do {
- hi = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_RISCV_CLINT0_MTIME + 4));
- lo = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_RISCV_CLINT0_MTIME));
- } while (__METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_RISCV_CLINT0_MTIME + 4)) != hi);
+ hi = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_CLINT0_MTIME + 4));
+ lo = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_CLINT0_MTIME));
+ } while (__METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
+ METAL_RISCV_CLINT0_MTIME +
+ 4)) != hi);
return (((unsigned long long)hi) << 32) | lo;
}
int __metal_driver_riscv_clint0_mtimecmp_set(struct metal_interrupt *controller,
int hartid,
- unsigned long long time)
-{
+ unsigned long long time) {
struct __metal_driver_riscv_clint0 *clint =
- (struct __metal_driver_riscv_clint0 *)(controller);
- unsigned long control_base = __metal_driver_sifive_clint0_control_base(&clint->controller);
+ (struct __metal_driver_riscv_clint0 *)(controller);
+ unsigned long control_base =
+ __metal_driver_sifive_clint0_control_base(&clint->controller);
/* Per spec, the RISC-V MTIME/MTIMECMP registers are 64 bit,
* and are NOT internally latched for multiword transfers.
* Need to be careful about sequencing to avoid triggering
* spurious interrupts: For that set the high word to a max
* value first.
*/
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_RISCV_CLINT0_MTIMECMP_BASE + 4)) = 0xFFFFFFFF;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_RISCV_CLINT0_MTIMECMP_BASE)) = (__metal_io_u32)time;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_RISCV_CLINT0_MTIMECMP_BASE + 4)) = (__metal_io_u32)(time >> 32);
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_RISCV_CLINT0_MTIMECMP_BASE +
+ 4)) = 0xFFFFFFFF;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_RISCV_CLINT0_MTIMECMP_BASE)) =
+ (__metal_io_u32)time;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_RISCV_CLINT0_MTIMECMP_BASE +
+ 4)) = (__metal_io_u32)(time >> 32);
return 0;
}
-static struct metal_interrupt *_get_cpu_intc()
-{
+static struct metal_interrupt *_get_cpu_intc() {
int hartid = 0;
__asm__ volatile("csrr %[hartid], mhartid"
- : [hartid] "=r" (hartid) :: "memory");
+ : [hartid] "=r"(hartid)::"memory");
struct metal_cpu *cpu = metal_cpu_get(hartid);
return metal_cpu_interrupt_controller(cpu);
}
-void __metal_driver_riscv_clint0_init (struct metal_interrupt *controller)
-{
- int num_interrupts = __metal_driver_sifive_clint0_num_interrupts(controller);
+void __metal_driver_riscv_clint0_init(struct metal_interrupt *controller) {
+ int num_interrupts =
+ __metal_driver_sifive_clint0_num_interrupts(controller);
struct __metal_driver_riscv_clint0 *clint =
- (struct __metal_driver_riscv_clint0 *)(controller);
+ (struct __metal_driver_riscv_clint0 *)(controller);
- if ( !clint->init_done ) {
- /* Register its interrupts with with parent controller, aka sw and timerto its default isr */
+ if (!clint->init_done) {
+ /* Register its interrupts with with parent controller, aka sw and
+ * timerto its default isr */
for (int i = 0; i < num_interrupts; i++) {
- struct metal_interrupt *intc = __metal_driver_sifive_clint0_interrupt_parents(controller, i);
- int line = __metal_driver_sifive_clint0_interrupt_lines(controller, i);
+ struct metal_interrupt *intc =
+ __metal_driver_sifive_clint0_interrupt_parents(controller, i);
+ int line =
+ __metal_driver_sifive_clint0_interrupt_lines(controller, i);
intc->vtable->interrupt_register(intc, line, NULL, controller);
- }
- clint->init_done = 1;
- }
+ }
+ clint->init_done = 1;
+ }
}
-int __metal_driver_riscv_clint0_register (struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_riscv_clint0_register(struct metal_interrupt *controller,
+ int id, metal_interrupt_handler_t isr,
+ void *priv) {
int rc = -1;
metal_vector_mode mode = __metal_controller_interrupt_vector_mode();
struct metal_interrupt *intc = NULL;
struct metal_interrupt *cpu_intc = _get_cpu_intc();
- int num_interrupts = __metal_driver_sifive_clint0_num_interrupts(controller);
+ int num_interrupts =
+ __metal_driver_sifive_clint0_num_interrupts(controller);
- if ( (mode != METAL_VECTOR_MODE) && (mode != METAL_DIRECT_MODE) ) {
+ if ((mode != METAL_VECTOR_MODE) && (mode != METAL_DIRECT_MODE)) {
return rc;
}
- for(int i = 0; i < num_interrupts; i++) {
- int line = __metal_driver_sifive_clint0_interrupt_lines(controller, i);
+ for (int i = 0; i < num_interrupts; i++) {
+ int line = __metal_driver_sifive_clint0_interrupt_lines(controller, i);
intc = __metal_driver_sifive_clint0_interrupt_parents(controller, i);
if (cpu_intc == intc && id == line) {
break;
}
- intc = NULL;
+ intc = NULL;
}
/* Register its interrupts with parent controller */
@@ -101,59 +114,60 @@ int __metal_driver_riscv_clint0_register (struct metal_interrupt *controller,
return rc;
}
-int __metal_driver_riscv_clint0_vector_register (struct metal_interrupt *controller,
- int id, metal_interrupt_vector_handler_t isr,
- void *priv)
-{
+int __metal_driver_riscv_clint0_vector_register(
+ struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t isr, void *priv) {
/* Not supported. User can override the 'weak' handler with their own */
int rc = -1;
return rc;
}
-metal_vector_mode __metal_driver_riscv_clint0_get_vector_mode (struct metal_interrupt *controller)
-{
+metal_vector_mode __metal_driver_riscv_clint0_get_vector_mode(
+ struct metal_interrupt *controller) {
return __metal_controller_interrupt_vector_mode();
}
-int __metal_driver_riscv_clint0_set_vector_mode (struct metal_interrupt *controller, metal_vector_mode mode)
-{
+int __metal_driver_riscv_clint0_set_vector_mode(
+ struct metal_interrupt *controller, metal_vector_mode mode) {
int rc = -1;
struct metal_interrupt *intc = _get_cpu_intc();
if (intc) {
- /* Valid vector modes are VECTOR and DIRECT, anything else is invalid (-1) */
+ /* Valid vector modes are VECTOR and DIRECT, anything else is invalid
+ * (-1) */
switch (mode) {
case METAL_VECTOR_MODE:
case METAL_DIRECT_MODE:
rc = intc->vtable->interrupt_set_vector_mode(intc, mode);
break;
- case METAL_HARDWARE_VECTOR_MODE:
- case METAL_SELECTIVE_NONVECTOR_MODE:
- case METAL_SELECTIVE_VECTOR_MODE:
- break;
+ default:
+ break;
}
}
return rc;
}
-int __metal_driver_riscv_clint0_enable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_clint0_enable(struct metal_interrupt *controller,
+ int id) {
int rc = -1;
- if ( id ) {
+ if (id) {
struct metal_interrupt *intc = NULL;
struct metal_interrupt *cpu_intc = _get_cpu_intc();
- int num_interrupts = __metal_driver_sifive_clint0_num_interrupts(controller);
+ int num_interrupts =
+ __metal_driver_sifive_clint0_num_interrupts(controller);
- for(int i = 0; i < num_interrupts; i++) {
- int line = __metal_driver_sifive_clint0_interrupt_lines(controller, i);
- intc = __metal_driver_sifive_clint0_interrupt_parents(controller, i);
- if(cpu_intc == intc && id == line) {
+ for (int i = 0; i < num_interrupts; i++) {
+ int line =
+ __metal_driver_sifive_clint0_interrupt_lines(controller, i);
+ intc =
+ __metal_driver_sifive_clint0_interrupt_parents(controller, i);
+ if (cpu_intc == intc && id == line) {
break;
}
- intc = NULL;
+ intc = NULL;
}
-
+
/* Enable its interrupts with parent controller */
if (intc) {
rc = intc->vtable->interrupt_enable(intc, id);
@@ -163,24 +177,27 @@ int __metal_driver_riscv_clint0_enable (struct metal_interrupt *controller, int
return rc;
}
-int __metal_driver_riscv_clint0_disable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_clint0_disable(struct metal_interrupt *controller,
+ int id) {
int rc = -1;
- if ( id ) {
+ if (id) {
struct metal_interrupt *intc = NULL;
struct metal_interrupt *cpu_intc = _get_cpu_intc();
- int num_interrupts = __metal_driver_sifive_clint0_num_interrupts(controller);
+ int num_interrupts =
+ __metal_driver_sifive_clint0_num_interrupts(controller);
- for(int i = 0; i < num_interrupts; i++) {
- int line = __metal_driver_sifive_clint0_interrupt_lines(controller, i);
- intc = __metal_driver_sifive_clint0_interrupt_parents(controller, i);
- if(cpu_intc == intc && id == line) {
+ for (int i = 0; i < num_interrupts; i++) {
+ int line =
+ __metal_driver_sifive_clint0_interrupt_lines(controller, i);
+ intc =
+ __metal_driver_sifive_clint0_interrupt_parents(controller, i);
+ if (cpu_intc == intc && id == line) {
break;
}
- intc = NULL;
+ intc = NULL;
}
-
+
/* Disable its interrupts with parent controller */
if (intc) {
rc = intc->vtable->interrupt_disable(intc, id);
@@ -190,92 +207,94 @@ int __metal_driver_riscv_clint0_disable (struct metal_interrupt *controller, int
return rc;
}
-int __metal_driver_riscv_clint0_command_request (struct metal_interrupt *controller,
- int command, void *data)
-{
+int __metal_driver_riscv_clint0_command_request(
+ struct metal_interrupt *controller, int command, void *data) {
int hartid;
int rc = -1;
struct __metal_driver_riscv_clint0 *clint =
- (struct __metal_driver_riscv_clint0 *)(controller);
- unsigned long control_base = __metal_driver_sifive_clint0_control_base(controller);
+ (struct __metal_driver_riscv_clint0 *)(controller);
+ unsigned long control_base =
+ __metal_driver_sifive_clint0_control_base(controller);
switch (command) {
case METAL_TIMER_MTIME_GET:
if (data) {
- *(unsigned long long *)data = __metal_clint0_mtime_get(clint);
+ *(unsigned long long *)data = __metal_clint0_mtime_get(clint);
rc = 0;
}
break;
case METAL_SOFTWARE_IPI_CLEAR:
- if (data) {
- hartid = *(int *)data;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4))) = METAL_DISABLE;
+ if (data) {
+ hartid = *(int *)data;
+ __METAL_ACCESS_ONCE((
+ __metal_io_u32 *)(control_base + (hartid * 4))) = METAL_DISABLE;
rc = 0;
}
break;
case METAL_SOFTWARE_IPI_SET:
- if (data) {
- hartid = *(int *)data;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4))) = METAL_ENABLE;
- /* Callers of this function assume it's blocking, in the sense that
- * the IPI is guarnteed to have been delivered before the function
- * returns. We can't really guarnteed it's delivered, but we can
- * read back the control register after writing it in at least an
- * attempt to provide some semblence of ordering here. The fence
- * ensures the read is order after the write -- it wouldn't be
- * necessary under RVWMO because this is the same address, but we
- * don't have an IO memory model so I'm being a bit overkill here.
- */
- __METAL_IO_FENCE(o,i);
- rc = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4)));
+ if (data) {
+ hartid = *(int *)data;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + (hartid * 4))) = METAL_ENABLE;
+ /* Callers of this function assume it's blocking, in the sense that
+ * the IPI is guarnteed to have been delivered before the function
+ * returns. We can't really guarnteed it's delivered, but we can
+ * read back the control register after writing it in at least an
+ * attempt to provide some semblence of ordering here. The fence
+ * ensures the read is order after the write -- it wouldn't be
+ * necessary under RVWMO because this is the same address, but we
+ * don't have an IO memory model so I'm being a bit overkill here.
+ */
+ __METAL_IO_FENCE(o, i);
+ rc = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + (hartid * 4)));
rc = 0;
}
break;
case METAL_SOFTWARE_MSIP_GET:
rc = 0;
- if (data) {
- hartid = *(int *)data;
- rc = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4)));
+ if (data) {
+ hartid = *(int *)data;
+ rc = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + (hartid * 4)));
}
break;
default:
- break;
+ break;
}
return rc;
}
-int __metal_driver_riscv_clint0_clear_interrupt (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_clint0_clear_interrupt(
+ struct metal_interrupt *controller, int id) {
int hartid = metal_cpu_get_current_hartid();
- return __metal_driver_riscv_clint0_command_request(controller,
- METAL_SOFTWARE_IPI_CLEAR, &hartid);
+ return __metal_driver_riscv_clint0_command_request(
+ controller, METAL_SOFTWARE_IPI_CLEAR, &hartid);
}
-int __metal_driver_riscv_clint0_set_interrupt (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_clint0_set_interrupt(
+ struct metal_interrupt *controller, int id) {
int hartid = metal_cpu_get_current_hartid();
- return __metal_driver_riscv_clint0_command_request(controller,
- METAL_SOFTWARE_IPI_SET, &hartid);
+ return __metal_driver_riscv_clint0_command_request(
+ controller, METAL_SOFTWARE_IPI_SET, &hartid);
}
-
__METAL_DEFINE_VTABLE(__metal_driver_vtable_riscv_clint0) = {
- .clint_vtable.interrupt_init = __metal_driver_riscv_clint0_init,
+ .clint_vtable.interrupt_init = __metal_driver_riscv_clint0_init,
.clint_vtable.interrupt_register = __metal_driver_riscv_clint0_register,
- .clint_vtable.interrupt_vector_register = __metal_driver_riscv_clint0_vector_register,
- .clint_vtable.interrupt_enable = __metal_driver_riscv_clint0_enable,
- .clint_vtable.interrupt_disable = __metal_driver_riscv_clint0_disable,
- .clint_vtable.interrupt_get_vector_mode = __metal_driver_riscv_clint0_get_vector_mode,
- .clint_vtable.interrupt_set_vector_mode = __metal_driver_riscv_clint0_set_vector_mode,
- .clint_vtable.interrupt_clear = __metal_driver_riscv_clint0_clear_interrupt,
- .clint_vtable.interrupt_set = __metal_driver_riscv_clint0_set_interrupt,
- .clint_vtable.command_request = __metal_driver_riscv_clint0_command_request,
- .clint_vtable.mtimecmp_set = __metal_driver_riscv_clint0_mtimecmp_set,
+ .clint_vtable.interrupt_vector_register =
+ __metal_driver_riscv_clint0_vector_register,
+ .clint_vtable.interrupt_enable = __metal_driver_riscv_clint0_enable,
+ .clint_vtable.interrupt_disable = __metal_driver_riscv_clint0_disable,
+ .clint_vtable.interrupt_get_vector_mode =
+ __metal_driver_riscv_clint0_get_vector_mode,
+ .clint_vtable.interrupt_set_vector_mode =
+ __metal_driver_riscv_clint0_set_vector_mode,
+ .clint_vtable.interrupt_clear = __metal_driver_riscv_clint0_clear_interrupt,
+ .clint_vtable.interrupt_set = __metal_driver_riscv_clint0_set_interrupt,
+ .clint_vtable.command_request = __metal_driver_riscv_clint0_command_request,
+ .clint_vtable.mtimecmp_set = __metal_driver_riscv_clint0_mtimecmp_set,
};
#endif /* METAL_RISCV_CLINT0 */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_cpu.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_cpu.c
index b693f312a..dda13b934 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_cpu.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_cpu.c
@@ -1,145 +1,157 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <stdint.h>
#include <metal/io.h>
-#include <metal/shutdown.h>
#include <metal/machine.h>
+#include <metal/shutdown.h>
+#include <stdint.h>
+
+#define __METAL_IRQ_VECTOR_HANDLER(id) \
+ void *priv; \
+ struct __metal_driver_riscv_cpu_intc *intc; \
+ struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()]; \
+ if (cpu) { \
+ intc = (struct __metal_driver_riscv_cpu_intc *) \
+ __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu); \
+ priv = intc->metal_int_table[id].exint_data; \
+ intc->metal_int_table[id].handler(id, priv); \
+ }
extern void __metal_vector_table();
unsigned long long __metal_driver_cpu_mtime_get(struct metal_cpu *cpu);
-int __metal_driver_cpu_mtimecmp_set(struct metal_cpu *cpu, unsigned long long time);
+int __metal_driver_cpu_mtimecmp_set(struct metal_cpu *cpu,
+ unsigned long long time);
-struct metal_cpu *__metal_driver_cpu_get(int hartid)
-{
+struct metal_cpu *__metal_driver_cpu_get(int hartid) {
if (hartid < __METAL_DT_MAX_HARTS) {
return &(__metal_cpu_table[hartid]->cpu);
}
return (struct metal_cpu *)NULL;
}
-uintptr_t __metal_myhart_id (void)
-{
+uintptr_t __metal_myhart_id(void) {
uintptr_t myhart;
- __asm__ volatile ("csrr %0, mhartid" : "=r"(myhart));
+ __asm__ volatile("csrr %0, mhartid" : "=r"(myhart));
return myhart;
}
-void __metal_zero_memory (unsigned char *base, unsigned int size)
-{
+void __metal_zero_memory(unsigned char *base, unsigned int size) {
volatile unsigned char *ptr;
- for (ptr = base; ptr < (base + size); ptr++){
+ for (ptr = base; ptr < (base + size); ptr++) {
*ptr = 0;
}
}
-void __metal_interrupt_global_enable (void) {
+void __metal_interrupt_global_enable(void) {
uintptr_t m;
- __asm__ volatile ("csrrs %0, mstatus, %1" : "=r"(m) : "r"(METAL_MIE_INTERRUPT));
+ __asm__ volatile("csrrs %0, mstatus, %1"
+ : "=r"(m)
+ : "r"(METAL_MIE_INTERRUPT));
}
-void __metal_interrupt_global_disable (void) {
+void __metal_interrupt_global_disable(void) {
uintptr_t m;
- __asm__ volatile ("csrrc %0, mstatus, %1" : "=r"(m) : "r"(METAL_MIE_INTERRUPT));
+ __asm__ volatile("csrrc %0, mstatus, %1"
+ : "=r"(m)
+ : "r"(METAL_MIE_INTERRUPT));
}
-void __metal_interrupt_software_enable (void) {
+void __metal_interrupt_software_enable(void) {
uintptr_t m;
- __asm__ volatile ("csrrs %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_SW));
+ __asm__ volatile("csrrs %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_SW));
}
-void __metal_interrupt_software_disable (void) {
+void __metal_interrupt_software_disable(void) {
uintptr_t m;
- __asm__ volatile ("csrrc %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_SW));
+ __asm__ volatile("csrrc %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_SW));
}
-void __metal_interrupt_timer_enable (void) {
+void __metal_interrupt_timer_enable(void) {
uintptr_t m;
- __asm__ volatile ("csrrs %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_TMR));
+ __asm__ volatile("csrrs %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_TMR));
}
-void __metal_interrupt_timer_disable (void) {
+void __metal_interrupt_timer_disable(void) {
uintptr_t m;
- __asm__ volatile ("csrrc %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_TMR));
+ __asm__ volatile("csrrc %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_TMR));
}
-void __metal_interrupt_external_enable (void) {
+void __metal_interrupt_external_enable(void) {
uintptr_t m;
- __asm__ volatile ("csrrs %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_EXT));
+ __asm__ volatile("csrrs %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_EXT));
}
-void __metal_interrupt_external_disable (void) {
+void __metal_interrupt_external_disable(void) {
unsigned long m;
- __asm__ volatile ("csrrc %0, mie, %1" : "=r"(m) : "r"(METAL_LOCAL_INTERRUPT_EXT));
+ __asm__ volatile("csrrc %0, mie, %1"
+ : "=r"(m)
+ : "r"(METAL_LOCAL_INTERRUPT_EXT));
}
-void __metal_interrupt_local_enable (int id) {
+void __metal_interrupt_local_enable(int id) {
uintptr_t b = 1 << id;
uintptr_t m;
- __asm__ volatile ("csrrs %0, mie, %1" : "=r"(m) : "r"(b));
+ __asm__ volatile("csrrs %0, mie, %1" : "=r"(m) : "r"(b));
}
-void __metal_interrupt_local_disable (int id) {
+void __metal_interrupt_local_disable(int id) {
uintptr_t b = 1 << id;
uintptr_t m;
- __asm__ volatile ("csrrc %0, mie, %1" : "=r"(m) : "r"(b));
+ __asm__ volatile("csrrc %0, mie, %1" : "=r"(m) : "r"(b));
}
-void __metal_default_exception_handler (struct metal_cpu *cpu, int ecode) {
+void __metal_default_exception_handler(struct metal_cpu *cpu, int ecode) {
metal_shutdown(100);
}
-void __metal_default_interrupt_handler (int id, void *priv) {
+void __metal_default_interrupt_handler(int id, void *priv) {
metal_shutdown(200);
}
/* The metal_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_interrupt_vector_handler (void) {
+void __attribute__((weak, interrupt)) metal_interrupt_vector_handler(void) {
metal_shutdown(300);
}
/* The metal_software_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_software_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_SW].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_SW].handler(METAL_INTERRUPT_ID_SW, priv);
- }
+void __attribute__((weak, interrupt))
+metal_software_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_SW);
}
-void __metal_default_sw_handler (int id, void *priv) {
+void __metal_default_sw_handler(int id, void *priv) {
uintptr_t mcause;
struct __metal_driver_riscv_cpu_intc *intc;
struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
- __asm__ volatile ("csrr %0, mcause" : "=r"(mcause));
- if ( cpu ) {
+ __asm__ volatile("csrr %0, mcause" : "=r"(mcause));
+ if (cpu) {
intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- intc->metal_exception_table[mcause & METAL_MCAUSE_CAUSE]((struct metal_cpu *)cpu, id);
+ __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
+ intc->metal_exception_table[mcause & METAL_MCAUSE_CAUSE](
+ (struct metal_cpu *)cpu, id);
}
}
/* The metal_timer_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_timer_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_TMR].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_TMR].handler(METAL_INTERRUPT_ID_TMR, priv);
- }
+void __attribute__((weak, interrupt))
+metal_timer_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_TMR);
}
-void __metal_default_timer_handler (int id, void *priv) {
+void __metal_default_beu_handler(int id, void *priv) {}
+
+void __metal_default_timer_handler(int id, void *priv) {
struct metal_cpu *cpu = __metal_driver_cpu_get(__metal_myhart_id());
unsigned long long time = __metal_driver_cpu_mtime_get(cpu);
@@ -148,52 +160,49 @@ void __metal_default_timer_handler (int id, void *priv) {
}
/* The metal_external_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_external_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_EXT].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_EXT].handler(METAL_INTERRUPT_ID_EXT, priv);
- }
+void __attribute__((weak, interrupt))
+metal_external_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_EXT);
}
void __metal_exception_handler(void) __attribute__((interrupt, aligned(128)));
-void __metal_exception_handler (void) {
+void __metal_exception_handler(void) {
int id;
void *priv;
uintptr_t mcause, mepc, mtval, mtvec;
struct __metal_driver_riscv_cpu_intc *intc;
struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
- __asm__ volatile ("csrr %0, mcause" : "=r"(mcause));
- __asm__ volatile ("csrr %0, mepc" : "=r"(mepc));
- __asm__ volatile ("csrr %0, mtval" : "=r"(mtval));
- __asm__ volatile ("csrr %0, mtvec" : "=r"(mtvec));
+ __asm__ volatile("csrr %0, mcause" : "=r"(mcause));
+ __asm__ volatile("csrr %0, mepc" : "=r"(mepc));
+ __asm__ volatile("csrr %0, mtval" : "=r"(mtval));
+ __asm__ volatile("csrr %0, mtvec" : "=r"(mtvec));
- if ( cpu ) {
+ if (cpu) {
intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
+ __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
id = mcause & METAL_MCAUSE_CAUSE;
if (mcause & METAL_MCAUSE_INTR) {
+ if (id == METAL_INTERRUPT_ID_BEU) {
+ priv = intc->metal_int_beu.exint_data;
+ intc->metal_int_beu.handler(id, priv);
+ return;
+ }
if ((id < METAL_INTERRUPT_ID_CSW) ||
- ((mtvec & METAL_MTVEC_MASK) == METAL_MTVEC_DIRECT)) {
+ ((mtvec & METAL_MTVEC_MASK) == METAL_MTVEC_DIRECT)) {
priv = intc->metal_int_table[id].exint_data;
intc->metal_int_table[id].handler(id, priv);
- return;
+ return;
}
if ((mtvec & METAL_MTVEC_MASK) == METAL_MTVEC_CLIC) {
- uintptr_t mtvt;
- metal_interrupt_handler_t mtvt_handler;
-
- __asm__ volatile ("csrr %0, 0x307" : "=r"(mtvt));
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_SW].sub_int;
- mtvt_handler = (metal_interrupt_handler_t)*(uintptr_t *)mtvt;
- mtvt_handler(id, priv);
- return;
+ uintptr_t mtvt;
+ metal_interrupt_handler_t mtvt_handler;
+
+ __asm__ volatile("csrr %0, 0x307" : "=r"(mtvt));
+ priv = intc->metal_int_table[METAL_INTERRUPT_ID_SW].sub_int;
+ mtvt_handler = (metal_interrupt_handler_t) * (uintptr_t *)mtvt;
+ mtvt_handler(id, priv);
+ return;
}
} else {
intc->metal_exception_table[id]((struct metal_cpu *)cpu, id);
@@ -202,234 +211,95 @@ void __metal_exception_handler (void) {
}
/* The metal_lc0_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc0_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC0].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC0].handler(METAL_INTERRUPT_ID_LC0, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc0_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC0);
}
/* The metal_lc1_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc1_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC1].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC1].handler(METAL_INTERRUPT_ID_LC1, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc1_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC1);
}
/* The metal_lc2_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc2_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC2].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC2].handler(METAL_INTERRUPT_ID_LC2, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc2_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC2);
}
/* The metal_lc3_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc3_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC3].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC3].handler(METAL_INTERRUPT_ID_LC3, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc3_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC3);
}
/* The metal_lc4_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc4_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC4].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC4].handler(METAL_INTERRUPT_ID_LC4, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc4_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC4);
}
/* The metal_lc5_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc5_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC5].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC5].handler(METAL_INTERRUPT_ID_LC5, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc5_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC5);
}
/* The metal_lc6_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc6_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC6].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC6].handler(METAL_INTERRUPT_ID_LC6, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc6_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC6);
}
/* The metal_lc7_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc7_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC7].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC7].handler(METAL_INTERRUPT_ID_LC7, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc7_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC7);
}
/* The metal_lc8_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc8_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC8].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC8].handler(METAL_INTERRUPT_ID_LC8, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc8_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC8);
}
/* The metal_lc9_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc9_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC9].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC9].handler(METAL_INTERRUPT_ID_LC9, priv);
- }
+void __attribute__((weak, interrupt)) metal_lc9_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC9);
}
/* The metal_lc10_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc10_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC10].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC10].handler(METAL_INTERRUPT_ID_LC10, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc10_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC10);
}
/* The metal_lc11_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc11_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC11].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC11].handler(METAL_INTERRUPT_ID_LC11, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc11_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC11);
}
/* The metal_lc12_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc12_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC12].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC12].handler(METAL_INTERRUPT_ID_LC12, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc12_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC12);
}
/* The metal_lc13_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc13_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC13].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC13].handler(METAL_INTERRUPT_ID_LC13, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc13_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC13);
}
/* The metal_lc14_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc14_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC14].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC14].handler(METAL_INTERRUPT_ID_LC14, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc14_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC14);
}
/* The metal_lc15_interrupt_vector_handler() function can be redefined. */
-void __attribute__((weak, interrupt)) metal_lc15_interrupt_vector_handler (void) {
- void *priv;
- struct __metal_driver_riscv_cpu_intc *intc;
- struct __metal_driver_cpu *cpu = __metal_cpu_table[__metal_myhart_id()];
-
- if ( cpu ) {
- intc = (struct __metal_driver_riscv_cpu_intc *)
- __metal_driver_cpu_interrupt_controller((struct metal_cpu *)cpu);
- priv = intc->metal_int_table[METAL_INTERRUPT_ID_LC15].exint_data;
- intc->metal_int_table[METAL_INTERRUPT_ID_LC15].handler(METAL_INTERRUPT_ID_LC15, priv);
- }
+void __attribute__((weak, interrupt))
+metal_lc15_interrupt_vector_handler(void) {
+ __METAL_IRQ_VECTOR_HANDLER(METAL_INTERRUPT_ID_LC15);
}
-metal_vector_mode __metal_controller_interrupt_vector_mode (void)
-{
+metal_vector_mode __metal_controller_interrupt_vector_mode(void) {
uintptr_t val;
- asm volatile ("csrr %0, mtvec" : "=r"(val));
+ __asm__ volatile("csrr %0, mtvec" : "=r"(val));
val &= METAL_MTVEC_MASK;
switch (val) {
@@ -443,35 +313,37 @@ metal_vector_mode __metal_controller_interrupt_vector_mode (void)
return METAL_DIRECT_MODE;
}
-void __metal_controller_interrupt_vector (metal_vector_mode mode, void *vec_table)
-{
+void __metal_controller_interrupt_vector(metal_vector_mode mode,
+ void *vec_table) {
uintptr_t trap_entry, val;
- __asm__ volatile ("csrr %0, mtvec" : "=r"(val));
+ __asm__ volatile("csrr %0, mtvec" : "=r"(val));
val &= ~(METAL_MTVEC_CLIC_VECTORED | METAL_MTVEC_CLIC_RESERVED);
trap_entry = (uintptr_t)vec_table;
switch (mode) {
case METAL_SELECTIVE_NONVECTOR_MODE:
case METAL_SELECTIVE_VECTOR_MODE:
- __asm__ volatile ("csrw 0x307, %0" :: "r"(trap_entry));
- __asm__ volatile ("csrw mtvec, %0" :: "r"(val | METAL_MTVEC_CLIC));
+ __asm__ volatile("csrw 0x307, %0" ::"r"(trap_entry));
+ __asm__ volatile("csrw mtvec, %0" ::"r"(val | METAL_MTVEC_CLIC));
break;
case METAL_HARDWARE_VECTOR_MODE:
- __asm__ volatile ("csrw 0x307, %0" :: "r"(trap_entry));
- __asm__ volatile ("csrw mtvec, %0" :: "r"(val | METAL_MTVEC_CLIC_VECTORED));
+ __asm__ volatile("csrw 0x307, %0" ::"r"(trap_entry));
+ __asm__ volatile(
+ "csrw mtvec, %0" ::"r"(val | METAL_MTVEC_CLIC_VECTORED));
break;
case METAL_VECTOR_MODE:
- __asm__ volatile ("csrw mtvec, %0" :: "r"(trap_entry | METAL_MTVEC_VECTORED));
+ __asm__ volatile(
+ "csrw mtvec, %0" ::"r"(trap_entry | METAL_MTVEC_VECTORED));
break;
case METAL_DIRECT_MODE:
- __asm__ volatile ("csrw mtvec, %0" :: "r"(trap_entry & ~METAL_MTVEC_CLIC_VECTORED));
+ __asm__ volatile(
+ "csrw mtvec, %0" ::"r"(trap_entry & ~METAL_MTVEC_CLIC_VECTORED));
break;
}
}
-int __metal_valid_interrupt_id (int id)
-{
+int __metal_valid_interrupt_id(int id) {
switch (id) {
case METAL_INTERRUPT_ID_SW:
case METAL_INTERRUPT_ID_TMR:
@@ -492,6 +364,7 @@ int __metal_valid_interrupt_id (int id)
case METAL_INTERRUPT_ID_LC13:
case METAL_INTERRUPT_ID_LC14:
case METAL_INTERRUPT_ID_LC15:
+ case METAL_INTERRUPT_ID_BEU:
return 1;
default:
break;
@@ -500,13 +373,11 @@ int __metal_valid_interrupt_id (int id)
return 0;
}
-
-int __metal_local_interrupt_enable (struct metal_interrupt *controller,
- metal_interrupt_id_e id, int enable)
-{
+int __metal_local_interrupt_enable(struct metal_interrupt *controller,
+ metal_interrupt_id_e id, int enable) {
int rc = 0;
-
- if ( !controller) {
+
+ if (!controller) {
return -1;
}
@@ -527,11 +398,11 @@ int __metal_local_interrupt_enable (struct metal_interrupt *controller,
break;
case METAL_INTERRUPT_ID_TMR:
if (enable) {
- __metal_interrupt_timer_enable();
- } else {
- __metal_interrupt_timer_disable();
- }
- break;
+ __metal_interrupt_timer_enable();
+ } else {
+ __metal_interrupt_timer_disable();
+ }
+ break;
case METAL_INTERRUPT_ID_EXT:
if (enable) {
__metal_interrupt_external_enable();
@@ -567,9 +438,8 @@ int __metal_local_interrupt_enable (struct metal_interrupt *controller,
return rc;
}
-int __metal_exception_register (struct metal_interrupt *controller,
- int ecode, metal_exception_handler_t isr)
-{
+int __metal_exception_register(struct metal_interrupt *controller, int ecode,
+ metal_exception_handler_t isr) {
struct __metal_driver_riscv_cpu_intc *intc = (void *)(controller);
if ((ecode < METAL_MAX_EXCEPTION_CODE) && isr) {
@@ -579,199 +449,198 @@ int __metal_exception_register (struct metal_interrupt *controller,
return -1;
}
-void __metal_driver_riscv_cpu_controller_interrupt_init (struct metal_interrupt *controller)
-{
+extern void early_trap_vector(void);
+void __metal_driver_riscv_cpu_controller_interrupt_init(
+ struct metal_interrupt *controller) {
struct __metal_driver_riscv_cpu_intc *intc = (void *)(controller);
- uintptr_t val;
-
- if ( !intc->init_done ) {
- /* Disable and clear all interrupt sources */
- __asm__ volatile ("csrc mie, %0" :: "r"(-1));
- __asm__ volatile ("csrc mip, %0" :: "r"(-1));
-
- /* Read the misa CSR to determine if the delegation registers exist */
- uintptr_t misa;
- __asm__ volatile ("csrr %0, misa" : "=r" (misa));
-
- /* The delegation CSRs exist if user mode interrupts (N extension) or
- * supervisor mode (S extension) are supported */
- if((misa & METAL_ISA_N_EXTENSIONS) || (misa & METAL_ISA_S_EXTENSIONS)) {
- /* Disable interrupt and exception delegation */
- __asm__ volatile ("csrc mideleg, %0" :: "r"(-1));
- __asm__ volatile ("csrc medeleg, %0" :: "r"(-1));
- }
-
- /* The satp CSR exists if supervisor mode (S extension) is supported */
- if(misa & METAL_ISA_S_EXTENSIONS) {
- /* Clear the entire CSR to make sure that satp.MODE = 0 */
- __asm__ volatile ("csrc satp, %0" :: "r"(-1));
- }
+ if (!intc->init_done) {
/* Default to use direct interrupt, setup sw cb table*/
for (int i = 0; i < METAL_MAX_MI; i++) {
intc->metal_int_table[i].handler = NULL;
intc->metal_int_table[i].sub_int = NULL;
intc->metal_int_table[i].exint_data = NULL;
- }
- for (int i = 0; i < METAL_MAX_ME; i++) {
- intc->metal_exception_table[i] = __metal_default_exception_handler;
- }
- __metal_controller_interrupt_vector(METAL_DIRECT_MODE, (void *)(uintptr_t)&__metal_exception_handler);
- __asm__ volatile ("csrr %0, misa" : "=r"(val));
- if (val & (METAL_ISA_D_EXTENSIONS | METAL_ISA_F_EXTENSIONS | METAL_ISA_Q_EXTENSIONS)) {
- /* Floating point architecture, so turn on FP register saving*/
- __asm__ volatile ("csrr %0, mstatus" : "=r"(val));
- __asm__ volatile ("csrw mstatus, %0" :: "r"(val | METAL_MSTATUS_FS_INIT));
- }
- intc->init_done = 1;
+ }
+
+ for (int i = 0; i < METAL_MAX_ME; i++) {
+ intc->metal_exception_table[i] = __metal_default_exception_handler;
+ }
+
+ /*
+ * Set the real trap handler if the value of mtvec is equal to
+ * early_trap_vector. If mtvec is not equal to early_trap_vector,
+ * that means user has own trap handler, then we don't overwrite it.
+ */
+ uintptr_t mtvec;
+ __asm__ volatile("csrr %0, mtvec" : "=r"(mtvec));
+ if (mtvec == (uintptr_t)&early_trap_vector) {
+ __metal_controller_interrupt_vector(
+ METAL_DIRECT_MODE,
+ (void *)(uintptr_t)&__metal_exception_handler);
+ }
+ intc->init_done = 1;
}
}
-int __metal_driver_riscv_cpu_controller_interrupt_register(struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_riscv_cpu_controller_interrupt_register(
+ struct metal_interrupt *controller, int id, metal_interrupt_handler_t isr,
+ void *priv) {
int rc = 0;
struct __metal_driver_riscv_cpu_intc *intc = (void *)(controller);
-
- if ( !__metal_valid_interrupt_id(id) ) {
+
+ if (!__metal_valid_interrupt_id(id)) {
return -11;
}
+ if ((id == METAL_INTERRUPT_ID_BEU) &&
+ (__metal_controller_interrupt_vector_mode() != METAL_DIRECT_MODE)) {
+ /* Only allow registration of the bus error unit interrupt if
+ * interrupt vectoring if off */
+ return -13;
+ }
if (isr) {
- intc->metal_int_table[id].handler = isr;
- intc->metal_int_table[id].exint_data = priv;
+ if (id == METAL_INTERRUPT_ID_BEU) {
+ intc->metal_int_beu.handler = isr;
+ intc->metal_int_beu.exint_data = priv;
+ } else {
+ intc->metal_int_table[id].handler = isr;
+ intc->metal_int_table[id].exint_data = priv;
+ }
} else {
- switch (id) {
- case METAL_INTERRUPT_ID_SW:
+ switch (id) {
+ case METAL_INTERRUPT_ID_SW:
intc->metal_int_table[id].handler = __metal_default_sw_handler;
intc->metal_int_table[id].sub_int = priv;
- break;
- case METAL_INTERRUPT_ID_TMR:
+ break;
+ case METAL_INTERRUPT_ID_TMR:
intc->metal_int_table[id].handler = __metal_default_timer_handler;
intc->metal_int_table[id].sub_int = priv;
- break;
- case METAL_INTERRUPT_ID_EXT:
- case METAL_INTERRUPT_ID_LC0:
- case METAL_INTERRUPT_ID_LC1:
- case METAL_INTERRUPT_ID_LC2:
- case METAL_INTERRUPT_ID_LC3:
- case METAL_INTERRUPT_ID_LC4:
- case METAL_INTERRUPT_ID_LC5:
- case METAL_INTERRUPT_ID_LC6:
- case METAL_INTERRUPT_ID_LC7:
- case METAL_INTERRUPT_ID_LC8:
- case METAL_INTERRUPT_ID_LC9:
- case METAL_INTERRUPT_ID_LC10:
- case METAL_INTERRUPT_ID_LC11:
- case METAL_INTERRUPT_ID_LC12:
- case METAL_INTERRUPT_ID_LC13:
- case METAL_INTERRUPT_ID_LC14:
- case METAL_INTERRUPT_ID_LC15:
- intc->metal_int_table[id].handler = __metal_default_interrupt_handler;
+ break;
+ case METAL_INTERRUPT_ID_BEU:
+ intc->metal_int_beu.handler = __metal_default_beu_handler;
+ intc->metal_int_beu.exint_data = priv;
+ break;
+ case METAL_INTERRUPT_ID_EXT:
+ case METAL_INTERRUPT_ID_LC0:
+ case METAL_INTERRUPT_ID_LC1:
+ case METAL_INTERRUPT_ID_LC2:
+ case METAL_INTERRUPT_ID_LC3:
+ case METAL_INTERRUPT_ID_LC4:
+ case METAL_INTERRUPT_ID_LC5:
+ case METAL_INTERRUPT_ID_LC6:
+ case METAL_INTERRUPT_ID_LC7:
+ case METAL_INTERRUPT_ID_LC8:
+ case METAL_INTERRUPT_ID_LC9:
+ case METAL_INTERRUPT_ID_LC10:
+ case METAL_INTERRUPT_ID_LC11:
+ case METAL_INTERRUPT_ID_LC12:
+ case METAL_INTERRUPT_ID_LC13:
+ case METAL_INTERRUPT_ID_LC14:
+ case METAL_INTERRUPT_ID_LC15:
+ intc->metal_int_table[id].handler =
+ __metal_default_interrupt_handler;
intc->metal_int_table[id].sub_int = priv;
- break;
- default:
- rc = -12;
- }
+ break;
+ default:
+ rc = -12;
+ }
}
return rc;
}
-int __metal_driver_riscv_cpu_controller_interrupt_enable (struct metal_interrupt *controller,
- int id)
-{
+int __metal_driver_riscv_cpu_controller_interrupt_enable(
+ struct metal_interrupt *controller, int id) {
return __metal_local_interrupt_enable(controller, id, METAL_ENABLE);
}
-int __metal_driver_riscv_cpu_controller_interrupt_disable (struct metal_interrupt *controller,
- int id)
-{
+int __metal_driver_riscv_cpu_controller_interrupt_disable(
+ struct metal_interrupt *controller, int id) {
return __metal_local_interrupt_enable(controller, id, METAL_DISABLE);
}
-int __metal_driver_riscv_cpu_controller_interrupt_enable_vector(struct metal_interrupt *controller,
- int id, metal_vector_mode mode)
-{
+int __metal_driver_riscv_cpu_controller_interrupt_enable_vector(
+ struct metal_interrupt *controller, int id, metal_vector_mode mode) {
struct __metal_driver_riscv_cpu_intc *intc = (void *)(controller);
if (id == METAL_INTERRUPT_ID_BASE) {
if (mode == METAL_DIRECT_MODE) {
- __metal_controller_interrupt_vector(mode, (void *)(uintptr_t)&__metal_exception_handler);
+ __metal_controller_interrupt_vector(
+ mode, (void *)(uintptr_t)&__metal_exception_handler);
return 0;
- }
+ }
if (mode == METAL_VECTOR_MODE) {
- __metal_controller_interrupt_vector(mode, (void *)&intc->metal_mtvec_table);
+ __metal_controller_interrupt_vector(
+ mode, (void *)&intc->metal_mtvec_table);
return 0;
}
}
return -1;
}
-int __metal_driver_riscv_cpu_controller_interrupt_disable_vector(struct metal_interrupt *controller,
- int id)
-{
+int __metal_driver_riscv_cpu_controller_interrupt_disable_vector(
+ struct metal_interrupt *controller, int id) {
if (id == METAL_INTERRUPT_ID_BASE) {
- __metal_controller_interrupt_vector(METAL_DIRECT_MODE, (void *)(uintptr_t)&__metal_exception_handler);
+ __metal_controller_interrupt_vector(
+ METAL_DIRECT_MODE, (void *)(uintptr_t)&__metal_exception_handler);
return 0;
}
return -1;
}
-metal_vector_mode __metal_driver_riscv_cpu_controller_get_vector_mode (struct metal_interrupt *controller)
-{
+metal_vector_mode __metal_driver_riscv_cpu_controller_get_vector_mode(
+ struct metal_interrupt *controller) {
return __metal_controller_interrupt_vector_mode();
}
-int __metal_driver_riscv_cpu_controller_set_vector_mode (struct metal_interrupt *controller,
- metal_vector_mode mode)
-{
- struct __metal_driver_riscv_cpu_intc *intc = (void *)(controller);
- ( void ) intc;
+int __metal_driver_riscv_cpu_controller_set_vector_mode(
+ struct metal_interrupt *controller, metal_vector_mode mode) {
if (mode == METAL_DIRECT_MODE) {
- __metal_controller_interrupt_vector(mode, (void *)(uintptr_t)&__metal_exception_handler);
- return 0;
+ __metal_controller_interrupt_vector(
+ mode, (void *)(uintptr_t)&__metal_exception_handler);
+ return 0;
}
if (mode == METAL_VECTOR_MODE) {
- __metal_controller_interrupt_vector(mode, (void *)__metal_vector_table);
+ __metal_controller_interrupt_vector(
+ mode, (void *)(uintptr_t)__metal_vector_table);
return 0;
}
return -1;
}
-int __metal_driver_riscv_cpu_controller_command_request (struct metal_interrupt *controller,
- int cmd, void *data)
-{
- /* NOP for now, unless local interrupt lines the like of clic, clint, plic */
+int __metal_driver_riscv_cpu_controller_command_request(
+ struct metal_interrupt *controller, int cmd, void *data) {
+ /* NOP for now, unless local interrupt lines the like of clic, clint, plic
+ */
return 0;
}
/* CPU driver !!! */
-unsigned long long __metal_driver_cpu_mcycle_get(struct metal_cpu *cpu)
-{
+unsigned long long __metal_driver_cpu_mcycle_get(struct metal_cpu *cpu) {
unsigned long long val = 0;
#if __riscv_xlen == 32
unsigned long hi, hi1, lo;
- __asm__ volatile ("csrr %0, mcycleh" : "=r"(hi));
- __asm__ volatile ("csrr %0, mcycle" : "=r"(lo));
- __asm__ volatile ("csrr %0, mcycleh" : "=r"(hi1));
- if (hi == hi1) {
- val = ((unsigned long long)hi << 32) | lo;
- }
+ do {
+ __asm__ volatile("csrr %0, mcycleh" : "=r"(hi));
+ __asm__ volatile("csrr %0, mcycle" : "=r"(lo));
+ __asm__ volatile("csrr %0, mcycleh" : "=r"(hi1));
+ /* hi != hi1 means mcycle overflow during we get value,
+ * so we must retry. */
+ } while (hi != hi1);
+
+ val = ((unsigned long long)hi << 32) | lo;
#else
- __asm__ volatile ("csrr %0, mcycle" : "=r"(val));
+ __asm__ volatile("csrr %0, mcycle" : "=r"(val));
#endif
return val;
}
-unsigned long long __metal_driver_cpu_timebase_get(struct metal_cpu *cpu)
-{
- int timebase;
+unsigned long long __metal_driver_cpu_timebase_get(struct metal_cpu *cpu) {
+ int timebase;
if (!cpu) {
return 0;
}
@@ -780,44 +649,43 @@ unsigned long long __metal_driver_cpu_timebase_get(struct metal_cpu *cpu)
return timebase;
}
-unsigned long long __metal_driver_cpu_mtime_get (struct metal_cpu *cpu)
-{
+unsigned long long __metal_driver_cpu_mtime_get(struct metal_cpu *cpu) {
unsigned long long time = 0;
struct metal_interrupt *tmr_intc;
struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
tmr_intc = intc->metal_int_table[METAL_INTERRUPT_ID_TMR].sub_int;
if (tmr_intc) {
- tmr_intc->vtable->command_request(tmr_intc,
- METAL_TIMER_MTIME_GET, &time);
+ tmr_intc->vtable->command_request(tmr_intc, METAL_TIMER_MTIME_GET,
+ &time);
}
}
return time;
}
-int __metal_driver_cpu_mtimecmp_set (struct metal_cpu *cpu, unsigned long long time)
-{
+int __metal_driver_cpu_mtimecmp_set(struct metal_cpu *cpu,
+ unsigned long long time) {
int rc = -1;
struct metal_interrupt *tmr_intc;
struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
tmr_intc = intc->metal_int_table[METAL_INTERRUPT_ID_TMR].sub_int;
if (tmr_intc) {
- rc = tmr_intc->vtable->mtimecmp_set(tmr_intc,
- __metal_driver_cpu_hartid(cpu),
- time);
+ rc = tmr_intc->vtable->mtimecmp_set(
+ tmr_intc, __metal_driver_cpu_hartid(cpu), time);
}
}
return rc;
}
struct metal_interrupt *
-__metal_driver_cpu_timer_controller_interrupt(struct metal_cpu *cpu)
-{
+__metal_driver_cpu_timer_controller_interrupt(struct metal_cpu *cpu) {
#ifdef __METAL_DT_RISCV_CLINT0_HANDLE
return __METAL_DT_RISCV_CLINT0_HANDLE;
#else
@@ -830,14 +698,12 @@ __metal_driver_cpu_timer_controller_interrupt(struct metal_cpu *cpu)
#endif
}
-int __metal_driver_cpu_get_timer_interrupt_id(struct metal_cpu *cpu)
-{
+int __metal_driver_cpu_get_timer_interrupt_id(struct metal_cpu *cpu) {
return METAL_INTERRUPT_ID_TMR;
}
struct metal_interrupt *
-__metal_driver_cpu_sw_controller_interrupt(struct metal_cpu *cpu)
-{
+__metal_driver_cpu_sw_controller_interrupt(struct metal_cpu *cpu) {
#ifdef __METAL_DT_RISCV_CLINT0_HANDLE
return __METAL_DT_RISCV_CLINT0_HANDLE;
#else
@@ -850,142 +716,153 @@ __metal_driver_cpu_sw_controller_interrupt(struct metal_cpu *cpu)
#endif
}
-int __metal_driver_cpu_get_sw_interrupt_id(struct metal_cpu *cpu)
-{
+int __metal_driver_cpu_get_sw_interrupt_id(struct metal_cpu *cpu) {
return METAL_INTERRUPT_ID_SW;
}
-int __metal_driver_cpu_set_sw_ipi (struct metal_cpu *cpu, int hartid)
-{
+int __metal_driver_cpu_set_sw_ipi(struct metal_cpu *cpu, int hartid) {
int rc = -1;
struct metal_interrupt *sw_intc;
- struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ struct __metal_driver_riscv_cpu_intc *intc =
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
sw_intc = intc->metal_int_table[METAL_INTERRUPT_ID_SW].sub_int;
if (sw_intc) {
- rc = sw_intc->vtable->command_request(sw_intc,
- METAL_SOFTWARE_IPI_SET, &hartid);
+ rc = sw_intc->vtable->command_request(
+ sw_intc, METAL_SOFTWARE_IPI_SET, &hartid);
}
}
return rc;
}
-int __metal_driver_cpu_clear_sw_ipi (struct metal_cpu *cpu, int hartid)
-{
+int __metal_driver_cpu_clear_sw_ipi(struct metal_cpu *cpu, int hartid) {
int rc = -1;
struct metal_interrupt *sw_intc;
struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
sw_intc = intc->metal_int_table[METAL_INTERRUPT_ID_SW].sub_int;
if (sw_intc) {
- rc = sw_intc->vtable->command_request(sw_intc,
- METAL_SOFTWARE_IPI_CLEAR, &hartid);
+ rc = sw_intc->vtable->command_request(
+ sw_intc, METAL_SOFTWARE_IPI_CLEAR, &hartid);
}
}
return rc;
}
-int __metal_driver_cpu_get_msip (struct metal_cpu *cpu, int hartid)
-{
+int __metal_driver_cpu_get_msip(struct metal_cpu *cpu, int hartid) {
int rc = 0;
struct metal_interrupt *sw_intc;
struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
sw_intc = intc->metal_int_table[METAL_INTERRUPT_ID_SW].sub_int;
if (sw_intc) {
- rc = sw_intc->vtable->command_request(sw_intc,
- METAL_SOFTWARE_MSIP_GET, &hartid);
+ rc = sw_intc->vtable->command_request(
+ sw_intc, METAL_SOFTWARE_MSIP_GET, &hartid);
}
}
return rc;
}
struct metal_interrupt *
-__metal_driver_cpu_controller_interrupt(struct metal_cpu *cpu)
-{
+__metal_driver_cpu_controller_interrupt(struct metal_cpu *cpu) {
return __metal_driver_cpu_interrupt_controller(cpu);
}
-int __metal_driver_cpu_enable_interrupt(struct metal_cpu *cpu, void *priv)
-{
- if ( __metal_driver_cpu_interrupt_controller(cpu) ) {
+int __metal_driver_cpu_enable_interrupt(struct metal_cpu *cpu, void *priv) {
+ if (__metal_driver_cpu_interrupt_controller(cpu)) {
/* Only support machine mode for now */
__metal_interrupt_global_enable();
- return 0;
+ return 0;
}
return -1;
}
-int __metal_driver_cpu_disable_interrupt(struct metal_cpu *cpu, void *priv)
-{
- if ( __metal_driver_cpu_interrupt_controller(cpu) ) {
+int __metal_driver_cpu_disable_interrupt(struct metal_cpu *cpu, void *priv) {
+ if (__metal_driver_cpu_interrupt_controller(cpu)) {
/* Only support machine mode for now */
__metal_interrupt_global_disable();
- return 0;
+ return 0;
}
return -1;
}
int __metal_driver_cpu_exception_register(struct metal_cpu *cpu, int ecode,
- metal_exception_handler_t isr)
-{
+ metal_exception_handler_t isr) {
struct __metal_driver_riscv_cpu_intc *intc =
- (struct __metal_driver_riscv_cpu_intc *)__metal_driver_cpu_interrupt_controller(cpu);
+ (struct __metal_driver_riscv_cpu_intc *)
+ __metal_driver_cpu_interrupt_controller(cpu);
if (intc) {
- return __metal_exception_register((struct metal_interrupt *)intc, ecode, isr);
+ return __metal_exception_register((struct metal_interrupt *)intc, ecode,
+ isr);
}
return -1;
}
-int __metal_driver_cpu_get_instruction_length(struct metal_cpu *cpu, uintptr_t epc)
-{
+int __metal_driver_cpu_get_instruction_length(struct metal_cpu *cpu,
+ uintptr_t epc) {
/**
* Per ISA compressed instruction has last two bits of opcode set.
* The encoding '00' '01' '10' are used for compressed instruction.
* Only enconding '11' isn't regarded as compressed instruction (>16b).
*/
- return ((*(unsigned short*)epc & METAL_INSN_LENGTH_MASK)
- == METAL_INSN_NOT_COMPRESSED) ? 4 : 2;
+ return ((*(unsigned short *)epc & METAL_INSN_LENGTH_MASK) ==
+ METAL_INSN_NOT_COMPRESSED)
+ ? 4
+ : 2;
}
-uintptr_t __metal_driver_cpu_get_exception_pc(struct metal_cpu *cpu)
-{
+uintptr_t __metal_driver_cpu_get_exception_pc(struct metal_cpu *cpu) {
uintptr_t mepc;
- __asm__ volatile ("csrr %0, mepc" : "=r"(mepc));
+ __asm__ volatile("csrr %0, mepc" : "=r"(mepc));
return mepc;
}
-int __metal_driver_cpu_set_exception_pc(struct metal_cpu *cpu, uintptr_t mepc)
-{
- __asm__ volatile ("csrw mepc, %0" :: "r"(mepc));
+int __metal_driver_cpu_set_exception_pc(struct metal_cpu *cpu, uintptr_t mepc) {
+ __asm__ volatile("csrw mepc, %0" ::"r"(mepc));
return 0;
}
+struct metal_buserror *__metal_driver_cpu_get_buserror(struct metal_cpu *cpu) {
+ return __metal_driver_cpu_buserror(cpu);
+}
+
__METAL_DEFINE_VTABLE(__metal_driver_vtable_riscv_cpu_intc) = {
- .controller_vtable.interrupt_init = __metal_driver_riscv_cpu_controller_interrupt_init,
- .controller_vtable.interrupt_register = __metal_driver_riscv_cpu_controller_interrupt_register,
- .controller_vtable.interrupt_enable = __metal_driver_riscv_cpu_controller_interrupt_enable,
- .controller_vtable.interrupt_disable = __metal_driver_riscv_cpu_controller_interrupt_disable,
- .controller_vtable.interrupt_get_vector_mode = __metal_driver_riscv_cpu_controller_get_vector_mode,
- .controller_vtable.interrupt_set_vector_mode = __metal_driver_riscv_cpu_controller_set_vector_mode,
- .controller_vtable.command_request = __metal_driver_riscv_cpu_controller_command_request,
+ .controller_vtable.interrupt_init =
+ __metal_driver_riscv_cpu_controller_interrupt_init,
+ .controller_vtable.interrupt_register =
+ __metal_driver_riscv_cpu_controller_interrupt_register,
+ .controller_vtable.interrupt_enable =
+ __metal_driver_riscv_cpu_controller_interrupt_enable,
+ .controller_vtable.interrupt_disable =
+ __metal_driver_riscv_cpu_controller_interrupt_disable,
+ .controller_vtable.interrupt_get_vector_mode =
+ __metal_driver_riscv_cpu_controller_get_vector_mode,
+ .controller_vtable.interrupt_set_vector_mode =
+ __metal_driver_riscv_cpu_controller_set_vector_mode,
+ .controller_vtable.command_request =
+ __metal_driver_riscv_cpu_controller_command_request,
};
__METAL_DEFINE_VTABLE(__metal_driver_vtable_cpu) = {
- .cpu_vtable.mcycle_get = __metal_driver_cpu_mcycle_get,
- .cpu_vtable.timebase_get = __metal_driver_cpu_timebase_get,
+ .cpu_vtable.mcycle_get = __metal_driver_cpu_mcycle_get,
+ .cpu_vtable.timebase_get = __metal_driver_cpu_timebase_get,
.cpu_vtable.mtime_get = __metal_driver_cpu_mtime_get,
.cpu_vtable.mtimecmp_set = __metal_driver_cpu_mtimecmp_set,
- .cpu_vtable.tmr_controller_interrupt = __metal_driver_cpu_timer_controller_interrupt,
- .cpu_vtable.get_tmr_interrupt_id = __metal_driver_cpu_get_timer_interrupt_id,
- .cpu_vtable.sw_controller_interrupt = __metal_driver_cpu_sw_controller_interrupt,
+ .cpu_vtable.tmr_controller_interrupt =
+ __metal_driver_cpu_timer_controller_interrupt,
+ .cpu_vtable.get_tmr_interrupt_id =
+ __metal_driver_cpu_get_timer_interrupt_id,
+ .cpu_vtable.sw_controller_interrupt =
+ __metal_driver_cpu_sw_controller_interrupt,
.cpu_vtable.get_sw_interrupt_id = __metal_driver_cpu_get_sw_interrupt_id,
.cpu_vtable.set_sw_ipi = __metal_driver_cpu_set_sw_ipi,
.cpu_vtable.clear_sw_ipi = __metal_driver_cpu_clear_sw_ipi,
@@ -995,5 +872,5 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_cpu) = {
.cpu_vtable.get_ilen = __metal_driver_cpu_get_instruction_length,
.cpu_vtable.get_epc = __metal_driver_cpu_get_exception_pc,
.cpu_vtable.set_epc = __metal_driver_cpu_set_exception_pc,
+ .cpu_vtable.get_buserror = __metal_driver_cpu_get_buserror,
};
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_plic0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_plic0.c
index 3272f1c66..21d16ab1c 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_plic0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/riscv_plic0.c
@@ -5,189 +5,308 @@
#ifdef METAL_RISCV_PLIC0
-#include <metal/io.h>
-#include <metal/shutdown.h>
+#define PLIC0_MAX_INTERRUPTS 1024
+
#include <metal/drivers/riscv_plic0.h>
+#include <metal/interrupt.h>
+#include <metal/io.h>
#include <metal/machine.h>
+#include <metal/shutdown.h>
-unsigned int __metal_plic0_claim_interrupt (struct __metal_driver_riscv_plic0 *plic)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base((struct metal_interrupt *)plic);
- return __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_CLAIM));
+unsigned int
+__metal_plic0_claim_interrupt(struct __metal_driver_riscv_plic0 *plic,
+ int context_id) {
+ unsigned long control_base = __metal_driver_sifive_plic0_control_base(
+ (struct metal_interrupt *)plic);
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_CONTEXT_BASE +
+ (context_id * METAL_RISCV_PLIC0_CONTEXT_PER_HART) +
+ METAL_RISCV_PLIC0_CONTEXT_CLAIM));
}
void __metal_plic0_complete_interrupt(struct __metal_driver_riscv_plic0 *plic,
- unsigned int id)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base((struct metal_interrupt *)plic);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_CLAIM)) = id;
-}
-
-int __metal_plic0_set_threshold(struct metal_interrupt *controller, unsigned int threshold)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base(controller);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_THRESHOLD)) = threshold;
- return 0;
+ int context_id, unsigned int id) {
+ unsigned long control_base = __metal_driver_sifive_plic0_control_base(
+ (struct metal_interrupt *)plic);
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_CONTEXT_BASE +
+ (context_id * METAL_RISCV_PLIC0_CONTEXT_PER_HART) +
+ METAL_RISCV_PLIC0_CONTEXT_CLAIM)) = id;
}
-unsigned int __metal_plic0_get_threshold(struct metal_interrupt *controller)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base(controller);
+int __metal_plic0_set_threshold(struct metal_interrupt *controller,
+ int context_id, unsigned int threshold) {
+ unsigned long control_base =
+ __metal_driver_sifive_plic0_control_base(controller);
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_CONTEXT_BASE +
+ (context_id * METAL_RISCV_PLIC0_CONTEXT_PER_HART) +
+ METAL_RISCV_PLIC0_CONTEXT_THRESHOLD)) = threshold;
+ return 0;
+}
- return __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_THRESHOLD));
+unsigned int __metal_plic0_get_threshold(struct metal_interrupt *controller,
+ int context_id) {
+ unsigned long control_base =
+ __metal_driver_sifive_plic0_control_base(controller);
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_CONTEXT_BASE +
+ (context_id * METAL_RISCV_PLIC0_CONTEXT_PER_HART) +
+ METAL_RISCV_PLIC0_CONTEXT_THRESHOLD));
}
-int __metal_plic0_set_priority(struct metal_interrupt *controller, int id, unsigned int priority)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base((struct metal_interrupt *)controller);
- unsigned int max_priority = __metal_driver_sifive_plic0_max_priority((struct metal_interrupt *)controller);
- if ( (max_priority) && (priority < max_priority) ) {
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_PRIORITY_BASE +
- (id << METAL_PLIC_SOURCE_PRIORITY_SHIFT))) = priority;
+int __metal_driver_riscv_plic0_set_priority(struct metal_interrupt *controller,
+ int id, unsigned int priority) {
+ unsigned long control_base = __metal_driver_sifive_plic0_control_base(
+ (struct metal_interrupt *)controller);
+ unsigned int max_priority = __metal_driver_sifive_plic0_max_priority(
+ (struct metal_interrupt *)controller);
+ if ((max_priority) && (priority < max_priority)) {
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_PRIORITY_BASE +
+ (id << METAL_PLIC_SOURCE_PRIORITY_SHIFT))) =
+ priority;
return 0;
}
return -1;
}
-unsigned int __metal_plic0_get_priority(struct metal_interrupt *controller, int id)
-{
- unsigned long control_base = __metal_driver_sifive_plic0_control_base(controller);
+unsigned int
+__metal_driver_riscv_plic0_get_priority(struct metal_interrupt *controller,
+ int id) {
+ unsigned long control_base =
+ __metal_driver_sifive_plic0_control_base(controller);
- return __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_PRIORITY_BASE +
- (id << METAL_PLIC_SOURCE_PRIORITY_SHIFT)));
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_PRIORITY_BASE +
+ (id << METAL_PLIC_SOURCE_PRIORITY_SHIFT)));
}
-void __metal_plic0_enable(struct __metal_driver_riscv_plic0 *plic, int id, int enable)
-{
+int __metal_plic0_enable(struct __metal_driver_riscv_plic0 *plic,
+ int context_id, int id, int enable) {
unsigned int current;
- unsigned long control_base = __metal_driver_sifive_plic0_control_base((struct metal_interrupt *)plic);
+ unsigned long control_base = __metal_driver_sifive_plic0_control_base(
+ (struct metal_interrupt *)plic);
+
+ current = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_ENABLE_BASE +
+ (context_id * METAL_RISCV_PLIC0_ENABLE_PER_HART) +
+ (id >> METAL_PLIC_SOURCE_SHIFT) * 4));
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_RISCV_PLIC0_ENABLE_BASE +
+ (context_id * METAL_RISCV_PLIC0_ENABLE_PER_HART) +
+ ((id >> METAL_PLIC_SOURCE_SHIFT) * 4))) =
+ enable ? (current | (1 << (id & METAL_PLIC_SOURCE_MASK)))
+ : (current & ~(1 << (id & METAL_PLIC_SOURCE_MASK)));
- current = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_ENABLE_BASE +
- (id >> METAL_PLIC_SOURCE_SHIFT) * 4));
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- METAL_RISCV_PLIC0_ENABLE_BASE +
- ((id >> METAL_PLIC_SOURCE_SHIFT) * 4))) =
- enable ? (current | (1 << (id & METAL_PLIC_SOURCE_MASK)))
- : (current & ~(1 << (id & METAL_PLIC_SOURCE_MASK)));
+ return 0;
}
-void __metal_plic0_default_handler (int id, void *priv) {
- metal_shutdown(300);
-}
+void __metal_plic0_default_handler(int id, void *priv) { metal_shutdown(300); }
-void __metal_plic0_handler (int id, void *priv)
-{
+void __metal_plic0_handler(int id, void *priv) {
struct __metal_driver_riscv_plic0 *plic = priv;
- unsigned int idx = __metal_plic0_claim_interrupt(plic);
- unsigned int num_interrupts = __metal_driver_sifive_plic0_num_interrupts((struct metal_interrupt *)plic);
-
- if ( (idx < num_interrupts) && (plic->metal_exint_table[idx]) ) {
- plic->metal_exint_table[idx](idx,
- plic->metal_exdata_table[idx].exint_data);
+ int contextid =
+ __metal_driver_sifive_plic0_context_ids(__metal_myhart_id());
+ unsigned int idx = __metal_plic0_claim_interrupt(plic, contextid);
+ unsigned int num_interrupts = __metal_driver_sifive_plic0_num_interrupts(
+ (struct metal_interrupt *)plic);
+
+ if ((idx < num_interrupts) && (plic->metal_exint_table[idx])) {
+ plic->metal_exint_table[idx](idx,
+ plic->metal_exdata_table[idx].exint_data);
}
- __metal_plic0_complete_interrupt(plic, idx);
+ __metal_plic0_complete_interrupt(plic, contextid, idx);
}
-void __metal_driver_riscv_plic0_init (struct metal_interrupt *controller)
-{
+void __metal_driver_riscv_plic0_init(struct metal_interrupt *controller) {
struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
- if ( !plic->init_done ) {
+ if (!plic->init_done) {
int num_interrupts, line;
struct metal_interrupt *intc;
- for(int parent = 0; parent < __METAL_PLIC_NUM_PARENTS; parent++) {
- num_interrupts = __metal_driver_sifive_plic0_num_interrupts(controller);
- intc = __metal_driver_sifive_plic0_interrupt_parents(controller, parent);
- line = __metal_driver_sifive_plic0_interrupt_lines(controller, parent);
-
- /* Initialize ist parent controller, aka cpu_intc. */
- intc->vtable->interrupt_init(intc);
-
- for (int i = 0; i < num_interrupts; i++) {
- __metal_plic0_enable(plic, i, METAL_DISABLE);
- __metal_plic0_set_priority(controller, i, 0);
- plic->metal_exint_table[i] = NULL;
- plic->metal_exdata_table[i].sub_int = NULL;
- plic->metal_exdata_table[i].exint_data = NULL;
- }
-
- __metal_plic0_set_threshold(controller, 0);
-
- /* Register plic (ext) interrupt with with parent controller */
- intc->vtable->interrupt_register(intc, line, NULL, plic);
- /* Register plic handler for dispatching its device interrupts */
- intc->vtable->interrupt_register(intc, line, __metal_plic0_handler, plic);
- /* Enable plic (ext) interrupt with with parent controller */
- intc->vtable->interrupt_enable(intc, line);
- }
+ for (int parent = 0; parent < __METAL_PLIC_NUM_PARENTS; parent++) {
+ num_interrupts =
+ __metal_driver_sifive_plic0_num_interrupts(controller);
+ intc = __metal_driver_sifive_plic0_interrupt_parents(controller,
+ parent);
+ line =
+ __metal_driver_sifive_plic0_interrupt_lines(controller, parent);
+
+ /* Initialize ist parent controller, aka cpu_intc. */
+ intc->vtable->interrupt_init(intc);
+
+ for (int i = 0; i < PLIC0_MAX_INTERRUPTS; i++) {
+ __metal_plic0_enable(plic, parent, i, METAL_DISABLE);
+ if (i < num_interrupts) {
+ __metal_driver_riscv_plic0_set_priority(controller, i, 0);
+ plic->metal_exint_table[i] = NULL;
+ plic->metal_exdata_table[i].sub_int = NULL;
+ plic->metal_exdata_table[i].exint_data = NULL;
+ }
+ }
+
+ __metal_plic0_set_threshold(controller, parent, 0);
+
+ /* Register plic (ext) interrupt with with parent controller */
+ intc->vtable->interrupt_register(intc, line, NULL, plic);
+ /* Register plic handler for dispatching its device interrupts */
+ intc->vtable->interrupt_register(intc, line, __metal_plic0_handler,
+ plic);
+ /* Enable plic (ext) interrupt with with parent controller */
+ intc->vtable->interrupt_enable(intc, line);
+ }
plic->init_done = 1;
}
}
-int __metal_driver_riscv_plic0_register (struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_riscv_plic0_register(struct metal_interrupt *controller,
+ int id, metal_interrupt_handler_t isr,
+ void *priv) {
struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
if (id >= __metal_driver_sifive_plic0_num_interrupts(controller)) {
return -1;
}
-
+
if (isr) {
- __metal_plic0_set_priority(controller, id, 2);
- plic->metal_exint_table[id] = isr;
- plic->metal_exdata_table[id].exint_data = priv;
+ __metal_driver_riscv_plic0_set_priority(controller, id, 2);
+ plic->metal_exint_table[id] = isr;
+ plic->metal_exdata_table[id].exint_data = priv;
} else {
- __metal_plic0_set_priority(controller, id, 1);
- plic->metal_exint_table[id] = __metal_plic0_default_handler;
- plic->metal_exdata_table[id].sub_int = priv;
+ __metal_driver_riscv_plic0_set_priority(controller, id, 1);
+ plic->metal_exint_table[id] = __metal_plic0_default_handler;
+ plic->metal_exdata_table[id].sub_int = priv;
}
return 0;
}
-int __metal_driver_riscv_plic0_enable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_plic0_enable(struct metal_interrupt *controller,
+ int id) {
struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
if (id >= __metal_driver_sifive_plic0_num_interrupts(controller)) {
return -1;
}
- __metal_plic0_enable(plic, id, METAL_ENABLE);
+ __metal_plic0_enable(plic, __metal_myhart_id(), id, METAL_ENABLE);
return 0;
}
-int __metal_driver_riscv_plic0_disable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_riscv_plic0_disable(struct metal_interrupt *controller,
+ int id) {
struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
if (id >= __metal_driver_sifive_plic0_num_interrupts(controller)) {
return -1;
}
- __metal_plic0_enable(plic, id, METAL_DISABLE);
+ __metal_plic0_enable(plic, __metal_myhart_id(), id, METAL_DISABLE);
+ return 0;
+}
+
+int __metal_driver_riscv_plic0_set_threshold(struct metal_interrupt *controller,
+ unsigned int threshold) {
+ return __metal_plic0_set_threshold(controller, __metal_myhart_id(),
+ threshold);
+}
+
+unsigned int
+__metal_driver_riscv_plic0_get_threshold(struct metal_interrupt *controller) {
+ return __metal_plic0_get_threshold(controller, __metal_myhart_id());
+}
+
+metal_affinity
+__metal_driver_riscv_plic0_affinity_enable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ metal_affinity ret = {0};
+ int context;
+
+ struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
+
+ if (id >= __metal_driver_sifive_plic0_num_interrupts(controller)) {
+ metal_affinity_set_val(ret, -1);
+ return ret;
+ }
+
+ for_each_metal_affinity(context, bitmask) {
+ if (context != 0)
+ metal_affinity_set_bit(
+ ret, context,
+ __metal_plic0_enable(plic, context, id, METAL_ENABLE));
+ }
+
+ return ret;
+}
+
+metal_affinity
+__metal_driver_riscv_plic0_affinity_disable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id) {
+ metal_affinity ret = {0};
+ int context;
+
+ struct __metal_driver_riscv_plic0 *plic = (void *)(controller);
+
+ if (id >= __metal_driver_sifive_plic0_num_interrupts(controller)) {
+ metal_affinity_set_val(ret, -1);
+ return ret;
+ }
+
+ for_each_metal_affinity(context, bitmask) {
+ if (context != 0)
+ metal_affinity_set_bit(
+ ret, context,
+ __metal_plic0_enable(plic, context, id, METAL_DISABLE));
+ }
+
+ return ret;
+}
+
+metal_affinity __metal_driver_riscv_plic0_affinity_set_threshold(
+ struct metal_interrupt *controller, metal_affinity bitmask,
+ unsigned int threshold) {
+ metal_affinity ret = {0};
+ int context;
+
+ for_each_metal_affinity(context, bitmask) {
+ if (context != 0)
+ metal_affinity_set_bit(
+ ret, context,
+ __metal_plic0_set_threshold(controller, context, threshold));
+ }
+
+ return ret;
+}
+
+unsigned int __metal_driver_riscv_plic0_affinity_get_threshold(
+ struct metal_interrupt *controller, int context_id) {
+ __metal_plic0_get_threshold(controller, context_id);
return 0;
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_riscv_plic0) = {
.plic_vtable.interrupt_init = __metal_driver_riscv_plic0_init,
.plic_vtable.interrupt_register = __metal_driver_riscv_plic0_register,
- .plic_vtable.interrupt_enable = __metal_driver_riscv_plic0_enable,
- .plic_vtable.interrupt_disable = __metal_driver_riscv_plic0_disable,
- .plic_vtable.interrupt_get_threshold = __metal_plic0_get_threshold,
- .plic_vtable.interrupt_set_threshold = __metal_plic0_set_threshold,
- .plic_vtable.interrupt_get_priority = __metal_plic0_get_priority,
- .plic_vtable.interrupt_set_priority = __metal_plic0_set_priority,
+ .plic_vtable.interrupt_enable = __metal_driver_riscv_plic0_enable,
+ .plic_vtable.interrupt_disable = __metal_driver_riscv_plic0_disable,
+ .plic_vtable.interrupt_get_threshold =
+ __metal_driver_riscv_plic0_get_threshold,
+ .plic_vtable.interrupt_set_threshold =
+ __metal_driver_riscv_plic0_set_threshold,
+ .plic_vtable.interrupt_get_priority =
+ __metal_driver_riscv_plic0_get_priority,
+ .plic_vtable.interrupt_set_priority =
+ __metal_driver_riscv_plic0_set_priority,
+ .plic_vtable.interrupt_affinity_enable =
+ __metal_driver_riscv_plic0_affinity_enable,
+ .plic_vtable.interrupt_affinity_disable =
+ __metal_driver_riscv_plic0_affinity_disable,
+ .plic_vtable.interrupt_affinity_get_threshold =
+ __metal_driver_riscv_plic0_affinity_get_threshold,
+ .plic_vtable.interrupt_affinity_set_threshold =
+ __metal_driver_riscv_plic0_affinity_set_threshold,
};
#endif /* METAL_RISCV_PLIC0 */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_buserror0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_buserror0.c
new file mode 100644
index 000000000..3a68fef44
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_buserror0.c
@@ -0,0 +1,257 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/drivers/sifive_buserror0.h>
+#include <metal/machine/platform.h>
+#include <stddef.h>
+#include <stdint.h>
+
+#ifdef METAL_SIFIVE_BUSERROR0
+
+#include <metal/cpu.h>
+#include <metal/init.h>
+#include <metal/io.h>
+#include <metal/machine.h>
+
+/* Enable all events on all hart bus error units */
+METAL_CONSTRUCTOR(metal_driver_sifive_buserror_init) {
+ for (int hart = 0; hart < metal_cpu_get_num_harts(); hart++) {
+ struct metal_cpu *cpu = metal_cpu_get(hart);
+ if (cpu != NULL) {
+ struct metal_buserror *beu = metal_cpu_get_buserror(cpu);
+ if (beu != NULL) {
+ metal_buserror_set_event_enabled(beu, METAL_BUSERROR_EVENT_ALL,
+ true);
+ }
+ }
+ }
+}
+
+int metal_buserror_set_event_enabled(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return 1;
+ }
+ if (!(events & METAL_BUSERROR_EVENT_ANY)) {
+ return 2;
+ }
+
+ uintptr_t reg_enable = base + METAL_SIFIVE_BUSERROR0_ENABLE;
+
+ if (enabled) {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)reg_enable) |= events;
+ } else {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)reg_enable) &= ~events;
+ }
+
+ if (!(events & __METAL_ACCESS_ONCE((__metal_io_u8 *)reg_enable))) {
+ return __METAL_ACCESS_ONCE((__metal_io_u8 *)reg_enable);
+ }
+
+ return 0;
+}
+
+metal_buserror_event_t
+metal_buserror_get_event_enabled(struct metal_buserror *beu) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return 1;
+ }
+
+ uintptr_t reg_enable = base + METAL_SIFIVE_BUSERROR0_ENABLE;
+
+ return __METAL_ACCESS_ONCE((__metal_io_u8 *)reg_enable);
+}
+
+int metal_buserror_set_platform_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return 1;
+ }
+ if (!(events & METAL_BUSERROR_EVENT_ANY)) {
+ return 2;
+ }
+
+ uintptr_t platform_interrupt =
+ base + METAL_SIFIVE_BUSERROR0_PLATFORM_INTERRUPT;
+
+ if (enabled) {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)platform_interrupt) |= events;
+ } else {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)platform_interrupt) &= ~events;
+ }
+
+ return 0;
+}
+
+int metal_buserror_set_local_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t events,
+ bool enabled) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return 1;
+ }
+ if (!(events & METAL_BUSERROR_EVENT_ANY)) {
+ return 2;
+ }
+
+ uintptr_t local_interrupt = base + METAL_SIFIVE_BUSERROR0_LOCAL_INTERRUPT;
+
+ if (enabled) {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)local_interrupt) |= events;
+ } else {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)local_interrupt) &= ~events;
+ }
+
+ return 0;
+}
+
+metal_buserror_event_t metal_buserror_get_cause(struct metal_buserror *beu) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return METAL_BUSERROR_EVENT_INVALID;
+ }
+
+ uintptr_t cause = base + METAL_SIFIVE_BUSERROR0_CAUSE;
+
+ return (metal_buserror_event_t)(
+ 1 << __METAL_ACCESS_ONCE((__metal_io_u8 *)cause));
+}
+
+int metal_buserror_clear_cause(struct metal_buserror *beu) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ /* We return (1 << 8) because the value of the cause register
+ * can never equal that value */
+ return (1 << 8);
+ }
+
+ uintptr_t cause = base + METAL_SIFIVE_BUSERROR0_CAUSE;
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)cause) = METAL_BUSERROR_EVENT_NONE;
+
+ return __METAL_ACCESS_ONCE((__metal_io_u8 *)cause);
+}
+
+uintptr_t metal_buserror_get_event_address(struct metal_buserror *beu) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return 0;
+ }
+
+ uintptr_t value = base + METAL_SIFIVE_BUSERROR0_VALUE;
+
+ return __METAL_ACCESS_ONCE((__metal_io_u8 *)value);
+}
+
+bool metal_buserror_is_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ return false;
+ }
+
+ uintptr_t accrued = base + METAL_SIFIVE_BUSERROR0_ACCRUED;
+
+ if (!(events & METAL_BUSERROR_EVENT_ANY)) {
+ return false;
+ }
+
+ return !!(events & __METAL_ACCESS_ONCE((__metal_io_u8 *)accrued));
+}
+
+int metal_buserror_clear_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t events) {
+ uintptr_t base = __metal_driver_sifive_buserror0_control_base(beu);
+ if (base == (uintptr_t)NULL) {
+ /* We return (1 << 8) because the value of the accrued register
+ * can never equal that value */
+ return (1 << 8);
+ }
+
+ uintptr_t accrued = base + METAL_SIFIVE_BUSERROR0_ACCRUED;
+
+ if (!(events & METAL_BUSERROR_EVENT_ANY)) {
+ /* We return (1 << 9) because the value of the accrued register
+ * can never equal that value */
+ return (1 << 9);
+ } else {
+ __METAL_ACCESS_ONCE((__metal_io_u8 *)accrued) &= ~events;
+ if (events & __METAL_ACCESS_ONCE((__metal_io_u8 *)accrued)) {
+ return __METAL_ACCESS_ONCE((__metal_io_u8 *)accrued);
+ }
+ }
+
+ return 0;
+}
+
+struct metal_interrupt *
+metal_buserror_get_platform_interrupt_parent(struct metal_buserror *beu) {
+ return __metal_driver_sifive_buserror0_interrupt_parent(beu);
+}
+
+int metal_buserror_get_platform_interrupt_id(struct metal_buserror *beu) {
+ return __metal_driver_sifive_buserror0_interrupt_id(beu);
+}
+
+int metal_buserror_get_local_interrupt_id(struct metal_buserror *beu) {
+ return 128;
+}
+
+#else
+
+int metal_buserror_set_event_enabled(struct metal_buserror *beu,
+ metal_buserror_event_t event,
+ bool enabled) {
+ return 1;
+}
+
+int metal_buserror_set_platform_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t event,
+ bool enabled) {
+ return 1;
+}
+
+int metal_buserror_set_local_interrupt(struct metal_buserror *beu,
+ metal_buserror_event_t event,
+ bool enabled) {
+ return 1;
+}
+
+metal_buserror_event_t metal_buserror_get_cause(struct metal_buserror *beu) {
+ return METAL_BUSERROR_EVENT_INVALID;
+}
+
+int metal_buserror_clear_cause(struct metal_buserror *beu) { return (1 << 9); }
+
+uintptr_t metal_buserror_get_event_address(struct metal_buserror *beu) {
+ return 0;
+}
+
+bool metal_buserror_is_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t event) {
+ return false;
+}
+
+int metal_buserror_clear_event_accrued(struct metal_buserror *beu,
+ metal_buserror_event_t event) {
+ return (1 << 8);
+}
+
+struct metal_interrupt *
+metal_buserror_get_platform_interrupt_parent(struct metal_buserror *beu) {
+ return NULL;
+}
+
+int metal_buserror_get_platform_interrupt_id(struct metal_buserror *beu) {
+ return 0;
+}
+
+int metal_buserror_get_local_interrupt_id(struct metal_buserror *beu) {
+ return 0;
+}
+
+#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_ccache0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_ccache0.c
index 6f8723735..76aeb25cc 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_ccache0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_ccache0.c
@@ -1,83 +1,311 @@
-/* Copyright 2019 SiFive, Inc */
+/* Copyright 2020 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
#include <metal/machine/platform.h>
#ifdef METAL_SIFIVE_CCACHE0
-#include <stdint.h>
-#include <metal/io.h>
#include <metal/drivers/sifive_ccache0.h>
+#include <metal/init.h>
#include <metal/machine.h>
+#include <stdint.h>
+
+/* Macros to access memory mapped registers */
+#define REGW(x) *(volatile uint32_t *)(METAL_SIFIVE_CCACHE0_0_BASE_ADDRESS + x)
+
+#define REGD(x) *(volatile uint64_t *)(METAL_SIFIVE_CCACHE0_0_BASE_ADDRESS + x)
+
+/* Macros to specify register bit shift */
+#define REG_SHIFT_4 4
+#define REG_SHIFT_8 8
+#define REG_SHIFT_16 16
+#define REG_SHIFT_24 24
+
+#define SIFIVE_CCACHE0_BYTE_MASK 0xFFUL
-#define L2_CONFIG_WAYS_SHIFT 8
-#define L2_CONFIG_WAYS_MASK (0xFF << L2_CONFIG_WAYS_SHIFT)
+static int sifive_ccache0_interrupts[] = METAL_SIFIVE_CCACHE0_INTERRUPTS;
-void __metal_driver_sifive_ccache0_init(struct metal_cache *l2, int ways);
+/* Initialize cache at start-up via metal constructors */
+METAL_CONSTRUCTOR(_sifive_ccache0_init) { sifive_ccache0_init(); }
-static void metal_driver_sifive_ccache0_init(void) __attribute__((constructor));
-static void metal_driver_sifive_ccache0_init(void)
-{
-#ifdef __METAL_DT_SIFIVE_CCACHE0_HANDLE
- /* Get the handle for the L2 cache controller */
- struct metal_cache *l2 = __METAL_DT_SIFIVE_CCACHE0_HANDLE;
- if(!l2) {
- return;
+/* Linker symbols to calculate LIM allocated size */
+extern char metal_segment_lim_target_start, metal_segment_lim_target_end;
+
+int sifive_ccache0_init(void) {
+ int ret;
+
+ sifive_ccache0_config config;
+
+ /* Get cache configuration data */
+ sifive_ccache0_get_config(&config);
+
+ int lim_size =
+ &metal_segment_lim_target_end - &metal_segment_lim_target_start;
+
+ if (lim_size) { /* Do not enable cache ways, corresponding to LIM area in
+ use. */
+ while (lim_size > 0) {
+ lim_size -= (config.block_size * config.num_sets * config.num_bank);
+ config.num_ways--;
+ }
}
- /* Get the number of available ways per bank */
- unsigned long control_base = __metal_driver_sifive_ccache0_control_base(l2);
- uint32_t ways = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CCACHE0_CONFIG));
- ways = ((ways & L2_CONFIG_WAYS_MASK) >> L2_CONFIG_WAYS_SHIFT);
+ /* Enable ways */
+ ret = sifive_ccache0_set_enabled_ways(config.num_ways);
- /* Enable all the ways */
- __metal_driver_sifive_ccache0_init(l2, ways);
-#endif
+ return ret;
}
-void __metal_driver_sifive_ccache0_init(struct metal_cache *l2, int ways)
-{
- metal_cache_set_enabled_ways(l2, ways);
+void sifive_ccache0_get_config(sifive_ccache0_config *config) {
+ uint32_t val;
+
+ if (config) /* Check for NULL */
+ {
+ val = REGW(METAL_SIFIVE_CCACHE0_CONFIG);
+
+ /* Populate cache configuration data */
+ config->num_bank = (val & SIFIVE_CCACHE0_BYTE_MASK);
+ config->num_ways = ((val >> REG_SHIFT_8) & SIFIVE_CCACHE0_BYTE_MASK);
+ config->num_sets =
+ 2 << (((val >> REG_SHIFT_16) & SIFIVE_CCACHE0_BYTE_MASK) - 1);
+ config->block_size =
+ 2 << (((val >> REG_SHIFT_24) & SIFIVE_CCACHE0_BYTE_MASK) - 1);
+ }
}
-int __metal_driver_sifive_ccache0_get_enabled_ways(struct metal_cache *cache)
-{
- unsigned long control_base = __metal_driver_sifive_ccache0_control_base(cache);
+uint32_t sifive_ccache0_get_enabled_ways(void) {
- uint32_t way_enable = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CCACHE0_WAYENABLE));
+ uint32_t val = 0;
- /* The stored number is the index, so add one */
- return (0xFF & way_enable) + 1;
+ val = SIFIVE_CCACHE0_BYTE_MASK & REGW(METAL_SIFIVE_CCACHE0_WAYENABLE);
+
+ /* The stored number is the way index, so increment by 1 */
+ val++;
+
+ return val;
}
-int __metal_driver_sifive_ccache0_set_enabled_ways(struct metal_cache *cache, int ways)
-{
- unsigned long control_base = __metal_driver_sifive_ccache0_control_base(cache);
+int sifive_ccache0_set_enabled_ways(uint32_t ways) {
+
+ int ret = 0;
/* We can't decrease the number of enabled ways */
- if(metal_cache_get_enabled_ways(cache) > ways) {
- return -2;
+ if (sifive_ccache0_get_enabled_ways() > ways) {
+ ret = -1;
+ } else {
+ /* The stored value is the index, so subtract one */
+ uint32_t value = 0xFF & (ways - 1);
+
+ /* Set the number of enabled ways */
+ REGW(METAL_SIFIVE_CCACHE0_WAYENABLE) = value;
+
+ /* Make sure the number of ways was set correctly */
+ if (sifive_ccache0_get_enabled_ways() != ways) {
+ ret = -2;
+ }
}
- /* The stored value is the index, so subtract one */
- uint32_t value = 0xFF & (ways - 1);
+ return ret;
+}
+
+void sifive_ccache0_inject_ecc_error(uint32_t bitindex,
+ sifive_ccache0_ecc_errtype_t type) {
+ /* Induce ECC error at given bit index and location */
+ REGW(METAL_SIFIVE_CCACHE0_ECCINJECTERROR) =
+ (uint32_t)(((type & 0x01) << REG_SHIFT_16) | (bitindex & 0xFF));
+}
+
+void sifive_ccache0_flush(uintptr_t flush_addr) {
+ /* Block memory access until operation completed */
+ __asm volatile("fence rw, io" : : : "memory");
+
+#if __riscv_xlen == 32
+ REGW(METAL_SIFIVE_CCACHE0_FLUSH32) = flush_addr >> REG_SHIFT_4;
+#else
+ REGD(METAL_SIFIVE_CCACHE0_FLUSH64) = flush_addr;
+#endif
+
+ __asm volatile("fence io, rw" : : : "memory");
+}
+
+uintptr_t sifive_ccache0_get_ecc_fix_addr(sifive_ccache0_ecc_errtype_t type) {
+ uintptr_t addr = 0;
+
+ switch (type) {
+ /* Get most recently ECC corrected address */
+ case SIFIVE_CCACHE0_DATA:
+ addr = (uintptr_t)REGD(METAL_SIFIVE_CCACHE0_DATECCFIXLOW);
+ break;
+
+ case SIFIVE_CCACHE0_DIR:
+ addr = (uintptr_t)REGD(METAL_SIFIVE_CCACHE0_DIRECCFIXLOW);
+ break;
+ }
+
+ return addr;
+}
+
+uint32_t sifive_ccache0_get_ecc_fix_count(sifive_ccache0_ecc_errtype_t type) {
+ uint32_t count = 0;
+
+ switch (type) {
+ /* Get number of times ECC errors were corrected */
+ case SIFIVE_CCACHE0_DATA:
+ count = REGW(METAL_SIFIVE_CCACHE0_DATECCFIXCOUNT);
+ break;
+
+ case SIFIVE_CCACHE0_DIR:
+ count = REGW(METAL_SIFIVE_CCACHE0_DIRECCFIXCOUNT);
+ break;
+ }
+
+ return count;
+}
+
+uintptr_t sifive_ccache0_get_ecc_fail_addr(sifive_ccache0_ecc_errtype_t type) {
+ uintptr_t addr = 0;
+
+ switch (type) {
+ /* Get address location of most recent uncorrected ECC error */
+ case SIFIVE_CCACHE0_DATA:
+ addr = (uintptr_t)REGD(METAL_SIFIVE_CCACHE0_DATECCFAILLOW);
+ break;
+
+ case SIFIVE_CCACHE0_DIR:
+ addr = (uintptr_t)REGD(METAL_SIFIVE_CCACHE0_DIRECCFAILLOW);
+ break;
+ }
+
+ return addr;
+}
+
+uint32_t sifive_ccache0_get_ecc_fail_count(sifive_ccache0_ecc_errtype_t type) {
+ uint32_t count = 0;
- /* Set the number of enabled ways */
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CCACHE0_WAYENABLE)) = value;
+ switch (type) {
+ /* Get number of times ECC errors were not corrected */
+ case SIFIVE_CCACHE0_DATA:
+ count = REGW(METAL_SIFIVE_CCACHE0_DATECCFAILCOUNT);
+ break;
- /* Make sure the number of ways was set correctly */
- if(metal_cache_get_enabled_ways(cache) != ways) {
- return -3;
+ case SIFIVE_CCACHE0_DIR:
+ count = REGW(METAL_SIFIVE_CCACHE0_DIRECCFAILCOUNT);
+ break;
}
+ return count;
+}
+
+uint64_t sifive_ccache0_get_way_mask(uint32_t master_id) {
+ uint64_t val = 0;
+
+ /* Get way mask for given master ID */
+ val = REGD(METAL_SIFIVE_CCACHE0_WAYMASK0 + master_id * 8);
+
+ return val;
+}
+
+int sifive_ccache0_set_way_mask(uint32_t master_id, uint64_t waymask) {
+
+ /* Set way mask for given master ID */
+ REGD(METAL_SIFIVE_CCACHE0_WAYMASK0 + master_id * 8) = waymask;
+
return 0;
}
-__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_ccache0) = {
- .cache.init = __metal_driver_sifive_ccache0_init,
- .cache.get_enabled_ways = __metal_driver_sifive_ccache0_get_enabled_ways,
- .cache.set_enabled_ways = __metal_driver_sifive_ccache0_set_enabled_ways,
-};
+void sifive_ccache0_set_pmevent_selector(uint32_t counter, uint64_t mask) {
+
+#if METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS > 0
+ if (counter < METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS) {
+
+ /* Set event selector for specified L2 event counter */
+ REGD(METAL_SIFIVE_CCACHE0_PMEVENTSELECT0 + counter * 8) = mask;
+ }
+#endif
+ return;
+}
+
+uint64_t sifive_ccache0_get_pmevent_selector(uint32_t counter) {
+ uint64_t val = 0;
+
+#if METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS > 0
+ if (counter < METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS) {
+
+ /* Get event selector for specified L2 event counter */
+ val = REGD(METAL_SIFIVE_CCACHE0_PMEVENTSELECT0 + counter * 8);
+ }
+#endif
+ return val;
+}
+
+void sifive_ccache0_clr_pmevent_counter(uint32_t counter) {
+
+#if METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS > 0
+ if (counter < METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS) {
+ /* Clear specified L2 event counter */
+ REGD(METAL_SIFIVE_CCACHE0_PMEVENTCOUNTER0 + counter * 8) = 0;
+ }
+#endif
+ return;
+}
+
+uint64_t sifive_ccache0_get_pmevent_counter(uint32_t counter) {
+#if __riscv_xlen == 32
+ uint32_t vh = 0, vh1 = 0, vl = 0;
+#else
+ uint64_t val = 0;
+#endif
+#if METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS > 0
+ if (counter < METAL_SIFIVE_CCACHE0_PERFMON_COUNTERS) {
+ /* Set counter register offset */
+ counter *= 8;
+
+#if __riscv_xlen == 32
+ do {
+ vh = REGW(METAL_SIFIVE_CCACHE0_PMEVENTCOUNTER0 + counter + 4);
+ vl = REGW(METAL_SIFIVE_CCACHE0_PMEVENTCOUNTER0 + counter);
+ vh1 = REGW(METAL_SIFIVE_CCACHE0_PMEVENTCOUNTER0 + counter + 4);
+ } while (vh != vh1);
+#else
+ val = REGD(METAL_SIFIVE_CCACHE0_PMEVENTCOUNTER0 + counter);
+#endif
+ }
+#endif
+#if __riscv_xlen == 32
+ return ((((unsigned long long)vh) << 32) | vl);
+#else
+ return val;
+#endif
+}
+
+void sifive_ccache0_set_client_filter(uint64_t mask) {
+
+ /* Set clients to be excluded from performance monitoring */
+ REGD(METAL_SIFIVE_CCACHE0_PMCLIENTFILTER) = mask;
+}
+
+uint64_t sifive_ccache0_get_client_filter(void) {
+ uint64_t val = 0;
+
+ /* Get currently active client filter mask */
+ val = REGD(METAL_SIFIVE_CCACHE0_PMCLIENTFILTER);
+
+ return val;
+}
+
+int sifive_ccache0_get_interrupt_id(uint32_t src) {
+ int ret = 0;
+
+ if (src < (uint32_t)sizeof(sifive_ccache0_interrupts) / sizeof(int)) {
+ ret = sifive_ccache0_interrupts[src];
+ }
+
+ return ret;
+}
+
+struct metal_interrupt *sifive_ccache0_interrupt_controller(void) {
+ return METAL_SIFIVE_CCACHE0_INTERRUPT_PARENT;
+}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_clic0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_clic0.c
index 12c3dac06..bf8fa16a0 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_clic0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_clic0.c
@@ -5,123 +5,135 @@
#ifdef METAL_SIFIVE_CLIC0
-#include <stdint.h>
-#include <metal/io.h>
-#include <metal/shutdown.h>
#include <metal/drivers/sifive_clic0.h>
+#include <metal/io.h>
#include <metal/machine.h>
+#include <metal/shutdown.h>
+#include <stdint.h>
+
+#define CLIC0_MAX_INTERRUPTS 4096
-typedef enum metal_clic_vector_{
+typedef enum metal_clic_vector_ {
METAL_CLIC_NONVECTOR = 0,
- METAL_CLIC_VECTORED = 1
+ METAL_CLIC_VECTORED = 1
} metal_clic_vector;
struct __metal_clic_cfg {
- unsigned char : 1,
- nmbits : 2,
- nlbits : 4,
- nvbit : 1;
+ unsigned char : 1, nmbits : 2, nlbits : 4, nvbit : 1;
};
const struct __metal_clic_cfg __metal_clic_defaultcfg = {
- .nmbits = METAL_INTR_PRIV_M_MODE,
- .nlbits = 0,
- .nvbit = METAL_CLIC_NONVECTOR
- };
+ .nmbits = METAL_INTR_PRIV_M_MODE,
+ .nlbits = 0,
+ .nvbit = METAL_CLIC_NONVECTOR};
void __metal_clic0_handler(int id, void *priv) __attribute__((aligned(64)));
-void __metal_clic0_default_vector_handler (void) __attribute__((interrupt, aligned(64)));
+void __metal_clic0_default_vector_handler(void)
+ __attribute__((interrupt, aligned(64)));
-struct __metal_clic_cfg __metal_clic0_configuration (struct __metal_driver_sifive_clic0 *clic,
- struct __metal_clic_cfg *cfg)
-{
+struct __metal_clic_cfg
+__metal_clic0_configuration(struct __metal_driver_sifive_clic0 *clic,
+ struct __metal_clic_cfg *cfg) {
volatile unsigned char val;
struct __metal_clic_cfg cliccfg;
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
- if ( cfg ) {
+ if (cfg) {
val = cfg->nmbits << 5 | cfg->nlbits << 1 | cfg->nvbit;
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICCFG)) = val;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICCFG)) = val;
}
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICCFG));
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICCFG));
cliccfg.nmbits = (val & METAL_SIFIVE_CLIC0_CLICCFG_NMBITS_MASK) >> 5;
cliccfg.nlbits = (val & METAL_SIFIVE_CLIC0_CLICCFG_NLBITS_MASK) >> 1;
cliccfg.nvbit = val & METAL_SIFIVE_CLIC0_CLICCFG_NVBIT_MASK;
return cliccfg;
}
-int __metal_clic0_interrupt_set_mode (struct __metal_driver_sifive_clic0 *clic, int id, int mode)
-{
+int __metal_clic0_interrupt_set_mode(struct __metal_driver_sifive_clic0 *clic,
+ int id, int mode) {
uint8_t mask, val;
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
-
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+
if (mode >= (cfg.nmbits << 1)) {
/* Do nothing, mode request same or exceed what configured in CLIC */
return 0;
}
-
+
/* Mask out nmbits and retain other values */
mask = ((uint8_t)(-1)) >> cfg.nmbits;
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) & mask;
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) = val | (mode << (8 - cfg.nmbits));
+ val =
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) &
+ mask;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) =
+ val | (mode << (8 - cfg.nmbits));
return 0;
}
-int __metal_clic0_interrupt_set_level (struct __metal_driver_sifive_clic0 *clic, int id, unsigned int level)
-{
+int __metal_clic0_interrupt_set_level(struct __metal_driver_sifive_clic0 *clic,
+ int id, unsigned int level) {
+
uint8_t mask, nmmask, nlmask, val;
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
/* Drop the LSBs that don't fit in nlbits */
- level = level >> (METAL_CLIC_MAX_NLBITS - cfg.nlbits);
-
- nmmask = ~( ((uint8_t)(-1)) >> (cfg.nmbits) );
- nlmask = ((uint8_t)(-1)) >> (cfg.nmbits + cfg.nlbits);
+ nlmask = (uint8_t)(-1) >> (cfg.nmbits + cfg.nlbits);
+ nmmask = ~((uint8_t)(-1) >> (cfg.nmbits));
mask = ~(nlmask | nmmask);
-
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) = __METAL_SET_FIELD(val, mask, level);
+
+ level &= mask;
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ val &= ~mask;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) =
+ (val | level);
+
return 0;
}
-unsigned int __metal_clic0_interrupt_get_level (struct __metal_driver_sifive_clic0 *clic, int id)
-{
+unsigned int
+__metal_clic0_interrupt_get_level(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
int level;
uint8_t mask, val, freebits, nlbits;
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_intbits = __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_intbits =
+ __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
if ((cfg.nmbits + cfg.nlbits) >= num_intbits) {
- nlbits = num_intbits - cfg.nmbits;
+ nlbits = (num_intbits >= cfg.nmbits) ? (num_intbits - cfg.nmbits) : 0;
} else {
- nlbits = cfg.nlbits;
+ nlbits = __METAL_MIN((num_intbits - cfg.nmbits), cfg.nlbits);
}
- mask = ((1 << nlbits) - 1) << (8 - (cfg.nmbits + nlbits));
+ mask = ((1 << nlbits) - 1)
+ << (METAL_CLIC_MAX_NLBITS - (cfg.nmbits + nlbits));
freebits = ((1 << METAL_CLIC_MAX_NLBITS) - 1) >> nlbits;
-
+
if (mask == 0) {
level = (1 << METAL_CLIC_MAX_NLBITS) - 1;
} else {
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
val = __METAL_GET_FIELD(val, mask);
level = (val << (METAL_CLIC_MAX_NLBITS - nlbits)) | freebits;
}
@@ -129,38 +141,45 @@ unsigned int __metal_clic0_interrupt_get_level (struct __metal_driver_sifive_cli
return level;
}
-int __metal_clic0_interrupt_set_priority (struct __metal_driver_sifive_clic0 *clic, int id, int priority)
-{
- uint8_t mask, npmask, val, npbits;
+int __metal_clic0_interrupt_set_priority(
+ struct __metal_driver_sifive_clic0 *clic, int id, int priority) {
+
+ uint8_t mask, nlmask, val, npbits;
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_intbits = __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_intbits =
+ __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
- if ((cfg.nmbits + cfg.nlbits) < num_intbits) {
+ if ((cfg.nmbits + cfg.nlbits) <= num_intbits) {
npbits = num_intbits - (cfg.nmbits + cfg.nlbits);
- priority = priority >> (8 - npbits);
-
- mask = ((uint8_t)(-1)) >> (cfg.nmbits + cfg.nlbits + npbits);
- npmask = ~(((uint8_t)(-1)) >> (cfg.nmbits + cfg.nlbits));
- mask = ~(mask | npmask);
-
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) = __METAL_SET_FIELD(val, mask, priority);
+
+ mask = (uint8_t)(-1) >> (cfg.nmbits + cfg.nlbits + npbits);
+ nlmask = ~((uint8_t)(-1) >> (cfg.nmbits + cfg.nlbits));
+ mask = ~(mask | nlmask);
+
+ priority &= mask;
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ val &= ~mask;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) =
+ (val | priority);
}
return 0;
}
-int __metal_clic0_interrupt_get_priority (struct __metal_driver_sifive_clic0 *clic, int id)
-{
+int __metal_clic0_interrupt_get_priority(
+ struct __metal_driver_sifive_clic0 *clic, int id) {
int priority;
uint8_t mask, val, freebits, nlbits;
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_intbits = __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_intbits =
+ __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
if ((cfg.nmbits + cfg.nlbits) >= num_intbits) {
nlbits = num_intbits - cfg.nmbits;
@@ -170,133 +189,148 @@ int __metal_clic0_interrupt_get_priority (struct __metal_driver_sifive_clic0 *cl
mask = ((1 << nlbits) - 1) << (8 - (cfg.nmbits + nlbits));
freebits = ((1 << METAL_CLIC_MAX_NLBITS) - 1) >> nlbits;
-
+
if (mask == 0) {
priority = (1 << METAL_CLIC_MAX_NLBITS) - 1;
- } else {
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ } else {
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
priority = __METAL_GET_FIELD(val, freebits);
}
return priority;
}
-int __metal_clic0_interrupt_set_vector_mode (struct __metal_driver_sifive_clic0 *clic, int id, int enable)
-{
+int __metal_clic0_interrupt_set_vector_mode(
+ struct __metal_driver_sifive_clic0 *clic, int id, int enable) {
uint8_t mask, val;
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_intbits = __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_intbits =
+ __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
mask = 1 << (8 - num_intbits);
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
- /* Ensure its value is 1 bit wide */
- enable &= 0x1;
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) = __METAL_SET_FIELD(val, mask, enable);
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ if (enable) {
+ val |= mask;
+ } else {
+ val &= ~mask;
+ }
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id)) = val;
return 0;
}
-int __metal_clic0_interrupt_is_vectored (struct __metal_driver_sifive_clic0 *clic, int id)
-{
+int __metal_clic0_interrupt_is_vectored(
+ struct __metal_driver_sifive_clic0 *clic, int id) {
uint8_t mask, val;
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_intbits = __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_intbits =
+ __metal_driver_sifive_clic0_num_intbits((struct metal_interrupt *)clic);
mask = 1 << (8 - num_intbits);
- val = __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
+ val = __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTCTL_BASE + id));
return __METAL_GET_FIELD(val, mask);
}
-int __metal_clic0_interrupt_enable (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_enable(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
- if (id >= num_subinterrupts) {
- return -1;
- }
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id)) = METAL_ENABLE;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id)) =
+ METAL_ENABLE;
return 0;
}
-int __metal_clic0_interrupt_disable (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_disable(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
- if (id >= num_subinterrupts) {
- return -1;
- }
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id)) = METAL_DISABLE;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id)) =
+ METAL_DISABLE;
return 0;
}
-int __metal_clic0_interrupt_is_enabled (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_is_enabled(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
if (id >= num_subinterrupts) {
return 0;
}
- return __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id));
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIE_BASE + id));
}
-int __metal_clic0_interrupt_is_pending (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_is_pending(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
if (id >= num_subinterrupts) {
return 0;
}
- return __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id));
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id));
}
-int __metal_clic0_interrupt_set (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_set(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
if (id < num_subinterrupts) {
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id)) = METAL_ENABLE;
- return 0;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id)) =
+ METAL_ENABLE;
}
- return -1;
+ return 0;
}
-int __metal_clic0_interrupt_clear (struct __metal_driver_sifive_clic0 *clic, int id)
-{
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+int __metal_clic0_interrupt_clear(struct __metal_driver_sifive_clic0 *clic,
+ int id) {
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
if (id < num_subinterrupts) {
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id)) = METAL_DISABLE;
- return 0;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base + METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIP_BASE + id)) =
+ METAL_DISABLE;
}
- return -1;
+ return 0;
}
-int __metal_clic0_configure_set_vector_mode (struct __metal_driver_sifive_clic0 *clic, metal_vector_mode mode)
-{
+int __metal_clic0_configure_set_vector_mode(
+ struct __metal_driver_sifive_clic0 *clic, metal_vector_mode mode) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
switch (mode) {
@@ -319,12 +353,12 @@ int __metal_clic0_configure_set_vector_mode (struct __metal_driver_sifive_clic0
return 0;
}
-metal_vector_mode __metal_clic0_configure_get_vector_mode (struct __metal_driver_sifive_clic0 *clic)
-{
+metal_vector_mode __metal_clic0_configure_get_vector_mode(
+ struct __metal_driver_sifive_clic0 *clic) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
metal_vector_mode mode = __metal_controller_interrupt_vector_mode();
- if (mode == METAL_SELECTIVE_VECTOR_MODE) {
+ if (mode == METAL_SELECTIVE_VECTOR_MODE) {
if (cfg.nvbit) {
return METAL_SELECTIVE_VECTOR_MODE;
} else {
@@ -335,8 +369,8 @@ metal_vector_mode __metal_clic0_configure_get_vector_mode (struct __metal_driver
}
}
-int __metal_clic0_configure_set_privilege (struct __metal_driver_sifive_clic0 *clic, metal_intr_priv_mode priv)
-{
+int __metal_clic0_configure_set_privilege(
+ struct __metal_driver_sifive_clic0 *clic, metal_intr_priv_mode priv) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
cfg.nmbits = priv;
@@ -344,15 +378,15 @@ int __metal_clic0_configure_set_privilege (struct __metal_driver_sifive_clic0 *c
return 0;
}
-metal_intr_priv_mode __metal_clic0_configure_get_privilege (struct __metal_driver_sifive_clic0 *clic)
-{
+metal_intr_priv_mode __metal_clic0_configure_get_privilege(
+ struct __metal_driver_sifive_clic0 *clic) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
return cfg.nmbits;
}
-int __metal_clic0_configure_set_level (struct __metal_driver_sifive_clic0 *clic, int level)
-{
+int __metal_clic0_configure_set_level(struct __metal_driver_sifive_clic0 *clic,
+ int level) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
cfg.nlbits = level & 0xF;
@@ -360,75 +394,82 @@ int __metal_clic0_configure_set_level (struct __metal_driver_sifive_clic0 *clic,
return 0;
}
-int __metal_clic0_configure_get_level (struct __metal_driver_sifive_clic0 *clic)
-{
+int __metal_clic0_configure_get_level(
+ struct __metal_driver_sifive_clic0 *clic) {
struct __metal_clic_cfg cfg = __metal_clic0_configuration(clic, NULL);
return cfg.nlbits;
}
-unsigned long long __metal_clic0_mtime_get (struct __metal_driver_sifive_clic0 *clic)
-{
+unsigned long long
+__metal_clic0_mtime_get(struct __metal_driver_sifive_clic0 *clic) {
__metal_io_u32 lo, hi;
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
/* Guard against rollover when reading */
do {
- hi = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CLIC0_MTIME + 4));
- lo = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CLIC0_MTIME));
- } while (__METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_CLIC0_MTIME + 4)) != hi);
+ hi = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_SIFIVE_CLIC0_MTIME + 4));
+ lo = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + METAL_SIFIVE_CLIC0_MTIME));
+ } while (__METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
+ METAL_SIFIVE_CLIC0_MTIME +
+ 4)) != hi);
return (((unsigned long long)hi) << 32) | lo;
}
int __metal_driver_sifive_clic0_mtimecmp_set(struct metal_interrupt *controller,
int hartid,
- unsigned long long time)
-{
+ unsigned long long time) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base((struct metal_interrupt *)clic);
+ unsigned long control_base = __metal_driver_sifive_clic0_control_base(
+ (struct metal_interrupt *)clic);
/* Per spec, the RISC-V MTIME/MTIMECMP registers are 64 bit,
* and are NOT internally latched for multiword transfers.
* Need to be careful about sequencing to avoid triggering
* spurious interrupts: For that set the high word to a max
* value first.
*/
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_SIFIVE_CLIC0_MTIMECMP_BASE + 4)) = 0xFFFFFFFF;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_SIFIVE_CLIC0_MTIMECMP_BASE)) = (__metal_io_u32)time;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) + METAL_SIFIVE_CLIC0_MTIMECMP_BASE + 4)) = (__metal_io_u32)(time >> 32);
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_SIFIVE_CLIC0_MTIMECMP_BASE +
+ 4)) = 0xFFFFFFFF;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_SIFIVE_CLIC0_MTIMECMP_BASE)) =
+ (__metal_io_u32)time;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + (8 * hartid) +
+ METAL_SIFIVE_CLIC0_MTIMECMP_BASE +
+ 4)) = (__metal_io_u32)(time >> 32);
return 0;
}
-void __metal_clic0_handler (int id, void *priv)
-{
+void __metal_clic0_handler(int id, void *priv) {
struct __metal_driver_sifive_clic0 *clic = priv;
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts((struct metal_interrupt *)clic);
+ int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(
+ (struct metal_interrupt *)clic);
- if ( (id < num_subinterrupts) && (clic->metal_exint_table[id].handler) ) {
- clic->metal_exint_table[id].handler(id, clic->metal_exint_table[id].exint_data);
+ if ((id < num_subinterrupts) && (clic->metal_exint_table[id].handler)) {
+ clic->metal_exint_table[id].handler(
+ id, clic->metal_exint_table[id].exint_data);
}
}
-void __metal_clic0_default_handler (int id, void *priv) {
- metal_shutdown(300);
-}
+void __metal_clic0_default_handler(int id, void *priv) { metal_shutdown(300); }
-void __metal_clic0_default_vector_handler (void) {
- metal_shutdown(400);
-}
+void __metal_clic0_default_vector_handler(void) { metal_shutdown(400); }
-void __metal_driver_sifive_clic0_init (struct metal_interrupt *controller)
-{
+void __metal_driver_sifive_clic0_init(struct metal_interrupt *controller) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
- if ( !clic->init_done ) {
+ if (!clic->init_done) {
int level, max_levels, line, num_interrupts, num_subinterrupts;
struct __metal_clic_cfg cfg = __metal_clic_defaultcfg;
struct metal_interrupt *intc =
- __metal_driver_sifive_clic0_interrupt_parent(controller);
+ __metal_driver_sifive_clic0_interrupt_parent(controller);
/* Initialize ist parent controller, aka cpu_intc. */
intc->vtable->interrupt_init(intc);
@@ -439,50 +480,54 @@ void __metal_driver_sifive_clic0_init (struct metal_interrupt *controller)
* Register its interrupts with with parent controller,
* aka sw, timer and ext to its default isr
*/
- num_interrupts = __metal_driver_sifive_clic0_num_interrupts(controller);
+ num_interrupts = __metal_driver_sifive_clic0_num_interrupts(controller);
for (int i = 0; i < num_interrupts; i++) {
- line = __metal_driver_sifive_clic0_interrupt_lines(controller, i);
+ line = __metal_driver_sifive_clic0_interrupt_lines(controller, i);
intc->vtable->interrupt_register(intc, line, NULL, clic);
}
/* Default CLIC mode to per dts */
- max_levels = __metal_driver_sifive_clic0_max_levels(controller);
- cfg.nlbits = (max_levels > METAL_CLIC_MAX_NLBITS) ?
- METAL_CLIC_MAX_NLBITS : max_levels;
+ max_levels = __metal_driver_sifive_clic0_max_levels(controller);
+ cfg.nlbits = (max_levels > METAL_CLIC_MAX_NLBITS)
+ ? METAL_CLIC_MAX_NLBITS
+ : max_levels;
__metal_clic0_configuration(clic, &cfg);
level = (1 << cfg.nlbits) - 1;
- num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(controller);
+ num_subinterrupts =
+ __metal_driver_sifive_clic0_num_subinterrupts(controller);
clic->metal_mtvt_table[0] = &__metal_clic0_handler;
- for (int i = 1; i < num_subinterrupts; i++) {
- clic->metal_mtvt_table[i] = NULL;
- clic->metal_exint_table[i].handler = NULL;
- clic->metal_exint_table[i].sub_int = NULL;
- clic->metal_exint_table[i].exint_data = NULL;
+ __metal_clic0_interrupt_disable(clic, 0);
+ __metal_clic0_interrupt_set_level(clic, 0, level);
+ for (int i = 1; i < CLIC0_MAX_INTERRUPTS; i++) {
+ if (i < num_subinterrupts) {
+ clic->metal_mtvt_table[i] = NULL;
+ clic->metal_exint_table[i].handler = NULL;
+ clic->metal_exint_table[i].sub_int = NULL;
+ clic->metal_exint_table[i].exint_data = NULL;
+ __metal_clic0_interrupt_set_level(clic, i, level);
+ }
__metal_clic0_interrupt_disable(clic, i);
- __metal_clic0_interrupt_set_level(clic, i, level);
}
- clic->init_done = 1;
- }
+ clic->init_done = 1;
+ }
}
-int __metal_driver_sifive_clic0_register (struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_sifive_clic0_register(struct metal_interrupt *controller,
+ int id, metal_interrupt_handler_t isr,
+ void *priv) {
int rc = -1;
int num_subinterrupts;
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
struct metal_interrupt *intc =
- __metal_driver_sifive_clic0_interrupt_parent(controller);
+ __metal_driver_sifive_clic0_interrupt_parent(controller);
metal_vector_mode mode = __metal_clic0_configure_get_vector_mode(clic);
-
- if ( ( (mode == METAL_SELECTIVE_VECTOR_MODE) &&
- (__metal_clic0_interrupt_is_vectored(clic, id)) ) ||
- (mode == METAL_HARDWARE_VECTOR_MODE) ||
- (mode == METAL_VECTOR_MODE) ||
- (mode == METAL_DIRECT_MODE) ) {
+
+ if (((mode == METAL_SELECTIVE_VECTOR_MODE) &&
+ (__metal_clic0_interrupt_is_vectored(clic, id))) ||
+ (mode == METAL_HARDWARE_VECTOR_MODE) || (mode == METAL_VECTOR_MODE) ||
+ (mode == METAL_DIRECT_MODE)) {
return rc;
}
@@ -490,14 +535,15 @@ int __metal_driver_sifive_clic0_register (struct metal_interrupt *controller,
if (id < METAL_INTERRUPT_ID_CSW) {
return intc->vtable->interrupt_register(intc, id, isr, priv);
}
-
- /*
+
+ /*
* CLIC (sub-interrupts) devices interrupts start at 16 but offset from 0
* Reset the IDs to reflects this.
*/
- num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(controller);
+ num_subinterrupts =
+ __metal_driver_sifive_clic0_num_subinterrupts(controller);
if (id < num_subinterrupts) {
- if ( isr) {
+ if (isr) {
clic->metal_exint_table[id].handler = isr;
clic->metal_exint_table[id].exint_data = priv;
} else {
@@ -509,29 +555,30 @@ int __metal_driver_sifive_clic0_register (struct metal_interrupt *controller,
return rc;
}
-int __metal_driver_sifive_clic0_vector_register (struct metal_interrupt *controller,
- int id, metal_interrupt_vector_handler_t isr,
- void *priv)
-{
+int __metal_driver_sifive_clic0_vector_register(
+ struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t isr, void *priv) {
int rc = -1;
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
struct metal_interrupt *intc =
- __metal_driver_sifive_clic0_interrupt_parent(controller);
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(controller);
+ __metal_driver_sifive_clic0_interrupt_parent(controller);
+ int num_subinterrupts =
+ __metal_driver_sifive_clic0_num_subinterrupts(controller);
metal_vector_mode mode = __metal_clic0_configure_get_vector_mode(clic);
- if ((mode != METAL_SELECTIVE_VECTOR_MODE) && (mode != METAL_HARDWARE_VECTOR_MODE)) {
+ if ((mode != METAL_SELECTIVE_VECTOR_MODE) &&
+ (mode != METAL_HARDWARE_VECTOR_MODE)) {
return rc;
}
if ((mode == METAL_SELECTIVE_VECTOR_MODE) &&
- (__metal_clic0_interrupt_is_vectored(clic, id) == 0) ) {
+ (__metal_clic0_interrupt_is_vectored(clic, id) == 0)) {
return rc;
}
if (id < num_subinterrupts) {
- if ( isr) {
+ if (isr) {
clic->metal_mtvt_table[id] = isr;
- clic->metal_exint_table[id].exint_data = priv;
+ clic->metal_exint_table[id].exint_data = priv;
} else {
clic->metal_mtvt_table[id] = __metal_clic0_default_vector_handler;
clic->metal_exint_table[id].sub_int = priv;
@@ -541,29 +588,31 @@ int __metal_driver_sifive_clic0_vector_register (struct metal_interrupt *control
return rc;
}
-int __metal_driver_sifive_clic0_enable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_clic0_enable(struct metal_interrupt *controller,
+ int id) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_enable(clic, id);
}
-int __metal_driver_sifive_clic0_disable (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_clic0_disable(struct metal_interrupt *controller,
+ int id) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_disable(clic, id);
}
-int __metal_driver_sifive_clic0_enable_interrupt_vector(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_clic0_enable_interrupt_vector(
+ struct metal_interrupt *controller, int id) {
int rc = -1;
- int num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(controller);
+ int num_subinterrupts =
+ __metal_driver_sifive_clic0_num_subinterrupts(controller);
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
metal_vector_mode mode = __metal_clic0_configure_get_vector_mode(clic);
- if ((mode != METAL_SELECTIVE_VECTOR_MODE) && (mode != METAL_HARDWARE_VECTOR_MODE)) {
+ if ((mode != METAL_SELECTIVE_VECTOR_MODE) &&
+ (mode != METAL_HARDWARE_VECTOR_MODE)) {
return rc;
}
if (id < num_subinterrupts) {
@@ -573,13 +622,14 @@ int __metal_driver_sifive_clic0_enable_interrupt_vector(struct metal_interrupt *
return -1;
}
-int __metal_driver_sifive_clic0_disable_interrupt_vector(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_clic0_disable_interrupt_vector(
+ struct metal_interrupt *controller, int id) {
int num_subinterrupts;
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
- num_subinterrupts = __metal_driver_sifive_clic0_num_subinterrupts(controller);
+ num_subinterrupts =
+ __metal_driver_sifive_clic0_num_subinterrupts(controller);
if (id < num_subinterrupts) {
__metal_clic0_interrupt_set_vector_mode(clic, id, METAL_DISABLE);
return 0;
@@ -587,148 +637,183 @@ int __metal_driver_sifive_clic0_disable_interrupt_vector(struct metal_interrupt
return -1;
}
-metal_vector_mode __metal_driver_sifive_clic0_get_vector_mode (struct metal_interrupt *controller)
-{
+metal_vector_mode __metal_driver_sifive_clic0_get_vector_mode(
+ struct metal_interrupt *controller) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_get_vector_mode(clic);
}
-int __metal_driver_sifive_clic0_set_vector_mode (struct metal_interrupt *controller, metal_vector_mode mode)
-{
+int __metal_driver_sifive_clic0_set_vector_mode(
+ struct metal_interrupt *controller, metal_vector_mode mode) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_set_vector_mode(clic, mode);
}
-metal_intr_priv_mode __metal_driver_sifive_clic0_get_privilege (struct metal_interrupt *controller)
-{
+metal_intr_priv_mode
+__metal_driver_sifive_clic0_get_privilege(struct metal_interrupt *controller) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_get_privilege(clic);
}
-int __metal_driver_sifive_clic0_set_privilege (struct metal_interrupt *controller, metal_intr_priv_mode priv)
-{
+int __metal_driver_sifive_clic0_set_privilege(
+ struct metal_interrupt *controller, metal_intr_priv_mode priv) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_set_privilege(clic, priv);
}
-unsigned int __metal_driver_sifive_clic0_get_threshold (struct metal_interrupt *controller)
-{
+unsigned int
+__metal_driver_sifive_clic0_get_threshold(struct metal_interrupt *controller) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_get_level(clic);
}
-int __metal_driver_sifive_clic0_set_threshold (struct metal_interrupt *controller, unsigned int level)
-{
+int __metal_driver_sifive_clic0_set_threshold(
+ struct metal_interrupt *controller, unsigned int level) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_configure_set_level(clic, level);
}
-unsigned int __metal_driver_sifive_clic0_get_priority (struct metal_interrupt *controller, int id)
-{
+unsigned int
+__metal_driver_sifive_clic0_get_priority(struct metal_interrupt *controller,
+ int id) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_get_priority(clic, id);
}
-int __metal_driver_sifive_clic0_set_priority (struct metal_interrupt *controller, int id, unsigned int priority)
-{
+int __metal_driver_sifive_clic0_set_priority(struct metal_interrupt *controller,
+ int id, unsigned int priority) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_set_priority(clic, id, priority);
}
-int __metal_driver_sifive_clic0_clear_interrupt (struct metal_interrupt *controller, int id)
-{
+unsigned int __metal_driver_sifive_clic0_get_preemptive_level(
+ struct metal_interrupt *controller, int id) {
+ struct __metal_driver_sifive_clic0 *clic =
+ (struct __metal_driver_sifive_clic0 *)(controller);
+ return __metal_clic0_interrupt_get_level(clic, id);
+}
+
+int __metal_driver_sifive_clic0_set_preemptive_level(
+ struct metal_interrupt *controller, int id, unsigned int level) {
+ struct __metal_driver_sifive_clic0 *clic =
+ (struct __metal_driver_sifive_clic0 *)(controller);
+ __metal_clic0_interrupt_set_level(clic, id, level);
+ return (__metal_clic0_interrupt_set_priority(clic, id, level));
+}
+
+int __metal_driver_sifive_clic0_clear_interrupt(
+ struct metal_interrupt *controller, int id) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_clear(clic, id);
}
-int __metal_driver_sifive_clic0_set_interrupt (struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_clic0_set_interrupt(
+ struct metal_interrupt *controller, int id) {
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
return __metal_clic0_interrupt_set(clic, id);
}
-int __metal_driver_sifive_clic0_command_request (struct metal_interrupt *controller,
- int command, void *data)
-{
+int __metal_driver_sifive_clic0_command_request(
+ struct metal_interrupt *controller, int command, void *data) {
int hartid;
int rc = -1;
struct __metal_driver_sifive_clic0 *clic =
- (struct __metal_driver_sifive_clic0 *)(controller);
- unsigned long control_base = __metal_driver_sifive_clic0_control_base(controller);
+ (struct __metal_driver_sifive_clic0 *)(controller);
+ unsigned long control_base =
+ __metal_driver_sifive_clic0_control_base(controller);
switch (command) {
case METAL_TIMER_MTIME_GET:
if (data) {
- *(unsigned long long *)data = __metal_clic0_mtime_get(clic);
+ *(unsigned long long *)data = __metal_clic0_mtime_get(clic);
rc = 0;
}
break;
case METAL_SOFTWARE_IPI_CLEAR:
- if (data) {
- hartid = *(int *)data;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4))) = METAL_DISABLE;
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIP_BASE)) = METAL_DISABLE;
+ if (data) {
+ hartid = *(int *)data;
+ __METAL_ACCESS_ONCE((
+ __metal_io_u32 *)(control_base + (hartid * 4))) = METAL_DISABLE;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base +
+ METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIP_BASE)) =
+ METAL_DISABLE;
rc = 0;
}
break;
case METAL_SOFTWARE_IPI_SET:
- if (data) {
- hartid = *(int *)data;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4))) = METAL_ENABLE;
- __METAL_ACCESS_ONCE((__metal_io_u8 *)(control_base +
- METAL_SIFIVE_CLIC0_MMODE_APERTURE +
- METAL_SIFIVE_CLIC0_CLICINTIP_BASE)) = METAL_ENABLE;
+ if (data) {
+ hartid = *(int *)data;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + (hartid * 4))) = METAL_ENABLE;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u8 *)(control_base +
+ METAL_SIFIVE_CLIC0_MMODE_APERTURE +
+ METAL_SIFIVE_CLIC0_CLICINTIP_BASE)) =
+ METAL_ENABLE;
rc = 0;
}
break;
case METAL_SOFTWARE_MSIP_GET:
rc = 0;
- if (data) {
- hartid = *(int *)data;
- rc = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base +
- (hartid * 4)));
+ if (data) {
+ hartid = *(int *)data;
+ rc = __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(control_base + (hartid * 4)));
}
break;
default:
- break;
+ break;
}
return rc;
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_clic0) = {
- .clic_vtable.interrupt_init = __metal_driver_sifive_clic0_init,
+ .clic_vtable.interrupt_init = __metal_driver_sifive_clic0_init,
.clic_vtable.interrupt_register = __metal_driver_sifive_clic0_register,
- .clic_vtable.interrupt_vector_register = __metal_driver_sifive_clic0_vector_register,
- .clic_vtable.interrupt_enable = __metal_driver_sifive_clic0_enable,
- .clic_vtable.interrupt_disable = __metal_driver_sifive_clic0_disable,
- .clic_vtable.interrupt_vector_enable = __metal_driver_sifive_clic0_enable_interrupt_vector,
- .clic_vtable.interrupt_vector_disable = __metal_driver_sifive_clic0_disable_interrupt_vector,
- .clic_vtable.interrupt_get_vector_mode = __metal_driver_sifive_clic0_get_vector_mode,
- .clic_vtable.interrupt_set_vector_mode = __metal_driver_sifive_clic0_set_vector_mode,
- .clic_vtable.interrupt_get_privilege = __metal_driver_sifive_clic0_get_privilege,
- .clic_vtable.interrupt_set_privilege = __metal_driver_sifive_clic0_set_privilege,
- .clic_vtable.interrupt_get_threshold = __metal_driver_sifive_clic0_get_threshold,
- .clic_vtable.interrupt_set_threshold = __metal_driver_sifive_clic0_set_threshold,
- .clic_vtable.interrupt_get_priority = __metal_driver_sifive_clic0_get_priority,
- .clic_vtable.interrupt_set_priority = __metal_driver_sifive_clic0_set_priority,
- .clic_vtable.interrupt_clear = __metal_driver_sifive_clic0_clear_interrupt,
- .clic_vtable.interrupt_set = __metal_driver_sifive_clic0_set_interrupt,
- .clic_vtable.command_request = __metal_driver_sifive_clic0_command_request,
- .clic_vtable.mtimecmp_set = __metal_driver_sifive_clic0_mtimecmp_set,
+ .clic_vtable.interrupt_vector_register =
+ __metal_driver_sifive_clic0_vector_register,
+ .clic_vtable.interrupt_enable = __metal_driver_sifive_clic0_enable,
+ .clic_vtable.interrupt_disable = __metal_driver_sifive_clic0_disable,
+ .clic_vtable.interrupt_vector_enable =
+ __metal_driver_sifive_clic0_enable_interrupt_vector,
+ .clic_vtable.interrupt_vector_disable =
+ __metal_driver_sifive_clic0_disable_interrupt_vector,
+ .clic_vtable.interrupt_get_vector_mode =
+ __metal_driver_sifive_clic0_get_vector_mode,
+ .clic_vtable.interrupt_set_vector_mode =
+ __metal_driver_sifive_clic0_set_vector_mode,
+ .clic_vtable.interrupt_get_privilege =
+ __metal_driver_sifive_clic0_get_privilege,
+ .clic_vtable.interrupt_set_privilege =
+ __metal_driver_sifive_clic0_set_privilege,
+ .clic_vtable.interrupt_get_threshold =
+ __metal_driver_sifive_clic0_get_threshold,
+ .clic_vtable.interrupt_set_threshold =
+ __metal_driver_sifive_clic0_set_threshold,
+ .clic_vtable.interrupt_get_priority =
+ __metal_driver_sifive_clic0_get_priority,
+ .clic_vtable.interrupt_set_priority =
+ __metal_driver_sifive_clic0_set_priority,
+ .clic_vtable.interrupt_get_preemptive_level =
+ __metal_driver_sifive_clic0_get_preemptive_level,
+ .clic_vtable.interrupt_set_preemptive_level =
+ __metal_driver_sifive_clic0_set_preemptive_level,
+ .clic_vtable.interrupt_clear = __metal_driver_sifive_clic0_clear_interrupt,
+ .clic_vtable.interrupt_set = __metal_driver_sifive_clic0_set_interrupt,
+ .clic_vtable.command_request = __metal_driver_sifive_clic0_command_request,
+ .clic_vtable.mtimecmp_set = __metal_driver_sifive_clic0_mtimecmp_set,
};
#endif /* METAL_SIFIVE_CLIC0 */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfrosc.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfrosc.c
index 61af8d314..d4df0402e 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfrosc.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfrosc.c
@@ -9,18 +9,20 @@
#include <metal/machine.h>
#define CONFIG_DIVIDER 0x0000003FUL
-#define CONFIG_TRIM 0x001F0000UL
-#define CONFIG_ENABLE 0x40000000UL
-#define CONFIG_READY 0x80000000UL
-
-long __metal_driver_sifive_fe310_g000_hfrosc_get_rate_hz(const struct metal_clock *clock)
-{
- struct metal_clock *ref = __metal_driver_sifive_fe310_g000_hfrosc_ref(clock);
- long config_offset = __metal_driver_sifive_fe310_g000_hfrosc_config_offset(clock);
+#define CONFIG_TRIM 0x001F0000UL
+#define CONFIG_ENABLE 0x40000000UL
+#define CONFIG_READY 0x80000000UL
+
+long __metal_driver_sifive_fe310_g000_hfrosc_get_rate_hz(
+ const struct metal_clock *clock) {
+ struct metal_clock *ref =
+ __metal_driver_sifive_fe310_g000_hfrosc_ref(clock);
+ long config_offset =
+ __metal_driver_sifive_fe310_g000_hfrosc_config_offset(clock);
struct __metal_driver_sifive_fe310_g000_prci *config_base =
- __metal_driver_sifive_fe310_g000_hfrosc_config_base(clock);
+ __metal_driver_sifive_fe310_g000_hfrosc_config_base(clock);
const struct __metal_driver_vtable_sifive_fe310_g000_prci *vtable =
- __metal_driver_sifive_fe310_g000_prci_vtable();
+ __metal_driver_sifive_fe310_g000_prci_vtable();
long cfg = vtable->get_reg(config_base, config_offset);
if ((cfg & CONFIG_ENABLE) == 0)
@@ -30,8 +32,8 @@ long __metal_driver_sifive_fe310_g000_hfrosc_get_rate_hz(const struct metal_cloc
return metal_clock_get_rate_hz(ref) / ((cfg & CONFIG_DIVIDER) + 1);
}
-long __metal_driver_sifive_fe310_g000_hfrosc_set_rate_hz(struct metal_clock *clock, long rate)
-{
+long __metal_driver_sifive_fe310_g000_hfrosc_set_rate_hz(
+ struct metal_clock *clock, long rate) {
return __metal_driver_sifive_fe310_g000_hfrosc_get_rate_hz(clock);
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfxosc.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfxosc.c
index 9ed7a0bf3..b8a9c6dda 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfxosc.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_hfxosc.c
@@ -8,17 +8,19 @@
#include <metal/drivers/sifive_fe310-g000_hfxosc.h>
#include <metal/machine.h>
-#define CONFIG_ENABLE 0x40000000UL
-#define CONFIG_READY 0x80000000UL
-
-long __metal_driver_sifive_fe310_g000_hfxosc_get_rate_hz(const struct metal_clock *clock)
-{
- struct metal_clock *ref = __metal_driver_sifive_fe310_g000_hfxosc_ref(clock);
- long config_offset = __metal_driver_sifive_fe310_g000_hfxosc_config_offset(clock);
+#define CONFIG_ENABLE 0x40000000UL
+#define CONFIG_READY 0x80000000UL
+
+long __metal_driver_sifive_fe310_g000_hfxosc_get_rate_hz(
+ const struct metal_clock *clock) {
+ struct metal_clock *ref =
+ __metal_driver_sifive_fe310_g000_hfxosc_ref(clock);
+ long config_offset =
+ __metal_driver_sifive_fe310_g000_hfxosc_config_offset(clock);
struct __metal_driver_sifive_fe310_g000_prci *config_base =
- __metal_driver_sifive_fe310_g000_hfxosc_config_base(clock);
+ __metal_driver_sifive_fe310_g000_hfxosc_config_base(clock);
const struct __metal_driver_vtable_sifive_fe310_g000_prci *vtable =
- __metal_driver_sifive_fe310_g000_prci_vtable();
+ __metal_driver_sifive_fe310_g000_prci_vtable();
long cfg = vtable->get_reg(config_base, config_offset);
if ((cfg & CONFIG_ENABLE) == 0)
@@ -28,8 +30,8 @@ long __metal_driver_sifive_fe310_g000_hfxosc_get_rate_hz(const struct metal_cloc
return metal_clock_get_rate_hz(ref);
}
-long __metal_driver_sifive_fe310_g000_hfxosc_set_rate_hz(struct metal_clock *clock, long rate)
-{
+long __metal_driver_sifive_fe310_g000_hfxosc_set_rate_hz(
+ struct metal_clock *clock, long rate) {
return __metal_driver_sifive_fe310_g000_hfxosc_get_rate_hz(clock);
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_lfrosc.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_lfrosc.c
index 324382b9d..926ad9de8 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_lfrosc.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_lfrosc.c
@@ -21,25 +21,30 @@
#define LFROSC_REGW(addr) (__METAL_ACCESS_ONCE((__metal_io_u32 *)addr))
-long __metal_driver_sifive_fe310_g000_lfrosc_get_rate_hz(const struct metal_clock *clock)
-{
- struct metal_clock *internal_ref = __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(clock);
- struct metal_clock *external_ref = __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(clock);
-
- unsigned long int cfg_reg = __metal_driver_sifive_fe310_g000_lfrosc_config_reg(clock);
- unsigned long int mux_reg = __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(clock);
-
- if(LFROSC_REGW(mux_reg) & METAL_LFCLKMUX_EXT_MUX_STATUS) {
+long __metal_driver_sifive_fe310_g000_lfrosc_get_rate_hz(
+ const struct metal_clock *clock) {
+ struct metal_clock *internal_ref =
+ __metal_driver_sifive_fe310_g000_lfrosc_lfrosc(clock);
+ struct metal_clock *external_ref =
+ __metal_driver_sifive_fe310_g000_lfrosc_psdlfaltclk(clock);
+
+ unsigned long int cfg_reg =
+ __metal_driver_sifive_fe310_g000_lfrosc_config_reg(clock);
+ unsigned long int mux_reg =
+ __metal_driver_sifive_fe310_g000_lfrosc_mux_reg(clock);
+
+ if (LFROSC_REGW(mux_reg) & METAL_LFCLKMUX_EXT_MUX_STATUS) {
return metal_clock_get_rate_hz(external_ref);
}
- const unsigned long int div = (LFROSC_REGW(cfg_reg) & METAL_LFROSCCFG_DIV_MASK) + 1;
+ const unsigned long int div =
+ (LFROSC_REGW(cfg_reg) & METAL_LFROSCCFG_DIV_MASK) + 1;
return metal_clock_get_rate_hz(internal_ref) / div;
}
-long __metal_driver_sifive_fe310_g000_lfrosc_set_rate_hz(struct metal_clock *clock, long rate)
-{
+long __metal_driver_sifive_fe310_g000_lfrosc_set_rate_hz(
+ struct metal_clock *clock, long rate) {
return __metal_driver_sifive_fe310_g000_lfrosc_get_rate_hz(clock);
}
@@ -50,4 +55,3 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_fe310_g000_lfrosc) = {
#endif /* METAL_SIFIVE_FE310_G000_LFROSC */
typedef int no_empty_translation_units;
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_pll.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_pll.c
index 2ca468f43..5f26d32d2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_pll.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_pll.c
@@ -5,28 +5,31 @@
#ifdef METAL_SIFIVE_FE310_G000_PLL
-#include <stdio.h>
#include <limits.h>
+#include <stdio.h>
+#include <metal/init.h>
#include <metal/machine.h>
+#include <metal/machine/platform.h>
+
#include <metal/drivers/sifive_fe310-g000_pll.h>
#include <stdlib.h>
-#define PLL_R 0x00000007UL
-#define PLL_F 0x000003F0UL
-#define PLL_Q 0x00000C00UL
-#define PLL_SEL 0x00010000UL
-#define PLL_REFSEL 0x00020000UL
-#define PLL_BYPASS 0x00040000UL
-#define PLL_LOCK 0x80000000UL
+#define PLL_R 0x00000007UL
+#define PLL_F 0x000003F0UL
+#define PLL_Q 0x00000C00UL
+#define PLL_SEL 0x00010000UL
+#define PLL_REFSEL 0x00020000UL
+#define PLL_BYPASS 0x00040000UL
+#define PLL_LOCK 0x80000000UL
-#define DIV_DIV 0x0000003FUL
-#define DIV_1 0x00000100UL
+#define DIV_DIV 0x0000003FUL
+#define DIV_1 0x00000100UL
-#define PLL_R_SHIFT(r) ((r << 0) & PLL_R)
-#define PLL_F_SHIFT(f) ((f << 4) & PLL_F)
-#define PLL_Q_SHIFT(q) ((q << 10) & PLL_Q)
-#define PLL_DIV_SHIFT(d) ((d << 0) & DIV_DIV)
+#define PLL_R_SHIFT(r) ((r << 0) & PLL_R)
+#define PLL_F_SHIFT(f) ((f << 4) & PLL_F)
+#define PLL_Q_SHIFT(q) ((q << 10) & PLL_Q)
+#define PLL_DIV_SHIFT(d) ((d << 0) & DIV_DIV)
struct pll_config_t {
unsigned long multiplier;
@@ -51,79 +54,79 @@ static const struct pll_config_t pll_configs[] = {
* | | | | | | ^ d
* | | | | | | | ^
* | | | | | | | | */
- { 1, 32, 12000000, 24000000, 1, 31, 3, 63},
- { 1, 32, 24000000, 48000000, 3, 31, 2, 63},
- { 1, 16, 6000000, 12000000, 0, 31, 3, 63},
- { 1, 16, 12000000, 24000000, 1, 31, 2, 63},
- { 1, 16, 24000000, 48000000, 3, 31, 2, 31},
- { 1, 8, 6000000, 12000000, 0, 31, 3, 31},
- { 1, 8, 12000000, 24000000, 1, 31, 2, 31},
- { 1, 8, 24000000, 48000000, 3, 31, 2, 15},
- { 1, 4, 6000000, 12000000, 0, 31, 3, 15},
- { 1, 4, 12000000, 24000000, 1, 31, 2, 15},
- { 1, 4, 24000000, 48000000, 3, 31, 2, 7},
- { 1, 2, 6000000, 12000000, 0, 31, 2, 15},
- { 1, 2, 12000000, 24000000, 1, 31, 1, 15},
- { 1, 2, 24000000, 48000000, 3, 31, 1, 7},
- { 2, 1, 6000000, 12000000, 0, 31, 1, 7},
- { 2, 1, 12000000, 24000000, 1, 31, 1, 3},
- { 2, 1, 24000000, 48000000, 3, 31, 3, -1},
- { 4, 1, 6000000, 12000000, 0, 31, 3, 0},
- { 4, 1, 12000000, 24000000, 1, 31, 3, -1},
- { 4, 1, 24000000, 48000000, 3, 31, 2, -1},
- { 6, 1, 6000000, 10666666, 0, 35, 1, 2},
- { 6, 1, 10666666, 12000000, 0, 23, 3, -1},
- { 6, 1, 12000000, 16000000, 1, 47, 3, -1},
- { 6, 1, 16000000, 18000000, 1, 23, 2, -1},
- { 6, 1, 18000000, 21333333, 2, 35, 2, -1},
- { 8, 1, 6000000, 12000000, 0, 31, 3, -1},
- { 8, 1, 12000000, 24000000, 1, 31, 2, -1},
- { 8, 1, 24000000, 48000000, 3, 31, 1, -1},
- {10, 1, 6000000, 9600000, 0, 39, 3, -1},
- {10, 1, 9600000, 12000000, 0, 19, 2, -1},
- {10, 1, 12000000, 19200000, 1, 39, 2, -1},
- {10, 1, 19200000, 24000000, 1, 19, 1, -1},
- {10, 1, 24000000, 38400000, 3, 39, 1, -1},
- {12, 1, 6000000, 8000000, 0, 47, 3, -1},
- {12, 1, 8000000, 12000000, 0, 23, 2, -1},
- {12, 1, 12000000, 16000000, 1, 47, 2, -1},
- {12, 1, 16000000, 24000000, 1, 23, 1, -1},
- {12, 1, 24000000, 30000000, 3, 47, 1, -1},
- {12, 1, 30000000, 32000000, 3, 47, 1, -1},
- {14, 1, 6000000, 6857142, 0, 55, 3, -1},
- {14, 1, 6857143, 12000000, 0, 27, 2, -1},
- {14, 1, 12000000, 13714285, 1, 55, 2, -1},
- {14, 1, 13714286, 24000000, 1, 27, 1, -1},
- {14, 1, 24000000, 27428571, 3, 55, 1, -1},
- {16, 1, 6000000, 12000000, 0, 31, 2, -1},
- {16, 1, 12000000, 24000000, 1, 31, 1, -1},
- {18, 1, 6000000, 10666666, 0, 35, 2, -1},
- {18, 1, 10666667, 12000000, 0, 17, 1, -1},
- {18, 1, 12000000, 21333333, 1, 35, 1, -1},
- {20, 1, 6000000, 9600000, 0, 39, 2, -1},
- {20, 1, 9600000, 12000000, 0, 19, 1, -1},
- {20, 1, 12000000, 19200000, 1, 39, 1, -1},
- {22, 1, 6000000, 8727272, 0, 43, 2, -1},
- {22, 1, 8727273, 12000000, 0, 21, 1, -1},
- {22, 1, 12000000, 17454545, 1, 43, 1, -1},
- {24, 1, 6000000, 8000000, 0, 47, 2, -1},
- {24, 1, 8000000, 12000000, 0, 23, 1, -1},
- {24, 1, 12000000, 16000000, 1, 47, 1, -1},
- {26, 1, 6000000, 7384615, 0, 51, 2, -1},
- {26, 1, 7384616, 12000000, 0, 25, 1, -1},
- {26, 1, 12000000, 14768230, 1, 51, 1, -1},
- {28, 1, 6000000, 6857142, 0, 55, 2, -1},
- {28, 1, 6857143, 12000000, 0, 27, 1, -1},
- {28, 1, 12000000, 13714285, 1, 55, 1, -1},
- {30, 1, 6000000, 6400000, 0, 59, 2, -1},
- {30, 1, 6400000, 12000000, 0, 29, 1, -1},
- {30, 1, 12000000, 12800000, 1, 59, 1, -1},
- {32, 1, 6000000, 12000000, 0, 31, 1, -1}
-};
+ {1, 32, 12000000, 24000000, 1, 31, 3, 63},
+ {1, 32, 24000000, 48000000, 3, 31, 2, 63},
+ {1, 16, 6000000, 12000000, 0, 31, 3, 63},
+ {1, 16, 12000000, 24000000, 1, 31, 2, 63},
+ {1, 16, 24000000, 48000000, 3, 31, 2, 31},
+ {1, 8, 6000000, 12000000, 0, 31, 3, 31},
+ {1, 8, 12000000, 24000000, 1, 31, 2, 31},
+ {1, 8, 24000000, 48000000, 3, 31, 2, 15},
+ {1, 4, 6000000, 12000000, 0, 31, 3, 15},
+ {1, 4, 12000000, 24000000, 1, 31, 2, 15},
+ {1, 4, 24000000, 48000000, 3, 31, 2, 7},
+ {1, 2, 6000000, 12000000, 0, 31, 2, 15},
+ {1, 2, 12000000, 24000000, 1, 31, 1, 15},
+ {1, 2, 24000000, 48000000, 3, 31, 1, 7},
+ {2, 1, 6000000, 12000000, 0, 31, 1, 7},
+ {2, 1, 12000000, 24000000, 1, 31, 1, 3},
+ {2, 1, 24000000, 48000000, 3, 31, 3, -1},
+ {4, 1, 6000000, 12000000, 0, 31, 3, 0},
+ {4, 1, 12000000, 24000000, 1, 31, 3, -1},
+ {4, 1, 24000000, 48000000, 3, 31, 2, -1},
+ {6, 1, 6000000, 10666666, 0, 35, 1, 2},
+ {6, 1, 10666666, 12000000, 0, 23, 3, -1},
+ {6, 1, 12000000, 16000000, 1, 47, 3, -1},
+ {6, 1, 16000000, 18000000, 1, 23, 2, -1},
+ {6, 1, 18000000, 21333333, 2, 35, 2, -1},
+ {8, 1, 6000000, 12000000, 0, 31, 3, -1},
+ {8, 1, 12000000, 24000000, 1, 31, 2, -1},
+ {8, 1, 24000000, 48000000, 3, 31, 1, -1},
+ {10, 1, 6000000, 9600000, 0, 39, 3, -1},
+ {10, 1, 9600000, 12000000, 0, 19, 2, -1},
+ {10, 1, 12000000, 19200000, 1, 39, 2, -1},
+ {10, 1, 19200000, 24000000, 1, 19, 1, -1},
+ {10, 1, 24000000, 38400000, 3, 39, 1, -1},
+ {12, 1, 6000000, 8000000, 0, 47, 3, -1},
+ {12, 1, 8000000, 12000000, 0, 23, 2, -1},
+ {12, 1, 12000000, 16000000, 1, 47, 2, -1},
+ {12, 1, 16000000, 24000000, 1, 23, 1, -1},
+ {12, 1, 24000000, 30000000, 3, 47, 1, -1},
+ {12, 1, 30000000, 32000000, 3, 47, 1, -1},
+ {14, 1, 6000000, 6857142, 0, 55, 3, -1},
+ {14, 1, 6857143, 12000000, 0, 27, 2, -1},
+ {14, 1, 12000000, 13714285, 1, 55, 2, -1},
+ {14, 1, 13714286, 24000000, 1, 27, 1, -1},
+ {14, 1, 24000000, 27428571, 3, 55, 1, -1},
+ {16, 1, 6000000, 12000000, 0, 31, 2, -1},
+ {16, 1, 12000000, 24000000, 1, 31, 1, -1},
+ {18, 1, 6000000, 10666666, 0, 35, 2, -1},
+ {18, 1, 10666667, 12000000, 0, 17, 1, -1},
+ {18, 1, 12000000, 21333333, 1, 35, 1, -1},
+ {20, 1, 6000000, 9600000, 0, 39, 2, -1},
+ {20, 1, 9600000, 12000000, 0, 19, 1, -1},
+ {20, 1, 12000000, 19200000, 1, 39, 1, -1},
+ {22, 1, 6000000, 8727272, 0, 43, 2, -1},
+ {22, 1, 8727273, 12000000, 0, 21, 1, -1},
+ {22, 1, 12000000, 17454545, 1, 43, 1, -1},
+ {24, 1, 6000000, 8000000, 0, 47, 2, -1},
+ {24, 1, 8000000, 12000000, 0, 23, 1, -1},
+ {24, 1, 12000000, 16000000, 1, 47, 1, -1},
+ {26, 1, 6000000, 7384615, 0, 51, 2, -1},
+ {26, 1, 7384616, 12000000, 0, 25, 1, -1},
+ {26, 1, 12000000, 14768230, 1, 51, 1, -1},
+ {28, 1, 6000000, 6857142, 0, 55, 2, -1},
+ {28, 1, 6857143, 12000000, 0, 27, 1, -1},
+ {28, 1, 12000000, 13714285, 1, 55, 1, -1},
+ {30, 1, 6000000, 6400000, 0, 59, 2, -1},
+ {30, 1, 6400000, 12000000, 0, 29, 1, -1},
+ {30, 1, 12000000, 12800000, 1, 59, 1, -1},
+ {32, 1, 6000000, 12000000, 0, 31, 1, -1}};
#define PLL_CONFIG_NOT_VALID -1
-void __metal_driver_sifive_fe310_g000_pll_init(struct __metal_driver_sifive_fe310_g000_pll *pll);
+void __metal_driver_sifive_fe310_g000_pll_init(
+ struct __metal_driver_sifive_fe310_g000_pll *pll);
/* Given the rate of the PLL input frequency and a PLL configuration, what
* will the resulting PLL output frequency be?
@@ -131,11 +134,13 @@ void __metal_driver_sifive_fe310_g000_pll_init(struct __metal_driver_sifive_fe31
* - pll_input_rate the PLL input frequency in hertz
* - config the PLL configuration
* Returns:
- * - PLL_CONFIG_NOT_VALID if the configuration is not valid for the input frequency
+ * - PLL_CONFIG_NOT_VALID if the configuration is not valid for the input
+ * frequency
* - the output frequency, in hertz */
-static long get_pll_config_freq(unsigned long pll_input_rate, const struct pll_config_t *config)
-{
- if(pll_input_rate < config->min_input_rate || pll_input_rate > config->max_input_rate)
+static long get_pll_config_freq(unsigned long pll_input_rate,
+ const struct pll_config_t *config) {
+ if (pll_input_rate < config->min_input_rate ||
+ pll_input_rate > config->max_input_rate)
return PLL_CONFIG_NOT_VALID;
return pll_input_rate * config->multiplier / config->divisor;
@@ -143,33 +148,37 @@ static long get_pll_config_freq(unsigned long pll_input_rate, const struct pll_c
#ifdef __METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE
-static void metal_sifive_fe310_g000_pll_init(void) __attribute__((constructor));
-static void metal_sifive_fe310_g000_pll_init(void) {
+METAL_CONSTRUCTOR(metal_sifive_fe310_g000_pll_init) {
long init_rate = __metal_driver_sifive_fe310_g000_pll_init_rate();
/* If the PLL init_rate is zero, don't initialize the PLL */
- if(init_rate != 0)
- __metal_driver_sifive_fe310_g000_pll_init(__METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE);
+ if (init_rate != 0)
+ __metal_driver_sifive_fe310_g000_pll_init(
+ __METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE);
}
#endif /* __METAL_DT_SIFIVE_FE310_G000__PLL_HANDLE */
-void __metal_driver_sifive_fe310_g000_pll_init(struct __metal_driver_sifive_fe310_g000_pll *pll) {
- struct metal_clock *pllref = __metal_driver_sifive_fe310_g000_pll_pllref(&(pll->clock));
+void __metal_driver_sifive_fe310_g000_pll_init(
+ struct __metal_driver_sifive_fe310_g000_pll *pll) {
+ struct metal_clock *pllref =
+ __metal_driver_sifive_fe310_g000_pll_pllref(&(pll->clock));
long init_rate = __metal_driver_sifive_fe310_g000_pll_init_rate();
long config_offset = __metal_driver_sifive_fe310_g000_pll_config_offset();
long base = __metal_driver_sifive_fe310_g000_prci_base();
- __metal_io_u32 *pllcfg = (__metal_io_u32 *) (base + config_offset);
+ __metal_io_u32 *pllcfg = (__metal_io_u32 *)(base + config_offset);
- /* If the PLL clock has had a _pre_rate_change_callback configured, call it */
+ /* If the PLL clock has had a _pre_rate_change_callback configured, call it
+ */
_metal_clock_call_all_callbacks(pll->clock._pre_rate_change_callback);
- /* If we're running off of the PLL, switch off before we start configuring it*/
- if((__METAL_ACCESS_ONCE(pllcfg) & PLL_SEL) == 0)
+ /* If we're running off of the PLL, switch off before we start configuring
+ * it*/
+ if ((__METAL_ACCESS_ONCE(pllcfg) & PLL_SEL) != 0)
__METAL_ACCESS_ONCE(pllcfg) &= ~(PLL_SEL);
/* Make sure we're running off of the external oscillator for stability */
- if(pllref != NULL)
+ if (pllref != NULL)
__METAL_ACCESS_ONCE(pllcfg) |= PLL_REFSEL;
/* Configure the PLL to run at the requested init frequency.
@@ -181,18 +190,22 @@ void __metal_driver_sifive_fe310_g000_pll_init(struct __metal_driver_sifive_fe31
_metal_clock_call_all_callbacks(pll->clock._post_rate_change_callback);
}
-long __metal_driver_sifive_fe310_g000_pll_get_rate_hz(const struct metal_clock *clock)
-{
- struct metal_clock *pllref = __metal_driver_sifive_fe310_g000_pll_pllref(clock);
- struct metal_clock *pllsel0 = __metal_driver_sifive_fe310_g000_pll_pllsel0(clock);
- long config_offset = __metal_driver_sifive_fe310_g000_pll_config_offset(clock);
+long __metal_driver_sifive_fe310_g000_pll_get_rate_hz(
+ const struct metal_clock *clock) {
+ struct metal_clock *pllref =
+ __metal_driver_sifive_fe310_g000_pll_pllref(clock);
+ struct metal_clock *pllsel0 =
+ __metal_driver_sifive_fe310_g000_pll_pllsel0(clock);
+ long config_offset =
+ __metal_driver_sifive_fe310_g000_pll_config_offset(clock);
struct __metal_driver_sifive_fe310_g000_prci *config_base =
- __metal_driver_sifive_fe310_g000_pll_config_base(clock);
- long divider_offset = __metal_driver_sifive_fe310_g000_pll_divider_offset(clock);
+ __metal_driver_sifive_fe310_g000_pll_config_base(clock);
+ long divider_offset =
+ __metal_driver_sifive_fe310_g000_pll_divider_offset(clock);
struct __metal_driver_sifive_fe310_g000_prci *divider_base =
- __metal_driver_sifive_fe310_g000_pll_divider_base(clock);
+ __metal_driver_sifive_fe310_g000_pll_divider_base(clock);
const struct __metal_driver_vtable_sifive_fe310_g000_prci *vtable =
- __metal_driver_sifive_fe310_g000_prci_vtable();
+ __metal_driver_sifive_fe310_g000_prci_vtable();
long cfg = vtable->get_reg(config_base, config_offset);
long div = vtable->get_reg(divider_base, divider_offset);
@@ -204,7 +217,8 @@ long __metal_driver_sifive_fe310_g000_pll_get_rate_hz(const struct metal_clock *
/* There's a clock mux before the PLL that selects between the HFROSC adn
* the HFXOSC as the PLL's input clock. */
- long ref_hz = metal_clock_get_rate_hz(__METAL_GET_FIELD(cfg, PLL_REFSEL) ? pllref : pllsel0);
+ long ref_hz = metal_clock_get_rate_hz(
+ __METAL_GET_FIELD(cfg, PLL_REFSEL) ? pllref : pllsel0);
/* It's possible to bypass the PLL, which is an internal bpyass. This
* still obays the PLL's input clock mu. */
@@ -236,21 +250,19 @@ long __metal_driver_sifive_fe310_g000_pll_get_rate_hz(const struct metal_clock *
* Returns:
* -1 if no valid configuration is available
* the index into pll_configs of a valid configuration */
-static int find_closest_config(long ref_hz, long rate)
-{
+static int find_closest_config(long ref_hz, long rate) {
int closest_index = -1;
long closest_diff = LONG_MAX;
/* We're probably trying for a fast output frequency, so start from
* the high end of the configs. */
- for(int i = (sizeof(pll_configs) / sizeof(pll_configs[0])) - 1; i >= 0; i--)
- {
+ for (int i = (sizeof(pll_configs) / sizeof(pll_configs[0])) - 1; i >= 0;
+ i--) {
long config_freq = get_pll_config_freq(ref_hz, &(pll_configs[i]));
- if(config_freq != PLL_CONFIG_NOT_VALID)
- {
- long freq_diff = abs(config_freq - rate);
- if(freq_diff < closest_diff)
- {
+ if (config_freq != PLL_CONFIG_NOT_VALID) {
+ long freq_diff = labs(config_freq - rate);
+
+ if (freq_diff < closest_diff) {
closest_index = i;
closest_diff = freq_diff;
}
@@ -260,9 +272,22 @@ static int find_closest_config(long ref_hz, long rate)
return closest_index;
}
+/* The PLL needs 100 usec to stabilize before we test PLL_LOCK. Since LFROSC
+ * on all targets with the FE310-G000 PLL runs at 32768 Hz, we need to wait
+ * at least
+ *
+ * ceil(100 usec * 32768 ticks/sec * 1 sec / 1000000 usec) = 4 ticks
+ *
+ * of mtime before we test PLL_LOCK.
+ *
+ * TODO: Determine the mtime timebase at compile or runtime and use that
+ * here.
+ */
+#define PLL_LOCK_WAIT_TICKS 4
+
/* Configure the PLL and wait for it to lock */
-static void configure_pll(__metal_io_u32 *pllcfg, __metal_io_u32 *plloutdiv, const struct pll_config_t *config)
-{
+static void configure_pll(__metal_io_u32 *pllcfg, __metal_io_u32 *plloutdiv,
+ const struct pll_config_t *config) {
__METAL_ACCESS_ONCE(pllcfg) &= ~(PLL_R);
__METAL_ACCESS_ONCE(pllcfg) |= PLL_R_SHIFT(config->r);
@@ -272,16 +297,13 @@ static void configure_pll(__metal_io_u32 *pllcfg, __metal_io_u32 *plloutdiv, con
__METAL_ACCESS_ONCE(pllcfg) &= ~(PLL_Q);
__METAL_ACCESS_ONCE(pllcfg) |= PLL_Q_SHIFT(config->q);
- if(config->d < 0)
- {
+ if (config->d < 0) {
/* disable final divider */
__METAL_ACCESS_ONCE(plloutdiv) |= DIV_1;
__METAL_ACCESS_ONCE(plloutdiv) &= ~(DIV_DIV);
__METAL_ACCESS_ONCE(plloutdiv) |= PLL_DIV_SHIFT(1);
- }
- else
- {
+ } else {
__METAL_ACCESS_ONCE(plloutdiv) &= ~(DIV_1);
__METAL_ACCESS_ONCE(plloutdiv) &= ~(DIV_DIV);
@@ -290,20 +312,49 @@ static void configure_pll(__metal_io_u32 *pllcfg, __metal_io_u32 *plloutdiv, con
__METAL_ACCESS_ONCE(pllcfg) &= ~(PLL_BYPASS);
+ /* Wait for the PLL to stabilize before testing it for lock */
+#ifdef __METAL_DT_RISCV_CLINT0_HANDLE
+ unsigned long long mtime, mtime_end;
+ __metal_driver_riscv_clint0_command_request(__METAL_DT_RISCV_CLINT0_HANDLE,
+ METAL_TIMER_MTIME_GET, &mtime);
+ mtime_end = mtime + PLL_LOCK_WAIT_TICKS;
+ while (mtime <= mtime_end) {
+ __metal_driver_riscv_clint0_command_request(
+ __METAL_DT_RISCV_CLINT0_HANDLE, METAL_TIMER_MTIME_GET, &mtime);
+ }
+#elif __METAL_DT_RISCV_CLIC0_HANDLE
+ unsigned long long mtime, mtime_end;
+ __metal_driver_sifive_clic0_command_request(__METAL_DT_RISCV_CLIC0_HANDLE,
+ METAL_TIMER_MTIME_GET, &mtime);
+ mtime_end = mtime + PLL_LOCK_WAIT_TICKS;
+ while (mtime <= mtime_end) {
+ __metal_driver_sifive_clic0_command_request(
+ __METAL_DT_RISCV_CLIC0_HANDLE, METAL_TIMER_MTIME_GET, &mtime);
+ }
+#else
+#pragma message( \
+ No handle for CLINT or CLIC found, PLL might race with lock signal !)
+#endif
+
/* Wait for PLL to lock */
- while((__METAL_ACCESS_ONCE(pllcfg) & PLL_LOCK) == 0) ;
+ while ((__METAL_ACCESS_ONCE(pllcfg) & PLL_LOCK) == 0)
+ ;
}
-long __metal_driver_sifive_fe310_g000_pll_set_rate_hz(struct metal_clock *clock, long rate)
-{
- struct metal_clock *pllref = __metal_driver_sifive_fe310_g000_pll_pllref(clock);
- struct metal_clock *pllsel0 = __metal_driver_sifive_fe310_g000_pll_pllsel0(clock);
- long config_offset = __metal_driver_sifive_fe310_g000_pll_config_offset(clock);
- long divider_offset = __metal_driver_sifive_fe310_g000_pll_divider_offset(clock);
+long __metal_driver_sifive_fe310_g000_pll_set_rate_hz(struct metal_clock *clock,
+ long rate) {
+ struct metal_clock *pllref =
+ __metal_driver_sifive_fe310_g000_pll_pllref(clock);
+ struct metal_clock *pllsel0 =
+ __metal_driver_sifive_fe310_g000_pll_pllsel0(clock);
+ long config_offset =
+ __metal_driver_sifive_fe310_g000_pll_config_offset(clock);
+ long divider_offset =
+ __metal_driver_sifive_fe310_g000_pll_divider_offset(clock);
long base = __metal_driver_sifive_fe310_g000_prci_base();
- __metal_io_u32 *pllcfg = (__metal_io_u32 *) (base + config_offset);
- __metal_io_u32 *plloutdiv = (__metal_io_u32 *) (base + divider_offset);
+ __metal_io_u32 *pllcfg = (__metal_io_u32 *)(base + config_offset);
+ __metal_io_u32 *plloutdiv = (__metal_io_u32 *)(base + divider_offset);
/* We can't modify the PLL if coreclk is driven by it, so switch it off */
if (__METAL_ACCESS_ONCE(pllcfg) & PLL_SEL)
@@ -311,22 +362,18 @@ long __metal_driver_sifive_fe310_g000_pll_set_rate_hz(struct metal_clock *clock,
/* There's a clock mux before the PLL that selects between the HFROSC and
* the HFXOSC as the PLL's input clock. */
- long ref_hz = metal_clock_get_rate_hz(__METAL_ACCESS_ONCE(pllcfg) & PLL_REFSEL ? pllref : pllsel0);
+ long ref_hz = metal_clock_get_rate_hz(
+ __METAL_ACCESS_ONCE(pllcfg) & PLL_REFSEL ? pllref : pllsel0);
- /* if the desired rate is within 75%-125% of the input clock, bypass the PLL */
- if((ref_hz * 3 / 4) <= rate && (ref_hz * 5 / 4) >= rate)
- {
+ /* if the desired rate is within 75%-125% of the input clock, bypass the PLL
+ */
+ if ((ref_hz * 3 / 4) <= rate && (ref_hz * 5 / 4) >= rate) {
__METAL_ACCESS_ONCE(pllcfg) |= PLL_BYPASS;
- }
- else
- {
+ } else {
int config_index = find_closest_config(ref_hz, rate);
- if(config_index != -1)
- {
+ if (config_index != -1) {
configure_pll(pllcfg, plloutdiv, &(pll_configs[config_index]));
- }
- else
- {
+ } else {
/* unable to find a valid configuration */
__METAL_ACCESS_ONCE(pllcfg) |= PLL_BYPASS;
}
@@ -339,13 +386,10 @@ long __metal_driver_sifive_fe310_g000_pll_set_rate_hz(struct metal_clock *clock,
}
#ifdef __METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE
-static void use_hfxosc(void) __attribute__((constructor));
-static void use_hfxosc(void)
-{
+METAL_CONSTRUCTOR(use_hfxosc) {
long init_rate = __metal_driver_sifive_fe310_g000_pll_init_rate();
- metal_clock_set_rate_hz(
- &__METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE->clock, init_rate
- );
+ metal_clock_set_rate_hz(&__METAL_DT_SIFIVE_FE310_G000_PLL_HANDLE->clock,
+ init_rate);
}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_prci.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_prci.c
index 1236eca3b..f863feb3d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_prci.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fe310-g000_prci.c
@@ -8,12 +8,15 @@
#include <metal/drivers/sifive_fe310-g000_prci.h>
#include <metal/machine.h>
-long __metal_driver_sifive_fe310_g000_prci_get_reg(const struct __metal_driver_sifive_fe310_g000_prci *prci, long offset) {
+long __metal_driver_sifive_fe310_g000_prci_get_reg(
+ const struct __metal_driver_sifive_fe310_g000_prci *prci, long offset) {
unsigned long base = __metal_driver_sifive_fe310_g000_prci_base();
return __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + offset));
}
-long __metal_driver_sifive_fe310_g000_prci_set_reg(const struct __metal_driver_sifive_fe310_g000_prci *prci, long offset, long value) {
+long __metal_driver_sifive_fe310_g000_prci_set_reg(
+ const struct __metal_driver_sifive_fe310_g000_prci *prci, long offset,
+ long value) {
unsigned long base = __metal_driver_sifive_fe310_g000_prci_base();
return __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + offset)) = value;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fu540-c000_l2.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fu540-c000_l2.c
deleted file mode 100644
index aafc6e5e3..000000000
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_fu540-c000_l2.c
+++ /dev/null
@@ -1,84 +0,0 @@
-/* Copyright 2018 SiFive, Inc */
-/* SPDX-License-Identifier: Apache-2.0 */
-
-#include <metal/machine/platform.h>
-
-#ifdef METAL_SIFIVE_FU540_C000_L2
-
-#include <stdint.h>
-#include <metal/io.h>
-#include <metal/drivers/sifive_fu540-c000_l2.h>
-#include <metal/machine.h>
-
-#define L2_CONFIG_WAYS_SHIFT 8
-#define L2_CONFIG_WAYS_MASK (0xFF << L2_CONFIG_WAYS_SHIFT)
-
-void __metal_driver_sifive_fu540_c000_l2_init(struct metal_cache *l2, int ways);
-
-static void metal_driver_sifive_fu540_c000_l2_init(void) __attribute__((constructor));
-static void metal_driver_sifive_fu540_c000_l2_init(void)
-{
-#ifdef __METAL_DT_SIFIVE_FU540_C000_L2_HANDLE
- /* Get the handle for the L2 cache controller */
- struct metal_cache *l2 = __METAL_DT_SIFIVE_FU540_C000_L2_HANDLE;
- if(!l2) {
- return;
- }
-
- /* Get the number of available ways per bank */
- unsigned long control_base = __metal_driver_sifive_fu540_c000_l2_control_base(l2);
- uint32_t ways = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_FU540_C000_L2_CONFIG));
- ways = ((ways & L2_CONFIG_WAYS_MASK) >> L2_CONFIG_WAYS_SHIFT);
-
- /* Enable all the ways */
- __metal_driver_sifive_fu540_c000_l2_init(l2, ways);
-#endif
-}
-
-void __metal_driver_sifive_fu540_c000_l2_init(struct metal_cache *l2, int ways)
-{
- metal_cache_set_enabled_ways(l2, ways);
-}
-
-int __metal_driver_sifive_fu540_c000_l2_get_enabled_ways(struct metal_cache *cache)
-{
- unsigned long control_base = __metal_driver_sifive_fu540_c000_l2_control_base(cache);
-
- uint32_t way_enable = __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_FU540_C000_L2_WAYENABLE));
-
- /* The stored number is the index, so add one */
- return (0xFF & way_enable) + 1;
-}
-
-int __metal_driver_sifive_fu540_c000_l2_set_enabled_ways(struct metal_cache *cache, int ways)
-{
- unsigned long control_base = __metal_driver_sifive_fu540_c000_l2_control_base(cache);
-
- /* We can't decrease the number of enabled ways */
- if(metal_cache_get_enabled_ways(cache) > ways) {
- return -2;
- }
-
- /* The stored value is the index, so subtract one */
- uint32_t value = 0xFF & (ways - 1);
-
- /* Set the number of enabled ways */
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(control_base + METAL_SIFIVE_FU540_C000_L2_WAYENABLE)) = value;
-
- /* Make sure the number of ways was set correctly */
- if(metal_cache_get_enabled_ways(cache) != ways) {
- return -3;
- }
-
- return 0;
-}
-
-__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_fu540_c000_l2) = {
- .cache.init = __metal_driver_sifive_fu540_c000_l2_init,
- .cache.get_enabled_ways = __metal_driver_sifive_fu540_c000_l2_get_enabled_ways,
- .cache.set_enabled_ways = __metal_driver_sifive_fu540_c000_l2_set_enabled_ways,
-};
-
-#endif
-
-typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_global-external-interrupts0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_global-external-interrupts0.c
index 0d56bafef..3fd96b91d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_global-external-interrupts0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_global-external-interrupts0.c
@@ -5,44 +5,51 @@
#ifdef METAL_SIFIVE_GLOBAL_EXTERNAL_INTERRUPTS0
-#include <metal/io.h>
-#include <metal/shutdown.h>
#include <metal/drivers/sifive_global-external-interrupts0.h>
+#include <metal/io.h>
#include <metal/machine.h>
+#include <metal/shutdown.h>
-void __metal_driver_sifive_global_external_interrupt_init(struct metal_interrupt *controller)
-{
+void __metal_driver_sifive_global_external_interrupt_init(
+ struct metal_interrupt *controller) {
struct __metal_driver_sifive_global_external_interrupts0 *global0;
- global0 = (struct __metal_driver_sifive_global_external_interrupts0 *)(controller);
- if ( !global0->init_done ) {
+ global0 = (struct __metal_driver_sifive_global_external_interrupts0
+ *)(controller);
+ if (!global0->init_done) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
-
- if (intc) {
- intc->vtable->interrupt_init(intc);
- /* Register its interrupts with with parent controller */
- for (int i = 0;
- i < __metal_driver_sifive_global_external_interrupts0_num_interrupts(controller);
- i++) {
- intc->vtable->interrupt_register(intc,
- __metal_driver_sifive_global_external_interrupts0_interrupt_lines(controller, i),
- NULL, controller);
- }
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
+
+ if (intc) {
+ intc->vtable->interrupt_init(intc);
+ /* Register its interrupts with with parent controller */
+ for (
+ int i = 0;
+ i <
+ __metal_driver_sifive_global_external_interrupts0_num_interrupts(
+ controller);
+ i++) {
+ intc->vtable->interrupt_register(
+ intc,
+ __metal_driver_sifive_global_external_interrupts0_interrupt_lines(
+ controller, i),
+ NULL, controller);
+ }
global0->init_done = 1;
- }
+ }
}
}
-int __metal_driver_sifive_global_external_interrupt_register(struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_sifive_global_external_interrupt_register(
+ struct metal_interrupt *controller, int id, metal_interrupt_handler_t isr,
+ void *priv) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -52,13 +59,14 @@ int __metal_driver_sifive_global_external_interrupt_register(struct metal_interr
return rc;
}
-int __metal_driver_sifive_global_external_interrupt_enable(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_global_external_interrupt_enable(
+ struct metal_interrupt *controller, int id) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -68,13 +76,14 @@ int __metal_driver_sifive_global_external_interrupt_enable(struct metal_interrup
return rc;
}
-int __metal_driver_sifive_global_external_interrupt_disable(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_global_external_interrupt_disable(
+ struct metal_interrupt *controller, int id) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -84,21 +93,22 @@ int __metal_driver_sifive_global_external_interrupt_disable(struct metal_interru
return rc;
}
-int __metal_driver_sifive_global_external_interrupt_set_threshold(struct metal_interrupt *controller,
- unsigned int threshold)
-{
+int __metal_driver_sifive_global_external_interrupt_set_threshold(
+ struct metal_interrupt *controller, unsigned int threshold) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
if (intc) {
return intc->vtable->interrupt_set_threshold(intc, threshold);
}
return -1;
}
-unsigned int __metal_driver_sifive_global_external_interrupt_get_threshold(struct metal_interrupt *controller)
-{
+unsigned int __metal_driver_sifive_global_external_interrupt_get_threshold(
+ struct metal_interrupt *controller) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
if (intc) {
return intc->vtable->interrupt_get_threshold(intc);
@@ -106,21 +116,22 @@ unsigned int __metal_driver_sifive_global_external_interrupt_get_threshold(struc
return 0;
}
-int __metal_driver_sifive_global_external_interrupt_set_priority(struct metal_interrupt *controller,
- int id, unsigned int priority)
-{
+int __metal_driver_sifive_global_external_interrupt_set_priority(
+ struct metal_interrupt *controller, int id, unsigned int priority) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
if (intc) {
return intc->vtable->interrupt_set_priority(intc, id, priority);
}
return -1;
}
-unsigned int __metal_driver_sifive_global_external_interrupt_get_priority(struct metal_interrupt *controller, int id)
-{
+unsigned int __metal_driver_sifive_global_external_interrupt_get_priority(
+ struct metal_interrupt *controller, int id) {
struct metal_interrupt *intc =
- __metal_driver_sifive_global_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_global_external_interrupts0_interrupt_parent(
+ controller);
if (intc) {
return intc->vtable->interrupt_get_priority(intc, id);
@@ -128,21 +139,23 @@ unsigned int __metal_driver_sifive_global_external_interrupt_get_priority(struct
return 0;
}
-int __metal_driver_sifive_global_external_command_request (struct metal_interrupt *controller,
- int command, void *data)
-{
+int __metal_driver_sifive_global_external_command_request(
+ struct metal_interrupt *controller, int command, void *data) {
int idx;
int rc = -1;
switch (command) {
case METAL_MAX_INTERRUPT_GET:
- rc = __metal_driver_sifive_global_external_interrupts0_num_interrupts(controller);
+ rc = __metal_driver_sifive_global_external_interrupts0_num_interrupts(
+ controller);
break;
case METAL_INDEX_INTERRUPT_GET:
rc = 0;
if (data) {
idx = *(int *)data;
- rc = __metal_driver_sifive_global_external_interrupts0_interrupt_lines(controller, idx);
+ rc =
+ __metal_driver_sifive_global_external_interrupts0_interrupt_lines(
+ controller, idx);
}
break;
default:
@@ -152,16 +165,26 @@ int __metal_driver_sifive_global_external_command_request (struct metal_interrup
return rc;
}
-__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_global_external_interrupts0) = {
- .global0_vtable.interrupt_init = __metal_driver_sifive_global_external_interrupt_init,
- .global0_vtable.interrupt_register = __metal_driver_sifive_global_external_interrupt_register,
- .global0_vtable.interrupt_enable = __metal_driver_sifive_global_external_interrupt_enable,
- .global0_vtable.interrupt_disable = __metal_driver_sifive_global_external_interrupt_disable,
- .global0_vtable.interrupt_get_threshold = __metal_driver_sifive_global_external_interrupt_get_threshold,
- .global0_vtable.interrupt_set_threshold = __metal_driver_sifive_global_external_interrupt_set_threshold,
- .global0_vtable.interrupt_get_priority = __metal_driver_sifive_global_external_interrupt_get_priority,
- .global0_vtable.interrupt_set_priority = __metal_driver_sifive_global_external_interrupt_set_priority,
- .global0_vtable.command_request = __metal_driver_sifive_global_external_command_request,
+__METAL_DEFINE_VTABLE(
+ __metal_driver_vtable_sifive_global_external_interrupts0) = {
+ .global0_vtable.interrupt_init =
+ __metal_driver_sifive_global_external_interrupt_init,
+ .global0_vtable.interrupt_register =
+ __metal_driver_sifive_global_external_interrupt_register,
+ .global0_vtable.interrupt_enable =
+ __metal_driver_sifive_global_external_interrupt_enable,
+ .global0_vtable.interrupt_disable =
+ __metal_driver_sifive_global_external_interrupt_disable,
+ .global0_vtable.interrupt_get_threshold =
+ __metal_driver_sifive_global_external_interrupt_get_threshold,
+ .global0_vtable.interrupt_set_threshold =
+ __metal_driver_sifive_global_external_interrupt_set_threshold,
+ .global0_vtable.interrupt_get_priority =
+ __metal_driver_sifive_global_external_interrupt_get_priority,
+ .global0_vtable.interrupt_set_priority =
+ __metal_driver_sifive_global_external_interrupt_set_priority,
+ .global0_vtable.command_request =
+ __metal_driver_sifive_global_external_command_request,
};
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-buttons.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-buttons.c
index 923fe2711..119bd8abe 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-buttons.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-buttons.c
@@ -5,13 +5,12 @@
#ifdef METAL_SIFIVE_GPIO_BUTTONS
-#include <string.h>
#include <metal/drivers/riscv_cpu.h>
#include <metal/drivers/sifive_gpio-buttons.h>
#include <metal/machine.h>
+#include <string.h>
-int __metal_driver_button_exist (struct metal_button *button, char *label)
-{
+int __metal_driver_button_exist(struct metal_button *button, char *label) {
if (strcmp(__metal_driver_sifive_gpio_button_label(button), label) == 0) {
return 1;
}
@@ -19,36 +18,33 @@ int __metal_driver_button_exist (struct metal_button *button, char *label)
}
struct metal_interrupt *
-__metal_driver_button_interrupt_controller(struct metal_button *button)
-{
+__metal_driver_button_interrupt_controller(struct metal_button *button) {
return __metal_driver_sifive_gpio_button_interrupt_controller(button);
}
-int __metal_driver_button_get_interrupt_id(struct metal_button *button)
-{
+int __metal_driver_button_get_interrupt_id(struct metal_button *button) {
int irq, max_irq;
struct metal_interrupt *irc;
irq = __metal_driver_sifive_gpio_button_interrupt_line(button);
- irc = __metal_driver_sifive_gpio_button_interrupt_controller(button);
+ irc = __metal_driver_sifive_gpio_button_interrupt_controller(button);
if (irc != NULL) {
- max_irq = _metal_interrupt_command_request(irc,
- METAL_MAX_INTERRUPT_GET,
+ max_irq = _metal_interrupt_command_request(irc, METAL_MAX_INTERRUPT_GET,
NULL);
if (irq < max_irq) {
- return _metal_interrupt_command_request(irc,
- METAL_INDEX_INTERRUPT_GET,
- (void *)&irq);
+ return _metal_interrupt_command_request(
+ irc, METAL_INDEX_INTERRUPT_GET, (void *)&irq);
}
}
return METAL_INTERRUPT_ID_LCMX;
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_button) = {
- .button_vtable.button_exist = __metal_driver_button_exist,
- .button_vtable.interrupt_controller = __metal_driver_button_interrupt_controller,
+ .button_vtable.button_exist = __metal_driver_button_exist,
+ .button_vtable.interrupt_controller =
+ __metal_driver_button_interrupt_controller,
.button_vtable.get_interrupt_id = __metal_driver_button_get_interrupt_id,
};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-leds.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-leds.c
index a6b627458..ef32528c8 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-leds.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-leds.c
@@ -5,79 +5,74 @@
#ifdef METAL_SIFIVE_GPIO_LEDS
-#include <string.h>
-#include <metal/gpio.h>
#include <metal/drivers/sifive_gpio-leds.h>
+#include <metal/gpio.h>
#include <metal/machine.h>
+#include <string.h>
-int __metal_driver_led_exist (struct metal_led *led, char *label)
-{
+int __metal_driver_led_exist(struct metal_led *led, char *label) {
if (strcmp(__metal_driver_sifive_gpio_led_label(led), label) == 0) {
return 1;
}
return 0;
}
-void __metal_driver_led_enable (struct metal_led *led)
-{
+void __metal_driver_led_enable(struct metal_led *led) {
int pin;
struct metal_gpio *gpio;
pin = __metal_driver_sifive_gpio_led_pin(led);
- gpio = __metal_driver_sifive_gpio_led_gpio(led);
+ gpio = __metal_driver_sifive_gpio_led_gpio(led);
if (gpio != NULL) {
/* Configure LED as output */
- metal_gpio_disable_input((struct metal_gpio *) gpio, pin);
- metal_gpio_enable_output((struct metal_gpio *) gpio, pin);
+ metal_gpio_disable_input((struct metal_gpio *)gpio, pin);
+ metal_gpio_enable_output((struct metal_gpio *)gpio, pin);
}
}
-void __metal_driver_led_on (struct metal_led *led)
-{
+void __metal_driver_led_on(struct metal_led *led) {
int pin;
struct metal_gpio *gpio;
pin = __metal_driver_sifive_gpio_led_pin(led);
- gpio = __metal_driver_sifive_gpio_led_gpio(led);
+ gpio = __metal_driver_sifive_gpio_led_gpio(led);
if (gpio != NULL) {
- metal_gpio_set_pin((struct metal_gpio *) gpio, pin, 1);
+ metal_gpio_set_pin((struct metal_gpio *)gpio, pin, 1);
}
}
-void __metal_driver_led_off (struct metal_led *led)
-{
+void __metal_driver_led_off(struct metal_led *led) {
int pin;
struct metal_gpio *gpio;
pin = __metal_driver_sifive_gpio_led_pin(led);
- gpio = __metal_driver_sifive_gpio_led_gpio(led);
+ gpio = __metal_driver_sifive_gpio_led_gpio(led);
if (gpio != NULL) {
- metal_gpio_set_pin((struct metal_gpio *) gpio, pin, 0);
+ metal_gpio_set_pin((struct metal_gpio *)gpio, pin, 0);
}
}
-void __metal_driver_led_toggle (struct metal_led *led)
-{
+void __metal_driver_led_toggle(struct metal_led *led) {
int pin;
struct metal_gpio *gpio;
pin = __metal_driver_sifive_gpio_led_pin(led);
- gpio = __metal_driver_sifive_gpio_led_gpio(led);
+ gpio = __metal_driver_sifive_gpio_led_gpio(led);
if (gpio != NULL) {
- metal_gpio_toggle_pin((struct metal_gpio *) gpio, pin);
+ metal_gpio_toggle_pin((struct metal_gpio *)gpio, pin);
}
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_led) = {
- .led_vtable.led_exist = __metal_driver_led_exist,
- .led_vtable.led_enable = __metal_driver_led_enable,
- .led_vtable.led_on = __metal_driver_led_on,
- .led_vtable.led_off = __metal_driver_led_off,
- .led_vtable.led_toggle = __metal_driver_led_toggle,
+ .led_vtable.led_exist = __metal_driver_led_exist,
+ .led_vtable.led_enable = __metal_driver_led_enable,
+ .led_vtable.led_on = __metal_driver_led_on,
+ .led_vtable.led_off = __metal_driver_led_off,
+ .led_vtable.led_toggle = __metal_driver_led_toggle,
};
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-switches.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-switches.c
index fa0a819f1..dc0adb792 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-switches.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio-switches.c
@@ -5,13 +5,12 @@
#ifdef METAL_SIFIVE_GPIO_SWITCHES
-#include <string.h>
#include <metal/drivers/riscv_cpu.h>
#include <metal/drivers/sifive_gpio-switches.h>
#include <metal/machine.h>
+#include <string.h>
-int __metal_driver_switch_exist (struct metal_switch *flip, char *label)
-{
+int __metal_driver_switch_exist(struct metal_switch *flip, char *label) {
if (strcmp(__metal_driver_sifive_gpio_switch_label(flip), label) == 0) {
return 1;
}
@@ -19,35 +18,32 @@ int __metal_driver_switch_exist (struct metal_switch *flip, char *label)
}
struct metal_interrupt *
-__metal_driver_switch_interrupt_controller(struct metal_switch *flip)
-{
+__metal_driver_switch_interrupt_controller(struct metal_switch *flip) {
return __metal_driver_sifive_gpio_switch_interrupt_controller(flip);
}
-int __metal_driver_switch_get_interrupt_id(struct metal_switch *flip)
-{
+int __metal_driver_switch_get_interrupt_id(struct metal_switch *flip) {
int irq, max_irq;
struct metal_interrupt *irc;
irq = __metal_driver_sifive_gpio_switch_interrupt_line(flip);
- irc = __metal_driver_sifive_gpio_switch_interrupt_controller(flip);
+ irc = __metal_driver_sifive_gpio_switch_interrupt_controller(flip);
if (irc != NULL) {
- max_irq = _metal_interrupt_command_request(irc,
- METAL_MAX_INTERRUPT_GET,
+ max_irq = _metal_interrupt_command_request(irc, METAL_MAX_INTERRUPT_GET,
NULL);
if (irq < max_irq) {
- return _metal_interrupt_command_request(irc,
- METAL_INDEX_INTERRUPT_GET,
- (void *)&irq);
+ return _metal_interrupt_command_request(
+ irc, METAL_INDEX_INTERRUPT_GET, (void *)&irq);
}
}
return METAL_INTERRUPT_ID_LCMX;
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_switch) = {
- .switch_vtable.switch_exist = __metal_driver_switch_exist,
- .switch_vtable.interrupt_controller = __metal_driver_switch_interrupt_controller,
+ .switch_vtable.switch_exist = __metal_driver_switch_exist,
+ .switch_vtable.interrupt_controller =
+ __metal_driver_switch_interrupt_controller,
.switch_vtable.get_interrupt_id = __metal_driver_switch_get_interrupt_id,
};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio0.c
index 9ebbea03c..1324eb6e1 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_gpio0.c
@@ -9,209 +9,243 @@
#include <metal/io.h>
#include <metal/machine.h>
-int __metal_driver_sifive_gpio0_enable_input(struct metal_gpio *ggpio, long source)
-{
+int __metal_driver_sifive_gpio0_enable_input(struct metal_gpio *ggpio,
+ long source) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_INPUT_EN)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_INPUT_EN)) |= source;
return 0;
}
-int __metal_driver_sifive_gpio0_disable_input(struct metal_gpio *ggpio, long source)
-{
+int __metal_driver_sifive_gpio0_disable_input(struct metal_gpio *ggpio,
+ long source) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_INPUT_EN)) &= ~source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_INPUT_EN)) &= ~source;
return 0;
}
-long __metal_driver_sifive_gpio0_input(struct metal_gpio *ggpio)
-{
+long __metal_driver_sifive_gpio0_input(struct metal_gpio *ggpio) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- return __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_VALUE));
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_VALUE));
}
-long __metal_driver_sifive_gpio0_output(struct metal_gpio *ggpio)
-{
+long __metal_driver_sifive_gpio0_output(struct metal_gpio *ggpio) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- return __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT));
+ return __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT));
}
-
-int __metal_driver_sifive_gpio0_disable_output(struct metal_gpio *ggpio, long source)
-{
+int __metal_driver_sifive_gpio0_disable_output(struct metal_gpio *ggpio,
+ long source) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_OUTPUT_EN)) &= ~source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_OUTPUT_EN)) &= ~source;
return 0;
}
-int __metal_driver_sifive_gpio0_enable_output(struct metal_gpio *ggpio, long source)
-{
+int __metal_driver_sifive_gpio0_enable_output(struct metal_gpio *ggpio,
+ long source) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_OUTPUT_EN)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_OUTPUT_EN)) |= source;
return 0;
}
-int __metal_driver_sifive_gpio0_output_set(struct metal_gpio *ggpio, long value)
-{
+int __metal_driver_sifive_gpio0_output_set(struct metal_gpio *ggpio,
+ long value) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) |= value;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) |=
+ value;
return 0;
}
-int __metal_driver_sifive_gpio0_output_clear(struct metal_gpio *ggpio, long value)
-{
+int __metal_driver_sifive_gpio0_output_clear(struct metal_gpio *ggpio,
+ long value) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) &= ~value;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) &=
+ ~value;
return 0;
}
-int __metal_driver_sifive_gpio0_output_toggle(struct metal_gpio *ggpio, long value)
-{
+int __metal_driver_sifive_gpio0_output_toggle(struct metal_gpio *ggpio,
+ long value) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
__METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) =
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) ^ value;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_PORT)) ^
+ value;
return 0;
}
-int __metal_driver_sifive_gpio0_enable_io(struct metal_gpio *ggpio, long source, long dest)
-{
+int __metal_driver_sifive_gpio0_enable_io(struct metal_gpio *ggpio, long source,
+ long dest) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_SEL)) &= ~source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_EN)) |= dest;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_SEL)) |= source;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_EN)) |=
+ dest;
return 0;
}
-int __metal_driver_sifive_gpio0_disable_io(struct metal_gpio *ggpio, long source)
-{
+int __metal_driver_sifive_gpio0_disable_io(struct metal_gpio *ggpio,
+ long source) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_EN)) &= ~source;
+ __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_IOF_EN)) &=
+ ~source;
return 0;
}
-int __metal_driver_sifive_gpio0_config_int(struct metal_gpio *ggpio, long source, int intr_type)
-{
+int __metal_driver_sifive_gpio0_config_int(struct metal_gpio *ggpio,
+ long source, int intr_type) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- switch (intr_type)
- {
- case METAL_GPIO_INT_DISABLE:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) &= ~source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) &= ~source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) &= ~source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) &= ~source;
- break;
- case METAL_GPIO_INT_RISING:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
- break;
- case METAL_GPIO_INT_FALLING:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
- break;
- case METAL_GPIO_INT_BOTH_EDGE:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
- break;
- case METAL_GPIO_INT_HIGH:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
- break;
- case METAL_GPIO_INT_LOW:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
- break;
- case METAL_GPIO_INT_BOTH_LEVEL:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
- break;
- case METAL_GPIO_INT_MAX:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
- break;
+ switch (intr_type) {
+ case METAL_GPIO_INT_DISABLE:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) &= ~source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) &= ~source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) &= ~source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) &= ~source;
+ break;
+ case METAL_GPIO_INT_RISING:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_FALLING:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_BOTH_EDGE:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_HIGH:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_LOW:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_BOTH_LEVEL:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
+ break;
+ case METAL_GPIO_INT_MAX:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IE)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IE)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IE)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IE)) |= source;
+ break;
}
return 0;
}
-int __metal_driver_sifive_gpio0_clear_int(struct metal_gpio *ggpio, long source, int intr_type)
-{
+int __metal_driver_sifive_gpio0_clear_int(struct metal_gpio *ggpio, long source,
+ int intr_type) {
long base = __metal_driver_sifive_gpio0_base(ggpio);
- switch (intr_type)
- {
- case METAL_GPIO_INT_RISING:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
- break;
- case METAL_GPIO_INT_FALLING:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
- break;
- case METAL_GPIO_INT_BOTH_EDGE:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
- break;
- case METAL_GPIO_INT_HIGH:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
- break;
- case METAL_GPIO_INT_LOW:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
- break;
- case METAL_GPIO_INT_BOTH_LEVEL:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
- break;
- case METAL_GPIO_INT_MAX:
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
- break;
+ switch (intr_type) {
+ case METAL_GPIO_INT_RISING:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_FALLING:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_BOTH_EDGE:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_HIGH:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_LOW:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_BOTH_LEVEL:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
+ break;
+ case METAL_GPIO_INT_MAX:
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_RISE_IP)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_FALL_IP)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_HIGH_IP)) |= source;
+ __METAL_ACCESS_ONCE(
+ (__metal_io_u32 *)(base + METAL_SIFIVE_GPIO0_LOW_IP)) |= source;
+ break;
}
return 0;
}
struct metal_interrupt *
-__metal_driver_gpio_interrupt_controller(struct metal_gpio *gpio)
-{
+__metal_driver_gpio_interrupt_controller(struct metal_gpio *gpio) {
return __metal_driver_sifive_gpio0_interrupt_parent(gpio);
}
-int __metal_driver_gpio_get_interrupt_id(struct metal_gpio *gpio, int pin)
-{
+int __metal_driver_gpio_get_interrupt_id(struct metal_gpio *gpio, int pin) {
int irq;
irq = __metal_driver_sifive_gpio0_interrupt_lines(gpio, pin);
return irq;
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_gpio0) = {
- .gpio.disable_input = __metal_driver_sifive_gpio0_disable_input,
- .gpio.enable_input = __metal_driver_sifive_gpio0_enable_input,
- .gpio.input = __metal_driver_sifive_gpio0_input,
- .gpio.output = __metal_driver_sifive_gpio0_output,
+ .gpio.disable_input = __metal_driver_sifive_gpio0_disable_input,
+ .gpio.enable_input = __metal_driver_sifive_gpio0_enable_input,
+ .gpio.input = __metal_driver_sifive_gpio0_input,
+ .gpio.output = __metal_driver_sifive_gpio0_output,
.gpio.disable_output = __metal_driver_sifive_gpio0_disable_output,
- .gpio.enable_output = __metal_driver_sifive_gpio0_enable_output,
- .gpio.output_set = __metal_driver_sifive_gpio0_output_set,
- .gpio.output_clear = __metal_driver_sifive_gpio0_output_clear,
- .gpio.output_toggle = __metal_driver_sifive_gpio0_output_toggle,
- .gpio.enable_io = __metal_driver_sifive_gpio0_enable_io,
- .gpio.disable_io = __metal_driver_sifive_gpio0_disable_io,
- .gpio.config_int = __metal_driver_sifive_gpio0_config_int,
- .gpio.clear_int = __metal_driver_sifive_gpio0_clear_int,
+ .gpio.enable_output = __metal_driver_sifive_gpio0_enable_output,
+ .gpio.output_set = __metal_driver_sifive_gpio0_output_set,
+ .gpio.output_clear = __metal_driver_sifive_gpio0_output_clear,
+ .gpio.output_toggle = __metal_driver_sifive_gpio0_output_toggle,
+ .gpio.enable_io = __metal_driver_sifive_gpio0_enable_io,
+ .gpio.disable_io = __metal_driver_sifive_gpio0_disable_io,
+ .gpio.config_int = __metal_driver_sifive_gpio0_config_int,
+ .gpio.clear_int = __metal_driver_sifive_gpio0_clear_int,
.gpio.interrupt_controller = __metal_driver_gpio_interrupt_controller,
.gpio.get_interrupt_id = __metal_driver_gpio_get_interrupt_id,
};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_i2c0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_i2c0.c
new file mode 100644
index 000000000..ec79bbc37
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_i2c0.c
@@ -0,0 +1,428 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine/platform.h>
+
+#ifdef METAL_SIFIVE_I2C0
+#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/sifive_gpio0.h>
+#include <metal/drivers/sifive_i2c0.h>
+#include <metal/io.h>
+#include <metal/machine.h>
+#include <metal/time.h>
+#include <stdio.h>
+
+/* Register fields */
+#define METAL_I2C_CONTROL_EN (1UL << 7)
+#define METAL_I2C_CONTROL_IE (1UL << 6)
+#define METAL_I2C_WRITE (0UL << 0)
+#define METAL_I2C_READ (1UL << 0)
+#define METAL_I2C_CMD_START (1UL << 7)
+#define METAL_I2C_CMD_STOP (1UL << 6)
+#define METAL_I2C_CMD_READ (1UL << 5)
+#define METAL_I2C_CMD_WRITE (1UL << 4)
+#define METAL_I2C_CMD_ACK (1UL << 3)
+#define METAL_I2C_CMD_IACK (1UL << 0)
+#define METAL_I2C_STATUS_RXACK (1UL << 7)
+#define METAL_I2C_STATUS_BUSY (1UL << 6)
+#define METAL_I2C_STATUS_AL (1UL << 5)
+#define METAL_I2C_STATUS_TIP (1UL << 1)
+#define METAL_I2C_STATUS_IP (1UL << 0)
+
+/* Prescaler max value */
+#define METAL_I2C_PRESCALE_MAX 0xFFFF
+/* Macros to access registers */
+#define METAL_I2C_REG(offset) ((base + offset))
+#define METAL_I2C_REGB(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u8 *)METAL_I2C_REG(offset)))
+#define METAL_I2C_REGW(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_I2C_REG(offset)))
+
+/* Timeout macros for register status checks */
+#define METAL_I2C_RXDATA_TIMEOUT 1
+#define METAL_I2C_TIMEOUT_RESET(timeout) \
+ timeout = metal_time() + METAL_I2C_RXDATA_TIMEOUT
+#define METAL_I2C_TIMEOUT_CHECK(timeout) \
+ if (metal_time() > timeout) { \
+ METAL_I2C_LOG("I2C timeout error.\n"); \
+ return METAL_I2C_RET_ERR; \
+ }
+#define METAL_I2C_REG_CHECK(exp, timeout) \
+ while (exp) { \
+ METAL_I2C_TIMEOUT_CHECK(timeout) \
+ }
+
+/* Driver console logging */
+#if defined(METAL_I2C_DEBUG)
+#define METAL_I2C_LOG(x) printf(x)
+#else
+#define METAL_I2C_LOG(x)
+#endif
+
+/* Check endianess */
+#if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__
+#error *** Unsupported endianess ***
+#endif
+
+#define METAL_SIFIVE_I2C_INSERT_STOP(stop_flag) ((stop_flag & 0x01UL) << 6)
+#define METAL_SIFIVE_I2C_INSERT_RW_BIT(addr, rw) \
+ ((addr & 0x7FUL) << 1 | (rw & 0x01UL))
+#define METAL_SIFIVE_I2C_GET_PRESCALER(baud) \
+ ((clock_rate / (baud_rate * 5)) - 1)
+#define METAL_I2C_INIT_OK 1
+#define METAL_I2C_RET_OK 0
+#define METAL_I2C_RET_ERR -1
+
+static void pre_rate_change_callback(void *priv) {
+ unsigned long base =
+ __metal_driver_sifive_i2c0_control_base((struct metal_i2c *)priv);
+ /* Check for any pending transfers */
+ while (METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) & METAL_I2C_STATUS_TIP)
+ ;
+}
+
+static void post_rate_change_callback(void *priv) {
+ struct __metal_driver_sifive_i2c0 *i2c = priv;
+ /* Set baud rate after clock rate change */
+ metal_i2c_set_baud_rate(&i2c->i2c, i2c->baud_rate);
+}
+
+static void __metal_driver_sifive_i2c0_init(struct metal_i2c *gi2c,
+ unsigned int baud_rate,
+ metal_i2c_mode_t mode) {
+ struct __metal_driver_sifive_gpio0 *pinmux =
+ __metal_driver_sifive_i2c0_pinmux(gi2c);
+ struct __metal_driver_sifive_i2c0 *i2c = (void *)gi2c;
+
+ if ((pinmux != NULL) && (gi2c != NULL)) {
+ /* configure I2C I/O pins */
+ long pinmux_output_selector =
+ __metal_driver_sifive_i2c0_pinmux_output_selector(gi2c);
+ long pinmux_source_selector =
+ __metal_driver_sifive_i2c0_pinmux_source_selector(gi2c);
+ pinmux->gpio.vtable->enable_io((struct metal_gpio *)pinmux,
+ pinmux_output_selector,
+ pinmux_source_selector);
+
+ /* 1: Master 0: Slave */
+ if (mode == METAL_I2C_MASTER) {
+ /* Set requested baud rate */
+ if (metal_i2c_set_baud_rate(gi2c, baud_rate) == METAL_I2C_RET_OK) {
+ i2c->init_done = METAL_I2C_INIT_OK;
+ }
+ } else {
+ /* Nothing to do. slave mode not supported */
+ }
+ }
+}
+
+static int __metal_driver_sifive_i2c0_get_baud_rate(struct metal_i2c *gi2c) {
+ struct __metal_driver_sifive_i2c0 *i2c = (void *)gi2c;
+ return i2c->baud_rate;
+}
+
+static int __metal_driver_sifive_i2c0_set_baud_rate(struct metal_i2c *gi2c,
+ unsigned int baud_rate) {
+ struct metal_clock *clock = __metal_driver_sifive_i2c0_clock(gi2c);
+ struct __metal_driver_sifive_i2c0 *i2c = (void *)gi2c;
+ unsigned long base = __metal_driver_sifive_i2c0_control_base(gi2c);
+ int ret = METAL_I2C_RET_ERR;
+
+ if ((clock != NULL) && (gi2c != NULL)) {
+ long clock_rate = clock->vtable->get_rate_hz(clock);
+
+ i2c->pre_rate_change_callback.callback = &pre_rate_change_callback;
+ i2c->pre_rate_change_callback.priv = i2c;
+ metal_clock_register_pre_rate_change_callback(
+ clock, &(i2c->pre_rate_change_callback));
+
+ i2c->post_rate_change_callback.callback = &post_rate_change_callback;
+ i2c->post_rate_change_callback.priv = i2c;
+ metal_clock_register_post_rate_change_callback(
+ clock, &(i2c->post_rate_change_callback));
+
+ /* Calculate prescaler value */
+ long prescaler = METAL_SIFIVE_I2C_GET_PRESCALER(baud_rate);
+
+ if ((prescaler > METAL_I2C_PRESCALE_MAX) || (prescaler < 0)) {
+ /* Out of range value, return error */
+ METAL_I2C_LOG("I2C Set baud failed.\n");
+ } else {
+ /* Set pre-scaler value */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_CONTROL) &= ~METAL_I2C_CONTROL_EN;
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_PRESCALE_LOW) = prescaler & 0xFF;
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_PRESCALE_HIGH) =
+ (prescaler >> 8) & 0xFF;
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_CONTROL) |= METAL_I2C_CONTROL_EN;
+
+ i2c->baud_rate = baud_rate;
+ ret = METAL_I2C_RET_OK;
+ }
+ } else {
+ METAL_I2C_LOG("I2C Set baud failed.\n");
+ }
+
+ return ret;
+}
+
+static int __metal_driver_sifive_i2c0_write_addr(unsigned long base,
+ unsigned int addr,
+ unsigned char rw_flag) {
+ time_t timeout;
+ int ret = METAL_I2C_RET_OK;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Check if any transfer is in progress */
+ METAL_I2C_REG_CHECK(
+ (METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) & METAL_I2C_STATUS_TIP),
+ timeout);
+
+ /* Set transmit register to given address with read/write flag */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_TRANSMIT) =
+ METAL_SIFIVE_I2C_INSERT_RW_BIT(addr, rw_flag);
+
+ /* Set start flag to trigger the address transfer */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_COMMAND) =
+ METAL_I2C_CMD_WRITE | METAL_I2C_CMD_START;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Check for transmit completion */
+ METAL_I2C_REG_CHECK(
+ (METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) & METAL_I2C_STATUS_TIP),
+ timeout);
+
+ /* Check for ACK from slave */
+ if ((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) & METAL_I2C_STATUS_RXACK)) {
+ /* No ACK, return error */
+ METAL_I2C_LOG("I2C RX ACK failed.\n");
+ ret = METAL_I2C_RET_ERR;
+ }
+
+ return ret;
+}
+
+static int __metal_driver_sifive_i2c0_write(struct metal_i2c *i2c,
+ unsigned int addr, unsigned int len,
+ unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ __metal_io_u8 command;
+ time_t timeout;
+ int ret;
+ unsigned long base = __metal_driver_sifive_i2c0_control_base(i2c);
+ unsigned int i;
+
+ if ((i2c != NULL) &&
+ ((struct __metal_driver_sifive_i2c0 *)i2c)->init_done) {
+
+ /* Send address over I2C bus, current driver supports only 7bit
+ * addressing */
+ ret =
+ __metal_driver_sifive_i2c0_write_addr(base, addr, METAL_I2C_WRITE);
+
+ if (ret != METAL_I2C_RET_OK) {
+ /* Write address failed */
+ METAL_I2C_LOG("I2C Address Write failed.\n");
+ } else {
+ /* Set command flags */
+ command = METAL_I2C_CMD_WRITE;
+
+ for (i = 0; i < len; i++) {
+ /* Copy into transmit register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_TRANSMIT) = buf[i];
+
+ /* for last byte transfer, check if stop condition is requested
+ */
+ if (i == (len - 1)) {
+ command |= METAL_SIFIVE_I2C_INSERT_STOP(stop_bit);
+ }
+ /* Write command register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_COMMAND) = command;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Check for transfer completion */
+ METAL_I2C_REG_CHECK((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_TIP),
+ timeout);
+
+ /* Check for ACK from slave */
+ if ((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_RXACK)) {
+ /* No ACK, return error */
+ METAL_I2C_LOG("I2C RX ACK failed.\n");
+ ret = METAL_I2C_RET_ERR;
+ break;
+ }
+ }
+ }
+
+ } else {
+ /* I2C device not initialized, return error */
+ METAL_I2C_LOG("I2C device not initialized.\n");
+ ret = METAL_I2C_RET_ERR;
+ }
+
+ return ret;
+}
+static int __metal_driver_sifive_i2c0_read(struct metal_i2c *i2c,
+ unsigned int addr, unsigned int len,
+ unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit) {
+ int ret;
+ __metal_io_u8 command;
+ time_t timeout;
+ unsigned int i;
+ unsigned long base = __metal_driver_sifive_i2c0_control_base(i2c);
+
+ if ((i2c != NULL) &&
+ ((struct __metal_driver_sifive_i2c0 *)i2c)->init_done) {
+
+ /* Send address over I2C bus, current driver supports only 7bit
+ * addressing */
+ ret = __metal_driver_sifive_i2c0_write_addr(base, addr, METAL_I2C_READ);
+
+ if (ret != METAL_I2C_RET_OK) {
+ /* Write address failed */
+ METAL_I2C_LOG("I2C Read failed.\n");
+ } else {
+ /* Set command flags */
+ command = METAL_I2C_CMD_READ;
+
+ for (i = 0; i < len; i++) {
+ /* check for last transfer */
+ if (i == (len - 1)) {
+ /* Set NACK to end read, if requested generate STOP
+ * condition */
+ command |= (METAL_I2C_CMD_ACK |
+ METAL_SIFIVE_I2C_INSERT_STOP(stop_bit));
+ }
+ /* Write command register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_COMMAND) = command;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Wait for the read to complete */
+ METAL_I2C_REG_CHECK((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_TIP),
+ timeout);
+ /* Store the received byte */
+ buf[i] = METAL_I2C_REGB(METAL_SIFIVE_I2C0_TRANSMIT);
+ }
+ }
+ } else {
+ /* I2C device not initialized, return error */
+ METAL_I2C_LOG("I2C device not initialized.\n");
+ ret = METAL_I2C_RET_ERR;
+ }
+
+ return ret;
+}
+
+static int
+__metal_driver_sifive_i2c0_transfer(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen) {
+ __metal_io_u8 command;
+ time_t timeout;
+ int ret;
+ unsigned int i;
+ unsigned long base = __metal_driver_sifive_i2c0_control_base(i2c);
+
+ if ((i2c != NULL) &&
+ ((struct __metal_driver_sifive_i2c0 *)i2c)->init_done) {
+ if (txlen) {
+ /* Set command flags */
+ command = METAL_I2C_CMD_WRITE;
+ /* Send address over I2C bus, current driver supports only 7bit
+ * addressing */
+ ret = __metal_driver_sifive_i2c0_write_addr(base, addr,
+ METAL_I2C_WRITE);
+
+ if (ret != METAL_I2C_RET_OK) {
+ /* Write address failed */
+ METAL_I2C_LOG("I2C Write failed.\n");
+ return ret;
+ }
+ for (i = 0; i < txlen; i++) {
+ /* Copy into transmit register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_TRANSMIT) = txbuf[i];
+
+ if (i == (txlen - 1) && (rxlen == 0)) {
+ /* Insert stop condition to end transfer */
+ command |= METAL_I2C_CMD_STOP;
+ }
+ /* Write command register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_COMMAND) = command;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Check for transfer completion. */
+ METAL_I2C_REG_CHECK((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_TIP),
+ timeout);
+
+ /* Check for ACK from slave. */
+ if ((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_RXACK)) {
+ /* No ACK, return error */
+ METAL_I2C_LOG("I2C RX ACK failed.\n");
+ ret = METAL_I2C_RET_ERR;
+ break;
+ }
+ }
+ }
+ if (rxlen) {
+ command = METAL_I2C_CMD_READ; /* Set command flags */
+ /* Send address over I2C bus, current driver supports only 7bit
+ * addressing */
+ ret = __metal_driver_sifive_i2c0_write_addr(base, addr,
+ METAL_I2C_READ);
+
+ if (ret != METAL_I2C_RET_OK) {
+ /* Return error */
+ METAL_I2C_LOG("I2C Read failed.\n");
+ return ret;
+ }
+ for (i = 0; i < rxlen; i++) {
+ /* check for last transfer */
+ if (i == (rxlen - 1)) {
+ /* Set NACK to end read, generate STOP condition */
+ command |= (METAL_I2C_CMD_ACK | METAL_I2C_CMD_STOP);
+ }
+ /* Write command register */
+ METAL_I2C_REGB(METAL_SIFIVE_I2C0_COMMAND) = command;
+ /* Reset timeout */
+ METAL_I2C_TIMEOUT_RESET(timeout);
+
+ /* Wait for the read to complete */
+ METAL_I2C_REG_CHECK((METAL_I2C_REGB(METAL_SIFIVE_I2C0_STATUS) &
+ METAL_I2C_STATUS_TIP),
+ timeout);
+ /* Store the received byte */
+ rxbuf[i] = METAL_I2C_REGB(METAL_SIFIVE_I2C0_TRANSMIT);
+ }
+ }
+ } else {
+ /* I2C device not initialized, return error */
+ METAL_I2C_LOG("I2C device not initialized.\n");
+ ret = METAL_I2C_RET_ERR;
+ }
+
+ return ret;
+}
+
+__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_i2c0) = {
+ .i2c.init = __metal_driver_sifive_i2c0_init,
+ .i2c.write = __metal_driver_sifive_i2c0_write,
+ .i2c.read = __metal_driver_sifive_i2c0_read,
+ .i2c.transfer = __metal_driver_sifive_i2c0_transfer,
+ .i2c.get_baud_rate = __metal_driver_sifive_i2c0_get_baud_rate,
+ .i2c.set_baud_rate = __metal_driver_sifive_i2c0_set_baud_rate,
+};
+
+#endif /* METAL_SIFIVE_I2C0 */
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_l2pf0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_l2pf0.c
new file mode 100644
index 000000000..63690fa38
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_l2pf0.c
@@ -0,0 +1,164 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine/platform.h>
+
+#ifdef METAL_SIFIVE_L2PF0
+
+#include <metal/drivers/sifive_l2pf0.h>
+#include <metal/machine.h>
+
+/* Macros to access memory mapped registers */
+#define REGW(x) \
+ *(volatile uint32_t *)(METAL_SIFIVE_L2PF0_0_BASE_ADDRESS + \
+ hartid * 0x2000 + x)
+
+/* Macros for register bit masks */
+#define REG_MASK_BITWIDTH1 0x01
+#define REG_MASK_BITWIDTH4 0x0F
+#define REG_MASK_BITWIDTH5 0x1F
+#define REG_MASK_BITWIDTH6 0x3F
+#define REG_MASK_BITWIDTH7 0x7F
+
+/* Macros to specify register bit shift */
+#define REG_BITSHIFT_1 1
+#define REG_BITSHIFT_2 2
+#define REG_BITSHIFT_4 4
+#define REG_BITSHIFT_8 8
+#define REG_BITSHIFT_9 9
+#define REG_BITSHIFT_13 13
+#define REG_BITSHIFT_14 14
+#define REG_BITSHIFT_20 20
+#define REG_BITSHIFT_21 21
+#define REG_BITSHIFT_28 28
+
+/* Macros to capture trap, if L2PF does not exist for a hart id. */
+#define SIFIVE_L2PF0_TRAP_CAPTURE(exit, mtvec) \
+ __asm__ __volatile__("la %0, 1f \n\t" \
+ "csrr %1, mtvec \n\t" \
+ "csrw mtvec, %0 \n\t" \
+ : "+r"(exit), "+r"(mtvec))
+
+#define SIFIVE_L2PF0_TRAP_RESTORE(mtvec) \
+ __asm__ __volatile__(".align 2 \n\t" \
+ "1: \n\t" \
+ "csrw mtvec, %0 \n\t" \
+ : "+r"(mtvec))
+
+void sifive_l2pf0_enable(void) {
+ volatile uintptr_t exit = 0, mtvec = 0;
+ int hartid;
+ __asm__ volatile("csrr %0, mhartid" : "=r"(hartid));
+
+ SIFIVE_L2PF0_TRAP_CAPTURE(exit, mtvec);
+
+ uint32_t val = REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL);
+
+ /* Enable L2 prefetch unit for current hart */
+ val |= REG_MASK_BITWIDTH1;
+
+ REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL) = val;
+
+ SIFIVE_L2PF0_TRAP_RESTORE(mtvec);
+}
+
+void sifive_l2pf0_disable(void) {
+ volatile uintptr_t exit = 0, mtvec = 0;
+ int hartid;
+ __asm__ volatile("csrr %0, mhartid" : "=r"(hartid));
+
+ SIFIVE_L2PF0_TRAP_CAPTURE(exit, mtvec);
+
+ uint32_t val = REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL);
+
+ /* Disable L2 prefetch unit for current hart */
+ val &= ~REG_MASK_BITWIDTH1;
+
+ REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL) = val;
+
+ SIFIVE_L2PF0_TRAP_RESTORE(mtvec);
+}
+
+void sifive_l2pf0_get_config(sifive_l2pf0_config *config) {
+ volatile uintptr_t exit = 0, mtvec = 0;
+ int hartid;
+ __asm__ volatile("csrr %0, mhartid" : "=r"(hartid));
+ uint32_t val;
+
+ SIFIVE_L2PF0_TRAP_CAPTURE(exit, mtvec);
+
+ if (config) /* Check for NULL */
+ {
+ /* Get currently active L2 prefetch configuration values */
+ val = REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL);
+
+ config->HwPrefetchEnable = (val & REG_MASK_BITWIDTH1);
+ config->CrossPageOptmDisable =
+ ((val >> REG_BITSHIFT_1) & REG_MASK_BITWIDTH1);
+ config->PrefetchDistance =
+ ((val >> REG_BITSHIFT_2) & REG_MASK_BITWIDTH6);
+ config->MaxAllowedDistance =
+ ((val >> REG_BITSHIFT_8) & REG_MASK_BITWIDTH6);
+ config->LinToExpThreshold =
+ ((val >> REG_BITSHIFT_14) & REG_MASK_BITWIDTH6);
+ config->AgeOutEn = ((val >> REG_BITSHIFT_20) & REG_MASK_BITWIDTH1);
+ config->NumLdsToAgeOut =
+ ((val >> REG_BITSHIFT_21) & REG_MASK_BITWIDTH7);
+ config->CrossPageEn = ((val >> REG_BITSHIFT_28) & REG_MASK_BITWIDTH1);
+
+ val = REGW(METAL_SIFIVE_L2PF0_USER_CONTROL);
+
+ config->QFullnessThreshold = (val & REG_MASK_BITWIDTH4);
+ config->HitCacheThreshold =
+ ((val >> REG_BITSHIFT_4) & REG_MASK_BITWIDTH5);
+ config->hitMSHRThreshold =
+ ((val >> REG_BITSHIFT_9) & REG_MASK_BITWIDTH4);
+ config->Window = ((val >> REG_BITSHIFT_13) & REG_MASK_BITWIDTH6);
+ }
+ SIFIVE_L2PF0_TRAP_RESTORE(mtvec);
+}
+
+void sifive_l2pf0_set_config(sifive_l2pf0_config *config) {
+ volatile uintptr_t exit = 0, mtvec = 0;
+ int hartid;
+ __asm__ volatile("csrr %0, mhartid" : "=r"(hartid));
+ uint32_t val;
+
+ SIFIVE_L2PF0_TRAP_CAPTURE(exit, mtvec);
+
+ if (config) /* Check for NULL */
+ {
+ /* Get values from configuration to write into register */
+ val = (uint32_t)(
+ (config->HwPrefetchEnable & REG_MASK_BITWIDTH1) |
+ ((config->CrossPageOptmDisable & REG_MASK_BITWIDTH1)
+ << REG_BITSHIFT_1) |
+ ((config->PrefetchDistance & REG_MASK_BITWIDTH6)
+ << REG_BITSHIFT_2) |
+ ((config->MaxAllowedDistance & REG_MASK_BITWIDTH6)
+ << REG_BITSHIFT_8) |
+ ((config->LinToExpThreshold & REG_MASK_BITWIDTH6)
+ << REG_BITSHIFT_14) |
+ ((config->AgeOutEn & REG_MASK_BITWIDTH1) << REG_BITSHIFT_20) |
+ ((config->NumLdsToAgeOut & REG_MASK_BITWIDTH7) << REG_BITSHIFT_21) |
+ ((config->CrossPageEn & REG_MASK_BITWIDTH1) << REG_BITSHIFT_28));
+
+ /* Set user specified L2 prefetch configuration values */
+ REGW(METAL_SIFIVE_L2PF0_BASIC_CONTROL) = val;
+
+ val = (uint32_t)(
+ (config->QFullnessThreshold & REG_MASK_BITWIDTH4) |
+ ((config->HitCacheThreshold & REG_MASK_BITWIDTH5)
+ << REG_BITSHIFT_4) |
+ ((config->hitMSHRThreshold & REG_MASK_BITWIDTH4)
+ << REG_BITSHIFT_9) |
+ ((config->Window & REG_MASK_BITWIDTH6) << REG_BITSHIFT_13));
+
+ REGW(METAL_SIFIVE_L2PF0_USER_CONTROL) = val;
+ }
+ SIFIVE_L2PF0_TRAP_RESTORE(mtvec);
+}
+
+#endif
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_local-external-interrupts0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_local-external-interrupts0.c
index 1c34ca447..99b5e3a86 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_local-external-interrupts0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_local-external-interrupts0.c
@@ -5,42 +5,50 @@
#ifdef METAL_SIFIVE_LOCAL_EXTERNAL_INTERRUPTS0
-#include <metal/io.h>
#include <metal/drivers/sifive_local-external-interrupts0.h>
+#include <metal/io.h>
#include <metal/machine.h>
-void __metal_driver_sifive_local_external_interrupt_init(struct metal_interrupt *controller)
-{
+void __metal_driver_sifive_local_external_interrupt_init(
+ struct metal_interrupt *controller) {
struct __metal_driver_sifive_local_external_interrupts0 *local0;
- local0 = (struct __metal_driver_sifive_local_external_interrupts0 *)(controller);
- if ( !local0->init_done ) {
+ local0 =
+ (struct __metal_driver_sifive_local_external_interrupts0 *)(controller);
+ if (!local0->init_done) {
struct metal_interrupt *intc =
- __metal_driver_sifive_local_external_interrupts0_interrupt_parent(controller);
-
- if (intc) {
- /* Register its interruptswith with parent controller, aka all external to default isr */
- for (int i = 0;
- i < __metal_driver_sifive_local_external_interrupts0_num_interrupts(controller);
- i++) {
- intc->vtable->interrupt_register(intc,
- __metal_driver_sifive_local_external_interrupts0_interrupt_lines(controller, i),
- NULL, controller);
- }
- local0->init_done = 1;
- }
+ __metal_driver_sifive_local_external_interrupts0_interrupt_parent(
+ controller);
+
+ if (intc) {
+ /* Register its interruptswith with parent controller, aka all
+ * external to default isr */
+ for (
+ int i = 0;
+ i <
+ __metal_driver_sifive_local_external_interrupts0_num_interrupts(
+ controller);
+ i++) {
+ intc->vtable->interrupt_register(
+ intc,
+ __metal_driver_sifive_local_external_interrupts0_interrupt_lines(
+ controller, i),
+ NULL, controller);
+ }
+ local0->init_done = 1;
+ }
}
}
-int __metal_driver_sifive_local_external_interrupt_register(struct metal_interrupt *controller,
- int id, metal_interrupt_handler_t isr,
- void *priv)
-{
+int __metal_driver_sifive_local_external_interrupt_register(
+ struct metal_interrupt *controller, int id, metal_interrupt_handler_t isr,
+ void *priv) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_local_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_local_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -50,13 +58,14 @@ int __metal_driver_sifive_local_external_interrupt_register(struct metal_interru
return rc;
}
-int __metal_driver_sifive_local_external_interrupt_enable(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_local_external_interrupt_enable(
+ struct metal_interrupt *controller, int id) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_local_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_local_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -66,13 +75,14 @@ int __metal_driver_sifive_local_external_interrupt_enable(struct metal_interrupt
return rc;
}
-int __metal_driver_sifive_local_external_interrupt_disable(struct metal_interrupt *controller, int id)
-{
+int __metal_driver_sifive_local_external_interrupt_disable(
+ struct metal_interrupt *controller, int id) {
int rc = -1;
if (id != 0) {
struct metal_interrupt *intc =
- __metal_driver_sifive_local_external_interrupts0_interrupt_parent(controller);
+ __metal_driver_sifive_local_external_interrupts0_interrupt_parent(
+ controller);
/* Enable its interrupts with parent controller */
if (intc) {
@@ -82,48 +92,47 @@ int __metal_driver_sifive_local_external_interrupt_disable(struct metal_interrup
return rc;
}
-int __metal_driver_sifive_local_external_interrupt_set_threshold(struct metal_interrupt *controller,
- unsigned int threshold)
-{
+int __metal_driver_sifive_local_external_interrupt_set_threshold(
+ struct metal_interrupt *controller, unsigned int threshold) {
/* Core controller does not support threshold configuration */
return -1;
}
-unsigned int __metal_driver_sifive_local_external_interrupt_get_threshold(struct metal_interrupt *controller)
-{
+unsigned int __metal_driver_sifive_local_external_interrupt_get_threshold(
+ struct metal_interrupt *controller) {
/* Core controller does not support threshold configuration */
return 0;
}
-
-int __metal_driver_sifive_local_external_interrupt_set_priority(struct metal_interrupt *controller,
- int id, unsigned int priority)
-{
+int __metal_driver_sifive_local_external_interrupt_set_priority(
+ struct metal_interrupt *controller, int id, unsigned int priority) {
/* Core controller does not support priority configuration */
return -1;
}
-unsigned int __metal_driver_sifive_local_external_interrupt_get_priority(struct metal_interrupt *controller, int id)
-{
+unsigned int __metal_driver_sifive_local_external_interrupt_get_priority(
+ struct metal_interrupt *controller, int id) {
/* Core controller does not support priority configuration */
return 0;
}
-int __metal_driver_sifive_local_external_command_request (struct metal_interrupt *controller,
- int command, void *data)
-{
+int __metal_driver_sifive_local_external_command_request(
+ struct metal_interrupt *controller, int command, void *data) {
int idx;
int rc = -1;
switch (command) {
case METAL_MAX_INTERRUPT_GET:
- rc = __metal_driver_sifive_local_external_interrupts0_num_interrupts(controller);
+ rc = __metal_driver_sifive_local_external_interrupts0_num_interrupts(
+ controller);
break;
case METAL_INDEX_INTERRUPT_GET:
rc = 0;
if (data) {
idx = *(int *)data;
- rc = __metal_driver_sifive_local_external_interrupts0_interrupt_lines(controller, idx);
+ rc =
+ __metal_driver_sifive_local_external_interrupts0_interrupt_lines(
+ controller, idx);
}
break;
default:
@@ -133,19 +142,28 @@ int __metal_driver_sifive_local_external_command_request (struct metal_interrupt
return rc;
}
-__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_local_external_interrupts0) = {
- .local0_vtable.interrupt_init = __metal_driver_sifive_local_external_interrupt_init,
- .local0_vtable.interrupt_register = __metal_driver_sifive_local_external_interrupt_register,
- .local0_vtable.interrupt_enable = __metal_driver_sifive_local_external_interrupt_enable,
- .local0_vtable.interrupt_disable = __metal_driver_sifive_local_external_interrupt_disable,
- .local0_vtable.interrupt_get_threshold = __metal_driver_sifive_local_external_interrupt_get_threshold,
- .local0_vtable.interrupt_set_threshold = __metal_driver_sifive_local_external_interrupt_set_threshold,
- .local0_vtable.interrupt_get_priority = __metal_driver_sifive_local_external_interrupt_get_priority,
- .local0_vtable.interrupt_set_priority = __metal_driver_sifive_local_external_interrupt_set_priority,
- .local0_vtable.command_request = __metal_driver_sifive_local_external_command_request,
+__METAL_DEFINE_VTABLE(
+ __metal_driver_vtable_sifive_local_external_interrupts0) = {
+ .local0_vtable.interrupt_init =
+ __metal_driver_sifive_local_external_interrupt_init,
+ .local0_vtable.interrupt_register =
+ __metal_driver_sifive_local_external_interrupt_register,
+ .local0_vtable.interrupt_enable =
+ __metal_driver_sifive_local_external_interrupt_enable,
+ .local0_vtable.interrupt_disable =
+ __metal_driver_sifive_local_external_interrupt_disable,
+ .local0_vtable.interrupt_get_threshold =
+ __metal_driver_sifive_local_external_interrupt_get_threshold,
+ .local0_vtable.interrupt_set_threshold =
+ __metal_driver_sifive_local_external_interrupt_set_threshold,
+ .local0_vtable.interrupt_get_priority =
+ __metal_driver_sifive_local_external_interrupt_get_priority,
+ .local0_vtable.interrupt_set_priority =
+ __metal_driver_sifive_local_external_interrupt_set_priority,
+ .local0_vtable.command_request =
+ __metal_driver_sifive_local_external_command_request,
};
#endif
typedef int no_empty_translation_units;
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_pwm0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_pwm0.c
new file mode 100644
index 000000000..415d46825
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_pwm0.c
@@ -0,0 +1,340 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine/platform.h>
+
+#ifdef METAL_SIFIVE_PWM0
+#include <metal/clock.h>
+#include <metal/compiler.h>
+#include <metal/drivers/sifive_gpio0.h>
+#include <metal/drivers/sifive_pwm0.h>
+#include <metal/io.h>
+#include <metal/machine.h>
+#include <metal/time.h>
+#include <stdio.h>
+
+/* Register fields */
+#define METAL_PWMCFG_STICKY (1UL << 8)
+#define METAL_PWMCFG_ZEROCMP (1UL << 9)
+#define METAL_PWMCFG_DEGLITCH (1UL << 10)
+#define METAL_PWMCFG_ENALWAYS (1UL << 12)
+#define METAL_PWMCFG_ENONESHOT (1UL << 13)
+#define METAL_PWMCFG_CMPCENTER(x) (1UL << (16 + x))
+#define METAL_PWMCFG_CMPIP(x) (1UL << (28 + x))
+#define METAL_SIFIVE_PWM0_PWMCMP(x) (METAL_SIFIVE_PWM0_PWMCMP0 + (x * 4))
+
+/* Macros to access registers */
+#define METAL_PWM_REG(offset) ((base + offset))
+#define METAL_PWM_REGW(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_PWM_REG(offset)))
+
+/* Macro to get PWM compare count */
+#define METAL_PWM_GETCMPVAL(duty) (duty * pwm->count_val) / 100U
+/* Max duty cycle value */
+#define METAL_PWM_MAXDUTY 100UL
+/* Max pre-scalar value */
+#define METAL_PWM_MAXPRESCAL 15UL
+
+/* Check endianess */
+#if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__
+#error *** Unsupported endianess ***
+#endif
+
+#if (METAL_MAX_PWM0_NCMP > METAL_MAX_PWM_CHANNELS)
+#error *** METAL_MAX_PWM_CHANNELS exceeded ***
+#endif
+
+/* Return values */
+#define METAL_PWM_RET_OK 0
+#define METAL_PWM_RET_ERR -1
+
+static void pre_rate_change_callback(void *priv) {
+ struct metal_pwm *gpwm = priv;
+ /* Disable active PWM instance. */
+ gpwm->vtable->stop(gpwm, 0);
+}
+
+static void post_rate_change_callback(void *priv) {
+ struct __metal_driver_sifive_pwm0 *pwm = priv;
+ struct metal_pwm *gpwm = priv;
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ unsigned int cmp_count = __metal_driver_sifive_pwm0_comparator_count(gpwm);
+ unsigned int idx = 0;
+ unsigned int duty;
+
+ /* Check if PWM frequency was set */
+ if (pwm->freq != 0) {
+ /* Set frequency after clock rate change */
+ gpwm->vtable->set_freq(gpwm, 0, pwm->freq);
+
+ /* Set duty cycle after clock rate change */
+ while (++idx < cmp_count) {
+ duty = pwm->duty[idx];
+ if (duty != 0) {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCMP(idx)) =
+ METAL_PWM_GETCMPVAL(duty);
+ }
+ }
+ }
+}
+
+static int __metal_driver_sifive_pwm0_enable(struct metal_pwm *gpwm) {
+ struct __metal_driver_sifive_gpio0 *pinmux =
+ __metal_driver_sifive_pwm0_pinmux(gpwm);
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ struct __metal_driver_sifive_pwm0 *pwm = (void *)gpwm;
+ int ret = METAL_PWM_RET_ERR;
+
+ if (base != 0) {
+
+ if ((pinmux != NULL) && (gpwm != NULL)) {
+ /* Configure PWM I/O pins */
+ long pinmux_output_selector =
+ __metal_driver_sifive_pwm0_pinmux_output_selector(gpwm);
+ long pinmux_source_selector =
+ __metal_driver_sifive_pwm0_pinmux_source_selector(gpwm);
+
+ pinmux->gpio.vtable->enable_io((struct metal_gpio *)pinmux,
+ pinmux_output_selector,
+ pinmux_source_selector);
+ }
+
+ /* Initialize default values */
+ pwm->max_count =
+ (1UL << __metal_driver_sifive_pwm0_compare_width(gpwm)) - 1;
+ pwm->freq = 0;
+ pwm->count_val = 0;
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) = 0;
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static int __metal_driver_sifive_pwm0_disable(struct metal_pwm *gpwm) {
+ struct __metal_driver_sifive_gpio0 *pinmux =
+ __metal_driver_sifive_pwm0_pinmux(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ if (gpwm != NULL) {
+
+ if (pinmux != NULL) {
+ /* Disable PWM I/O pins */
+ long pinmux_source_selector =
+ __metal_driver_sifive_pwm0_pinmux_source_selector(gpwm);
+ pinmux->gpio.vtable->disable_io((struct metal_gpio *)pinmux,
+ pinmux_source_selector);
+ }
+
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static int __metal_driver_sifive_pwm0_set_freq(struct metal_pwm *gpwm,
+ unsigned int idx,
+ unsigned int freq) {
+ struct metal_clock *clock = __metal_driver_sifive_pwm0_clock(gpwm);
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ unsigned int cmp_count = __metal_driver_sifive_pwm0_comparator_count(gpwm);
+ struct __metal_driver_sifive_pwm0 *pwm = (void *)gpwm;
+ unsigned int clock_rate;
+ unsigned int count;
+ unsigned int prescale = 0;
+ int ret = METAL_PWM_RET_ERR;
+
+ if ((clock != NULL) && (gpwm != NULL) && (idx < cmp_count)) {
+ clock_rate = clock->vtable->get_rate_hz(clock);
+ /* Register clock rate change call-backs */
+ if (pwm->freq == 0) {
+ pwm->pre_rate_change_callback.callback = &pre_rate_change_callback;
+ pwm->pre_rate_change_callback.priv = pwm;
+ metal_clock_register_pre_rate_change_callback(
+ clock, &(pwm->pre_rate_change_callback));
+
+ pwm->post_rate_change_callback.callback =
+ &post_rate_change_callback;
+ pwm->post_rate_change_callback.priv = pwm;
+ metal_clock_register_post_rate_change_callback(
+ clock, &(pwm->post_rate_change_callback));
+ }
+
+ /* Calculate count value for given PWM frequency */
+ do {
+ count = (clock_rate / (1UL << prescale)) / freq;
+ } while ((count > pwm->max_count) &&
+ (prescale++ < METAL_PWM_MAXPRESCAL));
+
+ pwm->freq = (clock_rate / (1UL << prescale)) / count;
+ pwm->count_val = --count;
+
+ /* Update values into registers */
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCMP0) = count;
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) |= (prescale & 0x0FUL);
+ ret = METAL_PWM_RET_OK;
+
+#if defined(METAL_PWM_DEBUG)
+ printf("PWM requested freq:%u set freq:%u \n", freq, pwm->freq);
+ printf("CPU Clk:%u Prescale:%u Count:%u \n", clock_rate, prescale,
+ count);
+#endif
+ }
+ return ret;
+}
+
+static int
+__metal_driver_sifive_pwm0_set_duty(struct metal_pwm *gpwm, unsigned int idx,
+ unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr) {
+ struct __metal_driver_sifive_pwm0 *pwm = (void *)gpwm;
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ unsigned int cmp_count = __metal_driver_sifive_pwm0_comparator_count(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ /* Check if duty value is within limits, duty cycle cannot be set for
+ * PWMCMP0 */
+ if ((idx > 0) && (idx < cmp_count) && (duty <= METAL_PWM_MAXDUTY)) {
+ /* Calculate PWM compare count value for given duty cycle */
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCMP(idx)) =
+ METAL_PWM_GETCMPVAL(duty);
+ pwm->duty[idx] = duty;
+
+ /* Enable / Disable phase correct PWM mode */
+ if (phase_corr == METAL_PWM_PHASE_CORRECT_ENABLE) {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) |=
+ METAL_PWMCFG_CMPCENTER(idx);
+ } else {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) &=
+ ~METAL_PWMCFG_CMPCENTER(idx);
+ }
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static unsigned int __metal_driver_sifive_pwm0_get_duty(struct metal_pwm *gpwm,
+ unsigned int idx) {
+ struct __metal_driver_sifive_pwm0 *pwm = (void *)gpwm;
+ unsigned int cmp_count = __metal_driver_sifive_pwm0_comparator_count(gpwm);
+ unsigned int duty = 0;
+
+ /* Check for valid parameters and get configured duty cycle value */
+ if ((pwm != NULL) && (idx > 0) && (idx < cmp_count)) {
+ duty = pwm->duty[idx];
+ }
+ return duty;
+}
+
+static unsigned int __metal_driver_sifive_pwm0_get_freq(struct metal_pwm *gpwm,
+ unsigned int idx) {
+ struct __metal_driver_sifive_pwm0 *pwm = (void *)gpwm;
+ unsigned int freq = 0;
+
+ (void)idx; /* Unused parameter, no support for per channel frequency */
+
+ /* Check for valid parameters and get configured PWM frequency value */
+ if (pwm != NULL) {
+ freq = pwm->freq;
+ }
+ return freq;
+}
+
+static int __metal_driver_sifive_pwm0_trigger(struct metal_pwm *gpwm,
+ unsigned int idx,
+ metal_pwm_run_mode_t mode) {
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ (void)idx; /* Unused parameter,for later use */
+
+ if (base != 0) {
+ /* Configure for requested PWM run mode */
+ if (mode == METAL_PWM_CONTINUOUS) {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) |= METAL_PWMCFG_DEGLITCH |
+ METAL_PWMCFG_ZEROCMP |
+ METAL_PWMCFG_ENALWAYS;
+ } else {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) |= METAL_PWMCFG_DEGLITCH |
+ METAL_PWMCFG_ZEROCMP |
+ METAL_PWMCFG_ENONESHOT;
+ }
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static int __metal_driver_sifive_pwm0_stop(struct metal_pwm *gpwm,
+ unsigned int idx) {
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ (void)idx; /* Unused parameter,for later use */
+
+ if (base != 0) {
+ /* Disable always running mode */
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) &= ~METAL_PWMCFG_ENALWAYS;
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static int
+__metal_driver_sifive_pwm0_cfg_interrupt(struct metal_pwm *gpwm,
+ metal_pwm_interrupt_t flag) {
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ if (base != 0) {
+ if (flag == METAL_PWM_INTERRUPT_ENABLE) {
+ /* Enable sticky bit, to make sure interrupts are not forgotten */
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) |= METAL_PWMCFG_STICKY;
+ } else {
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) &= ~METAL_PWMCFG_STICKY;
+ }
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static int __metal_driver_sifive_pwm0_clr_interrupt(struct metal_pwm *gpwm,
+ unsigned int idx) {
+ unsigned long base = __metal_driver_sifive_pwm0_control_base(gpwm);
+ unsigned int cmp_count = __metal_driver_sifive_pwm0_comparator_count(gpwm);
+ int ret = METAL_PWM_RET_ERR;
+
+ if ((base != 0) && (idx < cmp_count)) {
+ /* Clear interrupt pending bit for given PWM comparator */
+ METAL_PWM_REGW(METAL_SIFIVE_PWM0_PWMCFG) &= ~METAL_PWMCFG_CMPIP(idx);
+ ret = METAL_PWM_RET_OK;
+ }
+ return ret;
+}
+
+static struct metal_interrupt *
+__metal_driver_sifive_pwm0_interrupt_controller(struct metal_pwm *gpwm) {
+ return __metal_driver_sifive_pwm0_interrupt_parent(gpwm);
+}
+
+static int __metal_driver_sifive_pwm0_interrupt_id(struct metal_pwm *gpwm,
+ unsigned int idx) {
+ return __metal_driver_sifive_pwm0_interrupt_lines(gpwm, idx);
+}
+
+__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_pwm0) = {
+ .pwm.enable = __metal_driver_sifive_pwm0_enable,
+ .pwm.disable = __metal_driver_sifive_pwm0_disable,
+ .pwm.set_duty = __metal_driver_sifive_pwm0_set_duty,
+ .pwm.set_freq = __metal_driver_sifive_pwm0_set_freq,
+ .pwm.get_duty = __metal_driver_sifive_pwm0_get_duty,
+ .pwm.get_freq = __metal_driver_sifive_pwm0_get_freq,
+ .pwm.trigger = __metal_driver_sifive_pwm0_trigger,
+ .pwm.stop = __metal_driver_sifive_pwm0_stop,
+ .pwm.cfg_interrupt = __metal_driver_sifive_pwm0_cfg_interrupt,
+ .pwm.clr_interrupt = __metal_driver_sifive_pwm0_clr_interrupt,
+ .pwm.get_interrupt_controller =
+ __metal_driver_sifive_pwm0_interrupt_controller,
+ .pwm.get_interrupt_id = __metal_driver_sifive_pwm0_interrupt_id,
+};
+
+#endif /* METAL_SIFIVE_PWM0 */
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_rtc0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_rtc0.c
index 79b81e7bf..d9c06d349 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_rtc0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_rtc0.c
@@ -19,30 +19,40 @@
#define METAL_RTCCMP0_MAX UINT32_MAX
#define RTC_REG(base, offset) (((unsigned long)base + offset))
-#define RTC_REGW(base, offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)RTC_REG(base, offset)))
+#define RTC_REGW(base, offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)RTC_REG(base, offset)))
-uint64_t __metal_driver_sifive_rtc0_get_rate(const struct metal_rtc *const rtc) {
- const struct metal_clock *const clock = __metal_driver_sifive_rtc0_clock(rtc);
+uint64_t
+__metal_driver_sifive_rtc0_get_rate(const struct metal_rtc *const rtc) {
+ const struct metal_clock *const clock =
+ __metal_driver_sifive_rtc0_clock(rtc);
return metal_clock_get_rate_hz(clock);
}
-uint64_t __metal_driver_sifive_rtc0_set_rate(const struct metal_rtc *const rtc, const uint64_t rate) {
- const struct metal_clock *const clock = __metal_driver_sifive_rtc0_clock(rtc);
+uint64_t __metal_driver_sifive_rtc0_set_rate(const struct metal_rtc *const rtc,
+ const uint64_t rate) {
+ const struct metal_clock *const clock =
+ __metal_driver_sifive_rtc0_clock(rtc);
return metal_clock_get_rate_hz(clock);
}
-uint64_t __metal_driver_sifive_rtc0_get_compare(const struct metal_rtc *const rtc) {
+uint64_t
+__metal_driver_sifive_rtc0_get_compare(const struct metal_rtc *const rtc) {
const uint64_t base = __metal_driver_sifive_rtc0_control_base(rtc);
- const uint32_t shift = RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCFG) & METAL_RTCCFG_RTCSCALE_MASK;
+ const uint32_t shift =
+ RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCFG) & METAL_RTCCFG_RTCSCALE_MASK;
return ((uint64_t)RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCMP0) << shift);
}
-uint64_t __metal_driver_sifive_rtc0_set_compare(const struct metal_rtc *const rtc, const uint64_t compare) {
+uint64_t
+__metal_driver_sifive_rtc0_set_compare(const struct metal_rtc *const rtc,
+ const uint64_t compare) {
const uint64_t base = __metal_driver_sifive_rtc0_control_base(rtc);
- /* Determine the bit shift and shifted value to store in rtccmp0/rtccfg.scale */
+ /* Determine the bit shift and shifted value to store in
+ * rtccmp0/rtccfg.scale */
uint32_t shift = 0;
uint64_t comp_shifted = compare;
while (comp_shifted > METAL_RTCCMP0_MAX) {
@@ -57,12 +67,13 @@ uint64_t __metal_driver_sifive_rtc0_set_compare(const struct metal_rtc *const rt
RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCFG) = cfg;
/* Set the value of rtccmp0 */
- RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCMP0) = (uint32_t) comp_shifted;
+ RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCMP0) = (uint32_t)comp_shifted;
return __metal_driver_sifive_rtc0_get_compare(rtc);
}
-uint64_t __metal_driver_sifive_rtc0_get_count(const struct metal_rtc *const rtc) {
+uint64_t
+__metal_driver_sifive_rtc0_get_count(const struct metal_rtc *const rtc) {
const uint64_t base = __metal_driver_sifive_rtc0_control_base(rtc);
uint64_t count = RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCOUNTHI);
@@ -72,7 +83,8 @@ uint64_t __metal_driver_sifive_rtc0_get_count(const struct metal_rtc *const rtc)
return count;
}
-uint64_t __metal_driver_sifive_rtc0_set_count(const struct metal_rtc *const rtc, const uint64_t count) {
+uint64_t __metal_driver_sifive_rtc0_set_count(const struct metal_rtc *const rtc,
+ const uint64_t count) {
const uint64_t base = __metal_driver_sifive_rtc0_control_base(rtc);
RTC_REGW(base, METAL_SIFIVE_RTC0_RTCCOUNTHI) = (UINT_MAX & (count >> 32));
@@ -81,7 +93,8 @@ uint64_t __metal_driver_sifive_rtc0_set_count(const struct metal_rtc *const rtc,
return __metal_driver_sifive_rtc0_get_count(rtc);
}
-int __metal_driver_sifive_rtc0_run(const struct metal_rtc *const rtc, const enum metal_rtc_run_option option) {
+int __metal_driver_sifive_rtc0_run(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option) {
const uint64_t base = __metal_driver_sifive_rtc0_control_base(rtc);
switch (option) {
@@ -97,11 +110,13 @@ int __metal_driver_sifive_rtc0_run(const struct metal_rtc *const rtc, const enum
return 0;
}
-struct metal_interrupt *__metal_driver_sifive_rtc0_get_interrupt(const struct metal_rtc *const rtc) {
+struct metal_interrupt *
+__metal_driver_sifive_rtc0_get_interrupt(const struct metal_rtc *const rtc) {
return __metal_driver_sifive_rtc0_interrupt_parent(rtc);
}
-int __metal_driver_sifive_rtc0_get_interrupt_id(const struct metal_rtc *const rtc) {
+int __metal_driver_sifive_rtc0_get_interrupt_id(
+ const struct metal_rtc *const rtc) {
return __metal_driver_sifive_rtc0_interrupt_line(rtc);
}
@@ -119,3 +134,4 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_rtc0) = {
#endif
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_simuart0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_simuart0.c
new file mode 100644
index 000000000..7a3e1b655
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_simuart0.c
@@ -0,0 +1,79 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine/platform.h>
+
+#ifdef METAL_SIFIVE_SIMUART0
+
+#include <assert.h>
+#include <metal/drivers/sifive_simuart0.h>
+#include <metal/machine.h>
+
+/* TXDATA Fields */
+#define SIMUART_TXEN (1 << 0)
+
+#define SIMUART_REG(offset) (((unsigned long)control_base + offset))
+#define SIMUART_REGB(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u8 *)SIMUART_REG(offset)))
+#define SIMUART_REGW(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)SIMUART_REG(offset)))
+
+struct metal_interrupt *
+__metal_driver_sifive_simuart0_interrupt_controller(struct metal_uart *uart) {
+ return __metal_driver_sifive_simuart0_interrupt_parent(uart);
+}
+
+int __metal_driver_sifive_simuart0_get_interrupt_id(struct metal_uart *uart) {
+ return (__metal_driver_sifive_simuart0_interrupt_line(uart) +
+ METAL_INTERRUPT_ID_GL0);
+}
+
+int __metal_driver_sifive_simuart0_putc(struct metal_uart *uart, int c) {
+ long control_base = __metal_driver_sifive_simuart0_control_base(uart);
+
+ SIMUART_REGW(METAL_SIFIVE_SIMUART0_TXDATA) = c;
+ return 0;
+}
+
+int __metal_driver_sifive_simuart0_getc(struct metal_uart *uart, int *c) {
+ return 0;
+}
+
+int __metal_driver_sifive_simuart0_get_baud_rate(struct metal_uart *guart) {
+ struct __metal_driver_sifive_simuart0 *uart = (void *)guart;
+ return uart->baud_rate;
+}
+
+int __metal_driver_sifive_simuart0_set_baud_rate(struct metal_uart *guart,
+ int baud_rate) {
+ struct __metal_driver_sifive_simuart0 *uart = (void *)guart;
+ long control_base = __metal_driver_sifive_simuart0_control_base(guart);
+ struct metal_clock *clock = __metal_driver_sifive_simuart0_clock(guart);
+
+ uart->baud_rate = baud_rate;
+
+ if (clock != NULL) {
+ long clock_rate = clock->vtable->get_rate_hz(clock);
+ SIMUART_REGW(METAL_SIFIVE_SIMUART0_DIV) = clock_rate / baud_rate - 1;
+ SIMUART_REGW(METAL_SIFIVE_SIMUART0_TXCTRL) |= SIMUART_TXEN;
+ }
+ return 0;
+}
+
+void __metal_driver_sifive_simuart0_init(struct metal_uart *guart,
+ int baud_rate) {}
+
+__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_simuart0) = {
+ .uart.init = __metal_driver_sifive_simuart0_init,
+ .uart.putc = __metal_driver_sifive_simuart0_putc,
+ .uart.getc = __metal_driver_sifive_simuart0_getc,
+ .uart.get_baud_rate = __metal_driver_sifive_simuart0_get_baud_rate,
+ .uart.set_baud_rate = __metal_driver_sifive_simuart0_set_baud_rate,
+ .uart.controller_interrupt =
+ __metal_driver_sifive_simuart0_interrupt_controller,
+ .uart.get_interrupt_id = __metal_driver_sifive_simuart0_get_interrupt_id,
+};
+
+#endif /* METAL_SIFIVE_SIMUART0 */
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_spi0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_spi0.c
index 2a346354f..34f8e0a5d 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_spi0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_spi0.c
@@ -11,48 +11,51 @@
#include <time.h>
/* Register fields */
-#define METAL_SPI_SCKDIV_MASK 0xFFF
+#define METAL_SPI_SCKDIV_MASK 0xFFF
-#define METAL_SPI_SCKMODE_PHA_SHIFT 0
-#define METAL_SPI_SCKMODE_POL_SHIFT 1
+#define METAL_SPI_SCKMODE_PHA_SHIFT 0
+#define METAL_SPI_SCKMODE_POL_SHIFT 1
-#define METAL_SPI_CSMODE_MASK 3
-#define METAL_SPI_CSMODE_AUTO 0
-#define METAL_SPI_CSMODE_HOLD 2
-#define METAL_SPI_CSMODE_OFF 3
+#define METAL_SPI_CSMODE_MASK 3
+#define METAL_SPI_CSMODE_AUTO 0
+#define METAL_SPI_CSMODE_HOLD 2
+#define METAL_SPI_CSMODE_OFF 3
-#define METAL_SPI_PROTO_MASK 3
-#define METAL_SPI_PROTO_SINGLE 0
-#define METAL_SPI_PROTO_DUAL 1
-#define METAL_SPI_PROTO_QUAD 2
+#define METAL_SPI_PROTO_MASK 3
+#define METAL_SPI_PROTO_SINGLE 0
+#define METAL_SPI_PROTO_DUAL 1
+#define METAL_SPI_PROTO_QUAD 2
-#define METAL_SPI_ENDIAN_LSB 4
+#define METAL_SPI_ENDIAN_LSB 4
-#define METAL_SPI_DISABLE_RX 8
+#define METAL_SPI_DISABLE_RX 8
-#define METAL_SPI_FRAME_LEN_SHIFT 16
-#define METAL_SPI_FRAME_LEN_MASK (0xF << METAL_SPI_FRAME_LEN_SHIFT)
+#define METAL_SPI_FRAME_LEN_SHIFT 16
+#define METAL_SPI_FRAME_LEN_MASK (0xF << METAL_SPI_FRAME_LEN_SHIFT)
-#define METAL_SPI_TXDATA_FULL (1 << 31)
-#define METAL_SPI_RXDATA_EMPTY (1 << 31)
-#define METAL_SPI_TXMARK_MASK 7
-#define METAL_SPI_TXWM 1
-#define METAL_SPI_TXRXDATA_MASK (0xFF)
+#define METAL_SPI_TXDATA_FULL (1 << 31)
+#define METAL_SPI_RXDATA_EMPTY (1 << 31)
+#define METAL_SPI_TXMARK_MASK 7
+#define METAL_SPI_TXWM 1
+#define METAL_SPI_TXRXDATA_MASK (0xFF)
-#define METAL_SPI_INTERVAL_SHIFT 16
+#define METAL_SPI_INTERVAL_SHIFT 16
-#define METAL_SPI_CONTROL_IO 0
-#define METAL_SPI_CONTROL_MAPPED 1
+#define METAL_SPI_CONTROL_IO 0
+#define METAL_SPI_CONTROL_MAPPED 1
-#define METAL_SPI_REG(offset) (((unsigned long)control_base + offset))
-#define METAL_SPI_REGB(offset) (__METAL_ACCESS_ONCE((__metal_io_u8 *)METAL_SPI_REG(offset)))
-#define METAL_SPI_REGW(offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_SPI_REG(offset)))
+#define METAL_SPI_REG(offset) (((unsigned long)control_base + offset))
+#define METAL_SPI_REGB(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u8 *)METAL_SPI_REG(offset)))
+#define METAL_SPI_REGW(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_SPI_REG(offset)))
-#define METAL_SPI_RXDATA_TIMEOUT 1
+#define METAL_SPI_RXDATA_TIMEOUT 1
-static int configure_spi(struct __metal_driver_sifive_spi0 *spi, struct metal_spi_config *config)
-{
- long control_base = __metal_driver_sifive_spi0_control_base((struct metal_spi *)spi);
+static int configure_spi(struct __metal_driver_sifive_spi0 *spi,
+ struct metal_spi_config *config) {
+ long control_base =
+ __metal_driver_sifive_spi0_control_base((struct metal_spi *)spi);
/* Set protocol */
METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) &= ~(METAL_SPI_PROTO_MASK);
switch (config->protocol) {
@@ -77,21 +80,25 @@ static int configure_spi(struct __metal_driver_sifive_spi0 *spi, struct metal_sp
}
/* Set Polarity */
- if(config->polarity) {
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) |= (1 << METAL_SPI_SCKMODE_PHA_SHIFT);
+ if (config->polarity) {
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) |=
+ (1 << METAL_SPI_SCKMODE_POL_SHIFT);
} else {
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) &= ~(1 << METAL_SPI_SCKMODE_PHA_SHIFT);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) &=
+ ~(1 << METAL_SPI_SCKMODE_POL_SHIFT);
}
/* Set Phase */
- if(config->phase) {
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) |= (1 << METAL_SPI_SCKMODE_POL_SHIFT);
+ if (config->phase) {
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) |=
+ (1 << METAL_SPI_SCKMODE_PHA_SHIFT);
} else {
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) &= ~(1 << METAL_SPI_SCKMODE_POL_SHIFT);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKMODE) &=
+ ~(1 << METAL_SPI_SCKMODE_PHA_SHIFT);
}
/* Set Endianness */
- if(config->little_endian) {
+ if (config->little_endian) {
METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) |= METAL_SPI_ENDIAN_LSB;
} else {
METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) &= ~(METAL_SPI_ENDIAN_LSB);
@@ -101,24 +108,26 @@ static int configure_spi(struct __metal_driver_sifive_spi0 *spi, struct metal_sp
METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) &= ~(METAL_SPI_DISABLE_RX);
/* Set CS Active */
- if(config->cs_active_high) {
+ if (config->cs_active_high) {
METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSDEF) = 0;
} else {
METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSDEF) = 1;
}
/* Set frame length */
- if((METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) & METAL_SPI_FRAME_LEN_MASK) != (8 << METAL_SPI_FRAME_LEN_SHIFT)) {
+ if ((METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) & METAL_SPI_FRAME_LEN_MASK) !=
+ (8 << METAL_SPI_FRAME_LEN_SHIFT)) {
METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) &= ~(METAL_SPI_FRAME_LEN_MASK);
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) |= (8 << METAL_SPI_FRAME_LEN_SHIFT);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_FMT) |=
+ (8 << METAL_SPI_FRAME_LEN_SHIFT);
}
/* Set CS line */
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSID) = 1 << (config->csid);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSID) = config->csid;
/* Toggle off memory-mapped SPI flash mode, toggle on programmable IO mode
- * It seems that with this line uncommented, the debugger cannot have access
- * to the chip at all because it assumes the chip is in memory-mapped mode.
+ * It seems that with this line uncommented, the debugger cannot have access
+ * to the chip at all because it assumes the chip is in memory-mapped mode.
* I have to compile the code with this line commented and launch gdb,
* reset cores, reset $pc, set *((int *) 0x20004060) = 0, (set the flash
* interface control register to programmable I/O mode) and then continue
@@ -151,18 +160,16 @@ static void spi_mode_switch(struct __metal_driver_sifive_spi0 *spi,
}
int __metal_driver_sifive_spi0_transfer(struct metal_spi *gspi,
- struct metal_spi_config *config,
- size_t len,
- char *tx_buf,
- char *rx_buf)
-{
+ struct metal_spi_config *config,
+ size_t len, char *tx_buf,
+ char *rx_buf) {
struct __metal_driver_sifive_spi0 *spi = (void *)gspi;
long control_base = __metal_driver_sifive_spi0_control_base(gspi);
int rc = 0;
size_t i = 0;
rc = configure_spi(spi, config);
- if(rc != 0) {
+ if (rc != 0) {
return rc;
}
@@ -171,7 +178,7 @@ int __metal_driver_sifive_spi0_transfer(struct metal_spi *gspi,
METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSMODE) |= METAL_SPI_CSMODE_HOLD;
unsigned long rxdata;
-
+
/* Declare time_t variables to break out of infinite while loop */
time_t endwait;
@@ -269,9 +276,11 @@ int __metal_driver_sifive_spi0_transfer(struct metal_spi *gspi,
/* Master send bytes to the slave */
/* Wait for TXFIFO to not be full */
- while (METAL_SPI_REGW(METAL_SIFIVE_SPI0_TXDATA) & METAL_SPI_TXDATA_FULL);
-
- /* Transfer byte by modifying the least significant byte in the TXDATA register */
+ while (METAL_SPI_REGW(METAL_SIFIVE_SPI0_TXDATA) & METAL_SPI_TXDATA_FULL)
+ ;
+
+ /* Transfer byte by modifying the least significant byte in the TXDATA
+ * register */
if (tx_buf) {
METAL_SPI_REGB(METAL_SIFIVE_SPI0_TXDATA) = tx_buf[i];
} else {
@@ -281,15 +290,17 @@ int __metal_driver_sifive_spi0_transfer(struct metal_spi *gspi,
/* Master receives bytes from the RX FIFO */
- /* Wait for RXFIFO to not be empty, but break the nested loops if timeout
- * this timeout method needs refining, preferably taking into account
- * the device specs */
+ /* Wait for RXFIFO to not be empty, but break the nested loops if
+ * timeout this timeout method needs refining, preferably taking into
+ * account the device specs */
endwait = metal_time() + METAL_SPI_RXDATA_TIMEOUT;
- while ((rxdata = METAL_SPI_REGW(METAL_SIFIVE_SPI0_RXDATA)) & METAL_SPI_RXDATA_EMPTY) {
+ while ((rxdata = METAL_SPI_REGW(METAL_SIFIVE_SPI0_RXDATA)) &
+ METAL_SPI_RXDATA_EMPTY) {
if (metal_time() > endwait) {
/* If timeout, deassert the CS */
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSMODE) &= ~(METAL_SPI_CSMODE_MASK);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSMODE) &=
+ ~(METAL_SPI_CSMODE_MASK);
/* If timeout, return error code 1 immediately */
return 1;
@@ -298,29 +309,30 @@ int __metal_driver_sifive_spi0_transfer(struct metal_spi *gspi,
/* Only store the dequeued byte if the receive_buffer is not NULL */
if (rx_buf) {
- rx_buf[i] = (char) (rxdata & METAL_SPI_TXRXDATA_MASK);
+ rx_buf[i] = (char)(rxdata & METAL_SPI_TXRXDATA_MASK);
}
}
- /* On the last byte, set CSMODE to auto so that the chip select transitions back to high
- * The reason that CS pin is not deasserted after transmitting out the byte buffer is timing.
- * The code on the host side likely executes faster than the ability of FIFO to send out bytes.
- * After the host iterates through the array, fifo is likely not cleared yet. If host deasserts
- * the CS pin immediately, the following bytes in the output FIFO will not be sent consecutively.
+ /* On the last byte, set CSMODE to auto so that the chip select transitions
+ * back to high The reason that CS pin is not deasserted after transmitting
+ * out the byte buffer is timing. The code on the host side likely executes
+ * faster than the ability of FIFO to send out bytes. After the host
+ * iterates through the array, fifo is likely not cleared yet. If host
+ * deasserts the CS pin immediately, the following bytes in the output FIFO
+ * will not be sent consecutively.
* There needs to be a better way to handle this. */
METAL_SPI_REGW(METAL_SIFIVE_SPI0_CSMODE) &= ~(METAL_SPI_CSMODE_MASK);
return 0;
}
-int __metal_driver_sifive_spi0_get_baud_rate(struct metal_spi *gspi)
-{
+int __metal_driver_sifive_spi0_get_baud_rate(struct metal_spi *gspi) {
struct __metal_driver_sifive_spi0 *spi = (void *)gspi;
return spi->baud_rate;
}
-int __metal_driver_sifive_spi0_set_baud_rate(struct metal_spi *gspi, int baud_rate)
-{
+int __metal_driver_sifive_spi0_set_baud_rate(struct metal_spi *gspi,
+ int baud_rate) {
long control_base = __metal_driver_sifive_spi0_control_base(gspi);
struct metal_clock *clock = __metal_driver_sifive_spi0_clock(gspi);
struct __metal_driver_sifive_spi0 *spi = (void *)gspi;
@@ -333,7 +345,7 @@ int __metal_driver_sifive_spi0_set_baud_rate(struct metal_spi *gspi, int baud_ra
/* Calculate divider */
long div = (clock_rate / (2 * baud_rate)) - 1;
- if(div > METAL_SPI_SCKDIV_MASK) {
+ if (div > METAL_SPI_SCKDIV_MASK) {
/* The requested baud rate is lower than we can support at
* the current clock rate */
return -1;
@@ -341,62 +353,67 @@ int __metal_driver_sifive_spi0_set_baud_rate(struct metal_spi *gspi, int baud_ra
/* Set divider */
METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKDIV) &= ~METAL_SPI_SCKDIV_MASK;
- METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKDIV) |= (div & METAL_SPI_SCKDIV_MASK);
+ METAL_SPI_REGW(METAL_SIFIVE_SPI0_SCKDIV) |=
+ (div & METAL_SPI_SCKDIV_MASK);
}
return 0;
}
-static void pre_rate_change_callback_func(void *priv)
-{
- long control_base = __metal_driver_sifive_spi0_control_base((struct metal_spi *)priv);
+static void pre_rate_change_callback_func(void *priv) {
+ long control_base =
+ __metal_driver_sifive_spi0_control_base((struct metal_spi *)priv);
/* Detect when the TXDATA is empty by setting the transmit watermark count
- * to one and waiting until an interrupt is pending (indicating an empty TXFIFO) */
+ * to one and waiting until an interrupt is pending (indicating an empty
+ * TXFIFO) */
METAL_SPI_REGW(METAL_SIFIVE_SPI0_TXMARK) &= ~(METAL_SPI_TXMARK_MASK);
METAL_SPI_REGW(METAL_SIFIVE_SPI0_TXMARK) |= (METAL_SPI_TXMARK_MASK & 1);
- while((METAL_SPI_REGW(METAL_SIFIVE_SPI0_IP) & METAL_SPI_TXWM) == 0) ;
+ while ((METAL_SPI_REGW(METAL_SIFIVE_SPI0_IP) & METAL_SPI_TXWM) == 0)
+ ;
}
-static void post_rate_change_callback_func(void *priv)
-{
+static void post_rate_change_callback_func(void *priv) {
struct __metal_driver_sifive_spi0 *spi = priv;
metal_spi_set_baud_rate(&spi->spi, spi->baud_rate);
}
-void __metal_driver_sifive_spi0_init(struct metal_spi *gspi, int baud_rate)
-{
+void __metal_driver_sifive_spi0_init(struct metal_spi *gspi, int baud_rate) {
struct __metal_driver_sifive_spi0 *spi = (void *)(gspi);
struct metal_clock *clock = __metal_driver_sifive_spi0_clock(gspi);
- struct __metal_driver_sifive_gpio0 *pinmux = __metal_driver_sifive_spi0_pinmux(gspi);
+ struct __metal_driver_sifive_gpio0 *pinmux =
+ __metal_driver_sifive_spi0_pinmux(gspi);
- if(clock != NULL) {
+ if (clock != NULL) {
spi->pre_rate_change_callback.callback = &pre_rate_change_callback_func;
spi->pre_rate_change_callback.priv = spi;
- metal_clock_register_pre_rate_change_callback(clock, &(spi->pre_rate_change_callback));
+ metal_clock_register_pre_rate_change_callback(
+ clock, &(spi->pre_rate_change_callback));
- spi->post_rate_change_callback.callback = &post_rate_change_callback_func;
+ spi->post_rate_change_callback.callback =
+ &post_rate_change_callback_func;
spi->post_rate_change_callback.priv = spi;
- metal_clock_register_post_rate_change_callback(clock, &(spi->post_rate_change_callback));
+ metal_clock_register_post_rate_change_callback(
+ clock, &(spi->post_rate_change_callback));
}
metal_spi_set_baud_rate(&(spi->spi), baud_rate);
if (pinmux != NULL) {
- long pinmux_output_selector = __metal_driver_sifive_spi0_pinmux_output_selector(gspi);
- long pinmux_source_selector = __metal_driver_sifive_spi0_pinmux_source_selector(gspi);
- pinmux->gpio.vtable->enable_io(
- (struct metal_gpio *) pinmux,
- pinmux_output_selector,
- pinmux_source_selector
- );
+ long pinmux_output_selector =
+ __metal_driver_sifive_spi0_pinmux_output_selector(gspi);
+ long pinmux_source_selector =
+ __metal_driver_sifive_spi0_pinmux_source_selector(gspi);
+ pinmux->gpio.vtable->enable_io((struct metal_gpio *)pinmux,
+ pinmux_output_selector,
+ pinmux_source_selector);
}
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_spi0) = {
- .spi.init = __metal_driver_sifive_spi0_init,
- .spi.transfer = __metal_driver_sifive_spi0_transfer,
+ .spi.init = __metal_driver_sifive_spi0_init,
+ .spi.transfer = __metal_driver_sifive_spi0_transfer,
.spi.get_baud_rate = __metal_driver_sifive_spi0_get_baud_rate,
.spi.set_baud_rate = __metal_driver_sifive_spi0_set_baud_rate,
};
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_test0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_test0.c
index 79deebbf5..c21d09685 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_test0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_test0.c
@@ -12,18 +12,20 @@
#include <metal/drivers/sifive_test0.h>
#include <metal/io.h>
-void __metal_driver_sifive_test0_exit(const struct __metal_shutdown *sd, int code) __attribute__((noreturn));
-void __metal_driver_sifive_test0_exit(const struct __metal_shutdown *sd, int code)
-{
+void __metal_driver_sifive_test0_exit(const struct __metal_shutdown *sd,
+ int code) __attribute__((noreturn));
+void __metal_driver_sifive_test0_exit(const struct __metal_shutdown *sd,
+ int code) {
long base = __metal_driver_sifive_test0_base(sd);
uint32_t out = (code << 16) + (code == 0 ? 0x5555 : 0x3333);
while (1) {
- __METAL_ACCESS_ONCE((__metal_io_u32 *)(base + METAL_SIFIVE_TEST0_FINISHER_OFFSET)) = out;
+ __METAL_ACCESS_ONCE((
+ __metal_io_u32 *)(base + METAL_SIFIVE_TEST0_FINISHER_OFFSET)) = out;
}
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_test0) = {
- .shutdown.exit = &__metal_driver_sifive_test0_exit,
+ .shutdown.exit = &__metal_driver_sifive_test0_exit,
};
#endif /* METAL_SIFIVE_TEST0 */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_trace.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_trace.c
index 8b63fbd28..6b82e0f3e 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_trace.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_trace.c
@@ -34,8 +34,7 @@ static void write_itc_uint8(struct metal_uart *trace, uint8_t data) {
TRACE_REG8(METAL_SIFIVE_TRACE_ITCSTIMULUS + 3) = data;
}
-int __metal_driver_sifive_trace_putc(struct metal_uart *trace,
- unsigned char c) {
+int __metal_driver_sifive_trace_putc(struct metal_uart *trace, int c) {
static uint32_t buffer = 0;
static int bytes_in_buffer = 0;
@@ -48,7 +47,7 @@ int __metal_driver_sifive_trace_putc(struct metal_uart *trace,
buffer = 0;
bytes_in_buffer = 0;
- } else if ((c == '\n') || (c == '\r')) { // partial write
+ } else if (((char)c == '\n') || ((char)c == '\r')) { // partial write
switch (bytes_in_buffer) {
case 3: // do a full word write
write_itc_uint16(trace, (uint16_t)(buffer));
@@ -66,7 +65,7 @@ int __metal_driver_sifive_trace_putc(struct metal_uart *trace,
bytes_in_buffer = 0;
}
- return (int)c;
+ return c;
}
void __metal_driver_sifive_trace_init(struct metal_uart *trace, int baud_rate) {
@@ -93,3 +92,5 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_trace) = {
};
#endif /* METAL_SIFIVE_TRACE */
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_uart0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_uart0.c
index 2e8098aa7..8d2634413 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_uart0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_uart0.c
@@ -9,79 +9,132 @@
#include <metal/machine.h>
/* TXDATA Fields */
-#define UART_TXEN (1 << 0)
-#define UART_TXFULL (1 << 31)
+#define UART_TXEN (1 << 0)
+#define UART_TXFULL (1 << 31)
/* RXDATA Fields */
-#define UART_RXEN (1 << 0)
-#define UART_RXEMPTY (1 << 31)
+#define UART_RXEN (1 << 0)
+#define UART_RXEMPTY (1 << 31)
/* TXCTRL Fields */
-#define UART_NSTOP (1 << 1)
-#define UART_TXCNT(count) ((0x7 & count) << 16)
+#define UART_NSTOP (1 << 1)
+#define UART_TXCNT(count) ((0x7 & count) << 16)
+
+/* RXCTRL Fields */
+#define UART_RXCNT(count) ((0x7 & count) << 16)
/* IP Fields */
-#define UART_TXWM (1 << 0)
+#define UART_TXWM (1 << 0)
+#define UART_RXWM (1 << 1)
-#define UART_REG(offset) (((unsigned long)control_base + offset))
-#define UART_REGB(offset) (__METAL_ACCESS_ONCE((__metal_io_u8 *)UART_REG(offset)))
-#define UART_REGW(offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)UART_REG(offset)))
+#define UART_REG(offset) (((unsigned long)control_base + offset))
+#define UART_REGB(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u8 *)UART_REG(offset)))
+#define UART_REGW(offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)UART_REG(offset)))
struct metal_interrupt *
-__metal_driver_sifive_uart0_interrupt_controller(struct metal_uart *uart)
-{
+__metal_driver_sifive_uart0_interrupt_controller(struct metal_uart *uart) {
return __metal_driver_sifive_uart0_interrupt_parent(uart);
}
-int __metal_driver_sifive_uart0_get_interrupt_id(struct metal_uart *uart)
-{
- return (__metal_driver_sifive_uart0_interrupt_line(uart) + METAL_INTERRUPT_ID_GL0);
+int __metal_driver_sifive_uart0_get_interrupt_id(struct metal_uart *uart) {
+ return __metal_driver_sifive_uart0_interrupt_line(uart);
}
+int __metal_driver_sifive_uart0_tx_interrupt_enable(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ UART_REGW(METAL_SIFIVE_UART0_IE) |= UART_TXWM;
+ return 0;
+}
-int __metal_driver_sifive_uart0_txready(struct metal_uart *uart)
-{
- long control_base = __metal_driver_sifive_uart0_control_base(uart);
+int __metal_driver_sifive_uart0_tx_interrupt_disable(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
- return !((UART_REGW(METAL_SIFIVE_UART0_TXDATA) & UART_TXFULL));
+ UART_REGW(METAL_SIFIVE_UART0_IE) &= ~UART_TXWM;
+ return 0;
}
+int __metal_driver_sifive_uart0_rx_interrupt_enable(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ UART_REGW(METAL_SIFIVE_UART0_IE) |= UART_RXWM;
+ return 0;
+}
-int __metal_driver_sifive_uart0_putc(struct metal_uart *uart, int c)
-{
+int __metal_driver_sifive_uart0_rx_interrupt_disable(struct metal_uart *uart) {
long control_base = __metal_driver_sifive_uart0_control_base(uart);
- while (!__metal_driver_sifive_uart0_txready(uart)) {
- /* wait */
+ UART_REGW(METAL_SIFIVE_UART0_IE) &= ~UART_RXWM;
+ return 0;
+}
+
+int __metal_driver_sifive_uart0_txready(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ return !!((UART_REGW(METAL_SIFIVE_UART0_TXDATA) & UART_TXFULL));
+}
+
+int __metal_driver_sifive_uart0_set_tx_watermark(struct metal_uart *uart,
+ size_t level) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ UART_REGW(METAL_SIFIVE_UART0_TXCTRL) |= UART_TXCNT(level);
+ return 0;
+}
+
+size_t __metal_driver_sifive_uart0_get_tx_watermark(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ return ((UART_REGW(METAL_SIFIVE_UART0_TXCTRL) >> 16) & 0x7);
+}
+
+int __metal_driver_sifive_uart0_set_rx_watermark(struct metal_uart *uart,
+ size_t level) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ UART_REGW(METAL_SIFIVE_UART0_RXCTRL) |= UART_RXCNT(level);
+ return 0;
+}
+
+size_t __metal_driver_sifive_uart0_get_rx_watermark(struct metal_uart *uart) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ return ((UART_REGW(METAL_SIFIVE_UART0_RXCTRL) >> 16) & 0x7);
+}
+
+int __metal_driver_sifive_uart0_putc(struct metal_uart *uart, int c) {
+ long control_base = __metal_driver_sifive_uart0_control_base(uart);
+
+ while (__metal_driver_sifive_uart0_txready(uart) != 0) {
+ /* wait */
}
UART_REGW(METAL_SIFIVE_UART0_TXDATA) = c;
return 0;
}
-
-int __metal_driver_sifive_uart0_getc(struct metal_uart *uart, int *c)
-{
+int __metal_driver_sifive_uart0_getc(struct metal_uart *uart, int *c) {
uint32_t ch;
long control_base = __metal_driver_sifive_uart0_control_base(uart);
/* No seperate status register, we get status and the byte at same time */
- ch = UART_REGW(METAL_SIFIVE_UART0_RXDATA);;
- if( ch & UART_RXEMPTY ){
- *c = -1; /* aka: EOF in most of the world */
+ ch = UART_REGW(METAL_SIFIVE_UART0_RXDATA);
+ ;
+ if (ch & UART_RXEMPTY) {
+ *c = -1; /* aka: EOF in most of the world */
} else {
- *c = ch & 0x0ff;
+ *c = ch & 0x0ff;
}
return 0;
}
-
-int __metal_driver_sifive_uart0_get_baud_rate(struct metal_uart *guart)
-{
+int __metal_driver_sifive_uart0_get_baud_rate(struct metal_uart *guart) {
struct __metal_driver_sifive_uart0 *uart = (void *)guart;
return uart->baud_rate;
}
-int __metal_driver_sifive_uart0_set_baud_rate(struct metal_uart *guart, int baud_rate)
-{
+int __metal_driver_sifive_uart0_set_baud_rate(struct metal_uart *guart,
+ int baud_rate) {
struct __metal_driver_sifive_uart0 *uart = (void *)guart;
long control_base = __metal_driver_sifive_uart0_control_base(guart);
struct metal_clock *clock = __metal_driver_sifive_uart0_clock(guart);
@@ -97,11 +150,12 @@ int __metal_driver_sifive_uart0_set_baud_rate(struct metal_uart *guart, int baud
return 0;
}
-static void pre_rate_change_callback_func(void *priv)
-{
+static void pre_rate_change_callback_func(void *priv) {
struct __metal_driver_sifive_uart0 *uart = priv;
- long control_base = __metal_driver_sifive_uart0_control_base((struct metal_uart *)priv);
- struct metal_clock *clock = __metal_driver_sifive_uart0_clock((struct metal_uart *)priv);
+ long control_base =
+ __metal_driver_sifive_uart0_control_base((struct metal_uart *)priv);
+ struct metal_clock *clock =
+ __metal_driver_sifive_uart0_clock((struct metal_uart *)priv);
/* Detect when the TXDATA is empty by setting the transmit watermark count
* to one and waiting until an interrupt is pending */
@@ -109,63 +163,80 @@ static void pre_rate_change_callback_func(void *priv)
UART_REGW(METAL_SIFIVE_UART0_TXCTRL) &= ~(UART_TXCNT(0x7));
UART_REGW(METAL_SIFIVE_UART0_TXCTRL) |= UART_TXCNT(1);
- while((UART_REGW(METAL_SIFIVE_UART0_IP) & UART_TXWM) == 0) ;
+ while ((UART_REGW(METAL_SIFIVE_UART0_IP) & UART_TXWM) == 0)
+ ;
/* When the TXDATA clears, the UART is still shifting out the last byte.
* Calculate the time we must drain to finish transmitting and then wait
* that long. */
- long bits_per_symbol = (UART_REGW(METAL_SIFIVE_UART0_TXCTRL) & (1 << 1)) ? 9 : 10;
+ long bits_per_symbol =
+ (UART_REGW(METAL_SIFIVE_UART0_TXCTRL) & (1 << 1)) ? 9 : 10;
long clk_freq = clock->vtable->get_rate_hz(clock);
long cycles_to_wait = bits_per_symbol * clk_freq / uart->baud_rate;
- for(volatile long x = 0; x < cycles_to_wait; x++)
+ for (volatile long x = 0; x < cycles_to_wait; x++)
__asm__("nop");
}
-static void post_rate_change_callback_func(void *priv)
-{
+static void post_rate_change_callback_func(void *priv) {
struct __metal_driver_sifive_uart0 *uart = priv;
metal_uart_set_baud_rate(&uart->uart, uart->baud_rate);
}
-void __metal_driver_sifive_uart0_init(struct metal_uart *guart, int baud_rate)
-{
+void __metal_driver_sifive_uart0_init(struct metal_uart *guart, int baud_rate) {
struct __metal_driver_sifive_uart0 *uart = (void *)(guart);
struct metal_clock *clock = __metal_driver_sifive_uart0_clock(guart);
- struct __metal_driver_sifive_gpio0 *pinmux = __metal_driver_sifive_uart0_pinmux(guart);
+ struct __metal_driver_sifive_gpio0 *pinmux =
+ __metal_driver_sifive_uart0_pinmux(guart);
- if(clock != NULL) {
- uart->pre_rate_change_callback.callback = &pre_rate_change_callback_func;
+ if (clock != NULL) {
+ uart->pre_rate_change_callback.callback =
+ &pre_rate_change_callback_func;
uart->pre_rate_change_callback.priv = guart;
- metal_clock_register_pre_rate_change_callback(clock, &(uart->pre_rate_change_callback));
+ metal_clock_register_pre_rate_change_callback(
+ clock, &(uart->pre_rate_change_callback));
- uart->post_rate_change_callback.callback = &post_rate_change_callback_func;
+ uart->post_rate_change_callback.callback =
+ &post_rate_change_callback_func;
uart->post_rate_change_callback.priv = guart;
- metal_clock_register_post_rate_change_callback(clock, &(uart->post_rate_change_callback));
+ metal_clock_register_post_rate_change_callback(
+ clock, &(uart->post_rate_change_callback));
}
metal_uart_set_baud_rate(&(uart->uart), baud_rate);
if (pinmux != NULL) {
- long pinmux_output_selector = __metal_driver_sifive_uart0_pinmux_output_selector(guart);
- long pinmux_source_selector = __metal_driver_sifive_uart0_pinmux_source_selector(guart);
- pinmux->gpio.vtable->enable_io(
- (struct metal_gpio *) pinmux,
- pinmux_output_selector,
- pinmux_source_selector
- );
+ long pinmux_output_selector =
+ __metal_driver_sifive_uart0_pinmux_output_selector(guart);
+ long pinmux_source_selector =
+ __metal_driver_sifive_uart0_pinmux_source_selector(guart);
+ pinmux->gpio.vtable->enable_io((struct metal_gpio *)pinmux,
+ pinmux_output_selector,
+ pinmux_source_selector);
}
}
__METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_uart0) = {
- .uart.init = __metal_driver_sifive_uart0_init,
- .uart.putc = __metal_driver_sifive_uart0_putc,
- .uart.getc = __metal_driver_sifive_uart0_getc,
+ .uart.init = __metal_driver_sifive_uart0_init,
+ .uart.putc = __metal_driver_sifive_uart0_putc,
+ .uart.getc = __metal_driver_sifive_uart0_getc,
+ .uart.txready = __metal_driver_sifive_uart0_txready,
.uart.get_baud_rate = __metal_driver_sifive_uart0_get_baud_rate,
.uart.set_baud_rate = __metal_driver_sifive_uart0_set_baud_rate,
- .uart.controller_interrupt = __metal_driver_sifive_uart0_interrupt_controller,
- .uart.get_interrupt_id = __metal_driver_sifive_uart0_get_interrupt_id,
+ .uart.controller_interrupt =
+ __metal_driver_sifive_uart0_interrupt_controller,
+ .uart.get_interrupt_id = __metal_driver_sifive_uart0_get_interrupt_id,
+ .uart.tx_interrupt_enable = __metal_driver_sifive_uart0_tx_interrupt_enable,
+ .uart.tx_interrupt_disable =
+ __metal_driver_sifive_uart0_tx_interrupt_disable,
+ .uart.rx_interrupt_enable = __metal_driver_sifive_uart0_rx_interrupt_enable,
+ .uart.rx_interrupt_disable =
+ __metal_driver_sifive_uart0_rx_interrupt_disable,
+ .uart.set_tx_watermark = __metal_driver_sifive_uart0_set_tx_watermark,
+ .uart.get_tx_watermark = __metal_driver_sifive_uart0_get_tx_watermark,
+ .uart.set_rx_watermark = __metal_driver_sifive_uart0_set_rx_watermark,
+ .uart.get_rx_watermark = __metal_driver_sifive_uart0_get_rx_watermark,
};
#endif /* METAL_SIFIVE_UART0 */
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_wdog0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_wdog0.c
index 1a6cf362e..4f37b7eb2 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_wdog0.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/sifive_wdog0.c
@@ -21,54 +21,65 @@
/* WDOGCMP */
#define METAL_WDOGCMP_MASK 0xFFFF
-#define WDOG_REG(base, offset) (((unsigned long)base + offset))
-#define WDOG_REGB(base, offset) (__METAL_ACCESS_ONCE((__metal_io_u8 *)WDOG_REG(base, offset)))
-#define WDOG_REGW(base, offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)WDOG_REG(base, offset)))
+#define WDOG_REG(base, offset) (((unsigned long)base + offset))
+#define WDOG_REGB(base, offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u8 *)WDOG_REG(base, offset)))
+#define WDOG_REGW(base, offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)WDOG_REG(base, offset)))
/* All writes to watchdog registers must be precedded by a write of
* a magic number to WDOGKEY */
-#define WDOG_UNLOCK(base) (WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGKEY) = METAL_SIFIVE_WDOG0_MAGIC_KEY)
+#define WDOG_UNLOCK(base) \
+ (WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGKEY) = METAL_SIFIVE_WDOG0_MAGIC_KEY)
/* Unlock the watchdog and then perform a register access */
-#define WDOG_UNLOCK_REGW(base, offset) \
- WDOG_UNLOCK(base);\
+#define WDOG_UNLOCK_REGW(base, offset) \
+ WDOG_UNLOCK(base); \
WDOG_REGW(base, offset)
-int __metal_driver_sifive_wdog0_feed(const struct metal_watchdog *const wdog)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+int __metal_driver_sifive_wdog0_feed(const struct metal_watchdog *const wdog) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGFEED) = METAL_SIFIVE_WDOG0_MAGIC_FOOD;
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGFEED) =
+ METAL_SIFIVE_WDOG0_MAGIC_FOOD;
return 0;
}
-long int __metal_driver_sifive_wdog0_get_rate(const struct metal_watchdog *const wdog)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
- const struct metal_clock *const clock = __metal_driver_sifive_wdog0_clock(wdog);
-
+long int
+__metal_driver_sifive_wdog0_get_rate(const struct metal_watchdog *const wdog) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+ const struct metal_clock *const clock =
+ __metal_driver_sifive_wdog0_clock(wdog);
+
const long int clock_rate = metal_clock_get_rate_hz(clock);
if (clock_rate == 0)
return -1;
- const unsigned int scale = (WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) & METAL_WDOGCFG_SCALE_MASK);
+ const unsigned int scale = (WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &
+ METAL_WDOGCFG_SCALE_MASK);
return clock_rate / (1 << scale);
}
-long int __metal_driver_sifive_wdog0_set_rate(const struct metal_watchdog *const wdog, const long int rate)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
- const struct metal_clock *const clock = __metal_driver_sifive_wdog0_clock(wdog);
-
+long int
+__metal_driver_sifive_wdog0_set_rate(const struct metal_watchdog *const wdog,
+ const long int rate) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+ const struct metal_clock *const clock =
+ __metal_driver_sifive_wdog0_clock(wdog);
+
const long int clock_rate = metal_clock_get_rate_hz(clock);
if (rate >= clock_rate) {
/* We can't scale the rate above the driving clock. Clear the scale
* field and return the driving clock rate */
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &= ~(METAL_WDOGCFG_SCALE_MASK);
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &=
+ ~(METAL_WDOGCFG_SCALE_MASK);
return clock_rate;
}
@@ -88,30 +99,36 @@ long int __metal_driver_sifive_wdog0_set_rate(const struct metal_watchdog *const
}
}
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &= ~(METAL_WDOGCFG_SCALE_MASK);
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |= (METAL_WDOGCFG_SCALE_MASK & min_scale);
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &=
+ ~(METAL_WDOGCFG_SCALE_MASK);
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |=
+ (METAL_WDOGCFG_SCALE_MASK & min_scale);
return clock_rate / (1 << min_scale);
}
-long int __metal_driver_sifive_wdog0_get_timeout(const struct metal_watchdog *const wdog)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+long int __metal_driver_sifive_wdog0_get_timeout(
+ const struct metal_watchdog *const wdog) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
return (WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGCMP) & METAL_WDOGCMP_MASK);
}
-long int __metal_driver_sifive_wdog0_set_timeout(const struct metal_watchdog *const wdog, const long int timeout)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+long int
+__metal_driver_sifive_wdog0_set_timeout(const struct metal_watchdog *const wdog,
+ const long int timeout) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
/* Cap the timeout at the max value */
- const long int set_timeout = timeout > METAL_WDOGCMP_MASK ? METAL_WDOGCMP_MASK : timeout;
+ const long int set_timeout =
+ timeout > METAL_WDOGCMP_MASK ? METAL_WDOGCMP_MASK : timeout;
- /* If we edit the timeout value in-place by masking the compare value to 0 and
- * then writing it, we cause a spurious interrupt because the compare value
- * is temporarily 0. Instead, read the value into a local variable, modify it
- * there, and then write the whole register back */
+ /* If we edit the timeout value in-place by masking the compare value to 0
+ * and then writing it, we cause a spurious interrupt because the compare
+ * value is temporarily 0. Instead, read the value into a local variable,
+ * modify it there, and then write the whole register back */
uint32_t wdogcmp = WDOG_REGW(base, METAL_SIFIVE_WDOG0_WDOGCMP);
wdogcmp &= ~(METAL_WDOGCMP_MASK);
@@ -122,13 +139,15 @@ long int __metal_driver_sifive_wdog0_set_timeout(const struct metal_watchdog *co
return set_timeout;
}
-int __metal_driver_sifive_wdog0_set_result(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_result result)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+int __metal_driver_sifive_wdog0_set_result(
+ const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_result result) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
/* Turn off reset enable and counter reset */
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &= ~(METAL_WDOGCFG_RSTEN | METAL_WDOGCFG_ZEROCMP);
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &=
+ ~(METAL_WDOGCFG_RSTEN | METAL_WDOGCFG_ZEROCMP);
switch (result) {
default:
@@ -136,22 +155,26 @@ int __metal_driver_sifive_wdog0_set_result(const struct metal_watchdog *const wd
break;
case METAL_WATCHDOG_INTERRUPT:
/* Reset counter to zero after match */
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |= METAL_WDOGCFG_ZEROCMP;
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |=
+ METAL_WDOGCFG_ZEROCMP;
break;
case METAL_WATCHDOG_FULL_RESET:
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |= METAL_WDOGCFG_RSTEN;
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |=
+ METAL_WDOGCFG_RSTEN;
break;
}
return 0;
}
-int __metal_driver_sifive_wdog0_run(const struct metal_watchdog *const wdog,
- const enum metal_watchdog_run_option option)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+int __metal_driver_sifive_wdog0_run(
+ const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_run_option option) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &= ~(METAL_WDOGCFG_ENALWAYS | METAL_WDOGCFG_COREAWAKE);
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &=
+ ~(METAL_WDOGCFG_ENALWAYS | METAL_WDOGCFG_COREAWAKE);
switch (option) {
default:
@@ -161,32 +184,35 @@ int __metal_driver_sifive_wdog0_run(const struct metal_watchdog *const wdog,
/* Feed the watchdog before starting to reset counter */
__metal_driver_sifive_wdog0_feed(wdog);
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |= METAL_WDOGCFG_ENALWAYS;
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |=
+ METAL_WDOGCFG_ENALWAYS;
break;
case METAL_WATCHDOG_RUN_AWAKE:
/* Feed the watchdog before starting to reset counter */
__metal_driver_sifive_wdog0_feed(wdog);
- WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |= METAL_WDOGCFG_COREAWAKE;
+ WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) |=
+ METAL_WDOGCFG_COREAWAKE;
break;
}
return 0;
}
-struct metal_interrupt *__metal_driver_sifive_wdog0_get_interrupt(const struct metal_watchdog *const wdog)
-{
+struct metal_interrupt *__metal_driver_sifive_wdog0_get_interrupt(
+ const struct metal_watchdog *const wdog) {
return __metal_driver_sifive_wdog0_interrupt_parent(wdog);
}
-int __metal_driver_sifive_wdog0_get_interrupt_id(const struct metal_watchdog *const wdog)
-{
+int __metal_driver_sifive_wdog0_get_interrupt_id(
+ const struct metal_watchdog *const wdog) {
return __metal_driver_sifive_wdog0_interrupt_line(wdog);
}
-int __metal_driver_sifive_wdog0_clear_interrupt(const struct metal_watchdog *const wdog)
-{
- const uintptr_t base = (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
+int __metal_driver_sifive_wdog0_clear_interrupt(
+ const struct metal_watchdog *const wdog) {
+ const uintptr_t base =
+ (uintptr_t)__metal_driver_sifive_wdog0_control_base(wdog);
/* Clear the interrupt pending bit */
WDOG_UNLOCK_REGW(base, METAL_SIFIVE_WDOG0_WDOGCFG) &= ~(METAL_WDOGCFG_IP);
@@ -210,4 +236,3 @@ __METAL_DEFINE_VTABLE(__metal_driver_vtable_sifive_wdog0) = {
#endif /* METAL_SIFIVE_WDOG0 */
typedef int no_empty_translation_units;
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/ucb_htif0.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/ucb_htif0.c
new file mode 100644
index 000000000..417acbf09
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/drivers/ucb_htif0.c
@@ -0,0 +1,128 @@
+/* Copyright 2018 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine/platform.h>
+
+#ifdef METAL_UCB_HTIF0
+
+#include <metal/drivers/ucb_htif0.h>
+#include <metal/io.h>
+#include <stddef.h>
+#include <stdint.h>
+
+#define FINISHER_OFFSET 0
+
+volatile uint64_t fromhost __attribute__((aligned(4096)));
+volatile uint64_t tohost __attribute__((aligned(4096)));
+
+#if __riscv_xlen == 64
+#define TOHOST_CMD(dev, cmd, payload) \
+ (((uint64_t)(dev) << 56) | ((uint64_t)(cmd) << 48) | (uint64_t)(payload))
+#else
+#define TOHOST_CMD(dev, cmd, payload) \
+ ({ \
+ if ((dev) || (cmd)) \
+ __builtin_trap(); \
+ (payload); \
+ })
+#endif
+#define FROMHOST_DEV(fromhost_value) ((uint64_t)(fromhost_value) >> 56)
+#define FROMHOST_CMD(fromhost_value) ((uint64_t)(fromhost_value) << 8 >> 56)
+#define FROMHOST_DATA(fromhost_value) ((uint64_t)(fromhost_value) << 16 >> 16)
+
+static void __check_fromhost() {
+ uint64_t fh = fromhost;
+ if (!fh)
+ return;
+ fromhost = 0;
+}
+
+static void __set_tohost(uintptr_t dev, uintptr_t cmd, uintptr_t data) {
+ while (tohost)
+ __check_fromhost();
+ tohost = TOHOST_CMD(dev, cmd, data);
+}
+
+static void do_tohost_fromhost(uintptr_t dev, uintptr_t cmd, uintptr_t data) {
+ __set_tohost(dev, cmd, data);
+
+ while (1) {
+ uint64_t fh = fromhost;
+ if (fh) {
+ if (FROMHOST_DEV(fh) == dev && FROMHOST_CMD(fh) == cmd) {
+ fromhost = 0;
+ break;
+ }
+ __check_fromhost();
+ }
+ }
+}
+
+void __metal_driver_ucb_htif0_init(struct metal_uart *uart, int baud_rate) {}
+
+void __metal_driver_ucb_htif0_exit(const struct __metal_shutdown *sd,
+ int code) {
+ volatile uint64_t magic_mem[8];
+ magic_mem[0] = 93; // SYS_exit
+ magic_mem[1] = code;
+ magic_mem[2] = 0;
+ magic_mem[3] = 0;
+
+ do_tohost_fromhost(0, 0, (uintptr_t)magic_mem);
+
+ while (1) {
+ // loop forever
+ }
+}
+
+int __metal_driver_ucb_htif0_putc(struct metal_uart *htif, int c) {
+ volatile uint64_t magic_mem[8];
+ magic_mem[0] = 64; // SYS_write
+ magic_mem[1] = 1;
+ magic_mem[2] = (uintptr_t)&c;
+ magic_mem[3] = 1;
+
+ do_tohost_fromhost(0, 0, (uintptr_t)magic_mem);
+
+ return 0;
+}
+
+int __metal_driver_ucb_htif0_getc(struct metal_uart *htif, int *c) {
+ return -1;
+}
+
+int __metal_driver_ucb_htif0_get_baud_rate(struct metal_uart *guart) {
+ return 0;
+}
+
+int __metal_driver_ucb_htif0_set_baud_rate(struct metal_uart *guart,
+ int baud_rate) {
+ return 0;
+}
+
+struct metal_interrupt *
+__metal_driver_ucb_htif0_interrupt_controller(struct metal_uart *uart) {
+ return NULL;
+}
+
+int __metal_driver_ucb_htif0_get_interrupt_id(struct metal_uart *uart) {
+ return -1;
+}
+
+__METAL_DEFINE_VTABLE(__metal_driver_vtable_ucb_htif0_shutdown) = {
+ .shutdown.exit = &__metal_driver_ucb_htif0_exit,
+};
+
+__METAL_DEFINE_VTABLE(__metal_driver_vtable_ucb_htif0_uart) = {
+ .uart.init = __metal_driver_ucb_htif0_init,
+ .uart.putc = __metal_driver_ucb_htif0_putc,
+ .uart.getc = __metal_driver_ucb_htif0_getc,
+ .uart.get_baud_rate = __metal_driver_ucb_htif0_get_baud_rate,
+ .uart.set_baud_rate = __metal_driver_ucb_htif0_set_baud_rate,
+ .uart.controller_interrupt = __metal_driver_ucb_htif0_interrupt_controller,
+ .uart.get_interrupt_id = __metal_driver_ucb_htif0_get_interrupt_id,
+};
+
+#endif /* METAL_UCB_HTIF0 */
+
+typedef int no_empty_translation_units;
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/entry.S b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/entry.S
index 97da3fd33..b4a254f1c 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/entry.S
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/entry.S
@@ -24,31 +24,55 @@ _enter:
la gp, __global_pointer$
.option pop
- /* Set up a simple trap vector to catch anything that goes wrong early in
- * the boot process. */
- la t0, early_trap_vector
+ /* trap over the chicken bit register clearing, aloe & fe310 dont have it */
+ la t0, 1f
csrw mtvec, t0
- /* enable chicken bit if core is bullet series*/
+ /* chicken bit is enable if core are sifive series. */
la t0, __metal_chicken_bit
beqz t0, 1f
+ /* If set, always clear the feature disable register for all cores series */
csrwi 0x7C1, 0
+.align 4
1:
+ /* Set up a simple trap vector to catch anything that goes wrong early in
+ * the boot process. */
+ la t0, early_trap_vector
+ csrw mtvec, t0
/* There may be pre-initialization routines inside the MBI code that run in
- * C, so here we set up a C environment. First we set up a stack pointer,
+ * C, so here we set up a C environment. First we set up a stack pointer,
* which is left as a weak reference in order to allow initialization
* routines that do not need a stack to be set up to transparently be
* called. */
.weak __metal_stack_pointer
la sp, __metal_stack_pointer
+ /* The METAL is designed for a bare-metal environment and therefore is expected
+ * to define its own stack pointer. We also align the stack pointer here
+ * because the only RISC-V ABI that's currently defined, mandates 16-byte
+ * stack alignment. */
+
+ bne sp, zero, 1f
+ la sp, _sp
+1:
+ /* Increment by hartid number of stack sizes */
+ csrr a0, mhartid
+ li t0, 0
+ la t1, __stack_size
+1:
+ andi sp, sp, -16
+ beq t0, a0, 1f
+ add sp, sp, t1
+ addi t0, t0, 1
+ j 1b
+1:
+
/* Check for an initialization routine and call it if one exists, otherwise
* just skip over the call entirely. Note that __metal_initialize isn't
* actually a full C function, as it doesn't end up with the .bss or .data
* segments having been initialized. This is done to avoid putting a
* burden on systems that can be initialized without having a C environment
* set up. */
- .weak __metal_before_start
la ra, __metal_before_start
beqz ra, 1f
jalr ra
@@ -80,18 +104,6 @@ _enter:
.cfi_endproc
-/* For sanity's sake we set up an early trap vector that just does nothing. If
- * you end up here then there's a bug in the early boot code somewhere. */
-.section .text.metal.init.trapvec
-.align 2
-early_trap_vector:
- .cfi_startproc
- csrr t0, mcause
- csrr t1, mepc
- csrr t2, mtval
- j early_trap_vector
- .cfi_endproc
-
/* The GCC port might not emit a __register_frame_info symbol, which eventually
* results in a weak undefined reference that eventually causes crash when it
* is dereference early in boot. We really shouldn't need to put this here,
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/gpio.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/gpio.c
index 504526eb3..838590635 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/gpio.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/gpio.c
@@ -1,30 +1,40 @@
/* Copyright 2019 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <metal/machine.h>
#include <metal/gpio.h>
+#include <metal/machine.h>
-extern __inline__ int metal_gpio_disable_input(struct metal_gpio *gpio, int pin);
+extern __inline__ int metal_gpio_disable_input(struct metal_gpio *gpio,
+ int pin);
extern __inline__ int metal_gpio_enable_input(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_enable_output(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_disable_output(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_get_output_pin(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_get_input_pin(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_set_pin(struct metal_gpio *, int pin, int value);
+extern __inline__ int metal_gpio_enable_output(struct metal_gpio *gpio,
+ int pin);
+extern __inline__ int metal_gpio_disable_output(struct metal_gpio *gpio,
+ int pin);
+extern __inline__ int metal_gpio_get_output_pin(struct metal_gpio *gpio,
+ int pin);
+extern __inline__ int metal_gpio_get_input_pin(struct metal_gpio *gpio,
+ int pin);
+extern __inline__ int metal_gpio_set_pin(struct metal_gpio *, int pin,
+ int value);
extern __inline__ int metal_gpio_clear_pin(struct metal_gpio *, int pin);
extern __inline__ int metal_gpio_toggle_pin(struct metal_gpio *, int pin);
-extern __inline__ int metal_gpio_enable_pinmux(struct metal_gpio *, int pin, int io_function);
+extern __inline__ int metal_gpio_enable_pinmux(struct metal_gpio *, int pin,
+ int io_function);
extern __inline__ int metal_gpio_disable_pinmux(struct metal_gpio *, int pin);
-extern __inline__ struct metal_interrupt* metal_gpio_interrupt_controller(struct metal_gpio *gpio);
-extern __inline__ int metal_gpio_get_interrupt_id(struct metal_gpio *gpio, int pin);
-extern __inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio, int pin, int intr_type);
-extern __inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio, int pin, int intr_type);
+extern __inline__ struct metal_interrupt *
+metal_gpio_interrupt_controller(struct metal_gpio *gpio);
+extern __inline__ int metal_gpio_get_interrupt_id(struct metal_gpio *gpio,
+ int pin);
+extern __inline__ int metal_gpio_config_interrupt(struct metal_gpio *gpio,
+ int pin, int intr_type);
+extern __inline__ int metal_gpio_clear_interrupt(struct metal_gpio *gpio,
+ int pin, int intr_type);
-struct metal_gpio *metal_gpio_get_device(unsigned int device_num)
-{
- if(device_num > __MEE_DT_MAX_GPIOS) {
- return NULL;
+struct metal_gpio *metal_gpio_get_device(unsigned int device_num) {
+ if (device_num > __MEE_DT_MAX_GPIOS) {
+ return NULL;
}
- return (struct metal_gpio *) __metal_gpio_table[device_num];
+ return (struct metal_gpio *)__metal_gpio_table[device_num];
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/hpm.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/hpm.c
new file mode 100644
index 000000000..2e0bc051b
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/hpm.c
@@ -0,0 +1,345 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/drivers/riscv_cpu.h>
+#include <metal/hpm.h>
+#include <stdint.h>
+
+/* Macro to generate code within a switch case */
+#define METAL_HPM_HANDLE_SWITCH(m) \
+ m(3) m(4) m(5) m(6) m(7) m(8) m(9) m(10) m(11) m(12) m(13) m(14) m(15) \
+ m(16) m(17) m(18) m(19) m(20) m(21) m(22) m(23) m(24) m(25) m(26) \
+ m(27) m(28) m(29) m(30) m(31)
+
+/* Macro to set values into event selector register */
+#define METAL_HPM_SET_EVENT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrr %0, mhpmevent" #x : "=r"(val)); \
+ val &= ~bitmask; \
+ val |= bitmask; \
+ __asm__ __volatile__("csrw mhpmevent" #x ", %0" : : "r"(val)); \
+ break;
+
+/* Macro to set values into event selector register */
+#define METAL_HPM_CLR_EVENT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrr %0, mhpmevent" #x : "=r"(val)); \
+ val &= ~bitmask; \
+ __asm__ __volatile__("csrw mhpmevent" #x ", %0" : : "r"(val)); \
+ break;
+
+/* Macro to get values from event selector register */
+#define METAL_HPM_GET_EVENT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrr %0, mhpmevent" #x : "=r"(val)); \
+ break;
+
+/* Macro to read HW performance monitor counter values */
+#if __riscv_xlen == 32
+#define METAL_HPM_GET_COUNT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ do { \
+ __asm__ __volatile__("csrr %0, mhpmcounter" #x "h" : "=r"(vh)); \
+ __asm__ __volatile__("csrr %0, mhpmcounter" #x : "=r"(vl)); \
+ __asm__ __volatile__("csrr %0, mhpmcounter" #x "h" : "=r"(vh1)); \
+ } while (vh != vh1); \
+ break;
+#else
+#define METAL_HPM_GET_COUNT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrr %0, mhpmcounter" #x : "=r"(vl)); \
+ break;
+#endif
+
+/* Macro to clear HW performance monitor counter values */
+#if __riscv_xlen == 32
+#define METAL_HPM_CLR_COUNT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrw mhpmcounter" #x "h, zero"); \
+ __asm__ __volatile__("csrw mhpmcounter" #x ", zero"); \
+ __asm__ __volatile__("csrw mhpmcounter" #x "h, zero"); \
+ break;
+#else
+#define METAL_HPM_CLR_COUNT_REG(x) \
+ case METAL_HPM_COUNTER_##x: \
+ __asm__ __volatile__("csrw mhpmcounter" #x ", zero"); \
+ break;
+#endif
+
+/* Max available counters */
+#define METAL_HPM_COUNT_MAX 32
+
+/* Macro to check for instruction trap */
+#define MCAUSE_ILLEGAL_INST 0x02
+
+/* Return codes */
+#define METAL_HPM_RET_OK 0
+#define METAL_HPM_RET_NOK 1
+
+int metal_hpm_init(struct metal_cpu *gcpu) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+
+ /* Check if counters are initialized or pointer is NULL */
+ if ((gcpu) && (cpu->hpm_count == 0)) {
+ metal_hpm_counter n;
+
+ /* Count number of available hardware performance counters */
+ cpu->hpm_count = METAL_HPM_COUNT_MAX;
+
+ /* mcycle, mtime and minstret counters are always available */
+ for (n = METAL_HPM_COUNTER_3; n < METAL_HPM_COUNTER_31; n++) {
+ metal_hpm_set_event(gcpu, n, 0xFFFFFFFF);
+
+ if (metal_hpm_get_event(gcpu, n) == 0) {
+ break;
+ }
+ }
+ cpu->hpm_count = n;
+
+ /* TODO: mcountinhibit csr is not yet accessible.
+ * As per latest RiscV privileged spec v1.11,
+ * mcountinhibit controls which of the counters increment.
+ * Unused counters can be disabled to reduce power consumption. */
+ /* Keep all counters disabled, enable them later on as needed. */
+ /* __asm__ __volatile__("csrw mcountinhibit, zero"); */
+
+ /* Clear all counters */
+ for (unsigned int i = 0; i < cpu->hpm_count; i++) {
+ metal_hpm_clr_event(gcpu, i, 0xFFFFFFFF);
+ metal_hpm_clear_counter(gcpu, i);
+ }
+ } else {
+ return METAL_HPM_RET_NOK;
+ }
+
+ return METAL_HPM_RET_OK;
+}
+
+int metal_hpm_disable(struct metal_cpu *gcpu) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ uintptr_t temp = 0, val = 0;
+
+ /* Check if pointer is NULL */
+ if (gcpu) {
+ /* Disable counter access */
+ __asm__ __volatile__("la %0, 1f \n\t"
+ "csrr %1, mtvec \n\t"
+ "csrw mtvec, %0 \n\t"
+ "csrw mcounteren, zero \n\t"
+ ".align 4 \n\t"
+ "1: \n\t"
+ "csrw mtvec, %1 \n\t"
+ : "+r"(val), "+r"(temp));
+
+ /* TODO: Disable all counters */
+ /* __asm__ __volatile__("csrw mcountinhibit, zero"); */
+
+ cpu->hpm_count = 0;
+ } else {
+ return METAL_HPM_RET_NOK;
+ }
+
+ return METAL_HPM_RET_OK;
+}
+
+int metal_hpm_set_event(struct metal_cpu *gcpu, metal_hpm_counter counter,
+ unsigned int bitmask) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ unsigned int val;
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ switch (counter) {
+ /* Set event register bit mask as requested */
+ METAL_HPM_HANDLE_SWITCH(METAL_HPM_SET_EVENT_REG)
+
+ default:
+ break;
+ }
+
+ return METAL_HPM_RET_OK;
+}
+
+unsigned int metal_hpm_get_event(struct metal_cpu *gcpu,
+ metal_hpm_counter counter) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ unsigned int val = 0;
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ switch (counter) {
+ /* Read event registers */
+ METAL_HPM_HANDLE_SWITCH(METAL_HPM_GET_EVENT_REG)
+
+ default:
+ break;
+ }
+
+ return val;
+}
+
+int metal_hpm_clr_event(struct metal_cpu *gcpu, metal_hpm_counter counter,
+ unsigned int bitmask) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ unsigned int val;
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ switch (counter) {
+ /* Clear event registers as requested */
+ METAL_HPM_HANDLE_SWITCH(METAL_HPM_CLR_EVENT_REG)
+
+ default:
+ break;
+ }
+
+ return METAL_HPM_RET_OK;
+}
+
+int metal_hpm_enable_access(struct metal_cpu *gcpu, metal_hpm_counter counter) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ uintptr_t temp = 0, val = 0;
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ /* Set trap exit, to handle illegal instruction trap. */
+ __asm__ __volatile__("la %0, 1f \n\t"
+ "csrr %1, mtvec \n\t"
+ "csrw mtvec, %0 \n\t"
+ "csrr %0, mcounteren \n\t"
+ "or %0, %0, %2 \n\t"
+ "csrw mcounteren, %0 \n\t"
+ ".align 4 \n\t"
+ "1: \n\t"
+ "csrw mtvec, %1 \n\t"
+ : "+r"(val), "+r"(temp)
+ : "r"(1 << counter));
+
+ return METAL_HPM_RET_OK;
+}
+
+int metal_hpm_disable_access(struct metal_cpu *gcpu,
+ metal_hpm_counter counter) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ uintptr_t temp = 0, val = 0;
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ /* Set trap exit, to handle illegal instruction trap. */
+ __asm__ __volatile__("la %0, 1f \n\t"
+ "csrr %1, mtvec \n\t"
+ "csrw mtvec, %0 \n\t"
+ "csrr %0, mcounteren \n\t"
+ "and %0, %0, %2 \n\t"
+ "csrw mcounteren, %0 \n\t"
+ ".align 4 \n\t"
+ "1: \n\t"
+ "csrw mtvec, %1 \n\t"
+ : "+r"(val), "+r"(temp)
+ : "r"(~(1 << counter)));
+
+ return METAL_HPM_RET_OK;
+}
+
+unsigned long long metal_hpm_read_counter(struct metal_cpu *gcpu,
+ metal_hpm_counter counter) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+#if __riscv_xlen == 32
+ unsigned int vh = 0, vh1 = 0, vl = 0;
+#else
+ unsigned long long vl = 0;
+#endif
+
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ switch (counter) {
+ case METAL_HPM_CYCLE:
+#if __riscv_xlen == 32
+ do {
+ __asm__ __volatile__("csrr %0, mcycleh" : "=r"(vh));
+ __asm__ __volatile__("csrr %0, mcycle" : "=r"(vl));
+ __asm__ __volatile__("csrr %0, mcycleh" : "=r"(vh1));
+ } while (vh != vh1);
+#else
+ __asm__ __volatile__("csrr %0, mcycle" : "=r"(vl));
+#endif
+ break;
+ case METAL_HPM_TIME:
+ /* mtime is memory mapped within CLINT block,
+ * Use CLINT APIs to access this register. */
+ return METAL_HPM_RET_NOK;
+ break;
+
+ case METAL_HPM_INSTRET:
+#if __riscv_xlen == 32
+ do {
+ __asm__ __volatile__("csrr %0, minstreth" : "=r"(vh));
+ __asm__ __volatile__("csrr %0, minstret" : "=r"(vl));
+ __asm__ __volatile__("csrr %0, minstreth" : "=r"(vh1));
+ } while (vh != vh1);
+#else
+ __asm__ __volatile__("csrr %0, minstret" : "=r"(vl));
+#endif
+ break;
+ METAL_HPM_HANDLE_SWITCH(METAL_HPM_GET_COUNT_REG)
+
+ default:
+ break;
+ }
+
+#if __riscv_xlen == 32
+ return ((((unsigned long long)vh) << 32) | vl);
+#else
+ return vl;
+#endif
+}
+
+int metal_hpm_clear_counter(struct metal_cpu *gcpu, metal_hpm_counter counter) {
+ struct __metal_driver_cpu *cpu = (void *)gcpu;
+ /* Return error if counter is out of range or pointer is NULL */
+ if ((gcpu) && (counter >= cpu->hpm_count))
+ return METAL_HPM_RET_NOK;
+
+ switch (counter) {
+ case METAL_HPM_CYCLE:
+#if __riscv_xlen == 32
+ __asm__ __volatile__("csrw mcycleh, zero");
+ __asm__ __volatile__("csrw mcycle, zero");
+ __asm__ __volatile__("csrw mcycleh, zero");
+#else
+ __asm__ __volatile__("csrw mcycle, zero");
+#endif
+ break;
+ case METAL_HPM_TIME:
+ /* mtime is memory mapped within CLINT block */
+ return METAL_HPM_RET_NOK;
+ break;
+ case METAL_HPM_INSTRET:
+#if __riscv_xlen == 32
+ __asm__ __volatile__("csrw minstreth, zero");
+ __asm__ __volatile__("csrw minstret, zero");
+ __asm__ __volatile__("csrw minstreth, zero");
+#else
+ __asm__ __volatile__("csrw minstret, zero");
+#endif
+ break;
+ METAL_HPM_HANDLE_SWITCH(METAL_HPM_CLR_COUNT_REG)
+
+ default:
+ break;
+ }
+
+ return METAL_HPM_RET_OK;
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/i2c.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/i2c.c
new file mode 100644
index 000000000..6c342aa31
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/i2c.c
@@ -0,0 +1,28 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/i2c.h>
+#include <metal/machine.h>
+
+extern inline void metal_i2c_init(struct metal_i2c *i2c, unsigned int baud_rate,
+ metal_i2c_mode_t mode);
+extern inline int metal_i2c_write(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit);
+extern inline int metal_i2c_read(struct metal_i2c *i2c, unsigned int addr,
+ unsigned int len, unsigned char buf[],
+ metal_i2c_stop_bit_t stop_bit);
+extern inline int metal_i2c_transfer(struct metal_i2c *i2c, unsigned int addr,
+ unsigned char txbuf[], unsigned int txlen,
+ unsigned char rxbuf[], unsigned int rxlen);
+extern inline int metal_i2c_get_baud_rate(struct metal_i2c *i2c);
+extern inline int metal_i2c_set_baud_rate(struct metal_i2c *i2c, int baud_rate);
+
+struct metal_i2c *metal_i2c_get_device(unsigned int device_num) {
+#if __METAL_DT_MAX_I2CS > 0
+ if (device_num < __METAL_DT_MAX_I2CS) {
+ return (struct metal_i2c *)__metal_i2c_table[device_num];
+ }
+#endif
+ return NULL;
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/init.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/init.c
new file mode 100644
index 000000000..9d98737db
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/init.c
@@ -0,0 +1,72 @@
+/* Copyright 2019 SiFive Inc. */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/init.h>
+
+/*
+ * These function pointers are created by the linker script
+ * in the .init_array section. The arrays defined by these
+ * and end points are the set of functions defined by instances
+ * of METAL_CONSTRUCTOR() and METAL_DESTRUCTOR().
+ */
+extern metal_constructor_t metal_constructors_start;
+extern metal_constructor_t metal_constructors_end;
+extern metal_destructor_t metal_destructors_start;
+extern metal_destructor_t metal_destructors_end;
+
+void metal_init(void) {
+ /* Make sure the constructors only run once */
+ static int init_done = 0;
+ if (init_done) {
+ return;
+ }
+ init_done = 1;
+
+ if (&metal_constructors_end <= &metal_constructors_start) {
+ return;
+ }
+
+ metal_constructor_t *funcptr = &metal_constructors_start;
+ while (funcptr != &metal_constructors_end) {
+ metal_constructor_t func = *funcptr;
+
+ func();
+
+ funcptr += 1;
+ }
+}
+
+void metal_fini(void) {
+ /* Make sure the destructors only run once */
+ static int fini_done = 0;
+ if (fini_done) {
+ return;
+ }
+ fini_done = 1;
+
+ if (&metal_destructors_end <= &metal_destructors_start) {
+ return;
+ }
+
+ metal_destructor_t *funcptr = &metal_destructors_start;
+ while (funcptr != &metal_destructors_end) {
+ metal_destructor_t func = *funcptr;
+
+ func();
+
+ funcptr += 1;
+ }
+}
+
+/*
+ * metal_init_run() and metal_fini_run() are marked weak so that users
+ * can redefine them for their own purposes, including to no-ops
+ * in the case that users don't want the metal constructors or
+ * destructors to run.
+ */
+
+void metal_init_run(void) __attribute__((weak));
+void metal_init_run(void) { metal_init(); }
+
+void metal_fini_run(void) __attribute__((weak));
+void metal_fini_run(void) { metal_fini(); }
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/interrupt.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/interrupt.c
index eeb88b26f..c4a7050c5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/interrupt.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/interrupt.c
@@ -1,13 +1,12 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <string.h>
#include <metal/interrupt.h>
#include <metal/machine.h>
+#include <string.h>
-struct metal_interrupt* metal_interrupt_get_controller (metal_intr_cntrl_type cntrl,
- int id)
-{
+struct metal_interrupt *
+metal_interrupt_get_controller(metal_intr_cntrl_type cntrl, int id) {
switch (cntrl) {
case METAL_CPU_CONTROLLER:
break;
@@ -32,51 +31,81 @@ struct metal_interrupt* metal_interrupt_get_controller (metal_intr_cntrl_type cn
extern __inline__ void metal_interrupt_init(struct metal_interrupt *controller);
-extern __inline__ int metal_interrupt_set_vector_mode(struct metal_interrupt *controller,
- metal_vector_mode mode);
-extern __inline__ metal_vector_mode metal_interrupt_get_vector_mode(struct metal_interrupt *controller);
+extern __inline__ int
+metal_interrupt_set_vector_mode(struct metal_interrupt *controller,
+ metal_vector_mode mode);
+extern __inline__ metal_vector_mode
+metal_interrupt_get_vector_mode(struct metal_interrupt *controller);
+
+extern __inline__ int
+metal_interrupt_set_privilege(struct metal_interrupt *controller,
+ metal_intr_priv_mode mode);
+extern __inline__ metal_intr_priv_mode
+metal_interrupt_get_privilege(struct metal_interrupt *controller);
-extern __inline__ int metal_interrupt_set_privilege(struct metal_interrupt *controller,
- metal_intr_priv_mode mode);
-extern __inline__ metal_intr_priv_mode metal_interrupt_get_privilege(struct metal_interrupt *controller);
+extern __inline__ int
+metal_interrupt_set_threshold(struct metal_interrupt *controller,
+ unsigned int level);
+extern __inline__ unsigned int
+metal_interrupt_get_threshold(struct metal_interrupt *controller);
-extern __inline__ int metal_interrupt_set_threshold(struct metal_interrupt *controller,
- unsigned int level);
-extern __inline__ unsigned int metal_interrupt_get_threshold(struct metal_interrupt *controller);
+extern __inline__ unsigned int
+metal_interrupt_get_priority(struct metal_interrupt *controller, int id);
-extern __inline__ unsigned int metal_interrupt_get_priority(struct metal_interrupt *controller, int id);
+extern __inline__ int
+metal_interrupt_set_priority(struct metal_interrupt *controller, int id,
+ unsigned int priority);
-extern __inline__ int metal_interrupt_set_priority(struct metal_interrupt *controller, int id, unsigned int priority);
+extern __inline__ int
+metal_interrupt_set_preemptive_level(struct metal_interrupt *controller, int id,
+ unsigned int level);
-extern __inline__ int metal_interrupt_clear(struct metal_interrupt *controller, int id);
+extern __inline__ unsigned int
+metal_interrupt_get_preemptive_level(struct metal_interrupt *controller,
+ int id);
-extern __inline__ int metal_interrupt_set(struct metal_interrupt *controller, int id);
+extern __inline__ int metal_interrupt_clear(struct metal_interrupt *controller,
+ int id);
-extern __inline__ int metal_interrupt_register_handler(struct metal_interrupt *controller,
- int id,
- metal_interrupt_handler_t handler,
- void *priv);
+extern __inline__ int metal_interrupt_set(struct metal_interrupt *controller,
+ int id);
-extern __inline__ int metal_interrupt_register_vector_handler(struct metal_interrupt *controller,
- int id,
- metal_interrupt_vector_handler_t handler,
- void *priv_data);
+extern __inline__ int
+metal_interrupt_register_handler(struct metal_interrupt *controller, int id,
+ metal_interrupt_handler_t handler, void *priv);
-extern __inline__ int metal_interrupt_enable(struct metal_interrupt *controller, int id);
+extern __inline__ int metal_interrupt_register_vector_handler(
+ struct metal_interrupt *controller, int id,
+ metal_interrupt_vector_handler_t handler, void *priv_data);
-extern __inline__ int metal_interrupt_disable(struct metal_interrupt *controller, int id);
+extern __inline__ int metal_interrupt_enable(struct metal_interrupt *controller,
+ int id);
-extern __inline__ unsigned int metal_interrupt_get_threshold(struct metal_interrupt *controller);
+extern __inline__ int
+metal_interrupt_disable(struct metal_interrupt *controller, int id);
-extern __inline__ int metal_interrupt_set_threshold(struct metal_interrupt *controller, unsigned int threshold);
+extern __inline__ int
+metal_interrupt_vector_enable(struct metal_interrupt *controller, int id);
-extern __inline__ unsigned int metal_interrupt_get_priority(struct metal_interrupt *controller, int id);
+extern __inline__ int
+metal_interrupt_vector_disable(struct metal_interrupt *controller, int id);
-extern __inline__ int metal_interrupt_set_priority(struct metal_interrupt *controller, int id, unsigned int priority);
+extern __inline__ int
+_metal_interrupt_command_request(struct metal_interrupt *controller, int cmd,
+ void *data);
-extern __inline__ int metal_interrupt_vector_enable(struct metal_interrupt *controller, int id);
+extern __inline__ metal_affinity
+metal_interrupt_affinity_enable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id);
-extern __inline__ int metal_interrupt_vector_disable(struct metal_interrupt *controller, int id);
+extern __inline__ metal_affinity
+metal_interrupt_affinity_disable(struct metal_interrupt *controller,
+ metal_affinity bitmask, int id);
-extern __inline__ int _metal_interrupt_command_request(struct metal_interrupt *controller,
- int cmd, void *data);
+extern __inline__ metal_affinity
+metal_interrupt_affinity_set_threshold(struct metal_interrupt *controller,
+ metal_affinity bitmask,
+ unsigned int level);
+extern __inline__ unsigned int
+metal_interrupt_affinity_get_threshold(struct metal_interrupt *controller,
+ int contextid);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/led.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/led.c
index 91b74dbde..f48de663a 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/led.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/led.c
@@ -1,34 +1,31 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <string.h>
#include <metal/led.h>
#include <metal/machine.h>
+#include <string.h>
-struct metal_led* metal_led_get_rgb (char *label, char *color)
-{
+struct metal_led *metal_led_get_rgb(char *label, char *color) {
int i;
struct metal_led *led;
char led_label[100];
- if ((__METAL_DT_MAX_LEDS == 0) ||
- (label == NULL) || (color == NULL)) {
+ if ((__METAL_DT_MAX_LEDS == 0) || (label == NULL) || (color == NULL)) {
return NULL;
}
strcpy(led_label, label);
strcat(led_label, color);
for (i = 0; i < __METAL_DT_MAX_LEDS; i++) {
- led = (struct metal_led*)__metal_led_table[i];
+ led = (struct metal_led *)__metal_led_table[i];
if (led->vtable->led_exist(led, led_label)) {
- return led;
- }
+ return led;
+ }
}
return NULL;
}
-struct metal_led* metal_led_get (char *label)
-{
+struct metal_led *metal_led_get(char *label) {
return metal_led_get_rgb(label, "");
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/memory.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/memory.c
index 05ab7ead2..c963eb629 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/memory.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/memory.c
@@ -5,22 +5,25 @@
#include <metal/memory.h>
struct metal_memory *metal_get_memory_from_address(const uintptr_t address) {
- for(int i = 0; i < __METAL_DT_MAX_MEMORIES; i++) {
- struct metal_memory *mem = __metal_memory_table[i];
+ for (int i = 0; i < __METAL_DT_MAX_MEMORIES; i++) {
+ struct metal_memory *mem = __metal_memory_table[i];
- uintptr_t lower_bound = metal_memory_get_base_address(mem);
- uintptr_t upper_bound = lower_bound + metal_memory_get_size(mem);
+ uintptr_t lower_bound = metal_memory_get_base_address(mem);
+ uintptr_t upper_bound = lower_bound + metal_memory_get_size(mem);
- if((address >= lower_bound) && (address < upper_bound)) {
- return mem;
- }
- }
+ if ((address >= lower_bound) && (address < upper_bound)) {
+ return mem;
+ }
+ }
- return NULL;
+ return NULL;
}
-extern __inline__ uintptr_t metal_memory_get_base_address(const struct metal_memory *memory);
-extern __inline__ size_t metal_memory_get_size(const struct metal_memory *memory);
-extern __inline__ int metal_memory_supports_atomics(const struct metal_memory *memory);
-extern __inline__ int metal_memory_is_cachable(const struct metal_memory *memory);
-
+extern __inline__ uintptr_t
+metal_memory_get_base_address(const struct metal_memory *memory);
+extern __inline__ size_t
+metal_memory_get_size(const struct metal_memory *memory);
+extern __inline__ int
+metal_memory_supports_atomics(const struct metal_memory *memory);
+extern __inline__ int
+metal_memory_is_cachable(const struct metal_memory *memory);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pmp.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pmp.c
index 5c2f68ada..230a6c726 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pmp.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pmp.c
@@ -1,15 +1,14 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
+#include <metal/cpu.h>
#include <metal/machine.h>
#include <metal/pmp.h>
-#include <metal/cpu.h>
-#define CONFIG_TO_INT(_config) (*((char *) &(_config)))
-#define INT_TO_CONFIG(_int) (*((struct metal_pmp_config *)(char *) &(_int)))
+#define CONFIG_TO_INT(_config) (*((char *)&(_config)))
+#define INT_TO_CONFIG(_int) (*((struct metal_pmp_config *)(char *)&(_int)))
-struct metal_pmp *metal_pmp_get_device(void)
-{
+struct metal_pmp *metal_pmp_get_device(void) {
#ifdef __METAL_DT_PMP_HANDLE
return __METAL_DT_PMP_HANDLE;
#else
@@ -28,13 +27,13 @@ struct metal_pmp *metal_pmp_get_device(void)
* in a detected granularity of 2^(10 + 2) = 4096.
*/
static uintptr_t _get_detected_granularity(uintptr_t address) {
- if(address == 0) {
- return (uintptr_t) -1;
+ if (address == 0) {
+ return (uintptr_t)-1;
}
/* Get the index of the least significant set bit */
int index = 0;
- while(((address >> index) & 0x1) == 0) {
+ while (((address >> index) & 0x1) == 0) {
index += 1;
}
@@ -55,7 +54,7 @@ static uintptr_t _get_detected_granularity(uintptr_t address) {
static uintptr_t _get_pmpaddr_granularity(uintptr_t address) {
/* Get the index of the least significant unset bit */
int index = 0;
- while(((address >> index) & 0x1) == 1) {
+ while (((address >> index) & 0x1) == 1) {
index += 1;
}
@@ -64,8 +63,7 @@ static uintptr_t _get_pmpaddr_granularity(uintptr_t address) {
}
/* Get the number of pmp regions for the given hart */
-int metal_pmp_num_regions(int hartid)
-{
+int metal_pmp_num_regions(int hartid) {
struct metal_cpu *cpu = metal_cpu_get(hartid);
return __metal_driver_cpu_num_pmp_regions(cpu);
@@ -77,7 +75,7 @@ static unsigned int _pmp_regions() {
}
void metal_pmp_init(struct metal_pmp *pmp) {
- if(!pmp) {
+ if (!pmp) {
return;
}
@@ -89,196 +87,167 @@ void metal_pmp_init(struct metal_pmp *pmp) {
.R = 0,
};
- for(unsigned int i = 0; i < _pmp_regions(); i++) {
+ for (unsigned int i = 0; i < _pmp_regions(); i++) {
metal_pmp_set_region(pmp, i, init_config, 0);
}
/* Detect the region granularity by writing all 1s to pmpaddr0 while
* pmpcfg0 = 0. */
- if(metal_pmp_set_address(pmp, 0, -1) != 0) {
+ if (metal_pmp_set_address(pmp, 0, -1) != 0) {
/* Failed to detect granularity */
return;
}
/* Calculate the granularity based on the value that pmpaddr0 takes on */
- pmp->_granularity[metal_cpu_get_current_hartid()] = _get_detected_granularity(metal_pmp_get_address(pmp, 0));
+ pmp->_granularity[metal_cpu_get_current_hartid()] =
+ _get_detected_granularity(metal_pmp_get_address(pmp, 0));
/* Clear pmpaddr0 */
metal_pmp_set_address(pmp, 0, 0);
}
-int metal_pmp_set_region(struct metal_pmp *pmp,
- unsigned int region,
- struct metal_pmp_config config,
- size_t address)
-{
+int metal_pmp_set_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config config, size_t address) {
struct metal_pmp_config old_config;
size_t old_address;
size_t cfgmask;
size_t pmpcfg;
int rc = 0;
- if(!pmp) {
+ if (!pmp) {
/* Device handle cannot be NULL */
return 1;
}
- if(region > _pmp_regions()) {
+ if (region > _pmp_regions()) {
/* Region outside of supported range */
return 2;
}
- if(config.A == METAL_PMP_NA4 && pmp->_granularity[metal_cpu_get_current_hartid()] > 4) {
+ if (config.A == METAL_PMP_NA4 &&
+ pmp->_granularity[metal_cpu_get_current_hartid()] > 4) {
/* The requested granularity is too small */
return 3;
}
- if(config.A == METAL_PMP_NAPOT &&
- pmp->_granularity[metal_cpu_get_current_hartid()] > _get_pmpaddr_granularity(address))
- {
+ if (config.A == METAL_PMP_NAPOT &&
+ pmp->_granularity[metal_cpu_get_current_hartid()] >
+ _get_pmpaddr_granularity(address)) {
/* The requested granularity is too small */
return 3;
}
rc = metal_pmp_get_region(pmp, region, &old_config, &old_address);
- if(rc) {
+ if (rc) {
/* Error reading region */
return rc;
}
- if(old_config.L == METAL_PMP_LOCKED) {
+ if (old_config.L == METAL_PMP_LOCKED) {
/* Cannot modify locked region */
return 4;
}
/* Update the address first, because if the region is being locked we won't
* be able to modify it after we set the config */
- if(old_address != address) {
- switch(region) {
+ if (old_address != address) {
+ switch (region) {
case 0:
- __asm__("csrw pmpaddr0, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr0, %[addr]" ::[addr] "r"(address) :);
break;
case 1:
- __asm__("csrw pmpaddr1, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr1, %[addr]" ::[addr] "r"(address) :);
break;
case 2:
- __asm__("csrw pmpaddr2, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr2, %[addr]" ::[addr] "r"(address) :);
break;
case 3:
- __asm__("csrw pmpaddr3, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr3, %[addr]" ::[addr] "r"(address) :);
break;
case 4:
- __asm__("csrw pmpaddr4, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr4, %[addr]" ::[addr] "r"(address) :);
break;
case 5:
- __asm__("csrw pmpaddr5, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr5, %[addr]" ::[addr] "r"(address) :);
break;
case 6:
- __asm__("csrw pmpaddr6, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr6, %[addr]" ::[addr] "r"(address) :);
break;
case 7:
- __asm__("csrw pmpaddr7, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr7, %[addr]" ::[addr] "r"(address) :);
break;
case 8:
- __asm__("csrw pmpaddr8, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr8, %[addr]" ::[addr] "r"(address) :);
break;
case 9:
- __asm__("csrw pmpaddr9, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr9, %[addr]" ::[addr] "r"(address) :);
break;
case 10:
- __asm__("csrw pmpaddr10, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr10, %[addr]" ::[addr] "r"(address) :);
break;
case 11:
- __asm__("csrw pmpaddr11, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr11, %[addr]" ::[addr] "r"(address) :);
break;
case 12:
- __asm__("csrw pmpaddr12, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr12, %[addr]" ::[addr] "r"(address) :);
break;
case 13:
- __asm__("csrw pmpaddr13, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr13, %[addr]" ::[addr] "r"(address) :);
break;
case 14:
- __asm__("csrw pmpaddr14, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr14, %[addr]" ::[addr] "r"(address) :);
break;
case 15:
- __asm__("csrw pmpaddr15, %[addr]"
- :: [addr] "r" (address) :);
+ __asm__("csrw pmpaddr15, %[addr]" ::[addr] "r"(address) :);
break;
}
}
-#if __riscv_xlen==32
- if(CONFIG_TO_INT(old_config) != CONFIG_TO_INT(config)) {
+#if __riscv_xlen == 32
+ if (CONFIG_TO_INT(old_config) != CONFIG_TO_INT(config)) {
/* Mask to clear old pmpcfg */
- cfgmask = (0xFF << (8 * (region % 4)) );
- pmpcfg = (CONFIG_TO_INT(config) << (8 * (region % 4)) );
-
- switch(region / 4) {
+ cfgmask = (0xFF << (8 * (region % 4)));
+ pmpcfg = (CONFIG_TO_INT(config) << (8 * (region % 4)));
+
+ switch (region / 4) {
case 0:
- __asm__("csrc pmpcfg0, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg0, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg0, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg0, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
case 1:
- __asm__("csrc pmpcfg1, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg1, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg1, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg1, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
case 2:
- __asm__("csrc pmpcfg2, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg2, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg2, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg2, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
case 3:
- __asm__("csrc pmpcfg3, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg3, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg3, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg3, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
}
}
-#elif __riscv_xlen==64
- if(CONFIG_TO_INT(old_config) != CONFIG_TO_INT(config)) {
+#elif __riscv_xlen == 64
+ if (CONFIG_TO_INT(old_config) != CONFIG_TO_INT(config)) {
/* Mask to clear old pmpcfg */
- cfgmask = (0xFF << (8 * (region % 8)) );
- pmpcfg = (CONFIG_TO_INT(config) << (8 * (region % 8)) );
-
- switch(region / 8) {
+ cfgmask = (0xFF << (8 * (region % 8)));
+ pmpcfg = (CONFIG_TO_INT(config) << (8 * (region % 8)));
+
+ switch (region / 8) {
case 0:
- __asm__("csrc pmpcfg0, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg0, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg0, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg0, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
case 1:
- __asm__("csrc pmpcfg2, %[mask]"
- :: [mask] "r" (cfgmask) :);
+ __asm__("csrc pmpcfg2, %[mask]" ::[mask] "r"(cfgmask) :);
- __asm__("csrs pmpcfg2, %[cfg]"
- :: [cfg] "r" (pmpcfg) :);
+ __asm__("csrs pmpcfg2, %[cfg]" ::[cfg] "r"(pmpcfg) :);
break;
}
}
@@ -289,59 +258,50 @@ int metal_pmp_set_region(struct metal_pmp *pmp,
return 0;
}
-int metal_pmp_get_region(struct metal_pmp *pmp,
- unsigned int region,
- struct metal_pmp_config *config,
- size_t *address)
-{
+int metal_pmp_get_region(struct metal_pmp *pmp, unsigned int region,
+ struct metal_pmp_config *config, size_t *address) {
size_t pmpcfg = 0;
char *pmpcfg_convert = (char *)&pmpcfg;
- if(!pmp || !config || !address) {
+ if (!pmp || !config || !address) {
/* NULL pointers are invalid arguments */
return 1;
}
- if(region > _pmp_regions()) {
+ if (region > _pmp_regions()) {
/* Region outside of supported range */
return 2;
}
-#if __riscv_xlen==32
- switch(region / 4) {
+#if __riscv_xlen == 32
+ switch (region / 4) {
case 0:
- __asm__("csrr %[cfg], pmpcfg0"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg0" : [cfg] "=r"(pmpcfg)::);
break;
case 1:
- __asm__("csrr %[cfg], pmpcfg1"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg1" : [cfg] "=r"(pmpcfg)::);
break;
case 2:
- __asm__("csrr %[cfg], pmpcfg2"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg2" : [cfg] "=r"(pmpcfg)::);
break;
case 3:
- __asm__("csrr %[cfg], pmpcfg3"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg3" : [cfg] "=r"(pmpcfg)::);
break;
}
- pmpcfg = (0xFF & (pmpcfg >> (8 * (region % 4)) ) );
+ pmpcfg = (0xFF & (pmpcfg >> (8 * (region % 4))));
-#elif __riscv_xlen==64
- switch(region / 8) {
+#elif __riscv_xlen == 64
+ switch (region / 8) {
case 0:
- __asm__("csrr %[cfg], pmpcfg0"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg0" : [cfg] "=r"(pmpcfg)::);
break;
case 1:
- __asm__("csrr %[cfg], pmpcfg2"
- : [cfg] "=r" (pmpcfg) ::);
+ __asm__("csrr %[cfg], pmpcfg2" : [cfg] "=r"(pmpcfg)::);
break;
}
- pmpcfg = (0xFF & (pmpcfg >> (8 * (region % 8)) ) );
+ pmpcfg = (0xFF & (pmpcfg >> (8 * (region % 8))));
#else
#error XLEN is not set to supported value for PMP driver
@@ -349,88 +309,71 @@ int metal_pmp_get_region(struct metal_pmp *pmp,
*config = INT_TO_CONFIG(*pmpcfg_convert);
- switch(region) {
+ switch (region) {
case 0:
- __asm__("csrr %[addr], pmpaddr0"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr0" : [addr] "=r"(*address)::);
break;
case 1:
- __asm__("csrr %[addr], pmpaddr1"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr1" : [addr] "=r"(*address)::);
break;
case 2:
- __asm__("csrr %[addr], pmpaddr2"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr2" : [addr] "=r"(*address)::);
break;
case 3:
- __asm__("csrr %[addr], pmpaddr3"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr3" : [addr] "=r"(*address)::);
break;
case 4:
- __asm__("csrr %[addr], pmpaddr4"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr4" : [addr] "=r"(*address)::);
break;
case 5:
- __asm__("csrr %[addr], pmpaddr5"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr5" : [addr] "=r"(*address)::);
break;
case 6:
- __asm__("csrr %[addr], pmpaddr6"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr6" : [addr] "=r"(*address)::);
break;
case 7:
- __asm__("csrr %[addr], pmpaddr7"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr7" : [addr] "=r"(*address)::);
break;
case 8:
- __asm__("csrr %[addr], pmpaddr8"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr8" : [addr] "=r"(*address)::);
break;
case 9:
- __asm__("csrr %[addr], pmpaddr9"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr9" : [addr] "=r"(*address)::);
break;
case 10:
- __asm__("csrr %[addr], pmpaddr10"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr10" : [addr] "=r"(*address)::);
break;
case 11:
- __asm__("csrr %[addr], pmpaddr11"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr11" : [addr] "=r"(*address)::);
break;
case 12:
- __asm__("csrr %[addr], pmpaddr12"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr12" : [addr] "=r"(*address)::);
break;
case 13:
- __asm__("csrr %[addr], pmpaddr13"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr13" : [addr] "=r"(*address)::);
break;
case 14:
- __asm__("csrr %[addr], pmpaddr14"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr14" : [addr] "=r"(*address)::);
break;
case 15:
- __asm__("csrr %[addr], pmpaddr15"
- : [addr] "=r" (*address) ::);
+ __asm__("csrr %[addr], pmpaddr15" : [addr] "=r"(*address)::);
break;
}
return 0;
}
-int metal_pmp_lock(struct metal_pmp *pmp, unsigned int region)
-{
+int metal_pmp_lock(struct metal_pmp *pmp, unsigned int region) {
struct metal_pmp_config config;
size_t address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &address);
- if(rc) {
+ if (rc) {
return rc;
}
- if(config.L == METAL_PMP_LOCKED) {
+ if (config.L == METAL_PMP_LOCKED) {
return 0;
}
@@ -441,15 +384,14 @@ int metal_pmp_lock(struct metal_pmp *pmp, unsigned int region)
return rc;
}
-
-int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region, size_t address)
-{
+int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region,
+ size_t address) {
struct metal_pmp_config config;
size_t old_address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &old_address);
- if(rc) {
+ if (rc) {
return rc;
}
@@ -458,8 +400,7 @@ int metal_pmp_set_address(struct metal_pmp *pmp, unsigned int region, size_t add
return rc;
}
-size_t metal_pmp_get_address(struct metal_pmp *pmp, unsigned int region)
-{
+size_t metal_pmp_get_address(struct metal_pmp *pmp, unsigned int region) {
struct metal_pmp_config config;
size_t address = 0;
@@ -468,15 +409,14 @@ size_t metal_pmp_get_address(struct metal_pmp *pmp, unsigned int region)
return address;
}
-
-int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum metal_pmp_address_mode mode)
-{
+int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region,
+ enum metal_pmp_address_mode mode) {
struct metal_pmp_config config;
size_t address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &address);
- if(rc) {
+ if (rc) {
return rc;
}
@@ -487,8 +427,8 @@ int metal_pmp_set_address_mode(struct metal_pmp *pmp, unsigned int region, enum
return rc;
}
-enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp, unsigned int region)
-{
+enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp,
+ unsigned int region) {
struct metal_pmp_config config;
size_t address = 0;
@@ -497,15 +437,14 @@ enum metal_pmp_address_mode metal_pmp_get_address_mode(struct metal_pmp *pmp, un
return config.A;
}
-
-int metal_pmp_set_executable(struct metal_pmp *pmp, unsigned int region, int X)
-{
+int metal_pmp_set_executable(struct metal_pmp *pmp, unsigned int region,
+ int X) {
struct metal_pmp_config config;
size_t address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &address);
- if(rc) {
+ if (rc) {
return rc;
}
@@ -516,8 +455,7 @@ int metal_pmp_set_executable(struct metal_pmp *pmp, unsigned int region, int X)
return rc;
}
-int metal_pmp_get_executable(struct metal_pmp *pmp, unsigned int region)
-{
+int metal_pmp_get_executable(struct metal_pmp *pmp, unsigned int region) {
struct metal_pmp_config config;
size_t address = 0;
@@ -526,15 +464,13 @@ int metal_pmp_get_executable(struct metal_pmp *pmp, unsigned int region)
return config.X;
}
-
-int metal_pmp_set_writeable(struct metal_pmp *pmp, unsigned int region, int W)
-{
+int metal_pmp_set_writeable(struct metal_pmp *pmp, unsigned int region, int W) {
struct metal_pmp_config config;
size_t address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &address);
- if(rc) {
+ if (rc) {
return rc;
}
@@ -545,8 +481,7 @@ int metal_pmp_set_writeable(struct metal_pmp *pmp, unsigned int region, int W)
return rc;
}
-int metal_pmp_get_writeable(struct metal_pmp *pmp, unsigned int region)
-{
+int metal_pmp_get_writeable(struct metal_pmp *pmp, unsigned int region) {
struct metal_pmp_config config;
size_t address = 0;
@@ -555,15 +490,13 @@ int metal_pmp_get_writeable(struct metal_pmp *pmp, unsigned int region)
return config.W;
}
-
-int metal_pmp_set_readable(struct metal_pmp *pmp, unsigned int region, int R)
-{
+int metal_pmp_set_readable(struct metal_pmp *pmp, unsigned int region, int R) {
struct metal_pmp_config config;
size_t address;
int rc = 0;
rc = metal_pmp_get_region(pmp, region, &config, &address);
- if(rc) {
+ if (rc) {
return rc;
}
@@ -574,8 +507,7 @@ int metal_pmp_set_readable(struct metal_pmp *pmp, unsigned int region, int R)
return rc;
}
-int metal_pmp_get_readable(struct metal_pmp *pmp, unsigned int region)
-{
+int metal_pmp_get_readable(struct metal_pmp *pmp, unsigned int region) {
struct metal_pmp_config config;
size_t address = 0;
@@ -583,4 +515,3 @@ int metal_pmp_get_readable(struct metal_pmp *pmp, unsigned int region)
return config.R;
}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/privilege.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/privilege.c
index 54bfcfc2c..0919d77d7 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/privilege.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/privilege.c
@@ -5,53 +5,51 @@
#include <metal/privilege.h>
-#define METAL_MSTATUS_MIE_OFFSET 3
-#define METAL_MSTATUS_MPIE_OFFSET 7
-#define METAL_MSTATUS_SIE_OFFSET 1
-#define METAL_MSTATUS_SPIE_OFFSET 5
-#define METAL_MSTATUS_UIE_OFFSET 0
-#define METAL_MSTATUS_UPIE_OFFSET 4
+#define METAL_MSTATUS_MIE_OFFSET 3
+#define METAL_MSTATUS_MPIE_OFFSET 7
+#define METAL_MSTATUS_SIE_OFFSET 1
+#define METAL_MSTATUS_SPIE_OFFSET 5
+#define METAL_MSTATUS_UIE_OFFSET 0
+#define METAL_MSTATUS_UPIE_OFFSET 4
-#define METAL_MSTATUS_MPP_OFFSET 11
-#define METAL_MSTATUS_MPP_MASK 3
+#define METAL_MSTATUS_MPP_OFFSET 11
+#define METAL_MSTATUS_MPP_MASK 3
void metal_privilege_drop_to_mode(enum metal_privilege_mode mode,
- struct metal_register_file regfile,
- metal_privilege_entry_point_t entry_point)
-{
- uintptr_t mstatus;
- __asm__ volatile("csrr %0, mstatus" : "=r" (mstatus));
-
- /* Set xPIE bits based on current xIE bits */
- if(mstatus && (1 << METAL_MSTATUS_MIE_OFFSET)) {
- mstatus |= (1 << METAL_MSTATUS_MPIE_OFFSET);
- } else {
- mstatus &= ~(1 << METAL_MSTATUS_MPIE_OFFSET);
- }
- if(mstatus && (1 << METAL_MSTATUS_SIE_OFFSET)) {
- mstatus |= (1 << METAL_MSTATUS_SPIE_OFFSET);
- } else {
- mstatus &= ~(1 << METAL_MSTATUS_SPIE_OFFSET);
- }
- if(mstatus && (1 << METAL_MSTATUS_UIE_OFFSET)) {
- mstatus |= (1 << METAL_MSTATUS_UPIE_OFFSET);
- } else {
- mstatus &= ~(1 << METAL_MSTATUS_UPIE_OFFSET);
- }
-
- /* Set MPP to the requested privilege mode */
- mstatus &= ~(METAL_MSTATUS_MPP_MASK << METAL_MSTATUS_MPP_OFFSET);
- mstatus |= (mode << METAL_MSTATUS_MPP_OFFSET);
-
- __asm__ volatile("csrw mstatus, %0" :: "r" (mstatus));
-
- /* Set the entry point in MEPC */
- __asm__ volatile("csrw mepc, %0" :: "r" (entry_point));
-
- /* Set the register file */
- __asm__ volatile("mv ra, %0" :: "r" (regfile.ra));
- __asm__ volatile("mv sp, %0" :: "r" (regfile.sp));
-
- __asm__ volatile("mret");
+ struct metal_register_file regfile,
+ metal_privilege_entry_point_t entry_point) {
+ uintptr_t mstatus;
+ __asm__ volatile("csrr %0, mstatus" : "=r"(mstatus));
+
+ /* Set xPIE bits based on current xIE bits */
+ if (mstatus & (1 << METAL_MSTATUS_MIE_OFFSET)) {
+ mstatus |= (1 << METAL_MSTATUS_MPIE_OFFSET);
+ } else {
+ mstatus &= ~(1 << METAL_MSTATUS_MPIE_OFFSET);
+ }
+ if (mstatus & (1 << METAL_MSTATUS_SIE_OFFSET)) {
+ mstatus |= (1 << METAL_MSTATUS_SPIE_OFFSET);
+ } else {
+ mstatus &= ~(1 << METAL_MSTATUS_SPIE_OFFSET);
+ }
+ if (mstatus & (1 << METAL_MSTATUS_UIE_OFFSET)) {
+ mstatus |= (1 << METAL_MSTATUS_UPIE_OFFSET);
+ } else {
+ mstatus &= ~(1 << METAL_MSTATUS_UPIE_OFFSET);
+ }
+
+ /* Set MPP to the requested privilege mode */
+ mstatus &= ~(METAL_MSTATUS_MPP_MASK << METAL_MSTATUS_MPP_OFFSET);
+ mstatus |= (mode << METAL_MSTATUS_MPP_OFFSET);
+
+ __asm__ volatile("csrw mstatus, %0" ::"r"(mstatus));
+
+ /* Set the entry point in MEPC */
+ __asm__ volatile("csrw mepc, %0" ::"r"(entry_point));
+
+ /* Set the register file */
+ __asm__ volatile("mv ra, %0" ::"r"(regfile.ra));
+ __asm__ volatile("mv sp, %0" ::"r"(regfile.sp));
+
+ __asm__ volatile("mret");
}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pwm.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pwm.c
new file mode 100644
index 000000000..15e4e6ecf
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/pwm.c
@@ -0,0 +1,36 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine.h>
+#include <metal/pwm.h>
+
+extern inline int metal_pwm_enable(struct metal_pwm *pwm);
+extern inline int metal_pwm_disable(struct metal_pwm *pwm);
+extern inline int metal_pwm_set_freq(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int freq);
+extern inline int metal_pwm_set_duty(struct metal_pwm *pwm, unsigned int idx,
+ unsigned int duty,
+ metal_pwm_phase_correct_t phase_corr);
+extern inline unsigned int metal_pwm_get_duty(struct metal_pwm *pwm,
+ unsigned int idx);
+extern inline unsigned int metal_pwm_get_freq(struct metal_pwm *pwm,
+ unsigned int idx);
+extern inline int metal_pwm_trigger(struct metal_pwm *pwm, unsigned int idx,
+ metal_pwm_run_mode_t mode);
+extern inline int metal_pwm_stop(struct metal_pwm *pwm, unsigned int idx);
+extern inline int metal_pwm_cfg_interrupt(struct metal_pwm *pwm,
+ metal_pwm_interrupt_t flag);
+extern inline int metal_pwm_clr_interrupt(struct metal_pwm *pwm,
+ unsigned int idx);
+extern struct metal_interrupt *
+metal_pwm_interrupt_controller(struct metal_pwm *pwm);
+extern int metal_pwm_get_interrupt_id(struct metal_pwm *pwm, unsigned int idx);
+
+struct metal_pwm *metal_pwm_get_device(unsigned int device_num) {
+#if __METAL_DT_MAX_PWMS > 0
+ if (device_num < __METAL_DT_MAX_PWMS) {
+ return (struct metal_pwm *)__metal_pwm_table[device_num];
+ }
+#endif
+ return NULL;
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/rtc.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/rtc.c
index 8b79892df..ff43ec32c 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/rtc.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/rtc.c
@@ -7,21 +7,25 @@
#include <stddef.h>
extern inline uint64_t metal_rtc_get_rate(const struct metal_rtc *const rtc);
-extern inline uint64_t metal_rtc_set_rate(const struct metal_rtc *const rtc, const uint64_t rate);
+extern inline uint64_t metal_rtc_set_rate(const struct metal_rtc *const rtc,
+ const uint64_t rate);
extern inline uint64_t metal_rtc_get_compare(const struct metal_rtc *const rtc);
-extern inline uint64_t metal_rtc_set_compare(const struct metal_rtc *const rtc, const uint64_t compare);
+extern inline uint64_t metal_rtc_set_compare(const struct metal_rtc *const rtc,
+ const uint64_t compare);
extern inline uint64_t metal_rtc_get_count(const struct metal_rtc *const rtc);
-extern inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc, const uint64_t count);
-extern inline int metal_rtc_run(const struct metal_rtc *const rtc, const enum metal_rtc_run_option option);
-extern inline struct metal_interrupt *metal_rtc_get_interrupt(const struct metal_rtc *const rtc);
+extern inline uint64_t metal_rtc_set_count(const struct metal_rtc *const rtc,
+ const uint64_t count);
+extern inline int metal_rtc_run(const struct metal_rtc *const rtc,
+ const enum metal_rtc_run_option option);
+extern inline struct metal_interrupt *
+metal_rtc_get_interrupt(const struct metal_rtc *const rtc);
extern inline int metal_rtc_get_interrupt_id(const struct metal_rtc *const rtc);
struct metal_rtc *metal_rtc_get_device(int index) {
#ifdef __METAL_DT_MAX_RTCS
if (index < __METAL_DT_MAX_RTCS) {
- return (struct metal_rtc *) __metal_rtc_table[index];
+ return (struct metal_rtc *)__metal_rtc_table[index];
}
#endif
return NULL;
}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/scrub.S b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/scrub.S
new file mode 100644
index 000000000..08b4a73dc
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/scrub.S
@@ -0,0 +1,132 @@
+/* Copyright 2020 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+/*
+ * Scrub memory with zeroes
+ */
+
+/* Keep it in metal.init section with _enter */
+.section .text.metal.init.scrub
+/* Disable linker relaxation */
+.option push
+.option norelax
+
+/* Function to zero-scrub specified memory
+ * a0 : start address for zero-scrub
+ * a1 : size memory region size in bytes
+ */
+.global metal_mem_scrub
+.type metal_mem_scrub, @function
+metal_mem_scrub:
+
+ /* Disable machine interrupts,
+ restore previous mstatus value at exit */
+ li a3, 8
+ csrrc t1, mstatus, a3
+
+#if __riscv_xlen == 32
+ addi t0, x0, 4
+1:
+ blt a1, t0, 2f
+ andi a2, a0, 3
+ beqz a2, 3f
+2:
+ sb x0, 0(a0)
+ addi a0, a0, 1
+ addi a1, a1, -1
+ bgtz a1, 1b
+ csrw mstatus, t1
+ ret
+3:
+ sw x0, 0(a0)
+ addi a0, a0, 4
+ addi a1, a1, -4
+ bgtz a1, 1b
+ csrw mstatus, t1
+ ret
+#else
+ addi t0, x0, 8
+1:
+ blt a1, t0, 2f
+ andi a2, a0, 7
+ beqz a2, 3f
+2:
+ sb x0, 0(a0)
+ addi a0, a0, 1
+ addi a1, a1, -1
+ bgtz a1, 1b
+ csrw mstatus, t1
+ ret
+3:
+ sd x0, 0(a0)
+ addi a0, a0, 8
+ addi a1, a1, -8
+ bgtz a1, 1b
+ csrw mstatus, t1
+ ret
+#endif
+
+.type __metal_memory_scrub, @function
+__metal_memory_scrub:
+/* Zero out specified memory regions */
+1:
+#if __riscv_xlen == 32
+ sw x0, 0(t1)
+ addi t1, t1, 4
+ blt t1, t2, 1b
+#else
+ sd x0, 0(t1)
+ addi t1, t1, 8
+ blt t1, t2, 1b
+#endif
+ ret
+
+/*
+ * Initialize memories to zero
+ * This must be called before setting up any stack(s)
+ */
+.weak __metal_eccscrub_bit
+.weak __metal_before_start
+.global __metal_before_start
+.type __metal_before_start, @function
+__metal_before_start:
+ /* Save caller ra */
+ mv s0, ra
+
+ la t0, __metal_eccscrub_bit
+ beqz t0, skip_scrub
+
+ la t0, __metal_boot_hart
+ csrr a5, mhartid
+
+ /* Disable machine interrupts to be safe */
+ li a3, 8
+ csrc mstatus, a3
+
+ /* Zero out per hart stack */
+ mv t1, sp
+ la t2, __stack_size
+ add t2, t2, sp
+ beq t1, t2, 1f
+ jal __metal_memory_scrub
+1:
+ bne a5, t0, skip_scrub
+
+ /* Zero out data segment */
+ la t1, metal_segment_data_target_start
+ la t2, metal_segment_data_target_end
+ beq t1, t2, 1f
+ jal __metal_memory_scrub
+1:
+ /* Zero out itim memory */
+ la t1, metal_segment_itim_target_start
+ la t2, metal_segment_itim_target_end
+ beq t1, t2, skip_scrub
+ jal __metal_memory_scrub
+
+skip_scrub:
+ /* Restore caller ra */
+ mv ra, s0
+ ret
+
+.option pop
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/shutdown.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/shutdown.c
index c3b5255a7..eadb0fb89 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/shutdown.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/shutdown.c
@@ -4,19 +4,19 @@
#include <metal/machine.h>
#include <metal/shutdown.h>
-extern __inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd, int code);
+extern __inline__ void __metal_shutdown_exit(const struct __metal_shutdown *sd,
+ int code);
#if defined(__METAL_DT_SHUTDOWN_HANDLE)
-void metal_shutdown(int code)
-{
+void metal_shutdown(int code) {
__metal_shutdown_exit(__METAL_DT_SHUTDOWN_HANDLE, code);
}
#else
-#pragma message("There is no defined shutdown mechanism, metal_shutdown() will spin.")
-void metal_shutdown(int code)
-{
+#pragma message( \
+ "There is no defined shutdown mechanism, metal_shutdown() will spin.")
+void metal_shutdown(int code) {
while (1) {
- __asm__ volatile ("nop");
+ __asm__ volatile("nop");
}
}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/spi.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/spi.c
index de8cda737..19fcb9f04 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/spi.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/spi.c
@@ -5,15 +5,18 @@
#include <metal/spi.h>
extern __inline__ void metal_spi_init(struct metal_spi *spi, int baud_rate);
-extern __inline__ int metal_spi_transfer(struct metal_spi *spi, struct metal_spi_config *config, size_t len, char *tx_buf, char *rx_buf);
+extern __inline__ int metal_spi_transfer(struct metal_spi *spi,
+ struct metal_spi_config *config,
+ size_t len, char *tx_buf,
+ char *rx_buf);
extern __inline__ int metal_spi_get_baud_rate(struct metal_spi *spi);
-extern __inline__ int metal_spi_set_baud_rate(struct metal_spi *spi, int baud_rate);
+extern __inline__ int metal_spi_set_baud_rate(struct metal_spi *spi,
+ int baud_rate);
-struct metal_spi *metal_spi_get_device(unsigned int device_num)
-{
+struct metal_spi *metal_spi_get_device(unsigned int device_num) {
#if __METAL_DT_MAX_SPIS > 0
if (device_num < __METAL_DT_MAX_SPIS) {
- return (struct metal_spi *) __metal_spi_table[device_num];
+ return (struct metal_spi *)__metal_spi_table[device_num];
}
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/switch.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/switch.c
index 4f17229c7..fb72d1968 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/switch.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/switch.c
@@ -1,11 +1,10 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <metal/switch.h>
#include <metal/machine.h>
+#include <metal/switch.h>
-struct metal_switch* metal_switch_get (char *label)
-{
+struct metal_switch *metal_switch_get(char *label) {
int i;
struct metal_switch *flip;
@@ -14,7 +13,7 @@ struct metal_switch* metal_switch_get (char *label)
}
for (i = 0; i < __METAL_DT_MAX_BUTTONS; i++) {
- flip = (struct metal_switch*)__metal_switch_table[i];
+ flip = (struct metal_switch *)__metal_switch_table[i];
if (flip->vtable->switch_exist(flip, label)) {
return flip;
}
@@ -22,6 +21,6 @@ struct metal_switch* metal_switch_get (char *label)
return NULL;
}
-extern __inline__ struct metal_interrupt*
- metal_switch_interrupt_controller(struct metal_switch *flip);
+extern __inline__ struct metal_interrupt *
+metal_switch_interrupt_controller(struct metal_switch *flip);
extern __inline__ int metal_switch_get_interrupt_id(struct metal_switch *flip);
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/synchronize_harts.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/synchronize_harts.c
index a5338e942..b1548f9b5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/synchronize_harts.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/synchronize_harts.c
@@ -1,62 +1,66 @@
/* Copyright 2019 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
+#include <metal/cpu.h>
+#include <metal/io.h>
#include <metal/machine.h>
#include <metal/machine/platform.h>
-#include <metal/io.h>
-#include <metal/cpu.h>
-#define METAL_REG(base, offset) (((unsigned long)(base) + (offset)))
-#define METAL_REGW(base, offset) (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_REG((base), (offset))))
-#define METAL_MSIP(base, hart) (METAL_REGW((base),4*(hart)))
+#define METAL_REG(base, offset) (((unsigned long)(base) + (offset)))
+#define METAL_REGW(base, offset) \
+ (__METAL_ACCESS_ONCE((__metal_io_u32 *)METAL_REG((base), (offset))))
+#define METAL_MSIP(base, hart) (METAL_REGW((base), 4 * (hart)))
/*
* _synchronize_harts() is called by crt0.S to cause harts > 0 to wait for
* hart 0 to finish copying the datat section, zeroing the BSS, and running
* the libc contstructors.
*/
-__attribute__((section(".init")))
-void __metal_synchronize_harts() {
+__attribute__((section(".init"))) void __metal_synchronize_harts() {
#if __METAL_DT_MAX_HARTS > 1
int hart;
- __asm__ volatile("csrr %0, mhartid" : "=r" (hart) ::);
+ __asm__ volatile("csrr %0, mhartid" : "=r"(hart)::);
uintptr_t msip_base = 0;
/* Get the base address of the MSIP registers */
#ifdef __METAL_DT_RISCV_CLINT0_HANDLE
- msip_base = __metal_driver_sifive_clint0_control_base(__METAL_DT_RISCV_CLINT0_HANDLE);
+ msip_base = __metal_driver_sifive_clint0_control_base(
+ __METAL_DT_RISCV_CLINT0_HANDLE);
msip_base += METAL_RISCV_CLINT0_MSIP_BASE;
#elif __METAL_DT_RISCV_CLIC0_HANDLE
- msip_base = __metal_driver_sifive_clic0_control_base(__METAL_DT_RISCV_CLIC0_HANDLE);
+ msip_base =
+ __metal_driver_sifive_clic0_control_base(__METAL_DT_RISCV_CLIC0_HANDLE);
msip_base += METAL_RISCV_CLIC0_MSIP_BASE;
#else
-#pragma message(No handle for CLINT or CLIC found, harts may be unsynchronized after init!)
+#pragma message(No handle for CLINT or CLIC found, \
+ harts may be unsynchronized after init !)
#endif
/* Disable machine interrupts as a precaution */
- __asm__ volatile("csrc mstatus, %0" :: "r" (METAL_MSTATUS_MIE));
+ __asm__ volatile("csrc mstatus, %0" ::"r"(METAL_MSTATUS_MIE));
if (hart == 0) {
/* Hart 0 waits for all harts to set their MSIP bit */
- for (int i = 1 ; i < __METAL_DT_MAX_HARTS; i++) {
- while (METAL_MSIP(msip_base, i) == 0) ;
+ for (int i = 1; i < __METAL_DT_MAX_HARTS; i++) {
+ while (METAL_MSIP(msip_base, i) == 0)
+ ;
}
/* Hart 0 clears everyone's MSIP bit */
- for (int i = 1 ; i < __METAL_DT_MAX_HARTS; i++) {
+ for (int i = 1; i < __METAL_DT_MAX_HARTS; i++) {
METAL_MSIP(msip_base, i) = 0;
}
} else {
/* Other harts set their MSIP bit to indicate they're ready */
METAL_MSIP(msip_base, hart) = 1;
- __asm__ volatile ("fence w,rw");
+ __asm__ volatile("fence w,rw");
/* Wait for hart 0 to clear the MSIP bit */
- while (METAL_MSIP(msip_base, hart) == 1) ;
+ while (METAL_MSIP(msip_base, hart) == 1)
+ ;
}
#endif /* __METAL_DT_MAX_HARTS > 1 */
}
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/time.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/time.c
index 529f8bd56..a40a3ced0 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/time.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/time.c
@@ -4,14 +4,17 @@
#include <metal/time.h>
#include <metal/timer.h>
-int metal_gettimeofday(struct timeval *tp, void *tzp)
-{
+#include <stddef.h>
+
+int metal_gettimeofday(struct timeval *tp, void *tzp) {
int rv;
unsigned long long mcc, timebase;
- if ((rv = metal_timer_get_cyclecount(0, &mcc))) {
+ rv = metal_timer_get_cyclecount(0, &mcc);
+ if (rv != 0) {
return -1;
}
- if ((rv = metal_timer_get_timebase_frequency(0, &timebase))) {
+ rv = metal_timer_get_timebase_frequency(0, &timebase);
+ if (rv != 0) {
return -1;
}
tp->tv_sec = mcc / timebase;
@@ -19,12 +22,11 @@ int metal_gettimeofday(struct timeval *tp, void *tzp)
return 0;
}
-time_t metal_time (void)
-{
+time_t metal_time(void) {
struct timeval now;
if (metal_gettimeofday(&now, NULL) < 0)
- now.tv_sec = (time_t) -1;
+ now.tv_sec = (time_t)-1;
- return now.tv_sec;
+ return now.tv_sec;
}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/timer.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/timer.c
index f58413321..8e5859aa5 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/timer.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/timer.c
@@ -1,80 +1,83 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <sys/time.h>
-#include <sys/times.h>
#include <metal/cpu.h>
-#include <metal/timer.h>
#include <metal/machine.h>
+#include <metal/timer.h>
+#ifndef __SEGGER_LIBC__
+#include <sys/time.h>
+#include <sys/times.h>
+#endif
#if defined(__METAL_DT_MAX_HARTS)
/* This implementation serves as a small shim that interfaces with the first
* timer on a system. */
-int metal_timer_get_cyclecount(int hartid, unsigned long long *mcc)
-{
+int metal_timer_get_cyclecount(int hartid, unsigned long long *mcc) {
struct metal_cpu *cpu = metal_cpu_get(hartid);
- if ( cpu ) {
+ if (cpu) {
*mcc = metal_cpu_get_timer(cpu);
return 0;
- }
+ }
return -1;
}
-int metal_timer_get_timebase_frequency(int hartid, unsigned long long *timebase)
-{
+int metal_timer_get_timebase_frequency(int hartid,
+ unsigned long long *timebase) {
struct metal_cpu *cpu = metal_cpu_get(hartid);
- if ( cpu ) {
+ if (cpu) {
*timebase = metal_cpu_get_timebase(cpu);
return 0;
- }
+ }
return -1;
}
-int metal_timer_get_machine_time(int hartid)
-{
+int metal_timer_get_machine_time(int hartid) {
struct metal_cpu *cpu = metal_cpu_get(hartid);
-
- if ( cpu ) {
- return metal_cpu_get_mtime(cpu);
+
+ if (cpu) {
+ return metal_cpu_get_mtime(cpu);
}
return 0;
}
-int metal_timer_set_machine_time(int hartid, unsigned long long time)
-{
+int metal_timer_set_machine_time(int hartid, unsigned long long time) {
struct metal_cpu *cpu = metal_cpu_get(hartid);
- if ( cpu ) {
- return metal_cpu_set_mtimecmp(cpu, time);
+ if (cpu) {
+ return metal_cpu_set_mtimecmp(cpu, time);
}
return -1;
}
#else
-/* This implementation of gettimeofday doesn't actually do anything, it's just there to
- * provide a shim and return 0 so we can ensure that everything can link to _gettimeofday.
+/* This implementation of gettimeofday doesn't actually do anything, it's just
+ * there to provide a shim and return 0 so we can ensure that everything can
+ * link to _gettimeofday.
*/
-int nop_cyclecount(int id, unsigned long long *c) __attribute__((section(".text.metal.nop.cyclecount")));
+int nop_cyclecount(int id, unsigned long long *c)
+ __attribute__((section(".text.metal.nop.cyclecount")));
int nop_cyclecount(int id, unsigned long long *c) { return -1; }
-int nop_timebase(unsigned long long *t) __attribute__((section(".text.metal.nop.timebase")));
+int nop_timebase(unsigned long long *t)
+ __attribute__((section(".text.metal.nop.timebase")));
int nop_timebase(unsigned long long *t) { return -1; }
int nop_tick(int second) __attribute__((section(".text.metal.nop.tick")));
int nop_tick(int second) { return -1; }
-int metal_timer_get_cyclecount(int hartid, unsigned long long *c) __attribute__((weak, alias("nop_cyclecount")))
-{
-#pragma message("There is no default timer device, metal_timer_get_cyclecount() will always return cyclecount -1.")
+int metal_timer_get_cyclecount(int hartid, unsigned long long *c)
+ __attribute__((weak, alias("nop_cyclecount"))) {
+#pragma message( \
+ "There is no default timer device, metal_timer_get_cyclecount() will always return cyclecount -1.")
}
-int metal_timer_get_timebase_frequency(unsigned long long *t) __attribute__((weak, alias("nop_timebase")))
-{
-#pragma message("There is no default timer device, metal_timer_get_timebase_frequency() will always return timebase -1.")
+int metal_timer_get_timebase_frequency(unsigned long long *t)
+ __attribute__((weak, alias("nop_timebase"))) {
+#pragma message( \
+ "There is no default timer device, metal_timer_get_timebase_frequency() will always return timebase -1.")
}
-int metal_timer_set_tick(int second) __attribute__((weak, alias("nop_tick")))
-{
-#pragma message("There is no default timer device, metal_timer_set_tick) will always return -1.")
+int metal_timer_set_tick(int second) __attribute__((weak, alias("nop_tick"))) {
+#pragma message( \
+ "There is no default timer device, metal_timer_set_tick) will always return -1.")
}
#endif
-
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/trap.S b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/trap.S
index b55b6656a..7d12d640f 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/trap.S
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/trap.S
@@ -51,3 +51,18 @@ _metal_trap:
/* Jump to mtvec */
jr t0
+
+/*
+ * For sanity's sake we set up an early trap vector that just does nothing.
+ * If you end up here then there's a bug in the early boot code somewhere.
+ */
+.section .text.metal.init.trapvec
+.global early_trap_vector
+.align 2
+early_trap_vector:
+ .cfi_startproc
+ csrr t0, mcause
+ csrr t1, mepc
+ csrr t2, mtval
+ j early_trap_vector
+ .cfi_endproc
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/tty.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/tty.c
index 306192451..e5ffdb260 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/tty.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/tty.c
@@ -1,33 +1,23 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
-#include <metal/uart.h>
-#include <metal/tty.h>
+#include <metal/init.h>
#include <metal/machine.h>
+#include <metal/tty.h>
+#include <metal/uart.h>
#if defined(__METAL_DT_STDOUT_UART_HANDLE)
/* This implementation serves as a small shim that interfaces with the first
* UART on a system. */
-int metal_tty_putc(int c)
-{
- if (c == '\n') {
- metal_tty_putc_raw( '\r' );
- }
- return metal_tty_putc_raw( c );
-}
-
-int metal_tty_putc_raw(int c)
-{
+int metal_tty_putc(int c) {
return metal_uart_putc(__METAL_DT_STDOUT_UART_HANDLE, c);
}
-int metal_tty_getc(int *c)
-{
- do {
- metal_uart_getc( __METAL_DT_STDOUT_UART_HANDLE, c );
+int metal_tty_getc(int *c) {
+ do {
+ metal_uart_getc(__METAL_DT_STDOUT_UART_HANDLE, c);
/* -1 means no key pressed, getc waits */
- } while( -1 == *c )
- ;
+ } while (-1 == *c);
return 0;
}
@@ -35,9 +25,7 @@ int metal_tty_getc(int *c)
#define __METAL_DT_STDOUT_UART_BAUD 115200
#endif
-static void metal_tty_init(void) __attribute__((constructor));
-static void metal_tty_init(void)
-{
+METAL_CONSTRUCTOR(metal_tty_init) {
metal_uart_init(__METAL_DT_STDOUT_UART_HANDLE, __METAL_DT_STDOUT_UART_BAUD);
}
#else
@@ -45,7 +33,20 @@ static void metal_tty_init(void)
* provide a shim that eats all the characters so we can ensure that everything
* can link to metal_tty_putc. */
int nop_putc(int c) __attribute__((section(".text.metal.nop.putc")));
-int nop_putc(int c) { return -1; }
+// Use a customizable NOP hint instruction so that a post-processor parser can
+// look for this instruction, and use the value in a0 as the character to be
+// printed.
+int nop_putc(int c) {
+ // The ABI states that c will be passed in a0. However, under an LTO
+ // (link-time-optimizer), it may choose to optimize in ways that would
+ // break this assumption. We want to ensure that the passed argument is
+ // truly in a0, for easier post-processing, and so there is a single
+ // 32-bit opcode to match against.
+ // So explicitly ensure that the argument is placed into a0 first.
+ __asm__ volatile("mv a0, %0; slli x0,a0,0x11" ::"r"(c));
+ return -1;
+}
int metal_tty_putc(int c) __attribute__((weak, alias("nop_putc")));
-#pragma message("There is no default output device, metal_tty_putc() will throw away all input.")
+#pragma message( \
+ "There is no default output device, metal_tty_putc() will throw away all input.")
#endif
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/uart.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/uart.c
index 8981eb8d3..753e5b430 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/uart.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/uart.c
@@ -1,6 +1,7 @@
/* Copyright 2018 SiFive, Inc */
/* SPDX-License-Identifier: Apache-2.0 */
+#include <metal/machine.h>
#include <metal/uart.h>
extern __inline__ void metal_uart_init(struct metal_uart *uart, int baud_rate);
@@ -8,4 +9,34 @@ extern __inline__ int metal_uart_putc(struct metal_uart *uart, int c);
extern __inline__ int metal_uart_txready(struct metal_uart *uart);
extern __inline__ int metal_uart_getc(struct metal_uart *uart, int *c);
extern __inline__ int metal_uart_get_baud_rate(struct metal_uart *uart);
-extern __inline__ int metal_uart_set_baud_rate(struct metal_uart *uart, int baud_rate);
+extern __inline__ int metal_uart_set_baud_rate(struct metal_uart *uart,
+ int baud_rate);
+extern __inline__ struct metal_interrupt *
+metal_uart_interrupt_controller(struct metal_uart *uart);
+extern __inline__ int metal_uart_get_interrupt_id(struct metal_uart *uart);
+extern __inline__ int
+metal_uart_transmit_interrupt_enable(struct metal_uart *uart);
+extern __inline__ int
+metal_uart_transmit_interrupt_disable(struct metal_uart *uart);
+extern __inline__ int
+metal_uart_receive_interrupt_enable(struct metal_uart *uart);
+extern __inline__ int
+metal_uart_receive_interrupt_disable(struct metal_uart *uart);
+extern __inline__ int metal_uart_set_transmit_watermark(struct metal_uart *uart,
+ size_t level);
+extern __inline__ size_t
+metal_uart_get_transmit_watermark(struct metal_uart *uart);
+extern __inline__ int metal_uart_set_receive_watermark(struct metal_uart *uart,
+ size_t level);
+extern __inline__ size_t
+metal_uart_get_receive_watermark(struct metal_uart *uart);
+
+struct metal_uart *metal_uart_get_device(unsigned int device_num) {
+#if __METAL_DT_MAX_UARTS > 0
+ if (device_num < __METAL_DT_MAX_UARTS) {
+ return (struct metal_uart *)__metal_uart_table[device_num];
+ }
+#endif
+
+ return NULL;
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/watchdog.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/watchdog.c
new file mode 100644
index 000000000..5e9bc4965
--- /dev/null
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/freedom-metal/src/watchdog.c
@@ -0,0 +1,37 @@
+/* Copyright 2019 SiFive, Inc */
+/* SPDX-License-Identifier: Apache-2.0 */
+
+#include <metal/machine.h>
+#include <metal/watchdog.h>
+
+extern inline int metal_watchdog_feed(const struct metal_watchdog *const wdog);
+extern inline long int
+metal_watchdog_get_rate(const struct metal_watchdog *const wdog);
+extern inline long int
+metal_watchdog_set_rate(const struct metal_watchdog *const wdog,
+ const long int rate);
+extern inline long int
+metal_watchdog_get_timeout(const struct metal_watchdog *const wdog);
+extern inline long int
+metal_watchdog_set_timeout(const struct metal_watchdog *const wdog,
+ const long int timeout);
+extern inline int
+metal_watchdog_set_result(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_result result);
+extern inline int
+metal_watchdog_run(const struct metal_watchdog *const wdog,
+ const enum metal_watchdog_run_option option);
+extern inline struct metal_interrupt *
+metal_watchdog_get_interrupt(const struct metal_watchdog *const wdog);
+extern inline int
+metal_watchdog_get_interrupt_id(const struct metal_watchdog *const wdog);
+extern inline int
+metal_watchdog_clear_interrupt(const struct metal_watchdog *const wdog);
+
+struct metal_watchdog *metal_watchdog_get_device(const int index) {
+ if (index > __METAL_DT_MAX_WDOGS) {
+ return NULL;
+ }
+
+ return (struct metal_watchdog *)__metal_wdog_table[index];
+}
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/RegTest.S b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/RegTest.S
index 1ae58c4e0..daa68f191 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/RegTest.S
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/RegTest.S
@@ -1,266 +1,266 @@
-/*
- * FreeRTOS V202104.00
- * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
-
- .extern ulRegTest1LoopCounter
- .extern ulRegTest2LoopCounter
-
- .global vRegTest1Implementation
- .global vRegTest2Implementation
-
-/*-----------------------------------------------------------*/
-
-/*
- * The register check tasks are described in the comments at the top of
- * main_full.c.
- */
-
-.align( 4 )
-vRegTest1Implementation:
-
- /* Fill the core registers with known values. */
- li x5, 0x5
- li x6, 0x6
- li x7, 0x7
- li x8, 0x8
- li x9, 0x9
- li x10, 0xa
- li x11, 0xb
- li x12, 0xc
- li x13, 0xd
- li x14, 0xe
- li x15, 0xf
- li x16, 0x10
- li x17, 0x11
- li x18, 0x12
- li x19, 0x13
- li x20, 0x14
- li x21, 0x15
- li x22, 0x16
- li x23, 0x17
- li x24, 0x18
- li x25, 0x19
- li x26, 0x1a
- li x27, 0x1b
- li x28, 0x1c
- li x29, 0x1d
- li x30, 0x1e
-
-reg1_loop:
-
- /* Check each register still contains the expected known value.
- vRegTest1Implementation uses x31 as the temporary, vRegTest2Implementation
- uses x5 as the temporary. */
- li x31, 0x5
- bne x31, x5, reg1_error_loop
- li x31, 0x6
- bne x31, x6, reg1_error_loop
- li x31, 0x7
- bne x31, x7, reg1_error_loop
- li x31, 0x8
- bne x31, x8, reg1_error_loop
- li x31, 0x9
- bne x31, x9, reg1_error_loop
- li x31, 0xa
- bne x31, x10, reg1_error_loop
- li x31, 0xb
- bne x31, x11, reg1_error_loop
- li x31, 0xc
- bne x31, x12, reg1_error_loop
- li x31, 0xd
- bne x31, x13, reg1_error_loop
- li x31, 0xe
- bne x31, x14, reg1_error_loop
- li x31, 0xf
- bne x31, x15, reg1_error_loop
- li x31, 0x10
- bne x31, x16, reg1_error_loop
- li x31, 0x11
- bne x31, x17, reg1_error_loop
- li x31, 0x12
- bne x31, x18, reg1_error_loop
- li x31, 0x13
- bne x31, x19, reg1_error_loop
- li x31, 0x14
- bne x31, x20, reg1_error_loop
- li x31, 0x15
- bne x31, x21, reg1_error_loop
- li x31, 0x16
- bne x31, x22, reg1_error_loop
- li x31, 0x17
- bne x31, x23, reg1_error_loop
- li x31, 0x18
- bne x31, x24, reg1_error_loop
- li x31, 0x19
- bne x31, x25, reg1_error_loop
- li x31, 0x1a
- bne x31, x26, reg1_error_loop
- li x31, 0x1b
- bne x31, x27, reg1_error_loop
- li x31, 0x1c
- bne x31, x28, reg1_error_loop
- li x31, 0x1d
- bne x31, x29, reg1_error_loop
- li x31, 0x1e
- bne x31, x30, reg1_error_loop
-
- /* Everything passed, increment the loop counter. */
- lw x31, ulRegTest1LoopCounterConst
- lw x30, 0(x31)
- addi x30, x30, 1
- sw x30, 0(x31)
-
- /* Restore clobbered register reading for next loop. */
- li x30, 0x1e
-
- /* Yield to increase code coverage. */
- ecall
-
- /* Start again. */
- jal reg1_loop
-
-reg1_error_loop:
- /* Jump here if a register contains an uxpected value. This stops the loop
- counter being incremented so the check task knows an error was found. */
- ebreak
- jal reg1_error_loop
-
-.align( 4 )
-ulRegTest1LoopCounterConst: .word ulRegTest1LoopCounter
-
-/*-----------------------------------------------------------*/
-
-.align( 4 )
-vRegTest2Implementation:
-
- /* Fill the core registers with known values. */
- li x6, 0x61
- li x7, 0x71
- li x8, 0x81
- li x9, 0x91
- li x10, 0xa1
- li x11, 0xb1
- li x12, 0xc1
- li x13, 0xd1
- li x14, 0xe1
- li x15, 0xf1
- li x16, 0x20
- li x17, 0x21
- li x18, 0x22
- li x19, 0x23
- li x20, 0x24
- li x21, 0x25
- li x22, 0x26
- li x23, 0x27
- li x24, 0x28
- li x25, 0x29
- li x26, 0x2a
- li x27, 0x2b
- li x28, 0x2c
- li x29, 0x2d
- li x30, 0x2e
- li x31, 0x2f
-
-Reg2_loop:
-
- /* Check each register still contains the expected known value.
- vRegTest2Implementation uses x5 as the temporary, vRegTest1Implementation
- uses x31 as the temporary. */
- li x5, 0x61
- bne x5, x6, reg2_error_loop
- li x5, 0x71
- bne x5, x7, reg2_error_loop
- li x5, 0x81
- bne x5, x8, reg2_error_loop
- li x5, 0x91
- bne x5, x9, reg2_error_loop
- li x5, 0xa1
- bne x5, x10, reg2_error_loop
- li x5, 0xb1
- bne x5, x11, reg2_error_loop
- li x5, 0xc1
- bne x5, x12, reg2_error_loop
- li x5, 0xd1
- bne x5, x13, reg2_error_loop
- li x5, 0xe1
- bne x5, x14, reg2_error_loop
- li x5, 0xf1
- bne x5, x15, reg2_error_loop
- li x5, 0x20
- bne x5, x16, reg2_error_loop
- li x5, 0x21
- bne x5, x17, reg2_error_loop
- li x5, 0x22
- bne x5, x18, reg2_error_loop
- li x5, 0x23
- bne x5, x19, reg2_error_loop
- li x5, 0x24
- bne x5, x20, reg2_error_loop
- li x5, 0x25
- bne x5, x21, reg2_error_loop
- li x5, 0x26
- bne x5, x22, reg2_error_loop
- li x5, 0x27
- bne x5, x23, reg2_error_loop
- li x5, 0x28
- bne x5, x24, reg2_error_loop
- li x5, 0x29
- bne x5, x25, reg2_error_loop
- li x5, 0x2a
- bne x5, x26, reg2_error_loop
- li x5, 0x2b
- bne x5, x27, reg2_error_loop
- li x5, 0x2c
- bne x5, x28, reg2_error_loop
- li x5, 0x2d
- bne x5, x29, reg2_error_loop
- li x5, 0x2e
- bne x5, x30, reg2_error_loop
- li x5, 0x2f
- bne x5, x31, reg2_error_loop
-
- /* Everything passed, increment the loop counter. */
- lw x5, ulRegTest2LoopCounterConst
- lw x6, 0(x5)
- addi x6, x6, 1
- sw x6, 0(x5)
-
- /* Restore clobbered register reading for next loop. */
- li x6, 0x61
-
- /* Start again. */
- jal Reg2_loop
-
-reg2_error_loop:
- /* Jump here if a register contains an uxpected value. This stops the loop
- counter being incremented so the check task knows an error was found. */
- ebreak
- jal reg2_error_loop
-
-.align( 4 )
-ulRegTest2LoopCounterConst: .word ulRegTest2LoopCounter
-
-
+/*
+ * FreeRTOS V202104.00
+ * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of
+ * this software and associated documentation files (the "Software"), to deal in
+ * the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+ * the Software, and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+ * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+ * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+ * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ * http://www.FreeRTOS.org
+ * http://aws.amazon.com/freertos
+ *
+ * 1 tab == 4 spaces!
+ */
+
+ .extern ulRegTest1LoopCounter
+ .extern ulRegTest2LoopCounter
+
+ .global vRegTest1Implementation
+ .global vRegTest2Implementation
+
+/*-----------------------------------------------------------*/
+
+/*
+ * The register check tasks are described in the comments at the top of
+ * main_full.c.
+ */
+
+.align( 4 )
+vRegTest1Implementation:
+
+ /* Fill the core registers with known values. */
+ li x5, 0x5
+ li x6, 0x6
+ li x7, 0x7
+ li x8, 0x8
+ li x9, 0x9
+ li x10, 0xa
+ li x11, 0xb
+ li x12, 0xc
+ li x13, 0xd
+ li x14, 0xe
+ li x15, 0xf
+ li x16, 0x10
+ li x17, 0x11
+ li x18, 0x12
+ li x19, 0x13
+ li x20, 0x14
+ li x21, 0x15
+ li x22, 0x16
+ li x23, 0x17
+ li x24, 0x18
+ li x25, 0x19
+ li x26, 0x1a
+ li x27, 0x1b
+ li x28, 0x1c
+ li x29, 0x1d
+ li x30, 0x1e
+
+reg1_loop:
+
+ /* Check each register still contains the expected known value.
+ vRegTest1Implementation uses x31 as the temporary, vRegTest2Implementation
+ uses x5 as the temporary. */
+ li x31, 0x5
+ bne x31, x5, reg1_error_loop
+ li x31, 0x6
+ bne x31, x6, reg1_error_loop
+ li x31, 0x7
+ bne x31, x7, reg1_error_loop
+ li x31, 0x8
+ bne x31, x8, reg1_error_loop
+ li x31, 0x9
+ bne x31, x9, reg1_error_loop
+ li x31, 0xa
+ bne x31, x10, reg1_error_loop
+ li x31, 0xb
+ bne x31, x11, reg1_error_loop
+ li x31, 0xc
+ bne x31, x12, reg1_error_loop
+ li x31, 0xd
+ bne x31, x13, reg1_error_loop
+ li x31, 0xe
+ bne x31, x14, reg1_error_loop
+ li x31, 0xf
+ bne x31, x15, reg1_error_loop
+ li x31, 0x10
+ bne x31, x16, reg1_error_loop
+ li x31, 0x11
+ bne x31, x17, reg1_error_loop
+ li x31, 0x12
+ bne x31, x18, reg1_error_loop
+ li x31, 0x13
+ bne x31, x19, reg1_error_loop
+ li x31, 0x14
+ bne x31, x20, reg1_error_loop
+ li x31, 0x15
+ bne x31, x21, reg1_error_loop
+ li x31, 0x16
+ bne x31, x22, reg1_error_loop
+ li x31, 0x17
+ bne x31, x23, reg1_error_loop
+ li x31, 0x18
+ bne x31, x24, reg1_error_loop
+ li x31, 0x19
+ bne x31, x25, reg1_error_loop
+ li x31, 0x1a
+ bne x31, x26, reg1_error_loop
+ li x31, 0x1b
+ bne x31, x27, reg1_error_loop
+ li x31, 0x1c
+ bne x31, x28, reg1_error_loop
+ li x31, 0x1d
+ bne x31, x29, reg1_error_loop
+ li x31, 0x1e
+ bne x31, x30, reg1_error_loop
+
+ /* Everything passed, increment the loop counter. */
+ lw x31, ulRegTest1LoopCounterConst
+ lw x30, 0(x31)
+ addi x30, x30, 1
+ sw x30, 0(x31)
+
+ /* Restore clobbered register reading for next loop. */
+ li x30, 0x1e
+
+ /* Yield to increase code coverage. */
+ ecall
+
+ /* Start again. */
+ jal reg1_loop
+
+reg1_error_loop:
+ /* Jump here if a register contains an uxpected value. This stops the loop
+ counter being incremented so the check task knows an error was found. */
+ ebreak
+ jal reg1_error_loop
+
+.align( 4 )
+ulRegTest1LoopCounterConst: .word ulRegTest1LoopCounter
+
+/*-----------------------------------------------------------*/
+
+.align( 4 )
+vRegTest2Implementation:
+
+ /* Fill the core registers with known values. */
+ li x6, 0x61
+ li x7, 0x71
+ li x8, 0x81
+ li x9, 0x91
+ li x10, 0xa1
+ li x11, 0xb1
+ li x12, 0xc1
+ li x13, 0xd1
+ li x14, 0xe1
+ li x15, 0xf1
+ li x16, 0x20
+ li x17, 0x21
+ li x18, 0x22
+ li x19, 0x23
+ li x20, 0x24
+ li x21, 0x25
+ li x22, 0x26
+ li x23, 0x27
+ li x24, 0x28
+ li x25, 0x29
+ li x26, 0x2a
+ li x27, 0x2b
+ li x28, 0x2c
+ li x29, 0x2d
+ li x30, 0x2e
+ li x31, 0x2f
+
+Reg2_loop:
+
+ /* Check each register still contains the expected known value.
+ vRegTest2Implementation uses x5 as the temporary, vRegTest1Implementation
+ uses x31 as the temporary. */
+ li x5, 0x61
+ bne x5, x6, reg2_error_loop
+ li x5, 0x71
+ bne x5, x7, reg2_error_loop
+ li x5, 0x81
+ bne x5, x8, reg2_error_loop
+ li x5, 0x91
+ bne x5, x9, reg2_error_loop
+ li x5, 0xa1
+ bne x5, x10, reg2_error_loop
+ li x5, 0xb1
+ bne x5, x11, reg2_error_loop
+ li x5, 0xc1
+ bne x5, x12, reg2_error_loop
+ li x5, 0xd1
+ bne x5, x13, reg2_error_loop
+ li x5, 0xe1
+ bne x5, x14, reg2_error_loop
+ li x5, 0xf1
+ bne x5, x15, reg2_error_loop
+ li x5, 0x20
+ bne x5, x16, reg2_error_loop
+ li x5, 0x21
+ bne x5, x17, reg2_error_loop
+ li x5, 0x22
+ bne x5, x18, reg2_error_loop
+ li x5, 0x23
+ bne x5, x19, reg2_error_loop
+ li x5, 0x24
+ bne x5, x20, reg2_error_loop
+ li x5, 0x25
+ bne x5, x21, reg2_error_loop
+ li x5, 0x26
+ bne x5, x22, reg2_error_loop
+ li x5, 0x27
+ bne x5, x23, reg2_error_loop
+ li x5, 0x28
+ bne x5, x24, reg2_error_loop
+ li x5, 0x29
+ bne x5, x25, reg2_error_loop
+ li x5, 0x2a
+ bne x5, x26, reg2_error_loop
+ li x5, 0x2b
+ bne x5, x27, reg2_error_loop
+ li x5, 0x2c
+ bne x5, x28, reg2_error_loop
+ li x5, 0x2d
+ bne x5, x29, reg2_error_loop
+ li x5, 0x2e
+ bne x5, x30, reg2_error_loop
+ li x5, 0x2f
+ bne x5, x31, reg2_error_loop
+
+ /* Everything passed, increment the loop counter. */
+ lw x5, ulRegTest2LoopCounterConst
+ lw x6, 0(x5)
+ addi x6, x6, 1
+ sw x6, 0(x5)
+
+ /* Restore clobbered register reading for next loop. */
+ li x6, 0x61
+
+ /* Start again. */
+ jal Reg2_loop
+
+reg2_error_loop:
+ /* Jump here if a register contains an uxpected value. This stops the loop
+ counter being incremented so the check task knows an error was found. */
+ ebreak
+ jal reg2_error_loop
+
+.align( 4 )
+ulRegTest2LoopCounterConst: .word ulRegTest2LoopCounter
+
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/main_full.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/main_full.c
index d5b1d012b..f47e67962 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/main_full.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/full_demo/main_full.c
@@ -1,306 +1,313 @@
-/*
- * FreeRTOS V202104.00
- * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
-
-/******************************************************************************
- * NOTE 1: This project provides two demo applications. A simple blinky style
- * project, and a more comprehensive test and demo application. The
- * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select
- * between the two. See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY
- * in main.c. This file implements the comprehensive test and demo version.
- *
- * NOTE 2: This file only contains the source code that is specific to the
- * full demo. Generic functions, such FreeRTOS hook functions, and functions
- * required to configure the hardware, are defined in main.c.
- *
- ******************************************************************************
- *
- * main_full() creates all the demo application tasks and software timers, then
- * starts the scheduler. The web documentation provides more details of the
- * standard demo application tasks, which provide no particular functionality,
- * but do provide a good example of how to use the FreeRTOS API.
- *
- * In addition to the standard demo tasks, the following tasks and tests are
- * defined and/or created within this file:
- *
- * "Reg test" tasks - These fill both the core registers with known values, then
- * check that each register maintains its expected value for the lifetime of the
- * task. Each task uses a different set of values. The reg test tasks execute
- * with a very low priority, so get preempted very frequently. A register
- * containing an unexpected value is indicative of an error in the context
- * switching mechanism.
- *
- * "Check" task - The check executes every three seconds. It checks that all
- * the standard demo tasks, and the register check tasks, are not only still
- * executing, but are executing without reporting any errors. The check task
- * toggles the LED every three seconds if all the standard demo tasks are
- * executing as expected, or every 500ms if a potential error is discovered in
- * any task.
- */
-
-/* Standard includes. */
-#include <stdio.h>
-#include <string.h>
-#include <unistd.h>
-
-/* Kernel includes. */
-#include "FreeRTOS.h"
-#include "task.h"
-#include "timers.h"
-#include "semphr.h"
-
-/* Standard demo application includes. */
-#include "dynamic.h"
-#include "blocktim.h"
-#include "TimerDemo.h"
-#include "TaskNotify.h"
-
-/* Priorities for the demo application tasks. */
-#define mainCHECK_TASK_PRIORITY ( configMAX_PRIORITIES - 1 )
-
-/* The period of the check task, in ms, converted to ticks using the
-pdMS_TO_TICKS() macro. mainNO_ERROR_CHECK_TASK_PERIOD is used if no errors have
-been found, mainERROR_CHECK_TASK_PERIOD is used if an error has been found. */
-#define mainNO_ERROR_CHECK_TASK_PERIOD pdMS_TO_TICKS( 3000UL )
-#define mainERROR_CHECK_TASK_PERIOD pdMS_TO_TICKS( 500UL )
-
-/* Parameters that are passed into the register check tasks solely for the
-purpose of ensuring parameters are passed into tasks correctly. */
-#define mainREG_TEST_TASK_1_PARAMETER ( ( void * ) 0x12345678 )
-#define mainREG_TEST_TASK_2_PARAMETER ( ( void * ) 0x87654321 )
-
-/* The base period used by the timer test tasks. */
-#define mainTIMER_TEST_PERIOD ( 50 )
-
-/* The size of the stack allocated to the check task (as described in the
-comments at the top of this file. */
-#define mainCHECK_TASK_STACK_SIZE_WORDS 160
-
-/* Size of the stacks to allocated for the register check tasks. */
-#define mainREG_TEST_STACK_SIZE_WORDS 90
-
-/*-----------------------------------------------------------*/
-
-/*
- * Called by main() to run the full demo (as opposed to the blinky demo) when
- * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 0.
- */
-void main_full( void );
-
-/*
- * The check task, as described at the top of this file.
- */
-static void prvCheckTask( void *pvParameters );
-
-/*
- * Register check tasks as described at the top of this file. The nature of
- * these files necessitates that they are written in an assembly file, but the
- * entry points are kept in the C file for the convenience of checking the task
- * parameter.
- */
-static void prvRegTestTaskEntry1( void *pvParameters );
-extern void vRegTest1Implementation( void );
-static void prvRegTestTaskEntry2( void *pvParameters );
-extern void vRegTest2Implementation( void );
-
-/*
- * Tick hook used by the full demo, which includes code that interacts with
- * some of the tests.
- */
-void vFullDemoTickHook( void );
-
-/*-----------------------------------------------------------*/
-
-/* The following two variables are used to communicate the status of the
-register check tasks to the check task. If the variables keep incrementing,
-then the register check tasks have not discovered any errors. If a variable
-stops incrementing, then an error has been found. */
-uint32_t ulRegTest1LoopCounter = 0UL, ulRegTest2LoopCounter = 0UL;
-volatile uint32_t *pulRegTest1LoopCounter = &ulRegTest1LoopCounter;
-volatile uint32_t *pulRegTest2LoopCounter = &ulRegTest2LoopCounter;
-/*-----------------------------------------------------------*/
-
-void main_full( void )
-{
- /* Start all the other standard demo/test tasks. They have no particular
- functionality, but do demonstrate how to use the FreeRTOS API and test the
- kernel port. */
- vCreateBlockTimeTasks();
- vStartTimerDemoTask( mainTIMER_TEST_PERIOD );
- vStartDynamicPriorityTasks();
- vStartTaskNotifyTask();
-
- /* Create the register check tasks, as described at the top of this file.
- Use xTaskCreateStatic() to create a task using only statically allocated
- memory. */
- xTaskCreate( prvRegTestTaskEntry1, /* The function that implements the task. */
- "Reg1", /* The name of the task. */
- mainREG_TEST_STACK_SIZE_WORDS, /* Size of stack to allocate for the task - in words not bytes!. */
- mainREG_TEST_TASK_1_PARAMETER, /* Parameter passed into the task. */
- tskIDLE_PRIORITY, /* Priority of the task. */
- NULL ); /* Can be used to pass out a handle to the created task. */
- xTaskCreate( prvRegTestTaskEntry2, "Reg2", mainREG_TEST_STACK_SIZE_WORDS, mainREG_TEST_TASK_2_PARAMETER, tskIDLE_PRIORITY, NULL );
-
- /* Create the task that performs the 'check' functionality, as described at
- the top of this file. */
- xTaskCreate( prvCheckTask, "Check", mainCHECK_TASK_STACK_SIZE_WORDS, NULL, mainCHECK_TASK_PRIORITY, NULL );
-
- /* Start the scheduler. */
- vTaskStartScheduler();
-
- /* If all is well, the scheduler will now be running, and the following
- line will never be reached. If the following line does execute, then
- there was insufficient FreeRTOS heap memory available for the Idle and/or
- timer tasks to be created. See the memory management section on the
- FreeRTOS web site for more details on the FreeRTOS heap
- http://www.freertos.org/a00111.html. */
- for( ;; );
-}
-/*-----------------------------------------------------------*/
-
-static void prvCheckTask( void *pvParameters )
-{
-TickType_t xDelayPeriod = mainNO_ERROR_CHECK_TASK_PERIOD;
-TickType_t xLastExecutionTime;
-uint32_t ulLastRegTest1Value = 0, ulLastRegTest2Value = 0;
-char * const pcPassMessage = ".";
-char * pcStatusMessage = pcPassMessage;
-extern void vToggleLED( void );
-
- /* Just to stop compiler warnings. */
- ( void ) pvParameters;
-
- /* Initialise xLastExecutionTime so the first call to vTaskDelayUntil()
- works correctly. */
- xLastExecutionTime = xTaskGetTickCount();
-
- /* Cycle for ever, delaying then checking all the other tasks are still
- operating without error. The onboard LED is toggled on each iteration.
- If an error is detected then the delay period is decreased from
- mainNO_ERROR_CHECK_TASK_PERIOD to mainERROR_CHECK_TASK_PERIOD. This has the
- effect of increasing the rate at which the onboard LED toggles, and in so
- doing gives visual feedback of the system status. */
- for( ;; )
- {
- /* Delay until it is time to execute again. */
- vTaskDelayUntil( &xLastExecutionTime, xDelayPeriod );
-
- /* Check all the demo tasks (other than the flash tasks) to ensure
- that they are all still running, and that none have detected an error. */
- if( xAreDynamicPriorityTasksStillRunning() == pdFALSE )
- {
- pcStatusMessage = "ERROR: Dynamic priority demo/tests.\r\n";
- }
-
- if( xAreBlockTimeTestTasksStillRunning() == pdFALSE )
- {
- pcStatusMessage = "ERROR: Block time demo/tests.\r\n";
- }
-
- if( xAreTimerDemoTasksStillRunning( ( TickType_t ) xDelayPeriod ) == pdFALSE )
- {
- pcStatusMessage = "ERROR: Timer demo/tests.\r\n";
- }
-
- if( xAreTaskNotificationTasksStillRunning() == pdFALSE )
- {
- pcStatusMessage = "ERROR: Task notification demo/tests.\r\n";
- }
-
- /* Check that the register test 1 task is still running. */
- if( ulLastRegTest1Value == ulRegTest1LoopCounter )
- {
- pcStatusMessage = "ERROR: Register test 1.\r\n";
- }
- ulLastRegTest1Value = ulRegTest1LoopCounter;
-
- /* Check that the register test 2 task is still running. */
- if( ulLastRegTest2Value == ulRegTest2LoopCounter )
- {
- pcStatusMessage = "ERROR: Register test 2.\r\n";
- }
- ulLastRegTest2Value = ulRegTest2LoopCounter;
-
- /* Write the status message to the UART and toggle the LED to show the
- system status if the UART is not connected. */
- vToggleLED();
-
- /* If an error has been found then increase the LED toggle rate by
- increasing the cycle frequency. */
- if( pcStatusMessage != pcPassMessage )
- {
- xDelayPeriod = mainERROR_CHECK_TASK_PERIOD;
- }
- }
-}
-/*-----------------------------------------------------------*/
-
-static void prvRegTestTaskEntry1( void *pvParameters )
-{
- /* Although the regtest task is written in assembler, its entry point is
- written in C for convenience of checking the task parameter is being passed
- in correctly. */
- if( pvParameters == mainREG_TEST_TASK_1_PARAMETER )
- {
- /* Start the part of the test that is written in assembler. */
- vRegTest1Implementation();
- }
-
- /* The following line will only execute if the task parameter is found to
- be incorrect. The check task will detect that the regtest loop counter is
- not being incremented and flag an error. */
- vTaskDelete( NULL );
-}
-/*-----------------------------------------------------------*/
-
-static void prvRegTestTaskEntry2( void *pvParameters )
-{
- /* Although the regtest task is written in assembler, its entry point is
- written in C for convenience of checking the task parameter is being passed
- in correctly. */
- if( pvParameters == mainREG_TEST_TASK_2_PARAMETER )
- {
- /* Start the part of the test that is written in assembler. */
- vRegTest2Implementation();
- }
-
- /* The following line will only execute if the task parameter is found to
- be incorrect. The check task will detect that the regtest loop counter is
- not being incremented and flag an error. */
- vTaskDelete( NULL );
-}
-/*-----------------------------------------------------------*/
-
-void vFullDemoTickHook( void )
-{
- /* Called from vApplicationTickHook() when the project is configured to
- build the full test/demo applications. */
-
- /* Use task notifications from an interrupt. */
- xNotifyTaskFromISR();
-}
-/*-----------------------------------------------------------*/
-
+/*
+ * FreeRTOS V202104.00
+ * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of
+ * this software and associated documentation files (the "Software"), to deal in
+ * the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+ * the Software, and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+ * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+ * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+ * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ * http://www.FreeRTOS.org
+ * http://aws.amazon.com/freertos
+ *
+ * 1 tab == 4 spaces!
+ */
+
+/******************************************************************************
+ * NOTE 1: This project provides two demo applications. A simple blinky style
+ * project, and a more comprehensive test and demo application. The
+ * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select
+ * between the two. See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY
+ * in main.c. This file implements the comprehensive test and demo version.
+ *
+ * NOTE 2: This file only contains the source code that is specific to the
+ * full demo. Generic functions, such FreeRTOS hook functions, and functions
+ * required to configure the hardware, are defined in main.c.
+ *
+ ******************************************************************************
+ *
+ * main_full() creates all the demo application tasks and software timers, then
+ * starts the scheduler. The web documentation provides more details of the
+ * standard demo application tasks, which provide no particular functionality,
+ * but do provide a good example of how to use the FreeRTOS API.
+ *
+ * In addition to the standard demo tasks, the following tasks and tests are
+ * defined and/or created within this file:
+ *
+ * "Reg test" tasks - These fill both the core registers with known values, then
+ * check that each register maintains its expected value for the lifetime of the
+ * task. Each task uses a different set of values. The reg test tasks execute
+ * with a very low priority, so get preempted very frequently. A register
+ * containing an unexpected value is indicative of an error in the context
+ * switching mechanism.
+ *
+ * "Check" task - The check executes every three seconds. It checks that all
+ * the standard demo tasks, and the register check tasks, are not only still
+ * executing, but are executing without reporting any errors. The check task
+ * toggles the LED every three seconds if all the standard demo tasks are
+ * executing as expected, or every 500ms if a potential error is discovered in
+ * any task.
+ */
+
+/* Standard includes. */
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+
+/* Kernel includes. */
+#include "FreeRTOS.h"
+#include "task.h"
+#include "timers.h"
+#include "semphr.h"
+
+/* Standard demo application includes. */
+#include "dynamic.h"
+#include "blocktim.h"
+#include "TimerDemo.h"
+#include "TaskNotify.h"
+
+/* Priorities for the demo application tasks. */
+#define mainCHECK_TASK_PRIORITY ( configMAX_PRIORITIES - 1 )
+
+/* The period of the check task, in ms, converted to ticks using the
+pdMS_TO_TICKS() macro. mainNO_ERROR_CHECK_TASK_PERIOD is used if no errors have
+been found, mainERROR_CHECK_TASK_PERIOD is used if an error has been found. */
+#define mainNO_ERROR_CHECK_TASK_PERIOD pdMS_TO_TICKS( 3000UL )
+#define mainERROR_CHECK_TASK_PERIOD pdMS_TO_TICKS( 500UL )
+
+/* Parameters that are passed into the register check tasks solely for the
+purpose of ensuring parameters are passed into tasks correctly. */
+#define mainREG_TEST_TASK_1_PARAMETER ( ( void * ) 0x12345678 )
+#define mainREG_TEST_TASK_2_PARAMETER ( ( void * ) 0x87654321 )
+
+/* The base period used by the timer test tasks. */
+#define mainTIMER_TEST_PERIOD ( 50 )
+
+/* The size of the stack allocated to the check task (as described in the
+comments at the top of this file. */
+#define mainCHECK_TASK_STACK_SIZE_WORDS 160
+
+/* Size of the stacks to allocated for the register check tasks. */
+#define mainREG_TEST_STACK_SIZE_WORDS 90
+
+/* Success output messages. This is used by the CI - do not change. */
+#define mainDEMO_SUCCESS_MESSAGE "FreeRTOS Demo SUCCESS\r\n"
+/*-----------------------------------------------------------*/
+
+/*
+ * Called by main() to run the full demo (as opposed to the blinky demo) when
+ * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 0.
+ */
+void main_full( void );
+
+/*
+ * The check task, as described at the top of this file.
+ */
+static void prvCheckTask( void *pvParameters );
+
+/*
+ * Register check tasks as described at the top of this file. The nature of
+ * these files necessitates that they are written in an assembly file, but the
+ * entry points are kept in the C file for the convenience of checking the task
+ * parameter.
+ */
+static void prvRegTestTaskEntry1( void *pvParameters );
+extern void vRegTest1Implementation( void );
+static void prvRegTestTaskEntry2( void *pvParameters );
+extern void vRegTest2Implementation( void );
+
+/*
+ * Tick hook used by the full demo, which includes code that interacts with
+ * some of the tests.
+ */
+void vFullDemoTickHook( void );
+
+/*-----------------------------------------------------------*/
+
+/* The following two variables are used to communicate the status of the
+register check tasks to the check task. If the variables keep incrementing,
+then the register check tasks have not discovered any errors. If a variable
+stops incrementing, then an error has been found. */
+uint32_t ulRegTest1LoopCounter = 0UL, ulRegTest2LoopCounter = 0UL;
+volatile uint32_t *pulRegTest1LoopCounter = &ulRegTest1LoopCounter;
+volatile uint32_t *pulRegTest2LoopCounter = &ulRegTest2LoopCounter;
+/*-----------------------------------------------------------*/
+
+void main_full( void )
+{
+ /* Start all the other standard demo/test tasks. They have no particular
+ functionality, but do demonstrate how to use the FreeRTOS API and test the
+ kernel port. */
+ vCreateBlockTimeTasks();
+ vStartTimerDemoTask( mainTIMER_TEST_PERIOD );
+ vStartDynamicPriorityTasks();
+ vStartTaskNotifyTask();
+
+ /* Create the register check tasks, as described at the top of this file.
+ Use xTaskCreateStatic() to create a task using only statically allocated
+ memory. */
+ xTaskCreate( prvRegTestTaskEntry1, /* The function that implements the task. */
+ "Reg1", /* The name of the task. */
+ mainREG_TEST_STACK_SIZE_WORDS, /* Size of stack to allocate for the task - in words not bytes!. */
+ mainREG_TEST_TASK_1_PARAMETER, /* Parameter passed into the task. */
+ tskIDLE_PRIORITY, /* Priority of the task. */
+ NULL ); /* Can be used to pass out a handle to the created task. */
+ xTaskCreate( prvRegTestTaskEntry2, "Reg2", mainREG_TEST_STACK_SIZE_WORDS, mainREG_TEST_TASK_2_PARAMETER, tskIDLE_PRIORITY, NULL );
+
+ /* Create the task that performs the 'check' functionality, as described at
+ the top of this file. */
+ xTaskCreate( prvCheckTask, "Check", mainCHECK_TASK_STACK_SIZE_WORDS, NULL, mainCHECK_TASK_PRIORITY, NULL );
+
+ /* Start the scheduler. */
+ vTaskStartScheduler();
+
+ /* If all is well, the scheduler will now be running, and the following
+ line will never be reached. If the following line does execute, then
+ there was insufficient FreeRTOS heap memory available for the Idle and/or
+ timer tasks to be created. See the memory management section on the
+ FreeRTOS web site for more details on the FreeRTOS heap
+ http://www.freertos.org/a00111.html. */
+ for( ;; );
+}
+/*-----------------------------------------------------------*/
+
+static void prvCheckTask( void *pvParameters )
+{
+TickType_t xDelayPeriod = mainNO_ERROR_CHECK_TASK_PERIOD;
+TickType_t xLastExecutionTime;
+uint32_t ulLastRegTest1Value = 0, ulLastRegTest2Value = 0;
+char * const pcPassMessage = mainDEMO_SUCCESS_MESSAGE;
+char * pcStatusMessage = pcPassMessage;
+extern void vToggleLED( void );
+
+ /* Just to stop compiler warnings. */
+ ( void ) pvParameters;
+
+ /* Demo start marker. */
+ configPRINT_STRING( "FreeRTOS Demo Start\r\n" );
+
+ /* Initialise xLastExecutionTime so the first call to vTaskDelayUntil()
+ works correctly. */
+ xLastExecutionTime = xTaskGetTickCount();
+
+ /* Cycle for ever, delaying then checking all the other tasks are still
+ operating without error. The onboard LED is toggled on each iteration.
+ If an error is detected then the delay period is decreased from
+ mainNO_ERROR_CHECK_TASK_PERIOD to mainERROR_CHECK_TASK_PERIOD. This has the
+ effect of increasing the rate at which the onboard LED toggles, and in so
+ doing gives visual feedback of the system status. */
+ for( ;; )
+ {
+ /* Delay until it is time to execute again. */
+ vTaskDelayUntil( &xLastExecutionTime, xDelayPeriod );
+
+ /* Check all the demo tasks (other than the flash tasks) to ensure
+ that they are all still running, and that none have detected an error. */
+ if( xAreDynamicPriorityTasksStillRunning() == pdFALSE )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Dynamic priority demo/tests.\r\n";
+ }
+
+ if( xAreBlockTimeTestTasksStillRunning() == pdFALSE )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Block time demo/tests.\r\n";
+ }
+
+ if( xAreTimerDemoTasksStillRunning( ( TickType_t ) xDelayPeriod ) == pdFALSE )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Timer demo/tests.\r\n";
+ }
+
+ if( xAreTaskNotificationTasksStillRunning() == pdFALSE )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Task notification demo/tests.\r\n";
+ }
+
+ /* Check that the register test 1 task is still running. */
+ if( ulLastRegTest1Value == ulRegTest1LoopCounter )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Register test 1.\r\n";
+ }
+ ulLastRegTest1Value = ulRegTest1LoopCounter;
+
+ /* Check that the register test 2 task is still running. */
+ if( ulLastRegTest2Value == ulRegTest2LoopCounter )
+ {
+ pcStatusMessage = "FreeRTOS Demo ERROR: Register test 2.\r\n";
+ }
+ ulLastRegTest2Value = ulRegTest2LoopCounter;
+
+ /* Write the status message to the UART and toggle the LED to show the
+ system status if the UART is not connected. */
+ vToggleLED();
+
+ /* If an error has been found then increase the LED toggle rate by
+ increasing the cycle frequency. */
+ if( pcStatusMessage != pcPassMessage )
+ {
+ xDelayPeriod = mainERROR_CHECK_TASK_PERIOD;
+ }
+
+ configPRINT_STRING( pcStatusMessage );
+ }
+}
+/*-----------------------------------------------------------*/
+
+static void prvRegTestTaskEntry1( void *pvParameters )
+{
+ /* Although the regtest task is written in assembler, its entry point is
+ written in C for convenience of checking the task parameter is being passed
+ in correctly. */
+ if( pvParameters == mainREG_TEST_TASK_1_PARAMETER )
+ {
+ /* Start the part of the test that is written in assembler. */
+ vRegTest1Implementation();
+ }
+
+ /* The following line will only execute if the task parameter is found to
+ be incorrect. The check task will detect that the regtest loop counter is
+ not being incremented and flag an error. */
+ vTaskDelete( NULL );
+}
+/*-----------------------------------------------------------*/
+
+static void prvRegTestTaskEntry2( void *pvParameters )
+{
+ /* Although the regtest task is written in assembler, its entry point is
+ written in C for convenience of checking the task parameter is being passed
+ in correctly. */
+ if( pvParameters == mainREG_TEST_TASK_2_PARAMETER )
+ {
+ /* Start the part of the test that is written in assembler. */
+ vRegTest2Implementation();
+ }
+
+ /* The following line will only execute if the task parameter is found to
+ be incorrect. The check task will detect that the regtest loop counter is
+ not being incremented and flag an error. */
+ vTaskDelete( NULL );
+}
+/*-----------------------------------------------------------*/
+
+void vFullDemoTickHook( void )
+{
+ /* Called from vApplicationTickHook() when the project is configured to
+ build the full test/demo applications. */
+
+ /* Use task notifications from an interrupt. */
+ xNotifyTaskFromISR();
+}
+/*-----------------------------------------------------------*/
+
diff --git a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/main.c b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/main.c
index 7142850fc..0ddf8a93a 100644
--- a/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/main.c
+++ b/FreeRTOS/Demo/RISC-V_RV32_SiFive_HiFive1-RevB_FreedomStudio/main.c
@@ -1,271 +1,271 @@
-/*
- * FreeRTOS V202104.00
- * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
-
-/******************************************************************************
- * This project provides two demo applications. A simple blinky style project,
- * and a more comprehensive test and demo application. The
- * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting (defined in this file) is used to
- * select between the two. The simply blinky demo is implemented and described
- * in main_blinky.c. The more comprehensive test and demo application is
- * implemented and described in main_full.c.
- *
- * This file implements the code that is not demo specific, including the
- * hardware setup and standard FreeRTOS hook functions.
- *
- * When running on the HiFive Rev B hardware:
- * When executing correctly the blue LED will toggle every three seconds. If
- * the blue LED toggles every 500ms then one of the self-monitoring test tasks
- * discovered a potential issue. If the red led toggles rapidly then a hardware
- * exception occurred.
- *
- * ENSURE TO READ THE DOCUMENTATION PAGE FOR THIS PORT AND DEMO APPLICATION ON
- * THE http://www.FreeRTOS.org WEB SITE FOR FULL INFORMATION ON USING THIS DEMO
- * APPLICATION, AND ITS ASSOCIATE FreeRTOS ARCHITECTURE PORT!
- *
- */
-
-/* FreeRTOS kernel includes. */
-#include <FreeRTOS.h>
-#include <task.h>
-
-/* Freedom metal driver includes. */
-#include <metal/cpu.h>
-#include <metal/led.h>
-
-/* Set mainCREATE_SIMPLE_BLINKY_DEMO_ONLY to one to run the simple blinky demo,
-or 0 to run the more comprehensive test and demo application. */
-#define mainCREATE_SIMPLE_BLINKY_DEMO_ONLY 0
-
-/* Index to first HART (there is only one). */
-#define mainHART_0 0
-
-/* Registers used to initialise the PLIC. */
-#define mainPLIC_PENDING_0 ( * ( ( volatile uint32_t * ) 0x0C001000UL ) )
-#define mainPLIC_PENDING_1 ( * ( ( volatile uint32_t * ) 0x0C001004UL ) )
-#define mainPLIC_ENABLE_0 ( * ( ( volatile uint32_t * ) 0x0C002000UL ) )
-#define mainPLIC_ENABLE_1 ( * ( ( volatile uint32_t * ) 0x0C002004UL ) )
-
-/*-----------------------------------------------------------*/
-
-/*
- * main_blinky() is used when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1.
- * main_full() is used when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 0.
- */
-#if mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1
- extern void main_blinky( void );
-#else
- extern void main_full( void );
-#endif /* #if mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1 */
-
-/*
- * Prototypes for the standard FreeRTOS callback/hook functions implemented
- * within this file. See https://www.freertos.org/a00016.html
- */
-void vApplicationMallocFailedHook( void );
-void vApplicationIdleHook( void );
-void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName );
-void vApplicationTickHook( void );
-
-/*
- * Setup the hardware to run this demo.
- */
-static void prvSetupHardware( void );
-
-/*
- * Used by the Freedom Metal drivers.
- */
-static struct metal_led *pxBlueLED = NULL;
-
-/*-----------------------------------------------------------*/
-
-int main( void )
-{
- prvSetupHardware();
-
- /* The mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting is described at the top
- of this file. */
- #if( mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1 )
- {
- main_blinky();
- }
- #else
- {
- main_full();
- }
- #endif
-}
-/*-----------------------------------------------------------*/
-
-static void prvSetupHardware( void )
-{
-struct metal_cpu *pxCPU;
-struct metal_interrupt *pxInterruptController;
-
- /* Initialise the blue LED. */
- pxBlueLED = metal_led_get_rgb( "LD0", "blue" );
- configASSERT( pxBlueLED );
- metal_led_enable( pxBlueLED );
- metal_led_off( pxBlueLED );
-
- /* Initialise the interrupt controller. */
- pxCPU = metal_cpu_get( mainHART_0 );
- configASSERT( pxCPU );
- pxInterruptController = metal_cpu_interrupt_controller( pxCPU );
- configASSERT( pxInterruptController );
- metal_interrupt_init( pxInterruptController );
-
- /* Set all interrupt enable bits to 0. */
- mainPLIC_ENABLE_0 = 0UL;
- mainPLIC_ENABLE_1 = 0UL;
-}
-/*-----------------------------------------------------------*/
-
-void vApplicationMallocFailedHook( void )
-{
- /* vApplicationMallocFailedHook() will only be called if
- configUSE_MALLOC_FAILED_HOOK is set to 1 in FreeRTOSConfig.h. It is a hook
- function that will get called if a call to pvPortMalloc() fails.
- pvPortMalloc() is called internally by the kernel whenever a task, queue,
- timer or semaphore is created. It is also called by various parts of the
- demo application. If heap_1.c or heap_2.c are used, then the size of the
- heap available to pvPortMalloc() is defined by configTOTAL_HEAP_SIZE in
- FreeRTOSConfig.h, and the xPortGetFreeHeapSize() API function can be used
- to query the size of free heap space that remains (although it does not
- provide information on how the remaining heap might be fragmented). */
- taskDISABLE_INTERRUPTS();
- for( ;; );
-}
-/*-----------------------------------------------------------*/
-
-void vApplicationIdleHook( void )
-{
- /* vApplicationIdleHook() will only be called if configUSE_IDLE_HOOK is set
- to 1 in FreeRTOSConfig.h. It will be called on each iteration of the idle
- task. It is essential that code added to this hook function never attempts
- to block in any way (for example, call xQueueReceive() with a block time
- specified, or call vTaskDelay()). If the application makes use of the
- vTaskDelete() API function (as this demo application does) then it is also
- important that vApplicationIdleHook() is permitted to return to its calling
- function, because it is the responsibility of the idle task to clean up
- memory allocated by the kernel to any task that has since been deleted. */
-}
-/*-----------------------------------------------------------*/
-
-void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName )
-{
- ( void ) pcTaskName;
- ( void ) pxTask;
-
- /* Run time stack overflow checking is performed if
- configCHECK_FOR_STACK_OVERFLOW is defined to 1 or 2. This hook
- function is called if a stack overflow is detected. */
- taskDISABLE_INTERRUPTS();
- for( ;; );
-}
-/*-----------------------------------------------------------*/
-
-void vApplicationTickHook( void )
-{
- /* The tests in the full demo expect some interaction with interrupts. */
- #if( mainCREATE_SIMPLE_BLINKY_DEMO_ONLY != 1 )
- {
- extern void vFullDemoTickHook( void );
- vFullDemoTickHook();
- }
- #endif
-}
-/*-----------------------------------------------------------*/
-
-void vAssertCalled( void )
-{
-static struct metal_led *pxRedLED = NULL;
-volatile uint32_t ul;
-const uint32_t ulNullLoopDelay = 0x1ffffUL;
-
- taskDISABLE_INTERRUPTS();
-
- /* Initialise the red LED. */
- pxRedLED = metal_led_get_rgb( "LD0", "red" );
- configASSERT( pxRedLED );
- metal_led_enable( pxRedLED );
- metal_led_off( pxRedLED );
-
- /* Flash the red LED to indicate that assert was hit - interrupts are off
- here to prevent any further tick interrupts or context switches, so the
- delay is implemented as a crude loop instead of a peripheral timer. */
- for( ;; )
- {
- for( ul = 0; ul < ulNullLoopDelay; ul++ )
- {
- __asm volatile( "nop" );
- }
- metal_led_toggle( pxRedLED );
- }
-}
-/*-----------------------------------------------------------*/
-
-void handle_trap( void )
-{
-volatile uint32_t ulMEPC = 0UL, ulMCAUSE = 0UL, ulPLICPending0Register = 0UL, ulPLICPending1Register = 0UL;
-
- /* Store a few register values that might be useful when determining why this
- function was called. */
- __asm volatile( "csrr %0, mepc" : "=r"( ulMEPC ) );
- __asm volatile( "csrr %0, mcause" : "=r"( ulMCAUSE ) );
- ulPLICPending0Register = mainPLIC_PENDING_0;
- ulPLICPending1Register = mainPLIC_PENDING_1;
-
- /* Prevent compiler warnings about unused variables. */
- ( void ) ulPLICPending0Register;
- ( void ) ulPLICPending1Register;
-
- /* Force an assert as this function has not been implemented as the demo
- does not use external interrupts. */
- configASSERT( metal_cpu_get( mainHART_0 ) == 0x00 );
-}
-/*-----------------------------------------------------------*/
-
-void vToggleLED( void )
-{
- metal_led_toggle( pxBlueLED );
-}
-/*-----------------------------------------------------------*/
-
-void *malloc( size_t xSize )
-{
- /* The linker script does not define a heap so artificially force an assert()
- if something unexpectedly uses the C library heap. See
- https://www.freertos.org/a00111.html for more information. */
- configASSERT( metal_cpu_get( mainHART_0 ) == 0x00 );
-
- /* Remove warnings about unused parameter. */
- ( void ) xSize;
- return NULL;
-}
-/*-----------------------------------------------------------*/
-
-
+/*
+ * FreeRTOS V202104.00
+ * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy of
+ * this software and associated documentation files (the "Software"), to deal in
+ * the Software without restriction, including without limitation the rights to
+ * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+ * the Software, and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+ * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+ * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+ * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ *
+ * http://www.FreeRTOS.org
+ * http://aws.amazon.com/freertos
+ *
+ * 1 tab == 4 spaces!
+ */
+
+/******************************************************************************
+ * This project provides two demo applications. A simple blinky style project,
+ * and a more comprehensive test and demo application. The
+ * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting (defined in this file) is used to
+ * select between the two. The simply blinky demo is implemented and described
+ * in main_blinky.c. The more comprehensive test and demo application is
+ * implemented and described in main_full.c.
+ *
+ * This file implements the code that is not demo specific, including the
+ * hardware setup and standard FreeRTOS hook functions.
+ *
+ * When running on the HiFive Rev B hardware:
+ * When executing correctly the blue LED will toggle every three seconds. If
+ * the blue LED toggles every 500ms then one of the self-monitoring test tasks
+ * discovered a potential issue. If the red led toggles rapidly then a hardware
+ * exception occurred.
+ *
+ * ENSURE TO READ THE DOCUMENTATION PAGE FOR THIS PORT AND DEMO APPLICATION ON
+ * THE http://www.FreeRTOS.org WEB SITE FOR FULL INFORMATION ON USING THIS DEMO
+ * APPLICATION, AND ITS ASSOCIATE FreeRTOS ARCHITECTURE PORT!
+ *
+ */
+
+/* FreeRTOS kernel includes. */
+#include <FreeRTOS.h>
+#include <task.h>
+
+/* Freedom metal driver includes. */
+#include <metal/cpu.h>
+#include <metal/led.h>
+
+/* Set mainCREATE_SIMPLE_BLINKY_DEMO_ONLY to one to run the simple blinky demo,
+or 0 to run the more comprehensive test and demo application. */
+#define mainCREATE_SIMPLE_BLINKY_DEMO_ONLY 0
+
+/* Index to first HART (there is only one). */
+#define mainHART_0 0
+
+/* Registers used to initialise the PLIC. */
+#define mainPLIC_PENDING_0 ( * ( ( volatile uint32_t * ) 0x0C001000UL ) )
+#define mainPLIC_PENDING_1 ( * ( ( volatile uint32_t * ) 0x0C001004UL ) )
+#define mainPLIC_ENABLE_0 ( * ( ( volatile uint32_t * ) 0x0C002000UL ) )
+#define mainPLIC_ENABLE_1 ( * ( ( volatile uint32_t * ) 0x0C002004UL ) )
+
+/*-----------------------------------------------------------*/
+
+/*
+ * main_blinky() is used when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1.
+ * main_full() is used when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 0.
+ */
+#if mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1
+ extern void main_blinky( void );
+#else
+ extern void main_full( void );
+#endif /* #if mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1 */
+
+/*
+ * Prototypes for the standard FreeRTOS callback/hook functions implemented
+ * within this file. See https://www.freertos.org/a00016.html
+ */
+void vApplicationMallocFailedHook( void );
+void vApplicationIdleHook( void );
+void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName );
+void vApplicationTickHook( void );
+
+/*
+ * Setup the hardware to run this demo.
+ */
+static void prvSetupHardware( void );
+
+/*
+ * Used by the Freedom Metal drivers.
+ */
+static struct metal_led *pxBlueLED = NULL;
+
+/*-----------------------------------------------------------*/
+
+int main( void )
+{
+ prvSetupHardware();
+
+ /* The mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting is described at the top
+ of this file. */
+ #if( mainCREATE_SIMPLE_BLINKY_DEMO_ONLY == 1 )
+ {
+ main_blinky();
+ }
+ #else
+ {
+ main_full();
+ }
+ #endif
+}
+/*-----------------------------------------------------------*/
+
+static void prvSetupHardware( void )
+{
+struct metal_cpu *pxCPU;
+struct metal_interrupt *pxInterruptController;
+
+ /* Initialise the blue LED. */
+ pxBlueLED = metal_led_get_rgb( "LD0", "blue" );
+ configASSERT( pxBlueLED );
+ metal_led_enable( pxBlueLED );
+ metal_led_off( pxBlueLED );
+
+ /* Initialise the interrupt controller. */
+ pxCPU = metal_cpu_get( mainHART_0 );
+ configASSERT( pxCPU );
+ pxInterruptController = metal_cpu_interrupt_controller( pxCPU );
+ configASSERT( pxInterruptController );
+ metal_interrupt_init( pxInterruptController );
+
+ /* Set all interrupt enable bits to 0. */
+ mainPLIC_ENABLE_0 = 0UL;
+ mainPLIC_ENABLE_1 = 0UL;
+}
+/*-----------------------------------------------------------*/
+
+void vApplicationMallocFailedHook( void )
+{
+ /* vApplicationMallocFailedHook() will only be called if
+ configUSE_MALLOC_FAILED_HOOK is set to 1 in FreeRTOSConfig.h. It is a hook
+ function that will get called if a call to pvPortMalloc() fails.
+ pvPortMalloc() is called internally by the kernel whenever a task, queue,
+ timer or semaphore is created. It is also called by various parts of the
+ demo application. If heap_1.c or heap_2.c are used, then the size of the
+ heap available to pvPortMalloc() is defined by configTOTAL_HEAP_SIZE in
+ FreeRTOSConfig.h, and the xPortGetFreeHeapSize() API function can be used
+ to query the size of free heap space that remains (although it does not
+ provide information on how the remaining heap might be fragmented). */
+ taskDISABLE_INTERRUPTS();
+ for( ;; );
+}
+/*-----------------------------------------------------------*/
+
+void vApplicationIdleHook( void )
+{
+ /* vApplicationIdleHook() will only be called if configUSE_IDLE_HOOK is set
+ to 1 in FreeRTOSConfig.h. It will be called on each iteration of the idle
+ task. It is essential that code added to this hook function never attempts
+ to block in any way (for example, call xQueueReceive() with a block time
+ specified, or call vTaskDelay()). If the application makes use of the
+ vTaskDelete() API function (as this demo application does) then it is also
+ important that vApplicationIdleHook() is permitted to return to its calling
+ function, because it is the responsibility of the idle task to clean up
+ memory allocated by the kernel to any task that has since been deleted. */
+}
+/*-----------------------------------------------------------*/
+
+void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName )
+{
+ ( void ) pcTaskName;
+ ( void ) pxTask;
+
+ /* Run time stack overflow checking is performed if
+ configCHECK_FOR_STACK_OVERFLOW is defined to 1 or 2. This hook
+ function is called if a stack overflow is detected. */
+ taskDISABLE_INTERRUPTS();
+ for( ;; );
+}
+/*-----------------------------------------------------------*/
+
+void vApplicationTickHook( void )
+{
+ /* The tests in the full demo expect some interaction with interrupts. */
+ #if( mainCREATE_SIMPLE_BLINKY_DEMO_ONLY != 1 )
+ {
+ extern void vFullDemoTickHook( void );
+ vFullDemoTickHook();
+ }
+ #endif
+}
+/*-----------------------------------------------------------*/
+
+void vAssertCalled( void )
+{
+static struct metal_led *pxRedLED = NULL;
+volatile uint32_t ul;
+const uint32_t ulNullLoopDelay = 0x1ffffUL;
+
+ taskDISABLE_INTERRUPTS();
+
+ /* Initialise the red LED. */
+ pxRedLED = metal_led_get_rgb( "LD0", "red" );
+ configASSERT( pxRedLED );
+ metal_led_enable( pxRedLED );
+ metal_led_off( pxRedLED );
+
+ /* Flash the red LED to indicate that assert was hit - interrupts are off
+ here to prevent any further tick interrupts or context switches, so the
+ delay is implemented as a crude loop instead of a peripheral timer. */
+ for( ;; )
+ {
+ for( ul = 0; ul < ulNullLoopDelay; ul++ )
+ {
+ __asm volatile( "nop" );
+ }
+ metal_led_toggle( pxRedLED );
+ }
+}
+/*-----------------------------------------------------------*/
+
+void handle_trap( void )
+{
+volatile uint32_t ulMEPC = 0UL, ulMCAUSE = 0UL, ulPLICPending0Register = 0UL, ulPLICPending1Register = 0UL;
+
+ /* Store a few register values that might be useful when determining why this
+ function was called. */
+ __asm volatile( "csrr %0, mepc" : "=r"( ulMEPC ) );
+ __asm volatile( "csrr %0, mcause" : "=r"( ulMCAUSE ) );
+ ulPLICPending0Register = mainPLIC_PENDING_0;
+ ulPLICPending1Register = mainPLIC_PENDING_1;
+
+ /* Prevent compiler warnings about unused variables. */
+ ( void ) ulPLICPending0Register;
+ ( void ) ulPLICPending1Register;
+
+ /* Force an assert as this function has not been implemented as the demo
+ does not use external interrupts. */
+ configASSERT( metal_cpu_get( mainHART_0 ) == 0x00 );
+}
+/*-----------------------------------------------------------*/
+
+void vToggleLED( void )
+{
+ metal_led_toggle( pxBlueLED );
+}
+/*-----------------------------------------------------------*/
+
+void *malloc( size_t xSize )
+{
+ /* The linker script does not define a heap so artificially force an assert()
+ if something unexpectedly uses the C library heap. See
+ https://www.freertos.org/a00111.html for more information. */
+ configASSERT( metal_cpu_get( mainHART_0 ) == 0x00 );
+
+ /* Remove warnings about unused parameter. */
+ ( void ) xSize;
+ return NULL;
+}
+/*-----------------------------------------------------------*/
+
+
diff --git a/lexicon.txt b/lexicon.txt
index 2db8f8a84..0d7d058b8 100644
--- a/lexicon.txt
+++ b/lexicon.txt
@@ -218,6 +218,7 @@ checktimer
checkval
checkvalue
checon
+ci
ciconfiguration
circleos
ck