外设接口开发指南
引言
移远通信FC41D、FCMxx0D和FLMx40D模块支持QuecOpen®方案;QuecOpen®是基于RTOS的嵌入式开发平台,可简化IoT应用的软件设计和开发过程。有关QuecOpen®的详细信息,请参考 快速入门指南。
本文档适用于SDK构建环境的QuecOpen®方案,主要介绍在QuecOpen®方案下,如何使用FC41D、FCMxx0D和FLMx40D模块所支持的GPIO、UART、SPI、I2C、ADC和PWM API进行对应外设接口开发。
备注
- 模块当前支持两路UART,通过UART接收的数据默认采用FIFO方式缓存。
- SPI模式下主设备最大时钟频率为30 MHz,从设备最大时钟频率为10 MHz。
适用模块
适用模块:
| 模块系列 | 模块 |
|---|---|
| FC41D | |
| FCMxx0D | FCM100D |
| FCM740D | |
| FLMx40D | FLM040D |
| FLM140D | |
| FLM240D | |
| FLM340D |
GPIO API
头文件
GPIO API的头文件为ql_gpio.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_gpio_init
该函数用于初始化GPIO。
函数原型:
ql_gpio_errcode_e ql_gpio_init(ql_gpio_num_e gpio_num, ql_gpio_mode_e mode)
参数:
gpio_num:[In] GPIO引脚编号;详见ql_gpio_num_e。
mode:[In] GPIO模式;详见ql_gpio_mode_e。
返回值:
结果码;详见ql_gpio_errcode_e。
ql_gpio_num_e
GPIO编号信息的枚举定义如下:
typedef enum
{
QL_GPIO0 = 0,
QL_GPIO1,
QL_GPIO6 = 6,
QL_GPIO7,
QL_GPIO8,
QL_GPIO9,
QL_GPIO10,
QL_GPIO11,
QL_GPIO14 = 14,
QL_GPIO15,
QL_GPIO16,
QL_GPIO17,
QL_GPIO20 = 20,
QL_GPIO21,
QL_GPIO22,
QL_GPIO23,
QL_GPIO24,
QL_GPIO26 = 26,
QL_GPIO28 = 28,
} ql_gpio_num_e
成员:
| 成员 | 描述 |
|---|---|
QL_GPIO0 |
GPIO0 |
QL_GPIO1 |
GPIO1 |
QL_GPIO6 |
GPIO6 |
QL_GPIO7 |
GPIO7 |
QL_GPIO8 |
GPIO8 |
QL_GPIO9 |
GPIO9 |
QL_GPIO10 |
GPIO10 |
QL_GPIO11 |
GPIO11 |
QL_GPIO14 |
GPIO14 |
QL_GPIO15 |
GPIO15 |
QL_GPIO16 |
GPIO16 |
QL_GPIO17 |
GPIO17 |
QL_GPIO20 |
GPIO20 |
QL_GPIO21 |
GPIO21 |
QL_GPIO22 |
GPIO22 |
QL_GPIO23 |
GPIO23 |
QL_GPIO24 |
GPIO24 |
QL_GPIO26 |
GPIO26 |
QL_GPIO28 |
GPIO28 |
ql_gpio_mode_e
GPIO模式的枚举定义如下:
typedef enum
{
QL_GMODE_INPUT_PULLDOWN = 0,
QL_GMODE_OUTPUT,
QL_GMODE_SECOND_FUNC,
QL_GMODE_INPUT_PULLUP,
QL_GMODE_INPUT,
QL_GMODE_SECOND_FUNC_PULL_UP,//Special for uart1
QL_GMODE_OUTPUT_PULLUP,
QL_GMODE_SET_HIGH_IMPENDANCE,
QL_GMODE_DEEP_PS,
}ql_gpio_mode_e
成员:
| 成员 | 描述 |
|---|---|
QL_GMODE_INPUT_PULLDOWN |
下拉输入 |
QL_GMODE_OUTPUT |
推挽输出 |
QL_GMODE_SECOND_FUNC |
引脚第二功能 |
QL_GMODE_INPUT_PULLUP |
上拉输入 |
QL_GMODE_INPUT |
浮空输入 |
QL_GMODE_SECOND_FUNC_PULL_UP |
引脚第二功能上拉(仅UART1可用) |
QL_GMODE_OUTPUT_PULLUP |
上拉输出(暂不支持) |
QL_GMODE_SET_HIGH_IMPENDANCE |
高阻态 |
QL_GMODE_DEEP_PS |
高阻态 |
ql_gpio_errcode_e
GPIO API相关的结果码的枚举定义如下:
typedef enum
{
QL_GPIO_SUCCESS = 0,
QL_GPIO_EXECUTE_ERR,
QL_GPIO_INVALID_PARAM_ERR,
} ql_gpio_errcode_e
成员:
| 成员 | 描述 |
|---|---|
QL_GPIO_SUCCESS |
执行成功 |
QL_GPIO_EXECUTE_ERR |
执行失败 |
QL_GPIO_INVALID_PARAM_ERR |
无效参数 |
ql_gpio_set_level
该函数用于设置指定GPIO的引脚电平,仅对已经配置为输出模式的引脚有效。
函数原型:
ql_gpio_errcode_e ql_gpio_set_level(ql_gpio_num_e gpio_num, ql_gpio_output_level_e output_level)
参数:
gpio_num:[In] GPIO引脚编号;详见ql_gpio_num_e。
output_level:[In] 引脚电平设置,只针对输出引脚;详见ql_gpio_output_level_e。
返回值:
结果码;详见ql_gpio_errcode_e。
ql_gpio_output_level_e
GPIO输出电平的枚举定义如下:
typedef enum
{
QL_GPIO_OUTPUT_LOW =0,
QL_GPIO_OUTPUT_HIGH,
}ql_gpio_output_level_e
成员:
| 成员 | 描述 |
|---|---|
QL_GPIO_OUTPUT_LOW |
低电平 |
QL_GPIO_OUTPUT_HIGH |
高电平 |
ql_gpio_set_level_reverse
该函数用于翻转输出引脚的电平,仅对已经配置为输出模式的引脚有效。
函数原型:
ql_gpio_errcode_e ql_gpio_set_level_reverse(ql_gpio_num_e gpio_num)
参数:
gpio_num:
[In] GPIO引脚编号;详见ql_gpio_num_e。
返回值:
结果码;详见ql_gpio_errcode_e。
ql_gpio_get_level
该函数用于获取指定GPIO的引脚电平。
函数原型:
ql_gpio_errcode_e ql_gpio_get_level(ql_gpio_num_e gpio_num,UINT32 *input_level)
参数:
gpio_num:[In] GPIO引脚编号;详见ql_gpio_num_e。
input_level:[Out] 引脚电平值。
返回值:
结果码;详见ql_gpio_errcode_e。
ql_gpio_int_init
该函数用于初始化和使能GPIO中断。
函数原型:
ql_gpio_errcode_e ql_gpio_int_init(ql_gpio_num_e gpio_num,ql_gpio_irq_trigger_e trigger,ql_gpio_irq_callback calback)
参数:
gpio_num:[In] GPIO引脚编号;详见ql_gpio_num_e。
trigger:[In] GPIO中断触发方式;详见ql_gpio_irq_trigger_e。
calback:[In] GPIO中断回调函数;详见ql_gpio_irq_callback。
返回值:
结果码;详见ql_gpio_errcode_e。
ql_gpio_irq_trigger_e
GPIO中断触发方式的枚举定义如下:
typedef enum
{
QL_IRQ_TRIGGER_LOW_LEVEL = 0x0,
QL_IRQ_TRIGGER_HGIH_LEVEL,
QL_IRQ_TRIGGER_RISING_EDGE,
QL_IRQ_TRIGGER_FALLING_EDGE,
} ql_gpio_irq_trigger_e
成员:
| 成员 | 描述 |
|---|---|
QL_IRQ_TRIGGER_LOW_LEVEL |
低电平中断 |
QL_IRQ_TRIGGER_HGIH_LEVEL |
高电平中断 |
QL_IRQ_TRIGGER_RISING_EDGE |
上升沿中断 |
QL_IRQ_TRIGGER_FALLING_EDGE |
下降沿中断 |
ql_gpio_irq_callback
该函数为GPIO中断的回调函数。
函数原型:
typedef void (*ql_gpio_irq_callback)( void *arg )
参数:
arg:
[In] 触发中断的引脚。
ql_gpio_int_disable
该函数用于关闭配置的GPIO中断。
函数原型:
ql_gpio_errcode_e ql_gpio_int_disable(ql_gpio_num_e gpio_num)
参数:
gpio_num:
[In] GPIO引脚编号;详见ql_gpio_num_e。
返回值:
结果码;详见ql_gpio_errcode_e。
GPIO开发流程
本章节主要介绍在应用程序中如何使用上述的GPIO API,并进行简单的调试,示例中使用QL_GPIO6进行测试。
操作GPIO
模块SDK代码中提供了操作GPIO的示例,示例程序在ql_application/quectel_demo目录下ql_gpio_demo.c文件中。相关函数解析如下:
ql_gpio_demo_thread_creat():创建GPIO任务,运行示例程序需要调用该函数。ql_gpio_demo_thread():任务的执行函数,实现了GPIO功能的初始化、输出电平和中断触发。
若需运行该示例程序,打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_GPIO,ql_gpio_demo_thread_creat()和ql_gpio_demo_thread()会自动被调用以创建测试任务。


