精华内容
下载资源
问答
  • CRC校验码生成工具

    2018-07-20 16:27:08
    CRC校验码生成工具,CRC校验码生成工具,CRC校验码生成工具
  • 校验码生成工具软件包
  • 校验码生成

    2015-02-07 17:36:52
    下面的代码都是抄过来的,不怎么理解,用的时候方便copy 在jsp页面写上<img src="authImg"...代码如下,这段代码会生成随机的字母与数字混合的验证码: public class AuthIm...

    下面的代码都是抄过来的,不怎么理解,用的时候方便copy

    在jsp页面写上<img src="authImg" height:20px; width:60px"/>,就会自动的将request中的authImg加进去,不知道怎么回事,应该是会自动调用的。高和宽的值也要和代码中的一致。

    代码如下,这段代码会生成随机的字母与数字混合的验证码:

    public class AuthImg extends HttpServlet {

     private static final long serialVersionUID = -8281845659081613239L;

     private Font mFont = new Font("Times New Roman", Font.PLAIN, 18);

     public void init() throws ServletException {
     }

     public void doGet(HttpServletRequest request, HttpServletResponse response)
       throws ServletException, IOException {
      response.setContentType("image/jpeg");
      ServletOutputStream out = response.getOutputStream();

      int width = 60, height = 20;
      BufferedImage image = new BufferedImage(width, height,
        BufferedImage.TYPE_INT_RGB);

      Graphics g = image.getGraphics();
      Random random = new Random();

      g.setColor(getRandColor(200, 250));
      g.fillRect(0, 0, width, height);

      g.setFont(mFont);

      g.setColor(getRandColor(160, 200));
      for (int i = 0; i < 155; i++) {
       int x = random.nextInt(width);
       int y = random.nextInt(height);
       int xl = random.nextInt(12);
       int yl = random.nextInt(12);
       g.drawLine(x, y, x + xl, y + yl);
      }

      String rand = RandomChar.getChars(4, 4);
      char c;
      for (int i = 0; i < 4; i++) {
       c = rand.charAt(i);
       g.setColor(new Color(20 + random.nextInt(110), 20 + random
         .nextInt(110), 20 + random.nextInt(110)));
       g.drawString(String.valueOf(c), 13 * i + 6, 16);
      }
      HttpSession seesion = request.getSession();
      seesion.setAttribute("authCode", rand);
      JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(out);
      encoder.encode(image);
      out.close();
     }

     public void doPost(HttpServletRequest request, HttpServletResponse response)
       throws ServletException, IOException {
      doGet(request, response);
     }

     public void destroy() {
     }

     private Color getRandColor(int fc, int bc) {
      Random random = new Random();
      if (fc > 255) {
       fc = 255;
      }
      if (bc > 255) {
       bc = 255;
      }
      int r = fc + random.nextInt(bc - fc);
      int g = fc + random.nextInt(bc - fc);
      int b = fc + random.nextInt(bc - fc);
      return new Color(r, g, b);
     }
    }

    代码中涉及到一个类RandomChar。代码如下

    public class RandomChar {
     private static final String CHAR_ALL = "qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM";

     private static final String CHAR_LOWERCASE = "qwertyuiopasdfghjklzxcvbnm";

     private static final String CHAR_UPPERCASE = "QWERTYUIOPLAKSJDHFGZXCVBNM";

     private static final String NUMBERS = "0123456789";

     private static final String ALL = "qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM1234567890";

     private static final String CHAR_SPECIAL_ALL = "qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM~!@#$%^&*";

     public static final int RANDOM_CHAR_UPPERCASE = 0;

     public static final int RANDOM_CHAR_LOWERCASE = 1;

     public static final int RANDOM_CHAR_ALL = 2;

     public static final int RANDOM_NUMBERS = 3;

     public static final int RANDOM_ALL = 4;

     public static final int RANDOM_SPECIAL_ALL = 5;

     public static String getChars(int MOD, int count) {

      Random r = new Random();

      int i = 0;
      String random_source = null;
      switch (MOD) {
      case RANDOM_CHAR_UPPERCASE:
       random_source = CHAR_UPPERCASE;
       break;
      case RANDOM_CHAR_LOWERCASE:
       random_source = CHAR_LOWERCASE;
       break;
      case RANDOM_CHAR_ALL:
       random_source = CHAR_ALL;
       break;
      case RANDOM_NUMBERS:
       random_source = NUMBERS;
       break;
      case RANDOM_ALL:
       random_source = ALL;
       break;
      case RANDOM_SPECIAL_ALL:
       random_source = CHAR_SPECIAL_ALL;
       break;
      default:
       random_source = CHAR_SPECIAL_ALL;
       break;
      }

      int c = random_source.length();
      String result = "";

      while (i < count) {
       int v = Math.abs(r.nextInt()) % c;
       result += random_source.substring(v, v + 1);
       i++;
      }
      return result;
     }
    }

    展开全文
  • CRC校验码生成说明

    2015-04-08 17:02:04
    CRC校验码生成,简单地列举了一个CRC校验码生成的过程,说明CRC生成的过程和原理。希望对大家有用。
  • md5校验码生成工具软件免安装,md5校验码对比工具软件,免安装,解压缩后可直接使用,程序员必备小工具。
  • C# CRC 16 校验码生成

    2019-04-17 11:24:39
    1.C# CRC 16 校验码生成源码; 2.CRC-16 MODBUG; 3.C#写的CRC16检验算法;
  • ESN校验码生成软件

    2013-05-14 17:25:09
    ESN校验码生成软件
  • CRC-16校验码生成

    2016-04-18 20:09:39
    CRC校验码生成小程序,大大减小了编程的难度
  • CRC校验码生成工具modbus rtu,计算准确Win10CRC校验码生成工具modbus rtu,计算准确Win10CRC校验码生成工具modbus rtu,计算准确Win10CRC校验码生成工具modbus rtu,计算准确Win10可用
  • CRC16校验码生成工具

    千次下载 热门讨论 2008-12-12 14:34:42
    一款CRC16的校验码生成工具,可以自己设置校验码生成多项式,可以对十六进制序列和文件进行校验,得出16位CRC校验码。字符串需要输入ASCii码形式,例如:AE 13 4F 78 0C 90 A0 B1,每两个中间要加空格,当校验多项式...
  • CRC&LRC;校验码生成

    2018-10-16 18:24:57
    CRC&LRC;校验码生成器,可同时生成如下格式验证码: CRC16_CCITT CRC16_CCITT_FALSE CRC16_XMODEM CRC16_X25 CRC16_MODBUS CRC16_IBM CRC16_MAXIM CRC16_USB
  • CRC校验码生成程序及测试,用于通讯协议的简单校验,自己一直在用,好用
  • CRC16校验码生成

    热门讨论 2012-03-10 11:42:03
    crc16校验码生成工具,MFC可执行程序
  • 校验码生成工具

    千次阅读 2015-08-22 10:14:16
    为此,为此,我制作了个校验码生成小工具,当前版本支BCC(Block Check Character/信息组校验码)实际上就是所有字节的异或校验、CS(模256校验)即,所有字节相加不考虑溢出、CRC16(循环冗余校验),代码及实现效果...

           做单片机通信时常常需要用到校验码,在不确定单片机校验输出结果正确与否的情况下我们不得不手工对报文进行计算并对比结果。手工计算有多麻烦笔者就不形容了。为此,为此,我制作了个校验码生成小工具,当前版本支BCC(Block Check Character/信息组校验码)实际上就是所有字节的异或校验、CS(256校验)即,所有字节相加不考虑溢出、CRC16(循环冗余校验),代码及实现效果如下。


    using System;

    using System.Collections.Generic;

    using System.ComponentModel;

    using System.Data;

    using System.Drawing;

    using System.Linq;

    using System.Text;

    using System.Windows.Forms;

    namespace 校验码生成工具

    {

        public partial class Form1 : Form

        {

            public Form1()

            {

                InitializeComponent();

            }

            private void bt_Click(object sender, EventArgs e)

            {

                byte[] intputBuf;

                int result = 0;                                   //输出结果

                string intputStr = intputbox.Text;             //得到输入的16进制序列

                intputStr = intputStr.Replace(" """);      //去掉空格,如果存在

                intputStr = intputStr.Replace("0x""");     //去掉0x,如果存在

                intputStr = intputStr.Replace("0X""");     //去掉0X,如果存在

                intputStr = intputStr.Replace(",""");

                intputStr = intputStr.Replace("H""");

                intputStr = intputStr.Replace("h"""); 

                if (intputStr.Length % 2 != 0)

                {

                    intputStr += " ";

                }

                intputBuf = new byte[intputStr.Length/2];

                for (int i = 0; i < intputBuf.Length; i++)

                {

                    /*每次取出两个字符并转换成16进制----------------------------*/

                    try

                        {

                           intputBuf[i] = Convert.ToByte(intputStr.Substring( i * 2,2), 16);

                        }

                    catch

                    {

                        goto inputErr;

                    }

                }

                if (cs.Checked) //256运算

                {

                    for (int i = 0; i < intputBuf.Length; i++)

                    {

                        result = result + intputBuf[i];

                    }

                }

                else if (bcc.Checked)  //异或运算

                {

                    for (int i = 0; i < intputBuf.Length; i++)

                    {

                        result = result ^ intputBuf[i];

                    }

                   

                }

                else if (crc16.Checked)

                {

                    result = CRC.CRC16(intputBuf, intputBuf.Length);

                    outBox.Text = "0x";

                    outBox.Text += Convert.ToString(result, 16);

                    return;     /*结束-----------------------------*/

                }

                result &= 0xff;

                outBox.Text = "0x";

                outBox.Text += Convert.ToString(result,16);

                return;     /*结束-----------------------------*/

     

                inputErr:

                    MessageBox.Show("格式错误");

            }

            private void 复制ToolStripMenuItem1_Click(object sender, EventArgs e)

            {

                intputbox.Copy();

            }

     

            private void 粘贴ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.Paste();

            }

     

            private void 全选ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.SelectAll();

            }

     

            private void 撤销ToolStripMenuItem1_Click(object sender, EventArgs e)

            {

                intputbox.Undo();

            }

            private void 剪切ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.Cut();

            }

            private void 复制ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.Cut();

            }

            private void 复制ToolStripMenuItem2_Click(object sender, EventArgs e)

            {

                intputbox.Copy();

            }

     

            private void 删除ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.Cut();

            }

            private void 全选ToolStripMenuItem1_Click(object sender, EventArgs e)

            {

                intputbox.SelectAll();

            }

     

            private void 撤销ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                intputbox.Undo();

            }

     

            private void 关于ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                AboutBox1 ab = new AboutBox1();

                ab.Show();

            }

     

            private void 退出ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                this.Close();

            }

     

            private void 打开ToolStripMenuItem_Click(object sender, EventArgs e)

            {

                MessageBox.Show("打不开");

            }

        }

    }

     

    /*CRC------------------------------------------------------------------*/

    using System;

    using System.Collections.Generic;

    using System.Linq;

    using System.Text;

    namespace 校验和计算工具

    {

        class CRC

        {

    //crc16 查找表,根据CRC-CCITT多项式生成

            private static ushort[] CRC16Table = 

            {

              0x0000,0x1021,0x2042,0x3063,0x4084,0x50a5,0x60c6,0x70e7,

              0x8108,0x9129,0xa14a,0xb16b,0xc18c,0xd1ad,0xe1ce,0xf1ef,

              0x1231,0x0210,0x3273,0x2252,0x52b5,0x4294,0x72f7,0x62d6,

             0x9339,0x8318,0xb37b,0xa35a,0xd3bd,0xc39c,0xf3ff,0xe3de,

             0x2462,0x3443,0x0420,0x1401,0x64e6,0x74c7,0x44a4,0x5485,

             0xa56a,0xb54b,0x8528,0x9509,0xe5ee,0xf5cf,0xc5ac,0xd58d,

             0x3653,0x2672,0x1611,0x0630,0x76d7,0x66f6,0x5695,0x46b4,

             0xb75b,0xa77a,0x9719,0x8738,0xf7df,0xe7fe,0xd79d,0xc7bc,

             0x48c4,0x58e5,0x6886,0x78a7,0x0840,0x1861,0x2802,0x3823,

             0xc9cc,0xd9ed,0xe98e,0xf9af,0x8948,0x9969,0xa90a,0xb92b,

             0x5af5,0x4ad4,0x7ab7,0x6a96,0x1a71,0x0a50,0x3a33,0x2a12,

             0xdbfd,0xcbdc,0xfbbf,0xeb9e,0x9b79,0x8b58,0xbb3b,0xab1a,

             0x6ca6,0x7c87,0x4ce4,0x5cc5,0x2c22,0x3c03,0x0c60,0x1c41,

             0xedae,0xfd8f,0xcdec,0xddcd,0xad2a,0xbd0b,0x8d68,0x9d49,

             0x7e97,0x6eb6,0x5ed5,0x4ef4,0x3e13,0x2e32,0x1e51,0x0e70,

             0xff9f,0xefbe,0xdfdd,0xcffc,0xbf1b,0xaf3a,0x9f59,0x8f78,

             0x9188,0x81a9,0xb1ca,0xa1eb,0xd10c,0xc12d,0xf14e,0xe16f,

             0x1080,0x00a1,0x30c2,0x20e3,0x5004,0x4025,0x7046,0x6067,

            0x83b9,0x9398,0xa3fb,0xb3da,0xc33d,0xd31c,0xe37f,0xf35e,

            0x02b1,0x1290,0x22f3,0x32d2,0x4235,0x5214,0x6277,0x7256,

            0xb5ea,0xa5cb,0x95a8,0x8589,0xf56e,0xe54f,0xd52c,0xc50d,

            0x34e2,0x24c3,0x14a0,0x0481,0x7466,0x6447,0x5424,0x4405,

            0xa7db,0xb7fa,0x8799,0x97b8,0xe75f,0xf77e,0xc71d,0xd73c,

            0x26d3,0x36f2,0x0691,0x16b0,0x6657,0x7676,0x4615,0x5634,

            0xd94c,0xc96d,0xf90e,0xe92f,0x99c8,0x89e9,0xb98a,0xa9ab,

            0x5844,0x4865,0x7806,0x6827,0x18c0,0x08e1,0x3882,0x28a3,

            0xcb7d,0xdb5c,0xeb3f,0xfb1e,0x8bf9,0x9bd8,0xabbb,0xbb9a,

            0x4a75,0x5a54,0x6a37,0x7a16,0x0af1,0x1ad0,0x2ab3,0x3a92,

            0xfd2e,0xed0f,0xdd6c,0xcd4d,0xbdaa,0xad8b,0x9de8,0x8dc9,

            0x7c26,0x6c07,0x5c64,0x4c45,0x3ca2,0x2c83,0x1ce0,0x0cc1,

            0xef1f,0xff3e,0xcf5d,0xdf7c,0xaf9b,0xbfba,0x8fd9,0x9ff8,

            0x6e17,0x7e36,0x4e55,0x5e74,0x2e93,0x3eb2,0x0ed1,0x1ef0

            };

            public static ushort CRC16(byte[] DataBuf,int Len)

            {

                ushort  crc_reg = 0XFFFF;//:通信双方应约定相同的初值(如果是0xffff,结果应取反)

     

                for (int i = 0; i < Len; i++)

                {

                    crc_reg = (ushort)((crc_reg << 8) ^ CRC16Table[ ( (crc_reg >> 8 )  ^ DataBuf[i])& 0xff]);

                }

                return (ushort)(~crc_reg);

            }

            public static ushort CRC16(byte[] DataBuf,int  index ,int count)

            {

                ushort  crc_reg = 0XFFFF;//:通信双方应约定相同的初值(如果是0xffff,结果应取反)

     

                for (int i = index; i < count; i++)

                {

                    crc_reg = (ushort)((crc_reg << 8) ^ CRC16Table[ ( (crc_reg >> 8 )  ^ DataBuf[i])& 0xff]);

                }

                return (ushort)(~crc_reg);

            }

        }

    }

    实际效果图如下:




    展开全文
  • C# 校验码生成程序

    2009-07-17 20:56:58
    VS2008 下校验码生成项目,可自动生成校验码,产生图片格式的校验码~~~~~~~~~~~~~~~~~~~~~~~~~~
  • 基于FPGA 的CRC校验码生成器 今天给大侠带来基于FPGA的CRC校验码生成器,话不多说,上货。 1、概述 CRC即Cyclic Redundancy Check,循环冗余校验,是一种数字通信中的常用信道编码技术。其特征是信息段和校验...

    基于FPGA 的CRC校验码生成器

    今天给大侠带来基于FPGA的CRC校验码生成器,话不多说,上货。

     

    1、概述

    CRC即Cyclic Redundancy Check,循环冗余校验,是一种数字通信中的常用信道编码技术。其特征是信息段和校验字段的长度可以任意选定。

     

    2、CRC校验的基本原理

    CRC码是由两部分组成的,前部分是信息码,就是需要校验的信息,后部分是校验码,如果CRC码长共n bit,信息码长k bit,就称为(n,k)码,剩余的r bit即为校验位。如:(7,3)码:110 1001,前三位110为信息码,1001为校验码。

     

    3、校验码的生成规则

    • 1)将原信息码左移r bit,右侧补零,如 110--> 110 0000;

    • 2)用110 0000除以g(x) (注意,使用的是模2除法,见下文),得到的余数即为CRC校验码;

    • 3)将校验码续接到信息码的尾部,形成CRC码。

     

    4、关于生成多项式g(x)

    在产生CRC校验码时,要用到除法运算,一般来说,这是比较麻烦的,因此,把二进制信息预先转换成一定的格式,这就是CRC的多项式表示。二进制数表示为生成多项式的系数,如下:

    所有二进制数均被表示为一个多项式,x仅是码元位置的标记,因此我们并不关心x的取值,称之为码多项式。(我没研究过CRC代数推理过程,没体会到用多项式计算的方便之处,这里要学会的就是给出生成多项式g(x),能写出对应的二进制即可) 常见的生成多项式如下:

     

    5、关于模2除法

    模2运算就是加法不考虑进位,减法不考虑借位。

    1)加法运算:

    0+0=0 0+1=1 1+0=1 1+1=0

    例如0101+0011=0110,列竖式计算:

    2)减法运算:

    0-0=0 0-1=1 1-0=1 1-1=0

    例如0110-0011=0101,列竖式计算:

    3)乘法运算

    0×0=0 0×1=0 1×0=0 1×1=1

    多位二进制模2乘法类似于普通意义上的多位二进制乘法,不同之处在于后者累加中间结果时采用带进位的加法,而模2乘法对中间结果的处理方式采用的是模2加法。例如1011×101=100111,列竖式计算:

    4)除法运算:

    0÷1=0 1÷1=1

    多位二进制模2除法也类似于普通意义上的多位二进制除法,但是在如何确定商的问题上两者采用不同的规则。后者按带借位的二进制减法,根 据余数减除数够减与否确定商1还是商0,若够减则商1,否则商0。多位模2除法采用模2减法,不带借位的二进制减法,因此考虑余数够减除数与否是没有意义的。

    实际上,在CRC运算中,总能保证除数的首位为1,则模2除法运算的商是由余数首位与除数首位的模2除法运算结果确定。因为除数首位总是1,按照模2 除法运算法则,那么余数首位是1就商1,是0就商0。例如1100100÷1011=1110……110,列竖式计算:

    掌握了上面的运算规则,你可以尝试计算一个复杂一点的,如下:

    如果得到的余数结果正确,你掌握的东西就够用了。

     

    6.CRC-CCITT的硬件实现

    CRC-CCITT的生成多项式为:

    对应的二进制数就是上面复杂运算中那个除数。由刚才的计算可知,对于8 bit的数据 0xaa,它的CRC校验码为0001 0100 1010 0000,下面用verilog来实现,看能否得到这个结果。

    要实现这一过程,仍然需要LFSR电路,参看《FPGA产生基于LFSR的伪随机数》中关于该电路特性的介绍,如果您不需要了解原理,直接略过即可;有所改进的地方就是,可以将伪随机数发生器看作一个Moore型状态机,它的输出只与当前的状态有关;而此时利用LFSR电路,需要引入数据输入端,输出不仅取决于当前的状态,还取决于输入信号,相当于Mealy型状态机,如下图:

    注意对比与伪随机数产生器中该反馈支路的区别!

    反馈项gr+1gr……g0为生成多项式的系数,依然是1代表存在反馈,0代表不存在反馈;此电路可以完成上述的模2除法操作,若我们要求0xaa的CRC校验码,则从高位到低位顺序输入0xaa共8 bit后,D15……D0中的数据即为所要求的余数,即CRC校验位。

     

    7.verilog描述

    如果用时序电路串行实现,则8 bit数据要移位8次,就需要8个clk,效率低下,为了能在一个时钟周期输出结果,必须采用组合电路,当然,这是以空间换时间的方法,由于使用了for循环8次,直观的讲电路规模将扩大8倍。

    仿真结果如下:得到的是数据0xaa和0xf0的CRC校验码,为验证结果的正确性,您可以按照模2法则手工计算一下^.^

     

    8.4 bit信息位,5 bitCRC码的(9,4)码的程序和仿真结果

    同样给出一个4 bit信息位,5 bitCRC码的(9,4)码的程序和仿真结果,程序的流程与上述流程完全一样:

    后记:细心的读者可能发现,本文对LFSR电路能完成模2求余操作的原因避而不谈,不是因为不告诉你,是因为我也不是很清楚,工科背景对数学推理实在是有点不知所云,尤其是看到国内教材那好几页的公式的时候,如果您有深入浅出的讲解LFSR电路由来与应用的文章,注意是深入浅出的,请您大力推荐,在此感谢!

     

    【QQ交流群】

    群号:173560979,进群暗语:FPGA技术江湖粉丝。

    多年的FPGA企业开发经验,各种通俗易懂的学习资料以及学习方法,浓厚的交流学习氛围,QQ群目前已有1000多名志同道合的小伙伴,无广告纯净模式,给技术交流一片净土,从初学小白到行业精英业界大佬等,从军工领域到民用企业等,从通信、图像处理到人工智能等各个方向应有尽有。

     

    【微信交流群】

    现微信交流群已建立08群,人数已达数千人,欢迎关注“FPGA技术江湖”微信公众号,可获取进群方式。

    后续会持续更新,带来Vivado、 ISE、Quartus II 、candence等安装相关设计教程,学习资源、项目资源、好文推荐等,希望大侠持续关注。

    江湖偌大,继续闯荡,愿大侠一切安好,有缘再见!

    展开全文
  • CRC校验码生成器delphi版源码 本程序修改自网络资源。原程序有错误,因此进行了更正。 此程序本人是用于串口通信中的数据校验,符合Modbus协议GB/T19582.2-2008附录B中的算法。 本程序主要用于展示算法,带有详细...
  • WinMD5 校验码生成

    2011-06-15 17:43:33
    Windows下MD5校验码生成器,可以生成和检验MD5码,下载打开后可直接使用
  • 将十六进制字符串中的数(长度不限)累加求和,取累加和最低一个字节,生成CheckSum校验码。例如十六进制字符串:01 03 00 10 00 4D 31 30 30 20 32 36 64 42 6D 20 56 31 2E 30,生成CheckSum校验码为92(十六进制)...
  • LRC校验码生成工具

    热门讨论 2008-04-06 17:46:39
    用vb写的一个lrc校验码生成工具,对于使用LRC校验的通讯调试很有帮助。
  • ModBus RTU校验码生成

    2018-11-23 17:49:20
    ModBus RTU校验码自动生成,我的上一篇博客讲解了ModBus RTU协议,如有不清楚的可以参考下。
  • 用于汽车等机械第九位校验码生成,只需要输入前8位和后8位即可。第九位可以自动生成,用于汽车等机械第九位校验码生成,只需要输入前8位和后8位即可。第九位可以自动生成
  • 今天给大侠带来基于FPGA 的CRC校验码生成器设计,话不多说,上货。一、概述CRC,即Cyclic Redundancy Check,循环冗余校验,是一种数字通信中的常用信道编码技术。其...

    今天给大侠带来基于FPGA 的CRC校验码生成器设计,话不多说,上货。

    一、概述

    CRC,即Cyclic Redundancy Check,循环冗余校验,是一种数字通信中的常用信道编码技术。其特征是信息段和校验字段的长度可以任意选定。

    二、CRC校验的基本原理

    CRC码是由两部分组成的,前部分是信息码,就是需要校验的信息,后部分是校验码,如果CRC码长共n bit,信息码长k bit,就称为(n,k)码,剩余的r bit即为校验位。如:(7,3)码:110 1001,前三位110为信息码,1001为校验码。

    三、校验码的生成规则

    1) 将原信息码左移r bit,右侧补零,如 110--> 110 0000;

    2) 用110 0000除以g(x)  (注意,使用的是模2除法,见下文),得到的余数即为CRC校验码;

    3) 将校验码续接到信息码的尾部,形成CRC码。
           

    四、关于生成多项式g(x)

    在产生CRC校验码时,要用到除法运算,一般来说,这是比较麻烦的,因此,把二进制信息预先转换成一定的格式,这就是CRC的多项式表示。二进制数表示为生成多项式的系数,如下:      

    所有二进制数均被表示为一个多项式,x仅是码元位置的标记,因此我们并不关心x的取值,称之为码多项式。(我没研究过CRC代数推理过程,没体会到用多项式计算的方便之处,这里要学会的就是给出生成多项式g(x),能写出对应的二进制即可)

    常见的生成多项式如下:

    五、关于模2除法

    模2运算就是加法不考虑进位,减法不考虑借位。   

    1)加法运算:     

    0+0=0        0+1=1        1+0=1        1+1=0

    例如0101+0011=0110,列竖式计算:
              0 1 0 1
          + 0 0 1 1
          ──────
              0 1 1 0

     

    2)减法运算:      

    0-0=0        0-1=1        1-0=1        1-1=0  

    例如0110-0011=0101,列竖式计算:
             0 1 1 0
         -  0 0 1 1
           ──────
             0 1 0 1
     

    3)乘法运算

    0×0=0        0×1=0        1×0=0        1×1=1
          

    多位二进制模2乘法类似于普通意义上的多位二进制乘法,不同之处在于后者累加中间结果时采用带进位的加法,而模2乘法对中间结果的处理方式采用的是模2加法。例如1011×101=100111,列竖式计算:   

         

    4)除法运算:
           0÷1=0        1÷1=1
     

    多位二进制模2除法也类似于普通意义上的多位二进制除法,但是在如何确定商的问题上两者采用不同的规则。后者按带借位的二进制减法,根据余数减除数够减与否确定商1还是商0,若够减则商1,否则商0。多位模2除法采用模2减法,不带借位的二进制减法,因此考虑余数够减除数与否是没有意义的。

    实际上,在CRC运算中,总能保证除数的首位为1,则模2除法运算的商是由余数首位与除数首位的模2除法运算结果确定。因为除数首位总是1,按照模2除法运算法则,那么余数首位是1就商1,是0就商0。例如1100100÷1011=1110……110,列竖式计算:

    掌握了上面的运算规则,你可以尝试计算一个复杂一点的,如下:       

       

    如果得到的余数结果正确,你掌握的东西就够用了。
     

    六、CRC-CCITT的硬件实现

    CRC-CCITT的生成多项式为:   

         

    对应的二进制数就是上面复杂运算中那个除数。由刚才的计算可知,对于8 bit的数据 0xaa,它的CRC校验码为0001 0100 1010 0000,下面用verilog来实现,看能否得到这个结果:

    要实现这一过程,仍然需要LFSR电路,参看《FPGA设计中,产生LFSR伪随机数》中关于该电路特性的介绍,如果你不需要了解原理,直接略过即可;有所改进的地方就是,可以将伪随机数发生器看作一个Moore型状态机,它的输出只与当前的状态有关;而此时利用LFSR电路,需要引入数据输入端,输出不仅取决于当前的状态,还取决于输入信号,相当于Mealy型状态机,如下图:  

    注意对比与伪随机数产生器中该反馈支路的区别。

    反馈项gr+1gr……g0为生成多项式的系数,依然是1代表存在反馈,0代表不存在反馈;此电路可以完成上述的模2除法操作,若我们要求0xaa的CRC校验码,则从高位到低位顺序输入0xaa共8 bit后,D15……D0中的数据即为所要求的余数,即CRC校验位。

    七、verilog描述

    如果用时序电路串行实现,则8 bit数据要移位8次,就需要8个clk,效率低下,为了能在一个时钟周期输出结果,必须采用组合电路,当然,这是以空间换时间的方法,由于使用了for循环8次,直观的讲电路规模将扩大8倍。

          

    仿真结果如下:得到的是数据0xaa和0xf0的CRC校验码,为验证结果的正确性,可以按照模2法则手工计算一下。

    八、其他例子

    同样给出一个4 bit信息位,5 bitCRC码的(9,4)码的程序和仿真结果,程序的流程与上述流程完全一样:       

         

    说明:细心的大侠可能发现,本篇对LFSR电路能完成模2求余操作的原因避而不谈,不是因为不告诉你,是因为目前也不是很清楚,工科背景对数学推理实在是有点不知所云,尤其是看到国内教材那好几页的公式的时候,如果您有通俗易懂的讲解LFSR电路由来与应用的文章,注意是深入浅出的,请大力推荐,在此感谢。

    END
    展开全文
  • CRC循环冗余校验码生成器 ,计算机网络课程作业,有bug,参考,共享。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。...
  • 包含随机数据帧生成函数,CRC检验码生成函数,主函数对随机生成的数据帧进行计算生成CRC-16校验码,重难点在于指针的运用
  • 条形码校验码生成

    2019-09-20 22:12:38
    //判断25校验位是否正确///*交叉25码校验位的计算规则。交叉25校验位计算方法是 Mod 10 : 1、字符个数为偶数时为:10的倍数-[奇数位的数字之和(从左至右)+(偶数位数字之和)*3个位数] 2、字符个数为奇数时为...
  • CRC16校验码生成代码

    2018-05-17 09:17:47
    该代码为通用modbus CRC16检验码生成校验程序例程。采用查表方式,运行速度更快。crc16多项式为0xA001.

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,798
精华内容 1,119
关键字:

校验码生成