java - SecureRandom.nextBytes() 是为 SecureRandom 实例设置初始种子的唯一方法吗?
问题描述
我已经看过很多 SecureRandom 的教程来给出以下示例:
SecureRandom random = new SecureRandom();
random.nextBytes(new byte[20]);
从文档中可以看出,当创建 SecureRandom 实例时,它还没有播种。nextBytes() 方法将为其调用默认播种。因此,我还看到以下建议:
如果使用 SHA1PRNG,请始终在创建 PRNG 的新实例后立即调用 java.security.SecureRandom.nextBytes(byte[])。
我的第一个问题是:这是必须的吗?我还可以用以下方式播种吗:
SecureRandom random = new SecureRandom();
sandom.setSeed(random.generateSeed(20));
它也是一种安全的播种方式吗?
我的第二个问题是关于重新播种。
java.security.SecureRandom 类的 setSeed(long seed) 方法用于使用给定长种子中包含的 8 个字节重新设置此随机对象的种子。给定的种子是对现有种子的补充,而不是替代。因此,保证重复调用永远不会减少随机性。
因此,这意味着一旦我立即调用 nextBytes 来调用默认播种。不管重新播种的种子是什么,它总是安全的,对吗?这是否意味着以下提供硬编码种子的代码也是安全的:
SecureRandom random = new SecureRandom();
random.nextBytes(new byte[20]);
//reseed after usage
random.setSeed(new byte[]{0x(90),0x(15)});
我也对教程https://howtodoinjava.com/java8/secure-random-number-generation/感到困惑 有一个小节 2.3:
2.3. 提供更多机会增加熵
定期创建 SecureRandom 的新实例并重新设置种子,如下所示:
SecureRandom sr = SecureRandom.getInstance("SHA1PRNG", "SUN");
sr.setSeed(SecureRandom.generateSeed(int))
如果种子泄露,定期重新播种可防止数据泄露。如果使用 SHA1PRNG,请始终在创建 PRNG 的新实例后立即调用 java.security.SecureRandom.nextBytes(byte[])。
这让我很困惑。这很矛盾吗?为什么它给出的代码示例没有立即调用 nextBytes 而是使用 setSeed?是重新播种吗?我想重新播种是重复播种相同的 SecureRandom 实例。但是 SecureRandom sr = SecureRandom.getInstance("SHA1PRNG", "SUN") 会生成一个新的 secureRandom 实例,对吗?我们可以只使用一个 secureRandom 实例,但定期调用 setSeed() 来重新设置它吗?
解决方案
推荐阅读
- sql - 融入性能
- typescript - 键入“除...之外的所有可能的字符串值”
- python - 将序列日期列(yyyy-mm-dd)转换为英国日期格式(Pythonic 方式)
- python - client.scatter 耗时过长
- c# - JSON 硬编码数据 C#
- spring - Spring security:如何为某些匹配器启用匿名,但为其余匹配器禁用它?
- apache-spark - Spark HiveContext 获得与 hive 客户端选择相同的格式
- opengl - 纹理不起作用 - OpenGL
- vue.js - Vue.js 函数多次调用
- c++ - Tesseract C++:指定要查找的字符数量