这是本文档旧的修订版!
目录
NK-R39S2A1
主板框架图
接口定义
插针pin定义
RS485&232 | J_LED-IR1 | J_GPIO1 | SPK1 | UART1 | ||||||
---|---|---|---|---|---|---|---|---|---|---|
1 | RS485_A1 | 1 | VCC3_IR | 1 | GPIO1 | 1 | L_SPK+ | 1 | UART0_RX_CON | |
2 | RS485_B1 | 2 | IR | 2 | GPIO3 | 2 | L_SPK- | 2 | UART0_TX_CON | |
3 | RS485_A2 | 3 | GND | 3 | GPIO2 | 3 | R_SPK+ | 3 | VCC3_TTL | |
4 | RS485_B2 | 4 | AD | 4 | GPIO4 | 4 | R_SPK- | 4 | GND | |
5 | UART_RX3_232 | 5 | LEDB | 5 | SPI2_MOSI_CN | J_KEY1 | J_RS232 | |||
6 | UART_TX3_232 | 6 | P_LED | 6 | SPI2_MISO_CN | 1 | GND | 1 | UART_RX5_232 | |
7 | UART_RX4_232 | I2C-TP | 7 | SPI2_CLK_CN | 2 | P3V3 | 2 | UART_TX5_232 | ||
8 | UART_TX4_232 | 1 | GND | 8 | SPI2_CS_CN | 3 | POWER_ON_BT | 3 | VCC5_232 | |
9 | GND | 2 | I2C1_SDA_TP_C | 9 | VCC5_GPIO | 4 | Reset | 4 | GND | |
10 | GND | 3 | I2C1_SCL_TP_C | 10 | VCC5_GPIO | 5 | RECOVER_BUTTON | PUSB | ||
debug | 4 | TP_RST_C | 11 | GND | HOST1 | 1 | USB_VCC5 | |||
1 | NC | 5 | TP_INT_C | 12 | GND | 1 | HOST1_VCC5 | 2 | USB_D2N | |
2 | UART2_TX_ | 6 | TP_VDD | 2 | HOST1_D1N_CON | 3 | USB_D2P | |||
3 | UART2_RX | 3 | HOST1_D1P_CON | 4 | GND | |||||
4 | GND | 4 | GND |
Jump_sel
COM1_SEL | COM2_SEL | EDP | VDD_JU1 | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
1 | 3 | RS232 | 1 | 3 | RS232 | 1 | 3 | EDP | 1 | 2 | 3.3V | ||||
2 | 4 | 2 | 4 | 2 | 4 | 3 | 4 | 5V | |||||||
3 | 5 | RS485 | 3 | 5 | RS485 | 3 | 5 | LVDS | 5 | 6 | 12V | ||||
4 | 6 | 4 | 6 | 4 | 6 |
硬件特性
硬件资源规格 | |
---|---|
SOC | Rockchip RK3399 (28纳米HKMG制程) |
CPU | ARM®六核64位处理器,主频高达1.8GHz 基于big.LITTLE大小核架构, 双核Cortex-A72(大核) + 四核Cortex-A53(小核) |
GPU | ARM® Mali-T860 MP4 四核GPU 支持OpenGL ES1.1/2.0/3.0/3.1, OpenVG1.1, OpenCL, DX11 支持AFBC(帧缓冲压缩) |
NPU | |
ISP | |
编解码 | |
内存 | 4GB LPDDR4(2GB/4GB可选配) |
存储 | 16G/32G/64G可选 |
以太网 | 2*1000Mpbs ( 可选 ) |
WIFI | 2.4GHz 单频WiFi / 2.4G/5G 双频 |
视频输出 | 支持eDP. LVDS1080P. HDMI2.0 |
视频输入 | |
音频 | 2*SPK ( 6W 8Ω ) |
SATA | |
USB | 3*USB2.0 1*USB3.0 |
电源 | DC IN 12~24V |
其他 | |
硬件电气特性 | |
高低温环境 | -20℃~60℃ |
静电 | 满足ESD 等级3 ,接触放电6KV,空气放电8KV |
其他 | 满足EFT GB/T 17626.4-2008等级3 |
快速上手
系统烧录
Debug串口调试
1、通过串口进入系统后台,需要利用板子的Debug接口,接口位置和定义如图:
* 接口只需要用到3个引脚,TX、RX、GND
2、需要用到串口小板工具
- A部分需要接入TX、RX、GND
- B部分连接电脑USB口
3、硬件部分连接效果图
4、在电脑的设备管理器→端口 中看有没有串口信息
5、打开Xshell新建一个会话,在连接下选择协议为SERIAL,操作如图:
6、点击串口,端口号为设备管理器看到的串口号,波特率为:1500000
7、最后点击连接,串口进入后台
Android ADB
Linux SSH
Android 使用指南
接口功能测试
UART
1. 串口定义参考:
2. 安卓系统串口设备节点对应表:
主板丝印 | 设备节点 |
---|---|
UART0_TTL | /dev/ttyS0 |
RS232_Rx5/Tx5 | /dev/ttyS1 |
RS232_Rx3/Tx3 | /dev/ttyS2 |
RS232_Rx4/Tx4 | /dev/ttyS3 |
RS485_A1/B1 | /dev/ttyS4 |
RS485_A2/B2 | /dev/ttyS5 |
3. ComAssistant 测试串口通讯,以232_Rx5\Tx5回环测试为例
- 参考步骤1~2短接232_Rx5\Tx5的 Tx & Rx (1-2 pin)
- 打开ComAssistant APP,设置好串口参数:
波特率:9600 数据位:8bit 起始位:1bit 校验位:none
- 设置好串口参数后,打开串口,在数据发送区输入框中输入字符,点击发送,可以发送数据。如下图所示:
4. RS485测试通讯,不支持回环测试,测试方式:
- 通过USB转RS485工具,与上位机(Windows端)互测
- 通过RS485转RS232工具,与RS232互测
- 两个RS485对发测试
LAN
WIFI
4G/5G
1.测试4G网络
a)给板子断电,接上4G模块与天线,插入5G电话卡
b)打开设置,点击更多
c)点击4G路由设置
d)开启路由
状态栏右上角显示该图标,则为开启成功
2.测试5G网络
a)给板子断电,插入5G电话卡,接上5G模块与一根天线,天线接在模线帽接口
b)打开设置,点击更多
c)点击4G路由设置
d)开启路由
状态栏右上角显示该图标,则为开启成功
Can
GPIO/DIO
1.导出节点(编号为56、57、58、59)
先获取权限:su 再输入导出命令:echo 56 >/sys/class/gpio/export 也可以使用for循环一次性导出所有IO节点: $:cd /sys/class/gpio $:for i in {56,57,58,59}; do echo $i >export; done
2. IO 控制节点在目录:/sys/class/gpio/
3. IO 对应表如下:
功能 | 主板丝印 | 节点编号 |
---|---|---|
输入\输出 | J_GPIO1 | gpio56 |
J_GPIO2 | gpio57 | |
J_GPIO3 | gpio58 | |
J_GPIO4 | gpio59 |
- 设置IO方向为输出:
echo out >/sys/class/gpio/gpio56/direction
- 输出低电平:
echo 0 >/sys/class/gpio/gpio56/value
- 输出高电平:
echo 1 >/sys/class/gpio/gpio56/value
- 查看输出电平的值是否可控:
cat /sys/class/gpio/gpio56/value
- 使用电压表测量IO对应的针脚对GND的电压值
0 对应高电平 1.8V 1 对应低电平 0V
Audio
连接扬声器后,可播放音视频,测试左右声道
Mic
接好麦克风和一对喇叭后,使用系统内置的录音机APP,录音和播放测试
USB
SDCARD
5.1 插入TF卡至设备TF卡卡槽
5.2 上滑至应用页面 » 文件 » 查看外接TF卡信息
5.3 在系统下拷贝文件至TF卡,进行读写测试
5.4 上滑至应用页面 » 文件 » TF卡挂载名称 » 点击旁边的弹出图标,弹出TF卡
Bluetooth
WatchDog
Key
- 3pin-GND:power_on功能:poweroff状态下启动系统
- 4pin-GND:Reset功能:重启
- 5pin-GND:Recovery_key:Android-返回键;Linux-无
LCD
PowerManager
支持在线升级,系统内置升级APP,打开可查看是否有最新系统版本
RTC
- 在终端输入date查看系统时间(软件时间)
- 输入hwclock 查看RTC时间(硬件时间)
- 设置时间和时间格式:
date MMddHHmmyyyy.ss set(月日时分年.秒) 例如:date 052514192023.00 set
- 输入“hwclock -w”,保存时间。重启系统后,再查看当前时间是否保存,用于验证RTC时间是否生效
hwclock -w --从系统时间同步到硬件时钟 hwclock -s --从硬件时钟同步到系统时间
系统基本功能设置
系统性能测试
- 查看CPU信息
cat /sys/devices/system/cpu/cpu*/cpufreq/cpuinfo_cur_freq //查看cpu频率 cat /sys/class/thermal/thermal_zone0/temp //查看CPU当前温度
- 查看内存信息
free -h
- 查看存储信息
df -h
- 查看USB设备
lsusb
Android API 使用说明
NodkaAPI入口类
NodkaAPI使用方法:
1、在Application的onCreate中创建NodkaAPI实例
mNodkaAPI = NodkaAPI.nodkaAPICreate(this);
2、在Activity或Fragment中使用API步驟:
private NodkaAPI mNodkaAPI = APIApplication.getApplication().getNodkaAPI();
NodkaAPI接口说明:
1、以devinfo开头的是硬件及系统信息查询类api
2、以display开头的是显示控制类api
3、以gpio开头的是GPIO控制类api
4、以uart开头的是串口控制类api
5、以sysctrl开头的是系统控制类api,包括定时开关机
接口类别 | 方法名 | 方法说明 |
---|---|---|
硬件及系统信息查询类 | devinfo_getAndroidVersion() | 获取Android系统版本信息 |
devinfo_getAvailMem() | 获取可用内存容量 | |
devinfo_getBuildNumber() | 获取系统版本号信息 | |
devinfo_getCpuCores() | 获取cpu核心数 | |
devinfo_getCPUCurFreqKHz() | 获取cpu当前运行主频 | |
devinfo_getCPUMaxFreqKHz() | 获取cpu最大主频 | |
devinfo_getCPUMinFreqKHz() | 获取cpu最小主频 | |
devinfo_getCPUTemp() | 获取cpu温度 | |
devinfo_getDeviceModel() | 获取设备型号信息 | |
devinfo_getKernelVersion() | 获取内核版本信息 | |
devinfo_getSerialNum() | 获取设备SN号 | |
devinfo_getStorageAvailableSize() | 获取本机可用存储容量 | |
devinfo_getStorageTotalSize() | 获取本机存储容量(不包括系统分区) | |
devinfo_getTotalMem() | 获取内存总容量 | |
显示控制类 | display_getNavBar() | 获取是否显示导航栏跟状态栏 |
display_getScreenBrightness() | 获取屏幕亮度 | |
display_getScreenRotation() | 获取屏幕旋转方向 | |
display_getWindowHeight() | 获取屏幕分辨率高度 | |
display_getWindowWidth() | 获取屏幕分辨率宽度 | |
display_setNavBar(Boolean enable) | 设置是否显示导航栏跟状态栏 | |
display_setNavBarSlideShow(Boolean enable) | 设置滑动是否会显示导航栏跟状态栏 | |
display_setScreenBrightness(int screenBrightness) | 设置屏幕亮度 | |
display_setScreenRotation(int rotation) | 设置屏幕旋转方向 | |
GPIO控制类 | gpio_direction(int gpioNumber, String direction) | 设置GPIO的方向(输入输出),对指定的gpio号进行设置 |
gpio_export(int gpioNumber) | 导出控制的GPIO引脚,对指定的gpio号进行导出 | |
gpio_read(int gpioNumber) | 读取GPIO的输出电平值,对指定的gpio号进行读取 | |
gpio_unExport(int gpioNumber) | 取消导出控制的GPIO引脚,对指定的gpio号进行取消导出 | |
gpio_write(int gpioNumber, int value) | 设置GPIO的输出电平,对指定的gpio号进行设置 | |
串口控制类 | uart_close(String uartNode) | 关闭uart设备,如/dev/ttyXRUSB2 |
List<String> uart_getAvailableDevices() | 获取uart可用的设备节点 | |
uart_IsOpen(String uartNode) | uart设备是否已经打开,如/dev/ttyXRUSB2 | |
uart_open(String uartNode, int baudrate) | 打开uart设备,如/dev/ttyXRUSB2 | |
uart_receive(String uartNode, UartReceiveDataCallback callback) | 接收串口数据,如从/dev/ttyXRUSB2接收数据 | |
uart_send(String uartNode, byte[] buffer) | 发送串口数据,如向/dev/ttyXRUSB2发送数据 | |
uart_stopReceive(String uartNode) | 停止接收数据,调用后,不再有数据回调 | |
系统控制类 | sysctrl_cancelReboot() | 取消重启设备 |
sysctrl_cancelShutdown() | 取消自动关机 | |
sysctrl_powerOn(String time, boolean repeat) | 设置设备开机时间 | |
sysctrl_reboot(String time, boolean repeat) | 设置重启设备时间 | |
sysctrl_rebootNow() | 立即重启设备 | |
sysctrl_shutdown(String time, boolean repeat) | 设置设备关机时间 | |
sysctrl_shutdownNow() | 立即关机 | |
sysctrl_installApk(String apkPath) | 静默安装应用 |
Linux 使用指南
接口功能测试
GPIO
1. IO 控制节点都在/sys/class/io_control/
2. IO 对应表如下:
功能 | 主板丝印 | 节点名 |
---|---|---|
输入 | GPIO1 | gpio_ip0 |
GPIO2 | gpio_ip1 | |
GPIO3 | gpio_ip2 | |
GPIO4 | gpio_ip3 | |
输出 | GPIO5 | gpio_op0 |
GPIO6 | gpio_op1 | |
GPIO7 | gpio_op2 | |
GPIO8 | gpio_op3 |
- 输出低电平:
echo 0 >/sys/class/io_control/gpio_op0
*输出高电平:
echo 1 >/sys/class/io_control/gpio_op0
*查看输入电平:
cat /sys/class/io_control/gpio_ip0
UART
1. 串口定义参考:
2. 串口设备节点系统对应表:
主板丝印 | 设备节点 |
---|---|
J_RS232 RX2\TX2 | /dev/ttysWK1 |
J_RS232 RX3\TX3 | /dev/ttysWK2 |
J_RS232 RX4\TX4 | /dev/ttysWK3 |
RS485 | /dev/ttyS3 |
UART | /dev/ttyS4 |
3. CuTecom 测试串口,以/dev/ttysWK2回环测试为例
- 参考步骤1~2短接/dev/ttysWK2的 TX & RX (2~3 pin);
- 双击桌面CuteCom图标,打开APP,Device选择测试端口对应的设备节点(见步骤2);
- 点击Settings,设置串口参数,如下图所示:
- 设置好以后点击Open 打开串口,在input 文本输入框中输入字符,按回车发送数据:
4. 命令行方式测试串口,同样以J_RS232 RX3\TX3回环测试为例
打开终端输入如下指令接收数据:
com_recv /dev/ttysWK2 115200
打开另一个终端发送数据:
com_send /dev/ttysWK2 115200
测试结果如下:
LAN
1. 查看网卡IP地址,系统默认都为动态获取IP地址
#ifconfig -a
2. 设置网卡静态IP地址
- 方法1 – 使用图形界面工具设置
双击桌面图标Advanced Network Configuration
- 方法2 – 修改配置文件的方式:
vim /etc/network/interfaces
- 修改完成后输入重启生效。
WIFI
4G/5G
Can
GPIO/DIO
1. IO 控制节点都在/sys/class/io_control/
2. IO 对应表如下:
功能 | 主板丝印 | 节点名 |
---|---|---|
输入 | IO1 | gpio_ip0 |
IO2 | gpio_ip1 | |
IO3 | gpio_ip2 | |
IO4 | gpio_ip3 | |
输出 | IO5 | gpio_op0 |
IO6 | gpio_op1 | |
IO7 | gpio_op2 | |
IO8 | gpio_op3 |
3. IO控制方法:
- 输出低电平:
echo 0 >/sys/class/io_control/gpio_op0
*输出高电平:
echo 1 >/sys/class/io_control/gpio_op0
*查看输入电平:
cat /sys/class/io_control/gpio_ip0
1.导出节点(编号为56、57、58、59)
$:echo 56 >/sys/class/gpio/export 也可以使用for循环一次性导出所有IO节点: $:cd /sys/class/gpio $:for i in {56,57,58,59}; do echo $i >export; done
2. IO 控制节点在目录:/sys/class/gpio/
3. IO 对应表如下:
功能 | 主板丝印 | 节点编号 |
---|---|---|
输入\输出 | J_GPIO1 | gpio56 |
J_GPIO2 | gpio57 | |
J_GPIO3 | gpio58 | |
J_GPIO4 | gpio59 |
4. IO控制方法:
- 设置IO方向为输出:
echo out >/sys/class/gpio/gpio56/direction
- 输出低电平:
echo 0 >/sys/class/gpio/gpio56/value
- 输出高电平:
echo 1 >/sys/class/gpio/gpio56/value
- 查看输出电平的值是否可控:
cat /sys/class/gpio/gpio56/value
- 使用电压表测量IO对应的针脚对GND的电压值
0 对应高电平 1.8V 1 对应低电平 0V
Audio
Mic
USB
SDCARD
Bluetooth
WatchDog
Key
1. 输入命令evtest 查看系统下所有按键、输入设备:
root@rk3568:~# evtest No device specified, trying to scan all of /dev/input/event* Available devices: /dev/input/event0: rk805 pwrkey /dev/input/event1: Lenovo Precision USB Mouse /dev/input/event2: HID 04f3:0103 /dev/input/event3: HID 04f3:0103 Consumer Control /dev/input/event4: HID 04f3:0103 System Control /dev/input/event5: adc-keys /dev/input/event6: rk-headset Select the device event number [0-6]:
2. 按照上面提示选择测试按键,如RK3568 boot按键为 /dev/input/event5: adc-keys
则event number 为 5:按下按键会打印value 1,松开按键则会打印value 0,如下图:
3. 自定义按键功能,配置文件为:
/etc/triggerhappy/triggers.d/example.conf
如下,定义按键为reboot功能,也是系统默认配置,用户可以根据需要自定义
KEY_VOLUMEUP 1 reboot
LCD/Backlight
1. HDMI
系统默认支持HDMI显示,默认分辨率 1920 * 1080,设置屏幕分辨率:终端输入命令:dis ,调出设置屏参界面,点击保存
2. eDP
a) 如图,开发板断电状态下接好eDP屏数据线和背光线,支持USB触控屏线,注意跳线帽短接位置 ,背光电压和数据线电压是根据屏参确定的,这里以12V背光和3.3V数据线为例
b) 默认 eDP屏分辨率:1920 * 1080,支持eDP + HDMI 复制双显,支持12.5“1366 * 768, 12.5”1920 * 1080, 13.3“1920 * 1080, 15.6”1920 * 1080
注意:如果上电后屏幕不亮,需要在HDMI上调整 eDP 屏幕对应的分辨率
c) 设置屏幕分辨率:终端输入命令:dis ,调出设置屏参界面
3. LVDS
a) 如图,开发板断电状态下接好 LVDS屏数据线和背光线,支持USB触控屏线,注意跳线帽短接位置 ,背光电压和数据线电压是根据屏参确定的,这里以12V背光和3.3V数据线为例
b) 默认 LVDS屏分辨率:1920 * 1080,支持LVDS + HDMI 复制双显,支持12.5“1366 * 768, 12.5”1920 * 1080, 13.3“1920 * 1080, 15.6”1920 * 1080
注意:如果上电后屏幕不亮,需要在HDMI上调整LVDS屏幕对应的分辨率
c) 设置屏幕分辨率:终端输入命令:dis ,调出设置屏参界面
4. MiPi
a) 如图,开发板断电状态下接好MiPi屏线
b) MiPi屏分辨率:800 * 1280,支持 10.1“800 * 1280
c) 设置屏幕分辨率:终端输入命令:dis ,调出设置屏参界面,进入屏参切换界面,选择选择10.1_mipi_1280x800,点击保存,等待系统自动重启生效
5. 系统支持使用APP切换不同的LCD屏,输入dis命令打开APP如下图:
- 选择对应的 eDP/LVDS/MiPi 屏分辨率,然后点击保存,系统自动重启后即可切换到指定的LCD:
6. 背光亮度调节:
- 方法①:点击右下角系统托盘如下图标,打开背光调节APP
- 方法②:控制驱动应用层接口:
echo 100 > /sys/class/backlight/backlight1/brightness
(注:写入数值越大亮度越大,max_brightness 为255)
PowerManager
RTC/Timezone
1.查看当前系统时间:
[root@rk3399:~]# date Wed Jun 8 15:54:09 CST 2022
2. 设置同步硬件时钟:
[root@rk3399:/]# date -s "2022-06-08 17:01:01" Wed Jun 8 17:01:01 CST 2022 [root@rk3399:/]# hwclock -w [root@rk3399:/]# hwclock -r Wed Jun 8 17:01:09 2022 0.000000 seconds
3. 关机断电5秒以上,再开机查看系统时间是否保存:
[root@rk3399:/]# date Wed Jun 8 17:02:30 CST 2022
注:系统默认为网络时间同步,以上RTC测试需要在断外网情况下测试。
4. 时区设置
- 方法① – 修改link文件,如改为中国、上海:
ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime reboot
设置其他时区只需将上面命令中的Asia/Shanghai改为对应的时区城市即可。
- 方法② – 在图形界面依次打开首选项→时间和日期,选择时区如下图:
选择完成后关闭窗口,使用date命令查看时区变化:
CPU
Memory
EMMC
Linux 编程指南
GPIO 应用编程
C参考代码如下:
#include <stdio.h> #include <stdlib.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <unistd.h> #include <string.h> static char gpio_path[100]; //设置GPIO方向、高低电平 static int gpio_config(const char *file, const char *value) { char config_path[100]; int len; int fd; sprintf(config_path, "%s/%s", gpio_path, file); if (0 > (fd = open(config_path, O_WRONLY))) { perror("open error"); return fd; } len = strlen(value); if (len != write(fd, value, len)) { perror("write error"); close(fd); return -1; } close(fd); return 0; } //获取GPIO的方向、电平 static int gpio_get(const char *file) { char get_path[100]; char buf[10]={"\0"}; int len; int fd; sprintf(get_path, "%s/%s", gpio_path, file); if (0 > (fd = open(get_path, O_RDWR))) { perror("open error"); return fd; } if ( 0 > read(fd,buf,10)) { perror("read error"); return fd; } printf(" %s : %s",file,buf); close(fd); return 0; } int main(int argc, char *argv[]) { if (4 != argc) { if (3 != argc) { fprintf(stderr, "set gpio out : %s <gpio> <out> <value>\n", argv[0]); fprintf(stderr, "set gpio in : %s <gpio> <in>\n", argv[0]); exit(-1); } } sprintf(gpio_path, "/sys/class/gpio/gpio%s", argv[1]); if (access(gpio_path, F_OK)) { printf("%s inexistence,export %s... \n",gpio_path,argv[1]); int fd; int len; if (0 > (fd = open("/sys/class/gpio/export", O_WRONLY))) { perror("open error"); exit(-1); } len = strlen(argv[1]); if (len != write(fd, argv[1], len)) { perror("write error"); close(fd); exit(-1); } close(fd); } if (gpio_config("direction", argv[2])) exit(-1); if ( 0 == strcmp("out",argv[2] ) && argc == 4 ) { if(gpio_config("value", argv[3])) exit(-1); } printf("gpio_op%s:\n",argv[1]); if (gpio_get("direction")) exit(-1); if (gpio_get("value")) exit(-1); exit(0); }
交叉编译源码:
aarch64-linux-gnu-gcc -o a.out gpio.c
将编译好的gpio程序使用scp拷贝到 r39s2 主板上,执行测试:
使用方法:
0:./gpio 1 out 0
1:./gpio 1 out 1
UART 应用编程
系统下操作 UART 的测试串口,以 J_RS232 TX3\RX3 测试为例:
J_RS232 TX3\RX3 设备节点为:
/dev/ttysWK2
C参考UART高低电平输入代码如下:
#include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <unistd.h> #include <termios.h> #include <stdio.h> #include <string.h> #include <stdlib.h> #define UART_DEVICE "/dev/ttysWK2" //uart设备文件名称 int main(int argc, char *argv[]) { int fd, res; struct termios oldtio, newtio; char ch; char buf[256] = {0}; //-----------打开uart设备文件------------------ fd = open(UART_DEVICE, O_RDWR|O_NOCTTY);//没有设置O_NONBLOCK。所以这里read和write是堵塞操作 if (fd < 0) { perror(UART_DEVICE); exit(1); } else printf("Open %s successfully\n", UART_DEVICE); //-----------设置操作參数----------------------- tcgetattr(fd, &oldtio);//获取当前操作模式參数 memset(&newtio, 0, sizeof(newtio)); //波特率=115200 数据位=8 使能数据接收 newtio.c_cflag = B115200|CS8|CLOCAL|CREAD; newtio.c_iflag = IGNPAR; tcflush(fd, TCIFLUSH);//清空输入缓冲区和输出缓冲区 tcsetattr(fd, TCSANOW, &newtio);//设置新的操作參数 //------------向urat发送数据------------------- res=write(fd, "Begin Uart tx", 16); while(1) { //从控制台终端获取数据,然后通过uart发送出去,直到接收到!字符 while((ch=getchar()) != '!') { buf[0]=ch; res=write(fd, buf, 1); } buf[0]=ch; buf[1]=' '; res = write(fd, buf, 2); break; } //-------------从uart接收数据------------------- while(1) { res = read(fd, buf, 255);//程序将在这里挂起,直到从uart接收到数据(堵塞操作) if (res == 0) continue; buf[res] = ' '; printf("res = %d, buf = %s\n", res, buf);//将uart接收到的字符打印出来 if (buf[0] == '!')//uart接收到!字符后退出while break; } //------------关闭uart设备文件,恢复原先參数-------- close(fd); printf("Close %s\n", UART_DEVICE); tcsetattr(fd, TCSANOW, &oldtio); //恢复原先的设置 return 0; } }
交叉编译源码:
aarch64-linux-gnu-gcc -o a.out uart.c
将编译好的程序使用 scp 拷贝到 3399 主板上,执行测试:
KEY 应用编程
参考系统下操作Key的方法,获取到key的设备节点为
/dev/input/event2
C参考代码如下:
#include <unistd.h> #include <fcntl.h> #include <stdio.h> #include <stdlib.h> #include <linux/input.h> #include <sys/select.h> #define INPUT_DEVICE "/dev/input/event2" int main(int argc, char **argv){ int fd; struct input_event event; ssize_t bytesRead; int ret; fd_set readfds; if ( 0 > (fd = open(INPUT_DEVICE,O_RDONLY))) { perror("open error"); return fd; } while(1){ FD_ZERO(&readfds); FD_SET(fd,&readfds); ret = select(fd + 1, &readfds, NULL, NULL, NULL); if (ret == -1){ fprintf(stderr,"select call on%s : an error ocurred",argv[1]); break; } if(FD_ISSET(fd,&readfds)){ bytesRead = read(fd, &event,sizeof(struct input_event)); if(bytesRead == -1 ) fprintf(stderr,"bytesRead :%ld : an error ocurred",bytesRead); } if(event.type == EV_KEY && (event.value == 0 || event.value == 1)) { printf("key %s\n",(event.value) ? "pressed" : "released"); } } close(fd); return EXIT_SUCCESS; }
交叉编译源码:
aarch64-linux-gnu-gcc -o key1 key.c
将编译好的程序使用 scp 拷贝到 r39s2 主板上,执行测试,按动 key 打印如下:
- 按下按键时显示:key pressed
- 松开按键时显示:key released