From f8eab9ebd925604ec5047224d36fff9b25d7f2ec Mon Sep 17 00:00:00 2001 From: "A.M. Rowsell" Date: Tue, 6 Oct 2020 12:01:34 -0400 Subject: [PATCH] Renamed .h files, formatted all code with astyle -A14 I now have a post-build step which formats all the code using astyle -n -z2 -Z -A14 *.hpp *.cpp The options are to preserve the dates of each file, force the Linux line endings, and format the files directly omitting the creation of the .orig file. The -A14 is "Google" style which happens to be the style I've always personally used, which is handy. --- FIFO.cpp | 4 +- FIFO.hpp | 6 +- FlashStorage.cpp | 27 ++-- FlashStorage.hpp | 6 +- UART.cpp | 6 +- UART.hpp | 6 +- fuses.h => fuses.hpp | 2 +- i2c.cpp | 358 +++++++++++++++++++++---------------------- i2c.h => i2c.hpp | 6 +- main.cpp | 266 ++++++++++++++++---------------- 10 files changed, 343 insertions(+), 344 deletions(-) rename fuses.h => fuses.hpp (99%) rename i2c.h => i2c.hpp (98%) diff --git a/FIFO.cpp b/FIFO.cpp index 42c7cd6..5378138 100644 --- a/FIFO.cpp +++ b/FIFO.cpp @@ -1,7 +1,7 @@ -/* +/* * File: FIFO.cpp * Author: amr - * + * * Created on October 1, 2020, 4:58 PM */ diff --git a/FIFO.hpp b/FIFO.hpp index d38eafa..21a344f 100644 --- a/FIFO.hpp +++ b/FIFO.hpp @@ -1,4 +1,4 @@ -/* +/* * File: FIFO.hpp * Author: amr * @@ -12,7 +12,7 @@ #include class FIFO { -public: + public: FIFO(int size); uint8_t read(void); uint8_t write(uint8_t item); @@ -21,7 +21,7 @@ public: int writeIndex = 0; int usedSize = 0; uint8_t *fifoBuffer; -private: + private: }; diff --git a/FlashStorage.cpp b/FlashStorage.cpp index d3ad383..2d064ff 100644 --- a/FlashStorage.cpp +++ b/FlashStorage.cpp @@ -1,7 +1,7 @@ -/* +/* * File: FlashStorage.cpp * Author: amr - * + * * Created on October 1, 2020, 5:03 PM */ @@ -32,17 +32,14 @@ uint8_t FlashStorage::readStatusRegister(void) { while(!(SPI1STAT & 0x01)); // wait for byte statusReg = SPI1BUF; PORTASET = 0x10; - + if(statusReg & 0x01) { return FLASH_BUSY; - } - else if(statusReg & 0x20) { + } else if(statusReg & 0x20) { return FLASH_ERASE_ERROR; - } - else if(statusReg & 0x40) { + } else if(statusReg & 0x40) { return FLASH_PROG_ERROR; - } - else { + } else { return FLASH_OKAY; } } @@ -65,7 +62,7 @@ void FlashStorage::sectorErase(uint8_t sector) { // we need to wait for the erase while(readStatusRegister() != FLASH_OKAY) ; // this might end up crashing if there's an error, but... whatever - + } uint8_t FlashStorage::read(uint32_t addr, uint32_t length) { @@ -92,7 +89,7 @@ uint8_t FlashStorage::read(uint32_t addr, uint32_t length) { return 0; } } - + PORTASET = 0x10; // set CS high return length; } @@ -109,12 +106,12 @@ uint8_t FlashStorage::write(uint32_t addr, uint32_t length, uint8_t *data) { SPI1BUF = (uint8_t)((addr >> 8) & 0x000000FF); while(SPI1STAT & 0x02); SPI1BUF = (uint8_t)((addr) & 0x000000FF); - + for(uint32_t i = 0; i < length; i++) { while(SPI1STAT & 0x02); SPI1BUF = *(data + i); } - + PORTASET = 0x10; // set CS high while(readStatusRegister() != FLASH_OKAY) ; // wait for programming return 0; @@ -130,7 +127,7 @@ uint8_t FlashStorage::program(void) { sectorErase(0); sectorErase(1); sectorErase(2); - + while(1) { length = 0; serial->send(readySend); @@ -142,5 +139,5 @@ uint8_t FlashStorage::program(void) { curAddr += 64; } free(progBuffer); - return 0; + return 0; } \ No newline at end of file diff --git a/FlashStorage.hpp b/FlashStorage.hpp index 8732a13..2c5774c 100644 --- a/FlashStorage.hpp +++ b/FlashStorage.hpp @@ -1,4 +1,4 @@ -/* +/* * File: FlashStorage.hpp * Author: amr * @@ -20,14 +20,14 @@ #define FLASH_ERASE_ERROR 3 class FlashStorage { -public: + public: FlashStorage(FIFO *fifobuffer, UART *serialBus); uint8_t readStatusRegister(void); void sectorErase(uint8_t sector); uint8_t read(uint32_t addr, uint32_t length); uint8_t write(uint32_t addr, uint32_t length, uint8_t *data); uint8_t program(void); -private: + private: FIFO *buffer; UART *serial; void enableFlashWrite(void); diff --git a/UART.cpp b/UART.cpp index 5a012ae..9cbe112 100644 --- a/UART.cpp +++ b/UART.cpp @@ -1,7 +1,7 @@ -/* +/* * File: UART.cpp * Author: amr - * + * * Created on October 2, 2020, 5:51 PM */ @@ -12,7 +12,7 @@ UART::UART(uint32_t baud, uint32_t clockSpeed) { uint16_t ibaud = 0; cbaud = ((double)clockSpeed/((double)baud*16.0)) - 1.0; ibaud = (uint16_t)(cbaud - 0.5); - + U1BRG = ibaud; U1STAbits.UTXEN = 1; // enable transmitter U1STAbits.URXEN = 1; // enable receiver diff --git a/UART.hpp b/UART.hpp index 05ed840..df75573 100644 --- a/UART.hpp +++ b/UART.hpp @@ -1,4 +1,4 @@ -/* +/* * File: UART.hpp * Author: amr * @@ -11,11 +11,11 @@ #include #include class UART { -public: + public: UART(uint32_t baud, uint32_t clockSpeed); void send(uint8_t c); uint8_t receive(void); -private: + private: }; diff --git a/fuses.h b/fuses.hpp similarity index 99% rename from fuses.h rename to fuses.hpp index 375a0b5..271a016 100644 --- a/fuses.h +++ b/fuses.hpp @@ -1,4 +1,4 @@ -/* +/* * File: fuses.h * Author: amr * diff --git a/i2c.cpp b/i2c.cpp index bfeb8c8..400a4c6 100644 --- a/i2c.cpp +++ b/i2c.cpp @@ -1,5 +1,5 @@ /** @file i2c.cpp - * + * * This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. @@ -11,7 +11,7 @@ * @fn i2c::i2c * @param speed the requested I2C bus speed * @param pclk the speed of the peripheral clock - * + * * This constructor takes the requested bus speed and the peripheral * clock speed, and calculates the appropriate baud rate divisor for * I2C2BRG. Then it enables the I2C module. @@ -31,12 +31,12 @@ i2c::i2c(uint32_t speed, uint32_t pclk) { * @param recv buffer for data to be received, can be NULL * @param size number of bytes to send to received * @param mode which transactMode to use - * @param memAddr optional memory address, only used when communicating with - * EEPROMs, can be NULL if not needed. This is a pointer to the variable - * holding the memory address. This is done so that it can be NULL + * @param memAddr optional memory address, only used when communicating with + * EEPROMs, can be NULL if not needed. This is a pointer to the variable + * holding the memory address. This is done so that it can be NULL * when not needed. * @return a status code, not fully implemented - * + * * Note that the address needs to be sent in 7-bit mode * Note also that null pointers can be used when a mode * doesn't require use of one of the pointers @@ -52,48 +52,87 @@ i2c::i2c(uint32_t speed, uint32_t pclk) { * 2: NACK on data */ uint8_t i2c::transact(uint8_t addr, uint8_t *send, uint8_t *recv, \ - uint8_t size, transactMode mode, uint16_t *memAddr) { + uint8_t size, transactMode mode, uint16_t *memAddr) { uint8_t fullAddress, status = 0; uint8_t loopVar; const int max = 255; const int prime = 317; switch (mode) { - case SINGLE_SEND: // Single send - fullAddress = addr << 1; // we are writing, thus R/W = 0 - while (I2C2STATbits.TRSTAT); // wait for any transmission to finish - I2C2CONbits.SEN = 1; // send a start - while (I2C2CONbits.SEN); // wait for start to complete - I2C2TRN = fullAddress; // send address + case SINGLE_SEND: // Single send + fullAddress = addr << 1; // we are writing, thus R/W = 0 + while (I2C2STATbits.TRSTAT); // wait for any transmission to finish + I2C2CONbits.SEN = 1; // send a start + while (I2C2CONbits.SEN); // wait for start to complete + I2C2TRN = fullAddress; // send address + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= 1; // NACK on address + } + if(memAddr != NULL) { + // Send memory address + I2C2TRN = (uint8_t)(*memAddr >> 8); + while (I2C2STATbits.TRSTAT); // wait for transmission + I2C2TRN = (uint8_t)(*memAddr & 0x00FF); + while (I2C2STATbits.TRSTAT); // wait for transmission + } + if(send != NULL) { + // Now send the actual data + I2C2TRN = *send; // load buffer with data while (I2C2STATbits.TRSTAT); // wait for transmission if (I2C2STATbits.ACKSTAT == 0) { // acknowledge received } else { - status |= 1; // NACK on address + status |= 2; // NACK on data } - if(memAddr != NULL) { - // Send memory address - I2C2TRN = (uint8_t)(*memAddr >> 8); - while (I2C2STATbits.TRSTAT); // wait for transmission - I2C2TRN = (uint8_t)(*memAddr & 0x00FF); - while (I2C2STATbits.TRSTAT); // wait for transmission - } - if(send != NULL) { - // Now send the actual data - I2C2TRN = *send; // load buffer with data + } else { + status |= NULL_ERROR; + } + I2C2CONbits.PEN = 1; // send STOP + while (I2C2CONbits.PEN); // wait for stop to complete + break; + case MULTIPLE_SEND: // Multiple send + fullAddress = addr << 1; // we are writing, thus R/W = 0 + while (I2C2STATbits.TRSTAT); // wait for any transmission to finish + I2C2CONbits.SEN = 1; // send a start + while (I2C2CONbits.SEN); // wait for start to complete + I2C2TRN = fullAddress; // send address + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= 1; // NACK on address + } + if(memAddr != NULL) { + // Send memory address + I2C2TRN = (uint8_t)(*memAddr >> 8); + while (I2C2STATbits.TRSTAT); // wait for transmission + I2C2TRN = (uint8_t)(*memAddr & 0x00FF); + while (I2C2STATbits.TRSTAT); // wait for transmission + } + if(send != NULL) { // guard against NULL pointer + // Now send the actual data + for (loopVar = size; loopVar > 0; loopVar--) { // do until size hits zero + I2C2TRN = *send; // load buffer with (next) data while (I2C2STATbits.TRSTAT); // wait for transmission if (I2C2STATbits.ACKSTAT == 0) { // acknowledge received } else { status |= 2; // NACK on data } - } else { - status |= NULL_ERROR; + send++; // good old pointer increment... hope it works! } - I2C2CONbits.PEN = 1; // send STOP - while (I2C2CONbits.PEN); // wait for stop to complete - break; - case MULTIPLE_SEND: // Multiple send + } else { + status |= NULL_ERROR; + } + I2C2CONbits.PEN = 1; // send STOP + while (I2C2CONbits.PEN); // wait for stop to complete + + break; + case SINGLE_RECV: // Single receive + if(memAddr != NULL || send != NULL) { fullAddress = addr << 1; // we are writing, thus R/W = 0 while (I2C2STATbits.TRSTAT); // wait for any transmission to finish I2C2CONbits.SEN = 1; // send a start @@ -105,168 +144,129 @@ uint8_t i2c::transact(uint8_t addr, uint8_t *send, uint8_t *recv, \ } else { status |= 1; // NACK on address } - if(memAddr != NULL) { - // Send memory address - I2C2TRN = (uint8_t)(*memAddr >> 8); - while (I2C2STATbits.TRSTAT); // wait for transmission - I2C2TRN = (uint8_t)(*memAddr & 0x00FF); - while (I2C2STATbits.TRSTAT); // wait for transmission - } - if(send != NULL) { // guard against NULL pointer - // Now send the actual data - for (loopVar = size; loopVar > 0; loopVar--) { // do until size hits zero - I2C2TRN = *send; // load buffer with (next) data - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= 2; // NACK on data - } - send++; // good old pointer increment... hope it works! - } + } + if(memAddr != NULL) { + // Send memory address + I2C2TRN = (uint8_t)(*memAddr >> 8); + while (I2C2STATbits.TRSTAT); // wait for transmission + I2C2TRN = (uint8_t)(*memAddr & 0x00FF); + while (I2C2STATbits.TRSTAT); // wait for transmission + } + // Now send the actual data + if(send != NULL) { + I2C2TRN = *send; // load buffer with data + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received } else { - status |= NULL_ERROR; + status |= DATA_NACK; // NACK on data } - I2C2CONbits.PEN = 1; // send STOP - while (I2C2CONbits.PEN); // wait for stop to complete + } + if(recv != NULL) { // guard against NULL pointers + // RECEIVE SECTION + I2C2CONbits.RSEN = 1; // send restart + while (I2C2CONbits.RSEN); // wait for restart + fullAddress = (addr << 1) | 0x01; // address is now for reading + I2C2TRN = fullAddress; // send address + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= ADDR_NACK; // NACK on address + } + I2C2CONbits.RCEN = 1; // enable receiever + while (!I2C2STATbits.RBF); // wait for 8 bits to be receieved + *recv = I2C2RCV; + I2C2CONbits.ACKDT = 1; // change to NACK + I2C2CONbits.ACKEN = 1; // send ACKDT + while (I2C2CONbits.ACKEN); // wait for NACK to send + } else { + status |= NULL_ERROR; + } - break; - case SINGLE_RECV: // Single receive - if(memAddr != NULL || send != NULL) { - fullAddress = addr << 1; // we are writing, thus R/W = 0 - while (I2C2STATbits.TRSTAT); // wait for any transmission to finish - I2C2CONbits.SEN = 1; // send a start - while (I2C2CONbits.SEN); // wait for start to complete - I2C2TRN = fullAddress; // send address - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= 1; // NACK on address - } - } - if(memAddr != NULL) { - // Send memory address - I2C2TRN = (uint8_t)(*memAddr >> 8); - while (I2C2STATbits.TRSTAT); // wait for transmission - I2C2TRN = (uint8_t)(*memAddr & 0x00FF); - while (I2C2STATbits.TRSTAT); // wait for transmission + I2C2CONbits.PEN = 1; // send STOP + while (I2C2CONbits.PEN); // wait for stop to complete + break; + case MULTIPLE_RECV: // Multiple receive + if(memAddr != NULL || send != NULL) { // only send the write address if needed + fullAddress = addr << 1; // we are writing, thus R/W = 0 + while (I2C2STATbits.TRSTAT); // wait for any transmission to finish + I2C2CONbits.SEN = 1; // send a start + while (I2C2CONbits.SEN); // wait for start to complete + I2C2TRN = fullAddress; // send address + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= 1; // NACK on address } + } + if(memAddr != NULL) { + // Send memory address + I2C2TRN = (uint8_t)(*memAddr >> 8); + while (I2C2STATbits.TRSTAT); // wait for transmission + I2C2TRN = (uint8_t)(*memAddr & 0x00FF); + while (I2C2STATbits.TRSTAT); // wait for transmission + } + if(send != NULL) { // Now send the actual data - if(send != NULL) { - I2C2TRN = *send; // load buffer with data - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= DATA_NACK; // NACK on data - } + I2C2TRN = *send; // load buffer with data + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= 2; // NACK on data } - if(recv != NULL) { // guard against NULL pointers - // RECEIVE SECTION - I2C2CONbits.RSEN = 1; // send restart - while (I2C2CONbits.RSEN); // wait for restart - fullAddress = (addr << 1) | 0x01; // address is now for reading - I2C2TRN = fullAddress; // send address - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= ADDR_NACK; // NACK on address - } + } + if(recv != NULL) { + // RECEIVE SECTION + I2C2CONbits.RSEN = 1; // send restart + while (I2C2CONbits.RSEN); // wait for restart + fullAddress = (addr << 1) | 0x01; // address is now for reading + I2C2TRN = fullAddress; // send address + while (I2C2STATbits.TRSTAT); // wait for transmission + if (I2C2STATbits.ACKSTAT == 0) { + // acknowledge received + } else { + status |= 1; // NACK on address + } + for (loopVar = size; loopVar > 0; loopVar--) { I2C2CONbits.RCEN = 1; // enable receiever while (!I2C2STATbits.RBF); // wait for 8 bits to be receieved *recv = I2C2RCV; - I2C2CONbits.ACKDT = 1; // change to NACK - I2C2CONbits.ACKEN = 1; // send ACKDT - while (I2C2CONbits.ACKEN); // wait for NACK to send - } else { - status |= NULL_ERROR; - } - - I2C2CONbits.PEN = 1; // send STOP - while (I2C2CONbits.PEN); // wait for stop to complete - break; - case MULTIPLE_RECV: // Multiple receive - if(memAddr != NULL || send != NULL) { // only send the write address if needed - fullAddress = addr << 1; // we are writing, thus R/W = 0 - while (I2C2STATbits.TRSTAT); // wait for any transmission to finish - I2C2CONbits.SEN = 1; // send a start - while (I2C2CONbits.SEN); // wait for start to complete - I2C2TRN = fullAddress; // send address - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received + recv++; + if (loopVar > 1) { + I2C2CONbits.ACKDT = 0; // ACK + I2C2CONbits.ACKEN = 1; + while (I2C2CONbits.ACKEN); // wait for ACK } else { - status |= 1; // NACK on address + I2C2CONbits.ACKDT = 1; // change to NACK + I2C2CONbits.ACKEN = 1; // send ACKDT + while (I2C2CONbits.ACKEN); // wait for NACK to send } } - if(memAddr != NULL) { - // Send memory address - I2C2TRN = (uint8_t)(*memAddr >> 8); - while (I2C2STATbits.TRSTAT); // wait for transmission - I2C2TRN = (uint8_t)(*memAddr & 0x00FF); - while (I2C2STATbits.TRSTAT); // wait for transmission + } else { + status |= NULL_ERROR; + } + I2C2CONbits.PEN = 1; // send STOP + while (I2C2CONbits.PEN); // wait for stop to complete + break; + case TEST_MODE: // infinite test mode + do { + for (int i = 0; i < max; ++i) { + uint8_t c = (int) (i * prime) % max; + I2C2CONbits.SEN = 1; + while (I2C2CONbits.SEN); + I2C2TRN = c; + while (I2C2STATbits.TBF); // wait for transmission + I2C2CONbits.PEN = 1; + while (I2C2CONbits.PEN); } - if(send != NULL) { - // Now send the actual data - I2C2TRN = *send; // load buffer with data - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= 2; // NACK on data - } - } - if(recv != NULL) { - // RECEIVE SECTION - I2C2CONbits.RSEN = 1; // send restart - while (I2C2CONbits.RSEN); // wait for restart - fullAddress = (addr << 1) | 0x01; // address is now for reading - I2C2TRN = fullAddress; // send address - while (I2C2STATbits.TRSTAT); // wait for transmission - if (I2C2STATbits.ACKSTAT == 0) { - // acknowledge received - } else { - status |= 1; // NACK on address - } - for (loopVar = size; loopVar > 0; loopVar--) { - I2C2CONbits.RCEN = 1; // enable receiever - while (!I2C2STATbits.RBF); // wait for 8 bits to be receieved - *recv = I2C2RCV; - recv++; - if (loopVar > 1) { - I2C2CONbits.ACKDT = 0; // ACK - I2C2CONbits.ACKEN = 1; - while (I2C2CONbits.ACKEN); // wait for ACK - } else { - I2C2CONbits.ACKDT = 1; // change to NACK - I2C2CONbits.ACKEN = 1; // send ACKDT - while (I2C2CONbits.ACKEN); // wait for NACK to send - } - } - } else { - status |= NULL_ERROR; - } - I2C2CONbits.PEN = 1; // send STOP - while (I2C2CONbits.PEN); // wait for stop to complete - break; - case TEST_MODE: // infinite test mode - do { - for (int i = 0; i < max; ++i) { - uint8_t c = (int) (i * prime) % max; - I2C2CONbits.SEN = 1; - while (I2C2CONbits.SEN); - I2C2TRN = c; - while (I2C2STATbits.TBF); // wait for transmission - I2C2CONbits.PEN = 1; - while (I2C2CONbits.PEN); - } - } while (size--); - break; - default: - status |= 0x04; - break; + } while (size--); + break; + default: + status |= 0x04; + break; } return status; } \ No newline at end of file diff --git a/i2c.h b/i2c.hpp similarity index 98% rename from i2c.h rename to i2c.hpp index 2d2db1a..d9c5a3b 100644 --- a/i2c.h +++ b/i2c.hpp @@ -3,7 +3,7 @@ * Author: Alexander Rowsell * * Created on May 3, 2015, 1:06 AM - * + * * This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. @@ -31,7 +31,7 @@ enum statusCodes { /** * @class i2c * @brief The i2c class, controls all i2c comms - * + * * This class is an abstraction of the I2C peripheral * inside the PIC32MX1xx/2xx family of devices. * Simply create an instance of this class, and then @@ -39,7 +39,7 @@ enum statusCodes { * data over the I2C bus. Colours are excellent */ class i2c { -public: + public: i2c(uint32_t speed, uint32_t pclk); uint8_t transact(uint8_t addr, uint8_t *send, \ diff --git a/main.cpp b/main.cpp index 8a4d156..8bf962b 100644 --- a/main.cpp +++ b/main.cpp @@ -13,7 +13,7 @@ #include #include #include -#include "i2c.h" +#include "i2c.hpp" #include "FIFO.hpp" #include "FlashStorage.hpp" #include "UART.hpp" @@ -34,167 +34,169 @@ volatile uint8_t currentClip = 0; #define AUDIO_SIZE 509176 const uint32_t audioSize[16] = {0x0000ba8d, 0x0000d063, 0x000069fa, 0x00007c3e, - 0x000030b4, 0x0000c676, 0x000020fd, 0x00005314, 0x00002db8, 0x00002fbd, - 0x000046c0, 0x0000bc92, 0x0000a257, 0x00002830, 0x00011790, 0x0000a5b7}; + 0x000030b4, 0x0000c676, 0x000020fd, 0x00005314, 0x00002db8, 0x00002fbd, + 0x000046c0, 0x0000bc92, 0x0000a257, 0x00002830, 0x00011790, 0x0000a5b7 + }; const uint32_t audioAddress[16] = {0x00, 0x0000ba8d, 0x00018af0, 0x0001f4ea, - 0x00027128, 0x0002a1dc, 0x00036852, 0x0003894f, 0x0003dc63, 0x00040a1b, - 0x000439d8, 0x00048098, 0x00053d2a, 0x0005df81, 0x000607b1, 0x00071f41}; + 0x00027128, 0x0002a1dc, 0x00036852, 0x0003894f, 0x0003dc63, 0x00040a1b, + 0x000439d8, 0x00048098, 0x00053d2a, 0x0005df81, 0x000607b1, 0x00071f41 + }; #define dacAddress 0x62 void _delay(uint32_t cycles) { - cycles += (uint32_t) ((double) cycles * 1.4); - while (cycles--); - return; + cycles += (uint32_t) ((double) cycles * 1.4); + while (cycles--); + return; } uint8_t initSystem(void) { - /* set up GPIO */ - SYSKEY = 0x0; - SYSKEY = 0xAA996655; - SYSKEY = 0x556699AA; - CFGCON &= ~(1 << 13); // unlock PPS + /* set up GPIO */ + SYSKEY = 0x0; + SYSKEY = 0xAA996655; + SYSKEY = 0x556699AA; + CFGCON &= ~(1 << 13); // unlock PPS - // Pin configs - /* SPI: - * SO = RB5 - * SI = RC8 - * CS = RA4 - * - * I2C: - * SDA: RB2 - * SCL: RB3 - * - * UART: - * TX = RC5 - * RX = RC3 - */ - SDI1R = 0b0110; // RC8 - U1RXR = 0b0111; // RC3 - RPC0R = 0b0101; // OC1 on LED - RPB5R = 0b0011; // SD01 - RPC5R = 0b0001; // U1TX + // Pin configs + /* SPI: + * SO = RB5 + * SI = RC8 + * CS = RA4 + * + * I2C: + * SDA: RB2 + * SCL: RB3 + * + * UART: + * TX = RC5 + * RX = RC3 + */ + SDI1R = 0b0110; // RC8 + U1RXR = 0b0111; // RC3 + RPC0R = 0b0101; // OC1 on LED + RPB5R = 0b0011; // SD01 + RPC5R = 0b0001; // U1TX - OSCCONCLR = 0x00000010; // idle mode + OSCCONCLR = 0x00000010; // idle mode - SYSKEY = 0x12345678; // lock SYSKEY + SYSKEY = 0x12345678; // lock SYSKEY - // set up button & LED - ANSELACLR = 0xFFFF; - ANSELBCLR = 0xFFFF; - ANSELCCLR = 0xFFFF; // clear all analog functions - TRISCSET = 0x20; // PC5 is button input - TRISCCLR = 0x01; // PC0 is LED - PORTCCLR = 0x01; // turn LED off at boot + // set up button & LED + ANSELACLR = 0xFFFF; + ANSELBCLR = 0xFFFF; + ANSELCCLR = 0xFFFF; // clear all analog functions + TRISCSET = 0x20; // PC5 is button input + TRISCCLR = 0x01; // PC0 is LED + PORTCCLR = 0x01; // turn LED off at boot - CNENCSET = 0x20; // enable on PC5 - CNPUCSET = 0x20; // pullup enable - CNCONCSET = 0x8000; - IFS1CLR = 0x8000; - IPC8SET = 0xC0000; // priority 3 - //IEC1SET = 0x8000; // enable pin change interrupt port C + CNENCSET = 0x20; // enable on PC5 + CNPUCSET = 0x20; // pullup enable + CNCONCSET = 0x8000; + IFS1CLR = 0x8000; + IPC8SET = 0xC0000; // priority 3 + //IEC1SET = 0x8000; // enable pin change interrupt port C - /* Set up SPI1 */ - TRISACLR = 0x10; - PORTASET = 0x10; - TRISBCLR = 0x4000; // RB14 is SCK1 - SPI1BRG = 1; // 2.5MHz - SPI1CONbits.ENHBUF = 0; // enable enhanced buffer - SPI1CONbits.MSTEN = 1; // master mode - SPI1STATCLR = (1 << 6); // clear SPIROV - SPI1CONbits.ON = 1; // enable SPI + /* Set up SPI1 */ + TRISACLR = 0x10; + PORTASET = 0x10; + TRISBCLR = 0x4000; // RB14 is SCK1 + SPI1BRG = 1; // 2.5MHz + SPI1CONbits.ENHBUF = 0; // enable enhanced buffer + SPI1CONbits.MSTEN = 1; // master mode + SPI1STATCLR = (1 << 6); // clear SPIROV + SPI1CONbits.ON = 1; // enable SPI - // set up timer (needs to be about 8kHz) - T2CON = 0x0000; // timer continues in idle mode - PR2 = 0x04E2; // 1250 = 10e6/8e3 - TMR2 = 0x0000; + // set up timer (needs to be about 8kHz) + T2CON = 0x0000; // timer continues in idle mode + PR2 = 0x04E2; // 1250 = 10e6/8e3 + TMR2 = 0x0000; - IPC2bits.T2IP = 7; // priority 7 - IFS0bits.T2IF = 0; - IEC0bits.T2IE = 1; // enable timer interrupt + IPC2bits.T2IP = 7; // priority 7 + IFS0bits.T2IF = 0; + IEC0bits.T2IE = 1; // enable timer interrupt - INTCONSET = _INTCON_MVEC_MASK; - return 0; + INTCONSET = _INTCON_MVEC_MASK; + return 0; } void updateDAC(i2c *bus, uint16_t data) { - uint8_t bytes[2] = {0x00, 0x00}; - bytes[0] = (uint8_t) (data >> 8) & 0x0F; // clear top half of top byte - bytes[1] = (uint8_t) (data & 0x00FF); - bus->transact(dacAddress, bytes, NULL, 2, MULTIPLE_SEND); + uint8_t bytes[2] = {0x00, 0x00}; + bytes[0] = (uint8_t) (data >> 8) & 0x0F; // clear top half of top byte + bytes[1] = (uint8_t) (data & 0x00FF); + bus->transact(dacAddress, bytes, NULL, 2, MULTIPLE_SEND); } int main(void) { - volatile uint16_t audioSampleShifted = 0; - volatile uint8_t audioSample = 0; - initSystem(); + volatile uint16_t audioSampleShifted = 0; + volatile uint8_t audioSample = 0; + initSystem(); - FIFO audioBuffer(64); - UART serial(19200, 10e6); - FlashStorage flash(&audioBuffer, &serial); - i2c i2cBus(400e3, 10e6); + FIFO audioBuffer(64); + UART serial(19200, 10e6); + FlashStorage flash(&audioBuffer, &serial); + i2c i2cBus(400e3, 10e6); - // this needs to be as early as possible, but after SPI and UART setup - // if(LATC & 0x20) { - // // if button is held down at boot, it's programming mode - // globalState = STATE_PROGRAMMING; - // flash.program(); - // } + // this needs to be as early as possible, but after SPI and UART setup + // if(LATC & 0x20) { + // // if button is held down at boot, it's programming mode + // globalState = STATE_PROGRAMMING; + // flash.program(); + // } - const char testString[20] = "Welcome to Canada\n\r"; - // main state machine loop - //flash.program(); - globalState == STATE_PLAYING; - while (1) { - __builtin_disable_interrupts(); - if (globalState == STATE_PLAYING) { - if (audioBuffer.usedSize < 16) { - // read 48 bytes into buffer - flash.read(audioAddress[currentClip] + readByteCount, 48); - readByteCount += 48; - } - audioSample = audioBuffer.read(); - byteCount++; - if (byteCount >= audioSize[currentClip]) { - byteCount = 0; - readByteCount = 0; - //globalState = STATE_IDLE; - } - // Load sample into DAC - audioSampleShifted = (uint16_t) (audioSample << 4); - //updateDAC(&i2cBus, audioSampleShifted); - serial.send(audioSample); - __builtin_enable_interrupts(); - T2CONbits.ON = 1; // enable timer - asm volatile("wait"); - } else if (globalState == STATE_IDLE) { - for (uint8_t i = 0; i < 20; i++) { - serial.send(testString[i]); - } - __builtin_enable_interrupts(); - T2CONbits.ON = 1; // enable timer - asm volatile("wait"); - } - } + const char testString[20] = "Welcome to Canada\n\r"; + // main state machine loop + //flash.program(); + globalState == STATE_PLAYING; + while (1) { + __builtin_disable_interrupts(); + if (globalState == STATE_PLAYING) { + if (audioBuffer.usedSize < 16) { + // read 48 bytes into buffer + flash.read(audioAddress[currentClip] + readByteCount, 48); + readByteCount += 48; + } + audioSample = audioBuffer.read(); + byteCount++; + if (byteCount >= audioSize[currentClip]) { + byteCount = 0; + readByteCount = 0; + //globalState = STATE_IDLE; + } + // Load sample into DAC + audioSampleShifted = (uint16_t) (audioSample << 4); + //updateDAC(&i2cBus, audioSampleShifted); + serial.send(audioSample); + __builtin_enable_interrupts(); + T2CONbits.ON = 1; // enable timer + asm volatile("wait"); + } else if (globalState == STATE_IDLE) { + for (uint8_t i = 0; i < 20; i++) { + serial.send(testString[i]); + } + __builtin_enable_interrupts(); + T2CONbits.ON = 1; // enable timer + asm volatile("wait"); + } + } } extern "C" { - void __ISR(_TIMER_2_VECTOR, IPL7AUTO) Timer2Handler(void) { - T2CONbits.ON = 0; - IFS0bits.T2IF = 0; - } + void __ISR(_TIMER_2_VECTOR, IPL7AUTO) Timer2Handler(void) { + T2CONbits.ON = 0; + IFS0bits.T2IF = 0; + } - void __ISR(_CHANGE_NOTICE_VECTOR, IPL3AUTO) PinChangeHandler(void) { - // button is pushed - if (globalState == STATE_PLAYING) { - return; // do nothing, we're already playing - } - // pick a random number - currentClip += 1; - currentClip = currentClip % 8; // roll back around - globalState = STATE_PLAYING; - IFS0CLR = 0x00000100; - } + void __ISR(_CHANGE_NOTICE_VECTOR, IPL3AUTO) PinChangeHandler(void) { + // button is pushed + if (globalState == STATE_PLAYING) { + return; // do nothing, we're already playing + } + // pick a random number + currentClip += 1; + currentClip = currentClip % 8; // roll back around + globalState = STATE_PLAYING; + IFS0CLR = 0x00000100; + } } // end extern C