From ea0ac6b715c64a52e998cfb73ea89920491399a2 Mon Sep 17 00:00:00 2001 From: Kris Kwiatkowski Date: Sat, 8 Dec 2018 20:19:54 +0000 Subject: [PATCH] Init --- .gitignore | 2 + conf/sdk.mk | 93 +++++++++++++++++++++++++++++++++++++++++ conf/toolchain.mk | 13 ++++++ cyclecount/Makefile | 7 ++++ cyclecount/cyclecount.c | 25 +++++++++++ cyclecount/getcycles.S | 10 +++++ 6 files changed, 150 insertions(+) create mode 100644 .gitignore create mode 100644 conf/sdk.mk create mode 100644 conf/toolchain.mk create mode 100644 cyclecount/Makefile create mode 100644 cyclecount/cyclecount.c create mode 100644 cyclecount/getcycles.S diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..aad66d3 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +bin +libwrap.a diff --git a/conf/sdk.mk b/conf/sdk.mk new file mode 100644 index 0000000..3461d8f --- /dev/null +++ b/conf/sdk.mk @@ -0,0 +1,93 @@ +all: $(TARGET) + +MK_FILE_PATH = $(lastword $(MAKEFILE_LIST)) +PRJ_DIR = $(abspath $(dir $(MK_FILE_PATH))) + +# Hardcoded paths +OPENOCD_BIN := /usr/bin/riscv-openocd +RISCV_SDK_DIR := $(abspath $(PRJ_DIR)/../../riscv-sdk) +OUT_DIR := bin + +# Variables +SDK_INC := $(RISCV_SDK_DIR)/include +SDK_WRAP := $(RISCV_SDK_DIR)/libwrap +SDK_OPENOCD_CFG := $(RISCV_SDK_DIR)/openocd.cfg + +# libwrap config +include $(SDK_WRAP)/libwrap.mk + +# SDK sources +SDK_SRC_ASM := \ + $(RISCV_SDK_DIR)/entry.S \ + $(RISCV_SDK_DIR)/start.S + +SDK_SRC_C := \ + $(RISCV_SDK_DIR)/init.c +SDK_LINK_SCRIPT := \ + $(RISCV_SDK_DIR)/flash.lds + +# Variable used by libwrap.mk +INCLUDES := -I$(RISCV_SDK_DIR)/include + +# Platform specific: HiFive1 + +#Name of variable required by libwrap.mk +ARCH_FLAGS += \ + -march=rv32imac -mabi=ilp32 -mcmodel=medany + +CFLAGS += \ + -O3 -fno-builtin-printf \ + -Wall -Wextra -Wshadow -fno-common \ + $(ARCH_FLAGS) \ + $(LOCAL_CFLAGS) #-include sys/cdefs.h + +LDFLAGS += \ + -static \ + -L$(RISCV_SDK_DIR) \ + -T$(SDK_LINK_SCRIPT) \ + -nostartfiles \ + --specs=nano.specs \ + -Wl,--gc-sections \ + $(LOCAL_LDFLAGS) + +# Common targets +OBJ_S := \ + $(LOCAL_SRC_S:.S=.o) \ + $(SDK_SRC_ASM:.S=.o) +OBJ_C := \ + $(LOCAL_SRC_C:.c=.o) \ + $(SDK_SRC_C:.c=.o) + +# Compilation targets +$(OBJ_S): %.o: %.S + mkdir -p $(OUT_DIR)/$(dir $@) + $(CC) $(ARCH_FLAGS) -I$(SDK_INC) $(OPT) -c -o $(OUT_DIR)/$@ $< + +$(OBJ_C): %.o: %.c + mkdir -p $(OUT_DIR)/$(dir $@) + $(CC) -I$(SDK_INC) $(CFLAGS) $(OPT) -c -o $(OUT_DIR)/$@ $< + +$(TARGET): $(OBJ_C) $(OBJ_S) $(LIBWRAP) + $(CC) -I$(SDK_INC) $(CFLAGS) $(OPT) \ + $(addprefix $(OUT_DIR)/,$(OBJ_S)) \ + $(addprefix $(OUT_DIR)/,$(OBJ_C)) \ + -o $(OUT_DIR)/$@ $(LDFLAGS) +clean: + rm -rf $(OUT_DIR) + rm -rf $(LIBWRAP) + +run: + $(OPENOCD_BIN) -s "sdk" -f $(SDK_OPENOCD_CFG) & \ + $(GDB) \ + "$(OUT_DIR)/$(TARGET)" \ + --batch \ + -ex "set remotetimeout 240" \ + -ex "target extended-remote localhost:3333" \ + -ex "monitor reset halt" \ + -ex "monitor flash protect 0 64 last off" \ + -ex "load" \ + -ex "monitor resume" \ + -ex "monitor shutdown" \ + -ex "quit" + +.PHONY: clean all run diff --git a/conf/toolchain.mk b/conf/toolchain.mk new file mode 100644 index 0000000..b9211e9 --- /dev/null +++ b/conf/toolchain.mk @@ -0,0 +1,13 @@ +# Define toolchain to use +ARCH := riscv64 +VENDOR := unknown +ABI := elf +BIN_DIR := #/usr/local/bin/ +TOOLCHAIN := $(BIN_DIR)$(ARCH)-$(VENDOR)-$(ABI) + +# Defines compiler and tools to use +AR := $(TOOLCHAIN)-ar +AS := $(TOOLCHAIN)-as +CC := $(TOOLCHAIN)-gcc +STRIP := $(TOOLCHAIN)-strip +GDB := $(TOOLCHAIN)-gdb diff --git a/cyclecount/Makefile b/cyclecount/Makefile new file mode 100644 index 0000000..27e95e1 --- /dev/null +++ b/cyclecount/Makefile @@ -0,0 +1,7 @@ +TARGET := cyclecount.elf +LOCAL_SRC_C := cyclecount.c +LOCAL_SRC_S := getcycles.S +LOCAL_OPT_C := -Os -fno-builtin-printf -Wall -Wextra -pedantic + +include ../conf/toolchain.mk +include ../conf/sdk.mk diff --git a/cyclecount/cyclecount.c b/cyclecount/cyclecount.c new file mode 100644 index 0000000..e4fe8a6 --- /dev/null +++ b/cyclecount/cyclecount.c @@ -0,0 +1,25 @@ +#include + +uint64_t getcycles(); +static void do_something() +{ + for (int i = 0; i < 1000; ++i) { + __asm__("NOP"); + } +} + +int main(void) +{ + // Instruction cache misses are relatively expensive, so for more + // consistent benchmarks that depend less on the relative speed of + // the QSPI flash, you might want to fill the instruction cache first. + // Note that it can hold 16 KiB of instructions on the HiFive1. + do_something(); + getcycles(); + uint64_t oldcount = getcycles(); + do_something(); + uint64_t newcount = getcycles(); + + printf("That took %d cycles.\n", (unsigned int)(newcount-oldcount)); + return 0; +} diff --git a/cyclecount/getcycles.S b/cyclecount/getcycles.S new file mode 100644 index 0000000..f17b77a --- /dev/null +++ b/cyclecount/getcycles.S @@ -0,0 +1,10 @@ +.text + +.globl getcycles +.align 2 +getcycles: + csrr a1, mcycleh + csrr a0, mcycle + csrr a2, mcycleh + bne a1, a2, getcycles + ret