最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

C語言實現CRC校驗算法的示例詳解

 更新時間:2023年08月09日 16:26:08   作者:DS小龍哥  
CRC(Cyclic Redundancy Check,循環(huán)冗余校驗)是一種常用的錯誤檢測技術,用于驗證數據在傳輸或存儲過程中是否發(fā)生了錯誤,本文主要介紹了C語言如何實現CRC校驗算法,需要的可以參考一下

一、CRC介紹

CRC(Cyclic Redundancy Check,循環(huán)冗余校驗)是一種常用的錯誤檢測技術,用于驗證數據在傳輸或存儲過程中是否發(fā)生了錯誤。它通過對數據進行一系列計算和比較,生成一個校驗值,并將其附加到數據中。接收方可以使用相同的算法對接收到的數據進行校驗,然后與接收到的校驗值進行比較,從而確定數據是否存在錯誤。

CRC校驗通常用于以下方面:

(1)數據傳輸的可靠性:在數據通過媒體或網絡進行傳輸時,可能會發(fā)生噪聲、干擾或其他傳輸錯誤。通過在數據中添加CRC校驗值,接收方可以檢測到傳輸過程中是否發(fā)生了錯誤,并采取相應措施,如請求重新發(fā)送數據。

(2)存儲介質的完整性檢測:在存儲介質上讀取或寫入數據時,可能會發(fā)生位翻轉、介質故障等錯誤。通過在數據存儲時使用CRC校驗,可以在讀取數據時檢測到這些錯誤,并提供數據的完整性保證。

(3)網絡通信協議:許多網絡通信協議(如Ethernet、WiFi、USB等)使用CRC校驗作為數據幀的一部分,以確保傳輸的數據準確無誤。接收方在接收到數據幀后,使用CRC校驗來驗證數據的完整性。

在項目中,CRC校驗廣泛應用于各種通信系統(tǒng)、存儲系統(tǒng)和數據傳輸系統(tǒng)中。通過使用CRC校驗,可以提高數據的可靠性,并減少傳輸或存儲過程中的錯誤。它可以檢測到數據位級別的錯誤,并提供一定程度的數據完整性保證。CRC校驗在保障數據可靠性和完整性方面具有重要作用,特別是在對數據完整性有較高要求的應用場景中。

二、示例代碼

以下C語言代碼演示如何獲取一段數據的CRC校驗值:

#include <stdio.h>
#include <stdint.h>
?
// CRC校驗函數
uint16_t crc16(uint8_t *data, int length)
{
 ? ?uint16_t crc = 0xFFFF;
 ? ?for (int i = 0; i < length; i++)
 ?  {
 ? ? ? ?crc ^= data[i];
 ? ? ? ?for (int j = 0; j < 8; j++)
 ? ? ?  {
 ? ? ? ? ? ?if (crc & 1)
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ? ? ? ?crc ^= 0xA001;
 ? ? ? ? ?  }
 ? ? ? ? ? ?else
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ?  }
 ? ? ?  }
 ?  }
 ? ?return crc;
}
?
// 封裝的CRC校驗函數調用
uint16_t calculateCRC(uint8_t *data, int length)
{
 ? ?return crc16(data, length);
}
?
int main()
{
 ? ?uint8_t message[] = {0x01, 0x02, 0x03, 0x04, 0x05};
 ? ?int length = sizeof(message) / sizeof(message[0]);
 ? ?uint16_t crc = calculateCRC(message, length);
 ? ?printf("CRC: 0x%04X\n", crc);
 ? ?return 0;
}

在上面代碼中,crc16 函數實現了CRC校驗的計算邏輯。采用了常用的CRC-16算法(0xA001多項式)。calculateCRC 函數是對 crc16 的封裝,用于調用CRC校驗函數并返回校驗結果。

main 函數中,通過調用 calculateCRC 函數來計算給定數據的CRC校驗值,并將結果打印輸出。

代碼中的CRC校驗函數和封裝函數是基于無符號8位字節(jié)和無符號16位整數的數據類型進行計算的。

三、案例:數據校驗

