【问题标题】:Calculate d from n, e, p, q in RSA?从 RSA 中的 n、e、p、q 计算 d?
【发布时间】:2014-06-10 08:19:29
【问题描述】:

不确定这是否是提出密码学问题的正确地方,但这里是。

我正在尝试在 RSA 中计算“d”,我已经计算出了 p、q、e、n 和 ø(n);

p = 79, q = 113, e = 2621

n = pq                   ø(n) = (p-1)(q-1)
n = 79 x 113 = 8927      ø(n) = 78 x 112 = 8736

e = 2621
d = ???

我似乎找不到 d,我知道 d 是一个值……ed mod ø(n) = 1。任何帮助将不胜感激

例如 e = 17, d = 2753, ø(n) = 3120

17 * 2753 mod 3120 = 1

【问题讨论】:

标签: encryption cryptography rsa public-key-encryption


【解决方案1】:

您正在寻找 e (mod n) 的模逆,可以使用扩展欧几里得算法计算:

function inverse(x, m)
    a, b, u := 0, m, 1
    while x > 0
        q := b // x # integer division
        x, a, b, u := b % x, u, x, a - q * u
    if b == 1 return a % m
    error "must be coprime"

因此,在您的示例中,inverse(17, 3120) = 2753 和 inverse(2621, 8736) = 4373。如果您不想实现该算法,可以向 Wolfram|Alpha 询问答案。

【讨论】:

  • 干杯,我听说过 wolfram alpha,我认为这是一个您必须安装的程序,所以直到现在我才理会它。我得到的答案是 4373,通过使用命令 - 2621 模 8736 的倒数。但是,如果我重新检查答案,我得到 0,它不应该是 1 吗? “ed mod ø(n) = 1”。此外,我相信您应该在 RSA 中有 2 个小数和大数。我试图解决的问题是我有一个很大的“e”,但在这个例子中,“e”很小,“d”很大
  • 我原来的解决方案误读了数字;答案现在已经确定。对困惑感到抱歉。在 RSA 中,通常 e 在其二进制表示中只有少量的 1 位,因为没有对 0 位进行计算。因此,e = 3 = 11b 或 e = 65537 = 10000000000000001b 很常见。
  • @user3423572:我还是错了;阅读障碍必须是强大的dotay。现在已经修好了,我希望。骗子。
【解决方案2】:

您需要的算法是Extended Euclidean Algorithm。这允许您计算 Bézout 恒等式的系数,该系数表明对于任何两个非零整数 ab,存在整数 xy,这样:

ax + by = gcd(a,b)

这似乎不会立即有用,但是我们知道eφ(n) 是互质的,gcd(e,φ(n)) = 1。所以算法给了我们xy这样:

ex + φ(n)y = gcd(e,φ(n))
           = 1
Re-arrange:
ex = -φ(n)y + 1

这相当于说ex mod φ(n) = 1,所以x = d

【讨论】:

  • 感谢您的回复。我有点迷失了你的解释我正在努力将你提供的公式应用于我的问题。过去我遇到过欧几里得算法,但它只是计算最大公约数 - gcd
  • @user3423572 我的回答实际上是对算法为何起作用的描述 - 第一行中“扩展欧几里得算法”的链接应该为您指明正确的方向。没错,通常的欧几里得算法为您提供了 GCD,但是“扩展”版本为您提供了 Bézout 恒等式的系数 - 其中之一就是您需要的 d
  • @Iridium 如何知道我需要哪一个?
【解决方案3】:

例如,您需要在下一个中获取 d:
3*d = 1 (mod 9167368)

这同样是:
3*d = 1 + k * 9167368,其中 k = 1, 2, 3, ...

重写:
d = (1 + k * 9167368)/3

您的 d 必须是具有最低 k 的整数。
让我们写出公式:
d = (1 + k * fi)/e

public static int MultiplicativeInverse(int e, int fi)
        {
            double result;
            int k = 1;
            while (true)
            {
                result = (1 + (k * fi)) / (double) e;
                if ((Math.Round(result, 5) % 1) == 0) //integer
                {
                    return (int)result;
                }
                else
                {
                    k++;
                }
            }
        } 

让我们测试一下这段代码:

Assert.AreEqual(Helper.MultiplicativeInverse(3, 9167368), 6111579); // passed

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-08-07
    • 1970-01-01
    • 2013-04-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多