Commit Graph

8973 Commits

Author SHA1 Message Date
enjoy-digital 6c6cfeae7f
Merge pull request #1763 from josuah/radiant_wsl2
Allow use of Windows-side (.exe) Radiant toolchain
2023-09-03 19:27:32 +02:00
Josuah Demangeon 2e6ddd9dd9 build/lattice/radiant: allow use of Windows-side (.exe) radiant toolchain under WSL2 2023-09-02 22:28:40 +02:00
Dolu1990 8853215033
Merge pull request #1762 from motec-research/dma_fix
proof of concept coherent dma fix
2023-09-02 08:22:40 +02:00
Andrew Dennison 1bb4d299a6 vexrisc_smp: fix DMA bus address_width calculation 2023-09-02 11:46:11 +10:00
Andrew Dennison 48ab96fd43 soc/intregation: fix cpu name in logging
Fixed CPU name being reported as irq name in logging.

```
INFO:SoC:CPU vexriscv_smp adding Interrupt(s).
INFO:SoCIRQHandler:noirq IRQ added at Location 0.
INFO:SoC:CPU noirq adding DMA Bus.
INFO:SoCDMABusHandler:Creating Bus Handler...
```
2023-09-02 11:46:11 +10:00
Florent Kermarrec 57faa9102f CHANGES: Update. 2023-09-01 12:40:03 +02:00
Florent Kermarrec f473261bc6 soc/dma_bus: Make SoCDMABusHandler use the Bus Standard of the DMA Bus defined in the CPU.
Also simplify code by using automatic Bus conversion of SoCBusHandler.
2023-09-01 12:19:11 +02:00
Florent Kermarrec db2ad78860 interconnect/wishbone: Add address_width property to make sure all interfaces (Wishbone/AXI-Lite/AXI) have it. 2023-09-01 12:16:15 +02:00
enjoy-digital 33efa09663
Merge pull request #1760 from motec-research/dts_linux_fix
tools/litex_json2dts_linux: fix missed sdcard_ references
2023-09-01 10:46:04 +02:00
Richard Tucker 058cdd646b tools/litex_json2dts_linux: fix missed sdcard_ references 2023-09-01 16:54:41 +10:00
enjoy-digital 14012263af
Merge pull request #1758 from motec-research/spi_mmap_fix
soc/cores/spi_mmap: Fix clock divider
2023-09-01 08:38:53 +02:00
Radek Pesina d494e30166 soc/cores/spi_mmap: Fix clock divider 2023-09-01 12:34:51 +10:00
Florent Kermarrec 405296b7fd interconnect/axi/axi_full: Fix missing switch to LiteXModule. 2023-08-31 19:36:21 +02:00
Gwenhael Goavec-Merou 516038ce76 soc/cores/clock/efinix: don't hardcore create_clock (fix warning because clock is created after set_false_path), explicit clock name (fix warning when signal is absorbed) 2023-08-31 17:24:58 +02:00
Gwenhael Goavec-Merou fadf47d353 build/lattice/trellis: fix add_period_constraint signature (missing keep arg) 2023-08-31 16:52:48 +02:00
Florent Kermarrec 41357aba7d xilinx/vivado: Fix issue with #1755. 2023-08-31 16:38:50 +02:00
Florent Kermarrec ad924a522a interconnect/stream/AsyncFIFO: Remove Efinix workaround since seems to be solved with Efinity 2023.x. 2023-08-31 16:03:52 +02:00
enjoy-digital 124e0d22c9
Merge pull request #1755 from enjoy-digital/allows_clk_name_override
build/xx/toolchains: allows override clock naming
2023-08-31 15:57:39 +02:00
Gwenhael Goavec-Merou 46800176ae build/xx/toolchains: allows override clock naming 2023-08-31 15:18:15 +02:00
Gwenhael Goavec-Merou 2a7caa2696 build: all platforms: override add_period_constraint only when required 2023-08-31 12:29:09 +02:00
Gwenhael Goavec-Merou 3f43481eb9 build/efinix/efinity: build_timing_constraints: set_false_path is unidirectional -> add another one to -> from_ 2023-08-31 11:42:07 +02:00
Gwenhael Goavec-Merou a071cc343d litex/soc/integration/soc: add_etherxx: when eth_rx_clk is eth_tx_clk only apply constraints on eth_rx_clk 2023-08-31 11:36:24 +02:00
Florent Kermarrec 9854c9f322 CHANGES: Update. 2023-08-30 18:11:11 +02:00
Florent Kermarrec ff0df100e9 build/efinix: Add get_pin (from sig) to EfinixPlatform and use it to simplify/fix IOs exclusion. 2023-08-30 18:08:40 +02:00
Florent Kermarrec 72590dfde3 software/libliteeth: Fix udp_set_callback warning. 2023-08-30 17:44:00 +02:00
Florent Kermarrec 434e2225ea software/liblitedram: Fix swap_bit warning. 2023-08-30 17:22:57 +02:00
Florent Kermarrec c2714df198 build/efinix/common: Add initial EfinixDDROutput/EfinixDDRInput implementation.
Still need to figure out a few things:
- Clk is passed as a string for now.
- IOs exclusion still handled externally.
2023-08-30 11:28:48 +02:00
Florent Kermarrec c0ab4ed1c1 build/io: Allow passing clk as str on DDRInput/Output, wrap DDROutput IOs and minor ident fixes. 2023-08-30 10:52:13 +02:00
Florent Kermarrec 6dff371835 build/efinix/common: Simplify IO exclusion in EfinixTristateImpl and fix corner cases (ex eth_mdio that was not automatically excluded). 2023-08-30 09:16:46 +02:00
Florent Kermarrec 9528f89d45 CHANGES: Update. 2023-08-29 17:15:45 +02:00
Florent Kermarrec 85dadb827a clock/gowin_gw5a: Fix copyright. 2023-08-29 14:25:04 +02:00
enjoy-digital c122fef5ac
Merge pull request #1741 from Icenowy/gw5apll
soc/cores/clock: initial GW5A support
2023-08-29 14:21:02 +02:00
Icenowy Zheng 1636c0ef8d soc/cores/clock: initial GW5A support
GW5A has different PLLs than GW1N/GW2A, with multiple individual
ODIV's. GW5A-25 has a different PLL with GW5A[S]T-138, with lack of
dynamic control.