場景:在單片機通信里,單片機需要向上位機發(fā)送一段數據。比如,存放在char buff[1024];這個數組里。 需要封裝兩個函數,單片機端調用函數對這段數據進行CRC校驗,封裝校驗值,然后上位機收到數據之后驗證CRC,校驗數據是否傳輸正確。

3.1 發(fā)送方(封裝校驗值)

#include <stdio.h>
#include <stdint.h>
?
// CRC校驗函數
uint16_t crc16(uint8_t *data, int length)
{
 ? ?uint16_t crc = 0xFFFF;
 ? ?for (int i = 0; i < length; i++)
 ?  {
 ? ? ? ?crc ^= data[i];
 ? ? ? ?for (int j = 0; j < 8; j++)
 ? ? ?  {
 ? ? ? ? ? ?if (crc & 1)
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ? ? ? ?crc ^= 0xA001;
 ? ? ? ? ?  }
 ? ? ? ? ? ?else
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ?  }
 ? ? ?  }
 ?  }
 ? ?return crc;
}
?
// 封裝CRC校驗值到數據中
void appendCRC(uint8_t *data, int length)
{
 ? ?uint16_t crc = crc16(data, length);
 ? ?data[length] = crc & 0xFF; // 將低8位放入數據末尾
 ? ?data[length + 1] = crc >> 8; // 將高8位放入數據末尾的下一個位置
}
?
int main()
{
 ? ?uint8_t buff[1024] = {0x01, 0x02, 0x03, 0x04, 0x05}; // 原始數據
 ? ?int length = 5; // 數據長度
 ? ?// 在原始數據后追加CRC校驗值
 ? ?appendCRC(buff, length);
 ? ?// 輸出發(fā)送的數據(包括CRC校驗值)
 ? ?printf("發(fā)送的數據:");
 ? ?for (int i = 0; i < length + 2; i++)
 ?  {
 ? ? ? ?printf("%02X ", buff[i]);
 ?  }
 ? ?printf("\n");
 ? ?return 0;
}

在發(fā)送方的代碼中,使用 appendCRC 函數將CRC校驗值追加到原始數據的末尾。

3.2 接收方(校驗數據)

#include <stdio.h>
#include <stdint.h>
?
// CRC校驗函數
uint16_t crc16(uint8_t *data, int length)
{
 ? ?uint16_t crc = 0xFFFF;
 ? ?for (int i = 0; i < length; i++)
 ?  {
 ? ? ? ?crc ^= data[i];
 ? ? ? ?for (int j = 0; j < 8; j++)
 ? ? ?  {
 ? ? ? ? ? ?if (crc & 1)
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ? ? ? ?crc ^= 0xA001;
 ? ? ? ? ?  }
 ? ? ? ? ? ?else
 ? ? ? ? ?  {
 ? ? ? ? ? ? ? ?crc >>= 1;
 ? ? ? ? ?  }
 ? ? ?  }
 ?  }
 ? ?return crc;
}
?
// 驗證CRC校驗值是否正確
int verifyCRC(uint8_t *data, int length)
{
 ? ?uint16_t crc = crc16(data, length - 2); // 去除數據末尾的CRC校驗值
 ? ?// 獲取接收到的CRC校驗值
 ? ?uint16_t receivedCRC = (data[length - 1] << 8) | data[length - 2];
 ? ?// 比較計算得到的CRC校驗值與接收到的CRC校驗值
 ? ?if (crc == receivedCRC)
 ?  {
 ? ? ? ?return 1; // 校驗通過
 ?  }
 ? ?else
 ?  {
 ? ? ? ?return 0; // 校驗失敗
 ?  }
}
?
int main()
{
 ? ?uint8_t receivedData[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0xC2, 0x45}; // 收到的數據(包括CRC校驗值)
 ? ?int length = sizeof(receivedData) / sizeof(receivedData[0]);
 ? ?// 驗證CRC校驗值是否正確
 ? ?int crcResult = verifyCRC(receivedData, length);
 ? ?if (crcResult)
 ?  {
 ? ? ? ?printf("CRC校驗通過\n");
 ? ? ? ?// TODO: 進一步處理正確的數據
 ?  }
 ? ?else
 ?  {
 ? ? ? ?printf("CRC校驗失敗\n");
 ? ? ? ?// TODO: 處理校驗失敗的情況
 ?  }
 ? ?return 0;
}

