示例#1
0
/**
 * \brief Callback function for ADCIFE enter compasion window interrupt.
 */
static void adcife_set_wm_flag(void)
{
	/* Disable Window Monitor Interrupt. */
	adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
	g_uc_enter_win_flag = 1;
	adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
}
示例#2
0
/* Initialize ADC for reading sensors */
void hal_adc_init(void)
{
	/* Enable peripheral clock. */
#if SAM3S || SAM3N || SAM3XA || SAM4S
	uint32_t i;
	pmc_enable_periph_clk(ID_ADC);
#elif SAM3U
  #ifdef ADC_12B
    pmc_enable_periph_clk(ID_ADC12B);
  #else
    pmc_enable_periph_clk(ID_ADC);
  #endif
#endif

	/* Initialize ADC. */
#if SAM3S || SAM3N || SAM3XA || SAM4S
  adc_init(ADC, SystemCoreClock, ADC_FREQ_MAX, ADC_STARTUP_FAST);
#elif SAM3U
  #ifdef ADC_12B
    adc12b_init(ADC12B, sysclk_get_cpu_hz(), 6400000, 10, 10);
  #else
    adc_init(ADC, sysclk_get_cpu_hz(), 6400000, 10);
  #endif
#endif


//
  adc_configure_timing(ADC, 0, ADC_SETTLING_TIME_3, 1);
  adc_configure_trigger(ADC, ADC_TRIG_SW, 0); // Disable hardware trigger.
  adc_disable_interrupt(ADC, 0xFFFFFFFF); // Disable all ADC interrupts.
  adc_disable_all_channel(ADC);

}
示例#3
0
// Module initialisation
void AnalogInInit()
{
#if SAM3XA || SAM4S
	pmc_enable_periph_clk(ID_ADC);
	adc_init(ADC, SystemCoreClock, 2000000, ADC_STARTUP_TIME_12);	// 2MHz clock
	adc_configure_timing(ADC, 3, ADC_SETTLING_TIME_3, 1);			// Add transfer time
	adc_configure_trigger(ADC, ADC_TRIG_SW, 0);						// Disable hardware trigger
	adc_disable_interrupt(ADC, 0xFFFFFFFF);							// Disable all ADC interrupts
	adc_disable_all_channel(ADC);
#elif SAM4E || SAME70
	afec_enable(AFEC0);
	afec_enable(AFEC1);
	afec_config cfg;
	afec_get_config_defaults(&cfg);

#if 0	// these are probably not needed, the defaults should be OK
//	cfg.afec_clock = 2000000UL;						// reduce clock frequency
//	cfg.settling_time = AFEC_SETTLING_TIME_3;
#endif

	while (afec_init(AFEC0, &cfg) != STATUS_OK)
	{
		(void)afec_get_latest_value(AFEC0);
	}
	while (afec_init(AFEC1, &cfg) != STATUS_OK)
	{
		(void)afec_get_latest_value(AFEC1);
	}
	afec_disable_interrupt(AFEC0, AFEC_INTERRUPT_ALL);
	afec_disable_interrupt(AFEC1, AFEC_INTERRUPT_ALL);
	afec_set_trigger(AFEC0, AFEC_TRIG_SW);
	afec_set_trigger(AFEC1, AFEC_TRIG_SW);
#endif
}
示例#4
0
/**
 * \brief Callback function for ADCIFE interrupt.
 */
static void adcife_set_conv_flag(void)
{
	if ((adc_get_status(&g_adc_inst) & ADCIFE_SR_SEOC) == ADCIFE_SR_SEOC) {
		g_uc_condone_flag = 1;
		adc_clear_status(&g_adc_inst, ADCIFE_SCR_SEOC);
		adc_disable_interrupt(&g_adc_inst, ADC_SEQ_SEOC);
	}
}
示例#5
0
/**
 * \brief Application entry point for adcife example.
 *
 * \return Unused (ANSI-C compatibility).
 */