Add basic support for them.

Signed-off-by: Icenowy Zheng <uwu@icenowy.me>
2023-08-29 15:39:25 +08:00
Florent Kermarrec 82602f660c interconnect/stream: Fix #1736. 2023-08-28 16:19:31 +02:00
Florent Kermarrec 70e52b76fa CHANGES: Update. 2023-08-28 16:04:43 +02:00
Florent Kermarrec d29d2c09bb interconnect/stream: Minor review/cleanup. 2023-08-28 16:02:52 +02:00
enjoy-digital 8efcc4fdea
Merge pull request #1736 from rowanG077/buf-endpoint-cfg
soc/interconnect/stream: BufferizeEndpoints params
2023-08-28 15:58:46 +02:00
Gwenhael Goavec-Merou f7b35f09ae build/efinix/efinity: don't hardcode efinity version, read from scripts/sw_version.txt 2023-08-28 14:43:17 +02:00
Florent Kermarrec 8f54386aab gen/fhdl/module: Add some comments. 2023-08-24 09:17:35 +02:00
enjoy-digital a125f9aa6f
Merge pull request #1752 from enjoy-digital/naxriscv_update
cpu/naxriscv: Update recommended version.
2023-08-22 16:29:08 +02:00
Florent Kermarrec 6d8c04b401 cpu/naxriscv: Update recommended version. 2023-08-22 15:50:08 +02:00
Gwenhael Goavec-Merou 1520d0f382
Merge pull request #1745 from alexey-morozov/master
Litex offline installation fix
2023-08-16 15:18:57 +02:00
Alexey Morozov cd1012470e
To allow offline installation, the "liteiclink" package has to be installed before the "liteeth" package. Otherwise, to satisfy the dependency requirements, the setup will attempt to download the "liteiclink" package from the internet and will consequently fail. 2023-08-16 09:39:03 +02:00
Gwenhael Goavec-Merou 4d7a7f5ba1
Merge pull request #1742 from Icenowy/gwddrfix
build/gowin/common: Fix DDRInput
2023-08-16 08:01:29 +02:00
Icenowy Zheng c1d8db396d build/gowin/common: Fix DDRInput
The DDRInput of Gowin seems to be never used and contains a typo that
prevents it from being really used.

