zoukankan      html  css  js  c++  java
  • C# salt+hash 加密

    1   先明确几个基本概念

      (1)伪随机数:pseudo-random number generators ,简称为:PRNGs,是计算机利用一定的算法来产生的。伪随机数并不是假随机

          数,这里的“伪”是有规律的意思,就  是计算机产生的伪随机数既是随机的又是有规律的。怎样理解呢?产生的伪随机数有时遵守一定的规律,有

          时不遵守任何规律;伪随机数有一部分遵守一定的规律;另一部分不遵守任何规律。比如“世上没有两片形状完全相同的树叶”,这正是点到了事

          物的特性,即随机性,但是每种树的叶子都有近似的形状,这正是事物的共性,即规律性。从这个角度讲,你大概就会接受这样的事实了:计算机

          只能产生伪随机数而不能产生绝对随机的随机数。

      (2)真随机数:true random number generators ,简称为:TRNGs,是利用不可预知的物理方式来产生的随机数。

      (3)明文:原始密码,未经过任何算法加密的密码。

      (4)密文:原始密码经过某种算法加密后,形成的密码。

    2   C# salt+hash加密规则

       规则:salt伪随机值+原始密码,即salt伪随机值与原始密码组合成明文,然后经过hash算法形成密文,如:

               假设salt产生的伪随机数为:9de74893-0b41-4f4e-91dc-06f62241b8bc

               原始明文为:admin

               组合规则:原始明文+salt伪随机值,即admin9de74893-0b41-4f4e-91dc-06f62241b8bc

               hash加密后密文:urfFO/IWz912E2GXL4KiCzbosuZ6TdLpMk7lDRVVdYk=

               数据库表结果如下:

               

    3   C# salt产生伪随机数原理

       第一步:引入命名空间 using System;

       第二步:调用结构体Guid的NewGuid()方法;

       第三步:代码表示 string strSalt = Guid.NewGuid().ToString();  

           注释:当然,也可以调用类Random下的方法来产生伪随机数。

    4   hash原理

       hash是一种不可逆加密算法,C# HASH算法比较多,列举几种如下:

       (1)MD5

       (2)SHA家族:这里顺便提一下,美国政府以前广泛采用SHA-1算法,在2005年被我国山东大学的王小云教授发现了安全漏洞,所以现在比较常

           用SHA-1加长的变种,比如SHA-256。在.NET中,可以使用SHA256Managed类

       (3)关键代码如下:

    protected void btnRegister_Click(object sender, EventArgs e)
            {
               //用户名和密码
                string userName = this.TextBoxUserName.Text;
                string userPwd = this.TextBoxPWD.Text;
                //salt
                string strSalt= Guid.NewGuid().ToString();
               
                //SHA256加密
                byte[] pwdAndSalt = Encoding.UTF8.GetBytes(userPwd + strSalt);
                byte[] hashBytes = new SHA256Managed().ComputeHash(pwdAndSalt);
                string hashStr = Convert.ToBase64String(hashBytes);
    
                StringBuilder strBuid = new StringBuilder();
                strBuid.Append("INSERT INTO userInfo(");
                strBuid.Append("userName,userPassword,salt) values(");
                strBuid.Append("@userName,@hashStr,@strSalt)");
                SqlParameter[] sqlpara = {
                                             new SqlParameter("@userName",SqlDbType.NVarChar,50),
                                             new SqlParameter("@hashStr",SqlDbType.NVarChar,50),
                                             new SqlParameter("@strSalt",SqlDbType.NVarChar,50)
                                         };
                sqlpara[0].Value = this.TextBoxUserName.Text;
                sqlpara[1].Value = hashStr;
                sqlpara[2].Value = strSalt;
                //获取连接字符串
                string sqlConStr = ConfigurationManager.ConnectionStrings["conStr"].ConnectionString;
    
                using (SqlConnection con=new SqlConnection(sqlConStr))
                {
                    con.Open();
                    SqlCommand cmd = new SqlCommand(strBuid.ToString(),con);
                    cmd.Parameters.AddRange(sqlpara);
                    if (cmd.ExecuteNonQuery()>0)
                    {
                        Response.Write("<script>alert('注册成功!')</script>");
                    }
                    else
                    {
                        Response.Write("<script>alert('注册失败!')</script>");
                    }
                     
                }
            }
    

      

      

    5   C#常见加密算法

         MD5加密、SHA家族加密、RSA加密、DES加密,目前主流加密为RSA,如数字签名等,在本篇博客中,就不论述,以后会对这四类算法作详细论述。

    6   常见密码破解算法

         最简单、常见的破解方式当属字典破解(Dictionary Attack)和暴力破解(Brute Force Attack)方式。这两种方法说白了就是猜密码。

    image 

          字典破解和暴力破解都是效率比较低的破解方式。如果你知道了数据库中密码的哈希值,你就可以采用一种更高效的破解方式,查表法(Lookup Tables)。还有一些方法,比如逆向查表法(Reverse Lookup Tables)、彩虹表(Rainbow Tables)等,都和查表法大同小异。现在我们来看一下查表法的原理。

         查表法不像字典破解和暴力破解那样猜密码,它首先将一些比较常用的密码的哈希值算好,然后建立一张表,当然密码越多,这张表就越大。当你知道某个密码的哈希值时,你只需要在你建立好的表中查找该哈希值,如果找到了,你就知道对应的密码了。

     

    7   为什么使用hash来加密

    如果你需要保存密码(比如网站用户的密码),你要考虑如何保护这些密码数据,象下面那样直接将密码写入数据库中是极不安全的,因为任何可以打开数据库的人,都将可以直接看到这些密码。

    image

    解决的办法是将密码加密后再存储进数据库,比较常用的加密方法是使用哈希函数(Hash Function)。哈希函数的具体定义,大家可以在网上或者相关书籍中查阅到,简单地说,它的特性如下:

    (1)原始密码经哈希函数计算后得到一个哈希值

    (2)改变原始密码,哈希函数计算出的哈希值也会相应改变

    (3) 同样的密码,哈希值也是相同的

    (4) 哈希函数是单向、不可逆的。也就是说从哈希值,你无法推算出原始的密码是多少

    有了哈希函数,我们就可以将密码的哈希值存储进数据库。用户登录网站的时候,我们可以检验用户输入密码的哈希值是否与数据库中的哈希值相同。

    image

    由于哈希函数是不可逆的,即使有人打开了数据库,也无法看到用户的密码是多少。

    那么存储经过哈希函数加密后的密码是否就是安全的了呢?参照六、发现并不安全,只有加上salt才安全,因为salt是随机生成的。

    转载自:http://www.cnblogs.com/wangjiming/

  • 相关阅读:
    查看mysql版本的四种方法及常用命令
    newInstance和new的区别(good)
    Citrix 服务器虚拟化之六 Xenserver虚拟机创建与快照
    Java实现 蓝桥杯 算法训练 排序
    Java实现 蓝桥杯 算法训练 排序
    Java实现 蓝桥杯 算法训练 排序
    Java实现 蓝桥杯 算法训练 2的次幂表示
    Java实现 蓝桥杯 算法训练 2的次幂表示
    Java实现 蓝桥杯 算法训练 前缀表达式
    Java实现 蓝桥杯 算法训练 前缀表达式
  • 原文地址:https://www.cnblogs.com/guohu/p/8464737.html
Copyright © 2011-2022 走看看