From d66d92636a4e9ffc61243a8b2b0837e9b62b7fad Mon Sep 17 00:00:00 2001 From: Jean THOMAS Date: Tue, 9 Jun 2020 14:52:25 +0200 Subject: [PATCH] Refine libgram architecture --- libgram/Makefile | 2 +- libgram/include/gram.h | 13 ++++++-- libgram/src/dfii.c | 74 ++++++++++++++++++++++++++++++++++++++++++ libgram/src/dfii.h | 6 +++- libgram/src/helpers.h | 9 +++-- libgram/src/hw_regs.h | 6 ++-- libgram/src/init.c | 46 +++++--------------------- libgram/src/memtest.c | 2 +- libgram/tools/csv2c | 24 -------------- 9 files changed, 110 insertions(+), 72 deletions(-) create mode 100644 libgram/src/dfii.c delete mode 100755 libgram/tools/csv2c diff --git a/libgram/Makefile b/libgram/Makefile index cf7ee3f..530e83a 100644 --- a/libgram/Makefile +++ b/libgram/Makefile @@ -1,4 +1,4 @@ -OBJS := src/init.o src/memtest.o +OBJS := src/init.o src/memtest.o src/dfii.o TRIPLE := riscv64-unknown-elf diff --git a/libgram/include/gram.h b/libgram/include/gram.h index a16f5b8..7440c57 100644 --- a/libgram/include/gram.h +++ b/libgram/include/gram.h @@ -5,10 +5,17 @@ enum GramError { GRAM_ERR_NONE = 0, GRAM_ERR_UNDOCUMENTED, GRAM_ERR_MEMTEST, - }; -int gram_init(void); -int gram_memtest(void); +struct gramCoreRegs; +struct gramPHYRegs; +struct gramCtx { + volatile void *ddr_base; + volatile struct gramCoreRegs *core; + volatile struct gramPHYRegs *phy; +}; + +int gram_init(struct gramCtx *ctx, void *ddr_base, void *core_base, void *phy_base); +int gram_memtest(struct gramCtx *ctx); #endif /* GRAM_H */ diff --git a/libgram/src/dfii.c b/libgram/src/dfii.c new file mode 100644 index 0000000..b9367ba --- /dev/null +++ b/libgram/src/dfii.c @@ -0,0 +1,74 @@ +#include + +#include "hw_regs.h" +#include +#include "dfii.h" +#include "helpers.h" + +static void dfii_setcontrol(struct gramCtx *ctx, uint8_t val) { + ctx->core->control = val; +} + +void dfii_setsw(struct gramCtx *ctx, bool software_control) { + if (software_control) { + dfii_setcontrol(ctx, DFII_CONTROL_CKE|DFII_CONTROL_ODT|DFII_CONTROL_RESET_N); + } else { + dfii_setcontrol(ctx, DFII_CONTROL_SEL); + } +} + +static void dfii_set_p0_address(struct gramCtx *ctx, uint32_t val) { + ctx->core->phases[0].address = val; +} + +static void dfii_set_p0_baddress(struct gramCtx *ctx, uint32_t val) { + ctx->core->phases[0].baddress = val; +} + +static void dfii_p0_command(struct gramCtx *ctx, uint32_t cmd) { + ctx->core->phases[0].command = cmd; + ctx->core->phases[0].command_issue = 1; +} + +/* TODO: those values are hardcoded for ECPIX-5's RAM */ +/* Should add the capacity to generate MRx from RAM spec */ +void dfii_initseq(struct gramCtx *ctx) { + /* Release reset */ + dfii_set_p0_address(ctx, 0x0); + dfii_set_p0_baddress(ctx, 0); + dfii_setcontrol(ctx, DFII_CONTROL_ODT|DFII_CONTROL_RESET_N); + cdelay(50000); + + /* Bring CKE high */ + dfii_set_p0_address(ctx, 0x0); + dfii_set_p0_baddress(ctx, 0); + dfii_setcontrol(ctx, DFII_CONTROL_CKE|DFII_CONTROL_ODT|DFII_CONTROL_RESET_N); + cdelay(10000); + + /* Load Mode Register 2, CWL=5 */ + dfii_set_p0_address(ctx, 0x200); + dfii_set_p0_baddress(ctx, 2); + dfii_p0_command(ctx, DFII_COMMAND_RAS|DFII_COMMAND_CAS|DFII_COMMAND_WE|DFII_COMMAND_CS); + + /* Load Mode Register 3 */ + dfii_set_p0_address(ctx, 0x0); + dfii_set_p0_baddress(ctx, 3); + dfii_p0_command(ctx, DFII_COMMAND_RAS|DFII_COMMAND_CAS|DFII_COMMAND_WE|DFII_COMMAND_CS); + + /* Load Mode Register 1 */ + dfii_set_p0_address(ctx, 0x6); + dfii_set_p0_baddress(ctx, 1); + dfii_p0_command(ctx, DFII_COMMAND_RAS|DFII_COMMAND_CAS|DFII_COMMAND_WE|DFII_COMMAND_CS); + + /* Load Mode Register 0, CL=6, BL=8 */ + dfii_set_p0_address(ctx, 0x320); + dfii_set_p0_baddress(ctx, 0); + dfii_p0_command(ctx, DFII_COMMAND_RAS|DFII_COMMAND_CAS|DFII_COMMAND_WE|DFII_COMMAND_CS); + cdelay(200); + + /* ZQ Calibration */ + dfii_set_p0_address(ctx, 0x400); + dfii_set_p0_baddress(ctx, 0); + dfii_p0_command(ctx, DFII_COMMAND_WE|DFII_COMMAND_CS); + cdelay(200); +} diff --git a/libgram/src/dfii.h b/libgram/src/dfii.h index f4d3e23..ff0d912 100644 --- a/libgram/src/dfii.h +++ b/libgram/src/dfii.h @@ -1,6 +1,8 @@ #ifndef DFII_H #define DFII_H +#include + #define DFII_CONTROL_SEL (1 << 1) #define DFII_CONTROL_CKE (1 << 2) #define DFII_CONTROL_ODT (1 << 3) @@ -11,6 +13,8 @@ #define DFII_COMMAND_CAS (1 << 3) #define DFII_COMMAND_RAS (1 << 4) #define DFII_COMMAND_WRDATA (1 << 5) -#define DFII_COMMAND_WRDATA (1 << 6) + +void dfii_setsw(struct gramCtx *ctx, bool software_control); +void dfii_initseq(struct gramCtx *ctx); #endif /* DFII_H */ diff --git a/libgram/src/helpers.h b/libgram/src/helpers.h index 3418f72..e0f6b0f 100644 --- a/libgram/src/helpers.h +++ b/libgram/src/helpers.h @@ -1,6 +1,11 @@ #ifndef HELPERS_H #define HELPERS_H +__attribute__((unused)) static inline void cdelay(int i) { + while(i > 0) { + __asm__ volatile("nop"); + i--; + } +} - -#endif HELPERS_H +#endif /* HELPERS_H */ diff --git a/libgram/src/hw_regs.h b/libgram/src/hw_regs.h index 93ef450..6adb338 100644 --- a/libgram/src/hw_regs.h +++ b/libgram/src/hw_regs.h @@ -1,7 +1,7 @@ #ifndef HW_REGS_H #define HW_REGS_H -struct ECP5PHY { +struct gramPHYRegs { uint32_t dly_sel; uint32_t rdly_dq_rst; uint32_t rdly_dq_inc; @@ -20,9 +20,9 @@ struct DFII_Phase { uint32_t rddata; } __attribute__((packed)); -struct DFII { +struct gramCoreRegs { uint32_t control; - + struct DFII_Phase phases[4]; } __attribute__((packed)); #endif /* HW_REGS_H */ \ No newline at end of file diff --git a/libgram/src/init.c b/libgram/src/init.c index 4c517f4..839079f 100644 --- a/libgram/src/init.c +++ b/libgram/src/init.c @@ -1,40 +1,12 @@ #include +#include "dfii.h" -int gram_init(void) { -#ifdef CSR_DDRCTRL_BASE - ddrctrl_init_done_write(0); - ddrctrl_init_error_write(0); -#endif +int gram_init(struct gramCtx *ctx, void *ddr_base, void *core_base, void *phy_base) { + ctx->ddr_base = ddr_base; + ctx->core = core_base; + ctx->phy = phy_base; - sdrsw(); - init_sequence(); - -#ifdef CSR_DDRPHY_BASE -#ifdef DDRPHY_CMD_DELAY - ddrphy_cdly(DDRPHY_CMD_DELAY); -#endif -#if CSR_DDRPHY_EN_VTC_ADDR - ddrphy_en_vtc_write(0); -#endif -#if defined(SDRAM_PHY_WRITE_LEVELING_CAPABLE) || defined(SDRAM_PHY_READ_LEVELING_CAPABLE) - sdrlevel(); -#endif -#if CSR_DDRPHY_EN_VTC_ADDR - ddrphy_en_vtc_write(1); -#endif -#endif - sdrhw(); - - if(!memtest()) { -#ifdef CSR_DDRCTRL_BASE - ddrctrl_init_done_write(1); - ddrctrl_init_error_write(1); -#endif - return GRAM_ERR_MEMTEST; - } -#ifdef CSR_DDRCTRL_BASE - ddrctrl_init_done_write(1); -#endif - - return GRAM_ERR_NONE; -} + dfii_setsw(ctx, true); + dfii_initseq(ctx); + dfii_setsw(ctx, false); +} \ No newline at end of file diff --git a/libgram/src/memtest.c b/libgram/src/memtest.c index 69da9b1..55a5fc0 100644 --- a/libgram/src/memtest.c +++ b/libgram/src/memtest.c @@ -1,5 +1,5 @@ #include -int gram_memtest(void) { +int gram_memtest(struct gramCtx *ctx) { return 0; } diff --git a/libgram/tools/csv2c b/libgram/tools/csv2c deleted file mode 100755 index d9c16f8..0000000 --- a/libgram/tools/csv2c +++ /dev/null @@ -1,24 +0,0 @@ -#!/usr/bin/env python3 -import csv -import argparse - -def generateHeader(input_file, output_file): - constant = output_file.replace('.', '_').upper() - header = "#ifndef {}\n#define {}\n".format(constant, constant) - - with open('test.csv', newline='\n') as csvfile: - csrreader = csv.reader(filter(lambda row: row[0]!='#', csvfile), delimiter=',') - for row in csrreader: - header += "volatile uint32_t *{} = {};\n".format(row[0].strip(), row[1].strip()) - - header += "#endif /* {} */\n".format(constant) - - return header - -if __name__ == "__main__": - parser = argparse.ArgumentParser() - parser.add_argument("in_csv", help="input csv file") - parser.add_argument("out_h", help="output header file") - args = parser.parse_args() - - print(generateHeader(args.in_csv, args.out_h)) -- 2.30.2