感谢电子发烧友论坛和南京沁恒所提供的CH32V208 开发板的测试机会。
CH32V208 开发板的一个特色就是其提供了蓝牙协议栈,所以今天就来介绍使用开发板实现蓝牙键盘。
1测试例程HID_Keyboard
在厂商提供的蓝牙例程中有一个HID_Keyboard,这是个蓝牙键盘例程,模拟键盘设备,连接主机后定时上传键值。我们先来测试一下这个例程。这个例程位于\EVT\EXAM\BLE\HID_Keyboard目录中,如果你像我一样喜欢将例子拷贝到其他目录去编译,请注意这个例子用到几个公共目录的程序:SRC、HAL和LIB。具体处理方法见我的上一篇帖子。这个例程的编译和下载和其他程序没有区别。下载成功后重启板子就可以运行。
我们先使用串口工具MobaXterm观察一下程序的运行日志。由于该程序的日志只输出回车符(“\n”),而不是回车换行符("\r\n”),所以在MobaXterm中需要在窗口右键右键菜单中选择“Change terminal settings”。
然后在窗口中勾上下图的两个选项。
程序加电后从串口可以看到如下信息,其中Advertising表示蓝牙设备已经开始广播其信息,这时我们就能从电脑找到蓝牙设备了。
在Windows电脑的蓝牙设置中添加蓝牙设备,如下图所示。
在电脑扫描到的蓝牙设备中我们可以看到“HID Keyboard”,这个就是CH32V208 开发板。
连接到这个设备后,该设备会定时向电脑发送一个字符,从a到y,一直循环发送,如下图所示。直到我们断开蓝牙键盘的连接为止。
整个测试过程的日志如下图所示。当我们断开连接后设备再次进入广播状态,等待下次连接。
2程序逻辑分析
该例程的核心代码是在APP\hidkbd.c文件中,只看这一个文件基本就够了。
2.1关键数据结构
关键数据结构有三个:
- scanRspData:定义GAP的profile,表示设备提供哪些服务;
- advertData:广播相关数据;
- attDeviceName:设备名称。
2.2任务管理系统(TMOS)
低功耗蓝牙协议栈以及应用均基于 TMOS(Task Management Operating System),TMOS是一个控制循环,通过 TMOS 可设置事件的执行方式。TMOS 作为调度核心,BLE 协议栈、profile 定义、所有的应用都围绕它来实现。TMOS 不是传统意义上的操作系统,而是一种以实现多任务为核心的系统资源管理机制。有关TMOS的详细说明请参考《沁恒低功耗蓝牙软件开发参考手册》。
2.3HID设备初始化
HID设备初始化由HidEmu_Init函数完成,主要工作包括:
- 注册了TMOS任务函数HidEmu_ProcessEvent,这个函数负责处理各种事件;
- 设置和广播相关的各种参数;
- 添加键盘服务;
- 延迟启动START_DEVICE_EVT事件。
2.4消息处理函数
消息处理函数是HidEmu_ProcessEvent,它负责处理各种任务消息。其中键盘功能主要是靠START_REPORT_EVT消息实现的。这个事件中通过hidEmuSendKbdReport函数向电脑发送键盘消息。键盘码从4开始(对应这字符A),每次累加一个,最多到29再次循环回4。每次发送完成后还会发送一个0,表示按键释放,否则会形成长按键盘不松手的效果。这个消息处理过程中会启动一个2秒定时任务,再次发送一个字符。
2.5回调函数
应用程序的代码既可以写在事件处理的代码段中,也可以写在回调函数中。协议栈与应用程序之间的通信是由回调函数实现的。
回调函数hidEmuStateCB是用来跟踪系统状态的变化的,像刚才在串口打印的消息都在这个回调函数中。
回调函数hidEmuRptCB是用来相应系统的设备上报回调的。按键任务的第一次启动就是在这个回调中处理HID_DEV_OPER_ENABLE开始的。