0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

【飞凌RZ/G2L开发板试用体验】5. 迪文串口屏事件分析

开发板试用精选 来源:开发板试用 作者:电子发烧友论坛 2022-10-24 16:58 次阅读

本文来源电子发烧友社区,作者:voidpbq, 帖子地址:https://bbs.elecfans.com/jishu_2303725_1_1.html


一、前言

本章介绍下OKG2L的uart引脚、测试方法以及如何处理迪文串口的uart信息

二、硬件

2.1 电路图

OKG2L支持三个uart口,其中

image.png

GPIO33、35分别为rx,tx

image.png

image.png

在底板的P23,从下往上数左侧第9个为uart的rx(接收端),可以查看uart图标找到对应位置。

35是开发板的TX,33是开发板的RX。

使用电脑的串口工具时,连接usb ttl小板,开发板TX接小板RX。

2.2 连接图

连接迪文串口屏,开发板tx连接串口屏rx

连接如下图

image.png

三、代码

3.1 fltest_uarttest——官方实现uart基础测试

串口代码路径:drivers/tty/serial/sh-sci.c

开发板中路径:/dev/ttySX

外接的uart时ttySC1

官方提供的cmd:fltest_uarttest

image.png

fltest_uarttest工具代码路径:OKG2L-linux-sdk10appsrcforlinx-cmduarttest

我的代码也是基于这个增加了串口件通信
PS:注意,这里是一位一位获取数据的,经我测试,一次读取最多8位,所以需要增加新的机制判断一组数据是否获取完毕。
详见如下问题一节。

3.2 实现迪文串口间通信

此代码为我基于官方实现添加了迪文串口屏的事件判定,开源,禁止商用,谢谢。

uart_example.c



#include "dwin.h"

#include           /*��׼�����������*/
#include          /*��׼�����ⶨ��*/
#include          /*Unix��׼��������*/
#include       /**/
#include        /**/
#include           /*�ļ����ƶ���*/
#include         /*PPSIX�ն˿��ƶ���*/
#include           /*����Ŷ���*/
#include	 
#include     
#include     
#include    "stdbool.h"

#define uint8_t u_int8_t
#define bool _Bool

extern void u8_to_char(uint8_t * , char ** );
extern int judge_dwin_cmd(uint8_t ** );
extern int get_len(uint8_t *cmd_u8);
extern dwin_event_flag uart_judge_dwin_event(i_dwin_cmd * cmd);
extern i_dwin_cmd temp_cmd_recv;
extern dwin_event_key event_key_list[EVENT_KEY_NUM_MAX];
extern dwin_event_key_spec event_key_spec[EVENT_KEY_SPEC_NUM_MAX];

extern c_dwin_cmd cmd_recv_char; // from dwin
extern c_dwin_cmd cmd_send_char; // send to dwin
extern dwin_event_flag c_judge_dwin_event(c_dwin_cmd * cmd);
extern void c_dwin_cmd_analysis(char * in,c_dwin_cmd *cmd);
extern void c_print_cmd(c_dwin_cmd *cmd);

#define UART_ID                 0

#define UART_RECV_LEN           1024
#define BUF_RX_MAX 512
#define LEN_CHAR_TEMP 17

c_dwin_cmd cmd_char;

int search_str_end(uint8_t *str_z, int count)
{
int temp_zero = 1;
int temp_count = count -1;  // 有效字符11个,12个是0x00
printf("init count = %d, temp_count = %dn",count,temp_count);
uint8_t *str_temp1 = str_z;

while(1)
{
printf("str = [%02X], temp_zero = [%d], temp_count = [%d]n",*str_temp1,temp_zero,temp_count);
// if find 10 zero, will return count
if(*str_temp1 != 0x00)
{
printf("value = %02X, %ldn",*str_temp1,str_temp1-str_z);
temp_count += temp_zero;
str_temp1++;
temp_zero = 1;
}
else
{
temp_zero++;
printf("value = %02X, %ldn",*str_temp1,str_temp1-str_z);
}

if(temp_zero > 10)
break;

}
printf("init count = %d, temp_count = %dn",count,temp_count);
return temp_count;

}