int main(void)
{
	uint32_t uc_key = 0;

	/* Initialize the SAM system */
	sysclk_init();
	board_init();

	/* Initialize the UART console */
	configure_console();

	/* Output example information */
	puts(STRING_HEADER);

	/* Set default ADCIFE test mode. */
	g_adc_test_mode.uc_trigger_mode = TRIGGER_MODE_SOFTWARE;
	g_adc_test_mode.uc_pdc_en = 1;
	g_adc_test_mode.uc_gain_en = 0;

	display_menu();

	start_dac();

	start_adc();

	while (1) {
		/* ADCIFE software trigger per 1s */
		if (g_adc_test_mode.uc_trigger_mode == TRIGGER_MODE_SOFTWARE) {
			adc_start_software_conversion(&g_adc_inst);
		}
		if (!usart_read(CONF_UART, &uc_key)) {
			adc_disable_interrupt(&g_adc_inst, ADC_SEQ_SEOC);
			display_menu();
			set_adc_test_mode();
			start_adc();
			puts("Press any key to display configuration menu.\r");
		}
		delay_ms(1000);
		if (g_uc_condone_flag == 1) {
			if(g_adc_test_mode.uc_pdc_en == 0) {
				printf("Internal DAC Voltage = %4d mv  \r\n",
						(int)(g_adc_sample_data[0] * VOLT_REF / MAX_DIGITAL));
			} else {
				printf("Internal DAC Voltage = %4d mv  \r\n",
						(int)(g_adc_sample_data[0] * VOLT_REF /
							MAX_DIGITAL));
				printf("Scaled VCC Voltage = %4d mv  \r\n",
						(int)(g_adc_sample_data[1] * VOLT_REF /
							MAX_DIGITAL));
			}
			g_uc_condone_flag = 0;
		}
	}
}
示例#6
0
static void _adc_interrupt_handler(const uint8_t instance)
{
	struct adc_module *module = _adc_instances[instance];

	/* get interrupt flags and mask out enabled callbacks */
	uint32_t flags = module->hw->INTFLAG.reg;

	if (flags & ADC_INTFLAG_RESRDY) {
		if ((module->enabled_callback_mask & (1 << ADC_CALLBACK_READ_BUFFER)) &&
				(module->registered_callback_mask & (1 << ADC_CALLBACK_READ_BUFFER))) {
			/* clear interrupt flag */
			module->hw->INTFLAG.reg = ADC_INTFLAG_RESRDY;

			while (adc_is_syncing(module)) {
				/* Wait for synchronization */
			}

			/* store ADC result in job buffer */
			*(module->job_buffer++) = module->hw->RESULT.reg;

			if (--module->remaining_conversions > 0) {
				if (module->software_trigger == true) {
					adc_start_conversion(module);
				}
			} else {
				if (module->job_status == STATUS_BUSY) {
					/* job is complete. update status,disable interrupt
					 *and call callback */
					module->job_status = STATUS_OK;
					adc_disable_interrupt(module, ADC_INTERRUPT_RESULT_READY);

					(module->callback[ADC_CALLBACK_READ_BUFFER])(module);
				}
			}
		}
	}

	if (flags & ADC_INTFLAG_WINMON) {
		module->hw->INTFLAG.reg = ADC_INTFLAG_WINMON;
		if ((module->enabled_callback_mask & (1 << ADC_CALLBACK_WINDOW)) &&
				(module->registered_callback_mask & (1 << ADC_CALLBACK_WINDOW))) {
			(module->callback[ADC_CALLBACK_WINDOW])(module);
		}

	}

	if (flags & ADC_INTFLAG_OVERRUN) {
		module->hw->INTFLAG.reg = ADC_INTFLAG_OVERRUN;
		if ((module->enabled_callback_mask & (1 << ADC_CALLBACK_ERROR)) &&
				(module->registered_callback_mask & (1 << ADC_CALLBACK_ERROR))) {
			(module->callback[ADC_CALLBACK_ERROR])(module);
		}
	}
}
/**
 * \brief Aborts an ongoing job.
 *
 * Aborts an ongoing job.
 *
 * \param [in]  module_inst Pointer to the ADC software instance struct
 * \param [in]  type        Type of job to abort
 */
void adc_abort_job(
    struct adc_module *module_inst,
    enum adc_job_type type)
{
    /* Sanity check arguments */
    Assert(module_inst);

    if (type == ADC_JOB_READ_BUFFER) {
        /* Disable interrupt */
        adc_disable_interrupt(module_inst, ADC_INTERRUPT_RESULT_READY);
        /* Mark job as aborted */
        module_inst->job_status = STATUS_ABORTED;
        module_inst->remaining_conversions = 0;
    }
}
示例#8
0
/**
 * \brief Callback function for ADCIFE interrupt.
 */
