可靠地在C#中重现用PHP实现的传统密码散列方法

我们正在将在Linux上运行的PHP应用程序迁移到我们在C#中实现并在Windows上运行的新单点登录(SSO)基础架构。

作为迁移过程的一部分,我们需要我们的C#SSO基础架构能够以与PHP应用程序完全相同的方式散列密码。

虽然PHP应用程序使用了一个相当合理的密码散列算法,但是除了密码和salt之外, 不幸的是,得到散列的字符串还包含salt值的余弦值(解释为整数) ……这是一个相当不寻常的决定。 midly。

不出所料,事实certificate,在PHP和C#中计算大整数的余弦导致结果略有不同。 这意味着我们可能无法在新的SSO基础架构中可靠地重新实现传统密码散列算法。

我们考虑的一个解决方案是在AWS Lambda中运行PHP密码散列函数,并从我们的SSO基础架构中查询Lambda。

你能想到其他选择吗?

在你提出的另一个问题中

在使用Visual Studio 2017编译的简单C程序中,C的cos(double)函数给出了

 c = -0.57977754519881342 

虽然你没有直截了当地说,但这似乎是你正在寻找的结果(它肯定不同于Math.Cos的结果,不确定它是否与PHP按位相同)。

因此,使用VS2017编译一个DLL,然后P /调用它。 或者在C运行时库DLL中调用cos() ,它肯定会导出所有这些#include 函数。

 c:\Windows\System32>dumpbin /exports msvcr120.dll | find "cos" 1442 5A1 00081C44 acos 1443 5A2 00081F2C acosf 1444 5A3 000821B8 acosh 1445 5A4 0008227C acoshf 1446 5A5 0008233C acoshl 1472 5BF 00083ED4 cacos 1473 5C0 00084208 cacosf 1474 5C1 000844BC cacosh 1475 5C2 00084824 cacoshf 1476 5C3 00084AF4 cacoshl 1477 5C4 00084E5C cacosl 1497 5D8 00086CF4 ccos 1498 5D9 00086D70 ccosf 1499 5DA 00086EAC ccosh 1500 5DB 0008714C ccoshf 1501 5DC 000873AC ccoshl 1502 5DD 0008756C ccosl 1526 5F5 00088640 cos 1527 5F6 00088BA0 cosf 1528 5F7 000890A0 cosh 1529 5F8 00089574 coshf c:\Windows\System32>dumpbin /exports msvcrt.dll | find "cos" 1046 415 000372D0 acos 1047 416 00019BE0 acosf 1069 42C 000118F0 cos 1070 42D 00015480 cosf 1071 42E 000868F0 cosh 1072 42F 0001ABC0 coshf 

PHP将从glibc的math.h 调用 cos实现。 您可以查看该实现并在应用程序中重新创建它? 这可能会变得毛茸茸,因为glibc的数学东西非常复杂。 如果在您的应用程序中使用glibc作为依赖项是可以接受的,那么您可以尝试这种方法吗? 无论如何,这就是我开始的地方。

对我来说另一个问题是你实际上也在处理PHP的一些奇怪的浮点处理,所以算法的所有“字符”并非仅仅来自涉及的trig函数。

据推测,盐与每个密码一起存储。 您可以使用PHP代码计算余弦值,并将其与密码一起存储。 然后,我还会添加密码版本号,并将所有旧密码默认为版本1.然后,在您的C#代码中,对于任何新密码,您实施新的哈希算法,并将这些密码哈希值存储为密码版本2。任何版本1密码,要进行身份validation,您不必计算余弦,您只需使用与密码哈希和盐一起存储的密码。

PHP代码的程序员可能想要做一个聪明的胡椒版本。 通过存储余弦,或胡椒以及盐和密码哈希,你基本上将胡椒变成盐2。 因此,另一种无版本的方法是在C#散列代码中使用两个salt。 对于新密码,您可以将第二个盐留空或以其他方式分配。 对于旧密码,它将是余弦,但它已经计算好了。