在接收方的代碼中,使用 verifyCRC 函數驗證接收到的數據的CRC校驗值是否正確。如果校驗通過,可以執(zhí)行進一步的數據處理操作;如果校驗失敗,可以進行異常處理。

示例中的CRC校驗函數是基于無符號8位字節(jié)和無符號16位整數的數據類型進行計算的。可以根據實際需求進行適當修改,以適應不同的數據類型和CRC算法。

到此這篇關于C語言實現CRC校驗算法的示例詳解的文章就介紹到這了,更多相關C語言CRC校驗算法內容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • 減少C++代碼編譯時間的簡單方法(必看篇)

    減少C++代碼編譯時間的簡單方法(必看篇)

    下面小編就為大家?guī)硪黄獪p少C++代碼編譯時間的簡單方法(必看篇)。小編覺得挺不錯的,現在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-01-01
  • C/C++中可變參數的用法詳細解析

    C/C++中可變參數的用法詳細解析

    可變參數的使用方法遠遠不止以下介紹的幾種,不過在C,C++中使用可變參數時要小心,在使用printf()等函數時傳入的參數個數一定不能比前面的格式化字符串中的’%’符號個數少,否則會產生訪問越界,運氣不好的話還會導致程序崩潰
    2013-09-09
  • 使用C++實現一個高效的線程池

    使用C++實現一個高效的線程池

    在多線程編程中,線程池是一種常見且高效的設計模式,本文將詳細介紹如何使用C++實現一個線程池,并解析相關代碼實現細節(jié),需要的小伙伴可以參考下
    2024-12-12
  • 基于C++全局變量的聲明與定義的詳解

    基于C++全局變量的聲明與定義的詳解

    本篇文章是對C++全局變量的聲明與定義進行了詳細的分析介紹,需要的朋友參考下
    2013-05-05
  • C/C++的浮點數在內存中的存儲方式分析及實例

    C/C++的浮點數在內存中的存儲方式分析及實例

    這篇文章主要介紹了C/C++的浮點數在內存中的存儲方式分析及實例的相關資料,需要的朋友可以參考下
    2016-11-11
  • C++11的future和promise、parkged_task使用

    C++11的future和promise、parkged_task使用

    這篇文章主要介紹了C++11的future和promise、parkged_task使用,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2020-04-04
  • MFC中動態(tài)創(chuàng)建控件以及事件響應實現方法

    MFC中動態(tài)創(chuàng)建控件以及事件響應實現方法

    這篇文章主要介紹了MFC中動態(tài)創(chuàng)建控件以及事件響應實現方法,詳細講解了MFC中動態(tài)創(chuàng)建控件以及事件響應的概念與實現方法,具有一定的實用價值,需要的朋友可以參考下
    2014-10-10
  • c++ 成員函數與非成員函數的抉擇

    c++ 成員函數與非成員函數的抉擇

    盡量用類的非成員函數以及友元函數替換類的成員函數 例如一個類來模擬人People
    2013-01-01
  • Linux下用C++實現俄羅斯方塊

    Linux下用C++實現俄羅斯方塊

    這篇文章主要為大家詳細介紹了Linux下用C++實現俄羅斯方塊的相關資料,感興趣的小伙伴們可以參考一下
    2016-08-08
  • C語言函數指針的老生常談

    C語言函數指針的老生常談

    這篇文章主要為大家介紹了vue組件通信的幾種方法,具有一定的參考價值,感興趣的小伙伴們可以參考一下,希望能夠給你帶來幫助
    2021-11-11

最新評論

阿图什市| 鹤峰县| 石嘴山市| 华容县| 平泉县| 商南县| 丹巴县| 扬州市| 西盟| 措勤县| 榕江县| 伽师县| 永修县| 禹州市| 乌审旗| 郸城县| 溆浦县| 普定县| 青铜峡市| 凤台县| 南溪县| 镇坪县| 合肥市| 梧州市| 浦北县| 从化市| 兴山县| 娄底市| 丹阳市| 长兴县| 正蓝旗| 寿阳县| 抚远县| 尚义县| 纳雍县| 德安县| 徐水县| 句容市| 阜城县| 涿州市| 保靖县|