GPIO功能调试
用户需使用安装模块的开发板(以FC41D TE-B为例)进行GPIO功能调试,步骤如下:
步骤一:调试时先参照操作GPIO运行GPIO示例程序。
步骤二:重新编译固件版本并将其烧录至模块。
步骤三:重启模块。
步骤四:打开串口2,通过串口2获取调试Log,信息如下图所示:
{width="4.3125in" height="0.625in"}
若调试过程中打印如下信息,则表示触发GPIO中断。

UART API
头文件
UART API的头文件为ql_uart.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_uart_set_dcbconfig
该函数用于设置串口属性,设置后重新打开串口才能生效。
函数原型:
ql_uart_errcode_e ql_uart_set_dcbconfig(ql_uart_port_number_e port, ql_uart_config_s *dcb)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
dcb:[In] 串口属性配置,详见ql_uart_config_s。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_port_number_e
串口编号信息的枚举定义如下。当前仅支持2路物理串口。
typedef enum
{
QL_UART_PORT_1,
QL_UART_PORT_2,
}ql_uart_port_number_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_PORT_1 |
串口1 |
QL_UART_PORT_2 |
串口2 |
ql_uart_config_s
串口属性配置结构体定义如下:
typedef struct
{
ql_uart_baud_e baudrate;
ql_uart_databit_e data_bit;
ql_uart_stopbit_e stop_bit;
ql_uart_parityit_e parity_bit;
ql_uart_flowctrl_e flow_ctrl;
}ql_uart_config_s
参数:
| 类型 | 参数 | |
|---|---|---|
ql_uart_baud_e |
baudrate |
波特率,默认为115200 bps。详见ql_uart_baud_e |
ql_uart_databit_e |
data_bit |
数据位,默认为8位。详见ql_uart_databit_e |
ql_uart_stopbit_e |
stop_bit |
停止位,默认为1位。详见ql_uart_stopbit_e |
ql_uart_parityit_e |
parity_bit |
校验位,默认无校验。详见ql_uart_parityit_e |
ql_uart_flowctrl_e |
flow_ctrl |
流控,默认不开启。详见ql_uart_flowctrl_e |
ql_uart_baud_e
串口波特率枚举定义如下:
typedef enum
{
QL_UART_BAUD_1200 = 1200,
QL_UART_BAUD_2400 = 2400,
QL_UART_BAUD_4800 = 4800,
QL_UART_BAUD_9600 = 9600,
QL_UART_BAUD_14400 = 14400,
QL_UART_BAUD_19200 = 19200,
QL_UART_BAUD_28800 = 28800,
QL_UART_BAUD_33600 = 33600,
QL_UART_BAUD_38400 = 38400,
QL_UART_BAUD_57600 = 57600,
QL_UART_BAUD_115200 = 115200,
QL_UART_BAUD_230400 = 230400,
QL_UART_BAUD_460800 = 460800,
QL_UART_BAUD_921600 = 921600,
QL_UART_BAUD_1000000 = 1000000,
QL_UART_BAUD_2000000 = 2000000,
}ql_uart_baud_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_BAUD_1200 |
1200 bps |
QL_UART_BAUD_2400 |
2400 bps |
QL_UART_BAUD_4800 |
4800 bps |
QL_UART_BAUD_9600 |
9600 bps |
QL_UART_BAUD_14400 |
14400 bps |
QL_UART_BAUD_19200 |
19200 bps |
QL_UART_BAUD_28800 |
28800 bps |
QL_UART_BAUD_33600 |
33600 bps |
QL_UART_BAUD_38400 |
38400 bps |
QL_UART_BAUD_57600 |
57600 bps |
QL_UART_BAUD_115200 |
115200 bps |
QL_UART_BAUD_230400 |
230400 bps |
QL_UART_BAUD_460800 |
460800 bps |
QL_UART_BAUD_921600 |
921600 bps |
QL_UART_BAUD_1000000 |
1000000 bps |
QL_UART_BAUD_2000000 |
2000000 bps |
ql_uart_databit_e
串口数据位的枚举定义如下:
typedef enum
{
QL_UART_DATABIT_5 =0,
QL_UART_DATABIT_6,
QL_UART_DATABIT_7 ,
QL_UART_DATABIT_8 ,
}ql_uart_databit_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_DATABIT_5 |
5位 |
QL_UART_DATABIT_6 |
6位 |
QL_UART_DATABIT_7 |
7位 |
QL_UART_DATABIT_8 |
8位 |
ql_uart_stopbit_e
串口停止位枚举定义如下:
typedef enum
{
QL_UART_STOP_1 = 0,
QL_UART_STOP_2 ,
}ql_uart_stopbit_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_STOP_1 |
1位 |
QL_UART_STOP_2 |
2位 |
ql_uart_parityit_e
串口校验位枚举定义如下:
typedef enum
{
QL_UART_PARITY_NONE,
QL_UART_PARITY_ODD,
QL_UART_PARITY_EVEN,
}ql_uart_parityit_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_PARITY_NONE |
无校验 |
QL_UART_PARITY_ODD |
奇校验 |
QL_UART_PARITY_EVEN |
偶校验 |
ql_uart_flowctrl_e
串口流控枚举定义如下:
typedef enum
{
QL_FC_NONE = 0,
QL_FC_HW_CTS,
QL_FC_HW_RTS,
QL_FC_HW_RTS_CTS,
}ql_uart_flowctrl_e
成员:
| 成员 | 描述 |
|---|---|
QL_FC_NONE |
不开启流控 |
QL_FC_HW_CTS |
硬件CTS |
QL_FC_HW_RTS |
硬件RTS |
QL_FC_HW_RTS_CTS |
硬件CTS和RTS |
ql_uart_errcode_e
串口结果码枚举定义如下:
typedef enum
{
QL_UART_SUCCESS = 0,
QL_UART_EXECUTE_ERR ,
QL_UART_MEM_ADDR_NULL_ERR,
QL_UART_INVALID_PARAM_ERR,
QL_UART_NOT_OPEN_ERR ,
} ql_uart_errcode_e
成员:
| 成员 | 描述 |
|---|---|
QL_UART_SUCCESS |
执行成功 |
QL_UART_EXECUTE_ERR |
执行失败 |
QL_UART_MEM_ADDR_NULL_ERR |
参数地址:Null |
QL_UART_INVALID_PARAM_ERR |
无效参数 |
QL_UART_NOT_OPEN_ERR |
串口未打开 |
ql_uart_get_dcbconfig
该函数用于获取串口属性配置。
函数原型:
ql_uart_errcode_e ql_uart_get_dcbconfig(ql_uart_port_number_e port, ql_uart_config_s *dcb)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
dcb:[In] 串口属性配置;详见ql_uart_config_s。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_open
该函数用于打开串口。
函数原型:
ql_uart_errcode_e ql_uart_open(ql_uart_port_number_e port)
参数:
port:
[In] 串口编号;详见ql_uart_port_number_e。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_close
该函数用于关闭串口。
函数原型:
ql_uart_errcode_e ql_uart_close(ql_uart_port_number_e port)
参数:
port:
[In] 串口编号;详见ql_uart_port_number_e。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_write
该函数用于通过串口向模块写入数据。
函数原型:
int ql_uart_write(ql_uart_port_number_e port, unsigned char *data, unsigned int data_len)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
data:[In] 写入的数据。
data_len:[In] 写入的数据长度。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_read
该函数用于通过串口读取模块的数据。
函数原型:
int ql_uart_read(ql_uart_port_number_e port, unsigned char *data, unsigned int data_len)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
data:[Out] 读取的数据。
data_len:[In] 读取的数据长度。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_set_rx_cb
该函数用于注册串口接收数据中断事件的回调函数。
函数原型:
ql_uart_errcode_e ql_uart_set_rx_cb(ql_uart_port_number_e port, ql_uart_callback uart_cb)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
uart_cb:[In] 需要注册的回调函数;详见ql_uart_callback。
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_callback
该函数为串口中断的回调函数。
函数原型:
typedef void (*ql_uart_callback)(int uport, void *param);
参数:
uport:[In] 串口编号;详见ql_uart_port_number_e。
param:[In] 输入参数。
返回值:
无
ql_uart_set_tx_int
该函数用于设置数据发送完成的中断事件。
函数原型:
ql_uart_errcode_e ql_uart_set_tx_int(ql_uart_port_number_e port, unsigned int set)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
set:[In] 控制中断事件
1开启中断2关闭中断
返回值:
结果码;详见ql_uart_errcode_e。
ql_uart_set_tx_cb
该函数用于注册串口发送数据中断事件的回调函数。
函数原型:
ql_uart_errcode_e ql_uart_set_tx_cb(ql_uart_port_number_e port, ql_uart_callback uart_cb)
参数:
port:[In] 串口编号;详见ql_uart_port_number_e。
uart_cb:[In] 需要注册的回调函数;详见ql_uart_callback。
返回值:
结果码;详见ql_uart_errcode_e。
UART开发流程
本章节主要介绍在应用程序中如何使用上述的UART API,并进行简单的调试。本示例使用串口1进行测试。
操作串口
模块SDK代码中提供了操作UART的示例,示例程序在ql_application/quectel_demo目录下ql_uart_demo.c文件中。相关函数解析如下:
ql_uart_demo_thread_creat():该函数用于创建串口任务,运行示例程序需要调用该函数。ql_uart_demo_thread():该函数是任务的执行函数,简单实现了串口的初始化、发送数据和接收数据。
若需要运行该示例,则只需要打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_UART,ql_uart_demo_thread_creat()和ql_uart_demo_thread()会被自动调用来创建测试任务。如下图所示:



