• Python_Example_Modbus_CRC协议


     2018-09-09

    Author: 楚格

    IDE: Pycharm2018.02   Python 3.7   第三方库 crcmod

    KeyWord :  CRC modbus    cauCRC 和check

    Explain:

    1CRC原理

    2CRC知识

    3CRC代码

    1------------------------------------------------------------------------------------------------------------------

    CRC校验:CRC即循环冗余校验码:是数据通信领域中最常用的一种查错校验码,其特征是信息字段和校验字段的长度可以任意选定。循环冗余检查(CRC)是一种数据传输检错功能,对数据进行多项式计算,并将得到的结果附在帧的后面,接收设备也执行类似的算法,以保证数据传输的正确性和完整性。
    CRC校验原理:其根本思想就是先在要发送的帧后面附加一个数(这个就是用来校验的校验码,但要注意,这里的数也是二进制序列的,下同),生成一个新帧发送给接收端。当然,这个附加的数不是随意的,它要使所生成的新帧能与发送端和接收端共同选定的某个特定数整除(注意,这里不是直接采用二进制除法,而是采用一种称之为“模2除法”)。到达接收端后,再把接收到的新帧除以(同样采用“模2除法”)这个选定的除数。因为在发送端发送数据帧之前就已通过附加一个数,做了“去余”处理(也就已经能整除了),所以结果应该是没有余数。如果有余数,则表明该帧在传输过程中出现了差错。

    2------------------------------------------------------------------------------------------------------------------

    参考网址

    --

    >>> <http://www.ip33.com/crc.html >

    >>> CRC(循环冗余校验)在线计算

    --

    >>> < http://crcmod.sourceforge.net/crcmod.predefined.html#predefined-crc-algorithms >

    >>>  crcmod.predefined – CRC calculation using predefined algorithms

    --

    3------------------------------------------------------------------------------------------------------------------

    Code:

    CRC校验二种方法:

    1使用第三方库函数crcmod,但是不够完善,缺少输入输入数据反转处理。

    2使用计算法,利用CalCRC16和CheckCRC函数校验输入的byte。先calcuation 后check。

    --

    __all__ = ["CalCRC16","CheckCRC"]
    
    # ===============================================================
    import crcmod
    # ===============================================================
    def CalCRC16(data, length):
        print(data, length)
        crc=0xFFFF
        if length == 0:
            length = 1
        ## for j in data:
        ##     crc ^= j
        j = 0
        while length != 0:
            crc ^= list.__getitem__(data, j)
            #print('j=0x%02x, length=0x%02x, crc=0x%04x' %(j,length,crc))
            for i in range(0,8):
                if crc & 1:
                    crc >>= 1
                    crc ^= 0xA001
                else:
                    crc >>= 1
            length -= 1
            j += 1
            ##if length == 0:
            ##         break
    
        return crc
    # ===============================================================
    def CheckCRC(data, length, crctype):
        if length < 3:
            print('The data len(%d) is less than 3!!!', length)
            return 0
        crc_res = 0
        tmp=[0,0,0,0]
    
        if crctype == 0:
            crc_res = CalCRC16(data, length-2)
            tmp[0] = crc_res & 0xFF
            tmp[1] = (crc_res >> 8) & 0xFF
    
            if data[length-2] == tmp[0] and data[length-1] == tmp[1]:
                return 1
        elif crctype == 1:
            print('CRC32 is not support...')
    
        return 0
    # ===============================================================
    
    
    # ===============================================================
    '''
    #===============================================================
    #   测试专用
    #===============================================================
    '''
    if __name__ == '__main__':
    
        ## Name Identifier-name, Poly  Reverse Init-value XOR-out Check
        ## ['modbus','CrcModbus',0x18005,REVERSE,0xFFFF,0x0000,0x4B37]
        ## crc16 = crcmod.mkCrcFun(0x18005, rev=True, initCrc=0xFFFF,  xorOut=0x0000) # rev=True,False
    
        crc16 = crcmod.mkCrcFun(0x18005,  initCrc=0xFFFF,rev=True,  xorOut=0x0000) # rev=True,False
        crc_array = b'0xFE 0xFD'
        crc_calc = crc16(crc_array) #计算得到的CRC
        a=hex(crc_calc)
        print(crc_calc,a)
        print('
    ')
    
        # =========================================
        crc_value = [0x01, 0x04, 0x13, 0x87, 0x00, 0x30]
        crc_transformation = CalCRC16(crc_value,len(crc_value))
        crc_calculation    = hex(crc_transformation)
        # print('crc_calculation:',crc_calculation)
        tasd = [0x00,0x00]
        tasd[0]  = crc_transformation & 0xFF
        tasd[1] = (crc_transformation >> 8) & 0xFF
        H =hex(tasd[0])
        L =hex(tasd[1])
        H_value = int(H,16)
        L_value = int(L,16)
        crc_value.append(H_value)
        crc_value.append(L_value)
        print(crc_value)          # calculation value   CRC
    
        # ========================================================
        print('
    ')
        # crc_value2 = [0x01, 0x04, 0x13, 0x87, 0x00, 0x30,0x44,0xB3]
        # print('crc_value2:',crc_value2)
        # crc_cheak=CheckCRC(crc_value2,len(crc_value2),0)
    
        crc_check=CheckCRC(crc_value,len(crc_value),0)
        if crc_check == 1:
            print('Right')
        else:
            print('wrong')
    
        print(crc_check)    # check calculation value

     --

    Run Result:

    --

    44877 0xaf4d
    
    
    [1, 4, 19, 135, 0, 48] 6
    [1, 4, 19, 135, 0, 48, 68, 179]
    
    
    [1, 4, 19, 135, 0, 48, 68, 179] 6
    Right
    1
    
    Process finished with exit code 0
    

    --

    4------------------------------------------------------------------------------------------------------------------

    5------------------------------------------------------------------------------------------------------------------

    6------------------------------------------------------------------------------------------------------------------

    7------------------------------------------------------------------------------------------------------------------

    8------------------------------------------------------------------------------------------------------------------

    9------------------------------------------------------------------------------------------------------------------

    10------------------------------------------------------------------------------------------------------------------

  • 相关阅读:
    LeetCode——003 Longest Substring Without Repeating Characters
    LeetCode——002 Add Two Numbers
    LeetCode——001 Two Sum
    【日常训练】Hockey(CodeForces-96C)
    【日常训练】数据中心(CSP 201812-4)
    【赛后补题】Lucky Probability(CodeForces 110D)
    「Leetcode」14. Longest Common Prefix(Java)
    「Leetcode」13. Roman to Integer(Java)
    「日常训练」Magic Stones(CodeForces-1110E)
    「日常训练」Jongmah(Codeforces-1110D)
  • 原文地址:https://www.cnblogs.com/caochucheng/p/9612336.html
Copyright © 2020-2023  润新知