Fix this typo.

Signed-off-by: Icenowy Zheng <uwu@icenowy.me>
2023-08-11 14:56:56 +08:00
Florent Kermarrec 577674bff2 test: Add minimal test_spi_mmap with simulation of SPIMaster. 2023-08-04 17:51:22 +02:00
Florent Kermarrec 688dae0112 cores/spi: Add new SPIMMAP core allowing doing SPI accesses directly from MMAP.
Implements a new SPIMMAP module, allowing accessing multiple SPI peripherals directly
from MMAP. It allows configurable SPI transactions: mode, bit order, and data width.

Developed and funded through a collaboration with MoTeC.

Example of integration:

# SPI MMAP ---------------------------------------------------------------------------------
spi_pads = Record([("clk", 1), ("cs_n", 8), ("mosi", 1), ("miso", 1)])
spi_mmap_tx_region = SoCRegion(origin=0x8000_0000, size=4096, cached=False)
spi_mmap_rx_region = SoCRegion(origin=0x8000_1000, size=4096, cached=False)
self.spi_mmap = SPIMMAP(
    pads          = spi_pads,
    data_width    = 32,
    sys_clk_freq  = sys_clk_freq,
    tx_origin     = spi_mmap_tx_region.origin,
    rx_origin     = spi_mmap_rx_region.origin,
    tx_fifo_depth = 32,
    rx_fifo_depth = 32,
)

self.bus.add_slave(name="spi_tx",
    slave  = self.spi_mmap.tx_mmap.bus,
    region = spi_mmap_tx_region,
)
self.bus.add_slave(name="spi_rx",
    slave  = self.spi_mmap.rx_mmap.bus,
    region = spi_mmap_rx_region,
)
self.irq.add("spi_mmap", use_loc_if_exists=True)


Example of use from CPU C firmware:

/* SPI TX Offsets */
#define SPI_TX_CTRL_ENABLE    (1 << 0)
#define SPI_TX_CTRL_THRESHOLD (1 << 16)

#define SPI_TX_STAT_ONGOING   (1 << 0)
#define SPI_TX_STAT_EMPTY     (1 << 1)
#define SPI_TX_STAT_FULL      (1 << 2)
#define SPI_TX_STAT_LEVEL     (1 << 16)

/* SPI RX Offsets */
#define SPI_RX_CTRL_ENABLE    (1 << 0)
#define SPI_RX_CTRL_THRESHOLD (1 << 16)

#define SPI_RX_STAT_ONGOING   (1 << 0)
#define SPI_RX_STAT_EMPTY     (1 << 1)
#define SPI_RX_STAT_FULL      (1 << 2)
#define SPI_RX_STAT_LEVEL     (1 << 16)

/* SPI TX/RX Engine */
#define SPI_TX_RX_ENGINE_ENABLE (1 << 0)

/* SPI SLOT Offsets */
#define SPI_SLOT_ENABLE   (1 <<  0)
#define SPI_SLOT_MODE     (1 <<  1)
#define SPI_SLOT_LENGTH   (1 <<  3)
#define SPI_SLOT_BITORDER (1 <<  5)
#define SPI_SLOT_LOOPBACK (1 <<  6)
#define SPI_SLOT_DIVIDER  (1 << 16)

/* SPI SLOT Values */
#define SPI_SLOT_MODE_0 0b00
#define SPI_SLOT_MODE_3 0b11

#define SPI_SLOT_LENGTH_32B 0b00
#define SPI_SLOT_LENGTH_16B 0b01
#define SPI_SLOT_LENGTH_8B  0b10

#define SPI_SLOT_BITORDER_MSB_FIRST 0b0
#define SPI_SLOT_BITORDER_LSB_FIRST 0b1

#define SPI_SLOT_EV_TX (1 << 0)
#define SPI_SLOT_EV_RX (1 << 1)