UART功能调试
用户需使用安装模块的开发板(以FC41D TE-B为例)进行UART功能调试,步骤如下:
步骤一:调试时先参照操作串口运行串口示例程序。
步骤二:重新编译固件版本并将其烧录至模块。
步骤三:重启模块。
步骤四:打开串口1进行测试,
步骤五:打开串口2,通过串口2获取调试Log,Log信息如下图所示:

此时串口1接收到数据,如下图所示:

串口接收数据测试成功后,用串口助手工具发送20个字节的数据给串口1。如下图所示:

此时,串口2打印信息如下:

对比图10中发送的数据和图11接收的数据信息,可以获知,串口功能测试成功。
SPI API
模块SPI采用DMA方式进行数据发送和接收。
头文件
SPI API的头文件为ql_spi.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_spi_init
该函数用于初始化SPI,需要在使用其他SPI API前调用。
函数原型:
ql_spi_errcode_e ql_spi_init(ql_spi_config_s spi_cfg,ql_spi_messag_s * spi_msg)
参数:
spi_cfg:[In] SPI配置;详见ql_spi_config_s。
spi_msg:[In] SPI发送或接收的数据;详见ql_spi_messag_s。
返回值:
结果码;详见ql_spi_errcode_e。
ql_spi_config_s
SPI配置信息结构体定义如下:
typedef struct
{
UINT32 spiclk;
ql_spi_cpol_pol_e cpol;
ql_spi_cpha_pol_e cpha;
ql_spi_transfer_mode_e transmode;
ql_spi_master_slave_mode_e masterorslave;
} ql_spi_config_s
参数:
| 类型 | 参数 | |
|---|---|---|
UINT32 |
spiclk |
SPI时钟频率,最大30 MHz |
ql_spi_cpol_pol_e |
cpol |
SPI时钟极性;详见ql_spi_cpol_pol_e。 |
ql_spi_cpha_pol_e |
cpha |
SPI时钟相位;详见ql_spi_cpha_pol_e。 |
ql_spi_transfer_mode_e |
transmode |
SPI发送模式;详见ql_spi_transfer_mode_e。 |
ql_spi_master_slave_mode_e |
masterorslave |
SPI主从机选择;详见ql_spi_master_slave_mode_e。 |
ql_spi_cpol_pol_e
SPI时钟极性枚举定义如下:
typedef enum
{
QL_SPI_CPOL_LOW = 0,
QL_SPI_CPOL_HIGH,
} ql_spi_cpol_pol_e
成员:
| 成员 | 描述 |
|---|---|
QL_SPI_CPOL_LOW |
SCK在空闲状态处于低电平 |
QL_SPI_CPOL_HIGH |
SCK在空闲状态处于高电平 |
ql_spi_cpha_pol_e
SPI时钟相位枚举定义如下:
typedef enum
{
QL_SPI_CPHA_1Edge,
QL_SPI_CPHA_2Edge,
}ql_spi_cpha_pol_e
成员:
| 成员 | 描述 |
|---|---|
QL_SPI_CPHA_1Edge |
在SCK周期的第一个边沿采样数据。 |
QL_SPI_CPHA_2Edge |
在SCK周期的第二个边沿采样数据。 |
ql_spi_transfer_mode_e
SPI发送模式枚举定义如下:
typedef enum
{
QL_SPI_MSB =0,
QL_SPI_LSB,
}ql_spi_transfer_mode_e
成员:
| 成员 | 描述 |
|---|---|
QL_SPI_MSB |
数据高位先发送 |
QL_SPI_LSB |
数据低位先发送 |
ql_spi_master_slave_mode_e
SPI主从机选择枚举定义如下:
typedef enum
{
QL_SPI_MASTER =0,
QL_SPI_SLAVE,
}ql_spi_master_slave_mode_e
成员:
| 成员 | 描述 |
|---|---|
QL_SPI_MASTER |
SPI为主机 |
QL_SPI_SLAVE |
SPI为从机 |
ql_spi_messag_s
SPI发送或接收的数据结构体定义如下:
typedef struct
{
UINT8 *send_buf;
UINT32 send_len;
UINT8 *recv_buf;
UINT32 recv_len;
}ql_spi_messag_s
参数:
| 类型 | 参数 | |
|---|---|---|
UINT8 |
send_buf |
发送数据 |
UINT32 |
send_le |
发送的数据的长度 |
UINT8 |
recv_buf |
接收数据 |
UINT32 |
recv_len |
接收的数据的长度 |
ql_spi_errcode_e
SPI结果码枚举定义如下:
typedef enum
{
QL_SPI_SUCCESS = 0,
QL_SPI_EXECUTE_ERR,
} ql_spi_errcode_e
成员:
| 成员 | 描述 |
|---|---|
QL_SPI_SUCCESS |
执行成功 |
QL_SPI_EXECUTE_ERR |
执行失败 |
ql_spi_transfer
该函数用于发送或接收SPI数据。发送模式还是接收模式取决于ql_spi_messag_s()结构体的配置。
函数原型:
ql_spi_errcode_e ql_spi_transfer(ql_spi_messag_s * spi_msg)
参数:
spi_msg:
[In] SPI发送或接收的数据;详见ql_spi_messag_s。
返回值:
结果码;详见ql_spi_errcode_e。
SPI开发流程
本章节主要介绍在应用程序中如何使用上述的SPI API,并进行简单的调试,以及测试SPI主机发送数据。
操作SPI
模块SDK代码中提供了操作SPI的示例,示例程序在ql_application/quectel_demo目录下ql_spi_demo.c文件中。相关函数解析如下:
ql_spi_demo_thread_creat():创建SPI任务,运行SPI示例程序需要调用该函数;ql_spi_demo_thread():任务的执行函数,简单实现了SPI的DMA初始化和发送数据。
若需要运行该示例,需要打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_SPI,同时关闭宏定义CFG_SUPPORT_SPI_FLASH_TEST,ql_spi_demo_thread_creat()和ql_spi_demo_thread()会自动被调用来创建测试任务,如下图所示。

