From b2df34e622ddee5d51beb1e9e93d4ecbb1745e55 Mon Sep 17 00:00:00 2001 From: Bent Bisballe Nyeng Date: Sun, 2 Jun 2013 18:25:46 +0200 Subject: Initial experiments with SPI. --- .gitignore | 11 + firmware/Makefile | 97 +++++ firmware/buspirate.cfg | 35 ++ firmware/makedev.sh | 1 + firmware/openocd.cfg | 34 ++ firmware/src/dac.c | 24 ++ firmware/src/dac.h | 7 + firmware/src/p2m.c | 126 ++++++ firmware/src/sample.h | 1108 ++++++++++++++++++++++++++++++++++++++++++++++++ firmware/src/uart.c | 169 ++++++++ firmware/src/uart.h | 50 +++ 11 files changed, 1662 insertions(+) create mode 100644 .gitignore create mode 100644 firmware/Makefile create mode 100644 firmware/buspirate.cfg create mode 100755 firmware/makedev.sh create mode 100644 firmware/openocd.cfg create mode 100644 firmware/src/dac.c create mode 100644 firmware/src/dac.h create mode 100644 firmware/src/p2m.c create mode 100644 firmware/src/sample.h create mode 100644 firmware/src/uart.c create mode 100644 firmware/src/uart.h diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..0fd2f37 --- /dev/null +++ b/.gitignore @@ -0,0 +1,11 @@ +toolchain/arm-toolchain +toolchain/build +toolchain/src +toolchain/tarballs +*.o +*.d +*.bin +*.hex +*.elf +*.map +*.dump \ No newline at end of file diff --git a/firmware/Makefile b/firmware/Makefile new file mode 100644 index 0000000..ef9b0e1 --- /dev/null +++ b/firmware/Makefile @@ -0,0 +1,97 @@ +#/* THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED +# * OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF +# * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. +# * THE AUTHORS SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR +# * CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER. USE IT AT YOUR OWN RISK */ + +ARCH = arm-none-eabi +top_srcdir=${PWD} +LPC=${top_srcdir}/lpc17xx +DRV=${top_srcdir}/drivers +SRC=${top_srcdir}/src + +PROJ=p2m +EXECNAME=$(PROJ).elf + +# Tool definitions +CC = $(ARCH)-gcc +LD = $(ARCH)-ld +AR = $(ARCH)-ar +AS = $(ARCH)-as +CP = $(ARCH)-objcopy +OD = $(ARCH)-objdump +SIZE = $(ARCH)-size +RM = rm +Q = # @./quiet "$@" + +# Flags +CFLAGS = -W -Wall -O0 --std=gnu99 -fgnu89-inline -mcpu=cortex-m3 -mthumb +CFLAGS += -ffunction-sections -fdata-sections +CFLAGS += -I${LPC} -I${DRV} +ASFLAGS = +LDFLAGS = --gc-sections + +STDLIB_LDFLAGS = +#STDLIB_LDFLAGS += -L/home/deva/lib/arm/arm-toolchain/lib/gcc/arm-none-eabi/4.6.2/ +#STDLIB_LDFLAGS += -L/home/deva/lib/arm/arm-toolchain/arm-none-eabi/lib/ +#STDLIB_LDFLAGS += -lc -lgcc + +CPFLAGS = +ODFLAGS = -x --syms +PRFLAGS ?= + +# Source files +LINKER_SCRIPT = ${LPC}/LPC17xx.ld +CSRCS = \ + ${LPC}/startup_LPC17xx.c \ + $(wildcard ${CMSIS}/*.c) \ + $(wildcard ${LPC}/*.c) \ + $(wildcard ${DRV}/*.c) \ + $(wildcard ${SRC}/*.c) +CSRCS += ${SRC}/${PROJ}.c +ASRCS = + + +OBJS = $(CSRCS:.c=.o) $(ASRCS:.s=.o) + +.PHONY: all size clean nuke + +all: ${PROJ}.bin ${PROJ}.hex + +size: ${PROJ}.elf + @$(SIZE) $< + +%.hex: %.elf + $Q $(CP) $(CPFLAGS) -O ihex $< $*.hex + +%.bin: %.elf + $Q $(CP) $(CPFLAGS) -O binary $< $*.bin + +${PROJ}.elf: $(LINKER_SCRIPT) $(OBJS) + $Q $(LD) -Map $(@:.elf=.map) $(LDFLAGS) -T $^ -o $@ $(STDLIB_LDFLAGS) + $Q $(OD) $(ODFLAGS) $@ > $(@:.elf=.dump) + @$(SIZE) $@ + +%.o: %.c + @$(CC) -MM $< -MF $*.d -MP + $Q $(CC) -c $(CFLAGS) $< -o $@ + +%.o: %.S + $Q $(AS) $(ASFLAGS) $< -o $@ + +clean: + @-$(RM) -f *.elf + @-\ +for D in "." "**"; do \ + $(RM) -f $$D/*.o $$D/*.d $$D/*.lst $$D/*.dump $$D/*.map; \ +done + +nuke: clean + -$(RM) -f *.hex *.bin + +.PHONY : flash +flash: $(EXECNAME) + $(CP) -O ihex $(EXECNAME) $(PROJ).hex + openocd -f openocd.cfg -c 'flash write_image erase $(PROJ).hex' -c 'verify_image $(PROJ).hex' -c 'reset run' + +-include $(CSRCS:.c=.d) diff --git a/firmware/buspirate.cfg b/firmware/buspirate.cfg new file mode 100644 index 0000000..8d85846 --- /dev/null +++ b/firmware/buspirate.cfg @@ -0,0 +1,35 @@ +# ========================================================= +# What: BusPirate Version 3b with OpenOCD support +# Using: USB serial on COM port 13 +# JTAG: +# See: http://dangerousprototypes.com/docs/Bus_Pirate_JTAG_connections_for_OpenOCD +# Note: 1) If you have "normal" mode AND "0" pullup, +# THEN do not connect Vpu & VTref! +# 2) Cygwin uses serial USB COM ports as: +# /dev/ttyS[N-1] == /dev/comN +# Make sure it's not already used with +# any other terminal or programs... +# ========================================================= +interface buspirate +# Not yet implemented properly... +#transport select jtag +# Set the serial port to be used: +buspirate_port /dev/buspirate +#buspirate_port /dev/ttyS12 +# Set "normal" or "fast" (~1 MHz)communication speed: +buspirate_speed normal +# Turn OFF the voltage regulator: +#buspirate_vreg 0 +# --------------------------------------------------------- +# Remember that VTref (Vcc) is connected to pull-up's. +# If you are NOT using pull-up's with "normal" drain +# pin-mode, then do NOT connect Vpu to VTref! +# --------------------------------------------------------- +buspirate_mode normal +buspirate_pullup 0 +# --------------------------------------------------------- +#buspirate_mode open-drain +#buspirate_pullup 1 +# --------------------------------------------------------- +# This depends on the cable, you are safe with this option: +reset_config srst_only \ No newline at end of file diff --git a/firmware/makedev.sh b/firmware/makedev.sh new file mode 100755 index 0000000..fc69fb2 --- /dev/null +++ b/firmware/makedev.sh @@ -0,0 +1 @@ +cd /dev; ln -s ttyUSB0 buspirate; ln -s ttyUSB1 ftdi diff --git a/firmware/openocd.cfg b/firmware/openocd.cfg new file mode 100644 index 0000000..44bdfb3 --- /dev/null +++ b/firmware/openocd.cfg @@ -0,0 +1,34 @@ +# This file is for use with the PhotonSaw LPC1769 based laserctrl board. +# The script will flash the main.bin file to the board and run it. +# To flash the board call with: +# $ openocd -f openocd-flash.cfg + +jtag_khz 1 + +# This is the JTAG connector I use +#source [find interface/olimex-arm-usb-tiny-h.cfg] +source [find interface/buspirate.cfg] + +# This is close enough to the board I use +source [find target/lpc1768.cfg] + +adapter_nsrst_assert_width 10 +adapter_nsrst_delay 2 +reset_config srst_only + +#adapter_khz 0 +adapter_khz 500 +#jtag_khz 100 + +init +sleep 200 +reset halt +#sleep 200 +#soft_reset_halt +wait_halt +mww 0x400FC040 0x01 +sleep 200 + +#flash write_image erase vcomdemo.hex +#verify_image vcomdemo.hex +#reset runq diff --git a/firmware/src/dac.c b/firmware/src/dac.c new file mode 100644 index 0000000..2773f00 --- /dev/null +++ b/firmware/src/dac.c @@ -0,0 +1,24 @@ +#include "dac.h" + +//#include "api.h" +#include + +void dac_init() +{ + // setup the related pin to DAC output + LPC_PINCON->PINSEL1 = 0x00200000; // set p0.26 to DAC output + + // Clock tick pr. sample delay (DAC clock) + LPC_DAC->DACCNTVAL = 2267; // 44111Hz + LPC_DAC->DACCTRL = (0x1<<1)|(0x1<<2); + LPC_SC->PCLKSEL0 |= (0x1 << 22); // Use full 100MHz clock +} + +#define VOL 1 +void dac_play_samples(const short int *samples, int size) +{ + for(int i = 0; i < size; i++) { + LPC_DAC->DACR = ((unsigned short)(samples[i] * VOL)<< 6);// | DAC_BIAS; + for(int j = 0; j < 100; j++) { if(!LPC_DAC->DACR) LPC_DAC->DACR = 0; } + } +} diff --git a/firmware/src/dac.h b/firmware/src/dac.h new file mode 100644 index 0000000..6ee34bc --- /dev/null +++ b/firmware/src/dac.h @@ -0,0 +1,7 @@ +#ifndef __DAC_H__ +#define __DAC_H__ + +void dac_init(); +void dac_play_samples(const short int *samples, int size); + +#endif/*__DAC_H__*/ diff --git a/firmware/src/p2m.c b/firmware/src/p2m.c new file mode 100644 index 0000000..422cd34 --- /dev/null +++ b/firmware/src/p2m.c @@ -0,0 +1,126 @@ +/* THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED + * OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE. + * THE AUTHORS SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR + * CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER. USE IT AT YOUR OWN RISK */ + +#include + +#define SPI + +#ifdef DMA + +#include "dac.h" +#include "sample.h" + +int main (void) +{ + dac_init(); + + // int i = 0; + while(1) { + // fiprintf(stderr, "Play #%d: %d samples\n\r", i++, sizeof(samples) / sizeof(short)); + dac_play_samples(samples, sizeof(samples) / sizeof(short)); + } + return 0; +} + +#endif +volatile uint32_t temp; + +void _delay(uint32_t del); + +#ifdef BLINKY + +int main (void) +{ + LPC_SC->PCONP |= ( 1 << 15 ); // power up GPIO + LPC_GPIO1->FIODIR |= 1 << 29; // puts P1.29 into output mode. + while(1) + { + LPC_GPIO1->FIOPIN |= 1 << 29; // make P1.29 high + _delay( 1 << 24 ); + LPC_GPIO1->FIOPIN &= ~( 1 << 29 ); // make P1.29 low + _delay( 1 << 24 ); + } + return 0; + +} + +#endif + +#ifdef UART + +#include "LPC17xx.h" +#include +#include "uart.h" + +int main (void) +{ + /* SystemClockUpdate() updates the SystemFrequency variable */ + // SystemCoreClockUpdate();//SystemClockUpdate(); + UARTInit(0, 115200); /* baud rate setting */ + // UARTInit(1, 8000); /* baud rate setting */ + + LPC_SC->PCONP |= ( 1 << 15 ); // power up GPIO + LPC_GPIO1->FIODIR |= 1 << 29; // puts P1.29 into output mode. + + while (1) { + LPC_GPIO1->FIOPIN |= 1 << 29; // make P1.29 high + + //LPC_UART0->IER = IER_THRE | IER_RLS; // Disable RBR + UARTSend(0, (uint8_t *)"hello\n\r", 7); + //LPC_UART0->IER = IER_THRE | IER_RLS | IER_RBR; // Re-enable RBR + + _delay( 1 << 22 ); + + /// + + LPC_GPIO1->FIOPIN &= ~( 1 << 29 ); // make P1.29 low + /* + LPC_UART0->IER = IER_THRE | IER_RLS; // Disable RBR + UARTSend( 0, (uint8_t *)"l", 1); + LPC_UART0->IER = IER_THRE | IER_RLS | IER_RBR; // Re-enable RBR + */ + _delay( 1 << 22 ); + + } +} + +#endif + +#ifdef SPI + +#include "LPC17xx.h" +#include +#include "uart.h" + +int main (void) +{ + UARTInit(0, 115200); /* baud rate setting */ + + UARTSend(0, (uint8_t *)"init\n\r", 6); + + // PCONP register (Table 46), set bit PCSPI. + LPC_SC->PCONP |= 1 << 8; + + // In the PCLKSEL0 register (Table 40), set bit PCLK_SPI. In master mode, the + // clock must be an even number greater than or equal to 8 + LPC_SC->PCLKSEL0PCLK_SPI = 0;//(3 << 17); + // 1Mhz + + while (1) { + UARTSend(0, (uint8_t *)"hello\n\r", 7); + + _delay( 1 << 22 ); + } +} + +#endif + +void _delay(uint32_t del) +{ + uint32_t i; + for(i=0;i +#include //"type.h" +#include "uart.h" + +#define TRUE 1 +#define FALSE 0 + +volatile uint32_t UART0Status, UART1Status; +volatile uint8_t UART0TxEmpty = 1, UART1TxEmpty = 1; + +/***************************************************************************** +** Function name: UARTInit +** +** Descriptions: Initialize UART port, setup pin select, +** clock, parity, stop bits, FIFO, etc. +** +** parameters: portNum(0 or 1) and UART baudrate +** Returned value: true or false, return false only if the +** interrupt handler can't be installed to the +** VIC table +** +*****************************************************************************/ +uint32_t UARTInit( uint32_t PortNum, uint32_t baudrate ) +{ + uint32_t Fdiv; + uint32_t pclkdiv, pclk; + + uint32_t SystemFrequency = SystemCoreClock; + + if ( PortNum == 0 ) + { + LPC_PINCON->PINSEL0 &= ~0x000000F0; + LPC_PINCON->PINSEL0 |= 0x00000050; /* RxD0 is P0.3 and TxD0 is P0.2 */ + /* By default, the PCLKSELx value is zero, thus, the PCLK for + all the peripherals is 1/4 of the SystemFrequency. */ + /* Bit 6~7 is for UART0 */ + pclkdiv = (LPC_SC->PCLKSEL0 >> 6) & 0x03; + switch ( pclkdiv ) + { + case 0x00: + default: + pclk = SystemFrequency/4; + break; + case 0x01: + pclk = SystemFrequency; + break; + case 0x02: + pclk = SystemFrequency/2; + break; + case 0x03: + pclk = SystemFrequency/8; + break; + } + + LPC_UART0->LCR = 0x83; /* 8 bits, no Parity, 1 Stop bit */ + Fdiv = ( pclk / 16 ) / baudrate ; /*baud rate */ + LPC_UART0->DLM = Fdiv / 256; + LPC_UART0->DLL = Fdiv % 256; + LPC_UART0->LCR = 0x03; /* DLAB = 0 */ + LPC_UART0->FCR = 0x07; /* Enable and reset TX and RX FIFO. */ + + // NVIC_EnableIRQ(UART0_IRQn); + + //LPC_UART0->IER = IER_RBR | IER_THRE | IER_RLS; /* Enable UART0 interrupt */ + return (TRUE); + } + else if ( PortNum == 1 ) + { + LPC_PINCON->PINSEL4 &= ~0x0000000F; + LPC_PINCON->PINSEL4 |= 0x0000000A; /* Enable RxD1 P2.1, TxD1 P2.0 */ + + /* By default, the PCLKSELx value is zero, thus, the PCLK for + all the peripherals is 1/4 of the SystemFrequency. */ + /* Bit 8,9 are for UART1 */ + pclkdiv = (LPC_SC->PCLKSEL0 >> 8) & 0x03; + switch ( pclkdiv ) + { + case 0x00: + default: + pclk = SystemFrequency/4; + break; + case 0x01: + pclk = SystemFrequency; + break; + case 0x02: + pclk = SystemFrequency/2; + break; + case 0x03: + pclk = SystemFrequency/8; + break; + } + + LPC_UART1->LCR = 0x83; /* 8 bits, no Parity, 1 Stop bit */ + Fdiv = ( pclk / 16 ) / baudrate ; /*baud rate */ + LPC_UART1->DLM = Fdiv / 256; + LPC_UART1->DLL = Fdiv % 256; + LPC_UART1->LCR = 0x03; /* DLAB = 0 */ + LPC_UART1->FCR = 0x07; /* Enable and reset TX and RX FIFO. */ + + // NVIC_EnableIRQ(UART1_IRQn); + + LPC_UART1->IER = IER_RBR | IER_THRE | IER_RLS; /* Enable UART1 interrupt */ + return (TRUE); + } + return( FALSE ); +} + +/***************************************************************************** +** Function name: UARTSend +** +** Descriptions: Send a block of data to the UART 0 port based +** on the data length +** +** parameters: portNum, buffer pointer, and data length +** Returned value: None +** +*****************************************************************************/ +void UARTSend( uint32_t portNum, uint8_t *BufferPtr, uint32_t Length ) +{ + if ( portNum == 0 ) + { + while ( Length != 0 ) + { + /* THRE status, contain valid data */ + //while ( !(UART0TxEmpty & 0x01) ); + LPC_UART0->THR = *BufferPtr; + UART0TxEmpty = 0; /* not empty in the THR until it shifts out */ + BufferPtr++; + Length--; + } + } + else + { + while ( Length != 0 ) + { + /* THRE status, contain valid data */ + while ( !(UART1TxEmpty & 0x01) ); + LPC_UART1->THR = *BufferPtr; + UART1TxEmpty = 0; /* not empty in the THR until it shifts out */ + BufferPtr++; + Length--; + } + } + return; +} + +/****************************************************************************** +** End Of File +******************************************************************************/ diff --git a/firmware/src/uart.h b/firmware/src/uart.h new file mode 100644 index 0000000..870f581 --- /dev/null +++ b/firmware/src/uart.h @@ -0,0 +1,50 @@ +/**************************************************************************** + * $Id:: uart.h 5751 2010-11-30 23:56:11Z usb00423 $ + * Project: NXP LPC17xx UART example + * + * Description: + * This file contains UART code header definition. + * + **************************************************************************** + * Software that is described herein is for illustrative purposes only + * which provides customers with programming information regarding the + * products. This software is supplied "AS IS" without any warranties. + * NXP Semiconductors assumes no responsibility or liability for the + * use of the software, conveys no license or title under any patent, + * copyright, or mask work right to the product. NXP Semiconductors + * reserves the right to make changes in the software without + * notification. NXP Semiconductors also make no representation or + * warranty that such application will be suitable for the specified + * use without further testing or modification. +****************************************************************************/ +#ifndef __UART_H +#define __UART_H + +#define IER_RBR 0x01 +#define IER_THRE 0x02 +#define IER_RLS 0x04 + +#define IIR_PEND 0x01 +#define IIR_RLS 0x03 +#define IIR_RDA 0x02 +#define IIR_CTI 0x06 +#define IIR_THRE 0x01 + +#define LSR_RDR 0x01 +#define LSR_OE 0x02 +#define LSR_PE 0x04 +#define LSR_FE 0x08 +#define LSR_BI 0x10 +#define LSR_THRE 0x20 +#define LSR_TEMT 0x40 +#define LSR_RXFE 0x80 + +#define BUFSIZE 0x40 + +uint32_t UARTInit( uint32_t portNum, uint32_t Baudrate ); +void UARTSend(uint32_t portNum, uint8_t *BufferPtr, uint32_t Length ); + +#endif /* end __UART_H */ +/***************************************************************************** +** End Of File +******************************************************************************/ -- cgit v1.2.3