int my_strlen(uint8_t *str)
{
printf("enter my_strlen");
uint8_t *str_temp = str;
// assert(str);
int count = 0;

// while (*str != '') // this will ignore 0x00
while (*str_temp != '')
{
printf("value = %02X, %ldn",*str_temp,str_temp-str);
count++;
str_temp++;
}
// has found 0x00, str end. but uart data may contents 0x00 .. 0x00
// so, need to judge next value
count = search_str_end(str_temp-1,count);

return count;

}

int judge_char(uint8_t * str)
{
if (str != NULL){
// not empty
printf("enter judge_char");
if (my_strlen(str) != 0) {
// not ''
return 1;
}
else
return 0;
}
else
return -1;
}

void func_uart_write(uint8_t * str, int fd)
{
printf("enter func_uart_write");
unsigned int ret;

// plus 3 due to dwin has head1/2/len
ret = write(fd, str, *(str+2));
if (ret <0)
{
printf("%s, %d: LzUartInit(%d) failed!n", __FILE__, __LINE__, ret);
return;
}

}

void uint8_2_char(uint8_t * in,char * out, int cp_len)
{
printf("raw uint8_t data[");
int cmd_len=*(in+2)+3;
char tmp[3];
memset(tmp,0x00,3);
for(int i =0;i< cp_len;i++)
{
printf("%02X",*(in+i));
sprintf(tmp,"%02X",*(in+i));
strcat(out,tmp);

memset(tmp,0x00,3);
}
printf("]n");

}

void main(void)
{
int fd;
int nread;
char buf_rx[BUF_RX_MAX+1];
int n=0,i=0;
char dev[]  = "/dev/ttySC1";
struct termios oldtio,newtio;
speed_t speed = B115200;
int next_option,havearg = 0,flow = 0;


/*  打开串口 */
fd = open(dev, O_RDWR | O_NONBLOCK| O_NOCTTY | O_NDELAY);
if (fd < 0)	{
printf("Can't Open Serial Port!n");
exit(0);	
}

printf("Welcome to uart buf_txn");

//save to oldtio
tcgetattr(fd,&oldtio);
bzero(&newtio,sizeof(newtio));
newtio.c_cflag = speed|CS8|CLOCAL|CREAD;
newtio.c_cflag &= ~CSTOPB;
newtio.c_cflag &= ~PARENB;
newtio.c_iflag = IGNPAR;
newtio.c_oflag = 0;
// newtio.c_cc[VTIME]=10;
tcflush(fd,TCIFLUSH);
tcsetattr(fd,TCSANOW,&newtio);
tcgetattr(fd,&oldtio);

memset(buf_rx,0,BUF_RX_MAX+1);

char buf_tx[100]="forlinx_uart_test.1234567890...";

printf("Send buf_tx data:n[%s] [%ld]n",buf_tx,strlen(buf_tx));
write(fd, buf_tx, strlen(buf_tx));
fd_set rd;

int flag_rx=0;
bool flag_rx1= false;
bool flag_rx2 = false;

bool flag_print=true;
int cmd_len=0;

uint8_t str_send[UART_RECV_LEN] = "HelloWorld!n";
char str_send_char[513] = "";
uint8_t recv_int8[UART_RECV_LEN];
char recv_char[UART_RECV_LEN];
uint8_t recv_int8_t[9];
char recv_char_t[LEN_CHAR_TEMP];

char *recv_char_p=NULL;

bool status_uart_send = false;

init_dwin_status();

// ------------------- test uint8 to char -------------------
uint8_t xxx[]={0X5A,0XA5,0X05,0X82,0X10,0X00,0X00,0X01};
// u8_2_char(xxx);
char *yyy=(char *)malloc(get_len(recv_int8));
u8_to_char(xxx,&yyy);
// yyy = (char *)u8_to_char(xxx);
printf("yyy = %sn",yyy);
// ------------------- test uint8 to char -------------------

printf("enter whilen");

while (1)
{
// ----------------- uart read -----------------
memset(recv_int8_t,0x00,UART_RECV_LEN);
int nread = read(fd, recv_int8_t, UART_RECV_LEN);
if (nread >  0)
{
if(*recv_int8_t==0x5a && *(recv_int8_t+1)==0xa5)
{
cmd_len=*(recv_int8_t+2)+3;
cmd_len=2*cmd_len ;
printf("ncmd len = %dn",cmd_len);

}

memset(recv_char_t,0x00,LEN_CHAR_TEMP);
uint8_2_char(recv_int8_t,recv_char_t, nread);

strcat(recv_char,recv_char_t);

flag_rx1=true;
flag_rx2=true;


}
else if(nread < 0 )
{
printf("%s, %d: LzUartInit(%d) failed!n", __FILE__, __LINE__, nread);
return;
}
if(nread == 0)
{
// 判断传输停止
if(flag_rx1==true&&flag_rx2==true)
{
flag_rx2=false;
}
else if(flag_rx1==true&&flag_rx2==false)
{
flag_rx1=false;

if(strlen(recv_int8)>0)
{
if(strlen(recv_char)==cmd_len)
{
printf(">>>recv_cmd_char = [%s]n",recv_char);
c_dwin_cmd_analysis(recv_char,&cmd_recv_char);
memset(recv_char,0x00,UART_RECV_LEN);
tcflush(fd, TCIOFLUSH);
}

}


}


}

}
close(fd);

return;
}