{width="4.8in" height="6.6in"}
SPI功能调试
用户需使用安装模块的开发板(以FC41D TE-B为例)进行SPI功能调试,步骤如下:
步骤一:调试时先参照操作SPI运行SPI示例程序。
步骤二:重新编译固件版本并将其烧录至模块。
步骤三:重启模块。
步骤四:使用逻辑分析仪抓取波形。
步骤五:打开串口2,通过串口2获取Log信息,如下图所示。


I2C API
头文件
I2C API的头文件为ql_i2c1_eeprom.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_I2cInit
该函数用于初始化I2C总线。
函数原型:
int ql_I2cInit(DD_HANDLE* i2c_hdl,ql_i2c_mode_e Mode)
参数:
i2c_hdl:[Out] 获取的I2C句柄。
Mode:[In] I2C的工作模式;详见ql_i2c_mode_e。
返回值:
结果码;详见ql_errcode_i2c_e。
ql_i2c_mode_e
I2C工作模式的枚举定义如下:
typedef enum
{
STANDARD_MODE = 0,
FAST_MODE = 1,
} ql_i2c_mode_e
成员:
| 成员 | 描述 |
|---|---|
STANDARD_MODE |
标准模式 |
FAST_MODE |
快速模式 |
ql_errcode_i2c_e
I2C API相关的结果码的枚举定义如下:
typedef enum
{
QL_I2C_SUCCESS =0,
QL_I2C_INIT_ERR ,
QL_I2C_WRITE_ERR,
QL_I2C_READ_ERR,
QL_I2C_RELEASE_ERR,
}ql_errcode_i2c_e
成员:
| 成员 | 描述 |
|---|---|
QL_I2C_SUCCESS |
执行成功 |
QL_I2C_INIT_ERR |
I2C初始化失败 |
QL_I2C_WRITE_ERR |
向I2C总线中写入数据失败 |
QL_I2C_READ_ERR |
从I2C总线中读取数据失败 |
QL_I2C_RELEASE_ERR |
释放I2C失败 |
ql_I2cWrite
该函数用于向I2C总线中写入数据。
函数原型:
int ql_I2cWrite(DD_HANDLE i2c_hdl, UINT8 slave, UINT16 addr, char *data, UINT32 length, UINT8 addr_width)
参数:
i2c_hdl:[In] I2C句柄。
slave:[In] I2C从机设备地址。
addr:[In] I2C从机寄存器地址。
data:[In] 写入的数据。
length:[In] 写入数据的长度。
addr_width:[In] 从机寄存器地址的长度。
返回值:
结果码;详见ql_errcode_i2c_e。
ql_I2cRead
该函数用于从I2C总线中读取数据。
函数原型:
int ql_I2cRead(DD_HANDLE i2c_hdl, UINT8 slave, UINT16 addr, char *buf, UINT32 length,UINT8 addr_width)
参数:
i2c_hdl:[In] I2C句柄。
slave:[In] I2C从机设备地址。
addr:[In] I2C从机寄存器地址。
buf:[Out] 读取的数据。
length:[In] 读取数据的长度。
addr_width:[In] 从机寄存器地址长度。
返回值:
结果码;详见ql_errcode_i2c_e。
ql_I2cRelease
该函数用于释放I2C总线。如需重新初始化同一个I2C主机,请调用该函数释放I2C总线后,再重新调用ql_I2cInit()初始化I2C总线。
函数原型:
int ql_I2cRelease(DD_HANDLE i2c_hdl)
参数:
i2c_hdl:
[In] I2C句柄。
返回值:
结果码;详见ql_errcode_i2c_e。
示例
模块SDK代码中提供了操作I2C的示例,示例程序在ql_application/quectel_demo目录下ql_i2c_eeprom_demo.c文件中。I2C需要使用外设进行通信。本示例中,模块使用的是EEPROM芯片(型号:FM24C128A)。相关函数解析如下:
ql_i2c_demo_thread_creat():创建I2C任务,运行示例程序需要调用该函数。ql_i2c1_eeprom_demo_thread():任务的执行函数,实现了I2C外设初始化、写入数据、读取数据以及释放I2C总线的功能。
如需运行该示例,需打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_I2C1,ql_i2c_demo_thread_creat()和ql_i2c1_eeprom_demo_thread()会被自动调用以创建示例任务。如下图所示。


