大家好,我是痞子衡,是正经搞技术的痞子。今天痞子衡给大家讲的是嵌入式里数据差错控制技术-重复校验

  在嵌入式应用里,除了最核心的数据处理外,我们还会经常和数据传输打交道。数据传输需要硬件传输接口的支持,串行接口由于占用引脚少的优点目前应用比并行接口广泛,常用的串行接口种类非常多,比如UART,SPI,I2C,USB等,在使用这些接口传输数据时避不可免会遇到一个问题,如果传输过程中遇到未知硬件干扰发生bit错误怎么办?

  痞子衡今天给大家讲的就是数据传输过程中用于差错检测的最简单的方法,即重复校验法。

一、重复校验法基本原理

1.1 校验依据

  重复校验法的校验依据就是判断重复传输的q组n bits二进制数据是否一致。

1.2 重复校验位

  为了实现重复校验,就是不断重复传输这组n bits原始数据q次即可,一次校验的q*n bits数据块中,仅有n bits数据是原始有效数据,校验位就是那些重复的(q-1)*n bits数据。是不是觉得简单又粗暴?

1.3 校验方法

  假设原始数据块是X[n-1:0]共n bits,重复次数为q(q一般为奇数),按重复传输方式,可分为两个子类:

  • 按bit重复:发送数据序列为,q个X0(X0X0...),q个X1(X1X1...)...,q个Xn-1(Xn-1Xn-1...)
  • 按block重复:发送数据序列为,第1个X[n-1:0],第2个X[n-1:0]...,第q个X[n-1:0]。

  接受端收到数据后,逐次比较q个重复位,如完全一致,则认为没有错差;如不一致,则存在错误bit。如需纠错的话,原理也很简单,判断q个重复位里哪种数据位出现的次数多(这里解释了q为何应是奇数)则为原始正确数据位。

1.4 C代码实现

  实际中按block重复校验法应用比较多,此处示例代码以此为例:

安装包:codeblocks-17.12mingw-setup.exe

集成环境:CodeBlocks 17.12 rev 11256

编译器:GNU GCC 5.1.0

调试器:GNU gdb (GDB) 7.9.1

// repetition_code.c
//////////////////////////////////////////////////////////
#include <stdint.h>
#include <assert.h> /*!
* @brief 处理按block重复的数据块
*
* @param src, 待处理的数据块.
* @param dest, 处理完成的原始数据.
* @param lenInBytes, 待处理的数据块长度.
* @param repeatTimes, 数据重复次数(假定为奇数).
* @retval 0, 数据无错误位.
* @retval 1, 数据有错误位且已纠正.
*/
uint32_t verify_correct_repetition_block(uint8_t *src,
uint8_t *dest,
uint32_t lenInBytes,
uint32_t repeatTimes)
{
assert(repeatTimes % 2);
assert(!(lenInBytes % repeatTimes)); uint32_t result = 0;
uint32_t blockBytes = lenInBytes / repeatTimes; // 遍历一个block长度里每个byte
for (uint32_t i = 0; i < blockBytes; i++)
{
// 遍历当前byte的每个bit
uint8_t correctByte = 0;
for (uint32_t j = 0; j < 8; j++)
{
// 遍历当前byte的所有重复byte
uint32_t bit1Count = 0;
for (uint32_t k = 0; k < repeatTimes; k++)
{
// 记录所有重复byte中当前bit为1的个数
uint8_t countByte = *(src + i + k * blockBytes);
bit1Count += (countByte & (0x1u << j)) >> j;
}
// 当bit1出现半数则将当前bit认定为1
if (bit1Count > (repeatTimes / 2))
{
correctByte |= 0x1u << j;
}
// 首次发现错误bit时,置位result
if ((!result) && (bit1Count !=0) && bit1Count != repeatTimes)
{
result = 1;
}
}
// 将校验后的byte存入dest
*(dest + i) = correctByte;
} return result;
} // main.c
//////////////////////////////////////////////////////////
#include "repetition_code.h"
#include <stdio.h>
#include <stdlib.h> int main(void)
{
uint8_t src[3][4] = {{0x32, 0x33, 0x04, 0x08},
{0x32, 0x83, 0x04, 0xd8},
{0x31, 0x33, 0x04, 0xe8}};
uint8_t dest[4];
uint32_t result = verify_correct_repetition_block((uint8_t *)src, dest, sizeof(src), sizeof(src) / sizeof(src[0])); printf("result = %d\n", result);
for (uint32_t i = 0; i < sizeof(dest); i++)
{
printf("dest[%d] = 0x%x\n", i, dest[i]);
}
return 0;
}

1.5 行业应用

  实际上本文所讲的单纯的重复校验法行业因为效率的原因,行业里较少应用,其改进版的实现RA Codes应用在了FlexRay协议里。

二、重复校验法失效分析

  重复校验实现非常简单,具有比较理想的检错能力,但效率太低,并未得到广泛使用。即便牺牲了效率,但重复校验法也存在如下2个缺陷,导致其检错纠错并不可靠:

  • 当重复bit全部发生错误时,会被误认为没有错误bit发生。
  • 当错误bit出现概率大于原始bit时,在纠错时会认定错误bit是原始bit。

  有没有其他比重复校验法更高效的检错方法?痞子衡在下篇会继续聊。

  至此,嵌入式里数据差错控制技术之重复校验痞子衡便介绍完毕了,掌声在哪里~~~

欢迎订阅

文章会同时发布到我的 博客园主页CSDN主页微信公众号 平台上。