static void adcife_wm_handler(void)
{
	uint32_t ul_mode;
	uint16_t us_adc;

	/* Disable Window Monitor Interrupt. */
	adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);

	if ((adc_get_status(&g_adc_inst) & ADCIFE_SR_WM) == ADCIFE_SR_WM) {

		ul_mode = adc_get_wm_mode(&g_adc_inst);
		us_adc = adc_get_last_conv_value(&g_adc_inst);

		switch (ul_mode) {
		case 1:
			printf("-ISR-:DAC output voltage %d mv is above the low threshold:%d mv!\n\r",
					(int)(us_adc * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_low_threshold * VOLT_REF / MAX_DIGITAL));
			break;

		case 2:
			printf("-ISR-:DAC output voltage %d mv is below the high threshold:%d mv!\n\r",
					(int)(us_adc * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_high_threshold * VOLT_REF / MAX_DIGITAL));
			break;

		case 3:
			printf("-ISR-:DAC output voltage %d mv is in the comparison window:%d-%d mv!\n\r",
					(int)(us_adc * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_low_threshold * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_high_threshold * VOLT_REF / MAX_DIGITAL));
			break;

		case 4:
			printf("-ISR-:DAC output voltage %d mv is out of the comparison window:%d-%d mv!\n\r",
					(int)(us_adc * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_low_threshold * VOLT_REF / MAX_DIGITAL),
					(int)(gs_us_high_threshold * VOLT_REF / MAX_DIGITAL));
			break;
		}
		adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
	}
}
示例#9
0
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;
		}
	}
}
示例#10
0
/**
 * \brief Start ADC sample.
 * Initialize ADC, set clock and timing, and set ADC to given mode.
 */
static void start_adc(void)
{
	struct adc_config adc_cfg = {
		/* System clock division factor is 16 */
		.prescal = ADC_PRESCAL_DIV16,
		/* The APB clock is used */
		.clksel = ADC_CLKSEL_APBCLK,
		/* Max speed is 150K */
		.speed = ADC_SPEED_150K,
		/* ADC Reference voltage is 0.625*VCC */
		.refsel = ADC_REFSEL_1,
		/* Enables the Startup time */
		.start_up = CONFIG_ADC_STARTUP
	};
	struct adc_seq_config adc_seq_cfg = {
		/* Select Vref for shift cycle */
		.zoomrange = ADC_ZOOMRANGE_0,
		/* Pad Ground */
		.muxneg = ADC_MUXNEG_1,
		/* DAC internal */
		.muxpos = ADC_MUXPOS_3,
		/* Enables the internal voltage sources */
		.internal = ADC_INTERNAL_3,
		/* Disables the ADC gain error reduction */
		.gcomp = ADC_GCOMP_DIS,
		/* Disables the HWLA mode */
		.hwla = ADC_HWLA_DIS,
		/* 12-bits resolution */
		.res = ADC_RES_12_BIT,
		/* Enables the single-ended mode */
		.bipolar = ADC_BIPOLAR_SINGLEENDED
	};
	struct adc_ch_config adc_ch_cfg = {
		.seq_cfg = &adc_seq_cfg,
		/* Internal Timer Max Counter */
		.internal_timer_max_count = 60,
		/* Window monitor mode is off */
		.window_mode = 0,
		.low_threshold = 0,
		.high_threshold = 0,
	};
	if(adc_init(&g_adc_inst, ADCIFE, &adc_cfg) != STATUS_OK) {
		puts("-F- ADC Init Fail!\n\r");
		while(1);
	}
	if(adc_enable(&g_adc_inst) != STATUS_OK) {
		puts("-F- ADC Enable Fail!\n\r");
		while(1);
	}

	if (g_adc_test_mode.uc_pdc_en) {
		adc_disable_interrupt(&g_adc_inst, ADC_SEQ_SEOC);
		adc_pdca_set_config(&g_adc_pdca_cfg);
		pdca_channel_set_callback(CONFIG_ADC_PDCA_RX_CHANNEL, pdca_transfer_done,
				PDCA_0_IRQn, 1, PDCA_IER_TRC);
	} else {
		pdca_channel_disable_interrupt(CONFIG_ADC_PDCA_RX_CHANNEL,
				PDCA_IDR_TRC);
		pdca_channel_disable_interrupt(CONFIG_ADC_PDCA_TX_CHANNEL,
				PDCA_IDR_TRC);
		adc_ch_set_config(&g_adc_inst, &adc_ch_cfg);
		adc_set_callback(&g_adc_inst, ADC_SEQ_SEOC, adcife_read_conv_result,
				ADCIFE_IRQn, 1);
	}

	/* Configure trigger mode and start convention. */
	switch (g_adc_test_mode.uc_trigger_mode) {
	case TRIGGER_MODE_SOFTWARE:
		adc_configure_trigger(&g_adc_inst, ADC_TRIG_SW);
		break;
	case TRIGGER_MODE_CON:
		adc_configure_trigger(&g_adc_inst, ADC_TRIG_CON);
		break;
	case TRIGGER_MODE_ITIMER:
		adc_configure_trigger(&g_adc_inst, ADC_TRIG_INTL_TIMER);
		adc_configure_itimer_period(&g_adc_inst,
				adc_ch_cfg.internal_timer_max_count);
		adc_start_itimer(&g_adc_inst);
		break;
	default:
		break;
	}

	if (g_adc_test_mode.uc_gain_en) {
		adc_configure_gain(&g_adc_inst, ADC_GAIN_2X);
	} else {
		adc_configure_gain(&g_adc_inst, ADC_GAIN_1X);
	}
}

