hi

Dependencies:   CANMsg

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 #include "mbed.h"
00002 #include "canIds.h"
00003 #include <stdlib.h>
00004 #include <stdint.h>
00005 #include <stdio.h>
00006 
00007 #define BOARD1          // Comment this for one board, BOARD1 sends
00008 
00009 #define CHAR16                      3
00010 #define CHAR32                      5
00011 #define NUM_VOLTAGE_READINGS        31
00012 #define NUM_TEMP_READINGS           62
00013 
00014 
00015 #define MPPT_BASE_R     0x710 // MPPT Base ID (Request)
00016 #define MPPT_BASE_A     0x770 // MPPT Base ID (Answer)
00017 #define MPPT_OFF        0xF //MPPT Offset ID (set by DIP switch on board)
00018  
00019 Serial          pc(USBTX, USBRX);
00020 CAN             can(PA_11, PA_12);       // L432KC
00021 // CAN             can(PD_0, PD_1);            // 429ZI
00022 DigitalOut      led(LED1);
00023 CANMessage      msg;
00024  
00025  
00026 // Array Temperatures
00027 AnalogIn Vtemp1(PA_3); // RTD temperature sensor (pin A2)
00028 AnalogIn Vtemp2(PA_4); // RTD temperature sensor (pin A3)
00029 double tempmeas1;
00030 double tempmeas2;
00031 double avgval;
00032 double n;
00033 double tempoff1 = -1.8; // Offset in deg C to calibrate RTD 1
00034 double tempoff2 = -1.8; // Offset in deg C to calibrate RTD 2
00035 double slope1 = 1.25; // Slope correction to RTD
00036 double slope2 = 1.25; // Slope correction to RTD
00037 
00038 int counter = 0;
00039 #ifdef BOARD1
00040     int CanID = 0x0000001;
00041 #else
00042     int CanID = 0x0000002;
00043 #endif
00044  
00045 // https://stackoverflow.com/questions/24420246/c-function-to-convert-float-to-byte-array
00046 // Receives temperatures from the array
00047 void receiveArrayTemp(){
00048     // Temperature Measure 1
00049     avgval = 0.0;
00050     n=0;
00051     while(n<100){
00052         tempmeas1 = Vtemp1.read()*3.3;
00053         avgval=avgval+tempmeas1;
00054         n++;
00055     }
00056     tempmeas1 = tempoff1 + slope1*(avgval/100.0)*150.0/2.92;
00057     
00058     // Temperature Measure 2
00059     avgval = 0.0;
00060     n=0;
00061     while(n<100){
00062         tempmeas2 = Vtemp2.read()*3.3;
00063         avgval=avgval+tempmeas2;
00064         n++;
00065     }
00066     tempmeas2 = tempoff2 + slope2*(avgval/100.0)*150.0/2.92;
00067 }
00068 
00069 void float2Bytes(float val,uint8_t* bytes_array){
00070     uint8_t temp;
00071     // Create union of shared memory space
00072     union {
00073         float float_variable;
00074         uint8_t temp_array[4];
00075     } u;
00076     // Overite bytes of union with float variable
00077     u.float_variable = val;
00078     // Assign bytes to input array
00079     memcpy(bytes_array, u.temp_array, 4);
00080     temp = bytes_array[3];
00081     bytes_array[3] = bytes_array[0];
00082     bytes_array[0] = temp;
00083     temp = bytes_array[2];
00084     bytes_array[2] = bytes_array[1];
00085     bytes_array[1] = temp;
00086 }
00087 
00088 float bytes2Float(uint8_t* bytes_array) {
00089     union {
00090         float f;
00091         uint8_t b[4];
00092     } u;
00093     u.b[3] = bytes_array[0];
00094     u.b[2] = bytes_array[1];
00095     u.b[1] = bytes_array[2];
00096     u.b[0] = bytes_array[3];
00097     return u.f;
00098 } 
00099  
00100 // TODO: use snprintf to convert int, uint16_t stuff into char array for can message
00101 // sprintf(&voltagesChar[6*i], "%d", voltages[i]); 
00102 void generateValues() {
00103     // state of charge (SOC)
00104     //uint32_t socData = (rand() % (100 - 0 + 1)) + 0;
00105     float socData = (rand() % (100000 - 0 + 1)) + 0;
00106     socData = socData / 1000.0;
00107     uint8_t socDataBytes[4];                 // TODO: make separate ones once we thread
00108     float2Bytes(socData, &socDataBytes[0]);
00109     if(can.write(CANMessage(SOC_DATA, (char*)(socDataBytes), 4))) {
00110         pc.printf("Sent SOC_DATA: %f\n", socData);    
00111     } else {
00112         printf("Cannot write to CAN\n");
00113         NVIC_SystemReset();
00114     }
00115     
00116 //    // current data, 50-60A (while moving) fixed point, 32 bits
00117 //    // num = (rand() % (upper - lower + 1)) + lower
00118     float currentData = (rand() % (60000 - 50000 + 1)) + 50000;
00119     currentData = currentData / 1000.0;
00120     uint8_t bytes[4];
00121     float2Bytes(currentData, &bytes[0]);
00122     
00123     if(can.write(CANMessage(CURRENT_DATA, (char*)(bytes), 4))) {
00124         pc.printf("Sent CURRENT_DATA: %f\n", currentData);    
00125     } else {
00126         pc.printf("Cannot write to CAN\n");
00127         NVIC_SystemReset();
00128     }
00129     
00130     // voltage data, fixed point 2.7-4V
00131     // 16 bit
00132     float voltages[NUM_VOLTAGE_READINGS];
00133     for (int i = 0; i < NUM_VOLTAGE_READINGS; i++) {
00134         float voltageData = (rand() % (40000 - 27000 + 1)) + 27000;   
00135         voltageData = voltageData / 1000.0;
00136         //uint8_t bytes[4];
00137         float2Bytes(voltageData, &bytes[0]);
00138         
00139         uint8_t data[5];
00140         data[0] = i;
00141         data[1] = bytes[0];
00142         data[2] = bytes[1];
00143         data[3] = bytes[2];
00144         data[4] = bytes[3];
00145         if(can.write(CANMessage(VOLTAGE_DATA, (char*)(data), 5))) {
00146             pc.printf("Sent VOLTAGE_DATA: %f\n", voltageData); 
00147         } else {
00148             printf("Cannot write to CAN\n");
00149             NVIC_SystemReset();
00150         }
00151         wait(0.1);
00152     }
00153     
00154     // temperature data, 0-100C fixed point res 0.01
00155     // 16 bit
00156     float temperatures[NUM_TEMP_READINGS];
00157     
00158     for (int i = 0; i < NUM_TEMP_READINGS; i++) {
00159         float tempData = (rand() % (73000 - 0 + 1)) + 0;
00160         tempData = tempData / 1000.0;
00161         float2Bytes(tempData, &bytes[0]);
00162         
00163         uint8_t data[5];
00164         data[0] = i;
00165         data[1] = bytes[0];
00166         data[2] = bytes[1];
00167         data[3] = bytes[2];
00168         data[4] = bytes[3];
00169         
00170         if(can.write(CANMessage(TEMPERATURE_DATA, (char*)(data), 5))) {
00171             pc.printf("Sent TEMP_DATA: %f\n", tempData);
00172         } else {
00173             printf("Cannot write to CAN\n");
00174             NVIC_SystemReset();
00175         }
00176         wait(0.1);
00177     }
00178     
00179     // TODO: if these flags are not at the bottom of the function, it will skip values. figure this out.
00180     // bps trip always 0
00181     uint8_t bpsTrip = 0;
00182     if(can.write(CANMessage(BPS_TRIP, (char*)&bpsTrip, 1))) {
00183         pc.printf("Sent BPS_TRIP: %d\n", bpsTrip);    
00184     } else {
00185         printf("Cannot write to CAN\n");
00186         NVIC_SystemReset();
00187     }
00188     
00189     // bps all clear always 1
00190     uint8_t bpsClear = 1;
00191     if(can.write(CANMessage(BPS_ALL_CLEAR, (char*)&bpsClear, 1))) {
00192         pc.printf("Sent BPS_CLEAR: %d\n", bpsClear);    
00193     } else {
00194         printf("Cannot write to CAN\n");
00195         NVIC_SystemReset();
00196     }
00197     
00198     // bps off always 0
00199     uint8_t bpsOff = 0;
00200     if(can.write(CANMessage(BPS_OFF, (char*)&bpsOff, 1))) {
00201         pc.printf("Sent BPS_OFF: %d\n", bpsOff);    
00202     } else {
00203         printf("Cannot write to CAN\n");
00204         NVIC_SystemReset();
00205     }
00206     
00207     // watchdog triggered, 0 always
00208     uint8_t wdog = 0;
00209     if(can.write(CANMessage(WDOG_TRIGGERED, (char*)&wdog, 1))) {
00210         pc.printf("Sent WDOG_TRIGGERED: %d\n", wdog);    
00211     } else {
00212         printf("Cannot write to CAN\n");
00213         NVIC_SystemReset();
00214     }
00215     
00216     // TODO: can error, bps command message?
00217     //wait(1.0);
00218     // Send array temepratures
00219     receiveArrayTemp();
00220 //    uint8_t arrayTemp1 = 0;
00221 //    uint8_t arrayTemp2 = 0;
00222 //    
00223 //    double tempmeas1;
00224 //    double tempmeas2;
00225     float2Bytes((float) tempmeas1, &bytes[0]);
00226     if(can.write(CANMessage(ARRAY_TEMP_1,(char*)&tempmeas1, 4))) {
00227         pc.printf("Sent ARRAY_TEMP_1: %.1f\n", tempmeas1);    
00228     } else {
00229         printf("Cannot write to CAN\n");
00230         NVIC_SystemReset();
00231     }
00232     
00233     float2Bytes((float) tempmeas2, &bytes[0]);
00234     if(can.write(CANMessage(ARRAY_TEMP_2,(char*)&tempmeas2, 4))) {
00235         pc.printf("Sent ARRAY_TEMP_2: %.1f\n", tempmeas2);    
00236     } else {
00237         printf("Cannot write to CAN\n");
00238         NVIC_SystemReset();
00239     }
00240 } 
00241 
00242 float receiveCan(void) {
00243     uint32_t received;
00244     /*
00245     int cansuccess = 0;
00246     float data[2];
00247     data[1] = 0.0;
00248     int id = MPPT_BASE_R + MPPT_OFF;
00249  
00250     if (!can.write(CANMessage(id, (char*)data, 8)))
00251         printf("Request to MPPT failed \n\r");
00252     */
00253     if (can.read(msg)) {
00254         received = *((uint32_t*) msg.data);
00255     } else {
00256         return -1;
00257     } 
00258     pc.printf("-----------------------\r\n");
00259     
00260     /*
00261     if(msg.id == (MPPT_BASE_A+MPPT_OFF) ) {
00262         
00263         AnalogIn Vtemp1(PA_3); // RTD temperature sensor (pin A2)
00264 AnalogIn Vtemp2(PA_4); // RTD temperature sensor (pin A3)
00265         
00266         double tempmeas1;
00267     double tempmeas2;
00268     double tempoff1 = -1.8; // Offset in deg C to calibrate RTD 1
00269     double tempoff2 = -1.8; // Offset in deg C to calibrate RTD 2
00270     double slope1 = 1.25; // Slope correction to RTD
00271     double slope2 = 1.25; // Slope correction to RTD
00272     double avgval;
00273     int n = 0;
00274     
00275     float vscale = 150.49; // Input voltage scale factor, mV/LSB (Drivetek datasheet)
00276     float vscaleout = 208.79; // Output voltage scale factor, mV/LSB (Drivetek datasheet)
00277     float iscale = 8.72; // Input current scale factor, mA/LSB (Drivetek datasheet)
00278     float mpptpwr;
00279    
00280     cansuccess = 1;
00281     int involtmsb = msg.data[0] & 0x3; // Bit 0 and Bit 1 of Byte 1 are MSB Uin
00282     int involtlsb = msg.data[1]; // Byte 2 is LSB of Uin
00283     int involt = (involtmsb<<8)|(involtlsb);    
00284     int outvoltmsb = msg.data[4] & 0x3; // Bit 0 and Bit 1 of Byte 5 are MSB Uout
00285     int outvoltlsb = msg.data[5]; // Byte 6 is LSB of Uout
00286     int outvolt = (outvoltmsb<<8)|(outvoltlsb);    
00287     int incurmsb = msg.data[2] & 0x3; // Bit 0 and Bit 1 of Byte 3 are MSB Uin
00288     int incurlsb = msg.data[3]; // Byte 4 is LSB of Iin
00289     int incur = (incurmsb<<8)|(incurlsb);
00290     mpptpwr = (involt*vscale/1000.0)*(incur*iscale/1000.0);
00291    
00292     avgval = 0.0;
00293     n=0;
00294     while(n<100){
00295         tempmeas1 = Vtemp1.read()*3.3;
00296         avgval=avgval+tempmeas1;
00297         n++;
00298         }
00299     tempmeas1 = tempoff1 + slope1*(avgval/100.0)*150.0/2.92;
00300     avgval = 0.0;
00301     n=0;
00302     while(n<100){
00303         tempmeas2 = Vtemp2.read()*3.3;
00304         avgval=avgval+tempmeas2;
00305         n++;
00306         }
00307     tempmeas2 = tempoff2 + slope2*(avgval/100.0)*150.0/2.92;
00308     printf("Array Temperature 1 = %.1f", tempmeas1);
00309     printf(" deg C   ");
00310     printf("Array Temperature 2 = %.1f", tempmeas2);
00311     printf(" deg C \r\n");
00312     printf("MPPT In Vol = %.1f", involt*vscale/1000.0);
00313     printf("V Out Vol = %.1f", outvolt*vscaleout/1000.0);
00314     printf("V Input Cur = %.1f", incur*iscale/1000.0);
00315     printf("A In Pwr = %.2f", mpptpwr);
00316     printf("W \r\n");
00317     }
00318     */
00319     if (msg.id == DC_BUS_CURRENT){
00320         float DCbuscur = bytes2Float(msg.data);
00321         pc.printf("DC bus current is %f\n", DCbuscur);
00322         return DCbuscur;
00323     } else if (msg.id == DC_BUS_VOLTAGE){
00324         float DCbusvolt = bytes2Float(msg.data);
00325         pc.printf("DC bus voltage is %f\n", DCbusvolt);
00326         return DCbusvolt;
00327     } else if (msg.id == PHASE_B_CURRENT){
00328         float phaseBcurrent = bytes2Float(msg.data);
00329         pc.printf("Phase B current is %f\n", phaseBcurrent);
00330         return phaseBcurrent;
00331     } else if (msg.id == PHASE_C_CURRENT){
00332         float phaseCcurrent = bytes2Float(msg.data);
00333         pc.printf("Phase C current is %f\n", phaseCcurrent);
00334         return phaseCcurrent;
00335     } else if (msg.id == VEHICLE_VELOCITY){
00336         float vehicleVel = bytes2Float(msg.data);
00337         pc.printf("Vehicle velocity is %f\n", vehicleVel);
00338         return vehicleVel;
00339     } else if (msg.id == MOTOR_VELOCITY){
00340         float motorVel = bytes2Float(msg.data);
00341         pc.printf("Motor velocity is %f\n", motorVel);
00342         return motorVel;
00343     } else if (msg.id == VD){
00344         float vd = bytes2Float(msg.data);
00345         pc.printf("Velocity vector D is %f\n", vd);
00346         return vd;
00347     } else if (msg.id == VQ){
00348         float vq = bytes2Float(msg.data);
00349         pc.printf("Velocity vector Q is %f\n", vq);
00350         return vq;
00351     }  else if (msg.id == ID){
00352         float Id = bytes2Float(msg.data);
00353         pc.printf("Current vector D is %f\n", Id);
00354         return Id;
00355     } else if (msg.id == IQ){
00356         float Iq = bytes2Float(msg.data);
00357         pc.printf("Current vector Q is %f\n", Iq);
00358         return Iq;
00359     } else if (msg.id == BEMFD){
00360         float BEMFd = bytes2Float(msg.data);
00361         pc.printf("BackEMF Measurement D is %f\n", BEMFd);
00362         return BEMFd;
00363     } else if (msg.id == BEMFQ){
00364         float BEMFq = bytes2Float(msg.data);
00365         pc.printf("BackEMF Measurement Q is %f\n", BEMFq);
00366         return BEMFq;
00367     } else if (msg.id == HEAT_SINK_TEMPERATURE){
00368         float heatSinkTemp = bytes2Float(msg.data);
00369         pc.printf("Heat sink temperature is %f\n", heatSinkTemp);
00370         return heatSinkTemp;
00371     } else if (msg.id == MOTOR_TEMPERATURE){
00372         float motorTemp = bytes2Float(msg.data);
00373         pc.printf("Motor temperature is %f\n", motorTemp);
00374         return motorTemp;
00375     } else if (msg.id == DC_BUS_AMP_HOURS){
00376         float DCBusAmpHours = bytes2Float(msg.data);
00377         pc.printf("DC Bus AmpHours is %f\n", DCBusAmpHours);
00378         return DCBusAmpHours;
00379     } else if (msg.id == ODOMETER){
00380         float odometerValue = bytes2Float(msg.data);
00381         pc.printf("Odomoter value is %f\n", odometerValue);
00382         return odometerValue;
00383     } 
00384     
00385     // BPS
00386     if (msg.id == BPS_TRIP) {
00387         received = msg.data[0];
00388         pc.printf("BPS Trip is %d\n", received);
00389     } else if (msg.id == BPS_ALL_CLEAR) {
00390         received = msg.data[0];
00391         pc.printf("BPS All Clear is %d\n", received);
00392     } else if (msg.id == BPS_OFF) {
00393         received = msg.data[0];
00394         // sd card stuff
00395         pc.printf("BPS Off is %d\n", received);    
00396     } else if (msg.id == WDOG_TRIGGERED) {
00397         received = msg.data[0];
00398         pc.printf("WDOG Triggered is %d\n", received);    
00399     } else if (msg.id == CAN_ERROR) {
00400         received = msg.data[0];
00401         pc.printf("CAN Error is %d\n", received);    
00402     } else if (msg.id == VOLTAGE_DATA) {
00403         // voltage
00404         float voltage = bytes2Float(&msg.data[1]);
00405         pc.printf("Voltage is %.3fV from array index %d\n", voltage, msg.data[0]);
00406         return voltage;
00407     } else if (msg.id == TEMPERATURE_DATA){
00408         // temperature   
00409         float temp = bytes2Float(&msg.data[1]);
00410         pc.printf("Temp is %.3f from array index %d\n", temp, msg.data[0]);  
00411         return temp;
00412     } else if(msg.id == SOC_DATA){
00413         // state of charge
00414         float soc = bytes2Float(msg.data);
00415         pc.printf("SoC is %.3f%%\n", soc);
00416         return received;
00417     } else if(msg.id == CURRENT_DATA){
00418         // current
00419         float current = bytes2Float(msg.data);
00420         pc.printf("Current is %.3fA\n", current); 
00421         return current;
00422     }
00423     
00424     // Motor controller
00425     /*
00426     else if (msg.id == DC_BUS_CURRENT){
00427         float DCbuscur = bytes2Float(msg.data);
00428         pc.printf("DC bus current is %f\n", DCbuscur);
00429         return DCbuscur;
00430     } else if (msg.id == DC_BUS_VOLTAGE){
00431         float DCbusvolt = bytes2Float(msg.data);
00432         pc.printf("DC bus voltage is %f\n", DCbusvolt);
00433         return DCbusvolt;
00434     } else if (msg.id == PHASE_B_CURRENT){
00435         float phaseBcurrent = bytes2Float(msg.data);
00436         pc.printf("Phase B current is %f\n", phaseBcurrent);
00437         return phaseBcurrent;
00438     } else if (msg.id == PHASE_C_CURRENT){
00439         float phaseCcurrent = bytes2Float(msg.data);
00440         pc.printf("Phase C current is %f\n", phaseCcurrent);
00441         return phaseCcurrent;
00442     } else if (msg.id == VEHICLE_VELOCITY){
00443         float vehicleVel = bytes2Float(msg.data);
00444         pc.printf("Vehicle velocity is %f\n", vehicleVel);
00445         return vehicleVel;
00446     } else if (msg.id == MOTOR_VELOCITY){
00447         float motorVel = bytes2Float(msg.data);
00448         pc.printf("Motor velocity is %f\n", motorVel);
00449         return motorVel;
00450     } else if (msg.id == VD){
00451         float vd = bytes2Float(msg.data);
00452         pc.printf("Velocity vector D is %f\n", vd);
00453         return vd;
00454     } else if (msg.id == VQ){
00455         float vq = bytes2Float(msg.data);
00456         pc.printf("Velocity vector Q is %f\n", vq);
00457         return vq;
00458     }  else if (msg.id == ID){
00459         float Id = bytes2Float(msg.data);
00460         pc.printf("Current vector D is %f\n", Id);
00461         return Id;
00462     } else if (msg.id == IQ){
00463         float Iq = bytes2Float(msg.data);
00464         pc.printf("Current vector Q is %f\n", Iq);
00465         return Iq;
00466     } else if (msg.id == BEMFD){
00467         float BEMFd = bytes2Float(msg.data);
00468         pc.printf("BackEMF Measurement D is %f\n", BEMFd);
00469         return BEMFd;
00470     } else if (msg.id == BEMFQ){
00471         float BEMFq = bytes2Float(msg.data);
00472         pc.printf("BackEMF Measurement Q is %f\n", BEMFq);
00473         return BEMFq;
00474     } else if (msg.id == HEAT_SINK_TEMPERATURE){
00475         float heatSinkTemp = bytes2Float(msg.data);
00476         pc.printf("Heat sink temperature is %f\n", heatSinkTemp);
00477         return heatSinkTemp;
00478     } else if (msg.id == MOTOR_TEMPERATURE){
00479         float motorTemp = bytes2Float(msg.data);
00480         pc.printf("Motor temperature is %f\n", motorTemp);
00481         return motorTemp;
00482     } else if (msg.id == DC_BUS_AMP_HOURS){
00483         float DCBusAmpHours = bytes2Float(msg.data);
00484         pc.printf("DC Bus AmpHours is %f\n", DCBusAmpHours);
00485         return DCBusAmpHours;
00486     } else if (msg.id == ODOMETER){
00487         float odometerValue = bytes2Float(msg.data);
00488         pc.printf("Odomoter value is %f\n", odometerValue);
00489         return odometerValue;
00490     } 
00491     */
00492     
00493     
00494     pc.printf("-----------------------\r\n");
00495     //wait(0.5);
00496     return -1;
00497 } 
00498 
00499 int main() {
00500     pc.baud(9600);          // set serial speed
00501     can.frequency(125000); // max 1Mbps, usually 150000
00502     pc.printf("-----------------\r\n");
00503     pc.printf("    main loop    \r\n");
00504     pc.printf("this is board %d \r\n", CanID);
00505     pc.printf("-----------------\r\n");
00506     CANMessage msg;
00507     led = 0;
00508     
00509     while(1) {
00510        // Write CAN, comment for one board
00511        #ifdef BOARD1
00512         generateValues();
00513        #else
00514        // Read CAN, comment for the other
00515         receiveCan();
00516        #endif
00517        
00518         // comment for push
00519          // wait(1.0);
00520        
00521     }
00522 }