【问题标题】:Can I decrypt a password with c#, that was encrypted with PASSWORD_BCRYPT in php?我可以用 c# 解密密码,在 php 中用 PASSWORD_BCRYPT 加密吗?
【发布时间】:2019-10-17 22:20:13
【问题描述】:

我不确定我是否可以用 c# 解密密码,我存储在 mysql 数据库中。我使用 PASSWORD_BCRYPT 在 php 中加密了这些密码。 如果有可能我该怎么做?抱歉,我是初学者,在互联网上没有找到任何帮助。这是我用来加密密码的一段代码。

$passwort = $con->real_escape_string($_POST['passwort']);
$hash = password_hash($passwort, PASSWORD_BCRYPT);

在阅读了 cmets 之后,我尝试在 c# 中这样做,但它总是说密码错误

string email = textBox1.Text;
        string password = textBox2.Text;
        string passwordHash = BCrypt.Net.BCrypt.HashPassword(password);
        MessageBox.Show(passwordHash);
        MySqlConnection conn = new MySqlConnection("datasource=127.0.0.1;port=3306;username=root;password=CIAO6CIAO6;database=kontoprogramm");
        int i = 0;
        conn.Open();
        MySqlCommand cmd = new MySqlCommand("select KLPPassword from tklassenlehrpersonen where KLPEmail = '" + email + "' and KLPPassword = '" + passwordHash + "'", conn);
        cmd.ExecuteNonQuery();
        DataTable dt = new DataTable();
        MySqlDataAdapter da = new MySqlDataAdapter(cmd);
        da.Fill(dt);
        i = Convert.ToInt32(dt.Rows.Count.ToString());
        if (i == 0)
        {
            MessageBox.Show("Falsche Email oder Kennwort!");
        }
        else
        {
            MessageBox.Show("Angemeldet!");
        }

有人可以帮帮我吗?

【问题讨论】:

  • 您通常不会解密密码。如果您想查看密码是否正确,您将加密您正在检查的密码,如果加密密码与存储的加密密码匹配,那么很好。
  • 啊,谢谢。那么c#中的密码是否可以用php的PASSWORD_BCRYPT函数的相同哈希算法加密,这样我可以比较一下?
  • BCRYPT 不是加密方法,它是hashing function,因此无法解密
  • 对方法real_escape_string的调用不正确。如果您试图使用它来防止 SQL 注入,那么您应该使用准备好的语句。
  • @Dharman 好的,谢谢。另外,如何将我在数据库中使用 php 中的 BCRYPT 函数创建的哈希字符串与用户在我的 c# 程序中输入的密码进行比较?

标签: c# php hash bcrypt


【解决方案1】:

由于盐的原因,您无法在数据库中搜索哈希,而是仅通过用户名搜索并获取存储的哈希进行验证。这个answer 展示了如何在 PHP 中做到这一点,虽然原理是一样的。

在调用password_hash()之前不要转义用户输入,这会带来麻烦。

【讨论】:

    【解决方案2】:

    首先,你不能解密,只有你努力排查和破解密码解密,例如,使用Brute Force技术等,因为最终从PHP通过password_hash函数生成一个散列密码,散列结果。根据散列主概念,不可逆,但可以比较。

    您可以使用 PHP 函数 password_verify 比较密码哈希值(将数据库中存储的哈希值与 C# 应用程序中输入的密码进行比较)。如果你的需求真的是解密,那就需要改变帖子的重点,重新考虑排查问题,破解密码解密,例如使用Brute Force技术等。

    现在,让我们来解决问题:您有两种方法:

    a) 创建一个参数化为“明文”作为输入参数的PHP WebService,并得到输出结果为密文密码; Web Service 的核心(在 PHP 中)使用带有 PASSWORD_BCRYPT 选项的 password_hash 进行加密。之后,您的 C# 代码使用加密数据并将此输出哈希与数据库中存储的哈希进行比较;但是,这种替代方案需要在 WebServer 和 WebService 层的安全性上投入很多精力。例如,您的 C# 代码使用此 PHP Web 服务,代码如下:

    WebClient webclient = new WebClient();
    webclient.DownloadStringCompleted += new DownloadStringCompletedEventHandler(webclient_DownloadStringCompleted);
    webclient.DownloadStringAsync(new Uri("http://ws.phpurl.com/?password=stackoverflow@12345"));
    
    void webclient_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
    {
        string phpWsEncryptedPass = e.Result;
        string databaseEncryptedPass = //TO DO: query Database
                                       //using WHERE statement,
                                       //parsing 'phpWsEncryptedPass' as parameter;
    }
    

    b) ,下载您所使用的适用于 Windows 的相应 PHP 版本的 binaries,使用 DLL Reflector 应用程序(例如 dotPeek)了解这些 DLL 方法并使用C# Interop features 导入 DLL 有 password_hashpassword_verify 在你的 C# 代码中使用它;您需要努力打开 DLL,以获得正确的方法声明。注意:建议采用这种方式,因为使用 C/C++ 编写的 PHP 核心和 C# 代码可以使用 PHP 的 DLL for Windows 二进制文件,下面的代码有一个示例:

        [DllImport(@"C:\ProgramFiles\PHP\php_mbstring.dll", CharSet = CharSet.Unicode)]
        internal static extern IntPtr password_hash(string clearTextpassword, int option)
    
        [DllImport(@"C:\ProgramFiles\PHP\php_mbstring.dll", CharSet = CharSet.Unicode)]
        internal static extern bool password_verify(string clearTextpassword, string hash)
    

    就是这样。

    【讨论】:

      猜你喜欢
      • 2012-08-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多