Commit 524c7f61 authored by Angus Ainslie's avatar Angus Ainslie

m4 : add spi code

* add interrutps for times and uart code
* add spi code with interrupts

caveat: interrupts are not firing so the handlers are not getting
called. There is a possibility that they are firing and the A53
core is handling them before the M4 can.
parent dfa430c7
......@@ -7,7 +7,7 @@ CFLAGS += -g
CFLAGS += -march=armv7e-m -mthumb
AFLAGS += -march=armv7e-m -mthumb
OBJS = m4_start.o m4_main.o iomux-v3.o ddr_loader.o gpio.o timer.o uart.o
OBJS = m4_start.o m4_main.o iomux-v3.o ddr_loader.o gpio.o timer.o uart.o usdhc.c spi.c
all: m4.bin
......
source [find interface/ftdi/dp_busblaster.cfg]
source [find nxp_mcimx8m-evk.cfg]
reset_config srst_only srst_push_pull srst_nogate
source [find board/nxp_mcimx8m-evk.cfg]
#reset_config srst_only srst_push_pull srst_nogate
......@@ -6,19 +6,40 @@
#ifndef __M4_H__
#define __M4_H_
#include "spi.h"
#define NIRQ 256
#if !defined( __ASSEMBLER__ )
#include "usdhc.h"
#include "uart.h"
#include "spi.h"
#include "timer.h"
static void (*cortexM4_irq_table[])(void);
struct irq_vector {
int irq_num;
void *func;
};
struct irq_vector irq_vectors[] = {
{ USDHC1_INTR, usdhc1_isr },
{ USDHC2_INTR, usdhc2_isr },
{ UART1_INTR, uart1_isr },
{ UART2_INTR, uart2_isr },
{ UART3_INTR, uart3_isr },
{ UART4_INTR, uart4_isr },
{ TIMER1_INTR, timer1_isr },
{ TIMER2_INTR, timer2_isr },
{ TIMER3_INTR, timer3_isr },
{ TIMER4_INTR, timer4_isr },
{ TIMER5_INTR, timer5_isr },
{ TIMER6_INTR, timer6_isr },
{ ECSPI1_INTR, ecspi1_isr },
{ ECSPI2_INTR, ecspi2_isr },
{ ECSPI3_INTR, ecspi3_isr },
{ 0, 0 }
};
#endif /* __ASSEMBLER__ */
#endif /* __M4_H__ */
......@@ -14,6 +14,7 @@
#include "gpio.h"
#include "timer.h"
#include "uart.h"
#include "usdhc.h"
#define TCMU_BASE 0x20000000
#define TCMU_SIZE 0x20000
......@@ -48,6 +49,7 @@ void check_rdc(void)
int i;
uint32_t reg;
int p_check[] = { 0, 13,14,15,46,47,48, 70, 102,104, 105, -1 };
int clk_check[] = { 101, 102, -1 };
/* RDC_MDA1 */
reg = __raw_readl((void *)(0x303D0000 + 0x200 + (0x4d)));
......@@ -95,7 +97,8 @@ void check_rdc(void)
xputs( "\r\n" );
}
for( i=0; i<190; i++)
i=-1;
while( clk_check[++i] != -1 )
{
xputs( "Clock index " );
xputint( i );
......@@ -119,12 +122,57 @@ void check_rdc(void)
}
}
int default_ISR(void)
{
xputs("un-handled IRQ\r\n");
return 1;
}
void
cortexM4_init_irqs(void)
{
struct irq_vector *vectp;
int i;
xputs("Cortex M4 initializing interrupt vectors\r\n");
vectp = irq_vectors;
for (i=0; i<NIRQ; i++)
cortexM4_irq_table[i] = (void *)default_ISR;
while(vectp->irq_num) {
xputs("Cortex M4 adding isr ");
xputint( vectp->irq_num );
xputs(" ");
xputhex( vectp->irq_num );
xputs(" ");
xputhex( (uint32_t)vectp->func );
xputs("\r\n");
cortexM4_irq_table[vectp->irq_num] = vectp->func;
vectp++;
}
}
void scan_mmc()
{
int i;
xputs("Scanning MMC\r\n");
usdhc_sw_reset(0);
}
void
cortexM4_main(void)
{
uint32_t cmd_data = 0, st_data, arg_data, reg;
int i, j;
cortexM4_init_irqs();
__raw_writel(0, (void *)MB_CMD_A53);
__raw_writel(0, (void *)MB_ARG_A53);
__raw_writel(0, (void *)MB_ST_A53);
......@@ -136,13 +184,15 @@ cortexM4_main(void)
//iomux_v3_setup_pad(IMX8MQ_PAD_UART1_TXD__UART1_TX);
//iomux_v3_setup_pad(IMX8MQ_PAD_UART2_RXD__UART2_RX);
//iomux_v3_setup_pad(IMX8MQ_PAD_UART2_TXD__UART2_TX);
iomux_v3_setup_pad(IMX8MQ_PAD_GPIO1_IO13__GPIO1_IO13);
//iomux_v3_setup_pad(IMX8MQ_PAD_GPIO1_IO13__GPIO1_IO13);
//iomux_v3_setup_pad(IMX8MQ_PAD_GPIO1_IO13__PWM2_OUT);
//setup_uart(CONSOLE_PORT,115200);
xputs("Cortex M4 starting\r\n");
//scan_mmc();
for (;;)
{
xputs("Cortex M4 waiting for commands\r\n");
......
This diff is collapsed.
/*
* Copyright (C) 2018 Purism
*
* SPDX-License-Identifier: GPL-3.0+
*/
#ifndef __SPI_H__
#define __SPI_H_
#define ECSPI1_INTR 31
#define ECSPI2_INTR 32
#define ECSPI3_INTR 33
#define SPI_CPHA 0x01
#define SPI_CPOL 0x02
#define SPI_MODE_0 (0|0)
#define SPI_MODE_1 (0|SPI_CPHA)
#define SPI_MODE_2 (SPI_CPOL|0)
#define SPI_MODE_3 (SPI_CPOL|SPI_CPHA)
#define SPI_CS_HIGH 0x04
#define SPI_LSB_FIRST 0x08
#define SPI_3WIRE 0x10
#define SPI_LOOP 0x20
#define SPI_NO_CS 0x40
#define SPI_READY 0x80
#if !defined( __ASSEMBLER__ )
extern int ecspi1_isr();
extern int ecspi2_isr();
extern int ecspi3_isr();
extern int spi_transfer(int bus, uint8_t *tx_buf, uint8_t *rx_buf, int len);
#endif /* __ASSEMBLER__ */
#endif /* __SPI_H__ */
......@@ -19,6 +19,48 @@ uint32_t timer_base[] = {
TIMER_6_BASE
};
int timer1_isr(void)
{
xputs("timer isr1\r\n");
return 1;
}
int timer2_isr(void)
{
xputs("timer isr2\r\n");
return 1;
}
int timer3_isr(void)
{
xputs("timer isr3\r\n");
return 1;
}
int timer4_isr(void)
{
xputs("timer isr4\r\n");
return 1;
}
int timer5_isr(void)
{
xputs("timer isr5\r\n");
return 1;
}
int timer6_isr(void)
{
xputs("timer isr6\r\n");
return 1;
}
void timer_enable(int timer_n)
{
// 9. Enable GPT (EN=1) in GPT_CR register.
......@@ -81,6 +123,8 @@ void timer_init(int timer_n, int hs)
// 7. Clear GPT status register (GPT_SR) (i.e., w1c).
__raw_writel(0x3f, (void *)timer_base[timer_n] + GPT_SR_OFST);
/* enable interrupts */
__raw_writel(0x3f, (void *)timer_base[timer_n] + GPT_IR_OFST);
// 8. Set ENMOD=1 in GPT_CR register, to bring GPT counter to 0x00000000.
__raw_set_maskl(GPT_ENMOD_ENABLE, (void *)timer_base[timer_n] + GPT_CR_OFST);
......@@ -140,7 +184,6 @@ uint32_t msleep( uint32_t msec )
if(reg & GPT_OF1_FLAG)
done = 1;
reg = __raw_readl((void *)timer_base[timer] + GPT_CNT_OFST);
if( reg != 0 )
if( reg > msec )
{
done = 1;
......
......@@ -68,7 +68,20 @@
#define GPT_OF2_FLAG (1<<1)
#define GPT_OF1_FLAG 1
extern uint32_t usleep(uint32_t usec);
extern uint32_t msleep(uint32_t msec);
#define TIMER1_INTR 55
#define TIMER2_INTR 54
#define TIMER3_INTR 53
#define TIMER4_INTR 52
#define TIMER5_INTR 51
#define TIMER6_INTR 46
int timer1_isr(void);
int timer2_isr(void);
int timer3_isr(void);
int timer4_isr(void);
int timer5_isr(void);
int timer6_isr(void);
uint32_t usleep(uint32_t usec);
uint32_t msleep(uint32_t msec);
#endif
......@@ -34,6 +34,26 @@
#define CONSOLE_PORT 1
#define DEBUG
int uart1_isr(void)
{
return 1;
}
int uart2_isr(void)
{
return 1;
}
int uart3_isr(void)
{
return 1;
}
int uart4_isr(void)
{
return 1;
}
void xputc(char c, int console)
{
#ifdef DEBUG
......
......@@ -62,6 +62,15 @@
#define IMX_UCR2_SRST (1<<0)
#define IMX_UCR3_ADNIMP (1<<7)
#define UART1_INTR 26
#define UART2_INTR 27
#define UART3_INTR 28
#define UART4_INTR 29
int uart1_isr(void);
int uart2_isr(void);
int uart3_isr(void);
int uart4_isr(void);
void xputc(char c, int console);
void xputs(char *s);
void xputhex_digit(uint8_t d);
......
This diff is collapsed.
/*
* Copyright (C) 2018 Purism
*
* SPDX-License-Identifier: GPL-3.0+
*/
#ifndef __USDHC_H__
#define __USDHC_H__
#define USDHC1_INTR 22
#define USDHC2_INTR 23
#if !defined( __ASSEMBLER__ )
extern int usdhc1_isr();
extern int usdhc2_isr();
int usdhc_sw_reset(int ctrl);
#endif /* __ASSEMBLER__ */
#endif /* __USDHC_H__ */
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment