You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JS中RSA密钥生成异常:e的模逆d不满足e*d≡1 mod Φ(n)

问题分析与解决方案

你的代码核心问题是原生BigInt与peterolson的bigInt库对象混用,加上大整数转Number时的精度丢失,导致模逆计算失效。具体问题点和修复方案如下:

问题1:类型混用导致计算异常

你同时使用了原生BigInt(比如e、fiN的定义)和bigInt库的API(bigInt.gcd、bigInt.modInv),两种类型的对象不兼容:

  • bigInt.gcd(e, fiN)接收的是原生BigInt,库无法正确解析,返回的结果也不是原生BigInt,和1n比较时逻辑失效。
  • bigInt(e).modInv(fiN)返回的是库的bigInt对象,直接转BigInt(d)会丢失库的内部状态,导致后续计算错误。

问题2:大整数转Number的精度丢失

range = (fiN-1n) - BigInt(2)是BigInt类型,转成Number(range)时,因为Φ(n)远大于Number的安全整数范围(2^53≈9e15),转换后会丢失精度,生成的随机e实际值和预期不符,甚至可能破坏e与Φ(n)互质的条件。


修复后的代码

统一使用bigInt库的API处理所有大整数操作,避免类型混用和精度丢失:

const lowNumber = 10**9;
const highNumber = (10**10) - 1;
let p, q;

// 生成两个大素数p和q
for(let i = 0; i < 2; i++){
  let primeNumber = Math.floor(Math.random() * (highNumber - lowNumber + 1)) + lowNumber;
  while (!isPrime(primeNumber)){
    primeNumber = Math.floor(Math.random() * (highNumber - lowNumber + 1)) + lowNumber;
  }
  if(i === 0){
    p = bigInt(primeNumber); // 转成库的bigInt对象
  } else{
    q = bigInt(primeNumber);
  }
}

const n = p.multiply(q);
const fiN = p.subtract(1).multiply(q.subtract(1));

// 生成与fiN互质的素数e
let e;
while (true) {
  // 用库的random方法生成大整数,避免精度丢失
  e = bigInt.random(fiN.bitLength() - 1).add(2);
  while (!isPrime(e.toJSNumber())){ // 若isPrime不支持BigInt,需修改函数适配大整数
    e = bigInt.random(fiN.bitLength() - 1).add(2);
  }
  if (e.gcd(fiN).equals(bigInt(1))){
    break;
  }
}

// 计算模逆并验证
const d = e.modInv(fiN);
const result = e.multiply(d).mod(fiN);
console.log("inverse is: " + result.toString()); // 现在应该输出1

关键修改说明

  1. 统一类型:所有大整数(p、q、n、fiN、e、d)都用bigInt库的对象存储,避免原生BigInt和库对象混用。
  2. 避免精度丢失:用bigInt.random()生成大随机数,代替Math.random()转Number的方式。
  3. 正确调用库API:使用multiply()、subtract()、gcd()、modInv()等库方法完成运算,不要用原生的*、-、%。
  4. 素数判断兼容:如果你的isPrime函数不支持BigInt,需要修改它来处理大整数,或者直接使用库自带的bigInt.isProbablePrime()方法。

内容的提问来源于stack exchange,提问作者Marceli23

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.04 19:43:15