dwin.h



#include "stddef.h"
#include "string.h"
#include "stdio.h"
#include "stdlib.h"
#include "stdbool.h"
#include "stdint.h"

#define TRUE 1
#define FALSE 0
#define uint8_t u_int8_t
#define bool _Bool

typedef enum{
EVENT_FLAG_OK = 0X0,
EVENT_FLAG_AUDIO_RECORD = 0x3,
EVENT_FLAG_AUDIO_PLAY = 0x4,
EVENT_FLAG_CAM_SCAN = 0x5,
EVENT_FLAG_NFC_SCAN = 0x6,
EVENT_FLAG_BOOK_SEARCH = 0x10,
EVENT_FLAG_BOOK_INPUT = 0x11,
EVENT_FLAG_UNKOWN = -1,
}dwin_event_flag;

typedef enum{
// EVENT_FLAG_STATUS_START = 0x0,
EVENT_FLAG_STATUS_ING = TRUE,
EVENT_FLAG_STATUS_STOP = FALSE,
EVENT_FLAG_STATUS_ERROR = -1,
}dwin_event_flag_status;

typedef enum{
EVENT_TYPE_DWIN_SEND = 0x0,  // uart read
EVENT_FLAG_DWIN_RECV = 0x1,  // uart write
}dwin_event_type;

#define DWIN_CMD_LEN_U8_MAX 259

typedef struct
{
uint8_t head[2];
uint8_t len;
uint8_t wr;
uint8_t addr[2];
uint8_t * value;
// uint8_t cmd_u8[DWIN_CMD_LEN_U8_MAX];
uint8_t * cmd_u8;
char * cmd_char;
}i_dwin_cmd;

void uart_recv_value_cut(uint8_t * recv_all);
// dwin_event_flag uart_judge_dwin_event(char *str);
dwin_event_flag uart_judge_dwin_event(i_dwin_cmd * cmd);

void print_dwin_cmd(i_dwin_cmd cmd);

char * dwin_cmd_uint8_t2char(i_dwin_cmd cmd);

char * uint8_t2char(uint8_t value);

char * uint8_t2char_list(uint8_t * p_dwin_u8_value,int len);

void change_dwin_status(dwin_event_flag event_flag);

