Dev.to Security 🔐 Cybersecurity 👁 0 📖 2 min read

Why crypto.getRandomValues is not the whole password generator

Web Crypto gives a browser password generator secure random bytes. It does not decide how those bytes become characters or whether the result meets an account's rules. Those two steps can introduce bias even when the ran

Web Crypto gives a browser password generator secure random bytes. It does not decide how those bytes become characters or whether the result meets an account's rules. Those two steps can introduce bias even when the random source is right.

Consider an alphabet containing 62 characters: lowercase letters, uppercase letters and digits. A random byte has 256 possible values, from 0 through 255. Applying byte % 62 directly gives the first eight characters five possible byte values each. The other 54 get only four.

Reject bytes of 248 or higher before applying % 62. The remaining 248 values divide evenly into 62 groups of four. Every character now has the same probability. For a different alphabet size, calculate the largest multiple of that size below or equal to 256 and reject byte values at or above that threshold.

Character requirements are a separate issue. Allowing symbols in the alphabet does not guarantee that a generated password contains a symbol. The same applies to uppercase letters or digits.

Putting one required character from each group into fixed positions solves the form requirement but makes those positions predictable. Another approach is to generate the entire candidate, check whether every required group appears, and reject the candidate if one is missing. If candidates were sampled uniformly, the accepted result is uniform over the passwords that meet those requirements.

That loop still needs a stopping condition. Our implementation allows 128 candidate attempts, then shows an error. The cap bounds the work; it does not guarantee success. Failure must not trigger a fallback to Math.random or silently return a password that violates the requested settings.

The interface matters too. Changing a setting should clear the old output so users do not copy a password generated under different rules. Hidden output reduces casual exposure, but copying it can leave it in clipboard history. Clearing the page does not clear that history.

A trusted password manager's generator is my first recommendation. Use a distinct password for each account, check the destination's length and character rules, and enable MFA where available. A generator's supported minimum length is not a recommendation to choose that minimum.

I work on Firm Beacon. We used this approach in our browser password generator, which defaults to 20 characters and supports lengths from 8 to 128. It generates locally and does not upload or save the password. The page has analytics, but password values are not included in its telemetry:

https://www.firmbeacon.co.uk/tools/password-generator?utm_source=devto&utm_medium=article&utm_campaign=web_crypto_password_rules

MDN documents getRandomValues and its limits here:

https://developer.mozilla.org/en-US/docs/Web/API/Crypto/getRandomValues

📰 Read the original article on Dev.to Security

Originally published by Dev.to Security. Aggregated on AIWithGhost for educational purposes — full credit and traffic to the original publisher.