commit 0c7a0f042f3a21948c8d55c60c6dc5db544b803e Author: EIVE Cleanroom Date: Thu Feb 17 14:47:56 2022 +0100 Initial commit diff --git a/MAX122x.cpp b/MAX122x.cpp new file mode 100644 index 0000000..5d065ab --- /dev/null +++ b/MAX122x.cpp @@ -0,0 +1,323 @@ +#include "MAX122x.h" +#include + +MAX122x_library::MAX122x_library(bool displayMsg) { + // Anything you need when instantiating your object goes here +} + +// Reads out MAX122x internal temperature sensor +float MAX122x_library::max122xreadTemp(uint8_t Chipselect_Pin){ + // Utilise SPI bus with appropriate settings + SPI.beginTransaction(SPI_SETTINGS); + // Write Setup register + digitalWrite(Chipselect_Pin,LOW); + // Write in setup register + SPI.transfer(MAX122x_SETUP_0); + delayMicroseconds(SPI_delay_commandSkip); + // Write conversion register to get temperature + SPI.transfer(MAX122x_CONVERT_TMP); + // Wait for conversion to be finished (incl. int. ref. wake-up time) + delayMicroseconds(SPI_delay_conversionTime); + // Write 24-2 byte of zeros on bus + for (byte i=0;i<=21;i++){ + SPI.transfer(0x00); + } + // Fetch temperature from last 2 bytes of the 24 bytes sent + byte tmp_msb=SPI.transfer(0x00); // MSB of conversion + byte tmp_lsb=SPI.transfer(0x00); // LSB of conversion + // end ADC sampling + digitalWrite(Chipselect_Pin,HIGH); + // Clear bus + SPI.endTransaction(); + // recover 12 bit value into 16 bit/2byte/uint16_t + //adc_msb = adc_msb & 0x0F; + uint16_t tmp_comb=((uint16_t)tmp_msb << 8) | tmp_lsb; + // Convert to celsius + float tmp_result = (float)tmp_comb/8; + // Return result + return tmp_result; +} // end of max122xreadTMP() + +// Reads out single MAX122x ADC channnel +uint16_t MAX122x_library::max122xreadADCsingle(uint8_t Chipselect_Pin, byte channel){ + // Utilise SPI bus with appropriate settings + SPI.beginTransaction(SPI_SETTINGS); + // Write Setup register + digitalWrite(Chipselect_Pin,LOW); + // Write in setup register + SPI.transfer(MAX122x_SETUP_0); + delayMicroseconds(SPI_delay_commandSkip); + // Select channel + switch(channel){ + case 0 : SPI.transfer(MAX122x_CONVERT_CH0); + break; + case 1 : SPI.transfer(MAX122x_CONVERT_CH1); + break; + case 2 : SPI.transfer(MAX122x_CONVERT_CH2); + break; + case 3 : SPI.transfer(MAX122x_CONVERT_CH3); + break; + case 4 : SPI.transfer(MAX122x_CONVERT_CH4); + break; + case 5 : SPI.transfer(MAX122x_CONVERT_CH5); + break; + case 6 : SPI.transfer(MAX122x_CONVERT_CH6); + break; + case 7 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + case 8 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + case 9 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + case 10 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + case 11 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + default: break; + } + // Wait for conversion to be finished (incl. int. ref. wake-up time) + delayMicroseconds(SPI_delay_conversionTime); + byte data[16]={0}; + byte adc_msb=SPI.transfer(0x00); // MSB of conversion + byte adc_lsb=SPI.transfer(0x00); // LSB of conversion + // end ADC sampling + digitalWrite(Chipselect_Pin,HIGH); + // Clear bus + SPI.endTransaction(); + // recover 12 bit value into 16 bit/2byte/uint16_t + //adc_msb = adc_msb & 0x0F; + uint16_t adc_result=((uint16_t)adc_msb << 8) | adc_lsb; + // Return result + return adc_result; +} // end of max122xreadADCsingle() + + +// Reads out MAX122x ADC channel 0 through 3 (MAX1227 and MAX1229) +struct ADCresults0to3 MAX122x_library::max122xReadADC0to3(uint8_t Chipselect_Pin){ + // Instantiate struct + struct ADCresults0to3 adcresult0to3_instance; + // Initialise function variables + uint16_t results_concat; + // Utilise SPI bus with appropriate settings + SPI.beginTransaction(SPI_SETTINGS); + // Write Setup register + digitalWrite(Chipselect_Pin,LOW); + // Write in setup register + SPI.transfer(MAX122x_SETUP_0); + delayMicroseconds(SPI_delay_commandSkip); + // Loop over all channels + for(uint8_t i=0; i<=3; i++){ + switch(i){ + case 0 : SPI.transfer(MAX122x_CONVERT_CH0); + break; + case 1 : SPI.transfer(MAX122x_CONVERT_CH1); + break; + case 2 : SPI.transfer(MAX122x_CONVERT_CH2); + break; + case 3 : SPI.transfer(MAX122x_CONVERT_CH3); + break; + default: break; + } + // Wait for conversion to be finished (incl. int. ref. wake-up time) + if(i==0){ + delayMicroseconds(SPI_delay_conversionTime); + }else{ + delayMicroseconds(SPI_delay_commandSkip); + } + byte adc_msb=SPI.transfer(0x00); // MSB of conversion + byte adc_lsb=SPI.transfer(0x00); // LSB of conversion + // End ADC sampling + // Recover 12 bit value into 16 bit/2byte/uint16_t + //adc_msb = adc_msb & 0x0F; + results_concat=((uint16_t)adc_msb << 8) | adc_lsb; + // Write into instantiated struct + switch(i){ + case 0 : adcresult0to3_instance.result_ch0=results_concat; + break; + case 1 : adcresult0to3_instance.result_ch1=results_concat; + break; + case 2 : adcresult0to3_instance.result_ch2=results_concat; + break; + case 3 : adcresult0to3_instance.result_ch3=results_concat; + break; + default: break; + } + } + // Clear bus + digitalWrite(Chipselect_Pin,HIGH); + SPI.endTransaction(); + // Return result + return adcresult0to3_instance; +} // end of max122xReadADC0to3() + +// Reads out MAX122x ADC channel 0 through 7 (MAX1227 and MAX1229) +struct ADCresults0to7 MAX122x_library::max122xReadADC0to7(uint8_t Chipselect_Pin){ + // Instantiate struct + struct ADCresults0to7 adcresult0to7_instance; + // Initialise function variables + uint16_t results_concat; + // Utilise SPI bus with appropriate settings + SPI.beginTransaction(SPI_SETTINGS); + // Write Setup register + digitalWrite(Chipselect_Pin,LOW); + // Write in setup register + SPI.transfer(MAX122x_SETUP_0); + delayMicroseconds(SPI_delay_commandSkip); + // Loop over all channels + for(uint8_t i=0; i<=7; i++){ + switch(i){ + case 0 : SPI.transfer(MAX122x_CONVERT_CH0); + break; + case 1 : SPI.transfer(MAX122x_CONVERT_CH1); + break; + case 2 : SPI.transfer(MAX122x_CONVERT_CH2); + break; + case 3 : SPI.transfer(MAX122x_CONVERT_CH3); + break; + case 4 : SPI.transfer(MAX122x_CONVERT_CH4); + break; + case 5 : SPI.transfer(MAX122x_CONVERT_CH5); + break; + case 6 : SPI.transfer(MAX122x_CONVERT_CH6); + break; + case 7 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + default: break; + } + // Wait for conversion to be finished (incl. int. ref. wake-up time) + if(i==0){ + delayMicroseconds(SPI_delay_conversionTime); + }else{ + delayMicroseconds(SPI_delay_commandSkip); + } + byte adc_msb=SPI.transfer(0x00); // MSB of conversion + byte adc_lsb=SPI.transfer(0x00); // LSB of conversion + // End ADC sampling + // Recover 12 bit value into 16 bit/2byte/uint16_t + //adc_msb = adc_msb & 0x0F; + results_concat=((uint16_t)adc_msb << 8) | adc_lsb; + // Write into instantiated struct + switch(i){ + case 0 : adcresult0to7_instance.result_ch0=results_concat; + break; + case 1 : adcresult0to7_instance.result_ch1=results_concat; + break; + case 2 : adcresult0to7_instance.result_ch2=results_concat; + break; + case 3 : adcresult0to7_instance.result_ch3=results_concat; + break; + case 4 : adcresult0to7_instance.result_ch4=results_concat; + break; + case 5 : adcresult0to7_instance.result_ch5=results_concat; + break; + case 6 : adcresult0to7_instance.result_ch6=results_concat; + break; + case 7 : adcresult0to7_instance.result_ch7=results_concat; + break; + default: break; + } + } + // Clear bus + digitalWrite(Chipselect_Pin,HIGH); + SPI.endTransaction(); + // Return result + return adcresult0to7_instance; +} // end of max122xReadADC0to7() + + +// Reads out MAX122x ADC channel 0 through 11 (only MAX1229!) +struct ADCresults0to11 MAX122x_library::max122xReadADC0to11(uint8_t Chipselect_Pin){ + // Instantiate struct + struct ADCresults0to11 adcresult0to11_instance; + // Initialise function variables + uint16_t results_concat; + // Utilise SPI bus with appropriate settings + SPI.beginTransaction(SPI_SETTINGS); + // Write Setup register + digitalWrite(Chipselect_Pin,LOW); + // Write in setup register + SPI.transfer(MAX122x_SETUP_0); + delayMicroseconds(SPI_delay_commandSkip); + // Loop over all channels + for(uint8_t i=0; i<=11; i++){ + switch(i){ + case 0 : SPI.transfer(MAX122x_CONVERT_CH0); + break; + case 1 : SPI.transfer(MAX122x_CONVERT_CH1); + break; + case 2 : SPI.transfer(MAX122x_CONVERT_CH2); + break; + case 3 : SPI.transfer(MAX122x_CONVERT_CH3); + break; + case 4 : SPI.transfer(MAX122x_CONVERT_CH4); + break; + case 5 : SPI.transfer(MAX122x_CONVERT_CH5); + break; + case 6 : SPI.transfer(MAX122x_CONVERT_CH6); + break; + case 7 : SPI.transfer(MAX122x_CONVERT_CH7); + break; + case 8 : SPI.transfer(MAX122x_CONVERT_CH8); + break; + case 9 : SPI.transfer(MAX122x_CONVERT_CH9); + break; + case 10 : SPI.transfer(MAX122x_CONVERT_CH10); + break; + case 11 : SPI.transfer(MAX122x_CONVERT_CH11); + break; + default: break; + } + // Wait for conversion to be finished (incl. int. ref. wake-up time) + if(i==0){ + delayMicroseconds(SPI_delay_conversionTime); + }else{ + delayMicroseconds(SPI_delay_commandSkip); + } + byte adc_msb=SPI.transfer(0x00); // MSB of conversion + byte adc_lsb=SPI.transfer(0x00); // LSB of conversion + // End ADC sampling + // Recover 12 bit value into 16 bit/2byte/uint16_t + //adc_msb = adc_msb & 0x0F; + results_concat=((uint16_t)adc_msb << 8) | adc_lsb; + // Write into instantiated struct + switch(i){ + case 0 : adcresult0to11_instance.result_ch0=results_concat; + break; + case 1 : adcresult0to11_instance.result_ch1=results_concat; + break; + case 2 : adcresult0to11_instance.result_ch2=results_concat; + break; + case 3 : adcresult0to11_instance.result_ch3=results_concat; + break; + case 4 : adcresult0to11_instance.result_ch4=results_concat; + break; + case 5 : adcresult0to11_instance.result_ch5=results_concat; + break; + case 6 : adcresult0to11_instance.result_ch6=results_concat; + break; + case 7 : adcresult0to11_instance.result_ch7=results_concat; + break; + case 8 : adcresult0to11_instance.result_ch8=results_concat; + break; + case 9 : adcresult0to11_instance.result_ch9=results_concat; + break; + case 10 : adcresult0to11_instance.result_ch10=results_concat; + break; + case 11 : adcresult0to11_instance.result_ch11=results_concat; + break; + default: break; + } + } + // Clear bus + digitalWrite(Chipselect_Pin,HIGH); + SPI.endTransaction(); + // Return result + return adcresult0to11_instance; +} // end of max122xReadADC0to11() + + +float MAX122x_library::max122xFloatToVoltage(uint16_t adc_raw_value){ + static float v_ref = 2.5; // [V] ADC internal voltage reference + static uint16_t adc_bit = 4095; // [bit] 2^12 bit resolution + return (float(adc_raw_value)*v_ref/adc_bit); +} // End of max122xFloatToVoltage diff --git a/MAX122x.h b/MAX122x.h new file mode 100644 index 0000000..a24cb11 --- /dev/null +++ b/MAX122x.h @@ -0,0 +1,76 @@ +#ifndef _MAX122x_H_ +#define _MAX122x_H_ + +// SPI communication settings + #define SPI_SETTINGS SPISettings(4000000, MSBFIRST, SPI_MODE0) // max 4.8MHz readout clock speed on MAX122x + +// MAX122x Mode 11 registers + // Conversion MSBFirst: BIT7:1|BIT6:CHSEL3|BIT5:CHSEL2|BIT4:CHSEL1|BIT3:CHSEL0|BIT2:SCAN1|BIT1:SCAN0|BIT0:TEMP + #define MAX122x_CONVERT_CH0 0b10000110 // Initiates single ADC conversion on Ch0 + #define MAX122x_CONVERT_CH1 0b10001110 // Initiates single ADC conversion on Ch1 + #define MAX122x_CONVERT_CH2 0b10010110 // Initiates single ADC conversion on Ch2 + #define MAX122x_CONVERT_CH3 0b10011110 // Initiates single ADC conversion on Ch3 + #define MAX122x_CONVERT_CH4 0b10100110 // Initiates single ADC conversion on Ch4 + #define MAX122x_CONVERT_CH5 0b10101110 // Initiates single ADC conversion on Ch5 + #define MAX122x_CONVERT_CH6 0b10110110 // Initiates single ADC conversion on Ch6 + #define MAX122x_CONVERT_CH7 0b10111110 // Initiates single ADC conversion on Ch7 + #define MAX122x_CONVERT_CH8 0b11000110 // Initiates single ADC conversion on Ch8 + #define MAX122x_CONVERT_CH9 0b11001110 // Initiates single ADC conversion on Ch9 + #define MAX122x_CONVERT_CH10 0b11010110 // Initiates single ADC conversion on Ch10 + #define MAX122x_CONVERT_CH11 0b11011110 // Initiates single ADC conversion on Ch11 + #define MAX122x_CONVERT_TMP 0b10000001 // Initiates single TMP conversion + // Setup MSB first: BIT7:0|BIT6:1|BIT5:CKSEL1|BIT4:CKSEL0|BIT3:REFSEL1|BIT2:REFSEL0|BIT1:DIFFSEL1|BIT0:DIFFSEL0 + #define MAX122x_SETUP_0 0b01110000 // External Timed by SCLK, Internal Reference w/ wakeup time, no unipolar/bipolar register write + #define MAX122x_SETUP_1 0b01111000 // External Timed by SCLK, Internal Reference w/o wakeup time, no unipolar/bipolar register write + #define MAX122x_SETUP_2 0b01100000 // Internally timed, use of EOC signal, Internal Reference w/ wakeup time, no unipolar/bipolar register write + #define MAX122x_SETUP_3 0b01101000 // Internally timed, use of EOC signal, Internal Reference w/o wakeup time, no unipolar/bipolar register write + // Averaging + // Not implemented because Mode 11 does not allow averaging and scanning + // Reset (all registers to 0) + #define MAX122x_RESET_ALL 0b00011000 // Resets all registers + #define MAX122x_RESET_FIFO 0b00010000 // Clears FIFO only + // Unipolar mode setup & bipolar mode setup + // Not implemented since unipolar, single ended is default case + +// May be needed depending on Arduino version + #if (ARDUINO >=100) + #include "Arduino.h" + #else + #include "WProgram.h" + #endif + +struct ADCresults0to3{ + uint16_t result_ch0,result_ch1,result_ch2,result_ch3; +}; + +struct ADCresults0to7{ + uint16_t result_ch0,result_ch1,result_ch2,result_ch3,result_ch4,result_ch5,result_ch6,result_ch7; +}; + +struct ADCresults0to11{ + uint16_t result_ch0,result_ch1,result_ch2,result_ch3,result_ch4,result_ch5,result_ch6,result_ch7,result_ch8,result_ch9,result_ch10,result_ch11; +}; + + +// Create class for MAX122x ADC +class MAX122x_library { + public: + // Constructor + MAX122x_library(bool displayMsg=false); + + // Methods + float max122xreadTemp(uint8_t Chipselect_Pin); + uint16_t max122xreadADCsingle(uint8_t Chipselect_Pin, byte channel); + struct ADCresults0to3 max122xReadADC0to3(uint8_t Chipselect_Pin); + struct ADCresults0to7 max122xReadADC0to7(uint8_t Chipselect_Pin); + struct ADCresults0to11 max122xReadADC0to11(uint8_t Chipselect_Pin); + float max122xFloatToVoltage(uint16_t adc_raw_value); + + private: + + uint8_t SPI_delay_commandSkip = 8; // in microseconds + uint8_t SPI_delay_conversionTime = 65; // in microseconds + + +}; +#endif // _MAX122x_H_ diff --git a/SunSensor_Thermaltests.ino b/SunSensor_Thermaltests.ino new file mode 100644 index 0000000..4f94733 --- /dev/null +++ b/SunSensor_Thermaltests.ino @@ -0,0 +1,75 @@ + +#include + +#include +#define SCLK 13 +#define MOSI 11 +#define MISO 12 +#define CS_ADC 10 + +#include "MAX122x.h" +MAX122x_library max122x_library(true); +// SPISettings MAX1229_SETTINGS(4000000, MSBFIRST, SPI_MODE0); // max 4.8MHz readout clock speed on MAX1229 + +uint16_t ch0_bit,ch1_bit,ch2_bit,ch3_bit,ch4_bit,ch5_bit; +float ch0_volt,ch1_volt,ch2_volt,ch3_volt,ch4_volt,ch5_volt; +float temperature; +struct ADCresults0to3; + + +void setup() { + + // Initiate console + Serial.begin(9600); + Serial.setTimeout(1000000); + + // Initialise SPI pins and SPI protocol + pinMode(CS_ADC, OUTPUT); // declare SS output + pinMode(MOSI, OUTPUT); // declare MOSI output + pinMode(MISO, INPUT); // declare MISO input (not stricly necessary) + pinMode(SCLK, OUTPUT); // declare SCLK output + SPI.begin(); + //SPI.setClockDivider(SPI_CLOCK_DIV8); + digitalWrite(CS_ADC,HIGH); +}// end of setup() + +void loop() { + // Readout values + temperature = max122x_library.max122xreadTemp(CS_ADC); + ch0_bit = max122x_library.max122xreadADCsingle(CS_ADC,0); + ch1_bit = max122x_library.max122xreadADCsingle(CS_ADC,1); + ch2_bit = max122x_library.max122xreadADCsingle(CS_ADC,2); + ch3_bit = max122x_library.max122xreadADCsingle(CS_ADC,3); + ch4_bit = max122x_library.max122xreadADCsingle(CS_ADC,4); + ch5_bit = max122x_library.max122xreadADCsingle(CS_ADC,5); + ch0_volt = max122x_library.max122xFloatToVoltage(ch0_bit); + ch1_volt = max122x_library.max122xFloatToVoltage(ch1_bit); + ch2_volt = max122x_library.max122xFloatToVoltage(ch2_bit); + ch3_volt = max122x_library.max122xFloatToVoltage(ch3_bit); + ch4_volt = max122x_library.max122xFloatToVoltage(ch4_bit); + ch5_volt = max122x_library.max122xFloatToVoltage(ch5_bit); + + // Print out results on serial monitor + if(true){ + Serial.println(ch0_volt); + Serial.println(ch1_volt); + Serial.println(ch2_volt); + Serial.println(ch3_volt); + Serial.println(ch4_volt); + Serial.println(ch5_volt); + Serial.println(temperature); + Serial.println(); + } + if(false){ + Serial.println(ch0_bit); + Serial.println(ch1_bit); + Serial.println(ch2_bit); + Serial.println(ch3_bit); + Serial.println(ch4_bit); + Serial.println(ch5_bit); + Serial.println(temperature); + Serial.println(); + } + + +} // end of loop()