// UART recv/send judge dwin_event
#define EVENT_KEY_NUM_MAX 10
// #define EVENT_KEY_MAX -1

// function
void func_open_record();
void func_close_record();
void func_open_cam();
void func_close_cam();
void func_open_nfc();
void func_close_nfc();

#define EVENT_NAME_MAX 11
#define EVENT_FLAG_NAME_MAX 30
#define EVENT_KEY_VALUE_MAX 11   //"3000 0001"  is 8

typedef struct
{
dwin_event_flag flag;
char event_name[EVENT_NAME_MAX];
dwin_event_flag_status status;
char key[EVENT_KEY_VALUE_MAX];   // key[0,3] addr key[4,7] value
char flag_name[EVENT_FLAG_NAME_MAX];
void (*open)();
void (*close)();
}dwin_event_key;

dwin_event_key event_key_list[EVENT_KEY_NUM_MAX];
// {
//     // {
//     //     event_flag, event_name,
//     //     event_status,
//     //     event_addr, event_flag_name,
//     //     event_ops1, enent_ops1
//     // },

//     {
//         EVENT_FLAG_AUDIO_RECORD, "record",
//         EVENT_FLAG_STATUS_STOP,
//         "1503", "EVENT_FLAG_AUDIO_RECORD",
//         func_open_record,   func_close_record
//     },

//     {
//         EVENT_FLAG_CAM_SCAN,    "cam",
//         EVENT_FLAG_STATUS_STOP,
//         "1504", "EVENT_FLAG_CAM_SCAN",
//         func_open_cam,      func_close_cam
//     },

//     {
//         EVENT_FLAG_NFC_SCAN,    "nfc",
//         EVENT_FLAG_STATUS_STOP,
//         "1505", "EVENT_FLAG_NFC_SCAN",
//         func_open_nfc,      func_close_nfc
//     },

//     {
//         EVENT_FLAG_UNKOWN,  "unknow",
//         EVENT_FLAG_STATUS_STOP,
//         "0000" , "EVENT_FLAG_UNKOWN"
//     }
// };

typedef struct
{
char key[EVENT_KEY_VALUE_MAX];   // key[0,3] addr key[4,7] value
char event_name[EVENT_FLAG_NAME_MAX];
void (*func)();
}dwin_event_key_spec;

void func_search();
void func_spec_end();

void searc_spec_event();

#define EVENT_KEY_SPEC_VALUE "over"
#define EVENT_KEY_SPEC_NUM_MAX 20
dwin_event_key_spec event_key_spec[EVENT_KEY_SPEC_NUM_MAX];
// {
//     // special event, just one ops
//     // {
//     //     event_key, event_name,
//     //     event_ops
//     // },

//     {
//         "1502010012",  "search",
//         func_search
//     },
//     // ...

//     {EVENT_KEY_SPEC_VALUE,  "end",
//         func_spec_end
//     }
// };

void change_dwin_status_key(dwin_event_key *in_key);

void change_cmd_send_status(dwin_event_flag temp_event_flag);

// -------------------- basic func  --------------------

void copy_u8_2_u8(uint8_t * u8_raw);

void u8_to_char(uint8_t * in_u8, char ** out);

uint8_t * u8_to_u8(uint8_t * in_u8);

// -------------------- dwin func --------------------
void dwin_cmd_init_send();
void init_dwin_status();
void i_dwin_cmd_clear(i_dwin_cmd * cmd);

// get u8 from example
void uart_dwin_cmd_analysis(uint8_t *str);

void copy_u8_to_cmdu8(i_dwin_cmd *cmd, uint8_t * u8);

//int my_strlen(uint8_t *str);

// int search_str_end(uint8_t *str_z, int count);
// int my_strlen(uint8_t *str);
// int judge_char(uint8_t * str);