/**
 * \brief Start DAC ouput.
 * Initialize DAC, set clock and timing, and set DAC to given mode.
 */
static void start_dac(void)
{
	sysclk_enable_peripheral_clock(DACC);

	/* Reset DACC registers */
	dacc_reset(DACC);

	/* Half word transfer mode */
	dacc_set_transfer_mode(DACC, 0);

	/* Timing:
	 * startup                - 0x10 (17 clocks)
	 * internal trigger clock - 0x60 (96 clocks)
	 */
	dacc_set_timing(DACC, 0x10, 0x60);

	/* Enable DAC */
	dacc_enable(DACC);

	/* The DAC is 10-bit resolution, so output voltage should be
	 * (3300 * 255) / ((1 << 10) - 1) = 823mv */
	dacc_write_conversion_data(DACC, 0xFF);
}
void init( void )
{
  SystemInit();

  // Set Systick to 1ms interval, common to all SAM3 variants
  if (SysTick_Config(SystemCoreClock / 1000))
  {
    // Capture error
    while (true);
  }

  // Disable watchdog
  WDT_Disable(WDT);

  // Initialize C library
  __libc_init_array();

  // Disable pull-up on every pin
  for (int i = 0; i < PINS_COUNT; i++)
      digitalWrite(i, LOW);

  // Enable parallel access on PIO output data registers
  PIOA->PIO_OWER = 0xFFFFFFFF;
  PIOB->PIO_OWER = 0xFFFFFFFF;
  PIOC->PIO_OWER = 0xFFFFFFFF;
  PIOD->PIO_OWER = 0xFFFFFFFF;

  // Initialize Serial port U(S)ART pins
  PIO_Configure(
    g_APinDescription[PINS_UART].pPort,
    g_APinDescription[PINS_UART].ulPinType,
    g_APinDescription[PINS_UART].ulPin,
    g_APinDescription[PINS_UART].ulPinConfiguration);
  digitalWrite(0, HIGH); // Enable pullup for RX0
  PIO_Configure(
    g_APinDescription[PINS_USART0].pPort,
    g_APinDescription[PINS_USART0].ulPinType,
    g_APinDescription[PINS_USART0].ulPin,
    g_APinDescription[PINS_USART0].ulPinConfiguration);
  PIO_Configure(
    g_APinDescription[PINS_USART1].pPort,
    g_APinDescription[PINS_USART1].ulPinType,
    g_APinDescription[PINS_USART1].ulPin,
    g_APinDescription[PINS_USART1].ulPinConfiguration);
  PIO_Configure(
    g_APinDescription[PINS_USART3].pPort,
    g_APinDescription[PINS_USART3].ulPinType,
    g_APinDescription[PINS_USART3].ulPin,
    g_APinDescription[PINS_USART3].ulPinConfiguration);

  // Initialize USB pins
  PIO_Configure(
    g_APinDescription[PINS_USB].pPort,
    g_APinDescription[PINS_USB].ulPinType,
    g_APinDescription[PINS_USB].ulPin,
    g_APinDescription[PINS_USB].ulPinConfiguration);

  // Initialize CAN pins
 /* PIO_Configure(
    g_APinDescription[PINS_CAN0].pPort,
    g_APinDescription[PINS_CAN0].ulPinType,
    g_APinDescription[PINS_CAN0].ulPin,
    g_APinDescription[PINS_CAN0].ulPinConfiguration);
  PIO_Configure(
    g_APinDescription[PINS_CAN1].pPort,
    g_APinDescription[PINS_CAN1].ulPinType,
    g_APinDescription[PINS_CAN1].ulPin,
    g_APinDescription[PINS_CAN1].ulPinConfiguration); */

  // Initialize Analog Controller
  pmc_enable_periph_clk(ID_ADC);
  adc_init(ADC, SystemCoreClock, ADC_FREQ_MAX, ADC_STARTUP_FAST);
  adc_configure_timing(ADC, 0, ADC_SETTLING_TIME_3, 1);
  adc_configure_trigger(ADC, ADC_TRIG_SW, 0); // Disable hardware trigger.
  adc_disable_interrupt(ADC, 0xFFFFFFFF); // Disable all ADC interrupts.
  adc_disable_all_channel(ADC);

  // Initialize analogOutput module
  analogOutputInit();
}
示例#12
0
void init( void )
{
    SystemInit();

    // Set Systick to 1ms interval
    if (SysTick_Config(SystemCoreClock / 1000))
    {
        // Capture error
        while (true);
    }

    // Disable watchdog
    WDT_Disable(WDT);

    // Initialize C library
    __libc_init_array();

    // Disable pull-up on every pin
    for (uint i = 0u; i < PINS_COUNT; i++)
        digitalWrite(i, LOW);

    // Enable parallel access on PIO output data registers
    PIOA->PIO_OWER = 0xFFFFFFFF;
    PIOB->PIO_OWER = 0xFFFFFFFF;
    //PIOC->PIO_OWER = 0xFFFFFFFF;
    //PIOD->PIO_OWER = 0xFFFFFFFF;


    //turn off ERASE and JTAG pins
    MATRIX->CCFG_SYSIO = CCFG_SYSIO_SYSIO12 | CCFG_SYSIO_SYSIO7 | CCFG_SYSIO_SYSIO6 | CCFG_SYSIO_SYSIO5 | CCFG_SYSIO_SYSIO4;

// Initialize Serial port UART pins
    PIO_Configure(
        g_APinDescription[PINS_USART0].pPort,
        g_APinDescription[PINS_USART0].ulPinType,
        g_APinDescription[PINS_USART0].ulPin,
        g_APinDescription[PINS_USART0].ulPinConfiguration);
    digitalWrite(0u, HIGH); // Enable pullup for RX0

    // Initialize Serial port USART pins
    // Pins are disconnected from PIO controller and hooked to the peripheral.
    // Currently PIO_Configure always enables the pullup resistor for peripherals. This appears to be a bug, as it is not written correctly for that purpose, but has that affect.
    PIO_Configure(
        g_APinDescription[PINS_UART1].pPort,
        g_APinDescription[PINS_UART1].ulPinType,
        g_APinDescription[PINS_UART1].ulPin,
        g_APinDescription[PINS_UART1].ulPinConfiguration);

    PIO_Configure(
        g_APinDescription[B1].pPort,
        g_APinDescription[B1].ulPinType,
        g_APinDescription[B1].ulPin,
        g_APinDescription[B1].ulPinConfiguration);

    /*
    TODO: wire up USB ID line and check out USB configuration
     // Initialize USB pins
     PIO_Configure(
       g_APinDescription[PINS_USB].pPort,
       g_APinDescription[PINS_USB].ulPinType,
       g_APinDescription[PINS_USB].ulPin,
       g_APinDescription[PINS_USB].ulPinConfiguration);


    //TODO: Initialize I2C pins for crypto IC
     PIO_Configure(
       g_APinDescription[PINS_SPI].pPort,
       g_APinDescription[PINS_SPI].ulPinType,
       g_APinDescription[PINS_SPI].ulPin,
       g_APinDescription[PINS_SPI].ulPinConfiguration);
    */

    // Initialize Analog Controller
    pmc_enable_periph_clk(ID_ADC);
    adc_init(ADC, SystemCoreClock, ADC_FREQ_MAX, ADC_STARTUP_FAST);
    adc_configure_timing(ADC, 0, ADC_SETTLING_TIME_3, 1);
    adc_configure_trigger(ADC, ADC_TRIG_SW, 0); // Disable hardware trigger.
    adc_disable_interrupt(ADC, 0xFFFFFFFF); // Disable all ADC interrupts.
    adc_disable_all_channel(ADC);

    // Initialize analogOutput module
    analogOutputInit();
}
示例#13
0
/**
 *  \brief adc12 Application entry point.
 *
 *  \return Unused (ANSI-C compatibility).
 */
