Linduino  1.3.0
Linear Technology Arduino-Compatible Demonstration Board
DC2350AB.ino
Go to the documentation of this file.
1 /*! Analog Devices DC2350A-B Demonstration Board.
2 * LTC6813: Multicell Battery Monitors
3 *
4 *@verbatim
5 *NOTES
6 * Setup:
7 * Set the terminal baud rate to 115200 and select the newline terminator.
8 * Ensure all jumpers on the demo board are installed in their default positions from the factory.
9 * Refer to Demo Manual.
10 *
11 *USER INPUT DATA FORMAT:
12 * decimal : 1024
13 * hex : 0x400
14 * octal : 02000 (leading 0)
15 * binary : B10000000000
16 * float : 1024.0
17 *@endverbatim
18 *
19 * https://www.analog.com/en/products/ltc6813-1.html
20 * https://www.analog.com/en/design-center/evaluation-hardware-and-software/evaluation-boards-kits/dc2350a-b.html
21 *
22 ********************************************************************************
23 * Copyright 2019(c) Analog Devices, Inc.
24 *
25 * All rights reserved.
26 *
27 * Redistribution and use in source and binary forms, with or without
28 * modification, are permitted provided that the following conditions are met:
29 * - Redistributions of source code must retain the above copyright
30 * notice, this list of conditions and the following disclaimer.
31 * - Redistributions in binary form must reproduce the above copyright
32 * notice, this list of conditions and the following disclaimer in
33 * the documentation and/or other materials provided with the
34 * distribution.
35 * - Neither the name of Analog Devices, Inc. nor the names of its
36 * contributors may be used to endorse or promote products derived
37 * from this software without specific prior written permission.
38 * - The use of this software may or may not infringe the patent rights
39 * of one or more patent holders. This license does not release you
40 * from the requirement that you obtain separate licenses from these
41 * patent holders to use this software.
42 * - Use of the software either in source or binary form, must be run
43 * on or directly connected to an Analog Devices Inc. component.
44 *
45 * THIS SOFTWARE IS PROVIDED BY ANALOG DEVICES "AS IS" AND ANY EXPRESS OR
46 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, NON-INFRINGEMENT,
47 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
48 * IN NO EVENT SHALL ANALOG DEVICES BE LIABLE FOR ANY DIRECT, INDIRECT,
49 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
50 * LIMITED TO, INTELLECTUAL PROPERTY RIGHTS, PROCUREMENT OF SUBSTITUTE GOODS OR
51 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
52 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
53 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
54 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
55 *******************************************************************************/
56 
57 /*! @file
58  @ingroup LTC6813-1
59 */
60 
61 /************************************* Read me *******************************************
62 In this sketch book:
63  -All Global Variables are in Upper casing
64  -All Local Variables are in lower casing
65  -The Function wakeup_sleep(TOTAL_IC) : is used to wake the LTC681x from sleep state.
66  It is defined in LTC681x.cpp
67  -The Function wakeup_idle(TOTAL_IC) : is used to wake the ICs connected in daisy chain
68  via the LTC6820 by initiating a dummy SPI communication. It is defined in LTC681x.cpp
69 *******************************************************************************************/
70 
71 /************************* Includes ***************************/
72 #include <Arduino.h>
73 #include <stdint.h>
74 #include <SPI.h>
75 #include "Linduino.h"
76 #include "LT_SPI.h"
77 #include "UserInterface.h"
78 #include "LTC681x.h"
79 #include "LTC6813.h"
80 
81 /************************* Defines *****************************/
82 #define ENABLED 1
83 #define DISABLED 0
84 #define DATALOG_ENABLED 1
85 #define DATALOG_DISABLED 0
86 #define PWM 1
87 #define SCTL 2
88 
89 /**************** Local Function Declaration *******************/
90 void measurement_loop(uint8_t datalog_en);
91 void print_menu(void);
92 void print_wrconfig(void);
93 void print_wrconfigb(void);
94 void print_rxconfig(void);
95 void print_rxconfigb(void);
96 void print_cells(uint8_t datalog_en);
97 void print_aux(uint8_t datalog_en);
98 void print_stat(void);
99 void print_aux1(uint8_t datalog_en);
100 void print_sumofcells(void);
101 void check_mux_fail(void);
102 void print_selftest_errors(uint8_t adc_reg ,int8_t error);
103 void print_overlap_results(int8_t error);
104 void print_digital_redundancy_errors(uint8_t adc_reg ,int8_t error);
105 void print_open_wires(void);
106 void print_pec_error_count(void);
107 int8_t select_s_pin(void);
108 void print_wrpwm(void);
109 void print_rxpwm(void);
110 void print_wrsctrl(void);
111 void print_rxsctrl(void);
112 void print_wrpsb(uint8_t type);
113 void print_rxpsb(uint8_t type);
114 void print_wrcomm(void);
115 void print_rxcomm(void);
116 void check_mute_bit(void);
117 void print_conv_time(uint32_t conv_time);
118 void check_error(int error);
119 void serial_print_text(char data[]);
120 void serial_print_hex(uint8_t data);
121 char read_hex(void);
122 char get_char(void);
123 
124 /*******************************************************************
125  Setup Variables
126  The following variables can be modified to configure the software.
127 ********************************************************************/
128 const uint8_t TOTAL_IC = 2;//!< Number of ICs in the daisy chain
129 
130 /********************************************************************
131  ADC Command Configurations. See LTC681x.h for options
132 *********************************************************************/
133 const uint8_t ADC_OPT = ADC_OPT_DISABLED; //!< ADC Mode option bit
134 const uint8_t ADC_CONVERSION_MODE =MD_7KHZ_3KHZ; //!< ADC Mode
135 const uint8_t ADC_DCP = DCP_DISABLED; //!< Discharge Permitted
136 const uint8_t CELL_CH_TO_CONVERT =CELL_CH_ALL; //!< Channel Selection for ADC conversion
137 const uint8_t AUX_CH_TO_CONVERT = AUX_CH_ALL; //!< Channel Selection for ADC conversion
138 const uint8_t STAT_CH_TO_CONVERT = STAT_CH_ALL; //!< Channel Selection for ADC conversion
139 const uint8_t SEL_ALL_REG = REG_ALL; //!< Register Selection
140 const uint8_t SEL_REG_A = REG_1; //!< Register Selection
141 const uint8_t SEL_REG_B = REG_2; //!< Register Selection
142 
143 const uint16_t MEASUREMENT_LOOP_TIME = 500; //!< Loop Time in milliseconds(ms)
144 
145 //Under Voltage and Over Voltage Thresholds
146 const uint16_t OV_THRESHOLD = 41000; //!< Over voltage threshold ADC Code. LSB = 0.0001 ---(4.1V)
147 const uint16_t UV_THRESHOLD = 30000; //!< Under voltage threshold ADC Code. LSB = 0.0001 ---(3V)
148 
149 //Loop Measurement Setup. These Variables are ENABLED or DISABLED. Remember ALL CAPS
150 const uint8_t WRITE_CONFIG = DISABLED; //!< This is to ENABLED or DISABLED writing into to configuration registers in a continuous loop
151 const uint8_t READ_CONFIG = DISABLED; //!< This is to ENABLED or DISABLED reading the configuration registers in a continuous loop
152 const uint8_t MEASURE_CELL = ENABLED; //!< This is to ENABLED or DISABLED measuring the cell voltages in a continuous loop
153 const uint8_t MEASURE_AUX = DISABLED; //!< This is to ENABLED or DISABLED reading the auxiliary registers in a continuous loop
154 const uint8_t MEASURE_STAT = DISABLED; //!< This is to ENABLED or DISABLED reading the status registers in a continuous loop
155 const uint8_t PRINT_PEC = DISABLED; //!< This is to ENABLED or DISABLED printing the PEC Error Count in a continuous loop
156 /************************************
157  END SETUP
158 *************************************/
159 
160 /*******************************************************
161  Global Battery Variables received from 681x commands
162  These variables store the results from the LTC6813
163  register reads and the array lengths must be based
164  on the number of ICs on the stack
165  ******************************************************/
166 cell_asic BMS_IC[TOTAL_IC]; //!< Global Battery Variable
167 
168 /*************************************************************************
169  Set configuration register. Refer to the data sheet
170 **************************************************************************/
171 bool REFON = true; //!< Reference Powered Up Bit
172 bool ADCOPT = false; //!< ADC Mode option bit
173 bool GPIOBITS_A[5] = {false,false,true,true,true}; //!< GPIO Pin Control // Gpio 1,2,3,4,5
174 bool GPIOBITS_B[4] = {false,false,false,false}; //!< GPIO Pin Control // Gpio 6,7,8,9
175 uint16_t UV=UV_THRESHOLD; //!< Under voltage Comparison Voltage
176 uint16_t OV=OV_THRESHOLD; //!< Over voltage Comparison Voltage
177 bool DCCBITS_A[12] = {false,false,false,false,false,false,false,false,false,false,false,false}; //!< Discharge cell switch //Dcc 1,2,3,4,5,6,7,8,9,10,11,12
178 bool DCCBITS_B[7]= {false,false,false,false,false,false,false}; //!< Discharge cell switch //Dcc 0,13,14,15
179 bool DCTOBITS[4] = {true,false,true,false}; //!< Discharge time value //Dcto 0,1,2,3 // Programed for 4 min
180 /*Ensure that Dcto bits are set according to the required discharge time. Refer to the data sheet */
181 bool FDRF = false; //!< Force Digital Redundancy Failure Bit
182 bool DTMEN = true; //!< Enable Discharge Timer Monitor
183 bool PSBITS[2]= {false,false}; //!< Digital Redundancy Path Selection//ps-0,1
184 
185 /*!**********************************************************************
186  \brief Initializes hardware and variables
187  @return void
188  ***********************************************************************/
189 void setup()
190 {
191  Serial.begin(115200);
193  spi_enable(SPI_CLOCK_DIV16); // This will set the Linduino to have a 1MHz Clock
194  LTC6813_init_cfg(TOTAL_IC, BMS_IC);
195  LTC6813_init_cfgb(TOTAL_IC,BMS_IC);
196  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
197  {
200  }
201  LTC6813_reset_crc_count(TOTAL_IC,BMS_IC);
202  LTC6813_init_reg_limits(TOTAL_IC,BMS_IC);
203  print_menu();
204 }
205 
206 /*!*********************************************************************
207  \brief Main loop
208  @return void
209 ***********************************************************************/
210 void loop()
211 {
212  if (Serial.available()) // Check for user input
213  {
214  uint32_t user_command;
215  user_command = read_int(); // Read the user command
216  if(user_command=='m')
217  {
218  print_menu();
219  }
220  else
221  {
222  Serial.println(user_command);
223  run_command(user_command);
224  }
225  }
226 }
227 
228 /*!*****************************************
229  \brief executes the user command
230  @return void
231 *******************************************/
232 void run_command(uint32_t cmd)
233 {
234 
235  uint8_t streg=0;
236  int8_t error = 0;
237  uint32_t conv_time = 0;
238  int8_t s_pin_read=0;
239 
240  switch (cmd)
241  {
242  case 1: // Write and read Configuration Register
244  LTC6813_wrcfg(TOTAL_IC,BMS_IC); // Write into Configuration Register
245  LTC6813_wrcfgb(TOTAL_IC,BMS_IC); // Write into Configuration Register B
246  print_wrconfig();
247  print_wrconfigb();
248 
250  error = LTC6813_rdcfg(TOTAL_IC,BMS_IC); // Read Configuration Register
251  check_error(error);
252  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC); // Read Configuration Register B
253  check_error(error);
254  print_rxconfig();
255  print_rxconfigb();
256  break;
257 
258  case 2: // Read Configuration Register
260  error = LTC6813_rdcfg(TOTAL_IC,BMS_IC);
261  check_error(error);
262  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
263  check_error(error);
264  print_rxconfig();
265  print_rxconfigb();
266  break;
267 
268  case 3: // Start Cell ADC Measurement
271  conv_time = LTC6813_pollAdc();
272  print_conv_time(conv_time);
273  break;
274 
275  case 4: // Read Cell Voltage Registers
277  error = LTC6813_rdcv(SEL_ALL_REG,TOTAL_IC,BMS_IC); // Set to read back all cell voltage registers
278  check_error(error);
280  break;
281 
282  case 5: // Start GPIO ADC Measurement
285  conv_time = LTC6813_pollAdc();
286  print_conv_time(conv_time);
287  break;
288 
289  case 6: // Read AUX Voltage Registers
291  error = LTC6813_rdaux(SEL_ALL_REG,TOTAL_IC,BMS_IC); // Set to read back all aux registers
292  check_error(error);
294  break;
295 
296  case 7: // Start Status ADC Measurement
299  conv_time = LTC6813_pollAdc();
300  print_conv_time(conv_time);
301  break;
302 
303  case 8: // Read Status registers
305  error = LTC6813_rdstat(SEL_ALL_REG,TOTAL_IC,BMS_IC); // Set to read back all stat registers
306  check_error(error);
307  print_stat();
308  break;
309 
310  case 9: // Start Combined Cell Voltage and GPIO1, GPIO2 Conversion and Poll Status
313  conv_time = LTC6813_pollAdc();
314  print_conv_time(conv_time);
316  error = LTC6813_rdcv(SEL_ALL_REG, TOTAL_IC,BMS_IC); // Set to read back all cell voltage registers
317  check_error(error);
320  error = LTC6813_rdaux(SEL_REG_A,TOTAL_IC,BMS_IC); // Set to read back aux register A
321  check_error(error);
323  break;
324 
325  case 10: //Start Combined Cell Voltage and Sum of cells
328  conv_time = LTC6813_pollAdc();
329  print_conv_time(conv_time);
331  error = LTC6813_rdcv(SEL_ALL_REG, TOTAL_IC,BMS_IC); // Set to read back all cell voltage registers
332  check_error(error);
335  error = LTC6813_rdstat(SEL_REG_A,TOTAL_IC,BMS_IC); // Set to read back stat register A
336  check_error(error);
338  break;
339 
340  case 11: // Loop Measurements of configuration register or cell voltages or auxiliary register or status register without data-log output
342  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
343  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
345  print_menu();
346  break;
347 
348  case 12: // Data-log print option Loop Measurements of configuration register or cell voltages or auxiliary register or status register
350  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
351  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
353  print_menu();
354  break;
355 
356  case 13: // Clear all ADC measurement registers
358  LTC6813_clrcell();
359  LTC6813_clraux();
360  LTC6813_clrstat();
362  LTC6813_rdcv(SEL_ALL_REG, TOTAL_IC,BMS_IC); // read back all cell voltage registers
364  LTC6813_rdaux(SEL_ALL_REG,TOTAL_IC,BMS_IC); // read back all auxiliary registers
366  LTC6813_rdstat(SEL_ALL_REG,TOTAL_IC,BMS_IC); // read back all status registers
367  print_stat();
368  break;
369 
370  case 14: // Run the Mux Decoder Self Test
372  LTC6813_diagn();
373  LTC6813_pollAdc();
374  error = LTC6813_rdstat(SEL_REG_B,TOTAL_IC,BMS_IC); // Set to read back register B
375  check_error(error);
376  check_mux_fail();
377  break;
378 
379  case 15: // Run the ADC/Memory Self Test
380  error = 0;
383  print_selftest_errors(CELL, error);
384 
385  error = 0;
388  print_selftest_errors(AUX, error);
389 
390  error = 0;
393  print_selftest_errors(STAT, error);
394  break;
395 
396  case 16: // Run ADC Overlap self test
398  error = (int8_t)LTC6813_run_adc_overlap(TOTAL_IC,BMS_IC);
399  print_overlap_results(error);
400  break;
401 
402  case 17: // Run ADC Redundancy self test
406 
410  break;
411 
412  case 18: // Run open wire self test for single cell detection
416  break;
417 
418  case 19: // Run open wire self test for multiple cell and two consecutive cells detection
421  break;
422 
423  case 20: // Open wire Diagnostic for Auxiliary Measurements
427  break;
428 
429  case 21: // Print pec counter
431  break;
432 
433  case 22:// Reset pec counter
436  break;
437 
438  case 23: // Enable a discharge transistor
439  s_pin_read = select_s_pin();
441  LTC6813_set_discharge(s_pin_read,TOTAL_IC,BMS_IC);
442  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
443  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
444  print_wrconfig();
445  print_wrconfigb();
447  error = LTC6813_rdcfg(TOTAL_IC,BMS_IC);
448  check_error(error);
449  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
450  check_error(error);
451  print_rxconfig();
452  print_rxconfigb();
453  break;
454 
455  case 24: // Clear all discharge transistors
458  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
459  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
460  print_wrconfig();
461  print_wrconfigb();
463  error = LTC6813_rdcfg(TOTAL_IC,BMS_IC);
464  check_error(error);
465  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
466  check_error(error);
467  print_rxconfig();
468  print_rxconfigb();
469  break;
470 
471  case 25://Write and read pwm configuration
472  /*****************************************************
473  PWM configuration data.
474  1)Set the corresponding DCC bit to one for pwm operation.
475  2)Set the DCTO bits to the required discharge time.
476  3)Choose the value to be configured depending on the
477  required duty cycle.
478  Refer to the data sheet.
479  *******************************************************/
481 
482  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
483  {
484  BMS_IC[current_ic].pwm.tx_data[0]= 0x88; //Duty cycle for S pin 2 and 1
485  BMS_IC[current_ic].pwm.tx_data[1]= 0x88; //Duty cycle for S pin 4 and 3
486  BMS_IC[current_ic].pwm.tx_data[2]= 0x88; //Duty cycle for S pin 6 and 5
487  BMS_IC[current_ic].pwm.tx_data[3]= 0x88; //Duty cycle for S pin 8 and 7
488  BMS_IC[current_ic].pwm.tx_data[4]= 0x88; //Duty cycle for S pin 10 and 9
489  BMS_IC[current_ic].pwm.tx_data[5]= 0x88; //Duty cycle for S pin 12 and 11
490  }
491 
492  LTC6813_wrpwm(TOTAL_IC,0,BMS_IC); //Write pwm configuration
493 
494  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
495  {
496  BMS_IC[current_ic].pwmb.tx_data[0]= 0x88; //Duty cycle for S pin 14 and 13
497  BMS_IC[current_ic].pwmb.tx_data[1]= 0x88; //Duty cycle for S pin 16 and 15
498  BMS_IC[current_ic].pwmb.tx_data[2]= 0x88; //Duty cycle for S pin 18 and 17
499  }
500 
501  LTC6813_wrpsb(TOTAL_IC,BMS_IC); // Write PWM/S control register group B
502  print_wrpwm();
503  print_wrpsb(PWM);
504 
505  wakeup_idle(TOTAL_IC);
506  error=LTC6813_rdpwm(TOTAL_IC,0,BMS_IC); // Read pwm configuration
507  check_error(error);
508 
509  error=LTC6813_rdpsb(TOTAL_IC,BMS_IC); // Read PWM/S Control Register Group
510  check_error(error);
511  print_rxpwm();
512  print_rxpsb(PWM);
513  break;
514 
515  case 26: // Write and read S Control Register Group
516  /**************************************************************************************
517  S pin control.
518  1)Ensure that the pwm is set according to the requirement using the previous case.
519  2)Choose the value depending on the required number of pulses on S pin.
520  Refer to the data sheet.
521  ***************************************************************************************/
522  wakeup_sleep(TOTAL_IC);
523 
524  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
525  {
526  BMS_IC[current_ic].sctrl.tx_data[0]= 0xFF; // No. of high pulses on S pin 2 and 1
527  BMS_IC[current_ic].sctrl.tx_data[1]= 0xFF; // No. of high pulses on S pin 4 and 3
528  BMS_IC[current_ic].sctrl.tx_data[2]= 0xFF; // No. of high pulses on S pin 6 and 5
529  BMS_IC[current_ic].sctrl.tx_data[3]= 0xFF; // No. of high pulses on S pin 8 and 7
530  BMS_IC[current_ic].sctrl.tx_data[4]= 0xFF; // No. of high pulses on S pin 10 and 9
531  BMS_IC[current_ic].sctrl.tx_data[5]= 0xFF; // No. of high pulses on S pin 12 and 11
532  }
533 
534  LTC6813_wrsctrl(TOTAL_IC,streg,BMS_IC); // Write S Control Register Group
535 
536  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
537  {
538  BMS_IC[current_ic].sctrlb.tx_data[3]= 0xFF; // No. of high pulses on S pin 14 and 13
539  BMS_IC[current_ic].sctrlb.tx_data[4]= 0xFF; // No. of high pulses on S pin 16 and 15
540  BMS_IC[current_ic].sctrlb.tx_data[5]= 0xFF; // No. of high pulses on S pin 18 and 17
541  }
542 
543  LTC6813_wrpsb(TOTAL_IC,BMS_IC); // Write PWM/S control register group B
544  print_wrsctrl();
545  print_wrpsb(SCTL);
546 
547  wakeup_idle(TOTAL_IC);
548  LTC6813_stsctrl(); // Start S Control pulsing
549 
550  wakeup_idle(TOTAL_IC);
551  error=LTC6813_rdsctrl(TOTAL_IC,streg,BMS_IC); // Read S Control Register Group
552  check_error(error);
553 
554  error=LTC6813_rdpsb(TOTAL_IC,BMS_IC); // Read PWM/S Control Register Group
555  check_error(error);
556  print_rxsctrl();
557  print_rxpsb(SCTL);
558  break;
559 
560  case 27: // Clear S Control Register Group
561  wakeup_sleep(TOTAL_IC);
563  wakeup_idle(TOTAL_IC);
564  error=LTC6813_rdsctrl(TOTAL_IC,streg,BMS_IC);
565  check_error(error);
566  LTC6813_rdpsb(TOTAL_IC,BMS_IC);
567  print_rxsctrl();
568  print_rxpsb(SCTL);
569  break;
570 
571  case 28://SPI Communication
572  /************************************************************
573  Ensure to set the GPIO bits to 1 in the CFG register group.
574  *************************************************************/
575  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
576  {
577  //Communication control bits and communication data bytes. Refer to the data sheet.
578  BMS_IC[current_ic].com.tx_data[0]= 0x81; // Icom CSBM Low(8) + data D0 (0x11)
579  BMS_IC[current_ic].com.tx_data[1]= 0x10; // Fcom CSBM Low(0)
580  BMS_IC[current_ic].com.tx_data[2]= 0xA2; // Icom CSBM Falling Edge (A) + data D1 (0x25)
581  BMS_IC[current_ic].com.tx_data[3]= 0x50; // Fcom CSBM Low(0)
582  BMS_IC[current_ic].com.tx_data[4]= 0xA1; // Icom CSBM Falling Edge (A) + data D2 (0x17)
583  BMS_IC[current_ic].com.tx_data[5]= 0x79; // Fcom CSBM High(9)
584  }
585  wakeup_sleep(TOTAL_IC);
586  LTC6813_wrcomm(TOTAL_IC,BMS_IC);
587  print_wrcomm();
588 
589  wakeup_idle(TOTAL_IC);
590  LTC6813_stcomm(3);
591 
592  wakeup_idle(TOTAL_IC);
593  error = LTC6813_rdcomm(TOTAL_IC,BMS_IC);
594  check_error(error);
595  print_rxcomm();
596  break;
597 
598  case 29: // Write byte I2C Communication on the GPIO Ports(using I2C eeprom 24LC025)
599  /************************************************************
600  Ensure to set the GPIO bits to 1 in the CFG register group.
601  *************************************************************/
602  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
603  {
604  //Communication control bits and communication data bytes. Refer to the data sheet.
605  BMS_IC[current_ic].com.tx_data[0]= 0x6A; // Icom Start(6) + I2C_address D0 (0xA0)
606  BMS_IC[current_ic].com.tx_data[1]= 0x08; // Fcom master NACK(8)
607  BMS_IC[current_ic].com.tx_data[2]= 0x00; // Icom Blank (0) + eeprom address D1 (0x00)
608  BMS_IC[current_ic].com.tx_data[3]= 0x08; // Fcom master NACK(8)
609  BMS_IC[current_ic].com.tx_data[4]= 0x01; // Icom Blank (0) + data D2 (0x13)
610  BMS_IC[current_ic].com.tx_data[5]= 0x39; // Fcom master NACK + Stop(9)
611  }
612  wakeup_sleep(TOTAL_IC);
613  LTC6813_wrcomm(TOTAL_IC,BMS_IC); // write to comm register
614  print_wrcomm(); // print transmitted data from the comm register
615 
616  wakeup_idle(TOTAL_IC);
617  LTC6813_stcomm(3); // data length=3 // initiates communication between master and the I2C slave
618 
619  wakeup_idle(TOTAL_IC);
620  error = LTC6813_rdcomm(TOTAL_IC,BMS_IC); // read from comm register
621  check_error(error);
622  print_rxcomm(); // print received data into the comm register
623  break;
624 
625  case 30: // Read byte data I2C Communication on the GPIO Ports(using I2C eeprom 24LC025)
626  /************************************************************
627  Ensure to set the GPIO bits to 1 in the CFG register group.
628  *************************************************************/
629  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
630  {
631  //Communication control bits and communication data bytes. Refer to the data sheet.
632  BMS_IC[current_ic].com.tx_data[0]= 0x6A; // Icom Start (6) + I2C_address D0 (A0) (Write operation to set the word address)
633  BMS_IC[current_ic].com.tx_data[1]= 0x08; // Fcom master NACK(8)
634  BMS_IC[current_ic].com.tx_data[2]= 0x00; // Icom Blank (0) + eeprom address(word address) D1 (0x00)
635  BMS_IC[current_ic].com.tx_data[3]= 0x08; // Fcom master NACK(8)
636  BMS_IC[current_ic].com.tx_data[4]= 0x6A; // Icom Start (6) + I2C_address D2 (0xA1)(Read operation)
637  BMS_IC[current_ic].com.tx_data[5]= 0x18; // Fcom master NACK(8)
638  }
639  wakeup_sleep(TOTAL_IC);
640  LTC6813_wrcomm(TOTAL_IC,BMS_IC); // write to comm register
641 
642  wakeup_idle(TOTAL_IC);
643  LTC6813_stcomm(3); // data length=3 // initiates communication between master and the I2C slave
644 
645  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
646  {
647  //Communication control bits and communication data bytes. Refer to the data sheet.
648  BMS_IC[current_ic].com.tx_data[0]= 0x0F; // Icom Blank (0) + data D0 (FF)
649  BMS_IC[current_ic].com.tx_data[1]= 0xF9; // Fcom master NACK + Stop(9)
650  BMS_IC[current_ic].com.tx_data[2]= 0x7F; // Icom No Transmit (7) + data D1 (FF)
651  BMS_IC[current_ic].com.tx_data[3]= 0xF9; // Fcom master NACK + Stop(9)
652  BMS_IC[current_ic].com.tx_data[4]= 0x7F; // Icom No Transmit (7) + data D2 (FF)
653  BMS_IC[current_ic].com.tx_data[5]= 0xF9; // Fcom master NACK + Stop(9)
654  }
655  wakeup_idle(TOTAL_IC);
656  LTC6813_wrcomm(TOTAL_IC,BMS_IC); // write to comm register
657 
658  wakeup_idle(TOTAL_IC);
659  LTC6813_stcomm(1); // data length=1 // initiates communication between master and the I2C slave
660 
661  wakeup_idle(TOTAL_IC);
662  error = LTC6813_rdcomm(TOTAL_IC,BMS_IC); // read from comm register
663  check_error(error);
664  print_rxcomm(); // print received data from the comm register
665  break;
666 
667  case 31: // Enable MUTE
668  wakeup_sleep(TOTAL_IC);
669  LTC6813_mute();
670  wakeup_idle(TOTAL_IC);
671  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
672  check_error(error);
673  check_mute_bit();
674  break;
675 
676  case 32: // To enable UNMUTE
677  wakeup_sleep(TOTAL_IC);
678  LTC6813_unmute();
679  wakeup_idle(TOTAL_IC);
680  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
681  check_error(error);
682  check_mute_bit();
683  break;
684 
685  case 33: // Set and reset the gpio pins(to drive output on gpio pins)
686  /***********************************************************************
687  Please ensure you have set the GPIO bits according to your requirement
688  in the configuration register.( check the global variable GPIOBITS_A )
689  ************************************************************************/
690  wakeup_sleep(TOTAL_IC);
691  for (uint8_t current_ic = 0; current_ic<TOTAL_IC;current_ic++)
692  {
695  }
696 
697  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
698  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
699  print_wrconfig();
700  print_wrconfigb();
701  break;
702 
703  case 'm': //prints menu
704  print_menu();
705  break;
706 
707  default:
708  char str_error[]="Incorrect Option \n";
709  serial_print_text(str_error);
710  break;
711  }
712 }
713 
714 /*!**********************************************************************************************************************************************
715  \brief For writing/reading configuration data or measuring cell voltages or reading aux register or reading status register in a continuous loop
716  @return void
717 *************************************************************************************************************************************************/
718 void measurement_loop(uint8_t datalog_en)
719 {
720  int8_t error = 0;
721  char input = 0;
722 
723  Serial.println(F("Transmit 'm' to quit"));
724 
725  while (input != 'm')
726  {
727  if (Serial.available() > 0)
728  {
729  input = read_char();
730  }
731 
732  if (WRITE_CONFIG == ENABLED)
733  {
735  LTC6813_wrcfg(TOTAL_IC,BMS_IC);
736  LTC6813_wrcfgb(TOTAL_IC,BMS_IC);
737  print_wrconfig();
738  print_wrconfigb();
739  }
740 
741  if (READ_CONFIG == ENABLED)
742  {
744  error = LTC6813_rdcfg(TOTAL_IC,BMS_IC);
745  check_error(error);
746  error = LTC6813_rdcfgb(TOTAL_IC,BMS_IC);
747  check_error(error);
748  print_rxconfig();
749  print_rxconfigb();
750  }
751 
752  if (MEASURE_CELL == ENABLED)
753  {
756  LTC6813_pollAdc();
758  error = LTC6813_rdcv(0, TOTAL_IC,BMS_IC);
759  check_error(error);
760  print_cells(datalog_en);
761  }
762 
763  if (MEASURE_AUX == ENABLED)
764  {
767  LTC6813_pollAdc();
769  error = LTC6813_rdaux(0,TOTAL_IC,BMS_IC); // Set to read back all aux registers
770  check_error(error);
771  print_aux(datalog_en);
772  }
773 
774  if (MEASURE_STAT == ENABLED)
775  {
778  LTC6813_pollAdc();
780  error = LTC6813_rdstat(0,TOTAL_IC,BMS_IC); // Set to read back all aux registers
781  check_error(error);
782  print_stat();
783  }
784 
785  if(PRINT_PEC == ENABLED)
786  {
788  }
789 
790  delay(MEASUREMENT_LOOP_TIME);
791  }
792 }
793 
794 /*!*********************************
795  \brief Prints the main menu
796  @return void
797 ***********************************/
798 void print_menu(void)
799 {
800  Serial.println(F("List of LTC6813 Command:"));
801  Serial.println(F("Write and Read Configuration: 1 |Loop measurements with data-log output : 12 |Set Discharge: 23 "));
802  Serial.println(F("Read Configuration: 2 |Clear Registers: 13 |Clear Discharge: 24 "));
803  Serial.println(F("Start Cell Voltage Conversion: 3 |Run Mux Self Test: 14 |Write and Read of PWM : 25"));
804  Serial.println(F("Read Cell Voltages: 4 |Run ADC Self Test: 15 |Write and Read of S control : 26"));
805  Serial.println(F("Start Aux Voltage Conversion: 5 |ADC overlap Test : 16 |Clear S control register : 27"));
806  Serial.println(F("Read Aux Voltages: 6 |Run Digital Redundancy Test: 17 |SPI Communication : 28"));
807  Serial.println(F("Start Stat Voltage Conversion: 7 |Open Wire Test for single cell detection: 18 |I2C Communication Write to Slave :29"));
808  Serial.println(F("Read Stat Voltages: 8 |Open Wire Test for multiple cell or two consecutive cells detection:19 |I2C Communication Read from Slave :30"));
809  Serial.println(F("Start Combined Cell Voltage and GPIO1, GPIO2 Conversion: 9 |Open wire for Auxiliary Measurement: 20 |Enable MUTE : 31"));
810  Serial.println(F("Start Cell Voltage and Sum of cells : 10 |Print PEC Counter: 21 |Disable MUTE : 32"));
811  Serial.println(F("Loop Measurements: 11 |Reset PEC Counter: 22 |Set or reset the gpio pins: 33 \n "));
812  Serial.println(F("Print 'm' for menu"));
813  Serial.println(F("Please enter command: \n "));
814 }
815 
816 /*!******************************************************************************
817  \brief Prints the configuration data that is going to be written to the LTC6813
818  to the serial port.
819  @return void
820  ********************************************************************************/
821 void print_wrconfig(void)
822 {
823  int cfg_pec;
824  Serial.println(F("Written Configuration A Register: "));
825  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
826  {
827  Serial.print(F("CFGA IC "));
828  Serial.print(current_ic+1,DEC);
829  for(int i = 0;i<6;i++)
830  {
831  Serial.print(F(", 0x"));
832  serial_print_hex(BMS_IC[current_ic].config.tx_data[i]);
833  }
834  Serial.print(F(", Calculated PEC: 0x"));
835  cfg_pec = pec15_calc(6,&BMS_IC[current_ic].config.tx_data[0]);
836  serial_print_hex((uint8_t)(cfg_pec>>8));
837  Serial.print(F(", 0x"));
838  serial_print_hex((uint8_t)(cfg_pec));
839  Serial.println("\n");
840  }
841 }
842 
843 /*!******************************************************************************
844  \brief Prints the Configuration Register B data that is going to be written to
845  the LTC6813 to the serial port.
846  @return void
847  ********************************************************************************/
848 void print_wrconfigb(void)
849 {
850  int cfg_pec;
851  Serial.println(F("Written Configuration B Register: "));
852  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
853  {
854  Serial.print(F("CFGB IC "));
855  Serial.print(current_ic+1,DEC);
856  for(int i = 0;i<6;i++)
857  {
858  Serial.print(F(", 0x"));
859  serial_print_hex(BMS_IC[current_ic].configb.tx_data[i]);
860  }
861  Serial.print(F(", Calculated PEC: 0x"));
862  cfg_pec = pec15_calc(6,&BMS_IC[current_ic].configb.tx_data[0]);
863  serial_print_hex((uint8_t)(cfg_pec>>8));
864  Serial.print(F(", 0x"));
865  serial_print_hex((uint8_t)(cfg_pec));
866  Serial.println("\n");
867  }
868 }
869 
870 /*!*****************************************************************
871  \brief Prints the configuration data that was read back from the
872  LTC6813 to the serial port.
873  @return void
874  *******************************************************************/
875 void print_rxconfig(void)
876 {
877  Serial.println(F("Received Configuration A Register: "));
878  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
879  {
880  Serial.print(F("CFGA IC "));
881  Serial.print(current_ic+1,DEC);
882  for(int i = 0; i < 6; i++)
883  {
884  Serial.print(F(", 0x"));
885  serial_print_hex(BMS_IC[current_ic].config.rx_data[i]);
886  }
887  Serial.print(F(", Received PEC: 0x"));
888  serial_print_hex(BMS_IC[current_ic].config.rx_data[6]);
889  Serial.print(F(", 0x"));
890  serial_print_hex(BMS_IC[current_ic].config.rx_data[7]);
891  Serial.println("\n");
892  }
893 }
894 
895 /*!*****************************************************************
896  \brief Prints the Configuration Register B that was read back from
897  the LTC6813 to the serial port.
898  @return void
899  *******************************************************************/
900 void print_rxconfigb(void)
901 {
902  Serial.println(F("Received Configuration B Register: "));
903  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
904  {
905  Serial.print(F("CFGB IC "));
906  Serial.print(current_ic+1,DEC);
907  for(int i = 0; i < 6; i++)
908  {
909  Serial.print(F(", 0x"));
910  serial_print_hex(BMS_IC[current_ic].configb.rx_data[i]);
911  }
912  Serial.print(F(", Received PEC: 0x"));
913  serial_print_hex(BMS_IC[current_ic].configb.rx_data[6]);
914  Serial.print(F(", 0x"));
915  serial_print_hex(BMS_IC[current_ic].configb.rx_data[7]);
916  Serial.println("\n");
917  }
918 }
919 
920 /*!************************************************************
921  \brief Prints cell voltage codes to the serial port
922  @return void
923  *************************************************************/
924 void print_cells(uint8_t datalog_en)
925 {
926  for (int current_ic = 0 ; current_ic < TOTAL_IC; current_ic++)
927  {
928  if (datalog_en == 0)
929  {
930  Serial.print(" IC ");
931  Serial.print(current_ic+1,DEC);
932  Serial.print(", ");
933  for (int i=0; i<BMS_IC[0].ic_reg.cell_channels; i++)
934  {
935  Serial.print(" C");
936  Serial.print(i+1,DEC);
937  Serial.print(":");
938  Serial.print(BMS_IC[current_ic].cells.c_codes[i]*0.0001,4);
939  Serial.print(",");
940  }
941  Serial.println();
942  }
943  else
944  {
945  Serial.print(" Cells, ");
946  for (int i=0; i<BMS_IC[0].ic_reg.cell_channels; i++)
947  {
948  Serial.print(BMS_IC[current_ic].cells.c_codes[i]*0.0001,4);
949  Serial.print(",");
950  }
951  }
952  }
953  Serial.println("\n");
954 }
955 
956 /*!****************************************************************************
957  \brief Prints GPIO voltage codes and Vref2 voltage code onto the serial port
958  @return void
959  *****************************************************************************/
960 void print_aux(uint8_t datalog_en)
961 {
962  for (int current_ic =0 ; current_ic < TOTAL_IC; current_ic++)
963  {
964  if (datalog_en == 0)
965  {
966  Serial.print(" IC ");
967  Serial.print(current_ic+1,DEC);
968  for (int i=0; i < 5; i++)
969  {
970  Serial.print(F(" GPIO-"));
971  Serial.print(i+1,DEC);
972  Serial.print(":");
973  Serial.print(BMS_IC[current_ic].aux.a_codes[i]*0.0001,4);
974  Serial.print(",");
975  }
976 
977  for (int i=6; i < 10; i++)
978  {
979  Serial.print(F(" GPIO-"));
980  Serial.print(i,DEC);
981  Serial.print(":");
982  Serial.print(BMS_IC[current_ic].aux.a_codes[i]*0.0001,4);
983  }
984 
985  Serial.print(F(" Vref2"));
986  Serial.print(":");
987  Serial.print(BMS_IC[current_ic].aux.a_codes[5]*0.0001,4);
988  Serial.println();
989 
990  Serial.print(" OV/UV Flags : 0x");
991  Serial.print((uint8_t)BMS_IC[current_ic].aux.a_codes[11],HEX);
992  Serial.println();
993  }
994  else
995  {
996  Serial.print(" AUX, ");
997 
998  for (int i=0; i < 12; i++)
999  {
1000  Serial.print((uint8_t)BMS_IC[current_ic].aux.a_codes[i]*0.0001,4);
1001  Serial.print(",");
1002  }
1003  }
1004  }
1005  Serial.println("\n");
1006 }
1007 
1008 /*!****************************************************************************
1009  \brief Prints Status voltage codes and Vref2 voltage code onto the serial port
1010  @return void
1011  *****************************************************************************/
1012 void print_stat(void)
1013 {
1014  for (int current_ic =0 ; current_ic < TOTAL_IC; current_ic++)
1015  {
1016  double itmp;
1017 
1018  Serial.print(F(" IC "));
1019  Serial.print(current_ic+1,DEC);
1020  Serial.print(F(" SOC:"));
1021  Serial.print(BMS_IC[current_ic].stat.stat_codes[0]*0.0001*30,4);
1022  Serial.print(F(","));
1023  Serial.print(F(" Itemp:"));
1024  itmp = (double)((BMS_IC[current_ic].stat.stat_codes[1] * (0.0001 / 0.0076)) - 276); //Internal Die Temperature(°C) = ITMP • (100 µV / 7.6mV)°C - 276°C
1025  Serial.print(itmp,4);
1026  Serial.print(F(","));
1027  Serial.print(F(" VregA:"));
1028  Serial.print(BMS_IC[current_ic].stat.stat_codes[2]*0.0001,4);
1029  Serial.print(F(","));
1030  Serial.print(F(" VregD:"));
1031  Serial.print(BMS_IC[current_ic].stat.stat_codes[3]*0.0001,4);
1032  Serial.println();
1033  Serial.print(F(" OV/UV Flags:"));
1034  Serial.print(F(", 0x"));
1035  serial_print_hex(BMS_IC[current_ic].stat.flags[0]);
1036  Serial.print(F(", 0x"));
1037  serial_print_hex(BMS_IC[current_ic].stat.flags[1]);
1038  Serial.print(F(", 0x"));
1039  serial_print_hex(BMS_IC[current_ic].stat.flags[2]);
1040  Serial.print(F("\tMux fail flag:"));
1041  Serial.print(F(", 0x"));
1042  serial_print_hex(BMS_IC[current_ic].stat.mux_fail[0]);
1043  Serial.print(F("\tTHSD:"));
1044  Serial.print(F(", 0x"));
1045  serial_print_hex(BMS_IC[current_ic].stat.thsd[0]);
1046  Serial.println();
1047  }
1048  Serial.println("\n");
1049 }
1050 
1051 /*!****************************************************************************
1052  \brief Prints GPIO voltage codes (GPIO 1 & 2)
1053  @return void
1054  *****************************************************************************/
1055 void print_aux1(uint8_t datalog_en)
1056 {
1057 
1058  for (int current_ic =0 ; current_ic < TOTAL_IC; current_ic++)
1059  {
1060  if (datalog_en == 0)
1061  {
1062  Serial.print(" IC ");
1063  Serial.print(current_ic+1,DEC);
1064  for (int i=0; i < 2; i++)
1065  {
1066  Serial.print(F(" GPIO-"));
1067  Serial.print(i+1,DEC);
1068  Serial.print(":");
1069  Serial.print(BMS_IC[current_ic].aux.a_codes[i]*0.0001,4);
1070  Serial.print(",");
1071  }
1072  }
1073  else
1074  {
1075  Serial.print("AUX, ");
1076 
1077  for (int i=0; i < 12; i++)
1078  {
1079  Serial.print(BMS_IC[current_ic].aux.a_codes[i]*0.0001,4);
1080  Serial.print(",");
1081  }
1082  }
1083  }
1084  Serial.println("\n");
1085 }
1086 
1087 /*!****************************************************************************
1088  \brief Prints Status voltage codes for SOC onto the serial port
1089  *****************************************************************************/
1091 {
1092  for (int current_ic =0 ; current_ic < TOTAL_IC; current_ic++)
1093  {
1094  Serial.print(F(" IC "));
1095  Serial.print(current_ic+1,DEC);
1096  Serial.print(F(" SOC:"));
1097  Serial.print(BMS_IC[current_ic].stat.stat_codes[0]*0.0001*30,4);
1098  Serial.print(F(","));
1099  }
1100  Serial.println("\n");
1101 }
1102 
1103 /*!****************************************************************
1104  \brief Function to check the MUX fail bit in the Status Register
1105  @return void
1106 *******************************************************************/
1107 void check_mux_fail(void)
1108 {
1109  int8_t error = 0;
1110  for (int ic = 0; ic<TOTAL_IC; ic++)
1111  {
1112  Serial.print(" IC ");
1113  Serial.println(ic+1,DEC);
1114  if (BMS_IC[ic].stat.mux_fail[0] != 0) error++;
1115 
1116  if (error==0) Serial.println(F("Mux Test: PASS \n"));
1117  else Serial.println(F("Mux Test: FAIL \n"));
1118  }
1119 }
1120 
1121 /*!************************************************************
1122  \brief Prints Errors Detected during self test
1123  @return void
1124 *************************************************************/
1125 void print_selftest_errors(uint8_t adc_reg ,int8_t error)
1126 {
1127  if(adc_reg==1)
1128  {
1129  Serial.println("Cell ");
1130  }
1131  else if(adc_reg==2)
1132  {
1133  Serial.println("Aux ");
1134  }
1135  else if(adc_reg==3)
1136  {
1137  Serial.println("Stat ");
1138  }
1139  Serial.print(error, DEC);
1140  Serial.println(F(" : errors detected in Digital Filter and Memory \n"));
1141 }
1142 
1143 /*!************************************************************
1144  \brief Prints the output of the ADC overlap test
1145  @return void
1146 *************************************************************/
1148 {
1149  if (error==0) Serial.println(F("Overlap Test: PASS \n"));
1150  else Serial.println(F("Overlap Test: FAIL \n"));
1151 }
1152 
1153 /*!************************************************************
1154  \brief Prints Errors Detected during Digital Redundancy test
1155  @return void
1156 *************************************************************/
1157 void print_digital_redundancy_errors(uint8_t adc_reg ,int8_t error)
1158 {
1159  if(adc_reg==2)
1160  {
1161  Serial.println("Aux ");
1162  }
1163  else if(adc_reg==3)
1164  {
1165  Serial.println("Stat ");
1166  }
1167 
1168  Serial.print(error, DEC);
1169  Serial.println(F(" : errors detected in Measurement \n"));
1170 }
1171 
1172 /*!****************************************************************************
1173  \brief Prints Open wire test results to the serial port
1174  *****************************************************************************/
1176 {
1177  for (int current_ic =0 ; current_ic < TOTAL_IC; current_ic++)
1178  {
1179  if (BMS_IC[current_ic].system_open_wire == 65535)
1180  {
1181  Serial.print("No Opens Detected on IC ");
1182  Serial.print(current_ic+1, DEC);
1183  Serial.println();
1184  }
1185  else
1186  {
1187  Serial.print(F("There is an open wire on IC "));
1188  Serial.print(current_ic + 1,DEC);
1189  Serial.print(F(" Channel: "));
1190  Serial.println(BMS_IC[current_ic].system_open_wire);
1191  }
1192  }
1193  Serial.println("\n");
1194 }
1195 
1196 /*!****************************************************************************
1197  \brief Function to print the number of PEC Errors
1198  @return void
1199  *****************************************************************************/
1201 {
1202  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
1203  {
1204  Serial.println("");
1205  Serial.print(BMS_IC[current_ic].crc_count.pec_count,DEC);
1206  Serial.print(F(" : PEC Errors Detected on IC"));
1207  Serial.println(current_ic+1,DEC);
1208  }
1209  Serial.println("\n");
1210 }
1211 
1212 /*!****************************************************
1213  \brief Function to select the S pin for discharge
1214  @return void
1215  ******************************************************/
1216 int8_t select_s_pin(void)
1217 {
1218  int8_t read_s_pin=0;
1219 
1220  Serial.print(F("Please enter the Spin number: "));
1221  read_s_pin = (int8_t)read_int();
1222  Serial.println(read_s_pin);
1223  return(read_s_pin);
1224 }
1225 
1226 /*!****************************************************************************
1227  \brief prints data which is written on PWM register onto the serial port
1228  @return void
1229  *****************************************************************************/
1230 void print_wrpwm(void)
1231 {
1232  int pwm_pec;
1233 
1234  Serial.println(F("Written PWM Configuration: "));
1235  for (uint8_t current_ic = 0; current_ic<TOTAL_IC; current_ic++)
1236  {
1237  Serial.print(F("IC "));
1238  Serial.print(current_ic+1,DEC);
1239  for(int i = 0; i < 6; i++)
1240  {
1241  Serial.print(F(", 0x"));
1242  serial_print_hex(BMS_IC[current_ic].pwm.tx_data[i]);
1243  }
1244  Serial.print(F(", Calculated PEC: 0x"));
1245  pwm_pec = pec15_calc(6,&BMS_IC[current_ic].pwm.tx_data[0]);
1246  serial_print_hex((uint8_t)(pwm_pec>>8));
1247  Serial.print(F(", 0x"));
1248  serial_print_hex((uint8_t)(pwm_pec));
1249  Serial.println("\n");
1250  }
1251 }
1252 
1253 /*!****************************************************************************
1254  \brief Prints received data from PWM register onto the serial port
1255  @return void
1256  *****************************************************************************/
1257 void print_rxpwm(void)
1258 {
1259  Serial.println(F("Received pwm Configuration:"));
1260  for (uint8_t current_ic=0; current_ic<TOTAL_IC; current_ic++)
1261  {
1262  Serial.print(F("IC "));
1263  Serial.print(current_ic+1,DEC);
1264  for(int i = 0; i < 6; i++)
1265  {
1266  Serial.print(F(", 0x"));
1267  serial_print_hex(BMS_IC[current_ic].pwm.rx_data[i]);
1268  }
1269  Serial.print(F(", Received PEC: 0x"));
1270  serial_print_hex(BMS_IC[current_ic].pwm.rx_data[6]);
1271  Serial.print(F(", 0x"));
1272  serial_print_hex(BMS_IC[current_ic].pwm.rx_data[7]);
1273  Serial.println("\n");
1274  }
1275 }
1276 
1277 /*!****************************************************************************
1278  \brief prints data which is written on S Control register
1279  @return void
1280  *****************************************************************************/
1281 void print_wrsctrl(void)
1282 {
1283  int sctrl_pec;
1284 
1285  Serial.println(F("Written Data in Sctrl register: "));
1286  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
1287  {
1288  Serial.print(F(" IC: "));
1289  Serial.print(current_ic+1,DEC);
1290  Serial.print(F(" Sctrl register group:"));
1291  for(int i = 0; i < 6; i++)
1292  {
1293  Serial.print(F(", 0x"));
1294  serial_print_hex(BMS_IC[current_ic].sctrl.tx_data[i]);
1295  }
1296 
1297  Serial.print(F(", Calculated PEC: 0x"));
1298  sctrl_pec = pec15_calc(6,&BMS_IC[current_ic].sctrl.tx_data[0]);
1299  serial_print_hex((uint8_t)(sctrl_pec>>8));
1300  Serial.print(F(", 0x"));
1301  serial_print_hex((uint8_t)(sctrl_pec));
1302  Serial.println("\n");
1303  }
1304 }
1305 
1306 /*!****************************************************************************
1307  \brief prints data which is read back from S Control register
1308  @return void
1309  *****************************************************************************/
1310 void print_rxsctrl(void)
1311 {
1312  Serial.println(F("Received Data:"));
1313  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
1314  {
1315  Serial.print(F(" IC "));
1316  Serial.print(current_ic+1,DEC);
1317 
1318  for(int i = 0; i < 6; i++)
1319  {
1320  Serial.print(F(", 0x"));
1321  serial_print_hex(BMS_IC[current_ic].sctrl.rx_data[i]);
1322  }
1323 
1324  Serial.print(F(", Received PEC: 0x"));
1325  serial_print_hex(BMS_IC[current_ic].sctrl.rx_data[6]);
1326  Serial.print(F(", 0x"));
1327  serial_print_hex(BMS_IC[current_ic].sctrl.rx_data[7]);
1328  Serial.println("\n");
1329  }
1330 }
1331 
1332 /*!****************************************************************************
1333  \brief Prints data which is written on PWM/S control register group B onto
1334  the serial port
1335  @return void
1336  *****************************************************************************/
1337 void print_wrpsb(uint8_t type)
1338 {
1339  int psb_pec=0;
1340 
1341  Serial.println(F(" PWM/S control register group B: "));
1342  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
1343  {
1344  if(type == 1)
1345  {
1346  Serial.print(F(" IC: "));
1347  Serial.println(current_ic+1,DEC);
1348  Serial.print(F(" 0x"));
1349  serial_print_hex(BMS_IC[current_ic].pwmb.tx_data[0]);
1350  Serial.print(F(", 0x"));
1351  serial_print_hex(BMS_IC[current_ic].pwmb.tx_data[1]);
1352  Serial.print(F(", 0x"));
1353  serial_print_hex(BMS_IC[current_ic].pwmb.tx_data[2]);
1354 
1355  Serial.print(F(", Calculated PEC: 0x"));
1356  psb_pec = pec15_calc(6,&BMS_IC[current_ic].pwmb.tx_data[0]);
1357  serial_print_hex((uint8_t)(psb_pec>>8));
1358  Serial.print(F(", 0x"));
1359  serial_print_hex((uint8_t)(psb_pec));
1360  Serial.println("\n");
1361  }
1362  else if(type == 2)
1363  {
1364  Serial.print(F(" IC: "));
1365  Serial.println(current_ic+1,DEC);
1366  Serial.print(F(" 0x"));
1367  serial_print_hex(BMS_IC[current_ic].sctrlb.tx_data[3]);
1368  Serial.print(F(", 0x"));
1369  serial_print_hex(BMS_IC[current_ic].sctrlb.tx_data[4]);
1370  Serial.print(F(", 0x"));
1371  serial_print_hex(BMS_IC[current_ic].sctrlb.tx_data[5]);
1372 
1373  Serial.print(F(", Calculated PEC: 0x"));
1374  psb_pec = pec15_calc(6,&BMS_IC[current_ic].sctrlb.tx_data[0]);
1375  serial_print_hex((uint8_t)(psb_pec>>8));
1376  Serial.print(F(", 0x"));
1377  serial_print_hex((uint8_t)(psb_pec));
1378  Serial.println("\n");
1379  }
1380  }
1381 }
1382 
1383 
1384 /*!****************************************************************************
1385  \brief Prints received data from PWM/S control register group B
1386  onto the serial port
1387  @return void
1388  *****************************************************************************/
1389 void print_rxpsb(uint8_t type)
1390 {
1391  Serial.println(F(" PWM/S control register group B:"));
1392  if(type == 1)
1393  {
1394  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
1395  {
1396  Serial.print(F(" IC: "));
1397  Serial.println(current_ic+1,DEC);
1398  Serial.print(F(" 0x"));
1399  serial_print_hex(BMS_IC[current_ic].pwmb.rx_data[0]);
1400  Serial.print(F(", 0x"));
1401  serial_print_hex(BMS_IC[current_ic].pwmb.rx_data[1]);
1402  Serial.print(F(", 0x"));
1403  serial_print_hex(BMS_IC[current_ic].pwmb.rx_data[2]);
1404 
1405  Serial.print(F(", Received PEC: 0x"));
1406  serial_print_hex(BMS_IC[current_ic].pwmb.rx_data[6]);
1407  Serial.print(F(", 0x"));
1408  serial_print_hex(BMS_IC[current_ic].pwmb.rx_data[7]);
1409  Serial.println("\n");
1410  }
1411  }
1412  else if(type == 2)
1413  {
1414  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
1415  {
1416  Serial.print(F(" IC: "));
1417  Serial.println(current_ic+1,DEC);
1418  Serial.print(F(" 0x"));
1419  serial_print_hex(BMS_IC[current_ic].sctrlb.rx_data[3]);
1420  Serial.print(F(", 0x"));
1421  serial_print_hex(BMS_IC[current_ic].sctrlb.rx_data[4]);
1422  Serial.print(F(", 0x"));
1423  serial_print_hex(BMS_IC[current_ic].sctrlb.rx_data[5]);
1424 
1425  Serial.print(F(", Received PEC: 0x"));
1426  serial_print_hex(BMS_IC[current_ic].sctrlb.rx_data[6]);
1427  Serial.print(F(", 0x"));
1428  serial_print_hex(BMS_IC[current_ic].sctrlb.rx_data[7]);
1429  Serial.println("\n");
1430  }
1431  }
1432 }
1433 
1434 /*!****************************************************************************
1435  \brief prints data which is written on COMM register onto the serial port
1436  @return void
1437  *****************************************************************************/
1438 void print_wrcomm(void)
1439 {
1440  int comm_pec;
1441 
1442  Serial.println(F("Written Data in COMM Register: "));
1443  for (int current_ic = 0; current_ic<TOTAL_IC; current_ic++)
1444  {
1445  Serial.print(F(" IC- "));
1446  Serial.print(current_ic+1,DEC);
1447 
1448  for(int i = 0; i < 6; i++)
1449  {
1450  Serial.print(F(", 0x"));
1451  serial_print_hex(BMS_IC[current_ic].com.tx_data[i]);
1452  }
1453  Serial.print(F(", Calculated PEC: 0x"));
1454  comm_pec = pec15_calc(6,&BMS_IC[current_ic].com.tx_data[0]);
1455  serial_print_hex((uint8_t)(comm_pec>>8));
1456  Serial.print(F(", 0x"));
1457  serial_print_hex((uint8_t)(comm_pec));
1458  Serial.println("\n");
1459  }
1460 }
1461 
1462 /*!****************************************************************************
1463  \brief Prints received data from COMM register onto the serial port
1464  @return void
1465  *****************************************************************************/
1466 void print_rxcomm(void)
1467 {
1468  Serial.println(F("Received Data in COMM register:"));
1469  for (int current_ic=0; current_ic<TOTAL_IC; current_ic++)
1470  {
1471  Serial.print(F(" IC- "));
1472  Serial.print(current_ic+1,DEC);
1473 
1474  for(int i = 0; i < 6; i++)
1475  {
1476  Serial.print(F(", 0x"));
1477  serial_print_hex(BMS_IC[current_ic].com.rx_data[i]);
1478  }
1479  Serial.print(F(", Received PEC: 0x"));
1480  serial_print_hex(BMS_IC[current_ic].com.rx_data[6]);
1481  Serial.print(F(", 0x"));
1482  serial_print_hex(BMS_IC[current_ic].com.rx_data[7]);
1483  Serial.println("\n");
1484  }
1485 }
1486 
1487 /*!********************************************************************
1488  \brief Function to check the Mute bit in the Configuration Register
1489  @return void
1490 **********************************************************************/
1491 void check_mute_bit(void)
1492 {
1493  for (int current_ic = 0 ; current_ic < TOTAL_IC; current_ic++)
1494  {
1495  Serial.print(F(" Mute bit in Configuration Register B: 0x"));
1496  serial_print_hex((BMS_IC[current_ic].configb.rx_data[1])&(0x80));
1497  Serial.println("\n");
1498  }
1499 }
1500 
1501 /*!****************************************************************************
1502  \brief Function to print the Conversion Time
1503  @return void
1504  *****************************************************************************/
1505 void print_conv_time(uint32_t conv_time)
1506 {
1507  uint16_t m_factor=1000; // to print in ms
1508 
1509  Serial.print(F("Conversion completed in:"));
1510  Serial.print(((float)conv_time/m_factor), 1);
1511  Serial.println(F("ms \n"));
1512 }
1513 
1514 /*!****************************************************************************
1515  \brief Function to check error flag and print PEC error message
1516  @return void
1517  *****************************************************************************/
1519 {
1520  if (error == -1)
1521  {
1522  Serial.println(F("A PEC error was detected in the received data"));
1523  }
1524 }
1525 
1526 /*!************************************************************
1527  \brief Function to print text on serial monitor
1528  @return void
1529 *************************************************************/
1531 {
1532  Serial.println(data);
1533 }
1534 
1535 /*!****************************************************************************
1536  \brief Function to print in HEX form
1537  @return void
1538  *****************************************************************************/
1539 void serial_print_hex(uint8_t data)
1540 {
1541  if (data< 16)
1542  {
1543  Serial.print("0");
1544  Serial.print((byte)data,HEX);
1545  }
1546  else
1547  Serial.print((byte)data,HEX);
1548 }
1549 
1550 /*!*****************************************************************************
1551  \brief Hex conversion constants
1552  *******************************************************************************/
1553 char hex_digits[16]=
1554 {
1555  '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'
1556 };
1557 
1558 /*!************************************************************
1559  \brief Global Variables
1560  *************************************************************/
1562 {
1563  '0', 'x', '0', '0', '\0'
1564 };
1565 
1566 /*!************************************************************
1567  \brief Buffer for ASCII hex to byte conversion
1568  *************************************************************/
1570 {
1571  '\0','\0','\0'
1572 };
1573 
1574 /*!*****************************************************************************
1575  \brief Read 2 hex characters from the serial buffer and convert them to a byte
1576  @return char data Read Data
1577  ******************************************************************************/
1578 char read_hex(void)
1579 {
1580  byte data;
1583  get_char();
1584  get_char();
1585  data = strtol(hex_to_byte_buffer, NULL, 0);
1586  return(data);
1587 }
1588 
1589 /*!************************************************************
1590  \brief Read a command from the serial port
1591  @return char
1592  *************************************************************/
1593 char get_char(void)
1594 {
1595  // read a command from the serial port
1596  while (Serial.available() <= 0);
1597  return(Serial.read());
1598 }
int8_t LTC6813_rdaux(uint8_t reg, uint8_t total_ic, cell_asic *ic)
Reads and parses the LTC6813 auxiliary registers.
Definition: LTC6813.cpp:183
int16_t LTC6813_run_adc_redundancy_st(uint8_t adc_mode, uint8_t adc_reg, uint8_t total_ic, cell_asic *ic)
Helper function that runs the ADC Digital Redundancy commands and checks output for errors...
Definition: LTC6813.cpp:353
ic_register sctrl
Definition: LTC681x.h:180
const uint8_t READ_CONFIG
This is to ENABLED or DISABLED reading the configuration registers in a continuous loop...
Definition: DC2350AB.ino:151
static void print_wrsctrl(void)
Definition: DC2350AB.ino:1281
const uint8_t MEASURE_AUX
This is to ENABLED or DISABLED reading the auxiliary registers in a continuous loop.
Definition: DC2350AB.ino:153
uint32_t LTC6813_pollAdc()
This function will block operation until the ADC has finished it&#39;s conversion.
Definition: LTC6813.cpp:216
General BMS Library.
bool DCCBITS_A[12]
Discharge cell switch //Dcc 1,2,3,4,5,6,7,8,9,10,11,12.
Definition: DC2350AB.ino:177
const uint8_t PRINT_PEC
This is to ENABLED or DISABLED printing the PEC Error Count in a continuous loop. ...
Definition: DC2350AB.ino:155
void LTC6813_wrpsb(uint8_t total_ic, cell_asic *ic)
Write the 6813 PWM/Sctrl Register B.
Definition: LTC6813.cpp:507
cell_asic BMS_IC[TOTAL_IC]
Global Battery Variable.
Definition: DC2350AB.ino:166
const uint8_t SEL_REG_A
Register Selection.
Definition: DC2350AB.ino:140
void wakeup_sleep()
Definition: LTC68041.cpp:969
unsigned char user_command
uint8_t tx_data[6]
Stores data to be transmitted.
Definition: LTC681x.h:143
#define CELL_CH_ALL
CH Dec Channels to convert 0000 All Cells 0011 Cell 1 and Cell 7 0102 Cell 2 and Cell 8 0113 Cell 3 ...
Definition: LTC68041.h:142
bool PSBITS[2]
Digital Redundancy Path Selection//ps-0,1.
Definition: DC2350AB.ino:183
const uint8_t WRITE_CONFIG
This is to ENABLED or DISABLED writing into to configuration registers in a continuous loop...
Definition: DC2350AB.ino:150
static void serial_print_hex(uint8_t data)
Definition: DC2350AB.ino:1539
const uint8_t TOTAL_IC
Number of ICs in the daisy chain.
Definition: DC2350AB.ino:128
const uint8_t ADC_CONVERSION_MODE
ADC Mode.
Definition: DC2350AB.ino:134
char hex_digits[16]
Definition: DC2350AB.ino:1553
void LTC6813_adcvsc(uint8_t MD, uint8_t DCP)
Starts cell voltage and Sum of cells conversion.
Definition: LTC6813.cpp:160
ic_register sctrlb
Definition: LTC681x.h:181
#define SCTL
Definition: DC2350AB.ino:87
static void check_mute_bit(void)
Definition: DC2350AB.ino:1491
const uint8_t ADC_OPT
ADC Mode option bit.
Definition: DC2350AB.ino:133
#define ENABLED
Definition: DC2350AB.ino:82
#define AUX
Definition: LTC6810.h:63
static void print_aux1(uint8_t datalog_en)
Definition: DC2350AB.ino:1055
static void check_mux_fail(void)
Definition: DC2350AB.ino:1107
Header File for Linduino Libraries and Demo Code.
void LTC6813_init_cfgb(uint8_t total_ic, cell_asic *ic)
Helper Function to initialize the CFGR B data structures.
Definition: LTC6813.cpp:707
Cell variable structure.
Definition: LTC681x.h:170
void LTC6813_init_reg_limits(uint8_t total_ic, cell_asic *ic)
Helper function to initialize register limits.
Definition: LTC6813.cpp:67
static void print_rxconfig(void)
Definition: DC2350AB.ino:875
void LTC6813_wrsctrl(uint8_t total_ic, uint8_t sctrl_reg, cell_asic *ic)
Write the LTC6813 Sctrl register.
Definition: LTC6813.cpp:470
#define STAT_CH_ALL
Definition: LTC681x.h:88
#define AUX_CH_ALL
CHG Dec Channels to convert 000 0 All GPIOS and 2nd Ref 001 1 GPIO 1 010 2 GPIO 2 011 3 GPIO 3 100 4...
Definition: LTC68041.h:164
#define DISABLED
Definition: DC2350AB.ino:83
#define CELL
Definition: LTC6810.h:62
#define DATALOG_DISABLED
Definition: DC2350AB.ino:85
bool ADCOPT
ADC Mode option bit.
Definition: DC2350AB.ino:172
void LTC6813_set_discharge(int Cell, uint8_t total_ic, cell_asic *ic)
Helper Function to Set DCC bits in the CFGR Registers.
Definition: LTC6813.cpp:407
const uint8_t SEL_ALL_REG
Register Selection.
Definition: DC2350AB.ino:139
register_cfg ic_reg
Definition: LTC681x.h:185
void spi_enable(uint8_t spi_clock_divider)
Setup the processor for hardware SPI communication.
Definition: LT_SPI.cpp:160
void LTC6813_run_openwire_single(uint8_t total_ic, cell_asic *ic)
Helper function that runs the data sheet algorithm for open wire for single cell detection.
Definition: LTC6813.cpp:383
ic_register com
Definition: LTC681x.h:177
char hex_to_byte_buffer[5]
Definition: DC2350AB.ino:1561
void LTC6813_adcvax(uint8_t MD, uint8_t DCP)
Starts cell voltage and GPIO 1 & 2 conversion.
Definition: LTC6813.cpp:152
void LTC6813_adcv(uint8_t MD, uint8_t DCP, uint8_t CH)
Starts cell voltage conversion.
Definition: LTC6813.cpp:127
static void print_sumofcells(void)
Definition: DC2350AB.ino:1090
const uint16_t UV_THRESHOLD
Under voltage threshold ADC Code.
Definition: DC2350AB.ino:147
void LTC6813_adstat(uint8_t MD, uint8_t CHST)
Start a Status ADC Conversion.
Definition: LTC6813.cpp:144
char get_char(void)
Definition: DC2350AB.ino:1593
void LTC6813_set_cfgr(uint8_t nIC, cell_asic *ic, bool refon, bool adcopt, bool gpio[5], bool dcc[12], bool dcto[4], uint16_t uv, uint16_t ov)
Helper function to set appropriate bits in CFGR register based on bit function.
Definition: LTC6813.cpp:653
int8_t LTC6813_rdcfg(uint8_t total_ic, cell_asic *ic)
Reads configuration register A of a LTC6813 daisy chain.
Definition: LTC6813.cpp:107
const uint16_t OV_THRESHOLD
Over voltage threshold ADC Code.
Definition: DC2350AB.ino:146
const uint16_t MEASUREMENT_LOOP_TIME
Loop Time in milliseconds(ms)
Definition: DC2350AB.ino:143
static uint16_t UV
Under voltage Comparison Voltage.
Definition: DC2350AB.ino:175
void LTC6813_adax(uint8_t MD, uint8_t CHG)
Start a GPIO and Vref2 Conversion.
Definition: LTC6813.cpp:136
static void print_rxconfigb(void)
Definition: DC2350AB.ino:900
union LT_union_int32_4bytes data
Definition: DC2094A.ino:138
static void print_rxpwm(void)
Definition: DC2350AB.ino:1257
void LTC6813_clrstat()
Clears the LTC6813 Stat registers.
Definition: LTC6813.cpp:246
#define STAT
Definition: LTC6810.h:64
uint8_t LTC6813_rdcv(uint8_t reg, uint8_t total_ic, cell_asic *ic)
Reads and parses the LTC6813 cell voltage registers.
Definition: LTC6813.cpp:168
bool GPIOBITS_A[5]
GPIO Pin Control // Gpio 1,2,3,4,5.
Definition: DC2350AB.ino:173
bool DTMEN
Enable Discharge Timer Monitor.
Definition: DC2350AB.ino:182
static void serial_print_text(char data[])
Definition: DC2350AB.ino:1530
uint8_t LTC6813_rdpsb(uint8_t total_ic, cell_asic *ic)
Reading pwm/s control register B.
Definition: LTC6813.cpp:533
static void print_wrcomm(void)
Definition: DC2350AB.ino:1438
void LTC6813_stcomm(uint8_t len)
Issues a stcomm command and clocks data out of the COMM register.
Definition: LTC6813.cpp:604
static void check_error(int error)
Definition: DC2350AB.ino:1518
static uint16_t OV
Over voltage Comparison Voltage.
Definition: DC2350AB.ino:176
static void run_command(uint32_t cmd)
Definition: DC2350AB.ino:232
static void measurement_loop(uint8_t datalog_en)
Definition: DC2350AB.ino:718
#define ADC_OPT_DISABLED
Definition: LTC681x.h:67
static void print_overlap_results(int8_t error)
Definition: DC2350AB.ino:1147
void LTC6813_mute()
Mutes the LTC6813 discharge transistors.
Definition: LTC6813.cpp:610
void LTC6813_wrcfg(uint8_t total_ic, cell_asic *ic)
Write the LTC6813 configuration register A.
Definition: LTC6813.cpp:87
static void loop()
Definition: DC2350AB.ino:210
ic_register pwm
Definition: LTC681x.h:178
static void print_conv_time(uint32_t conv_time)
Definition: DC2350AB.ino:1505
const uint8_t STAT_CH_TO_CONVERT
Channel Selection for ADC conversion.
Definition: DC2350AB.ino:138
void wakeup_idle()
Definition: LTC68041.cpp:957
#define REG_ALL
Definition: LTC681x.h:94
static void print_wrpwm(void)
Definition: DC2350AB.ino:1230
const uint8_t CELL_CH_TO_CONVERT
Channel Selection for ADC conversion.
Definition: DC2350AB.ino:136
#define REG_2
Definition: LTC681x.h:96
#define input(pin)
Return the state of pin "pin".
Definition: Linduino.h:79
static void print_pec_error_count(void)
Definition: DC2350AB.ino:1200
uint8_t cell_channels
Number of Cell channels.
Definition: LTC681x.h:161
static int error
static void print_cells(uint8_t datalog_en)
Definition: DC2350AB.ino:924
uint16_t LTC6813_run_adc_overlap(uint8_t total_ic, cell_asic *ic)
Helper Function that runs the ADC Overlap test.
Definition: LTC6813.cpp:319
bool FDRF
Force Digital Redundancy Failure Bit.
Definition: DC2350AB.ino:181
bool GPIOBITS_B[4]
GPIO Pin Control // Gpio 6,7,8,9.
Definition: DC2350AB.ino:174
uint16_t pec15_calc(uint8_t len, uint8_t *data)
Definition: LTC68041.cpp:985
void LTC6813_clraux()
Clears the LTC6813 Auxiliary registers.
Definition: LTC6813.cpp:236
void LTC6813_reset_crc_count(uint8_t total_ic, cell_asic *ic)
Helper Function that resets the PEC error counters.
Definition: LTC6813.cpp:639
const uint8_t MEASURE_CELL
This is to ENABLED or DISABLED measuring the cell voltages in a continuous loop.
Definition: DC2350AB.ino:152
static void print_stat(void)
Definition: DC2350AB.ino:1012
static void print_wrconfigb(void)
Definition: DC2350AB.ino:848
LT_SPI: Routines to communicate with ATmega328P&#39;s hardware SPI port.
void LTC6813_clrsctrl()
Clears the LTC6813 Sctrl registers.
Definition: LTC6813.cpp:501
static void print_open_wires(void)
Definition: DC2350AB.ino:1175
#define DATALOG_ENABLED
Definition: DC2350AB.ino:84
static void print_menu(void)
Definition: DC2350AB.ino:798
int8_t LTC6813_rdcfgb(uint8_t total_ic, cell_asic *ic)
Reads configuration register B of a LTC6813 daisy chain.
Definition: LTC6813.cpp:117
void LTC6813_clrcell()
Clears the LTC6813 cell voltage registers.
Definition: LTC6813.cpp:226
void LTC6813_set_cfgrb(uint8_t nIC, cell_asic *ic, bool fdrf, bool dtmen, bool ps[2], bool gpiobits[4], bool dccbits[7])
Helper function to set appropriate bits in CFGR register based on bit function.
Definition: LTC6813.cpp:719
int8_t LTC6813_rdstat(uint8_t reg, uint8_t total_ic, cell_asic *ic)
Reads and parses the LTC6813 stat registers.
Definition: LTC6813.cpp:199
const uint8_t AUX_CH_TO_CONVERT
Channel Selection for ADC conversion.
Definition: DC2350AB.ino:137
void LTC6813_wrcomm(uint8_t total_ic, cell_asic *ic)
Write the LTC6813 COMM register.
Definition: LTC6813.cpp:586
int8_t LTC6813_rdsctrl(uint8_t total_ic, uint8_t sctrl_reg, cell_asic *ic)
Reads sctrl registers of a LTC6813 daisy chain.
Definition: LTC6813.cpp:479
#define MD_7KHZ_3KHZ
Definition: LTC681x.h:63
static void print_digital_redundancy_errors(uint8_t adc_reg, int8_t error)
Definition: DC2350AB.ino:1157
static void print_selftest_errors(uint8_t adc_reg, int8_t error)
Definition: DC2350AB.ino:1125
bool DCCBITS_B[7]
Discharge cell switch //Dcc 0,13,14,15.
Definition: DC2350AB.ino:178
void LTC6813_wrcfgb(uint8_t total_ic, cell_asic *ic)
Write the LTC6813 configuration register B.
Definition: LTC6813.cpp:99
void quikeval_SPI_connect()
Connect SPI pins to QuikEval connector through the Linduino MUX. This will disconnect I2C...
Definition: LT_SPI.cpp:138
const uint8_t MEASURE_STAT
This is to ENABLED or DISABLED reading the status registers in a continuous loop. ...
Definition: DC2350AB.ino:154
#define REG_1
Definition: LTC681x.h:95
int32_t read_int()
void LTC6813_stsctrl()
Start Sctrl data communication This command will start the sctrl pulse communication over the spins...
Definition: LTC6813.cpp:491
void LTC6813_init_cfg(uint8_t total_ic, cell_asic *ic)
Helper Function to initialize the CFGR data structures.
Definition: LTC6813.cpp:647
LTC6813: Multicell Battery Monitors.
static int8_t select_s_pin(void)
Definition: DC2350AB.ino:1216
static void print_rxpsb(uint8_t type)
Definition: DC2350AB.ino:1389
#define DCP_DISABLED
Definition: LTC68041.h:183
void LTC6813_unmute()
Clears the LTC6813 Mute Discharge.
Definition: LTC6813.cpp:620
int8_t LTC6813_rdpwm(uint8_t total_ic, uint8_t pwmReg, cell_asic *ic)
Reads pwm registers of a LTC6813 daisy chain.
Definition: LTC6813.cpp:459
char byte_to_hex_buffer[3]
Definition: DC2350AB.ino:1569
static void print_wrconfig(void)
Definition: DC2350AB.ino:821
static void print_aux(uint8_t datalog_en)
Definition: DC2350AB.ino:960
static void setup()
Definition: DC2350AB.ino:189
static int i
Definition: DC2430A.ino:184
static void print_wrpsb(uint8_t type)
Definition: DC2350AB.ino:1337
int16_t LTC6813_run_cell_adc_st(uint8_t adc_reg, uint8_t total_ic, cell_asic *ic, uint8_t md, bool adcopt)
Helper function that runs the ADC Self Tests.
Definition: LTC6813.cpp:306
static void print_rxsctrl(void)
Definition: DC2350AB.ino:1310
bool REFON
Reference Powered Up Bit.
Definition: DC2350AB.ino:171
const uint8_t ADC_DCP
Discharge Permitted.
Definition: DC2350AB.ino:135
int8_t LTC6813_rdcomm(uint8_t total_ic, cell_asic *ic)
Reads comm registers of a LTC6813 daisy chain.
Definition: LTC6813.cpp:594
static void print_rxcomm(void)
Definition: DC2350AB.ino:1466
int8_t read_char()
bool DCTOBITS[4]
Discharge time value //Dcto 0,1,2,3 // Programed for 4 min.
Definition: DC2350AB.ino:179
ic_register pwmb
Definition: LTC681x.h:179
const uint8_t SEL_REG_B
Register Selection.
Definition: DC2350AB.ino:141
#define PWM
Definition: DC2350AB.ino:86
char read_hex(void)
Definition: DC2350AB.ino:1578
void LTC6813_clear_discharge(uint8_t total_ic, cell_asic *ic)
Helper Function to clear DCC bits in the CFGR Registers.
Definition: LTC6813.cpp:442
void LTC6813_run_openwire_multi(uint8_t total_ic, cell_asic *ic)
Helper function that runs open wire for multiple cell and two consecutive cells detection.
Definition: LTC6813.cpp:391
void LTC6813_wrpwm(uint8_t total_ic, uint8_t pwmReg, cell_asic *ic)
Write the LTC6813 PWM register.
Definition: LTC6813.cpp:450
void LTC6813_diagn()
Starts the Mux Decoder diagnostic self test Running this command will start the Mux Decoder Diagnosti...
Definition: LTC6813.cpp:252
void LTC6813_run_gpio_openwire(uint8_t total_ic, cell_asic *ic)
Runs open wire for GPIOs.
Definition: LTC6813.cpp:399