Advertisement
Guest User

C-Code for Teensy

a guest
Jul 26th, 2015
466
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 7.08 KB | None | 0 0
  1. //_____ M A C R O S
  2. #define TRUE 1
  3. #define FALSE 0
  4. //#define F_CPU 4000000UL // 4 MHz XTAL
  5. #define CMD_RESET 0x1E // ADC reset command
  6. #define CMD_ADC_READ 0x00 // ADC read command
  7. #define CMD_ADC_CONV 0x40 // ADC conversion command
  8. #define CMD_ADC_D1 0x00 // ADC D1 conversion
  9. #define CMD_ADC_D2 0x10 // ADC D2 conversion
  10. #define CMD_ADC_256 0x00 // ADC OSR=256
  11. #define CMD_ADC_512 0x02 // ADC OSR=512
  12. #define CMD_ADC_1024 0x04 // ADC OSR=1024
  13. #define CMD_ADC_2048 0x06 // ADC OSR=2056
  14. #define CMD_ADC_4096 0x08 // ADC OSR=4096
  15. #define CMD_PROM_RD 0xA0 // Prom read command
  16.  
  17. //_____ I N C L U D E S
  18. #include <stdio.h>
  19. #include <math.h>
  20. #include <SPI.h>
  21.  
  22. //_____ D E F I N I T I O N S
  23. unsigned long D1; // ADC value of the pressure conversion
  24. unsigned long D2; // ADC value of the temperature conversion
  25. unsigned int C[8]; // calibration coefficients
  26. double P; // compensated pressure value
  27. double T; // compensated temperature value
  28. double dT; // difference between actual and measured temperature
  29. double OFF; // offset at actual temperature
  30. double SENS; // sensitivity at actual temperature
  31. double T2; // compensated pressure value, 2nd order
  32. double OFF2; // compensated pressure value, 2nd order
  33. double SENS2; // compensated pressure value, 2nd order
  34.  
  35. int i = 0;
  36. unsigned char n_crc;
  37.  
  38. const int miso_port = 23;
  39. const int mosi_port = 22;
  40. const int sck_port = 14;
  41. const int slaveSelectPin = 21;
  42.  
  43. SPISettings settings(4000000, MSBFIRST, SPI_MODE0);
  44.  
  45. elapsedMillis looptime = 0;
  46.  
  47. void setup() {
  48.   delay(1000);
  49.   pinMode(slaveSelectPin, OUTPUT);
  50.   pinMode(miso_port, OUTPUT);
  51.   pinMode(sck_port, OUTPUT);
  52.   pinMode(mosi_port, INPUT);
  53.   SPI.setMOSI(mosi_port);
  54.   SPI.setMISO(miso_port);
  55.   SPI.setSCK(sck_port);
  56.   SPI.begin();
  57.  
  58.   SPI.beginTransaction(settings);
  59.   //cmd_reset(); // reset the module after powerup
  60.   for (i=0;i<8;i++){ C[i]=cmd_prom(i);} // read calibration coefficients
  61.   n_crc=crc4(C);
  62.   SPI.endTransaction();
  63. }
  64.  
  65. void loop() {
  66.   SPI.beginTransaction(settings);
  67.   // put your main code here, to run repeatedly:
  68.   D1 = cmd_adc(CMD_ADC_D1 + CMD_ADC_256); // read uncompensated pressure
  69.   D2 = cmd_adc(CMD_ADC_D2 + CMD_ADC_4096); // read uncompensated temperature
  70.  
  71.   // calcualte 1st order temperature (MS5803_01b 1st order algorithm), base for 2nd order temperature and pressure
  72.   dT = D2 - C[5] * pow(2, 8);
  73.   OFF = C[2] * pow(2, 16) + dT * C[4] / pow(2, 7);
  74.   SENS = C[1] * pow(2, 15) + dT * C[3] / pow(2, 8);
  75.  
  76.   T = (2000 + (dT * C[6]) / pow(2, 23)) / 100;
  77.  
  78.   // calcualte 2nd order pressure and temperature (MS5803_01b 2nd order algorithm)
  79.   if (T > 20) {
  80.     T2 = 0;
  81.     OFF2 = 0;
  82.     SENS2 = 0;
  83.  
  84.     if (T > 45) {
  85.       SENS2 -= pow(T - 4500, 2) / pow(2, 3);
  86.     }
  87.   }
  88.   else {
  89.     T2 = pow(dT, 2) / pow(2, 31);
  90.     OFF2 = 3 * pow(100*T - 2000, 2);
  91.     SENS2 = 7 * pow(100*T - 2000, 2) / pow(2, 3);
  92.  
  93.     if (T < 15) {
  94.       SENS2 += 2 * pow(100*T + 1500, 2);
  95.     }
  96.   }
  97.  
  98.   //Recalculate T, OFF, SENS based on T2, OFF2, SENS2
  99.   T -= T2;
  100.   OFF -= OFF2;
  101.   SENS -= SENS2;
  102.  
  103.   P = (((D1 * SENS) / pow(2, 21) - OFF) / pow(2, 15)) / 100;
  104.   SPI.endTransaction();
  105.   Serial.println(T);
  106.   delay(100);
  107.   looptime = 0;
  108. }
  109.  
  110. ////********************************************************
  111. ////! @brief send 8 bit using SPI hardware interface
  112. ////!
  113. ////! @return 0
  114. ////********************************************************
  115. //void spi_send(char cmd)
  116. //{
  117. // SPDR= cmd; // put the byte in the SPI hardware buffer and start sending
  118. // while (bit_is_clear(SPSR, 7)); // wait that the data is sent
  119. //}
  120. //********************************************************
  121. //! @brief send reset sequence
  122. //!
  123. //! @return 0
  124. //********************************************************
  125. void cmd_reset(void)
  126. {
  127.   digitalWrite(slaveSelectPin, LOW); //csb_lo(); // pull CSB low to start the command
  128.   SPI.transfer(CMD_RESET); // send reset sequence
  129.   delay(3); // wait for the reset sequence timing
  130.   digitalWrite(slaveSelectPin, HIGH); //csb_hi(); // pull CSB high to finish the command
  131. }
  132. //********************************************************
  133. //! @brief preform adc conversion
  134. //!
  135. //! @return 24bit result
  136. //********************************************************
  137. unsigned long cmd_adc(char cmd)
  138. {
  139.   digitalWrite(slaveSelectPin, LOW);
  140.   unsigned int ret;
  141.   unsigned long temp = 0;
  142.   cmd = SPI.transfer(CMD_ADC_CONV + cmd); // send conversion command
  143.   switch (cmd & 0x0f) // wait necessary conversion time
  144.   {
  145.     case CMD_ADC_256 : delayMicroseconds(900); break;
  146.     case CMD_ADC_512 : delay(3); break;
  147.     case CMD_ADC_1024: delay(4); break;
  148.     case CMD_ADC_2048: delay(6); break;
  149.     case CMD_ADC_4096: delay(10); break;
  150.   }
  151.   digitalWrite(slaveSelectPin, HIGH); // csb_hi(); // pull CSB high to finish the conversion
  152.   digitalWrite(slaveSelectPin, LOW); // csb_lo(); // pull CSB low to start new command
  153.   SPI.transfer(CMD_ADC_READ); // send ADC read command
  154.   SPDR = SPI.transfer(0x00); // send 0 to read 1st byte (MSB)
  155.   ret = SPDR;
  156.   temp = 65536 * ret;
  157.   SPDR = SPI.transfer(0x00); // send 0 to read 2nd byte
  158.   ret = SPDR;
  159.   temp = temp + 256 * ret;
  160.   SPDR = SPI.transfer(0x00); // send 0 to read 3rd byte (LSB)
  161.   ret = SPDR;
  162.   temp = temp + ret;
  163.   digitalWrite(slaveSelectPin, HIGH); // csb_hi(); // pull CSB high to finish the read command
  164.   return temp;
  165. }
  166. //********************************************************
  167. //! @brief Read calibration coefficients
  168. //!
  169. //! @return coefficient
  170. //********************************************************
  171. unsigned int cmd_prom(char coef_num)
  172. {
  173.   unsigned int ret;
  174.   unsigned int rC = 0;
  175.  
  176.   digitalWrite(slaveSelectPin, LOW); //csb_lo(); // pull CSB low
  177.   SPI.transfer(CMD_PROM_RD + coef_num * 2); // send PROM READ command
  178.   SPDR = SPI.transfer(0x00); // send 0 to read the MSB
  179.   ret = SPDR;
  180.   rC = 256 * ret;
  181.   SPDR = SPI.transfer(0x00); // send 0 to read the LSB
  182.   ret = SPDR;
  183.   rC = rC + ret;
  184.   digitalWrite(slaveSelectPin, HIGH); //csb_hi(); // pull CSB high
  185.   return rC;
  186. }
  187. //********************************************************
  188. //! @brief calculate the CRC code for details look into CRC CODE NOTES
  189. //!
  190. //! @return crc code
  191. //********************************************************
  192. unsigned char crc4(unsigned int n_prom[])
  193. {
  194.   int cnt; // simple counter
  195.   unsigned int n_rem; // crc reminder
  196.   unsigned int crc_read; // original value of the crc
  197.   unsigned char n_bit;
  198.   n_rem = 0x00;
  199.   crc_read = n_prom[7]; //save read CRC
  200.   n_prom[7] = (0xFF00 & (n_prom[7])); //CRC byte is replaced by 0
  201.   for (cnt = 0; cnt < 16; cnt++) // operation is performed on bytes
  202.   { // choose LSB or MSB
  203.     if (cnt % 2 == 1) n_rem ^= (unsigned short) ((n_prom[cnt >> 1]) & 0x00FF);
  204.     else n_rem ^= (unsigned short) (n_prom[cnt >> 1] >> 8);
  205.     for (n_bit = 8; n_bit > 0; n_bit--)
  206.     {
  207.       if (n_rem & (0x8000))
  208.       {
  209.         n_rem = (n_rem << 1) ^ 0x3000;
  210.       }
  211.       else
  212.       {
  213.         n_rem = (n_rem << 1);
  214.       }
  215.     }
  216.   }
  217.   n_rem = (0x000F & (n_rem >> 12)); // // final 4-bit reminder is CRC code
  218.   n_prom[7] = crc_read; // restore the crc_read to its original place
  219.   return (n_rem ^ 0x00);
  220. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement