树莓派的的串口通信协议

news2024/9/28 11:20:08

首先,回顾一下串口的核心知识点,也是面试重点

  • 串口通信通常使用在多机通讯中
  • 串口通信是全双工的
  • 决定串口通信的成功与否的是 数据格式 和 波特率
  • 数据格式:1. 数据位 2.停止位 3. 奇偶校验位

树莓派恢复串口

回忆前几节树莓派刷机的开端,为了能通过串口连接到树莓派,事先将串口设置为了系统交互的方式,这会导致无法进行正常的串口的开发,况且现在已经成功可以使用SSH登录,所以可以将串口设置回来了:

  • 修改 /boot/cmdline.txt:
1. sudo vi /boot/cmdline.txt
2. 将“console=serial,115200”删除

  • sudo reboot重启 

设置完成!

树莓派的串口开发

再打开串口后,由于都是基于wiringPi库,所以串口开发和香橙派的也是一样一样的,这里我直接把在香橙派写好的串口开发文件上传过来然后直接开始写:

(注意,树莓派的串口驱动文件是/dev/下的ttyAMA0

mjm_uart_tool.c:

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <stdarg.h>
#include <string.h>
#include <termios.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include "wiringSerial.h"

int myserialOpen (const char *device, const int baud)
{
	struct termios options ;
	speed_t myBaud ;
	int status, fd ;
	switch (baud){
		case 9600: myBaud = B9600 ; break ;
		case 115200: myBaud = B115200 ; break ;
	}
	if ((fd = open (device, O_RDWR | O_NOCTTY | O_NDELAY | O_NONBLOCK)) == -1)
		return -1 ;
	fcntl (fd, F_SETFL, O_RDWR) ;
	// Get and modify current options:
	tcgetattr (fd, &options) ;
	cfmakeraw (&options) ;
	cfsetispeed (&options, myBaud) ;
	cfsetospeed (&options, myBaud) ;
	options.c_cflag |= (CLOCAL | CREAD) ;
	options.c_cflag &= ~PARENB ;
	options.c_cflag &= ~CSTOPB ;
	options.c_cflag &= ~CSIZE ;
	options.c_cflag |= CS8 ;
	options.c_lflag &= ~(ICANON | ECHO | ECHOE | ISIG) ;
	options.c_oflag &= ~OPOST ;
	options.c_cc [VMIN] = 0 ;
	options.c_cc [VTIME] = 100 ; // Ten seconds (100 deciseconds)
	tcsetattr (fd, TCSANOW, &options) ;
	ioctl (fd, TIOCMGET, &status);
	status |= TIOCM_DTR ;
	status |= TIOCM_RTS ;
	ioctl (fd, TIOCMSET, &status);
	usleep (10000) ; // 10mS
	return fd ;
}

void serialSendstring (const int fd, const char *s)
{
	int ret;
	ret = write (fd, s, strlen (s));
	if (ret < 0)
		printf("Serial Puts Error\n");
}

int serialGetstring (const int fd, char *buffer)
{
	int n_read;
	n_read = read(fd, buffer,32);
	return n_read;
}

int serialDataAvail (const int fd)
{
  int result ;

  if (ioctl (fd, FIONREAD, &result) == -1)
    return -1 ;

  return result ;
}

mjm_uart_tool.h:

int myserialOpen (const char *device, const int baud);
void serialSendstring (const int fd, const char *s);
int serialGetstring (const int fd, char *buffer);
int serialDataAvail (const int fd);

serial_mjm_test.c:

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <stdarg.h>
#include <string.h>
#include <termios.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <pthread.h>
#include <errno.h>
#include "mjm_uart_tool.h"

void *write_serial(void *arg)
{
	char *sendbuf;
	sendbuf = (char *)malloc(32*sizeof(char));

	while(1){
		memset(sendbuf,'\0',32*sizeof(char));
		fgets(sendbuf,sizeof(sendbuf),stdin);
		serialSendstring (*((int *)arg), sendbuf) ;
	}

	pthread_exit(NULL);

}


void *read_serial(void *arg)
{
	char readbuf[32] = {'\0'};
	while(1){
		while(serialDataAvail (*((int *)arg))){
			serialGetstring (*((int *)arg),readbuf) ;
			printf("-> %s\n",readbuf);
			memset(readbuf,'\0',32);
		}
	}

	pthread_exit(NULL);
}



int main ()
{
	int fd ;

	int ret;
	pthread_t read_thread;
	pthread_t write_thread;

	if ((fd = myserialOpen ("/dev/ttyAMA0", 115200)) < 0) //打开驱动文件,配置波特率
	{
		fprintf (stderr, "Unable to open serial device: %s\n", strerror (errno)) ;
		return 1 ;
	}

	/*	if (wiringPiSetup () == -1)
		{
		fprintf (stdout, "Unable to start wiringPi: %s\n", strerror (errno)) ;
		return 1 ;
		}*/

	ret = pthread_create(&read_thread,NULL,read_serial,(void *)&fd);
	if(ret != 0){
		printf("read_serial create error\n");
		return 1;
	}
	ret = pthread_create(&write_thread,NULL,write_serial,(void *)&fd);
	if(ret != 0){
		printf("write_serial create error\n");
		return 1;
	}

	pthread_join(read_thread,NULL);
	pthread_join(write_thread,NULL);

	return 0 ;
}

编译

由于此处实现的串口函数是我参考wiringPi库自己实现的,所以无需链wiringPi库,只需链线程库就ok

gcc serial_mjm_test.c mjm_uart_tool.c -lpthread

运行效果

可见,轻松的实现了通讯效果!

封装动态库 

由于这里使用的是我自己封装的串口函数,所以可以根据上上节的知识将它封装成动态库:

详见我之前的博文:

使用树莓派学习Linux系统编程的 --- 库编程(面试重点)-CSDN博客

  • 生成动态库,命名为“mjmserial
gcc -shared -fpic mjm_uart_tool.c -o libmjmserial.so
  •  编译main函数所在C文件,链库,将可执行文件命名为“serialtest”:
gcc serial_mjm_test.c -L ./ -lmjmserial -lpthread -o serialtest
  • 此时可以使用环境变量的方法指定动态库搜索路径或者直接复制动态库到/usr/lib下,由于后者上节实现过了,这次尝试前者:

写一个脚本:

1. vi serialtest.sh
2. 内容为:“
export LD_LIBRARY_PATH="/home/pi/mjm_code/"
 
./serialtest”
3. chmod +x serialtest.sh

  • 最后直接执行“ ./serialtest.sh ”:

可见,运行成功! 此时我只需要提供动态库的.so文件和.h文件给别人,别人就可以调用我封装好的串口函数了,并且别人无法看到我封装函数的具体实现

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1235821.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

ES 查询语法-详解

文章目录 1.DSL查询文档1.1.DSL查询分类1.2.全文检索查询1.2.1.使用场景1.2.2.基本语法1.2.3.总结 1.3.精准查询1.3.1.term查询1.3.2.总结 1.DSL查询文档 elasticsearch的查询依然是基于JSON风格的DSL来实现的。 1.1.DSL查询分类 Elasticsearch提供了基于JSON的DSL&#xff…

gwas数据获取如何获取完整的GWAS summary数据(1)------GWAS catalog数据库

IEU OpenGWAS project (mrcieu.ac.uk) UK Biobank - UK Biobank GWAS Catalog 在孟德尔随机化&#xff08;Mendelian randomization&#xff0c;MR&#xff09;研究中&#xff0c;对于暴露数据我们只需要那些显著的SNP信息&#xff0c;这样的信息在各种GWAS数据库中都是很容…

2019ICPC南京站

A A Hard Problem 题意&#xff1a;给定一个正整数 n &#xff0c;你需要找出最小整数 k&#xff0c;满足&#xff1a;从{1,2,⋯,n}中任意选择长度为k的子集&#xff0c;存在两个不同的整数 u,v∈T, 且 u 是 v 的因数。 思路&#xff1a;打表找规律 #include <bits/std…

分类问题的评价指标

一、logistic regression logistic regression也叫做对数几率回归。虽然名字是回归&#xff0c;但是不同于linear regression&#xff0c;logistic regression是一种分类学习方法。 同时在深度神经网络中&#xff0c;有一种线性层的输出也叫做logistic&#xff0c;他是被输入…

【docker下安装jenkins】(一)

目的&#xff1a;在Linux操作系统&#xff08;x86_64)下&#xff0c;使用docker部署jenkins&#xff0c;python使用压缩包安装 安装jenkins的步骤 &#xff11;、编排jenkins的docker-compose.yml文件 说明&#xff1a;这里遇到部署jenkins后&#xff0c;占用内存8G,所以重新…

智能时代的智能工具(gpt)国产化助手

目前gpt对代码以及其他领域都是可以支持&#xff0c;在国内有很多&#xff0c;常用的百度的 文心一言 &#xff0c;阿里的 通义千问 &#xff0c;还有&#xff08;“豆包”&#xff0c;“”讯飞星火“”&#xff09;等&#xff0c;除了写代码可以外&#xff0c;也可以很好的支持…

设计模式—结构型模式之享元模式

设计模式—结构型模式之享元模式 享元模式(Flyweight Pattern)&#xff0c;运用共享技术有效地支持大量细粒度对象的复用。系统只使用少量的对象&#xff0c;而这些对象都很相似&#xff0c;状态变化很小&#xff0c;可以实现对象的多次复用。对象结构型。 在享元模式中可以共…

OpenCV中的形态学8

文章目录 形态学概述图像全局二值化阈值类型自适应阈值二值化OpenCV腐蚀获取形态学卷积核OpenCV膨胀开运算闭运算形态学梯度顶帽运算黑帽操作小结 形态学概述 开运算&#xff1a;先做腐蚀后做膨胀&#xff08;腐蚀可以理解为缩小&#xff09; 闭运算&#xff1a;先膨胀后腐蚀 …

LeetCode209.长度最小的子数组(滑动窗口法、暴力法)

LeetCode209.长度最小的子数组 1.问题描述2.解题思路3.代码4.知识点 1.问题描述 给定一个含有 n 个正整数的数组和一个正整数 target 。找出该数组中满足其总和大于等于 target 的长度最小的 连续子数组 [numsl, numsl1, ..., numsr-1, numsr] &#xff0c;并返回其长度。如果…

OpenGeometry 开源社区特聘子虔科技云CAD专家 共建云几何内核

11月5日&#xff0c;由广东省工业和信息化厅、广东省科学技术厅、广东省教育厅、深圳市人民政府主办的2023工业软件生态大会在广东省深圳市召开。 开幕式上&#xff0c;备受关注的云几何内核开源平台——OpenGeometry开源社区正式发布。这意味着在几何引擎领域将通过开源这个模…

界面控件DevExpress WPF流程图组件,完美复制Visio UI!(一)

DevExpress WPF Diagram&#xff08;流程图&#xff09;控件帮助用户完美复制Microsoft Visio UI&#xff0c;并将信息丰富且组织良好的图表、流程图和组织图轻松合并到您的下一个WPF项目中。 P.S&#xff1a;DevExpress WPF拥有120个控件和库&#xff0c;将帮助您交付满足甚至…

专业课140+总分420+东南大学920专业综合考研,信息学院通信专业考研分享

专业课140总分420东南大学920专业综合考研&#xff0c;信息学院通信专业考研分享 我是三月开始系统考研备战&#xff0c;寒假先看的高数全书&#xff0c;奈何在家效率极其低下&#xff0c;才草草看了前三四章。回校后学习的比较认真&#xff0c;每天大概保持10个小时左右&…

List操作的一些常见问题

文章目录 阿里巴巴开发手册强制规约&#xff1a;1. Arrays.asList转换基本类型数组2. Arrays.asList返回的List不支持增删操作3. 对原始数组的修改会影响到我们获得的那个List4. ArrayList.subList强转ArrayList导致异常5. ArrayList中的subList切片造成OOM6.Copy-On-Write 是什…

nodejs微信小程序+python+PHP-维斯公司财务管理系统的设计与实现-计算机毕业设计推荐

目 录 摘 要 I ABSTRACT II 目 录 II 第1章 绪论 1 1.1背景及意义 1 1.2 国内外研究概况 1 1.3 研究的内容 1 第2章 相关技术 3 2.1 nodejs简介 4 2.2 express框架介绍 6 2.4 MySQL数据库 4 第3章 系统分析 5 3.1 需求分析 5 3.2 系统可行性分析 5 3.2.1技术可行性&#xff1a;…

【libGDX】使用Mesh绘制三角形

1 Mesh 和 ShaderProgram 简介 1.1 创建 Mesh 1&#xff09;Mesh 的构造方法 public Mesh(boolean isStatic, int maxVertices, int maxIndices, VertexAttribute... attributes) public Mesh(boolean isStatic, int maxVertices, int maxIndices, VertexAttributes attribut…

使用MONAI轻松加载医学公开数据集,包括医学分割十项全能挑战数据集和MedMNIST分类数据集

在深度学习中&#xff0c;使用公开数据集具有以下优点&#xff1a; 提供了一个标准化的基准来比较不同算法或模型的性能&#xff0c;因为这些公共数据集被广泛使用&#xff0c;许多研究人员都使用它们来评估他们的方法。可以节省大量的时间和金钱&#xff0c;因为这些数据集已…

Pytorch从零开始实战10

Pytorch从零开始实战——ResNet-50算法实战 本系列来源于365天深度学习训练营 原作者K同学 文章目录 Pytorch从零开始实战——ResNet-50算法实战环境准备数据集模型选择开始训练可视化模型预测总结 环境准备 本文基于Jupyter notebook&#xff0c;使用Python3.8&#xff0c…

成长在于积累——https 认证失败的学习与思考

1. 引言 本周二长城项目在收尾过程中&#xff0c;出现了一个车端无法进行注册的问题&#xff1a;curl提示证书认证失败&#xff08;其实已经能确认问题方向了&#xff0c;运维人员去确认证书问题即可&#xff09;。虽然最终的原因是由于长城运维人员导致的。但是这个过程让我颇…

享元模式 rust和java的实现

文章目录 享元模式介绍实现javarust实现代码 rust仓库rust仓库 享元模式 享元模式&#xff08;Flyweight Pattern&#xff09;主要用于减少创建对象的数量&#xff0c;以减少内存占用和提高性能。这种类型的设计模式属于结构型模式&#xff0c;它提供了减少对象数量从而改善应…