void GetSensorValue(void) { totalFR = totalFR + adc_get_channel_value(ADC,ADC_CHANNEL_7) * (3.3/2.55); totalFL = totalFL + adc_get_channel_value(ADC,ADC_CHANNEL_6) * (3.3/2.55); totalBR = totalBR + adc_get_channel_value(ADC,ADC_CHANNEL_5) * (3.3/2.55); totalBL = totalBL + adc_get_channel_value(ADC,ADC_CHANNEL_4) * (3.3/2.55); count++; if(count==avg_sensor_read) { uint32_t sensorValueFR = totalFR/avg_sensor_read; uint32_t sensorValueFL = totalFL/avg_sensor_read; uint32_t sensorValueBR = totalBR/avg_sensor_read; uint32_t sensorValueBL = totalBL/avg_sensor_read; totalFR = 0; totalFL = 0; totalBR = 0; totalBL = 0; count = 0; sensor_diff_f = sensorValueFL-sensorValueFR; sensor_diff_b = sensorValueBL-sensorValueBR; //printf("högerfram: %d \n", sensorValuefr); //printf("vänsterfram: %d \n", sensorvaluefl); //printf("högerbak: %d \n", sensorvaluebr); //printf("vänsterbak: %d \n", sensorvaluebl); //printf("Differens fram: %d \n", sensor_diff_f); //printf("Differens bak: %d \n", sensor_diff_b); } }
// Start converting the enabled channels void AnalogInStartConversion(uint32_t channels) { #if SAM3XA || SAM4S // Clear out any existing conversion complete bits in the status register for (uint32_t chan = 0; chan < 16; ++chan) { if ((adc_get_status(ADC) & (1 << chan)) != 0) { (void)adc_get_channel_value(ADC, static_cast<adc_channel_num_t>(chan)); } } adc_start(ADC); #elif SAM4E channels &= activeChannels; if ((channels & 0x0000FFFF) != 0) { StartConversion(AFEC0); } if ((channels & 0xFFFF0000) != 0) { StartConversion(AFEC1); } #elif SAME70 channels &= activeChannels; if ((channels & 0x000003FF) != 0) { StartConversion(AFEC0); } if ((channels & 0x003FF800) != 0) { StartConversion(AFEC1); } #endif }
/** * \brief ADC interrupt handler. * Entramos aqui quando a conversao for concluida. */ void ADC_Handler(void) { uint32_t tempValue; uint32_t status ; status = adc_get_status(ADC); /* Checa se a interrupção é devido ao canal 5 */ if ((status & ADC_ISR_EOC5)) { tempValue = adc_get_channel_value(ADC, ADC_POT_CHANNEL); if ((tempValue > adc_value_old + 2) || (tempValue < adc_value_old - 2)) { if (isAmp){ amplitude = tempValue; atualiza_amp(amplitude); } else { frequencia = tempValue; tc_stop(TC0,0); configure_tc((frequencia*32768/2000)/4095); atualiza_freq(frequencia); } } adc_value_old = tempValue; } }
/*************************************************************************** Reads the Analog 0 pin on Due. Retun values for the x-axis of the joystick. ***************************************************************************/ uint32_t ReadAnalog0(void) { uint32_t xAngle; adc_start(ADC); xAngle = adc_get_channel_value(ADC,ADC_CHANNEL_7); return xAngle; }
/** * \brief ADC interrupt handler. */ void ADC_Handler(void) { uint32_t tmp; uint32_t status ; status = adc_get_status(ADC); /* Checa se a interrupção é devido ao canal 5 */ static float rad_antes = 0; if ((status & ADC_ISR_EOC5)) { tmp = adc_get_channel_value(ADC, ADC_POT_CHANNEL); ili93xx_set_foreground_color(COLOR_WHITE); ili93xx_draw_filled_rectangle(9, 39, ILI93XX_LCD_WIDTH,55); v=3.3*((float)tmp)/4095.0; rad=2*pi*((float)tmp)/4095.0; ili93xx_draw_line(120,160,120+54*arm_cos_f32(rad_antes),160+54*arm_sin_f32(rad_antes)); ili93xx_set_foreground_color(COLOR_BLACK); sprintf(vet, "Tensao: %f", v); ili93xx_draw_string(10, 40, vet); ili93xx_draw_line(120,160,120+54*arm_cos_f32(rad),160+54*arm_sin_f32(rad)); rad_antes = rad; } }
/**************************************************************************** Reads the Analog 1 pin on Due. Retun values for the y-axis of the joystick. ****************************************************************************/ uint32_t ReadAnalog1(void) { uint32_t yAngle; adc_start(ADC); yAngle = adc_get_channel_value(ADC,ADC_CHANNEL_6); return yAngle; }
/**************************************************************************** Reads the Analog 2 pin on Due. Retun values for the IR sensor. ****************************************************************************/ uint32_t ReadAnalog2(void) { uint32_t IRSensorer; adc_start(ADC); IRSensorer = adc_get_channel_value(ADC,ADC_CHANNEL_5); return IRSensorer; }
/** * Interrupt handler for TC0 interrupt. */ void ADC_Handler(void) { uint32_t tmp; uint32_t status ; status = adc_get_status(ADC); max_digital = adc_get_channel_value(ADC, ADC_POT_CHANNEL); }
// 40kHz sampler. // // Runs at too high a priority to call FreeRTOS routines. // This routine executes each (approximately) 2000 cycles. It is important that // it is not slow. void PWM_Handler(void) { // Read status to indicate that interrupt has been handled uint32_t isr = PWM->PWM_ISR1; if (isr != (1 << 2)) { // Must be interrupt two fatalBlink(1, 6); } if (mode == AM_ADC) { // Temporary code - read ADC, calculate result. // TODO: replace with DMA. // TODO: handle fading. uint32_t data0 = adc_get_channel_value(ADC, 0); uint32_t data1 = adc_get_channel_value(ADC, 1); uint32_t sum = data0 + data1; // sum is a 13 bit value // Calculate output value for DACC dacc_write_conversion_data(DACC, sum / 2); // Calculate duty cycle value for PWM Channel 2. // Calculated value must be between 0 and US_PERIOD-1, non inclusive. int32_t duty = ((US_PERIOD - 2) * sum / 8192) + 1; // For testing with silence // int32_t duty = US_PERIOD / 2; PWM->PWM_CH_NUM[2].PWM_CDTYUPD = duty; } else if (mode == AM_HZ) { // Get TIOA value from status register bool mtioa = TC0->TC_CHANNEL[0].TC_SR & TC_SR_MTIOA; // Write to DACC int16_t dDelta = 2046 * audioVolume / 255; if (!mtioa) { dDelta = -dDelta; } dacc_write_conversion_data(DACC, dDelta + 2048); // Set PWM int16_t pDelta = (US_PERIOD - 2) / 2 * audioVolume / 255; if (!mtioa) { pDelta = -pDelta; } PWM->PWM_CH_NUM[2].PWM_CDTYUPD = pDelta + (US_PERIOD / 2); } }
/** * \brief ADC interrupt handler. * Entramos aqui quando a conversao for concluida. */ void ADC_Handler(void) { uint32_t resistencia; if ((adc_get_status(ADC) & ADC_ISR_RXBUFF) == ADC_ISR_RXBUFF) { resistencia = adc_get_channel_value(ADC, ADC_POT_CHANNEL); } }
uint32_t analogRead(void) { adc_start(ADC); //delay_us(100); //delayMicroseconds(100); return adc_get_channel_value(ADC,ADC_CHANNEL_7); /* Replace with actual value read from A/D input*/ }
// Read the most recent 12-bit result from a channel uint16_t AnalogInReadChannel(AnalogChannelNumber channel) { if ((unsigned int)channel < numChannels) { #if SAM3XA || SAM4S return adc_get_channel_value(ADC, GetAdcChannel(channel)); #elif SAM4E || SAME70 return afec_channel_get_value(GetAfec(channel), GetAfecChannel(channel)); #endif } return 0; }
/** Display current information,including * voltage on potentiometer, thresholds and comparison mode. */ static void display_info(void) { uint32_t ul_adc_value = adc_get_channel_value(ADC, ADC_CHANNEL_POTENTIOMETER); float f_low_threshold = (float)gs_us_low_threshold * VOLT_REF / MAX_DIGITAL; float f_high_threshold = (float)gs_us_high_threshold * VOLT_REF / MAX_DIGITAL; uint32_t ul_low_threshold = f_to_int(f_low_threshold); uint32_t ul_high_threshold = f_to_int(f_high_threshold); printf("-I- Thresholds: %u mv - %u mv.\n\r", ul_low_threshold, ul_high_threshold); printf("-I- Voltage on potentiometer: %u mv.\n\r", (unsigned int)(ul_adc_value * VOLT_REF / MAX_DIGITAL)); printf("-I- Comparison mode is %u\n\r.", (unsigned int)(ADC->ADC_EMR & ADC_EMR_CMPMODE_Msk)); }
/** * \brief Handler for ADC interrupt. */ void ADC_Handler(void) { uint32_t low_threshold; uint32_t high_threshold; uint32_t status = adc_get_status(ADC); /* Read the status to ack the IT */ if ((status & ADC_ISR_COMPE) == ADC_ISR_COMPE) { /* Get the potentiometer initial value */ pontentiometer_value = adc_get_channel_value( ADC, ADC_CHANNEL_POTENTIOMETER ); /* Set Window threshold according to the initial values */ low_threshold = pontentiometer_value - (NB_INTERVALS * (0x1000 / 256)); if (low_threshold > 0xf0000000) { low_threshold = 0; } high_threshold = pontentiometer_value + (NB_INTERVALS * (0x1000 / 256)); if (high_threshold >= 0x1000) { high_threshold = 0x1000 - 1; } /* Normalize the value 0 -> 255 */ pontentiometer_value = pontentiometer_value*100 + 1; ppt_delay_clapse_counter = 0; /* Setup Threshold*/ adc_set_comparison_window( ADC, low_threshold, high_threshold); /* Compare mode, in the window. */ adc_enable_interrupt(ADC, ADC_IER_COMPE); } if (status & ADC_ISR_ENDRX) { /* Start next buffer */ ADC->ADC_RNPR = (uint32_t) frame_buffer[(adc_buf_ndx + 2) % AUDIO_NB_BUFFER]; ADC->ADC_RNCR = AUDIO_FRAME_SIZE; adc_buf_ndx = (adc_buf_ndx + 1) % AUDIO_NB_BUFFER; adc_nb_samples += AUDIO_FRAME_SIZE; } }
/** * \brief ADC interrupt handler. */ void ADC_Handler(void) { uint32_t tmp; uint32_t status ; status = adc_get_status(ADC); /* Checa se a interrupção é devido ao canal 5 */ if ((status & ADC_ISR_EOC5)) { tmp = adc_get_channel_value(ADC, ADC_POT_CHANNEL); if(tmp != adc_value_old) { adc_value_old = tmp; adc_value_new = 1; } } }
void ADC_Handler(void) { uint32_t ul_mode; uint16_t us_adc; /* Disable Compare Interrupt. */ adc_disable_interrupt(ADC, ADC_IDR_COMPE); if ((adc_get_status(ADC) & ADC_ISR_COMPE) == ADC_ISR_COMPE) { ul_mode = adc_get_comparison_mode(ADC); us_adc = adc_get_channel_value(ADC, ADC_CHANNEL_POTENTIOMETER); switch (ul_mode) { case 0: printf("-ISR-:Potentiometer voltage %d mv is below the low " "threshold:%d mv!\n\r", us_adc * VOLT_REF / MAX_DIGITAL, gs_us_low_threshold * VOLT_REF / MAX_DIGITAL); break; case 1: printf("-ISR-:Potentiometer voltage %d mv is above the high " "threshold:%d mv!\n\r", us_adc * VOLT_REF / MAX_DIGITAL, gs_us_high_threshold * VOLT_REF / MAX_DIGITAL); break; case 2: printf("-ISR-:Potentiometer voltage %d mv is in the comparison " "window:%d-%d mv!\n\r", us_adc * VOLT_REF / MAX_DIGITAL, gs_us_low_threshold * VOLT_REF / MAX_DIGITAL, gs_us_high_threshold * VOLT_REF / MAX_DIGITAL); break; case 3: printf("-ISR-:Potentiometer voltage %d mv is out of the comparison" " window:%d-%d mv!\n\r", us_adc * VOLT_REF / MAX_DIGITAL, gs_us_low_threshold * VOLT_REF / MAX_DIGITAL, gs_us_high_threshold * VOLT_REF / MAX_DIGITAL); break; } } }
/** * \brief Turn on/off ADC module. * * \param on True to start ADC, false to turn off. */ static void demo_start_adc(bool on) { uint32_t low_threshold, high_threshold; if (on == true) { /* Check if already enabled */ if (demo_adc_on) { return; } demo_config_adc(); /* Start TC0 and hardware trigger. */ tc_start(TC0, 1); /* Get the potentiometer initial value */ pontentiometer_value = adc_get_channel_value(ADC, ADC_CHANNEL_POTENTIOMETER); /* Set Window threshold according to the initial values */ low_threshold = pontentiometer_value - (NB_INTERVALS * (0x1000 / 256)); if (low_threshold > 0xf000000) { low_threshold = 0; } high_threshold = pontentiometer_value + (NB_INTERVALS * (0x1000 / 256)); if (high_threshold >= 0x1000) { high_threshold = 0x1000 - 1; } pontentiometer_value = pontentiometer_value*100 + 1; /* Channel 5 has to be compared. */ adc_set_comparison_channel(ADC, ADC_CHANNEL_POTENTIOMETER); /* Compare mode, out the window. */ adc_set_comparison_mode(ADC, ADC_EMR_CMPMODE_OUT); /* Set up Threshold. */ adc_set_comparison_window(ADC, low_threshold, high_threshold); /* Enable ADC interrupt. */ NVIC_EnableIRQ(ADC_IRQn); /* Enable Compare Interrupt. */ adc_enable_interrupt(ADC, ADC_IER_COMPE); /* Set adc on flag */ demo_adc_on = 1; /* Reset clapse time */ ppt_delay_clapse_counter = 0; } else { tc_stop(TC0, 1); /* Enable ADC interrupt. */ NVIC_DisableIRQ(ADC_IRQn); /* Enable Compare Interrupt. */ adc_disable_interrupt(ADC, ADC_IDR_COMPE); /* Set adc off flag */ demo_adc_on = 0; } }
int main(void) { uint8_t i; uint8_t temperature[BUFFER_SIZE]; uint8_t light[BUFFER_SIZE]; uint8_t value_disp[5]; uint32_t adc_value; double temp; // Initialize clocks. sysclk_init(); // Initialize GPIO states. board_init(); // Configure ADC for light sensor. configure_adc(); // Initialize at30tse. at30tse_init(); // Configure IO1 buttons. configure_buttons(); // Initialize SPI and SSD1306 controller. ssd1306_init(); ssd1306_clear(); // Clear internal buffers. for (i = 0; i < BUFFER_SIZE; ++i) { temperature[i] = 0; light[i] = 0; } while (true) { /* Refresh page title only if necessary. */ if (app_mode_switch > 0) { app_mode = app_mode_switch - 1; // Clear screen. ssd1306_clear(); ssd1306_set_page_address(0); ssd1306_set_column_address(0); /* Temperature mode. */ if (app_mode == 0) { ioport_set_pin_level(IO1_LED1_PIN, IO1_LED1_ACTIVE); ioport_set_pin_level(IO1_LED2_PIN, !IO1_LED2_ACTIVE); ioport_set_pin_level(IO1_LED3_PIN, !IO1_LED3_ACTIVE); ssd1306_write_text("Temperature sensor:"); } /* Light mode. */ else if (app_mode == 1) { ioport_set_pin_level(IO1_LED2_PIN, IO1_LED2_ACTIVE); ioport_set_pin_level(IO1_LED1_PIN, !IO1_LED1_ACTIVE); ioport_set_pin_level(IO1_LED3_PIN, !IO1_LED3_ACTIVE); ssd1306_write_text("Light sensor:"); } /* SD mode. */ else { ioport_set_pin_level(IO1_LED3_PIN, IO1_LED3_ACTIVE); ioport_set_pin_level(IO1_LED1_PIN, !IO1_LED1_ACTIVE); ioport_set_pin_level(IO1_LED2_PIN, !IO1_LED2_ACTIVE); display_sd_info(); } app_mode_switch = 0; } // Shift graph buffers. for (i = 0; i < BUFFER_SIZE - 1; ++i) { temperature[i] = temperature[i + 1]; light[i] = light[i + 1]; } // Get temperature in a range from 0 to 40 degrees. if (at30tse_read_temperature(&temp) == TWI_SUCCESS) { // Don't care about negative temperature. if (temp < 0) temp = 0; // Update temperature for display. // Note: -12 in order to rescale for better rendering. if (temp < 12) temperature[BUFFER_SIZE - 1] = 0; else temperature[BUFFER_SIZE - 1] = temp - 12; } else { // Error print zero values. temperature[BUFFER_SIZE - 1] = 0; } // Get light sensor information. // Rescale for better rendering. adc_start(ADC); adc_value = adc_get_channel_value(ADC, ADC_CHANNEL_4); light[BUFFER_SIZE - 1] = 24 - adc_value * 24 / 4096; // Print temperature in text format. if (app_mode == 0) { sprintf(value_disp, "%d", (uint8_t)temp); ssd1306_set_column_address(95); ssd1306_write_command(SSD1306_CMD_SET_PAGE_START_ADDRESS(0)); ssd1306_write_text(" "); ssd1306_write_text(value_disp); // Display degree symbol. ssd1306_write_data(0x06); ssd1306_write_data(0x06); ssd1306_write_text("c"); // Refresh graph. ssd1306_draw_graph(0, 1, BUFFER_SIZE, 3, temperature); } else if (app_mode == 1) { sprintf(value_disp, "%lu", 100 - (adc_value * 100 / 4096)); ssd1306_set_column_address(98); ssd1306_write_command(SSD1306_CMD_SET_PAGE_START_ADDRESS(0)); ssd1306_write_text(" "); ssd1306_write_text(value_disp); ssd1306_write_text("%"); // Refresh graph. ssd1306_draw_graph(0, 1, BUFFER_SIZE, 3, light); } else { // Is card has been inserted or removed? if (sd_status_update == 1) { // Clear screen. ssd1306_clear(); ssd1306_set_page_address(0); ssd1306_set_column_address(0); // Show SD card info. display_sd_info(); sd_status_update = 0; } } /* Wait and stop screen flickers. */ delay_ms(50); } }
/** * \brief ACC example application entry point. * * \return Unused (ANSI-C compatibility). */ int main(void) { uint8_t uc_key; int16_t s_volt = 0; uint32_t ul_value = 0; volatile uint32_t ul_status = 0x0; int32_t l_volt_dac0 = 0; /* Initialize the system */ sysclk_init(); board_init(); /* Initialize debug console */ configure_console(); /* Output example information */ puts(STRING_HEADER); /* Initialize DACC */ /* Enable clock for DACC */ pmc_enable_periph_clk(ID_DACC); /* Reset DACC registers */ dacc_reset(DACC); /* External trigger mode disabled. DACC in free running mode. */ dacc_disable_trigger(DACC); /* Half word transfer mode */ dacc_set_transfer_mode(DACC, 0); /* Power save: * sleep mode - 0 (disabled) * fast wake-up - 0 (disabled) */ dacc_set_power_save(DACC, 0, 0); /* Timing: * refresh - 0x08 (1024*8 dacc clocks) * max speed mode - 0 (disabled) * startup time - 0xf (960 dacc clocks) */ dacc_set_timing(DACC, 0x08, 0, 0xf); /* Disable TAG and select output channel DACC_CHANNEL */ dacc_set_channel_selection(DACC, DACC_CHANNEL_0); /* Enable output channel DACC_CHANNEL */ dacc_enable_channel(DACC, DACC_CHANNEL_0); /* Setup analog current */ dacc_set_analog_control(DACC, DACC_ANALOG_CONTROL); /* Set DAC0 output at ADVREF/2. The DAC formula is: * * (5/6 * VOLT_REF) - (1/6 * VOLT_REF) volt - (1/6 * VOLT_REF) * ----------------------------------- = -------------------------- * MAX_DIGITAL digit * * Here, digit = MAX_DIGITAL/2 */ dacc_write_conversion_data(DACC, MAX_DIGITAL / 2); l_volt_dac0 = (MAX_DIGITAL / 2) * (2 * VOLT_REF / 3) / MAX_DIGITAL + VOLT_REF / 6; /* Initialize ADC */ /* Enable clock for ADC */ pmc_enable_periph_clk(ID_ADC); /* * Formula: ADCClock = MCK / ( (PRESCAL+1) * 2 ) * For example, MCK = 64MHZ, PRESCAL = 4, then: * ADCClock = 64 / ((4+1) * 2) = 6.4MHz; */ adc_init(ADC, sysclk_get_cpu_hz(), ADC_CLOCK, ADC_STARTUP_TIME_SETTING); /* Formula: * Startup Time = startup value / ADCClock * Transfer Time = (TRANSFER * 2 + 3) / ADCClock * Tracking Time = (TRACKTIM + 1) / ADCClock * Settling Time = settling value / ADCClock * For example, ADC clock = 6MHz (166.7 ns) * Startup time = 512 / 6MHz = 85.3 us * Transfer Time = (1 * 2 + 3) / 6MHz = 833.3 ns * Tracking Time = (0 + 1) / 6MHz = 166.7 ns * Settling Time = 3 / 6MHz = 500 ns */ /* Set ADC timing */ adc_configure_timing(ADC, ADC_TRACK_SETTING, ADC_SETTLING_TIME_3, ADC_TRANSFER_SETTING); /* Channel 5 has to be compared */ adc_enable_channel(ADC, ADC_CHANNEL_5); //! [acc_enable_clock] /** Enable clock for ACC */ pmc_enable_periph_clk(ID_ACC); //! [acc_enable_clock] //! [acc_init] /** Initialize ACC */ acc_init(ACC, ACC_MR_SELPLUS_AD5, ACC_MR_SELMINUS_DAC0, ACC_MR_EDGETYP_ANY, ACC_MR_INV_DIS); //! [acc_init] //! [acc_irq_enable] /** Enable ACC interrupt */ NVIC_EnableIRQ(ACC_IRQn); /** Enable */ acc_enable_interrupt(ACC); //! [acc_irq_enable] dsplay_menu(); while (1) { while (uart_read(CONSOLE_UART, &uc_key)) { } printf("input: %c\r\n", uc_key); switch (uc_key) { case 's': case 'S': printf("Input DAC0 output voltage (%d~%d mv): ", (VOLT_REF / 6), (VOLT_REF * 5 / 6)); s_volt = get_input_voltage(); puts("\r"); if (s_volt > 0) { l_volt_dac0 = s_volt; /* The DAC formula is: * * (5/6 * VOLT_REF) - (1/6 * VOLT_REF) volt - (1/6 * VOLT_REF) * ----------------------------------- = -------------------------- * MAX_DIGITAL digit * */ ul_value = ((s_volt - (VOLT_REF / 6)) * (MAX_DIGITAL * 6) / 4) / VOLT_REF; dacc_write_conversion_data(DACC, ul_value); puts("-I- Set ok\r"); } else { puts("-I- Input voltage is invalid\r"); } break; case 'v': case 'V': /* Start conversion */ adc_start(ADC); ul_status = adc_get_status(ADC); while ((ul_status & ADC_ISR_EOC5) != ADC_ISR_EOC5) { ul_status = adc_get_status(ADC); } /* Conversion is done */ ul_value = adc_get_channel_value(ADC, ADC_CHANNEL_5); /* * Convert ADC sample data to voltage value: * voltage value = (sample data / max. resolution) * reference voltage */ s_volt = (ul_value * VOLT_REF) / MAX_DIGITAL; printf("-I- Voltage on potentiometer(AD5) is %d mv\n\r", s_volt); printf("-I- Voltage on DAC0 is %ld mv \n\r", (long)l_volt_dac0); break; case 'm': case 'M': dsplay_menu(); break; } } }
/** * \brief Example entry point. * * Initialize ADC to 12-bit, enable channel "ADC_CHANNEL_POTENTIOMETER", then * enable hardware trigger with TIOA0 every second. Finally, start conversion. * * \return Unused (ANSI-C compatibility). */ int main(void) { uint8_t c_choice; int16_t s_adc_value; int16_t s_threshold = 0; /* Initialize the SAM system. */ sysclk_init(); board_init(); configure_console(); /* Output example information. */ puts(STRING_HEADER); /* Initialize threshold. */ gs_us_low_threshold = 0x0; gs_us_high_threshold = MAX_DIGITAL; /* Enable peripheral clock. */ pmc_enable_periph_clk(ID_ADC); /* Initialize ADC. */ /* startup = 10: 640 periods of ADCClock * for prescale = 4 * prescale: ADCClock = MCK / ( (PRESCAL+1) * 2 ) => 64MHz / ((4+1)*2) = 6.4MHz * ADC clock = 6.4 MHz */ adc_init(ADC, sysclk_get_cpu_hz(), 6400000, 10); #if SAM3S || SAM3XA || SAM4S adc_configure_timing(ADC, 0, ADC_SETTLING_TIME_3, 1); #elif SAM3N adc_configure_timing(ADC, 0); #endif adc_check(ADC, sysclk_get_cpu_hz()); /* Hardware trigger TIOA0. */ adc_configure_trigger(ADC, ADC_TRIG_TIO_CH_0, 0); /* Enable channels for x,y and z. */ adc_enable_channel(ADC, ADC_CHANNEL_POTENTIOMETER); /* Configure TC. */ configure_tc0(); /* Channel 5 has to be compared. */ adc_set_comparison_channel(ADC, ADC_CHANNEL_POTENTIOMETER); /* Compare mode, in the window. */ adc_set_comparison_mode(ADC, ADC_EMR_CMPMODE_IN); /* Set up Threshold. */ adc_set_comparison_window(ADC, gs_us_high_threshold, gs_us_low_threshold); /* Enable ADC interrupt. */ NVIC_EnableIRQ(ADC_IRQn); /* Start TC0 and hardware trigger. */ tc_start(TC0, 0); /* Display main menu. */ display_menu(); while (1) { while (uart_read(CONSOLE_UART, &c_choice)) { } printf("%c\r\n", c_choice); switch (c_choice) { case '0': s_adc_value = adc_get_channel_value(ADC, ADC_CHANNEL_POTENTIOMETER); printf("-I- Current voltage is %d mv, %d%% of ADVREF\n\r", (s_adc_value * VOLT_REF / MAX_DIGITAL), (s_adc_value * 100 / MAX_DIGITAL)); break; case '1': puts("Low threshold is set to(mv):"); s_threshold = get_voltage(); puts("\r"); if (s_threshold >= 0) { s_adc_value = s_threshold * MAX_DIGITAL / VOLT_REF; adc_set_comparison_window(ADC, s_adc_value, gs_us_high_threshold); /* Renew low threshold. */ gs_us_low_threshold = s_adc_value; float f_low_threshold = (float)gs_us_low_threshold * VOLT_REF / MAX_DIGITAL; uint32_t ul_low_threshold = f_to_int(f_low_threshold); printf("Setting low threshold to %u mv (reg value to 0x%x ~%d%%)\n\r", ul_low_threshold, gs_us_low_threshold, gs_us_low_threshold * 100 / MAX_DIGITAL); } break; case '2': puts("High threshold is set to(mv):"); s_threshold = get_voltage(); puts("\r"); if (s_threshold >= 0) { s_adc_value = s_threshold * MAX_DIGITAL / VOLT_REF; adc_set_comparison_window(ADC, gs_us_low_threshold, s_adc_value); /* Renew high threshold. */ gs_us_high_threshold = s_adc_value; float f_high_threshold = (float)gs_us_high_threshold * VOLT_REF / MAX_DIGITAL; uint32_t ul_high_threshold = f_to_int(f_high_threshold); printf("Setting high threshold to %u mv (reg value to 0x%x ~%d%%)\n\r", ul_high_threshold, gs_us_high_threshold, gs_us_high_threshold * 100 / MAX_DIGITAL); } break; case '3': puts("-a. Below low threshold.\n\r" "-b. Above high threshold.\n\r" "-c. In the comparison window.\n\r" "-d. Out of the comparison window.\n\r" "-q. Quit the setting.\r"); c_choice = get_comparison_mode(); adc_set_comparison_mode(ADC, c_choice); printf("Comparison mode is %c.\n\r", 'a' + c_choice); break; case 'm': case 'M': display_menu(); break; case 'i': case 'I': display_info(); break; case 's': case 'S': enter_asleep(); break; } puts("Press \'m\' or \'M\' to display the main menu again!\r"); } }