
Basic Mid-Level control for the rebuilt MorphGI control unit, using PWM to communicate with the low level controllers.
Dependencies: ros_lib_kinetic
LLComms.cpp
- Committer:
- WD40andTape
- Date:
- 2018-08-29
- Revision:
- 13:a373dfc57b89
- Parent:
- 12:595ed862e52f
- Child:
- 14:54c3759e76ed
File content as of revision 13:a373dfc57b89:
// LLComms.cpp #include "LLComms.h" //DigitalOut pinTesty(PB_8); LLComms::LLComms() : queue(32 * EVENTS_EVENT_SIZE), //32 //8 * EVENTS_EVENT_SIZE pinGate6(PE_11), spi(PC_12, PC_11, PC_10), pinCheck(PE_5), // These interrupt pins have to be declared AFTER SPI declaration. No Clue Why. pinGate0(PF_11), pinGate1(PG_14), pinGate2(PF_15), pinGate3(PF_12), pinGate4(PF_3), pinGate5(PF_13), //pinGate6(PE_11), // See above nonsense pinGate7(PE_13), pinReset(PD_2) { // Constructor PinName LLPins[8] = {PD_15, PE_10, PD_11, PD_14, PE_7, PD_12, PF_10, PD_13}; //PinName LLPins[8] = {PD_15, PE_10, PD_14, PD_11, PE_7, PD_12, PF_10, PD_13}; PinName ADCPins[8] = {PG_12, PG_9, PE_1, PG_0, PD_0, PD_1, PF_0, PF_1}; for (short int i = 0; i < 8; i++) { isDataReady[i] = 0; cs_LL[i] = new DigitalOut(LLPins[i]); cs_ADC[i] = new DigitalOut(ADCPins[i]); } // Initialise relevant variables for(short int i = 0; i<N_CHANNELS; i++) { // All chip selects in off state *cs_LL[i] = 1; *cs_ADC[i] = 1; } pinReset = 1; // Initialise reset pin to not reset the controllers. wait(0.25); pinReset=0; // Reset controllers to be safe wait(0.25); pinReset = 1; // Ready to go // Set up rise interrupts MIGHT NOT NEED TO BE POINTERS pinGate0.rise(callback(this,&LLComms::rise0)); pinGate1.rise(callback(this,&LLComms::rise1)); pinGate2.rise(callback(this,&LLComms::rise2)); pinGate3.rise(callback(this,&LLComms::rise3)); pinGate4.rise(callback(this,&LLComms::rise4)); pinGate5.rise(callback(this,&LLComms::rise5)); pinGate6.rise(callback(this,&LLComms::rise6)); pinGate7.rise(callback(this,&LLComms::rise7)); // Set up fall interrupts MIGHT NOT NEED TO BE POINTERS pinGate0.fall(callback(this,&LLComms::fall0)); pinGate1.fall(callback(this,&LLComms::fall1)); pinGate2.fall(callback(this,&LLComms::fall2)); pinGate3.fall(callback(this,&LLComms::fall3)); pinGate4.fall(callback(this,&LLComms::fall4)); pinGate5.fall(callback(this,&LLComms::fall5)); pinGate6.fall(callback(this,&LLComms::fall6)); pinGate7.fall(callback(this,&LLComms::fall7)); } //LLComms::~LLComms(void) { } // Destructor void LLComms::SendReceiveData(int channel) { //pinTesty = 1; int intPosSPI_Rx[N_CHANNELS]; // 13 bit value received over SPI from the actuator // Get data from controller spi.format(16,2); spi.frequency(LOW_LEVEL_SPI_FREQUENCY); mutChannel[channel].lock(); // Lock mutex for specific Channel *cs_LL[channel] = 0; // Select relevant chip intPosSPI_Rx[channel] = spi.write(demandPosition[channel]); // Transmit & receive *cs_LL[channel] = 1; // Deselect chip isDataReady[channel] = 0; // Data no longer ready, i.e. we now require new data /*if(channel == 0) { intGlobalTest = intPosSPI_Rx[channel]; dblGlobalTest = ((double) (intPosSPI_Rx[channel])/8191.0*52.2); }*/ // Sort out received data chrErrorFlag[channel] = intPosSPI_Rx[channel]>>13; intPosSPI_Rx[channel] = intPosSPI_Rx[channel] & 0x1FFF; //dblPosition_mtrs[channel] = (double)intPosSPI_Rx[channel]/8191*(MAX_ACTUATOR_LENGTH/DBL_ACTUATOR_CONVERSION[channel])/1000; mutChannel[channel].unlock();//unlock mutex for specific channel //if(IS_PRINT_OUTPUT) printf("%d, %d\r\n",intPosSPI_Rx[0],_intDemandPos_Tx[0]); //pinTesty = 0; } // Common rise handler function void LLComms::common_rise_handler(int channel) { pinCheck = 1; if (isDataReady[channel]) { // Check if data is ready for tranmission ThreadID[channel] = queue.call(this,&LLComms::SendReceiveData,channel); // Schedule transmission } } // Common fall handler functions void LLComms::common_fall_handler(int channel) { pinCheck = 0; queue.cancel(ThreadID[channel]); // Cancel relevant queued event } // Stub rise functions void LLComms::rise0(void) { common_rise_handler(0); } void LLComms::rise1(void) { common_rise_handler(1); } void LLComms::rise2(void) { common_rise_handler(2); } void LLComms::rise3(void) { common_rise_handler(3); } void LLComms::rise4(void) { common_rise_handler(4); } void LLComms::rise5(void) { common_rise_handler(5); } void LLComms::rise6(void) { common_rise_handler(6); } void LLComms::rise7(void) { common_rise_handler(7); } // Stub fall functions void LLComms::fall0(void) { common_fall_handler(0); } void LLComms::fall1(void) { common_fall_handler(1); } void LLComms::fall2(void) { common_fall_handler(2); } void LLComms::fall3(void) { common_fall_handler(3); } void LLComms::fall4(void) { common_fall_handler(4); } void LLComms::fall5(void) { common_fall_handler(5); } void LLComms::fall6(void) { common_fall_handler(6); } void LLComms::fall7(void) { common_fall_handler(7); } // NEEDS CALIBRATING double LLComms::ReadADCPosition_mtrs(int channel) { unsigned int outputA; unsigned int outputB; int output; double dblOutput; spi.format(8,0); spi.frequency(1000000); *cs_ADC[channel] = 0; spi.write(PREAMBLE); outputA = spi.write(CHAN_3); outputB = spi.write(0xFF); *cs_ADC[channel] = 1; outputA = outputA & DATA_MASK; outputA = outputA<<8; output = (outputA | outputB); output = 4095- output; dblOutput = (double) (output); dblOutput = dblOutput*0.0229 - 21.582; return dblOutput; } double LLComms::ReadADCPressure_bar(int channel) { unsigned int outputA; unsigned int outputB; int output; double dblOutput; spi.format(8,0); spi.frequency(1000000); *cs_ADC[channel] = 0; spi.write(PREAMBLE); outputA = spi.write(CHAN_1); outputB = spi.write(0xFF); *cs_ADC[channel] = 1; outputA = outputA & DATA_MASK; outputA = outputA<<8; output = (outputA | outputB); dblOutput = (double)(output); dblOutput = dblOutput-502.0; dblOutput = dblOutput/4095.0*8.0; return dblOutput; }