/* Test SPI with various length (BE) */
void test_spi_length_8_16_32(void) {
	volatile unsigned char  *spi_tx_8  = (unsigned char  *)SPI_TX_BASE;
	volatile unsigned short *spi_tx_16 = (unsigned short *)SPI_TX_BASE;
	volatile unsigned int   *spi_tx_32 = (unsigned int   *)SPI_TX_BASE;

	volatile unsigned char  *spi_rx_8  = (unsigned char  *)SPI_RX_BASE;
	volatile unsigned short *spi_rx_16 = (unsigned short *)SPI_RX_BASE;
	volatile unsigned int   *spi_rx_32 = (unsigned int   *)SPI_RX_BASE;

	int errors = 0;

	printf("Test SPI with various length (BE): 8, 16 and 32-bit...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control1_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control2_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control3_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 8-bit transfers */
	spi_tx_8[0]  = 0x5a;
	spi_tx_8[4]  = 0x01;
	spi_tx_8[8]  = 0x5a;
	spi_tx_8[12] = 0x01;

	/* TX 16-bit transfers */
	spi_tx_16[0] = 0x5aa5;
	spi_tx_16[2] = 0x0102;
	spi_tx_16[4] = 0x5aa5;
	spi_tx_16[6] = 0x0102;

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0x5aa55aa5;
	spi_tx_32[1] = 0x01020304;
	spi_tx_32[2] = 0x5aa55aa5;
	spi_tx_32[3] = 0x01020304;

	/* Small delay */
	busy_wait(1);

	/* Read RX 8-bit transfers */
	if (spi_rx_8[ 0] != 0x5a)
		errors++;
	if (spi_rx_8[ 4] != 0x01)
		errors++;
	if (spi_rx_8[ 8] != 0x5a)
		errors++;
	if (spi_rx_8[12] != 0x01)
		errors++;

	/* Read RX 16-bit transfers */
	if (spi_rx_16[0] != 0x5aa5)
		errors++;
	if (spi_rx_16[2] != 0x0102)
		errors++;
	if (spi_rx_16[4] != 0x5aa5)
		errors++;
	if (spi_rx_16[6] != 0x0102)
		errors++;

	/* Read RX 32-bit tranfers */
	if (spi_rx_32[0] != 0x5aa55aa5)
		errors++;
	if (spi_rx_32[1] != 0x01020304)
		errors++;
	if (spi_rx_32[2] != 0x5aa55aa5)
		errors++;
	if (spi_rx_32[3] != 0x01020304)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}

/* Test SPI with various clk divider */
void test_spi_clk_divider(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int errors = 0;

	printf("Test SPI with various clk divider: 4, 8, 16 and 32...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control1_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  8 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control2_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								 16 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control3_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								 32 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0x01020304;
	spi_tx_32[1] = 0x5aa55aa5;
	spi_tx_32[2] = 0x01020304;
	spi_tx_32[3] = 0x5aa55aa5;

	/* Small delay */
	busy_wait(1);

	/* Read RX 32-bit tranfers */
	if (spi_rx_32[0] != 0x01020304)
		errors++;
	if (spi_rx_32[1] != 0x5aa55aa5)
		errors++;
	if (spi_rx_32[2] != 0x01020304)
		errors++;
	if (spi_rx_32[3] != 0x5aa55aa5)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}

/* Test SPI with various SPI modes */
void test_spi_modes(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int errors = 0;

	printf("Test SPI with various SPI modes: 0 and 3...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control1_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_3 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0x5aa55aa5;
	spi_tx_32[1] = 0x5aa55aa5;

	/* Small delay */
	busy_wait(1);

	/* Read RX 32-bit tranfers */
	if (spi_rx_32[0] != 0x5aa55aa5)
		errors++;
	if (spi_rx_32[1] != 0x5aa55aa5)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}

/* Test SPI with various bitorders */
void test_spi_bitorders(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int errors = 0;

	printf("Test SPI with various bitorders: MSB and LSB first...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);
	spi_mmap_ctrl_slot_control1_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_LSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  4 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0xff000000;
	spi_tx_32[1] = 0xff000000;

	/* Small delay */
	busy_wait(1);

	/* Read RX 32-bit tranfers */
	if (spi_rx_32[0] != 0xff000000)
		errors++;
	if (spi_rx_32[1] != 0xff000000)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}

/* Test SPI TX/RX levels */
void test_spi_tx_rx_levels(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int i;
	int errors = 0;
	int pattern;

	printf("Test SPI TX/RX levels...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								128 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	pattern = 0x00000001;
	for (i=0; i<16; i++){
		if ((spi_mmap_ctrl_tx_status_read() >> 16) != i)
			errors++;
		spi_tx_32[0] = pattern;
	}

	/* Small delay */
	busy_wait(1);

	/* Read RX 32-bit tranfers */
	for (i=0; i<16; i++){
		pattern = spi_rx_32[0];
		if ((spi_mmap_ctrl_rx_status_read() >> 16) != (16-1-i))
			errors++;
	}

	if ((spi_mmap_ctrl_tx_status_read() >> 16) != 0)
		errors++;
	if ((spi_mmap_ctrl_rx_status_read() >> 16) != 0)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}

/* Test SPI TX/RX IRQs */
void test_spi_tx_rx_irqs(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int errors = 0;
	int data __attribute__((unused));

	printf("Test SPI TX/RX IRQs...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								128 * SPI_SLOT_DIVIDER
	);

	/* Enable TX/RX EventManager */
	spi_mmap_ev_enable_write(0);
	spi_mmap_ev_pending_write(spi_mmap_ev_pending_read());
	spi_mmap_ev_enable_write(SPI_SLOT_EV_TX | SPI_SLOT_EV_RX);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0x00000001;

	/* Small delay */
	busy_wait(1);

	/* Verify TX/RX events */
	if (spi_mmap_ev_pending_read() != (SPI_SLOT_EV_TX | SPI_SLOT_EV_RX))
		errors++;

	/* Read RX 32-bit tranfers */
	data = spi_rx_32[0];

	/* Clear events */
	spi_mmap_ev_pending_write(spi_mmap_ev_pending_read());

	/* Verify TX/RX events */
	if (spi_mmap_ev_pending_read() != 0)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}


/* Test SPI Back-to-Back */
void test_spi_back_to_back(void) {
	volatile unsigned int *spi_tx_32 = (unsigned int *)SPI_TX_BASE;
	volatile unsigned int *spi_rx_32 = (unsigned int *)SPI_RX_BASE;

	int errors = 0;

	printf("Test SPI Back-to-Back...\n");

	/* Configure Slots */
	spi_mmap_ctrl_slot_control0_write(
								  1 * SPI_SLOT_ENABLE   |
					SPI_SLOT_MODE_0 * SPI_SLOT_MODE     |
				SPI_SLOT_LENGTH_32B * SPI_SLOT_LENGTH   |
		SPI_SLOT_BITORDER_MSB_FIRST * SPI_SLOT_BITORDER |
								  1 * SPI_SLOT_LOOPBACK |
								  8 * SPI_SLOT_DIVIDER
	);

	/* Enable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(1 * SPI_TX_RX_ENGINE_ENABLE);

	/* TX 32-bit transfers */
	spi_tx_32[0] = 0x00000001;
	spi_tx_32[0] = 0x00000002;

	/* Small delay */
	busy_wait(1);

	/* Read RX 32-bit tranfers */
	if (spi_rx_32[0] != 0x00000001)
		errors++;
	if (spi_rx_32[0] != 0x00000002)
		errors++;

	/* Disable SPI Engine */
	spi_mmap_tx_rx_engine_control_write(0 * SPI_TX_RX_ENGINE_ENABLE);

	/* Result */
	printf("errors: %d\n", errors);
}
2023-08-04 17:44:54 +02:00
Florent Kermarrec 036193d046 CHANGES: Update. 2023-08-04 16:08:00 +02:00
Florent Kermarrec 587981a6b8 interconnect/csr_bus: Improve description. 2023-08-01 17:11:13 +02:00
Florent Kermarrec bfd4dcdefc interconnect/ahb: Cleanup and document a bit. 2023-08-01 16:52:20 +02:00