int main(void)
{
	uint32_t i;
	uint8_t uc_key;
	/* Initialize the SAM system. */
	sysclk_init();
	board_init();

	configure_console();

	/* Output example information. */
	puts(STRING_HEADER);

	puts("Configure system tick to get 1ms tick period.\r");
	if (SysTick_Config(sysclk_get_cpu_hz() / 1000)) {
		puts("-F- Systick configuration error\r");
		while (1);
	}

	/* Set default ADC test mode. */
	memset((void *)&g_adc_test_mode, 0, sizeof(g_adc_test_mode));
	g_adc_test_mode.uc_trigger_mode = TRIGGER_MODE_SOFTWARE;
	g_adc_test_mode.uc_pdc_en = 1;
	g_adc_test_mode.uc_sequence_en = 0;
	g_adc_test_mode.uc_gain_en = 0;
	g_adc_test_mode.uc_offset_en = 0;

	display_menu();
	start_adc();

	puts("Press any key to display configuration menu.\r");
	while (1) {
		/* ADC software trigger per 1s */
		if (g_adc_test_mode.uc_trigger_mode == TRIGGER_MODE_SOFTWARE) {
			mdelay(1000);
#if SAM3S || SAM3N || SAM3XA || SAM4S || SAM4C
			adc_start(ADC);
#elif SAM3U
#ifdef ADC_12B
			adc12b_start(ADC12B);
#else
			adc_start(ADC);
#endif
#endif
		}

		/* Check if the user enters a key. */
		if (!uart_read(CONSOLE_UART, &uc_key)) {
#if SAM3S || SAM3N || SAM3XA || SAM4S || SAM4C
			adc_disable_interrupt(ADC, 0xFFFFFFFF);	/* Disable all adc interrupt. */
#elif SAM3U
#ifdef ADC_12B
			adc12b_disable_interrupt(ADC12B, 0xFFFFFFFF);	/* Disable all adc interrupt. */
#else
			adc_disable_interrupt(ADC, 0xFFFFFFFF);	/* Disable all adc interrupt. */
#endif
#endif
			tc_start(TC0, 0);	/* Stop the Timer. */
#if SAM3S || SAM3U || SAM3XA || SAM4S
			pwm_channel_disable(PWM, 0);
#endif
			display_menu();
			set_adc_test_mode();
			start_adc();
			puts("Press any key to display configuration menu.\r");
		}

		/* Check if ADC sample is done. */
		if (g_adc_sample_data.us_done == ADC_DONE_MASK) {
			for (i = 0; i < NUM_CHANNELS; i++) {
				printf("CH%02d: %04d mv.    ",
						(int)g_adc_sample_data.uc_ch_num[i],
						(int)(g_adc_sample_data.
								us_value[i] *
								VOLT_REF /
								MAX_DIGITAL));
			}
			puts("\r");
			g_adc_sample_data.us_done = 0;
		}
	}
}
示例#14
0
文件: demo.c 项目: thegeek82000/asf
/**
 * \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;
	}
}
示例#15
0
/**
 * \brief Example entry point.
 *
 * \return Unused (ANSI-C compatibility).
 */
