From 9e4a9f0f30215457a12c759bdb2043d6e680891c Mon Sep 17 00:00:00 2001 From: Unknown <mdryden@chem.utoronto.ca> Date: Fri, 29 Sep 2017 18:02:11 -0400 Subject: [PATCH] Switch experiment parameters to all DAC units. --- src/config/conf_board.h | 1 + src/experiment.c | 162 +++++++++++++++++++++++++++------------- src/experiment.h | 12 +-- src/settings.c | 12 ++- src/settings.h | 3 +- 5 files changed, 128 insertions(+), 62 deletions(-) diff --git a/src/config/conf_board.h b/src/config/conf_board.h index 37265f9..99f2af8 100644 --- a/src/config/conf_board.h +++ b/src/config/conf_board.h @@ -34,6 +34,7 @@ #define SETTINGS_R100M_TRIM 0 #define SETTINGS_EIS_CAL1 3000U #define SETTINGS_EIS_CAL2 3000000UL +#define SETTINGS_DAC_UNITS_TRUE 0 #endif // CONF_BOARD_H diff --git a/src/experiment.c b/src/experiment.c index e565b36..d5d9330 100644 --- a/src/experiment.c +++ b/src/experiment.c @@ -60,7 +60,7 @@ static port_callback_t portd_int1_callback; void experiment_handler(char command[]){ static int16_t p1, p2, p3; - static uint16_t u1, u2, u3, u4; + static uint16_t u1, u2, u3, u4, u5, u6; static uint8_t p5, o1, o2, o3; static int16_t pcv1, pcv2; static uint16_t pct1, pct2; @@ -83,27 +83,87 @@ void experiment_handler(char command[]){ break; case 'L': //LSV - start, stop, slope - sscanf(command+1, "%u%u%i%i%i%i%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1); - precond(pcv1,pct1,pcv2,pct2); - lsv_experiment(p1,p2,u1,2); + if (settings.settings.dac_units_true) { + sscanf(command+1, "%u%u%u%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&u1,&u2,&u3); + precond(pcv1,pct1,pcv2,pct2); + lsv_experiment(u1,u2,u3,2); + } else { + sscanf(command+1, "%u%u%i%i%i%i%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1); + + //start + u2 = ceil(p1*(65536/(double)3000)+32768); + //stop + u3 = ceil(p2*(65536/(double)3000)+32768); + + precond(pcv1,pct1,pcv2,pct2); + lsv_experiment(u2,u3,u1,2); + } break; case 'C': //CV - v1, v2, start, scans, slope - sscanf(command+1, "%u%u%i%i%i%i%i%hhu%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&p3,&p5,&u1); - precond(pcv1,pct1,pcv2,pct2); - cv_experiment(p1,p2,p3,p5,u1); + if (settings.settings.dac_units_true) { + sscanf(command+1, "%u%u%i%i%u%u%u%hhu%u",&pct1,&pct2,&pcv1,&pcv2,&u1,&u2,&u3,&p5,&u4); + precond(pcv1,pct1,pcv2,pct2); + cv_experiment(u1,u2,u3,p5,u4); + } else { + sscanf(command+1, "%u%u%i%i%i%i%i%hhu%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&p3,&p5,&u4); + + //v1 + u1 = ceil(p1*(65536/(double)3000)+32768); + //v2 + u2 = ceil(p2*(65536/(double)3000)+32768); + //start + u3 = ceil(p3*(65536/(double)3000)+32768); + //slope + u4 = ceil(u4*(65536/(double)3000)); + + precond(pcv1,pct1,pcv2,pct2); + cv_experiment(u1,u2,u3,p5,u4); + } break; case 'S': //SWV - start, stop, step size, pulse_height, frequency, scans - sscanf(command+1, "%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4); - precond(pcv1,pct1,pcv2,pct2); - swv_experiment(p1,p2,u1,u2,u3,u4); + if (settings.settings.dac_units_true) { + sscanf(command+1, "%u%u%i%i%u%u%u%u%u%hhu",&pct1,&pct2,&pcv1,&pcv2,&u1,&u2,&u3,&u4,&u5,&p5); + precond(pcv1,pct1,pcv2,pct2); + swv_experiment(u1,u2,u3,u4,u5,p5); + } else { + sscanf(command+1, "%u%u%i%i%i%i%u%u%u%hhu",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&p5); + + //start + uint16_t start = ceil(p1*(65536/(double)3000)+32768); + //stop + uint16_t stop = ceil(p2*(65536/(double)3000)+32768); + //step + u1 = ceil(u1*(65536/(double)3000)); + //pulse_height + u2 = ceil(u2*(65536/(double)3000)); + + precond(pcv1,pct1,pcv2,pct2); + swv_experiment(start,stop,u1,u2,u3,p5); + } break; case 'D': //DPV - start, stop, step size, pulse_height, period, width - sscanf(command+1, "%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4); - precond(pcv1,pct1,pcv2,pct2); - dpv_experiment(p1,p2,u1,u2,u3,u4); + if (settings.settings.dac_units_true) { + sscanf(command+1, "%u%u%i%i%u%u%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&u1,&u2,&u3,&u4,&u5,&u6); + precond(pcv1,pct1,pcv2,pct2); + dpv_experiment(u1,u2,u3,u4,u5,u6); + } else { + sscanf(command+1, "%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4); + + //start + uint16_t start = ceil(p1*(65536/(double)3000)+32768); + //stop + uint16_t stop = ceil(p2*(65536/(double)3000)+32768); + //step + u1 = ceil(u1*(65536/(double)3000)); + //pulse_height + u2 = ceil(u2*(65536/(double)3000)); + + precond(pcv1,pct1,pcv2,pct2); + dpv_experiment(start,stop,u1,u2,u3,u4); + } break; case 'M': //PMT idle mode - holds voltage at 0 V with no data output @@ -462,7 +522,7 @@ void ocp_exp_start(void){ } #endif -void precond(int16_t v1, uint16_t t1, int16_t v2, uint16_t t2){ //assumes potentiostat switches are already set +void precond(uint16_t v1, uint16_t t1, uint16_t v2, uint16_t t2){ //assumes potentiostat switches are already set /** * Performs experiment preconditioning. * @@ -536,16 +596,16 @@ static void precond_rtc_callback(uint32_t time){ RTC.INTCTRL |= RTC_COMPINTLVL_OFF_gc; } -void cv_experiment(int16_t v1, int16_t v2, int16_t start, uint8_t scans, uint16_t slope){ +void cv_experiment(uint16_t v1, uint16_t v2, uint16_t start, uint8_t scans, uint16_t slope){ /** * Perform a CV experiment. * * Calls lsv_experiment several times to make a CV experiment. - * @param v1 Vertex 1 in mV. - * @param v2 Vertex 2 in mV. - * @param start Start voltage in mV. + * @param v1 Vertex 1 in dac units. + * @param v2 Vertex 2 in dac units. + * @param start Start voltage in dac units. * @param scans Number of scans. - * @param slope Scan rate in mV/s. + * @param slope Scan rate in dac units/s. */ // check if start is [v1,v2] @@ -587,33 +647,33 @@ void cv_experiment(int16_t v1, int16_t v2, int16_t start, uint8_t scans, uint16_ return; } -uint8_t lsv_experiment(int16_t start, int16_t stop, uint16_t slope, int8_t first_run){ +uint8_t lsv_experiment(uint16_t start, uint16_t stop, uint16_t slope, int8_t first_run){ /** * Perform a LSV experiment. * * Uses porte_int0_lsv to output to USB. - * @param start Start potential in mV. - * @param stop Stop potential in mV. - * @param slope Scan rate in mV/s. + * @param start Start potential in dac units. + * @param stop Stop potential in dac units. + * @param slope Scan rate in dac units/s. * @param first_run Keeps track of number of scans so potentiostat isn't initialized twice or disconnected when doing CV. Set to 2 for normal LSV. */ uint8_t ret = 0; //check experiment limits - if(start<-1500 || start>=1500 ||start==stop|| stop<-1500 || stop>=1500 || slope>7000) + if(start==stop) { printf("#ERR: Experiment parameters outside limits\n"); return ret; } - uint16_t dacindex_start = ceil(start*(65536/(double)3000)+32768); - dacindex_stop = ceil(stop*(65536/(double)3000)+32768); +// uint16_t dacindex_start = ceil(start*(65536/(double)3000)+32768); +// dacindex_stop = ceil(stop*(65536/(double)3000)+32768); uint32_t timer_period; uint16_t temp_div; - max5443_set_voltage1(dacindex_start); + max5443_set_voltage1(start); if (first_run == 1 || first_run == 2){ volt_exp_start(); @@ -631,7 +691,7 @@ uint8_t lsv_experiment(int16_t start, int16_t stop, uint16_t slope, int8_t first EVSYS.CH0MUX = EVSYS_CHMUX_TCD0_OVF_gc; EVSYS.CH0CTRL = 0; - timer_period = ceil(1/((double)slope/(3000./65536))*(F_CPU)); + timer_period = ceil(1/(double)slope*(F_CPU)); temp_div = ceil(timer_period/65536.); if (temp_div <= 1) @@ -671,7 +731,7 @@ uint8_t lsv_experiment(int16_t start, int16_t stop, uint16_t slope, int8_t first } - EXP_TC1_0.CNT = dacindex_start; + EXP_TC1_0.CNT = start; if (stop > start) { @@ -684,7 +744,7 @@ uint8_t lsv_experiment(int16_t start, int16_t stop, uint16_t slope, int8_t first tc_set_direction(&EXP_TC1_0, TC_DOWN); } - tc_write_cc(&EXP_TC1_0, TC_CCA, dacindex_stop); + tc_write_cc(&EXP_TC1_0, TC_CCA, stop); tc_enable_cc_channels(&EXP_TC1_0, TC_CCAEN); EXP_TC0_0.CNT = 0; @@ -944,23 +1004,23 @@ static void ca_cca_callback(void){ return; } -void swv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_height, uint16_t frequency, uint16_t scans){ +void swv_experiment(uint16_t start, uint16_t stop, uint16_t step, uint16_t pulse_height, uint16_t frequency, uint8_t scans){ /** * Perform a SWV experiment * - * @param start Start voltage in mV. - * @param stop Stop voltage in mV. - * @param step Step voltage in mV. - * @param pulse_height Pulse amplitude in mV. + * @param start Start voltage in dac units. + * @param stop Stop voltage in dac units. + * @param step Step voltage in dac units. + * @param pulse_height Pulse amplitude in dac units. * @param frequency Frequency in Hz. * @param scans Number of scans (0 for single direction mode) */ uint8_t direction; - uint16_t dacindex_start = ceil((start)*(65536/(double)3000))+32768; - uint16_t dacindex_stop = ceil(stop*(65536/(double)3000))+32768; - uint16_t dacindex_step = ceil(step*(65536/(double)3000)); - uint16_t dacindex_pulse_height = ceil(pulse_height*(65536/(double)3000)); +// uint16_t dacindex_start = ceil((start)*(65536/(double)3000))+32768; +// uint16_t dacindex_stop = ceil(stop*(65536/(double)3000))+32768; +// uint16_t dacindex_step = ceil(step*(65536/(double)3000)); +// uint16_t dacindex_pulse_height = ceil(pulse_height*(65536/(double)3000)); uint32_t period; if (start < stop) @@ -988,13 +1048,13 @@ void swv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_h EXP_TC0_1.CNT = 0; EXP_TC0_0.CNT = 0; - if (_swv_singledir(dacindex_start, dacindex_stop, dacindex_pulse_height, dacindex_step, direction)) + if (_swv_singledir(start, stop, pulse_height, step, direction)) goto aborting; //function will return non-zero if abort called over USB if (scans > 0){ //non-cyclic mode skips out after one direction EXP_TC0_1.CNT = 0; EXP_TC0_0.CNT = 0; - if (_swv_singledir(dacindex_stop, dacindex_start, dacindex_pulse_height, dacindex_step, !direction)) //swap start and stop and invert direction for second half of scan + if (_swv_singledir(stop, start, pulse_height, step, !direction)) //swap start and stop and invert direction for second half of scan goto aborting; } @@ -1111,23 +1171,23 @@ uint8_t _swv_singledir (uint16_t dacindex, uint16_t dacindex_stop, uint16_t daci return 0; } -void dpv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_height, uint16_t pulse_period, uint16_t pulse_width){ +void dpv_experiment(uint16_t start, uint16_t stop, uint16_t step, uint16_t pulse_height, uint16_t pulse_period, uint16_t pulse_width){ /** * Perform a DPV experiment * - * @param start Start voltage in mV. - * @param stop Stop voltage in mV. - * @param step Step voltage in mV. - * @param pulse_height Pulse amplitude in mV. + * @param start Start voltage in dac units. + * @param stop Stop voltage in dac units. + * @param step Step voltage in dac units. + * @param pulse_height Pulse amplitude in dac units. * @param pulse_period Pulse period in ms. * @param pulse_width Pulse width in ms. */ uint8_t direction; - uint16_t dacindex_start = ceil((start)*(65536/(double)3000))+32768; - uint16_t dacindex_stop = ceil(stop*(65536/(double)3000))+32768; - uint16_t dacindex_step = ceil(step*(65536/(double)3000)); - uint16_t dacindex_pulse_height = ceil(pulse_height*(65536/(double)3000)); +// uint16_t dacindex_start = ceil((start)*(65536/(double)3000))+32768; +// uint16_t dacindex_stop = ceil(stop*(65536/(double)3000))+32768; +// uint16_t dacindex_step = ceil(step*(65536/(double)3000)); +// uint16_t dacindex_pulse_height = ceil(pulse_height*(65536/(double)3000)); uint32_t cpu_period; uint32_t cpu_width; @@ -1160,7 +1220,7 @@ void dpv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_h EXP_TC0_1.CNT = 0; EXP_TC0_0.CNT = 0; - if (_dpv_singledir(dacindex_start, dacindex_stop, dacindex_pulse_height, dacindex_step, direction)) + if (_dpv_singledir(start, stop, pulse_height, step, direction)) goto aborting; //function will return non-zero if abort called over USB printf("D\n"); //signal end of experiment diff --git a/src/experiment.h b/src/experiment.h index a410b82..684d6df 100644 --- a/src/experiment.h +++ b/src/experiment.h @@ -91,9 +91,9 @@ void pot_init(void); void pot_set_gain(void); void volt_exp_start(void); void volt_exp_stop(void); -void precond(int16_t v1, uint16_t t1, int16_t v2, uint16_t t2); -void cv_experiment(int16_t v1, int16_t v2, int16_t start, uint8_t scans, uint16_t slope); -uint8_t lsv_experiment(int16_t start, int16_t stop, uint16_t slope, int8_t first_run); +void precond(uint16_t v1, uint16_t t1, uint16_t v2, uint16_t t2); +void cv_experiment(uint16_t v1, uint16_t v2, uint16_t start, uint8_t scans, uint16_t slope); +uint8_t lsv_experiment(uint16_t start, uint16_t stop, uint16_t slope, int8_t first_run); #if BOARD_VER_MAJOR == 1 && BOARD_VER_MINOR >= 2 void ocp_exp_start(void); @@ -102,7 +102,7 @@ void pot_experiment(uint16_t time_seconds, uint8_t exp_type); #endif void ca_experiment(uint16_t steps, uint16_t step_dac[], uint16_t step_seconds[]); -void swv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_height, uint16_t frequency, uint16_t scans); -void dpv_experiment(int16_t start, int16_t stop, uint16_t step, uint16_t pulse_height, uint16_t pulse_period, uint16_t pulse_width); +void swv_experiment(uint16_t start, uint16_t stop, uint16_t step, uint16_t pulse_height, uint16_t frequency, uint8_t scans); +void dpv_experiment(uint16_t start, uint16_t stop, uint16_t step, uint16_t pulse_height, uint16_t pulse_period, uint16_t pulse_width); -#endif /* EXPERIMENT_H_ */ \ No newline at end of file +#endif /* EXPERIMENT_H_ */ diff --git a/src/settings.c b/src/settings.c index a03a25b..06e0db6 100644 --- a/src/settings.c +++ b/src/settings.c @@ -31,7 +31,7 @@ void settings_handler(char command[]){ break; case 'W': //Write new settings - sscanf(command+1, "%i%hhu%u%i%i%i%i%i%i%i%lu%lu", + sscanf(command+1, "%i%hhu%u%i%i%i%i%i%i%i%lu%lu%hhu", &settings.settings.max5443_offset, &settings.settings.tcs_enabled, &settings.settings.tcs_clear_threshold, @@ -43,7 +43,8 @@ void settings_handler(char command[]){ &settings.settings.r30M_trim, &settings.settings.r100M_trim, &settings.settings.eis_cal1, - &settings.settings.eis_cal2); + &settings.settings.eis_cal2, + &settings.settings.dac_units_true); settings_write_eeprom(); break; @@ -84,7 +85,8 @@ void settings_read_eeprom(void){ printf("#INFO: r100M_trim = %i\n", settings.settings.r100M_trim); printf("#INFO: eis_cal1 = %lu\n", settings.settings.eis_cal1); printf("#INFO: eis_cal2 = %lu\n", settings.settings.eis_cal2); - printf("Smax5443_offset.%u:tcs_enabled.%u:tcs_clear_threshold.%u:r100_trim.%i:r3k_trim.%i:r30k_trim.%i:r300k_trim.%i:r3M_trim.%i:r30M_trim.%i:r100M_trim.%i:eit_cal1.%lu:eis_cal2.%lu\n", + printf("#INFO: dac_units_true = %u\n", settings.settings.dac_units_true); + printf("Smax5443_offset.%u:tcs_enabled.%u:tcs_clear_threshold.%u:r100_trim.%i:r3k_trim.%i:r30k_trim.%i:r300k_trim.%i:r3M_trim.%i:r30M_trim.%i:r100M_trim.%i:eit_cal1.%lu:eis_cal2.%lu:dac_units_true.%u\n", settings.settings.max5443_offset, settings.settings.tcs_enabled, settings.settings.tcs_clear_threshold, @@ -96,7 +98,8 @@ void settings_read_eeprom(void){ settings.settings.r30M_trim, settings.settings.r100M_trim, settings.settings.eis_cal1, - settings.settings.eis_cal2); + settings.settings.eis_cal2, + settings.settings.dac_units_true); } void settings_write_eeprom(void){ @@ -119,6 +122,7 @@ void settings_restore_defaults(void){ settings.settings.r100M_trim = SETTINGS_R100M_TRIM; settings.settings.eis_cal1 = SETTINGS_EIS_CAL1; settings.settings.eis_cal2 = SETTINGS_EIS_CAL2; + settings.settings.dac_units_true = SETTINGS_DAC_UNITS_TRUE; settings_write_eeprom(); } diff --git a/src/settings.h b/src/settings.h index b2b5091..32b6d9d 100644 --- a/src/settings.h +++ b/src/settings.h @@ -30,7 +30,8 @@ struct settings_list { //Make sure this doesn't exceed 32 bytes int16_t r30M_trim; int16_t r100M_trim; uint32_t eis_cal1; - uint32_t eis_cal2; //28 bytes + uint32_t eis_cal2; + uint8_t dac_units_true; //29 bytes }; union { -- GitLab