Chua chaotic oscillator and MCP4922 DAC

Dependencies:   mbed

Committer:
JLS
Date:
Sat May 07 19:27:14 2011 +0000
Revision:
0:e5edc0373da0

        

Who changed what in which revision?

UserRevisionLine numberNew contents of line
JLS 0:e5edc0373da0 1 /*
JLS 0:e5edc0373da0 2 * MCP4922 - DAC library.
JLS 0:e5edc0373da0 3 */
JLS 0:e5edc0373da0 4
JLS 0:e5edc0373da0 5 #include "mbed.h"
JLS 0:e5edc0373da0 6 #include "MCP4922.h"
JLS 0:e5edc0373da0 7
JLS 0:e5edc0373da0 8 using namespace mbed;
JLS 0:e5edc0373da0 9
JLS 0:e5edc0373da0 10 int dac =0;
JLS 0:e5edc0373da0 11
JLS 0:e5edc0373da0 12 MCP4922::MCP4922(PinName mosi, PinName sclk, PinName cs) : _spi(mosi, NC, sclk) {
JLS 0:e5edc0373da0 13
JLS 0:e5edc0373da0 14 int i;
JLS 0:e5edc0373da0 15 _ndacs = 1;
JLS 0:e5edc0373da0 16 _ncs_array = new DigitalOut*[ _ndacs ];
JLS 0:e5edc0373da0 17 for (i=0; i<_ndacs; i++) {
JLS 0:e5edc0373da0 18 _ncs_array[i] = new DigitalOut(cs);
JLS 0:e5edc0373da0 19 }
JLS 0:e5edc0373da0 20
JLS 0:e5edc0373da0 21 // Initialise the DAC SPI interface.
JLS 0:e5edc0373da0 22 _init();
JLS 0:e5edc0373da0 23 }
JLS 0:e5edc0373da0 24
JLS 0:e5edc0373da0 25 // Destructor
JLS 0:e5edc0373da0 26 MCP4922::~MCP4922() {
JLS 0:e5edc0373da0 27
JLS 0:e5edc0373da0 28 // Before destroying the object, shut down all the chips.
JLS 0:e5edc0373da0 29 //shdn_all();
JLS 0:e5edc0373da0 30
JLS 0:e5edc0373da0 31 // Delete all the NCS DigitalOut objects and the array pointing to
JLS 0:e5edc0373da0 32 // them.
JLS 0:e5edc0373da0 33 int i;
JLS 0:e5edc0373da0 34 for (i=0; i<_ndacs; i++) {
JLS 0:e5edc0373da0 35 delete _ncs_array[i];
JLS 0:e5edc0373da0 36 }
JLS 0:e5edc0373da0 37 delete [] _ncs_array;
JLS 0:e5edc0373da0 38
JLS 0:e5edc0373da0 39 // Delete the LDAC DigitalOut object if it exists.
JLS 0:e5edc0373da0 40 if (_latched ) delete _nldac;
JLS 0:e5edc0373da0 41 }
JLS 0:e5edc0373da0 42
JLS 0:e5edc0373da0 43 // Initialise SPI interface.
JLS 0:e5edc0373da0 44 void MCP4922::_init() {
JLS 0:e5edc0373da0 45
JLS 0:e5edc0373da0 46 // Set up the SPI for 16-bit values (12-bit + 4 command bits) and mode 0.
JLS 0:e5edc0373da0 47 _spi.format(16, 0);
JLS 0:e5edc0373da0 48
JLS 0:e5edc0373da0 49 // Start with all the CS and LDAC signals high (disabled)
JLS 0:e5edc0373da0 50 int i;
JLS 0:e5edc0373da0 51 for (i=0; i<_ndacs; i++) {
JLS 0:e5edc0373da0 52 _ncs_array[i]->write(1);
JLS 0:e5edc0373da0 53 }
JLS 0:e5edc0373da0 54
JLS 0:e5edc0373da0 55 if (_latched ) _nldac->write(1);
JLS 0:e5edc0373da0 56 return;
JLS 0:e5edc0373da0 57 }
JLS 0:e5edc0373da0 58
JLS 0:e5edc0373da0 59 // Set SPI clock frequency.
JLS 0:e5edc0373da0 60 void MCP4922::frequency( int freq ) {
JLS 0:e5edc0373da0 61
JLS 0:e5edc0373da0 62 // Set the SPI interface clock frequency in Hz.
JLS 0:e5edc0373da0 63 _spi.frequency( freq );
JLS 0:e5edc0373da0 64 return;
JLS 0:e5edc0373da0 65 }
JLS 0:e5edc0373da0 66
JLS 0:e5edc0373da0 67 /*
JLS 0:e5edc0373da0 68 * Note: There is a lot of code in common between the following 4 functions.
JLS 0:e5edc0373da0 69 * The code is kept in line to keep it efficient. Could the functions have
JLS 0:e5edc0373da0 70 * been written as templates?
JLS 0:e5edc0373da0 71 */
JLS 0:e5edc0373da0 72 // Write to DAC channel A with gain 1.
JLS 0:e5edc0373da0 73 void MCP4922::writeA(int value) {
JLS 0:e5edc0373da0 74
JLS 0:e5edc0373da0 75 // Set up the command register with the appropriate value.
JLS 0:e5edc0373da0 76 // For efficiency, the caller is assumed to have checked dac.
JLS 0:e5edc0373da0 77 int reg;
JLS 0:e5edc0373da0 78 //int dac = 0;
JLS 0:e5edc0373da0 79 reg = (value & 0x0FFF) | MCP4922_REG_A1;
JLS 0:e5edc0373da0 80
JLS 0:e5edc0373da0 81 // Select the DAC chip, write to its command register and
JLS 0:e5edc0373da0 82 // then unselect the DAC chip.
JLS 0:e5edc0373da0 83 _ncs_array[dac]->write(0);
JLS 0:e5edc0373da0 84 _spi.write(reg);
JLS 0:e5edc0373da0 85 _ncs_array[dac]->write(1);
JLS 0:e5edc0373da0 86 return;
JLS 0:e5edc0373da0 87 }
JLS 0:e5edc0373da0 88
JLS 0:e5edc0373da0 89 // Write to DAC channel B with gain 1.
JLS 0:e5edc0373da0 90 void MCP4922::writeB(int value) {
JLS 0:e5edc0373da0 91
JLS 0:e5edc0373da0 92 // Set up the command register with the appropriate value.
JLS 0:e5edc0373da0 93 // For efficiency, the caller is assumed to have checked dac.
JLS 0:e5edc0373da0 94 int reg;
JLS 0:e5edc0373da0 95 reg = (value & 0x0FFF) | MCP4922_REG_B1;
JLS 0:e5edc0373da0 96
JLS 0:e5edc0373da0 97 // Select the DAC chip, write to its command register and then
JLS 0:e5edc0373da0 98 // unselect the DAC chip.
JLS 0:e5edc0373da0 99 _ncs_array[dac]->write(0);
JLS 0:e5edc0373da0 100 _spi.write(reg);
JLS 0:e5edc0373da0 101 _ncs_array[dac]->write(1);
JLS 0:e5edc0373da0 102 return;
JLS 0:e5edc0373da0 103 }
JLS 0:e5edc0373da0 104
JLS 0:e5edc0373da0 105 // Write an array of values to the DACs.
JLS 0:e5edc0373da0 106 void MCP4922::write(int nchans, int values[], int gain, int latch) {
JLS 0:e5edc0373da0 107
JLS 0:e5edc0373da0 108 // nchans must be at least 1 but less than or equal to ndacs x 2.
JLS 0:e5edc0373da0 109 if (nchans < 1) nchans = 1;
JLS 0:e5edc0373da0 110 const int maxchans = _ndacs * 2;
JLS 0:e5edc0373da0 111 if (nchans > maxchans) nchans = maxchans;
JLS 0:e5edc0373da0 112
JLS 0:e5edc0373da0 113 if (latch && _latched)
JLS 0:e5edc0373da0 114 latch_disable();
JLS 0:e5edc0373da0 115
JLS 0:e5edc0373da0 116 int i;
JLS 0:e5edc0373da0 117
JLS 0:e5edc0373da0 118 for (i=0; i<nchans;) {
JLS 0:e5edc0373da0 119 dac = i/2;
JLS 0:e5edc0373da0 120 writeA(values[i]);
JLS 0:e5edc0373da0 121 i++;
JLS 0:e5edc0373da0 122 if (i < nchans) {
JLS 0:e5edc0373da0 123 writeB(values[i]);
JLS 0:e5edc0373da0 124 i++;
JLS 0:e5edc0373da0 125 } else break;
JLS 0:e5edc0373da0 126 }
JLS 0:e5edc0373da0 127
JLS 0:e5edc0373da0 128 // Automatically latch the new voltages if the latch flag is 1.
JLS 0:e5edc0373da0 129 if (latch && _latched)
JLS 0:e5edc0373da0 130 latch_enable();
JLS 0:e5edc0373da0 131 return;
JLS 0:e5edc0373da0 132 }
JLS 0:e5edc0373da0 133
JLS 0:e5edc0373da0 134 // Set latch signal to "enable".
JLS 0:e5edc0373da0 135 void MCP4922::latch_enable() {
JLS 0:e5edc0373da0 136
JLS 0:e5edc0373da0 137 // Latch all chips. There should be a delay of at least T_LS=40
JLS 0:e5edc0373da0 138 // nanoseconds between the last CS rising edge and the LDAC falling
JLS 0:e5edc0373da0 139 // edge. The software function calls seem to be sufficient to
JLS 0:e5edc0373da0 140 // introduce that delay. A delay may be inserted here if this
JLS 0:e5edc0373da0 141 // software is ported to a faster processor.
JLS 0:e5edc0373da0 142 if (_latched) _nldac->write(0);
JLS 0:e5edc0373da0 143 // The LDAC pulse width must be at least T_LD=100 nanoseconds long.
JLS 0:e5edc0373da0 144 // A delay can be inserted here if necessary, but so far this has
JLS 0:e5edc0373da0 145 // not been needed (see above).
JLS 0:e5edc0373da0 146 return;
JLS 0:e5edc0373da0 147 }
JLS 0:e5edc0373da0 148
JLS 0:e5edc0373da0 149 // Set latch signal to "disable".
JLS 0:e5edc0373da0 150 void MCP4922::latch_disable() {
JLS 0:e5edc0373da0 151
JLS 0:e5edc0373da0 152 // Disable latch for all chips.
JLS 0:e5edc0373da0 153 if (_latched) _nldac->write(1);
JLS 0:e5edc0373da0 154 return;
JLS 0:e5edc0373da0 155 }
JLS 0:e5edc0373da0 156