1 ADC 相关的数据结构和 API
1.1 概论
OpenCPU 支持两个模拟输入引脚可用于检测外部电压。请参照管脚定义和ADC 硬件特性。 可以检测的电压范围可分四挡,分别是 1V,2V,3V。本文介绍的数据结构和 API 可以参考 SDK 中 Zyf_adc.h 文件。
1.2 用法
直接调用 ZYF_AdcRead 接口即可读取 ADC 值,为确认读取 ADC 可靠性,建议读取多次,并做平均处理。
1.3 ADC 相关 API
1.3.1 ZYF_AdcRead 取 读取 ADC 值
函数原型
int32_t ZYF_AdcRead(uint8_t adc_channel, uint8_t adc_scale)
参数
adc_channel:
[输入] 取样通道,ADC 引脚为 AUXIN4,通道 ID 值为 4
adc_scale:
[输入] 量程
返回结果
ZYF_RET_ERR_CHANNEL_OUTRANGE,ADC 通道超出范围。
ZYF_RET_ERR FATAL,读取 ADC 值时出现一些致命错误。
其他,ADC 采样结果。它是一个 10 位 A / D 转换器,输入电压范围为 0〜2800mV。
2 ADC 例程介绍
本章节主要介绍如何在 SDK 中使用 example_adc.c 单独测试 adc 功能。
编译方法:.\examples\build\对应的.bat 文件双击执行或打开就可以编译。
生成文件:.\out\对应目录\hex\M601_example_**.pac
adc 的例程主要是通过创建定时器,在该定时器中根据设置的时间间隔不断
的去读取 adc 采样值。ADC 采样结果。它是一个 10 位 A / D 转换器,输入电压
范围为 0〜2800mV。
#include <stdint.h>
#include "zyf_trace.h"
#include "zyf_adc.h"
#include "zyf_timer.h"
#include "zyf_app.h"
#include "zyf_uart.h"
#include "zyf_thread.h"
#define TIMER_INTERVAL 1000 //units ms
typedef struct {
ZYF_Timer_t *ptTimer;
uint32_t wParam;
uint32_t runtimes;
} AppTimer_t;
static AppTimer_t s_tTimer;
static Uart_Param_t g_uart1param;
static void ZYF_TimerCallback(void *pvArg)
{
AppTimer_t *ptAppTimer = (AppTimer_t *)pvArg;
int32_t value = -1;
static uint32_t runcnt = 0;
runcnt++;
if (ptAppTimer != NULL)
{
ZYF_LOG("timer run times %d.",runcnt);
ZYF_StartTimer(ptAppTimer->ptTimer, TIMER_INTERVAL);
}
if (runcnt > ptAppTimer->runtimes && ZYF_StopTimer(ptAppTimer->ptTimer) < 0)
{
runcnt = 0;
ZYF_LOG("Failed to delete timer");
}
value = ZYF_AdcRead(ZYF_ADC_CHANNEL_0, ZYF_ADC_SCALE_5V000);
ZYF_LOG("ADC0: %d", value);
value = ZYF_AdcRead(ZYF_ADC_CHANNEL_1, ZYF_ADC_SCALE_5V000);
ZYF_LOG("ADC1: %d", value);
}
void ZYF_ADCTimerInit(void)
{
s_tTimer.runtimes = 500;
s_tTimer.ptTimer = ZYF_CreateTimer(ZYF_TimerCallback, (void *)&s_tTimer);
if (s_tTimer.ptTimer != NULL)
{
ZYF_StartTimer(s_tTimer.ptTimer, TIMER_INTERVAL);
}
}
void ADCThread_Example(void * Param)
{
ZYF_MsgQ_t *ptMsg;
ZYF_AppMsg_t tMsg;
int iRet = -1;
ptMsg = ZYF_MsgQCreate(10, sizeof(ZYF_AppMsg_t));
ZYF_LOG("thread enter!");
ZYF_ADCTimerInit();
while (1) {
ZYF_LOG("in while.");
iRet = ZYF_MsgQGet(ptMsg, (void *)&tMsg);
if (iRet < 0) {
ZYF_LOG("Failed to get msg");
ZYF_ThreadSleep(1000);
}
}
}
void UartWriteCallBack(void* Param) // general com
{
Uart_Param_t *uartparam = (Uart_Param_t *)Param;
if(Param == NULL)
{
return;
}
ZYF_UartWrite(uartparam->port,(uint8_t *)"UartWrite succeed\r\n",strlen("UartWrite succeed\r\n"));
ZYF_UartWriteCallbackSwitch(uartparam->port,false);
}
void UartReadCallBack(void* Param) //
{
uint32_t recvlen = 0;
Uart_Param_t *uartparam = (Uart_Param_t *)Param;
ZYF_LOG("Uart%d recv",uartparam->port);
while(ZYF_UartRead(uartparam->port, &(uartparam->uartbuf[recvlen]), 1))
{
ZYF_LOG("recv :%02x",uartparam->uartbuf[recvlen]);
recvlen++;
}
ZYF_UartWrite(uartparam->port,uartparam->uartbuf,recvlen);
ZYF_UartWriteCallbackSwitch(uartparam->port,true);
}
static void AppUartInit(void)
{
int32_t ret;
g_uart1param.port = DEBUG_PORT;
ZYF_UartRegister(g_uart1param.port, UartReadCallBack,&g_uart1param);
ZYF_UartWriteCbRegister(g_uart1param.port,UartWriteCallBack,&g_uart1param);
ZYF_UartOpen(g_uart1param.port, 115200, ZYF_FC_NONE);
ZYF_LOG("AppUartInit");
return;
}
static void prvInvokeGlobalCtors(void)
{
extern void (*__init_array_start[])();
extern void (*__init_array_end[])();
size_t count = __init_array_end - __init_array_start;
for (size_t i = 0; i < count; ++i)
__init_array_start[i]();
}
int appimg_enter(void *param)
{
AppUartInit();
ZYF_LOG("application image enter, param 0x%x", param);
prvInvokeGlobalCtors();
ZYF_ThreadCreate("UartThread_Example", ADCThread_Example, NULL, ZYF_PRIORITY_HIGH, 10*1024);
return 0;
}
void appimg_exit(void)
{
OSI_LOGI(0, "application image exit");
}