#define DWIN_CMD_CHAR_ADDR_VALUE 8
#define DWIN_CMD_CHAR_VALUE_VALUE 12
#define DWIN_CMD_CHAR_MAX 513
#define DWIN_CMD_U8_MAX 256

// add for char
#define C_CMD_POINT_HEAD 0
#define C_CMD_POINT_LEN 4
#define C_CMD_POINT_WR 6
#define C_CMD_POINT_ADDR 8
#define C_CMD_POINT_VALUE 12

typedef struct
{
char head[5];
char len[3];
char wr[3];
char addr[5];
char * value;
char * cmd_char;
}c_dwin_cmd;


四、测试结果

image.png

这是检索事件

image.png

录音及停止事件

image.png

扫码及停止

image.png

nfc检索及停止

PS:电子发烧友的代码显示有异常,有兴趣的话去我的csdn查看,后续会更新出来。
https://blog.csdn.net/qq_38091632

六、编译

命令:$CC uart_example.c dwin.c -o dwin_test

五、问题

5.1 字符串地址传递

void u8_to_char(uint8_t * , char ** );

子函数内如果使用malloc分配空间,建议使用char **进行地址传递。

也可以在main函数中先分配,再传指针进子函数。

5.2 uart数据

串口传输可以选择hex还是字符串,我们在使用串口工具测试时选择hex,模拟实际迪文屏数据传输。

此外注意传入的数据为uint_8,需要转换为字符串进行分析。

原数据:0x5AA5
字符串:"5AA5"

传出时再进行字符串转为uint_8

5.3 一次接收8位

使用read函数对ttySC1进行读取,一次只能读8位。

由于迪文屏的串口数据结构,其中的第三个字节传输的是后续数据的长度。

比如0x5AA5 06 82 1000 01 1234

其中的06就是后续的82 1000 01 1234长度,所以先计算出一组数据长度为06+3,3是前面的5AA5加上len。

代码中先判断head为5AA5,然后存入len,当接收到的字符串长度为len*2,一组接收完毕。

乘以2是因为uint_8转换为两位char。

六、小结

串口通信较为简单,实现了基础的读写功能后再结合串口屏的传输协议进行数据处理。

此功能应该适用于其他linux开发板,后续可以在其他平台上试试。

目前上述代码只是实现了基本的事件判断架构,后续各种判断条件可以自行添加,只需要定义匹配的字符串以及执行的函数即可。

最后,感谢飞凌提供的试用机会。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • 飞凌
    +关注

    关注

    0

    文章

    130

    浏览量

    15955
  • 开发板试用
    +关注

    关注

    3

    文章

    299

    浏览量

    1912