int main(void)
{
	uint8_t c_choice;
	int16_t s_adc_value;
	int16_t s_dac_value;
	int16_t s_threshold = 0;
	float f_dac_data;
	uint32_t ul_dac_data;

	/* Initialize the SAM system. */
	sysclk_init();
	board_init();

	configure_console();

	/* Output example information. */
	puts(STRING_HEADER);

	/* Initialize threshold. */
	gs_us_low_threshold = 500;
	gs_us_high_threshold = 2000;

	struct adc_config adc_cfg = {
		/* System clock division factor is 16 */
		.prescal = ADC_PRESCAL_DIV16,
		/* The APB clock is used */
		.clksel = ADC_CLKSEL_APBCLK,
		/* Max speed is 150K */
		.speed = ADC_SPEED_150K,
		/* ADC Reference voltage is 0.625*VCC */
		.refsel = ADC_REFSEL_1,
		/* Enables the Startup time */
		.start_up = CONFIG_ADC_STARTUP
	};
	struct adc_seq_config adc_seq_cfg = {
		/* Select Vref for shift cycle */
		.zoomrange = ADC_ZOOMRANGE_0,
		/* Pad Ground */
		.muxneg = ADC_MUXNEG_1,
		/* DAC Internal */
		.muxpos = ADC_MUXPOS_3,
		/* Enables the internal voltage sources */
		.internal = ADC_INTERNAL_3,
		/* Disables the ADC gain error reduction */
		.gcomp = ADC_GCOMP_DIS,
		/* Disables the HWLA mode */
		.hwla = ADC_HWLA_DIS,
		/* 12-bits resolution */
		.res = ADC_RES_12_BIT,
		/* Enables the single-ended mode */
		.bipolar = ADC_BIPOLAR_SINGLEENDED
	};
	struct adc_ch_config adc_ch_cfg = {
		.seq_cfg = &adc_seq_cfg,
		/* Internal Timer Max Counter */
		.internal_timer_max_count = 60,
		/* Window monitor mode is off */
		.window_mode = ADC_WM_MODE_3,
		/* The equivalent voltage value is 500 * VOLT_REF / 4095 = 251mv. */
		.low_threshold = gs_us_low_threshold,
		/* The equivalent voltage value is 2000 * VOLT_REF / 4095 = 1002mv. */
		.high_threshold = gs_us_high_threshold,
	};

	start_dac();

	if(adc_init(&g_adc_inst, ADCIFE, &adc_cfg) != STATUS_OK) {
		puts("-F- ADC Init Fail!\n\r");
		while(1);
	}
	if(adc_enable(&g_adc_inst) != STATUS_OK) {
		puts("-F- ADC Enable Fail!\n\r");
		while(1);
	}
	adc_ch_set_config(&g_adc_inst, &adc_ch_cfg);
	adc_configure_trigger(&g_adc_inst, ADC_TRIG_CON);
	adc_configure_gain(&g_adc_inst, ADC_GAIN_1X);
	adc_set_callback(&g_adc_inst, ADC_WINDOW_MONITOR, adcife_wm_handler,
			ADCIFE_IRQn, 1);

	/* Display main menu. */
	display_menu();

	while (1) {

		scanf("%c", (char *)&c_choice);
		printf("%c\r\n", c_choice);
		switch (c_choice) {
		case '0':
			adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			printf("DAC output is set to(mv) from 0mv to %dmv: ",
					(int32_t)VOLT_REF);
			s_dac_value = get_voltage();
			puts("\r");
			f_dac_data = (float)s_dac_value * DACC_MAX_DATA / VDDANA;
			ul_dac_data = f_to_int(f_dac_data);
			if (s_dac_value >= 0) {
				dacc_write_conversion_data(DACC, ul_dac_data);
			}
			delay_ms(100);
			adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
			adc_enable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			break;

		case '1':
			adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			printf("Low threshold is set to(mv) from 0mv to %dmv: ",
					(int32_t)VOLT_REF);
			s_threshold = get_voltage();
			puts("\r");
			if (s_threshold >= 0) {
				s_adc_value = s_threshold * MAX_DIGITAL /
						VOLT_REF;
				adc_configure_wm_threshold(&g_adc_inst,
						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);
			}
			adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
			adc_enable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			break;

		case '2':
			adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			printf("High threshold is set to(mv)from 0mv to %dmv:",
					(int32_t)VOLT_REF);
			s_threshold = get_voltage();
			puts("\r");
			if (s_threshold >= 0) {
				s_adc_value = s_threshold * MAX_DIGITAL /
						VOLT_REF;
				adc_configure_wm_threshold(&g_adc_inst,
						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);
			}
			adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
			adc_enable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			break;

		case '3':
			adc_disable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			puts("-a. Above low threshold.\n\r"
					"-b. Below 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_wm_mode();
			adc_configure_wm_mode(&g_adc_inst, c_choice);
			printf("Comparison mode is %c.\n\r", 'a' + c_choice - 1);
			adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
			adc_enable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			break;

		case 'm':
			display_menu();
			break;

		case 'i':
			display_info();
			adc_clear_status(&g_adc_inst, ADCIFE_SCR_WM);
			adc_enable_interrupt(&g_adc_inst, ADC_WINDOW_MONITOR);
			break;
		}
		puts("Press \'m\' or \'M\' to display the main menu again!\r");
	}
}