From e7baf2e96f1cec2071cb2e1e6a4735c36611bc26 Mon Sep 17 00:00:00 2001 From: Sam Anthony Date: Thu, 2 Oct 2025 17:13:22 -0400 Subject: dac fw module --- fw/dac.c | 71 +++++++++++++++++++++++++++++++++++++++++++ fw/dac.h | 36 ++++++++++++++++++++++ fw/eeprom.h | 4 +-- fw/spi.c | 2 +- fw/tests/system/dac_systest.c | 37 ++++++++++++++++++++++ fw/types.c | 6 ++++ fw/types.h | 4 +++ 7 files changed, 157 insertions(+), 3 deletions(-) create mode 100644 fw/dac.c create mode 100644 fw/dac.h create mode 100644 fw/tests/system/dac_systest.c (limited to 'fw') diff --git a/fw/dac.c b/fw/dac.c new file mode 100644 index 0000000..0c9fb90 --- /dev/null +++ b/fw/dac.c @@ -0,0 +1,71 @@ +#include + +#include + +#include "system.h" +#include "types.h" +#include "spi.h" + +#include "dac.h" + +// Configuration bits: +// buffered, gain=1x, mode=active +typedef enum { + CONFA = 0x70, // DAC A + CONFB = 0xF0, // DAC B +} Conf; + +void +dacInit(void) { + DAC1_CS_TRIS = OUT; + DAC2_CS_TRIS = OUT; + DAC1_CS = 1; + DAC2_CS = 1; + + U16 level = {0u, 0u}; + dacSet1a(level); + dacSet1b(level); + dacSet2a(level); + dacSet2b(level); +} + +static void +set(U8 dacNum, Conf conf, U16 level) { + lshiftU16(&level, 2u); // D0 at bit 2 + level.hi = (U8)conf | (level.hi & 0x0F); // set config bits + + if (dacNum == 1u) { + DAC1_CS = 0; + } else { + DAC2_CS = 0; + } + _delay(1); + + (void)spiTx(level.hi); + (void)spiTx(level.lo); + + if (dacNum == 1u) { + DAC1_CS = 1; + } else { + DAC2_CS = 1; + } +} + +void +dacSet1a(U16 level) { + set(1u, CONFA, level); +} + +void +dacSet1b(U16 level) { + set(1u, CONFB, level); +} + +void +dacSet2a(U16 level) { + set(2u, CONFA, level); +} +void +dacSet2b(U16 level) { + set(2u, CONFB, level); +} diff --git a/fw/dac.h b/fw/dac.h new file mode 100644 index 0000000..7bbf66a --- /dev/null +++ b/fw/dac.h @@ -0,0 +1,36 @@ +/* Microchip MCP4912 10-bit DAC + * + * Device: PIC16F1459 + * Compiler: XC8 v3.00 + * + * Usage: + * + * #include + * #include "types.h" + * #include "spi.h" + * #include "dac.h" + */ + +// Pin mapping +#define DAC1_CS_TRIS TRISBbits.TRISB7 +#define DAC1_CS LATBbits.LATB7 +#define DAC2_CS_TRIS TRISBbits.TRISB5 +#define DAC2_CS LATBbits.LATB5 + +void dacInit(void); + +// Set DAC1 VOUTA. +// Only the lower 10 bits are used. +void dacSet1a(U16 level); + +// Set DAC1 VOUTB. +// Only the lower 10 bits are used. +void dacSet1b(U16 level); + +// Set DAC2 VOUTA. +// Only the lower 10 bits are used. +void dacSet2a(U16 level); + +// Set DAC2 VOUTB. +// Only the lower 10 bits are used. +void dacSet2b(U16 level); diff --git a/fw/eeprom.h b/fw/eeprom.h index 16d9d72..9b8652e 100644 --- a/fw/eeprom.h +++ b/fw/eeprom.h @@ -11,8 +11,8 @@ */ // Pin mapping -#define EEPROM_CS_TRIS TRISAbits.TRISA5 -#define EEPROM_CS LATAbits.LATA5 +#define EEPROM_CS_TRIS TRISCbits.TRISC5 +#define EEPROM_CS LATCbits.LATC5 void eepromInit(void); void eepromWriteEnable(void); diff --git a/fw/spi.c b/fw/spi.c index 9198ab1..c8abe71 100644 --- a/fw/spi.c +++ b/fw/spi.c @@ -15,7 +15,7 @@ spiInit(void) { TRISCbits.TRISC7 = OUT; // SDO TRISBbits.TRISB6 = OUT; // SCK - SSPSTAT = 0x00; + SSPSTAT = 0x40; // CKE=1 SSPCON1 = 0x22; // FOSC/64 => 750kHz SPI clock junk = SSPBUF; // dummy read to clear BF (void)junk; diff --git a/fw/tests/system/dac_systest.c b/fw/tests/system/dac_systest.c new file mode 100644 index 0000000..8653f96 --- /dev/null +++ b/fw/tests/system/dac_systest.c @@ -0,0 +1,37 @@ +#include + +#include + +#include "system.h" +#include "types.h" +#include "spi.h" +#include "dac.h" + +void +main(void) { + sysInit(); + spiInit(); + dacInit(); + + dacSet1a((U16){0u, 252u}); // 1.23V + + for (;;) { + + } +} + +void +__interrupt() isr(void) { + static U8 ctr = 0u; + static U16 level = {0, 0}; + + if (TMR1IF) { + ctr++; + if (ctr == 23u) { // 1s period + ctr = 0u; + dacSet1a(level); + addU16(&level, 50u); + } + TMR1IF = 0; + } +} diff --git a/fw/types.c b/fw/types.c index a6c2411..d87c891 100644 --- a/fw/types.c +++ b/fw/types.c @@ -11,3 +11,9 @@ addU16(U16 *a, U8 b) { a->hi++; } } + +void +lshiftU16(U16 *a, U8 b) { + a->hi = (U8)(a->hi << b) | (a->lo >> (8u-b)); + a->lo <<= b; +} diff --git a/fw/types.h b/fw/types.h index 835491d..392c7cf 100644 --- a/fw/types.h +++ b/fw/types.h @@ -18,4 +18,8 @@ typedef struct { U8 hi, lo; } U16; +// *a = *a+b void addU16(U16 *a, U8 b); + +// *a = *a<