main.o \
boot-helper.o \
boot.o \
- helpers.o
+ helpers.o \
+ cmd_bios.o \
+ cmd_boot.o \
+ cmd_dram.o \
+ cmd_mdio.o \
+ cmd_mem_access.o \
+ cmd_sdcard.o \
+ cmd_spi_flash.o \
+ cmd_usddrphy.o
ifdef TERM_NO_HIST
CFLAGS += -DTERM_NO_HIST
%.o: $(BIOS_DIRECTORY)/%.c
$(compile)
+%.o: $(BIOS_DIRECTORY)/commands/%.c
+ $(compile)
+
%.o: $(BIOS_DIRECTORY)/%.S
$(assemble)
--- /dev/null
+// This file is Copyright (c) 2020 Franck Jullien <franck.jullien@gmail.com>
+
+// SPDX-License-Identifier: BSD-Source-Code
+
+#ifndef __COMMAND_H__
+#define __COMMAND_H__
+
+#define MAX_PARAM 8
+
+#define MISC_CMDS 0
+#define SYSTEM_CMDS 1
+#define CACHE_CMDS 2
+#define BOOT_CMDS 3
+#define DRAM_CMDS 4
+#define MDIO_CMDS 5
+#define MEM_CMDS 6
+#define SD_CMDS 7
+#define SPIFLASH_CMDS 8
+#define DDR_CMDS 9
+#define NB_OF_GROUPS 10
+
+typedef void (*cmd_handler)(int nb_params, char **params);
+
+struct command_struct {
+ void (*func)(int nb_params, char **params);
+ const char *name;
+ const char *help;
+ int group;
+};
+
+extern struct command_struct *const __bios_cmd_start[];
+extern struct command_struct *const __bios_cmd_end[];
+
+#define define_command(cmd_name, handler, help_txt, group_id) \
+ struct command_struct s_##cmd_name = { \
+ .func = (cmd_handler)handler, \
+ .name = #cmd_name, \
+ .help = help_txt, \
+ .group = group_id, \
+ }; \
+ const struct command_struct *__bios_cmd_##cmd_name __attribute__((__used__)) \
+ __attribute__((__section__(".bios_cmd"))) = &s_##cmd_name
+
+
+struct command_struct *command_dispatcher(char *command, int nb_params, char **params);
+
+#endif
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <id.h>
+#include <generated/csr.h>
+#include <crc.h>
+#include <system.h>
+
+#include "../command.h"
+#include "../helpers.h"
+
+/**
+ * Command "help"
+ *
+ * Print a list of available commands with their help text
+ *
+ */
+static void help_handler(int nb_params, char **params)
+{
+ struct command_struct * const *cmd;
+ int i, not_empty;
+
+ puts("\nLiteX BIOS, available commands:\n");
+
+ for (i = 0; i < NB_OF_GROUPS; i++) {
+ not_empty = 0;
+ for (cmd = __bios_cmd_start; cmd != __bios_cmd_end; cmd++) {
+ if ((*cmd)->group == i) {
+ printf("%-16s - %s\n", (*cmd)->name, (*cmd)->help ? (*cmd)->help : "-");
+ not_empty = 1;
+ }
+ }
+ if (not_empty)
+ printf("\n");
+ }
+}
+
+define_command(help, help_handler, "Print this help", MISC_CMDS);
+
+/**
+ * Command "ident"
+ *
+ * Print SoC identyifier if available
+ *
+ */
+static void ident_helper(int nb_params, char **params)
+{
+ char buffer[IDENT_SIZE];
+
+ get_ident(buffer);
+ printf("Ident: %s", *buffer ? buffer : "-");
+}
+
+define_command(ident, ident_helper, "Display identifier", SYSTEM_CMDS);
+
+/**
+ * Command "reboot"
+ *
+ * Reboot the system
+ *
+ */
+#ifdef CSR_CTRL_BASE
+static void reboot(int nb_params, char **params)
+{
+ ctrl_reset_write(1);
+}
+
+define_command(reboot, reboot, "Reset processor", SYSTEM_CMDS);
+#endif
+
+/**
+ * Command "crc"
+ *
+ * Compute CRC32 over an address range
+ *
+ */
+static void crc(int nb_params, char **params)
+{
+ char *c;
+ unsigned int addr;
+ unsigned int length;
+
+ if (nb_params < 2) {
+ printf("crc <address> <length>");
+ return;
+ }
+
+ addr = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect address");
+ return;
+ }
+
+ length = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect length");
+ return;
+ }
+
+ printf("CRC32: %08x", crc32((unsigned char *)addr, length));
+}
+
+define_command(crc, crc, "Compute CRC32 of a part of the address space", MISC_CMDS);
+
+/**
+ * Command "flush_cpu_dcache"
+ *
+ * Flush CPU data cache
+ *
+ */
+
+define_command(flush_cpu_dcache, flush_cpu_dcache, "Flush CPU data cache", CACHE_CMDS);
+
+/**
+ * Command "flush_l2_cache"
+ *
+ * Flush L2 cache
+ *
+ */
+#ifdef CONFIG_L2_SIZE
+define_command(flush_l2_cache, flush_l2_cache, "Flush L2 cache", CACHE_CMDS);
+#endif
+
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+#include "../boot.h"
+
+/**
+ * Command "flashboot"
+ *
+ * Boot software from flash
+ *
+ */
+#ifdef FLASH_BOOT_ADDRESS
+define_command(flashboot, flashboot, "Boot from flash", BOOT_CMDS);
+#endif
+
+/**
+ * Command "romboot"
+ *
+ * Boot software from embedded rom
+ *
+ */
+#ifdef ROM_BOOT_ADDRESS
+define_command(romboot, romboot, "Boot from embedded rom", BOOT_CMDS);
+#endif
+
+/**
+ * Command "serialboot"
+ *
+ * Boot software from serial interface
+ *
+ */
+define_command(serialboot, serialboot, "Boot via SFL", BOOT_CMDS);
+
+/**
+ * Command "netboot"
+ *
+ * Boot software from TFTP server
+ *
+ */
+#ifdef CSR_ETHMAC_BASE
+define_command(netboot, netboot, "Boot via TFTP", BOOT_CMDS);
+#endif
+
+/**
+ * Command "spisdcardboot"
+ *
+ * Boot software from SDcard
+ *
+ */
+#ifdef CSR_SPISDCARD_BASE
+define_command(spisdcardboot, spisdcardboot, "Boot from SDCard via SPI hardware bitbang", BOOT_CMDS);
+#endif
+
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+#include "../sdram.h"
+
+/**
+ * Command "sdrrow"
+ *
+ * Precharge/Activate row
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+static void sdrrow_handler(int nb_params, char **params)
+{
+ char *c;
+ unsigned int row;
+
+ if (nb_params < 1) {
+ sdrrow(0);
+ printf("Precharged");
+ }
+
+ row = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect row");
+ return;
+ }
+
+ sdrrow(row);
+ printf("Activated row %d", row);
+}
+define_command(sdrrow, sdrrow_handler, "Precharge/Activate row", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrsw"
+ *
+ * Gives SDRAM control to SW
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+define_command(sdrsw, sdrsw, "Gives SDRAM control to SW", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrhw"
+ *
+ * Gives SDRAM control to HW
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+define_command(sdrhw, sdrhw, "Gives SDRAM control to HW", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrrdbuf"
+ *
+ * Dump SDRAM read buffer
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+static void sdrrdbuf_handler(int nb_params, char **params)
+{
+ sdrrdbuf(-1);
+}
+
+define_command(sdrrdbuf, sdrrdbuf_handler, "Dump SDRAM read buffer", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrrd"
+ *
+ * Read SDRAM data
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+static void sdrrd_handler(int nb_params, char **params)
+{
+ unsigned int addr;
+ int dq;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdrrd <address>");
+ return;
+ }
+
+ addr = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect address");
+ return;
+ }
+
+ if (nb_params < 2)
+ dq = -1;
+ else {
+ dq = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect DQ");
+ return;
+ }
+ }
+
+ sdrrd(addr, dq);
+}
+
+define_command(sdrrd, sdrrd_handler, "Read SDRAM data", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrrderr"
+ *
+ * Print SDRAM read errors
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+static void sdrrderr_handler(int nb_params, char **params)
+{
+ int count;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdrrderr <count>");
+ return;
+ }
+
+ count = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect count");
+ return;
+ }
+
+ sdrrderr(count);
+}
+
+define_command(sdrrderr, sdrrderr_handler, "Print SDRAM read errors", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrwr"
+ *
+ * Write SDRAM test data
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+static void sdrwr_handler(int nb_params, char **params)
+{
+ unsigned int addr;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdrwr <address>");
+ return;
+ }
+
+ addr = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect address");
+ return;
+ }
+
+ sdrwr(addr);
+}
+
+define_command(sdrwr, sdrwr_handler, "Write SDRAM test data", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrinit"
+ *
+ * Start SDRAM initialisation
+ *
+ */
+#if defined(CSR_SDRAM_BASE) && defined(CSR_DDRPHY_BASE)
+define_command(sdrinit, sdrinit, "Start SDRAM initialisation", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrwlon"
+ *
+ * Write leveling ON
+ *
+ */
+#if defined(CSR_DDRPHY_BASE) && defined(SDRAM_PHY_WRITE_LEVELING_CAPABLE) && defined(CSR_SDRAM_BASE)
+define_command(sdrwlon, sdrwlon, "Enable write leveling", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrwloff"
+ *
+ * Write leveling OFF
+ *
+ */
+#if defined(CSR_DDRPHY_BASE) && defined(SDRAM_PHY_WRITE_LEVELING_CAPABLE) && defined(CSR_SDRAM_BASE)
+define_command(sdrwloff, sdrwloff, "Disable write leveling", DRAM_CMDS);
+#endif
+
+/**
+ * Command "sdrlevel"
+ *
+ * Perform read/write leveling
+ *
+ */
+#if defined(CSR_DDRPHY_BASE) && defined(CSR_SDRAM_BASE)
+define_command(sdrlevel, sdrlevel, "Perform read/write leveling", DRAM_CMDS);
+#endif
+
+/**
+ * Command "memtest"
+ *
+ * Run a memory test
+ *
+ */
+#ifdef CSR_SDRAM_BASE
+define_command(memtest, memtest, "Run a memory test", DRAM_CMDS);
+#endif
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+
+/**
+ * Command "mdiow"
+ *
+ * Write MDIO register
+ *
+ */
+#ifdef CSR_ETHPHY_MDIO_W_ADDR
+static void mdiow(int nb_params, char **params)
+{
+ char *c;
+ unsigned int phyadr2;
+ unsigned int reg2;
+ unsigned int val2;
+
+ if (nb_params < 3) {
+ printf("mdiow <phyadr> <reg> <value>");
+ return;
+ }
+
+ phyadr2 = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect phyadr");
+ return;
+ }
+
+ reg2 = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect reg");
+ return;
+ }
+
+ val2 = strtoul(params[2], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect val");
+ return;
+ }
+
+ mdio_write(phyadr2, reg2, val2);
+}
+
+define_command(mdiow, mdiow, "Write MDIO register", MDIO_CMDS);
+#endif
+
+/**
+ * Command "mdior"
+ *
+ * Read MDIO register
+ *
+ */
+#ifdef CSR_ETHPHY_MDIO_W_ADDR
+static void mdior(int nb_params, char **params)
+{
+ char *c;
+ unsigned int phyadr2;
+ unsigned int reg2;
+ unsigned int val;
+
+ if (nb_params < 2) {
+ printf("mdior <phyadr> <reg>");
+ return;
+ }
+
+ phyadr2 = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect phyadr");
+ return;
+ }
+
+ reg2 = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect reg");
+ return;
+ }
+
+ val = mdio_read(phyadr2, reg2);
+ printf("Reg %d: 0x%04x", reg2, val);
+}
+
+define_command(mdior, mdior, "Read MDIO register", MDIO_CMDS);
+#endif
+
+/**
+ * Command "mdiod"
+ *
+ * Dump MDIO registers
+ *
+ */
+#ifdef CSR_ETHPHY_MDIO_W_ADDR
+static void mdiod(int nb_params, char **params)
+{
+ char *c;
+ unsigned int phyadr;
+ unsigned int count;
+ unsigned int val;
+ int i;
+
+ if (nb_params < 2) {
+ printf("mdiod <phyadr> <count>");
+ return;
+ }
+
+ phyadr = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect phyadr");
+ return;
+ }
+
+ count = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect count");
+ return;
+ }
+
+ printf("MDIO dump @0x%x:\n", phyadr);
+ for (i = 0; i < count; i++) {
+ val = mdio_read(phyadr, i);
+ printf("reg %d: 0x%04x", i, val);
+ }
+}
+
+define_command(mdiod, mdiod, "Dump MDIO registers", MDIO_CMDS);
+#endif
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "../command.h"
+#include "../helpers.h"
+
+/**
+ * Command "mr"
+ *
+ * Memory read
+ *
+ */
+static void mr(int nb_params, char **params)
+{
+ char *c;
+ unsigned int *addr;
+ unsigned int length;
+
+ if (nb_params < 1) {
+ printf("mr <address> [length]");
+ return;
+ }
+ addr = (unsigned int *)strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect address");
+ return;
+ }
+ if (nb_params == 1) {
+ length = 4;
+ } else {
+ length = strtoul(params[1], &c, 0);
+ if(*c != 0) {
+ printf("\nIncorrect length");
+ return;
+ }
+ }
+
+ dump_bytes(addr, length, (unsigned long)addr);
+}
+
+define_command(mr, mr, "Read address space", MEM_CMDS);
+
+/**
+ * Command "mw"
+ *
+ * Memory write
+ *
+ */
+static void mw(int nb_params, char **params)
+{
+ char *c;
+ unsigned int *addr;
+ unsigned int value;
+ unsigned int count;
+ unsigned int i;
+
+ if (nb_params < 2) {
+ printf("mw <address> <value> [count]");
+ return;
+ }
+
+ addr = (unsigned int *)strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect address");
+ return;
+ }
+
+ value = strtoul(params[1], &c, 0);
+ if(*c != 0) {
+ printf("Incorrect value");
+ return;
+ }
+
+ if (nb_params == 2) {
+ count = 1;
+ } else {
+ count = strtoul(params[2], &c, 0);
+ if(*c != 0) {
+ printf("Incorrect count");
+ return;
+ }
+ }
+
+ for (i = 0; i < count; i++)
+ *addr++ = value;
+}
+
+define_command(mw, mw, "Write address space", MEM_CMDS);
+
+/**
+ * Command "mc"
+ *
+ * Memory copy
+ *
+ */
+static void mc(int nb_params, char **params)
+{
+ char *c;
+ unsigned int *dstaddr;
+ unsigned int *srcaddr;
+ unsigned int count;
+ unsigned int i;
+
+ if (nb_params < 2) {
+ printf("mc <dst> <src> [count]");
+ return;
+ }
+
+ dstaddr = (unsigned int *)strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect destination address");
+ return;
+ }
+
+ srcaddr = (unsigned int *)strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect source address");
+ return;
+ }
+
+ if (nb_params == 2) {
+ count = 1;
+ } else {
+ count = strtoul(params[2], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect count");
+ return;
+ }
+ }
+
+ for (i = 0; i < count; i++)
+ *dstaddr++ = *srcaddr++;
+}
+
+define_command(mc, mc, "Copy address space", MEM_CMDS);
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+#include "../sdcard.h"
+
+/**
+ * Command "sdclk"
+ *
+ * Configure SDcard clock frequency
+ *
+ */
+#ifdef CSR_SDCORE_BASE
+static void sdclk(int nb_params, char **params)
+{
+ unsigned int frequ;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdclk <frequ>");
+ return;
+ }
+
+ frequ = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect frequency");
+ return;
+ }
+
+ sdclk_set_clk(frequ);
+}
+
+struct command_struct cmd_sdclk =
+{
+ .func = sdclk,
+ .name = "sdclk",
+ .help = "SDCard set clk frequency (Mhz)",
+};
+
+define_command(sdclk, sdclk, "SDCard set clk frequency (Mhz)", SD_CMDS);
+#endif
+
+/**
+ * Command "sdinit"
+ *
+ * Initialize SDcard
+ *
+ */
+#ifdef CSR_SDCORE_BASE
+define_command(sdinit, sdinit, "SDCard initialization", SD_CMDS);
+#endif
+
+/**
+ * Command "sdtest"
+ *
+ * Perform SDcard access tests
+ *
+ */
+#ifdef CSR_SDCORE_BASE
+static void sdtest(int nb_params, char **params)
+{
+ unsigned int loops;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdtest <loops>");
+ return;
+ }
+
+ loops = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect number of loops");
+ return;
+ }
+
+ sdcard_test(loops);
+}
+
+define_command(sdtest, sdtest, "SDCard test", SD_CMDS);
+#endif
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+
+/**
+ * Command "fw"
+ *
+ * Write data from a memory buffer to SPI flash
+ *
+ */
+#if (defined CSR_SPIFLASH_BASE && defined SPIFLASH_PAGE_SIZE)
+static void fw(int nb_params, char **params)
+{
+ char *c;
+ unsigned int addr;
+ unsigned int value;
+ unsigned int count;
+ unsigned int i;
+
+ if (nb_params < 2) {
+ printf("fw <offset> <value> [count]");
+ return;
+ }
+
+ addr = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect offset");
+ return;
+ }
+
+ value = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect value");
+ return;
+ }
+
+ if (nb_params == 2) {
+ count = 1;
+ } else {
+ count = strtoul(count, &c, 0);
+ if (*c != 0) {
+ printf("Incorrect count");
+ return;
+ }
+ }
+
+ for (i = 0; i < count; i++)
+ write_to_flash(addr + i * 4, (unsigned char *)&value, 4);
+}
+
+define_command(fw, fw, "Write to flash", SPIFLASH_CMDS);
+#endif
+
+/**
+ * Command "fe"
+ *
+ * Flash erase
+ *
+ */
+#if (defined CSR_SPIFLASH_BASE && defined SPIFLASH_PAGE_SIZE)
+static void fe(int nb_params, char **params)
+{
+ erase_flash();
+ printf("Flash erased\n");
+}
+
+define_command(fe, fe, "Erase whole flash", SPIFLASH_CMDS);
+#endif
+
--- /dev/null
+// SPDX-License-Identifier: BSD-Source-Code
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <generated/csr.h>
+
+#include "../command.h"
+#include "../helpers.h"
+#include "../sdram.h"
+
+/**
+ * Command "sdram_cdly"
+ *
+ * Set SDRAM clk/cmd delay
+ *
+ */
+#ifdef USDDRPHY_DEBUG
+static void sdram_cdly(int nb_params, char **params)
+{
+ unsigned int delay;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdram_cdly <delay>");
+ return;
+ }
+
+ delay = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect delay");
+ return;
+ }
+
+ ddrphy_cdly(delay);
+}
+
+define_command(sdram_cdly, sdram_cdly, "Set SDRAM clk/cmd delay", DDR_CMDS);
+#endif
+
+/**
+ * Command "sdram_cdly"
+ *
+ * Run SDRAM calibration
+ *
+ */
+#ifdef USDDRPHY_DEBUG
+define_command(sdram_cal, sdram_cal, "Run SDRAM calibration", DDR_CMDS);
+#endif
+
+/**
+ * Command "sdram_mpr"
+ *
+ * Read SDRAM MPR
+ *
+ */
+#ifdef USDDRPHY_DEBUG
+define_command(sdram_mpr, sdram_mpr, "Read SDRAM MPR", DDR_CMDS);
+#endif
+
+
+/**
+ * Command "sdram_mrwr"
+ *
+ * Write SDRAM mode registers
+ *
+ */
+#ifdef USDDRPHY_DEBUG
+static void sdram_mrwr(int nb_params, char **params)
+{
+ unsigned int reg;
+ unsigned int value;
+ char *c;
+
+ if (nb_params < 2) {
+ printf("sdram_mrwr <reg> <value>");
+ return;
+ }
+
+ reg = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect register value");
+ return;
+ }
+
+ value = strtoul(params[1], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect value");
+ return;
+ }
+
+ sdrsw();
+ printf("Writing 0x%04x to SDRAM mode register %d\n", value, reg);
+ sdrmrwr(reg, value);
+ sdrhw();
+}
+
+define_command(sdram_mrwr, sdram_mrwr, "Write SDRAM mode registers", DDR_CMDS);
+#endif
+
+/**
+ * Command "sdram_cdly_scan"
+ *
+ * Enable/disable cdly scan
+ *
+ */
+#ifdef USDDRPHY_DEBUG
+static void sdram_cdly_scan(int nb_params, char **params)
+{
+ unsigned int value;
+ char *c;
+
+ if (nb_params < 1) {
+ printf("sdram_cdly_scan <value>");
+ return;
+ }
+
+ value = strtoul(params[0], &c, 0);
+ if (*c != 0) {
+ printf("Incorrect value");
+ return;
+ }
+
+ sdr_cdly_scan(value);
+}
+
+define_command(sdram_cdly_scan, sdram_cdly_scan, "Enable/disable cdly scan", DDR_CMDS);
+#endif
#include "readline.h"
#include "helpers.h"
+#include "command.h"
extern unsigned int _ftext, _edata;
printf(" The system will continue, but expect problems.\n");
}
}
+
+int get_param(char *buf, char **cmd, char **params)
+{
+ int nb_param = 0;
+ int i;
+
+ for (i = 0; i < MAX_PARAM; i++)
+ params[i] = NULL;
+
+ *cmd = buf;
+
+ while ((*buf != ' ') && (*buf !=0))
+ buf++;
+
+ if (*buf == 0)
+ return nb_param;
+
+ *buf++ = 0;
+
+ while (1) {
+ while ((*buf == ' ') && (*buf !=0))
+ buf++;
+
+
+ if (*buf == 0)
+ return nb_param;
+
+ params[nb_param++] = buf;
+
+ while ((*buf != ' ') && (*buf !=0))
+ buf++;
+
+ if (*buf == 0)
+ return nb_param;
+ *buf++ = 0;
+ }
+}
+
+struct command_struct *command_dispatcher(char *command, int nb_params, char **params)
+{
+ struct command_struct * const *cmd;
+
+ for (cmd = __bios_cmd_start; cmd != __bios_cmd_end; cmd++) {
+ if (!strcmp(command, (*cmd)->name)) {
+ (*cmd)->func(nb_params, params);
+ return (*cmd);
+ }
+ }
+
+ return NULL;
+}
void dump_bytes(unsigned int *ptr, int count, unsigned long addr);
void crcbios(void);
+int get_param(char *buf, char **cmd, char **params);
+struct command_struct *command_dispatcher(char *command, int nb_params, char **params);
#endif
_erodata = .;
} > rom
+ .commands :
+ {
+ PROVIDE_HIDDEN (__bios_cmd_start = .);
+ KEEP(*(.bios_cmd))
+ PROVIDE_HIDDEN (__bios_cmd_end = .);
+ } > rom
+
.data :
{
. = ALIGN(8);
#include "boot.h"
#include "readline.h"
#include "helpers.h"
-
-/* General address space functions */
-
-static void mr(char *startaddr, char *len)
-{
- char *c;
- unsigned int *addr;
- unsigned int length;
-
- if(*startaddr == 0) {
- printf("mr <address> [length]\n");
- return;
- }
- addr = (unsigned *)strtoul(startaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect address\n");
- return;
- }
- if(*len == 0) {
- length = 4;
- } else {
- length = strtoul(len, &c, 0);
- if(*c != 0) {
- printf("incorrect length\n");
- return;
- }
- }
-
- dump_bytes(addr, length, (unsigned long)addr);
-}
-
-static void mw(char *addr, char *value, char *count)
-{
- char *c;
- unsigned int *addr2;
- unsigned int value2;
- unsigned int count2;
- unsigned int i;
-
- if((*addr == 0) || (*value == 0)) {
- printf("mw <address> <value> [count]\n");
- return;
- }
- addr2 = (unsigned int *)strtoul(addr, &c, 0);
- if(*c != 0) {
- printf("incorrect address\n");
- return;
- }
- value2 = strtoul(value, &c, 0);
- if(*c != 0) {
- printf("incorrect value\n");
- return;
- }
- if(*count == 0) {
- count2 = 1;
- } else {
- count2 = strtoul(count, &c, 0);
- if(*c != 0) {
- printf("incorrect count\n");
- return;
- }
- }
- for (i=0;i<count2;i++) *addr2++ = value2;
-}
-
-static void mc(char *dstaddr, char *srcaddr, char *count)
-{
- char *c;
- unsigned int *dstaddr2;
- unsigned int *srcaddr2;
- unsigned int count2;
- unsigned int i;
-
- if((*dstaddr == 0) || (*srcaddr == 0)) {
- printf("mc <dst> <src> [count]\n");
- return;
- }
- dstaddr2 = (unsigned int *)strtoul(dstaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect destination address\n");
- return;
- }
- srcaddr2 = (unsigned int *)strtoul(srcaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect source address\n");
- return;
- }
- if(*count == 0) {
- count2 = 1;
- } else {
- count2 = strtoul(count, &c, 0);
- if(*c != 0) {
- printf("incorrect count\n");
- return;
- }
- }
- for (i=0;i<count2;i++) *dstaddr2++ = *srcaddr2++;
-}
-
-#if (defined CSR_SPIFLASH_BASE && defined SPIFLASH_PAGE_SIZE)
-static void fw(char *addr, char *value, char *count)
-{
- char *c;
- unsigned int addr2;
- unsigned int value2;
- unsigned int count2;
- unsigned int i;
-
- if((*addr == 0) || (*value == 0)) {
- printf("fw <offset> <value> [count]\n");
- return;
- }
- addr2 = strtoul(addr, &c, 0);
- if(*c != 0) {
- printf("incorrect offset\n");
- return;
- }
- value2 = strtoul(value, &c, 0);
- if(*c != 0) {
- printf("incorrect value\n");
- return;
- }
- if(*count == 0) {
- count2 = 1;
- } else {
- count2 = strtoul(count, &c, 0);
- if(*c != 0) {
- printf("incorrect count\n");
- return;
- }
- }
- for (i=0;i<count2;i++) write_to_flash(addr2 + i * 4, (unsigned char *)&value2, 4);
-}
-
-static void fe(void)
-{
- erase_flash();
- printf("flash erased\n");
-}
-#endif
-
-#ifdef CSR_ETHPHY_MDIO_W_ADDR
-static void mdiow(char *phyadr, char *reg, char *val)
-{
- char *c;
- unsigned int phyadr2;
- unsigned int reg2;
- unsigned int val2;
-
- if((*phyadr == 0) || (*reg == 0) || (*val == 0)) {
- printf("mdiow <phyadr> <reg> <value>\n");
- return;
- }
- phyadr2 = strtoul(phyadr, &c, 0);
- if(*c != 0) {
- printf("incorrect phyadr\n");
- return;
- }
- reg2 = strtoul(reg, &c, 0);
- if(*c != 0) {
- printf("incorrect reg\n");
- return;
- }
- val2 = strtoul(val, &c, 0);
- if(*c != 0) {
- printf("incorrect val\n");
- return;
- }
- mdio_write(phyadr2, reg2, val2);
-}
-
-static void mdior(char *phyadr, char *reg)
-{
- char *c;
- unsigned int phyadr2;
- unsigned int reg2;
- unsigned int val;
-
- if((*phyadr == 0) || (*reg == 0)) {
- printf("mdior <phyadr> <reg>\n");
- return;
- }
- phyadr2 = strtoul(phyadr, &c, 0);
- if(*c != 0) {
- printf("incorrect phyadr\n");
- return;
- }
- reg2 = strtoul(reg, &c, 0);
- if(*c != 0) {
- printf("incorrect reg\n");
- return;
- }
- val = mdio_read(phyadr2, reg2);
- printf("reg %d: 0x%04x\n", reg2, val);
-}
-
-static void mdiod(char *phyadr, char *count)
-{
- char *c;
- unsigned int phyadr2;
- unsigned int count2;
- unsigned int val;
- int i;
-
- if((*phyadr == 0) || (*count == 0)) {
- printf("mdiod <phyadr> <count>\n");
- return;
- }
- phyadr2 = strtoul(phyadr, &c, 0);
- if(*c != 0) {
- printf("incorrect phyadr\n");
- return;
- }
- count2 = strtoul(count, &c, 0);
- if(*c != 0) {
- printf("incorrect count\n");
- return;
- }
- printf("MDIO dump @0x%x:\n", phyadr2);
- for (i=0; i<count2; i++) {
- val = mdio_read(phyadr2, i);
- printf("reg %d: 0x%04x\n", i, val);
- }
-}
-#endif
-
-static void crc(char *startaddr, char *len)
-{
- char *c;
- char *addr;
- unsigned int length;
-
- if((*startaddr == 0)||(*len == 0)) {
- printf("crc <address> <length>\n");
- return;
- }
- addr = (char *)strtoul(startaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect address\n");
- return;
- }
- length = strtoul(len, &c, 0);
- if(*c != 0) {
- printf("incorrect length\n");
- return;
- }
-
- printf("CRC32: %08x\n", crc32((unsigned char *)addr, length));
-}
-
-static void ident(void)
-{
- char buffer[IDENT_SIZE];
-
- get_ident(buffer);
- printf("Ident: %s\n", buffer);
-}
-
-/* Init + command line */
-
-static void help(void)
-{
- puts("LiteX BIOS, available commands:");
- puts("mr - read address space");
- puts("mw - write address space");
- puts("mc - copy address space");
-#if (defined CSR_SPIFLASH_BASE && defined SPIFLASH_PAGE_SIZE)
- puts("fe - erase whole flash");
- puts("fw - write to flash");
-
-#endif
-#ifdef CSR_ETHPHY_MDIO_W_ADDR
- puts("mdiow - write MDIO register");
- puts("mdior - read MDIO register");
- puts("mdiod - dump MDIO registers");
-#endif
- puts("");
- puts("crc - compute CRC32 of a part of the address space");
- puts("ident - display identifier");
- puts("");
- puts("flush_cpu_dcache - flush CPU data cache");
-#ifdef CONFIG_L2_SIZE
- puts("flush_l2_cache - flush L2 cache");
-#endif
- puts("");
-#ifdef CSR_CTRL_BASE
- puts("reboot - reset processor");
-#endif
-#ifdef CSR_ETHMAC_BASE
- puts("netboot - boot via TFTP");
-#endif
- puts("serialboot - boot via SFL");
-#ifdef FLASH_BOOT_ADDRESS
- puts("flashboot - boot from flash");
-#endif
-#ifdef ROM_BOOT_ADDRESS
- puts("romboot - boot from embedded rom");
-#endif
- puts("");
-#ifdef CSR_SDRAM_BASE
- puts("memtest - run a memory test");
-#endif
- puts("");
-#ifdef CSR_SDCORE_BASE
- puts("sdclk <freq> - SDCard set clk frequency (Mhz)");
- puts("sdinit - SDCard initialization");
- puts("sdtest <loops> - SDCard test");
-#endif
-#ifdef USDDRPHY_DEBUG
- puts("");
- puts("sdram_cdly value - Set SDRAM clk/cmd delay");
- puts("sdram_cal - run SDRAM calibration");
- puts("sdram_mpr - read SDRAM MPR");
- puts("sdram_mrwr reg value - write SDRAM mode registers");
- puts("sdram_cdly_scan enabled - enable/disable cdly scan");
-#endif
-#ifdef CSR_SPISDCARD_BASE
- puts("spisdcardboot - boot from SDCard via SPI hardware bitbang");
-#endif
-}
-
-static char *get_token(char **str)
-{
- char *c, *d;
-
- c = (char *)strchr(*str, ' ');
- if(c == NULL) {
- d = *str;
- *str = *str+strlen(*str);
- return d;
- }
- *c = 0;
- d = *str;
- *str = c+1;
- return d;
-}
-
-#ifdef CSR_CTRL_BASE
-static void reboot(void)
-{
- ctrl_reset_write(1);
-}
-#endif
-
-static void do_command(char *c)
-{
- char *token;
-
- token = get_token(&c);
-
- if(strcmp(token, "mr") == 0) mr(get_token(&c), get_token(&c));
- else if(strcmp(token, "mw") == 0) mw(get_token(&c), get_token(&c), get_token(&c));
- else if(strcmp(token, "mc") == 0) mc(get_token(&c), get_token(&c), get_token(&c));
-#if (defined CSR_SPIFLASH_BASE && defined SPIFLASH_PAGE_SIZE)
- else if(strcmp(token, "fw") == 0) fw(get_token(&c), get_token(&c), get_token(&c));
- else if(strcmp(token, "fe") == 0) fe();
-#endif
-#ifdef CSR_ETHPHY_MDIO_W_ADDR
- else if(strcmp(token, "mdiow") == 0) mdiow(get_token(&c), get_token(&c), get_token(&c));
- else if(strcmp(token, "mdior") == 0) mdior(get_token(&c), get_token(&c));
- else if(strcmp(token, "mdiod") == 0) mdiod(get_token(&c), get_token(&c));
-#endif
- else if(strcmp(token, "crc") == 0) crc(get_token(&c), get_token(&c));
- else if(strcmp(token, "ident") == 0) ident();
-
- else if(strcmp(token, "flush_cpu_dcache") == 0) flush_cpu_dcache();
-#ifdef CONFIG_L2_SIZE
- else if(strcmp(token, "flush_l2_cache") == 0) flush_l2_cache();
-#endif
-
-#ifdef CSR_CTRL_BASE
- else if(strcmp(token, "reboot") == 0) reboot();
-#endif
-#ifdef FLASH_BOOT_ADDRESS
- else if(strcmp(token, "flashboot") == 0) flashboot();
-#endif
-#ifdef ROM_BOOT_ADDRESS
- else if(strcmp(token, "romboot") == 0) romboot();
-#endif
- else if(strcmp(token, "serialboot") == 0) serialboot();
-#ifdef CSR_ETHMAC_BASE
- else if(strcmp(token, "netboot") == 0) netboot();
-#endif
-
- else if(strcmp(token, "help") == 0) help();
-
-#ifdef CSR_SDRAM_BASE
- else if(strcmp(token, "sdrrow") == 0) sdrrow(get_token(&c));
- else if(strcmp(token, "sdrsw") == 0) sdrsw();
- else if(strcmp(token, "sdrhw") == 0) sdrhw();
- else if(strcmp(token, "sdrrdbuf") == 0) sdrrdbuf(-1);
- else if(strcmp(token, "sdrrd") == 0) sdrrd(get_token(&c), get_token(&c));
- else if(strcmp(token, "sdrrderr") == 0) sdrrderr(get_token(&c));
- else if(strcmp(token, "sdrwr") == 0) sdrwr(get_token(&c));
-#ifdef CSR_DDRPHY_BASE
- else if(strcmp(token, "sdrinit") == 0) sdrinit();
-#ifdef SDRAM_PHY_WRITE_LEVELING_CAPABLE
- else if(strcmp(token, "sdrwlon") == 0) sdrwlon();
- else if(strcmp(token, "sdrwloff") == 0) sdrwloff();
-#endif
- else if(strcmp(token, "sdrlevel") == 0) sdrlevel();
-#endif
- else if(strcmp(token, "memtest") == 0) memtest();
-#endif
-
-#ifdef CSR_SDCORE_BASE
- else if(strcmp(token, "sdclk") == 0) sdclk_set_clk(atoi(get_token(&c)));
- else if(strcmp(token, "sdinit") == 0) sdcard_init();
- else if(strcmp(token, "sdtest") == 0) sdcard_test(atoi(get_token(&c)));
-#endif
-#ifdef USDDRPHY_DEBUG
- else if(strcmp(token, "sdram_cdly") == 0)
- ddrphy_cdly(atoi(get_token(&c)));
- else if(strcmp(token, "sdram_cal") == 0)
- sdrcal();
- else if(strcmp(token, "sdram_mpr") == 0)
- sdrmpr();
- else if(strcmp(token, "sdram_mrwr") == 0) {
- unsigned int reg;
- unsigned int value;
- reg = atoi(get_token(&c));
- value = atoi(get_token(&c));
- sdrsw();
- printf("Writing 0x%04x to SDRAM mode register %d\n", value, reg);
- sdrmrwr(reg, value);
- sdrhw();
- }
- else if(strcmp(token, "sdram_cdly_scan") == 0) {
- unsigned int enabled;
- enabled = atoi(get_token(&c));
- sdr_cdly_scan(enabled);
- }
-#endif
-#ifdef CSR_SPISDCARD_BASE
- else if(strcmp(token, "spisdcardboot") == 0) spisdcardboot();
-#endif
-
- else if(strcmp(token, "") != 0)
- printf("Command not found\n");
-}
+#include "command.h"
static void boot_sequence(void)
{
int main(int i, char **c)
{
char buffer[CMD_LINE_BUFFER_SIZE];
+ char *params[MAX_PARAM];
+ char *command;
+ struct command_struct *cmd;
+ int nb_params;
int sdr_ok;
+
#ifdef CONFIG_CPU_HAS_INTERRUPT
irq_setmask(0);
irq_setie(1);
readline(buffer, CMD_LINE_BUFFER_SIZE);
if (buffer[0] != 0) {
printf("\n");
- do_command(buffer);
+ nb_params = get_param(buffer, &command, params);
+ cmd = command_dispatcher(command, nb_params, params);
+ if (!cmd)
+ printf("Command not found");
}
printf("\n%s", PROMPT);
}
printf("SDRAM now under hardware control\n");
}
-void sdrrow(char *_row)
+void sdrrow(unsigned int row)
{
- char *c;
- unsigned int row;
-
- if(*_row == 0) {
+ if(row == 0) {
sdram_dfii_pi0_address_write(0x0000);
sdram_dfii_pi0_baddress_write(0);
command_p0(DFII_COMMAND_RAS|DFII_COMMAND_WE|DFII_COMMAND_CS);
cdelay(15);
- printf("Precharged\n");
} else {
- row = strtoul(_row, &c, 0);
- if(*c != 0) {
- printf("incorrect row\n");
- return;
- }
sdram_dfii_pi0_address_write(row);
sdram_dfii_pi0_baddress_write(0);
command_p0(DFII_COMMAND_RAS|DFII_COMMAND_CS);
cdelay(15);
- printf("Activated row %d\n", row);
}
}
printf("\n");
}
-void sdrrd(char *startaddr, char *dq)
+void sdrrd(unsigned int addr, int dq)
{
- char *c;
- unsigned int addr;
- int _dq;
-
- if(*startaddr == 0) {
- printf("sdrrd <address>\n");
- return;
- }
- addr = strtoul(startaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect address\n");
- return;
- }
- if(*dq == 0)
- _dq = -1;
- else {
- _dq = strtoul(dq, &c, 0);
- if(*c != 0) {
- printf("incorrect DQ\n");
- return;
- }
- }
-
sdram_dfii_pird_address_write(addr);
sdram_dfii_pird_baddress_write(0);
command_prd(DFII_COMMAND_CAS|DFII_COMMAND_CS|DFII_COMMAND_RDDATA);
cdelay(15);
- sdrrdbuf(_dq);
+ sdrrdbuf(dq);
}
-void sdrrderr(char *count)
+void sdrrderr(int count)
{
int addr;
- char *c;
- int _count;
int i, j, p;
unsigned char prev_data[SDRAM_PHY_PHASES][DFII_PIX_DATA_BYTES];
unsigned char errs[SDRAM_PHY_PHASES][DFII_PIX_DATA_BYTES];
unsigned char new_data[DFII_PIX_DATA_BYTES];
- if(*count == 0) {
- printf("sdrrderr <count>\n");
- return;
- }
- _count = strtoul(count, &c, 0);
- if(*c != 0) {
- printf("incorrect count\n");
- return;
- }
-
for(p=0;p<SDRAM_PHY_PHASES;p++)
for(i=0;i<DFII_PIX_DATA_BYTES;i++)
errs[p][i] = 0;
csr_rd_buf_uint8(sdram_dfii_pix_rddata_addr[p],
prev_data[p], DFII_PIX_DATA_BYTES);
- for(j=0;j<_count;j++) {
+ for(j=0;j<count;j++) {
command_prd(DFII_COMMAND_CAS|DFII_COMMAND_CS|DFII_COMMAND_RDDATA);
cdelay(15);
for(p=0;p<SDRAM_PHY_PHASES;p++) {
printf("\n");
}
-void sdrwr(char *startaddr)
+void sdrwr(unsigned int addr)
{
int i, p;
- char *c;
- unsigned int addr;
unsigned char buf[DFII_PIX_DATA_BYTES];
- if(*startaddr == 0) {
- printf("sdrwr <address>\n");
- return;
- }
- addr = strtoul(startaddr, &c, 0);
- if(*c != 0) {
- printf("incorrect address\n");
- return;
- }
-
for(p=0;p<SDRAM_PHY_PHASES;p++) {
for(i=0;i<DFII_PIX_DATA_BYTES;i++)
buf[i] = 0x10*p + i;
void sdrsw(void);
void sdrhw(void);
-void sdrrow(char *_row);
+void sdrrow(unsigned int row);
void sdrrdbuf(int dq);
-void sdrrd(char *startaddr, char *dq);
-void sdrrderr(char *count);
-void sdrwr(char *startaddr);
+void sdrrd(unsigned int addr, int dq);
+void sdrrderr(int count);
+void sdrwr(unsigned int addr);
void sdrwlon(void);
void sdrwloff(void);