收藏 人收藏

    评论

    相关推荐

    瑞萨RZ/G2L串口SCI的使用(上)

    瑞萨RZ/G2L串口简称SCI,全称Serial Communication Interface。
    的头像 发表于 01-17 12:19 645次阅读
    瑞萨<b class='flag-5'>RZ</b>/<b class='flag-5'>G2L</b><b class='flag-5'>串口</b>SCI的使用(上)

    AM6254开发板试用】+5内核编译串口芯片Linux驱动(原创)

    /jishu_2374537_1_1.html 【AM6254开发板试用】+2机器视觉环境搭建(原创) -
    发表于 09-23 23:21

    AM6254开发板试用】 4-机器视觉(原创)

    /jishu_2374537_1_1.html 【AM6254开发板试用】+2机器视觉环境搭建(原创) -
    发表于 09-12 22:57

    【米尔瑞萨RZ/G2L开发板-试用体验】认识一下米尔瑞萨RZ/G2L开发板的核心

    收到米尔瑞萨RZ/G2L开发板后一直对米尔旗下开发板的做工感到非常精致,同时也有着很强大的功能,也一直很喜欢米尔系列开发板。 引领工业市场从
    发表于 07-29 00:21

    【米尔瑞萨RZ/G2L开发板-试用体验】米尔瑞萨RZ/G2L开发板使用SSH登录

    收到的米尔瑞萨RZ/G2L开发板上电测试一下SSH登录方式和其它测试! SSH登录 在使用之前,需要事先连接网络,笔者这里使用的是以太网,事先需要使用串口的登录,然后输入以下命令
    发表于 06-11 21:47

    【米尔瑞萨RZ/G2L开发板-试用体验】创建TCP服务器

    在米尔RZ/G2L开发板上用C 创建TCP服务器
    的头像 发表于 05-27 08:59 7503次阅读
    【米尔瑞萨<b class='flag-5'>RZ</b>/<b class='flag-5'>G2L</b><b class='flag-5'>开发板</b>-<b class='flag-5'>试用</b>体验】创建TCP服务器

    米尔瑞萨RZ/G2L开发板 安装交叉编译器

    米尔瑞萨RZ/G2L开发板安装交叉编译器
    的头像 发表于 05-26 22:05 1714次阅读
    米尔瑞萨<b class='flag-5'>RZ</b>/<b class='flag-5'>G2L</b><b class='flag-5'>开发板</b> 安装交叉编译器

    150套开发板免费送!还有5G手机拿?米尔RZ/G2L开发板创意秀

    人间最美五月天 不负韶华不负卿 米尔又来送板子了 不是3套,也不是4套 150套****米尔RZ/G2L开发板 送!免费!板卡不回收! 01 这是什么样的有奖活动? 米尔RZ/
    发表于 05-24 16:36

    【米尔瑞萨RZ/G2L开发板-试用体验】米尔瑞萨RZ/G2L开发板开箱视频

    今天刚刚收到米尔瑞萨RZ/G2L开发板,拆开包裹后给人的感觉是惊艳,板卡设计真的很棒,来看看视频做个简单了解吧。 更多板卡可以登录官网了解哦。https://www.myir.cn/
    发表于 05-22 21:58

    【米尔瑞萨RZ/G2L开发板-试用体验】米尔-瑞萨RZG2L - 64位双核MPU开发板开箱测评

    刚收到米尔瑞萨RZ/G2L开发板打开包装后看到的很大的一块黑色PCB,做工精美的开发板,给人眼前一亮的感觉。 首先来介绍以下这家公司: 深圳市米尔电子有限公司,是一家专注于嵌入式处理器
    发表于 05-22 21:53

    【米尔瑞萨RZ/G2L开发板-试用体验】LCD 显示测试

    实验器材 1、米尔瑞萨RZ/G2L开发板 2、MY-TFT070-K显示 实现步骤 1、连接开发板
    发表于 05-22 19:26

    米尔瑞萨RZ/G2L开发板 TF卡读写速度测试

    米尔瑞萨RZ/G2L开发板TF卡读写测试
    的头像 发表于 05-22 09:07 1007次阅读
    米尔瑞萨<b class='flag-5'>RZ</b>/<b class='flag-5'>G2L</b><b class='flag-5'>开发板</b> TF卡读写速度测试

    【米尔瑞萨RZ/G2L开发板-试用体验】开箱 + 开机

    感谢 感谢电子发烧友论坛、感谢米尔电子,把米尔瑞萨RZ/G2L开发板试用话动的机会给了我。最近事情比较多,赶在这个空挡时间完成开箱报告。 开箱 第一次拿到米尔电子的
    发表于 05-18 19:33

    米尔瑞萨RZ/G2L开发板-初体验

    介绍米尔RZ/G2L开发板
    的头像 发表于 05-15 09:10 701次阅读
    米尔瑞萨<b class='flag-5'>RZ</b>/<b class='flag-5'>G2L</b><b class='flag-5'>开发板</b>-初体验

    【米尔瑞萨RZ/G2L开发板-试用体验】开箱

    感谢 感谢电子发烧友论坛、感谢米尔电子,把米尔瑞萨RZ/G2L开发板试用话动的机会给了我。虽然周五就收到了开发板,但是由于复阳了,为了能及时
    发表于 05-14 19:41