ADC API
头文件
ADC API的头文件为ql_adc.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_adc_thread_init
该函数用于创建ADC任务。
函数原型:
ql_adc_errcode_e ql_adc_thread_init(void)
参数:
无
返回值:
结果码;详见ql_adc_errcode_e。
ql_adc_errcode_e
ADC结果码枚举定义如下:
typedef enum
{
QL_ADC_SUCCESS = 0,
QL_ADC_EXECUTE_ERR,
QL_ADC_INVALID_PARAM_ERR,
} ql_adc_errcode_e
成员:
| 成员 | 描述 |
|---|---|
QL_ADC_SUCCESS |
函数执行成功 |
QL_ADC_EXECUTE_ERR |
函数执行失败 |
QL_ADC_INVALID_PARAM_ERR |
参数无效 |
ql_adc_channel_init
该函数用于配置ADC通道参数。
函数原型:
ql_adc_errcode_e ql_adc_channel_init(ql_adc_obj_s *handle, ql_adc_obj_callback cb, ql_adc_channel_e channel, void *user_data)
参数:
handle:[In] ADC通道信息;详见ql_adc_obj_s。
cb:[In] 通道检测完成的回调函数;详见ql_adc_obj_callback。
channel:[In] ADC通道编号;详见ql_adc_channel_e。
user_data:[In] 用户数据。
返回值:
结果码;详见ql_adc_errcode_e。
ql_adc_obj_s
ADC通道信息结构体定义如下:
typedef struct adc_obj_ {
void *user_data;
ql_adc_channel_e channel;
ql_adc_obj_callback cb;
struct adc_obj_ *next;
}ql_adc_obj_s
参数:
| 类型 | 参数 | |
|---|---|---|
void |
user_data |
用户数据 |
ql_adc_channel_e |
channel |
ADC通道编号,详见ql_adc_channel_e。 |
ql_adc_obj_callback |
cb |
通道检测完成的回调函数 |
struct adc_obj_ |
next |
链表下一个节点的地址 |
ql_adc_obj_callback
该函数为ADC通道检测完成的回调函数。
函数原型:
typedef void (*ql_adc_obj_callback)(int new_mv, void *user_data)
参数:
new_mv:[In] ADC检测电压值范围(0~2400 mV)。
user_data:[In] 用户数据。
返回值:
无
ql_adc_channel_e
ADC通道编号枚举定义如下:
typedef enum
{
QL_ADC_CHANNEL_0 = 0,
QL_ADC_CHANNEL_1,
QL_ADC_CHANNEL_2,
QL_ADC_CHANNEL_3,
QL_ADC_CHANNEL_4,
QL_ADC_CHANNEL_5,
QL_ADC_CHANNEL_6,
}ql_adc_channel_e
成员:
| 成员 | 描述 |
|---|---|
QL_ADC_CHANNEL_0 |
通道0,检测VBAT引脚电压,读取值为VBAT电压值的1/2 |
QL_ADC_CHANNEL_1 |
通道1,检测GPIO26引脚电压 |
QL_ADC_CHANNEL_2 |
通道2,检测GPIO24引脚电压 |
QL_ADC_CHANNEL_3 |
通道3,检测GPIO23引脚电压 |
QL_ADC_CHANNEL_4 |
通道4,检测GPIO28引脚电压 |
QL_ADC_CHANNEL_5 |
通道5,检测GPIO22引脚电压 |
QL_ADC_CHANNEL_6 |
通道6,检测GPIO21引脚电压 |
ql_adc_channel_start
该函数用于使能ADC检测。
函数原型:
ql_adc_errcode_e ql_adc_channel_start(ql_adc_obj_s *handle)
参数:
handle:
[In] ADC通道信息;详见ql_adc_obj_s。
返回值:
结果码;详见ql_adc_errcode_e。
ql_adc_channel_stop
该函数用于停止ADC检测。
函数原型:
ql_adc_errcode_e ql_adc_channel_stop(ql_adc_obj_s *handle)
参数:
handle:
[In] ADC通道信息;详见ql_adc_obj_s。
返回值:
结果码;详见ql_adc_errcode_e。
ADC开发流程
本章节主要介绍在应用程序中如何使用上述的API,并进行简单的调试,示例中使用通道1进行测试。
操作ADC
模块的SDK代码中提供了操作ADC的示例,示例程序在ql_application/quectel_demo目录下ql_adc_demo.c文件中。相关函数解析如下:
ql_adc_demo_thread_creat():创建ADC任务,运行ADC示例程序需要调用该函数;ql_adc_demo_thread():任务的执行函数,简单实现了ADC的初始化、电压检测。
若需要运行该示例,只需要打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_ADC,ql_adc_demo_thread_creat()和ql_adc_demo_thread()会被自动调用来创建测试任务。如下图所示:


ADC功能调试
用户需使用安装模块的开发板(FC41D TE-B)进行ADC功能调试,步骤如下:
步骤一:调试时先参照操作ADC运行ADC示例程序。
步骤二:重新编译固件版本并将其烧录至模块。
步骤三:重启模块。
步骤四:打开串口2,通过串口2获取Log信息,如下图所示。

改变引脚输入电压,检测值随之改变。
PWM API
头文件
PWM API的头文件为ql_pwm.h,位于SDK包的ql_components/qadpt/include/目录下。若无特别说明,本文档所涉及头文件均在该目录下。
函数详解
ql_pwmInit
该函数用于初始化PWM。
函数原型:
ql_pwm_errcode_e ql_pwmInit(ql_pwm_channel_e pwm, UINT32 period, UINT32 duty_cycle)
参数:
pwm:[In] PWM通道;详见ql_pwm_channel_e。
period:[In] PWM周期值;实际输出频率:F = 26 MHz / period。
duty_cycle:[In] PWM占空比值;小于周期值。
返回值:
结果码;详见ql_pwm_errcode_e。
ql_pwm_channel_e
PWM通道枚举定义如下。共6路PWM通道。
typedef enum
{
QL_PWM_0,
QL_PWM_1,
QL_PWM_2,
QL_PWM_3,
QL_PWM_4,
QL_PWM_5,
} ql_pwm_channel_e
成员:
| 成员 | 描述 |
|---|---|
QL_PWM_0 |
PWM通道0 |
QL_PWM_1 |
PWM通道1 |
QL_PWM_2 |
PWM通道2 |
QL_PWM_3 |
PWM通道3 |
QL_PWM_4 |
PWM通道4 |
QL_PWM_5 |
PWM通道5 |
ql_pwm_errcode_e
PWM结果码的枚举定义如下:
typedef enum
{
QL_PWM_SUCCESS = 0,
QL_PWM_EXECUTE_ERR,
QL_PWM_INVALID_PARAM_ERR,
} ql_pwm_errcode_e
成员:
| 成员 | 描述 |
|---|---|
QL_PWM_SUCCESS |
执行成功 |
QL_PWM_EXECUTE_ERR |
执行失败 |
QL_PWM_INVALID_PARAM_ERR |
无效参数 |
ql_pwmInit_level
该函数用于配置PWM初始输出电平。
函数原型:
ql_pwm_errcode_e ql_pwmInit_level(ql_pwm_channel_e pwm, ql_pwm_init_level_e level)
参数:
pwm:[In] PWM通道;详见ql_pwm_channel_e。
level:[In] PWM初始电平;详见ql_pwm_init_level_e。
返回值:
结果码;详见ql_pwm_errcode_e。
ql_pwm_init_level_e
PWM初始电平枚举定义如下:
typedef enum
{
QL_PWM_INIT_LEVEL_LOW =0,
QL_PWM_INIT_LEVEL_HIGH,
}ql_pwm_init_level_e
成员:
| 成员 | 描述 |
|---|---|
QL_PWM_INIT_LEVEL_LOW |
低电平 |
QL_PWM_INIT_LEVEL_HIGH |
高电平 |
ql_pwm_enable
该函数用于使能PWM输出。
函数原型:
ql_pwm_errcode_e ql_pwm_enable(ql_pwm_channel_e pwm)
参数:
pwm:
[In] PWM通道;详见ql_pwm_channel_e。
返回值:
结果码;详见ql_pwm_errcode_e。
ql_pwm_disable
该函数用于停止PWM输出。
函数原型:
ql_pwm_errcode_e ql_pwm_disable(ql_pwm_channel_e pwm)
参数:
pwm:
[In] PWM通道;详见ql_pwm_channel_e。
返回值:
结果码;详见ql_pwm_errcode_e。
ql_pwm_update_param
该函数用于更新PWM配置参数,更新后在下一个PWM周期生效。
函数原型:
ql_pwm_errcode_e ql_pwm_update_param(ql_pwm_channel_e pwm, UINT32 period, UINT32 duty_cycle)
参数:
pwm:[In] PWM通道;详见ql_pwm_channel_e。
period:[In] PWM周期值;实际输出频率:F = 26 MHz / period。
duty_cycle:[In] PWM占空比值;小于周期值。
返回值:
结果码;详见ql_pwm_errcode_e。
PWM开发流程
本章节主要介绍在应用程序中如何使用上述的PWM API,并进行简单的调试。本示例中使用PWM通道1进行测试。
操作PWM
模块的SDK代码中提供了操作PWM的示例,示例程序在ql_application/quectel_demo目录下ql_pwm_demo.c文件中。相关函数解析如下:
ql_pwm_demo_thread_creat():该函数用于创建PWM任务,运行PWM示例程序需要调用该函数。ql_pwm_demo_thread():任务的执行函数。实现了PWM的输出功能。
若需要运行该示例程序,打开宏定义CFG_ENABLE_QUECTEL_DEMO和CFG_ENABLE_QUECTEL_PWM,ql_pwm_demo_thread_creat()和ql_pwm_demo_thread()会自动被调用以创建测试任务。


