我2天前买了北欧评估板。我一直在搜索论坛,以启用和测试电池的电压水平,并通过UART进行监控。经过几个小时的追踪和错误。我设法将两个北欧的例子合二为一,但我无法看到我的UART上的电压电平。你们能为我提供一个使用UART作为输出的ADC示例。我会做其余的事。
感谢
编辑:
#include "simple_uart.h"
#include <stdbool.h>
#include <stdio.h>
#include <stdint.h>
#include "nrf.h"
#include "nrf_gpio.h"
#include "boards.h"
#include "nrf_delay.h"
//#define ENABLE_LOOPBACK_TEST /**< if defined, then this example will be a loopback test, which means that TX should be connected to RX to get data loopback. */
#define ERROR_PIN (LED_0) /**< gpio pin number to show error if loopback is enabled. */
#define MAX_TEST_DATA_BYTES (15U) /**< max number of test bytes to be used for tx and rx. */
#define LFCLK_FREQUENCY (32768UL) /*!< LFCLK frequency in Hertz, constant */
#define RTC_FREQUENCY (10UL) /*!< required RTC working clock RTC_FREQUENCY Hertz. Changable */
#define COUNTER_PRESCALER ((LFCLK_FREQUENCY/RTC_FREQUENCY) - 1) /* f = LFCLK/(prescaler + 1) */
/** Configures port 1 as output
*/
static void gpio_config(void)
{
nrf_gpio_range_cfg_output(8, 15);
nrf_gpio_port_write(NRF_GPIO_PORT_SELECT_PORT1, 0);
}
static void hfclk_config(void)
{
/* Start 16 MHz crystal oscillator */
NRF_CLOCK->EVENTS_HFCLKSTARTED = 0;
NRF_CLOCK->TASKS_HFCLKSTART = 1;
/* Wait for the external oscillator to start up */
while (NRF_CLOCK->EVENTS_HFCLKSTARTED == 0) {}
}
static void lfclk_config(void)
{
NRF_CLOCK->LFCLKSRC = (CLOCK_LFCLKSRC_SRC_Xtal << CLOCK_LFCLKSRC_SRC_Pos);
NRF_CLOCK->EVENTS_LFCLKSTARTED = 0;
NRF_CLOCK->TASKS_LFCLKSTART = 1;
// Wait for the low frequency clock to start
while (NRF_CLOCK->EVENTS_LFCLKSTARTED == 0) {}
NRF_CLOCK->EVENTS_LFCLKSTARTED = 0;
}
/** Configure and start RTC
*/
static void rtc_config(void)
{
NRF_RTC0->PRESCALER = COUNTER_PRESCALER; // Set prescaler to a TICK of RTC_FREQUENCY
NRF_RTC0->EVTENSET = RTC_EVTENSET_TICK_Msk; // Enable TICK event
NRF_RTC0->TASKS_START = 1; // Start RTC0
}
static void ppi_init(void)
{
// Configure PPI channel 0 to start ADC task
NRF_PPI->CH[0].EEP = (uint32_t)&NRF_RTC0->EVENTS_TICK;
NRF_PPI->CH[0].TEP = (uint32_t)&NRF_ADC->TASKS_START;
// Enable PPI channel 0
NRF_PPI->CHEN = (PPI_CHEN_CH0_Enabled << PPI_CHEN_CH0_Pos);
}
/** Configures and enables the ADC
*/
void ADC_init(void)
{
/* Enable interrupt on ADC sample ready event*/
NRF_ADC->INTENSET = ADC_INTENSET_END_Msk;
NVIC_EnableIRQ(ADC_IRQn);
// config ADC
NRF_ADC->CONFIG = (ADC_CONFIG_EXTREFSEL_None << ADC_CONFIG_EXTREFSEL_Pos) /* Bits 17..16 : ADC external reference pin selection. */
| (ADC_CONFIG_PSEL_AnalogInput6 << ADC_CONFIG_PSEL_Pos) /*!< Use analog input 6 as analog input (P0.05). */
| (ADC_CONFIG_REFSEL_VBG << ADC_CONFIG_REFSEL_Pos) /*!< Use internal 1.2V bandgap voltage as reference for conversion. */
| (ADC_CONFIG_INPSEL_AnalogInputNoPrescaling << ADC_CONFIG_INPSEL_Pos) /*!< Analog input specified by PSEL with no prescaling used as input for the conversion. */
| (ADC_CONFIG_RES_8bit << ADC_CONFIG_RES_Pos); /*!< 8bit ADC resolution. */
/* Enable ADC*/
NRF_ADC->ENABLE = ADC_ENABLE_ENABLE_Enabled;
}
/* Interrupt handler for ADC data ready event. It will be executed when ADC sampling is complete */
void ADC_IRQHandler(void)
{
/* Clear dataready event */
NRF_ADC->EVENTS_END = 0;
/* Write ADC result to port 1 */
//simple_uart_putstring((const uint8_t *) NRF_ADC->RESULT);
//nrf_gpio_port_write(NRF_GPIO_PORT_SELECT_PORT1, NRF_ADC->RESULT);
}
#ifndef ENABLE_LOOPBACK_TEST
/** @brief Function for sending 'Exit!' string to UART.
*
* @note Execution is blocked until UART peripheral detects all characters have been sent.
*/
static __INLINE void uart_quit()
{
simple_uart_putstring((const uint8_t *)" \n\rExit!\n\r");
}
/** @brief Function for sending 'Start:' string to UART.
* @details Execution is blocked until UART peripheral detects all characters have been sent.
*/
static __INLINE void uart_start()
{
simple_uart_putstring((const uint8_t *)" \n\rStart: ");
}
#else
/** @brief Function for setting the @ref ERROR_PIN high, and then enter an infinite loop.
* This function is called if any of the nRF6350 functions fail.
*/
static void show_error(void)
{
nrf_gpio_pin_write(ERROR_PIN, 1);
while(true)
{
// Do nothing.
}
}
/** @brief Function for testing UART loop back.
* @details Transmitts one character at a time to check if the data received from the loopback is same as the transmitted data.
* @note @ref TX_PIN_NUMBER must be connected to @ref RX_PIN_NUMBER)
*/
static void uart_loopback_test()
{
uint8_t *tx_data = (uint8_t *)("\n\rLOOPBACK_TEST");
uint8_t rx_data;
// Start sending one byte and see if you get the same
for (uint32_t i = 0; i < MAX_TEST_DATA_BYTES; i++)
{
bool status;
simple_uart_put(tx_data[i]);
status = simple_uart_get_with_timeout(2, &rx_data);
if ((rx_data != tx_data[i]) || (!status))
{
show_error();
}
}
return;
}
#endif
/**
* @brief Function for main application entry.
*/
int main(void)
{
char buffer[20U];
simple_uart_config(RTS_PIN_NUMBER, TX_PIN_NUMBER, CTS_PIN_NUMBER, RX_PIN_NUMBER, HWFC);
nrf_gpio_cfg_output(ERROR_PIN); // ERROR_PIN configured as output.
nrf_gpio_cfg_output(LED_0);
nrf_gpio_pin_clear(LED_0);
gpio_config();
lfclk_config();
rtc_config();
ppi_init();
ADC_init();
#ifndef ENABLE_LOOPBACK_TEST
uart_start();
while (true)
{
uint8_t cr = simple_uart_get();
simple_uart_put(cr);
uint8_t adc_result = (float) NRF_ADC->RESULT;
switch(cr)
{
case ('q'):
uart_quit();
while(true)
{
//Do nothing
}
break;
case ('1'):
{
nrf_gpio_pin_set(LED_0);
sprintf (buffer, "value: %05u", adc_result);
simple_uart_putstring((uint8_t*)buffer);
}
break;
case ('2'):
{
nrf_gpio_pin_clear(LED_0);
}
break;
default:
{
}
}
}
#else
// This part of the example is just for testing the loopback .
while(true)
{
uart_loopback_test();
}
#endif
}
/** @} */