微信搜索"痞子衡嵌入式"或者扫描下面二维码,就可以在手机上第一时间看了哦。

痞子衡随笔:常用的数据传输差错检测技术(1)- 奇偶校验(Parity Check)的更多相关文章

  1. 痞子衡嵌入式:常用的数据差错控制技术(2)- 奇偶校验(Parity Check)

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家讲的是嵌入式里数据差错控制技术-奇偶校验. 在系列第一篇文章里,痞子衡给大家介绍了最简单的校验法-重复校验,该校验法实现简单,检错纠错能力都还不 ...

  2. 痞子衡嵌入式:走进二维码(QR Code)的世界(1)- 引言

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家分享的是走进二维码(QR Code)的世界专题的引言. 如今二维码可以说是深入走进大家的生活了,推送名片.扫码支付都离不开它,大家几乎每天都会和 ...

  3. 痞子衡嵌入式:我的博文总量终于追平了jicheng0622

    自打2016年10月选定清爽又复古的博客园平台作为痞子衡的个人博客主战场之后,痞子衡就一直坚持在博客园首发原创技术文章,然后再同步到其他平台(CSDN,知乎,微信公众号...),在坚持更文近四年半(2 ...

  4. 痞子衡嵌入式:常用的数据差错控制技术(1)- 重复校验(Repetition Code)

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家讲的是嵌入式里数据差错控制技术-重复校验. 在嵌入式应用里,除了最核心的数据处理外,我们还会经常和数据传输打交道.数据传输需要硬件传输接口的支持 ...

  5. 痞子衡嵌入式:常用的数据差错控制技术(3)- 和校验(Checksum)

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家讲的是嵌入式里数据差错控制技术-和校验. 在系列前一篇文章里,痞子衡给大家介绍了比较简单的校验法-奇偶校验,该校验法主要是针对byte传输校验而 ...

  6. 痞子衡嵌入式:i.MXRT中FlexSPI外设不常用的读选通采样时钟源 - loopbackFromSckPad

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家分享的是i.MXRT中FlexSPI外设不常用的读选通采样时钟源 - loopbackFromSckPad. 最近碰到一个客户,他们在 i.MX ...

  7. 痞子衡嵌入式:串口调试工具Jays-PyCOM诞生记(3)- 串口功能实现(pySerial)

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家介绍的是串口调试工具Jays-PyCOM诞生之串口功能实现. 串口调试助手是最核心的当然是串口数据收发与显示的功能,Jays-PyCOM借助的是 ...

  8. 痞子衡嵌入式:从头开始认识i.MXRT启动头FDCB里的lookupTable

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家介绍的是i.MXRT启动头FDCB里的lookupTable. 一个MCU内部通常有很多外设模块,这些外设模块是各MCU厂商做差异化产品的本质, ...

  9. 痞子衡嵌入式:嵌入式里串口(UART)自动波特率识别程序设计与实现

    大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家分享的是嵌入式里串口(UART)自动波特率识别程序设计与实现. 串口(UART)是嵌入式里最基础最常用也最简单的一种通讯(数据传输)方式,可以说 ...

随机推荐

  1. 整理关于web项目如何防止CSRF和XSS攻击的方法

    1 了解CSRF的定义 CSRF(Cross-site request forgery)跨站请求伪造,也被称为"One Click Attack"或者Session Riding, ...

  2. 现代 PHP 新特性系列(三) —— Trait 概览

    Trait是PHP 5.4引入的新概念,看上去既像类又像接口,其实都不是,Trait可以看做类的部分实现,可以混入一个或多个现有的PHP类中,其作用有两个:表明类可以做什么:提供模块化实现.Trait ...

  3. Hadoop问题:chmod 0700 of directory /var/lib/apt/lists/

    问题描述: apt-get update W: chmod of directory /: Operation not permitted) E: Could not open : Permissio ...

  4. 让自己写的项目支持Cocoapods管理

    学会使用别人的 Pods 依赖库以后, 你一定对创建自己的依赖库很有兴趣吧,现在我们一起来制作自己的Pods依赖库. 1.创建自己的 github 仓库 上图中标识出了6处地方 Repository ...

  5. yarn 淘宝源安装与使用用法

    Yarn 淘宝源 yarn config set registry https://registry.npm.taobao.org -g yarn config set sass_binary_sit ...

  6. confirm显示数组中的内容时,总是带一个逗号分隔的解决方法

    问题的关键 就是在给confirm显示之前,将数组转换成字符串,并以每个数组的元素为一个字符串,加上一个换行回车符即可: 代码中的背景色 为关键的点 <script type="tex ...

  7. Django中url使用命名空间的错误

    出的错误: 1. Reverse for 'llist' with arguments '()' and keyword arguments '{}' not found. 0 pattern(s) ...

  8. scrapy-redis功能简介

    connection:连接redis最基本文件 default:默认值设置文件 dupefiler_key 保存指纹 dupefilter:替换scrapy默认的url去重器 piklecompat: ...

  9. python_分支循环

    什么是分支+循环? --不同条件进行不同逻辑处理            -- 分支 --满足条件进行反复相同逻辑处理     -- 循环 分支的形式? -- if 条件:  执行体   else: 执 ...

  10. Java进阶篇(六)——Swing程序设计(下)

    三.布局管理器 Swing中,每个组件在容器中都有一个具体的位置和大小,在容器中摆放各自组件时很难判断其具体位置和大小,这里我们就要引入布局管理器了,它提供了基本的布局功能,可以有效的处理整个窗体的布 ...