PWM功能调试
用户需使用安装模块的开发板(以FC41D TE-B为例)进行PWM功能调试,步骤如下:
步骤一:调试时先参照操作PWM运行PWM示例程序。
步骤二:重新编译固件版本并将其烧录至模块。
步骤三:重启模块。
步骤四:使用逻辑分析仪获取PWM通道1的引脚波形。
步骤五:打开串口2,通过串口2获取Log信息,如下图所示:


由上图可知,PWM波形与配置相同,说明PWM功能测试成功。
附录
参考文档:
| 文档名称 |
|---|
| Quectel_FC41D&FCMxx0D&FLMx40D_QuecOpen(SDK)_快速开发指导 |
术语缩写:
| 缩写 | 英文全称 | |
|---|---|---|
| ADC | Analog-to-Digital Converter | 模数转换器 |
| API | Application Programming Interface | 应用程序接口 |
| CLK | Clock | 时钟 |
| CPHA | Clock Phase | 时钟相位 |
| CPOL | Clock Polarity | 时钟极性 |
| CTS | Clear To Send | 清除发送 |
| DMA | Direct Memory Access | 直接存储器访问 |
| EEPROM | Electrically Erasable Programmable Read-Only Memory | 带电可擦可编程只读存储器 |
| FIFO | First in First Out | 先进先出 |
| GPIO | General-Purpose Input/Output | 通用型输入/输出 |
| I2C | Inter-Integrated Circuit | 内置集成电路总线 |
| IoT | Internet of Things | 物联网 |
| PWM | Pulse Width Modulation | 脉冲宽度调制 |
| RTOS | Real-Time Operating System | 实时操作系统 |
| RTS | Ready To Send/Request to Send | 准备发送/请求发送 |
| SCK | Serial Clock | 串行时钟 |
| SDK | Software Development Kit | 软件开发工具包 |
| SPI | Universal Serial Bus | 串行外设接口 |
| UART | Universal Asynchronous Receiver/Transmitter | 通用异步收发传输器 |
| VBAT | Voltage at Battery (Pin) | 电池电压(引脚) |