人民医院前端

rng.js 2.7KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879
  1. // Random number generator - requires a PRNG backend, e.g. prng4.js
  2. import { prng_newstate, rng_psize } from "./prng4";
  3. var rng_state;
  4. var rng_pool = null;
  5. var rng_pptr;
  6. // Initialize the pool with junk if needed.
  7. if (rng_pool == null) {
  8. rng_pool = [];
  9. rng_pptr = 0;
  10. var t = void 0;
  11. if (typeof window !== 'undefined' && window.crypto && window.crypto.getRandomValues) {
  12. // Extract entropy (2048 bits) from RNG if available
  13. var z = new Uint32Array(256);
  14. window.crypto.getRandomValues(z);
  15. for (t = 0; t < z.length; ++t) {
  16. rng_pool[rng_pptr++] = z[t] & 255;
  17. }
  18. }
  19. // Use mouse events for entropy, if we do not have enough entropy by the time
  20. // we need it, entropy will be generated by Math.random.
  21. var count = 0;
  22. var onMouseMoveListener_1 = function (ev) {
  23. count = count || 0;
  24. if (count >= 256 || rng_pptr >= rng_psize) {
  25. if (window.removeEventListener) {
  26. window.removeEventListener("mousemove", onMouseMoveListener_1, false);
  27. }
  28. else if (window.detachEvent) {
  29. window.detachEvent("onmousemove", onMouseMoveListener_1);
  30. }
  31. return;
  32. }
  33. try {
  34. var mouseCoordinates = ev.x + ev.y;
  35. rng_pool[rng_pptr++] = mouseCoordinates & 255;
  36. count += 1;
  37. }
  38. catch (e) {
  39. // Sometimes Firefox will deny permission to access event properties for some reason. Ignore.
  40. }
  41. };
  42. if (typeof window !== 'undefined') {
  43. if (window.addEventListener) {
  44. window.addEventListener("mousemove", onMouseMoveListener_1, false);
  45. }
  46. else if (window.attachEvent) {
  47. window.attachEvent("onmousemove", onMouseMoveListener_1);
  48. }
  49. }
  50. }
  51. function rng_get_byte() {
  52. if (rng_state == null) {
  53. rng_state = prng_newstate();
  54. // At this point, we may not have collected enough entropy. If not, fall back to Math.random
  55. while (rng_pptr < rng_psize) {
  56. var random = Math.floor(65536 * Math.random());
  57. rng_pool[rng_pptr++] = random & 255;
  58. }
  59. rng_state.init(rng_pool);
  60. for (rng_pptr = 0; rng_pptr < rng_pool.length; ++rng_pptr) {
  61. rng_pool[rng_pptr] = 0;
  62. }
  63. rng_pptr = 0;
  64. }
  65. // TODO: allow reseeding after first request
  66. return rng_state.next();
  67. }
  68. var SecureRandom = /** @class */ (function () {
  69. function SecureRandom() {
  70. }
  71. SecureRandom.prototype.nextBytes = function (ba) {
  72. for (var i = 0; i < ba.length; ++i) {
  73. ba[i] = rng_get_byte();
  74. }
  75. };
  76. return SecureRandom;
  77. }());
  78. export { SecureRandom };