{"_id":"secure-random-uniform","_rev":"12-5b299c3354951c7bc247240bf74e969d","name":"secure-random-uniform","description":"Generate secure, random, uniform integers, compensating for modulo bias","dist-tags":{"latest":"4.0.0"},"versions":{"1.0.0":{"name":"secure-random-uniform","version":"1.0.0","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"randombytes":"^2.0.3"},"devDependencies":{},"scripts":{"test":"node verification"},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"98bfd86c7b348b0ee41a838280efe7b21798c5c6","_id":"secure-random-uniform@1.0.0","_shasum":"d3bf60343a7c58d0fe2113f0740cc93ff51e5573","_from":".","_npmVersion":"3.10.6","_nodeVersion":"6.3.0","_npmUser":{"name":"emilbay","email":"github@tixz.dk"},"dist":{"shasum":"d3bf60343a7c58d0fe2113f0740cc93ff51e5573","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-1.0.0.tgz","integrity":"sha512-RscEX8qFUWTfILEGbd7bavu+101Jj5wweQ+tzZqpR07O++2yllQZ56MByGKYiVASsA8UarYEL4wd0hY1Lu9Dgw==","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEQCIFpzLObDzDP1lOlXmzANIe2q2BicldqtxYXPKhPZqB/YAiA0zhPMClR//5bc2xn59wWQBmOs1kjMfwcVmFjsauOmzw=="}]},"maintainers":[{"name":"emilbay","email":"github@tixz.dk"}],"_npmOperationalInternal":{"host":"packages-16-east.internal.npmjs.com","tmp":"tmp/secure-random-uniform-1.0.0.tgz_1476366973945_0.7250199199188501"},"directories":{}},"1.0.1":{"name":"secure-random-uniform","version":"1.0.1","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"randombytes":"^2.0.3"},"devDependencies":{},"scripts":{"test":"node verification"},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"db288f7d74423a88eac203735104fe439e93da55","_id":"secure-random-uniform@1.0.1","_shasum":"bbbf80b2062eb7196690c3ada5c1f559f38814ba","_from":".","_npmVersion":"3.10.6","_nodeVersion":"6.3.0","_npmUser":{"name":"emilbay","email":"github@tixz.dk"},"dist":{"shasum":"bbbf80b2062eb7196690c3ada5c1f559f38814ba","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-1.0.1.tgz","integrity":"sha512-1DfGtSwYdWY+45LOUN9vq1uGFyPSbbIV/wTWxGxv3rhmkKHnj6Z0h8PQj1rH5y3WL6utUwydN4FSYXtO+yziZQ==","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIGk4LoMKIyhuoA2xGaGD8KTjoXGM6ED4L0wl/kygdcSBAiEAklj2NIc6gS13nQ8ApTPwxa4YbzFOUVF4rhNZUnpCgqs="}]},"maintainers":[{"name":"emilbay","email":"github@tixz.dk"}],"_npmOperationalInternal":{"host":"packages-16-east.internal.npmjs.com","tmp":"tmp/secure-random-uniform-1.0.1.tgz_1476367046640_0.9635015418753028"},"directories":{}},"2.0.0":{"name":"secure-random-uniform","version":"2.0.0","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"nanoassert":"^1.1.0","randombytes":"^2.0.3","sodium-universal":"^2.0.0"},"scripts":{},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"b20264b77f779a7f99c83cf7526faee075f6b097","_id":"secure-random-uniform@2.0.0","_npmVersion":"5.5.1","_nodeVersion":"8.9.1","_npmUser":{"name":"emilbayes","email":"github@tixz.dk"},"dist":{"integrity":"sha512-EJEc+cEx6dSkNnYpaVagdxMMBuWxRYFR1MsIbQUcUg6cxid8fdvh0/cpqkHT4nwdgd1dNfPJOUYBLsjx//ARgw==","shasum":"07043fd25666ca8942ae0cd56db1c04d1844d4fa","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-2.0.0.tgz","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEYCIQD5GTzv93QdGFK0xs8OwUTH1lIvzbgK4k0L8SsouCMjGgIhAM/Kqxag4gt6kGBck8KVKELrRdfuZpZR3a5v1joRHiLM"}]},"maintainers":[{"email":"github@tixz.dk","name":"emilbayes"},{"email":"github@tixz.dk","name":"emilbay"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/secure-random-uniform-2.0.0.tgz_1515015325740_0.5386006878688931"},"directories":{}},"3.0.0":{"name":"secure-random-uniform","version":"3.0.0","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"nanoassert":"^1.1.0","randombytes":"^2.0.3","sodium-universal":"^2.0.0"},"scripts":{},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"2f4ab70228e547318207536ea8d0811a42fc137d","_id":"secure-random-uniform@3.0.0","_npmVersion":"5.5.1","_nodeVersion":"8.9.1","_npmUser":{"name":"emilbayes","email":"github@tixz.dk"},"dist":{"integrity":"sha512-xlDA2+fuUJ6EVl2jCD8OisITqXOBb4mQApUsX+/eOLe5kglYCoaAo/5Zh7FjOFWjkoU2tw0baXpp9RiOi23xTg==","shasum":"426e94c8bed1fd0c89ace3c65af8e1de3673ed45","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-3.0.0.tgz","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIQDBcPJKn1CVn1m2URlaxmjCZj72iRLeYQzm8VuQ6BQDMAIgS+quXJ5WG31qPxYDjlLKEFWx0RuO0AmAfYz7mzyhOxw="}]},"maintainers":[{"email":"github@tixz.dk","name":"emilbayes"},{"email":"github@tixz.dk","name":"emilbay"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/secure-random-uniform-3.0.0.tgz_1515099866741_0.13677824870683253"},"directories":{}},"3.0.1":{"name":"secure-random-uniform","version":"3.0.1","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"nanoassert":"^1.1.0","randombytes":"^2.0.3","sodium-universal":"^2.0.0"},"scripts":{},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"c030231e5100a3bb84a8773c708357718c7f99cd","_id":"secure-random-uniform@3.0.1","_npmVersion":"5.5.1","_nodeVersion":"8.9.1","_npmUser":{"name":"emilbayes","email":"github@tixz.dk"},"dist":{"integrity":"sha512-1dEu6OUnJdDkb4DRsdiMjTOSVp50JCtPssFnZpFFp8Pzq1uAf3wkbTXCboPOSVqHauZUYm9GqSvzkkH8Yo6+3g==","shasum":"136c2eee0ca0447d6793fc846dfb420a3c5563c0","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-3.0.1.tgz","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIQDP3eefw6iPomaeEwvoqqOe1EBeXT9JoTr+Bnr9guhxUAIgUtVoG4TlPoDQcwYmZ9YwHXumQt2VFCauwxaysCcBJhA="}]},"maintainers":[{"email":"github@tixz.dk","name":"emilbayes"},{"email":"github@tixz.dk","name":"emilbay"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/secure-random-uniform-3.0.1.tgz_1515143827208_0.8444126339163631"},"directories":{}},"3.1.0":{"name":"secure-random-uniform","version":"3.1.0","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"nanoassert":"^1.1.0","randombytes":"^2.0.3","sodium-universal":"^2.0.0"},"scripts":{},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"9aa6231d900af812c80e58884b2b87c8c848fac1","_id":"secure-random-uniform@3.1.0","_npmVersion":"5.6.0","_nodeVersion":"10.0.0","_npmUser":{"name":"emilbayes","email":"github@tixz.dk"},"dist":{"integrity":"sha512-uRsCi2xIEhGx73ZW3k4OCIdEvN/N+Xk8GFPaFoYpguHoc2Qx1IZZGLmwM2eSmLShutyD9ve/lF0nx5MjGXbhmg==","shasum":"2880b1e4f334dfb803bf58b1208277a7cd45a7ea","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-3.1.0.tgz","fileCount":8,"unpackedSize":7921,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJa53OaCRA9TVsSAnZWagAAQUgP/isopLQUktHg++tINW/X\nY57J/HSTgjraBgkPSts8/FNJ00NGcPDkkwsgHWUfu+Calr4edzLDwL5g2KpC\nvDyeBczRdM8ue/ueOYR8VozgF9L4SY//rcg9Sf8JaB1/9Cn3XxgJqJUbpi4c\nlMZ/o17HkHrpijIWA/GAFU5sb4gI9+79bzDh9frWDUQmMMH//vwkHmQwcE90\nGi9RJA3RcifINDiPrqpq5e7ytyYrCjDp4dKrV9Tqc9nlrFu8Vgm1vr1ek1cv\n/lVF1MbTdTZdekjktGyJNPm10A/uDzJnvoCulkWn6lnoBS1ovjJMPX42kc1h\nPYclY5M6b4lGVF9339GolKLLUsdfRgBSGSl+10va+Xx1miIxCQ5ViDBnkIe2\nQ+e3ZJkTsttCtl/RA1WVmTAYGHG5sogSKmqIYRXkCInlN4YIfH6PkBiP3nzp\nyGipLafgEgJS5QXu8S983ZLL2KnvemfVmhyUu/o70RWoj4NxHjWJ1VeYxRdm\nBYQis6Sod27ByhZeVnAihPBUS6Mx5L/mMyK+neb1sTBd1lMrlOJcQD/11YPg\nPfDNkwGTl6rCX5B5jzOee/X/QHgg+MweZbsA1KeXcRDP3UIKsFo2Yu/SRJzL\nTa8MnbSvKIL2nvA5pNk2kUcK75+nPyv7tnrNubfLgeQIBRDt1ZpMw+l7xkgn\n8exd\r\n=JrYb\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIQC4gPTOUtHfRfIBCZUKq6yWhJJtfnkCdRxmegOnQ90dnwIgNAAtZ9nHjWz91kautc/+hhOxWHCvyScUXO0gfx8drxU="}]},"maintainers":[{"email":"github@tixz.dk","name":"emilbay"},{"email":"github@tixz.dk","name":"emilbayes"}],"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/secure-random-uniform_3.1.0_1525117848698_0.5357456665230202"},"_hasShrinkwrap":false},"4.0.0":{"name":"secure-random-uniform","version":"4.0.0","description":"Generate secure, random, uniform integers, compensating for modulo bias","main":"index.js","dependencies":{"nanoassert":"^1.1.0","randombytes":"^2.0.3","sodium-native":"^3.1.1"},"scripts":{},"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"author":{"name":"Emil Bay","email":"github@tixz.dk"},"license":"ISC","bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","gitHead":"afba01f312e1539ec11ab4e245d2ffc85fe08c41","_id":"secure-random-uniform@4.0.0","_nodeVersion":"12.16.2","_npmVersion":"6.14.4","dist":{"integrity":"sha512-lG3gfPH/3gIxZCzC/phX2Ig4/ixA+9/bGuFEBHCfztB+d9ldUMYKSd7lDM8MrblHkKnqPD+QNAWben3u9tjLbQ==","shasum":"2a9a19987f14ba7ac97eb9138e0814d21e347a4c","tarball":"https://registry.npmjs.org/secure-random-uniform/-/secure-random-uniform-4.0.0.tgz","fileCount":9,"unpackedSize":8027,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJezou8CRA9TVsSAnZWagAAMy4P+wRruW3G+MhAaY6+oFgG\nqRYl4Ac4iJ3X2IhD8XpCPmwBZD6QpX2563w6eSYkgLxm5Cc/PTVXoGlwF7k1\nQq4YuqmLlbOT230XpJlnmrogHr3l0x7fZbCPj3fGT9NSPSNO8Fl/cCPf1Z2o\nu8Pl/zXCCqKTZmjQg4EA2VuG8Ymk587X+flk1mENjXlzB2aFXpbA9Og6p/CS\nNCJURAaL4TIOurhI4kqWp1LyCQ6QyPE9vxPhMMiLI79wmjO7mVqC9z01+QeN\nJEUZmvh/caLtG4esDe9snCfslqWpDRdjOwv8iefd+iXOoWdDwzaHdqKHg7YA\nCajmkv3oDTVw8PcMrFLMk+KgqTLYk1YqLYJ+5C6vhWgiACrpLJAgnNC3T0O0\nBkcPXnA2D8R4ffjBYKkWuG+va8Zezm/OoAZQMJ2sxL/DNSkF85KyJ07JP9Wj\nnj6wAc5/K0jI5G0iuU9HclBqyykLJVyGPcgF2ayXcWd+nUAs6Qbm6Dbww6pL\nh7TZKBMkVf89F2D38BveKPFOjEojndSw40EiHuvK0OM7kfQEMuFKFRB4dyHB\n/VoazH/iKRZZ1LkxZBe9EfMPOYQ2pZ9ekC3ZdddsnKZWazPgFpPk+JCCQPb7\nsuAaN/CI6ICHmE0pzGwtBw8aEfDwEpwGmB+DS0z3GFpqWqc7BRHmOgSlUbrO\nxQUL\r\n=08XP\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEYCIQDYQySruLcFcZ/5eGu66LGmTK7K7WsXOUFgcFkHLE+zFQIhAIyDcI2Q94XPAaF0wdtBhwkpiGuNF5p0tq1h8y+0xFVE"}]},"maintainers":[{"email":"github@tixz.dk","name":"emilbay"},{"email":"github@tixz.dk","name":"emilbayes"}],"_npmUser":{"name":"emilbayes","email":"github@tixz.dk"},"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/secure-random-uniform_4.0.0_1590594491642_0.4953141506080845"},"_hasShrinkwrap":false}},"readme":"# `secure-random-uniform`\n\n> Generate secure, random, uniform integers, compensating for modulo bias\n\n## Usage\n\n```js\nvar secureRandom = require('secure-random-uniform')\n\n// Numbers from [0, 2000)\nsecureRandom(2000)\n\n// Numbers from [100, 110)\nsecureRandom(10) + 100\n\n// Numbers from [-10, 10]\nsecureRandom(21) - 10\n```\n\n### BigInt support (Experimental!)\n\n```js\nvar secureRandom = require('secure-random-uniform/bigint')\n\n// Numbers from [0, 2^64)\nsecureRandom(2n ** 64n)\n\n// Numbers from [0, googol)\nsecureRandom(10n ** 100n)\n```\n\n## API\n\n#### `var num = secureRandomUniform(limit)`\nReturns a number from the uniform distribution `[0, limit)` (limit exclusive).\nNote that limit must not be larger than `2^53 - 1` (`Number.MAX_SAFE_INTEGER`).\n\n## Background\n\n### Modulo reduction: Bytes to integers\n\nA naive implementation might look like:\n\n```js\nfunction insecureRandom (limit) {\n  return secureRandomSource() % limit\n}\n```\n\nHowever this will only yield a uniform distribution if `limit` is a divisor\nof whatever is the maximum value of `secureRandomSource()`. Consider `limit = 3`\nand the maximum value returned by `secureRandomSource()` being `5`. Then in the\nlong run the frequency of numbers returned will be `[0 = 2/5, 1 = 2/5, 2 = 1/5]`,\ncausing the distribution to be skewed (ie. not uniform).\nThis is called \"Modulo Bias\".\n\nThis module borrows from `arc4random_uniform` and keeps generating a new random\nnumber until it hits a range that's congruent to `limit`. This is not as bad as\nit sounds. The worst case is if `limit ≈ (2^48 - 1) / 2`, in which case it will\nhave a ~ 0.5 chance of doing a redraw. The number of redraws required can be\nmodelled by as `0.5^(redraws)` which quickly converges towards zero. In practise\nonly one draw is required on average.\n\nSee [`verify-modulo-reduction.js`](verify-modulo-reduction.js) for a deterministic test of the algorithm\n\n### Random bytes to integers\n\nThe next issue is transforming random bytes into unsigned numbers. We can\nefficiently transform bytes into signed 32-bit integers in JS with:\n\n```js\n(byte[3] << 24) | (byte[2] << 16) | (byte[1] << 8) | (byte[0])\n```\n\nTo make the number unsigned we can do a zero-fill right shift, which will cause\nthe sign bit to become 0:\n\n```js\n((byte[3] << 24) | (byte[2] << 16) | (byte[1] << 8) | (byte[0])) >>> 0\n```\n\nTo go beyond 32-bit integers, to the maximum of 53-bit integers representable in\nJavascript `Number`s (IEEE 754), we can construct the remaining 21 bits and move\nthem up using a floating point multiplication.\n\n```js\n((((buf[6] & 0b00011111) << 16) | (buf[5] << 8) | (buf[4])) >>> 0) * 0x100000000\n+ (((byte[3] << 24) | (byte[2] << 16) | (byte[1] << 8) | (byte[0])) >>> 0)\n```\n\nNote that the bitwise operations have been wrapped in parenthesis, otherwise\nthe add and multiplication operation will become 32-bit operations,\nreducing the number modulo 2^32\n\nSee [`verify-readle.js`](verify-readle.js) for verification against a known\nimplementation of converting bytes to unsigned integers.\n\n## License\n\n[ISC](LICENSE.md)\n","maintainers":[{"email":"github@tixz.dk","name":"emilbay"},{"email":"github@tixz.dk","name":"emilbayes"}],"time":{"modified":"2022-06-26T17:14:15.324Z","created":"2016-10-13T13:56:16.021Z","1.0.0":"2016-10-13T13:56:16.021Z","1.0.1":"2016-10-13T13:57:28.754Z","2.0.0":"2018-01-03T21:35:26.690Z","3.0.0":"2018-01-04T21:04:27.673Z","3.0.1":"2018-01-05T09:17:07.282Z","3.1.0":"2018-04-30T19:50:48.811Z","4.0.0":"2020-05-27T15:48:11.746Z"},"homepage":"https://github.com/emilbayes/secure-random-uniform#readme","keywords":["secure","random","uniform","arc4random_uniform","crypto","modulo bias","bias"],"repository":{"type":"git","url":"git+https://github.com/emilbayes/secure-random-uniform.git"},"author":{"name":"Emil Bay","email":"github@tixz.dk"},"bugs":{"url":"https://github.com/emilbayes/secure-random-uniform/issues"},"license":"ISC","readmeFilename":"README.md"}