TOTP and HOTP code generator
Work out the RFC 6238 TOTP or RFC 4226 HOTP one-time code for a secret and a time or counter you type, with the otpauth URI.
A clear answer. Here’s how.
HOTP (RFC 4226 section 5.3) computes HMAC(secret, counter) with the counter as 8 big-endian bytes, takes 4 bytes at the offset given by the low 4 bits of the last HMAC byte (dynamic truncation), clears the top bit and keeps the last 6 to 8 decimal digits. TOTP (RFC 6238 section 4) is HOTP with the counter T = floor((Unix time − T0) ÷ step), here with T0 = 0 and a step of 30 seconds unless you change it; SHA-256 and SHA-512 use the same truncation (RFC 6238 section 1.2). The page shows the HMAC, the offset and the truncated number so each step can be checked against the RFC tables, the codes for the previous and next time steps (servers usually accept one step either side), and the seconds left in the step. The otpauth URI follows Google’s Key Uri Format: the secret in unpadded Base32, issuer, algorithm, digits and period or counter; many apps ignore everything but the secret. Web Crypto computes the HMAC on this device; the secret is masked, never saved or sent, and never put in a link. The page does not read the clock, so it cannot tell you the code for “now” unless you type the current Unix time.
How this is checked
5 reference checks passed These 5 cases were run when this page was built, on 20 October 2026, and all reproduce within the stated tolerance. The same cases are part of the automated tests that run on every change to Toolmoz. Engine version 1.
See the checks and where each expected answer comes from
Case 1
- Inputs
- Type hotpShared secret 12345678901234567890Secret is written as asciiHMAC hash SHA-1Digits 6Counter 0
- Expected, and what Toolmoz gave
- Code expected 755224, Toolmoz 755224HMAC (hex) expected cc93cf18508d94934c64b65d8ba7667fb7cde4b0, Toolmoz cc93cf18508d94934c64b65d8ba7667fb7cde4b0Truncated value (decimal) expected 1284755224, Toolmoz 1284755224
- Where the expected answer comes from
- RFC 4226 appendix D, count 0: HMAC cc93cf18508d94934c64b65d8ba7667fb7cde4b0, truncated 4c93cf18 = 1284755224, HOTP 755224
- Allowed difference
- exact
Case 2
- Inputs
- Type hotpShared secret 12345678901234567890Secret is written as asciiHMAC hash SHA-1Digits 6Counter 9
- Expected, and what Toolmoz gave
- Code expected 520489, Toolmoz 520489Truncated value (decimal) expected 645520489, Toolmoz 645520489
- Where the expected answer comes from
- RFC 4226 appendix D, count 9: truncated 2679dc69 = 645520489, HOTP 520489
- Allowed difference
- exact
Case 3
- Inputs
- Type totpShared secret 12345678901234567890Secret is written as asciiHMAC hash SHA-1Digits 8Unix time in seconds 59Time step in seconds 30
- Expected, and what Toolmoz gave
- Code expected 94287082, Toolmoz 94287082Time step T expected 1, Toolmoz 1Seconds left in this step expected 1, Toolmoz 1
- Where the expected answer comes from
- RFC 6238 appendix B: time 59, T = 0000000000000001, SHA1, TOTP 94287082; 59 is 29 s into the step 30 to 60, so 1 s is left
- Allowed difference
- exact
Case 4
- Inputs
- Type totpShared secret 12345678901234567890123456789012Secret is written as asciiHMAC hash SHA-256Digits 8Unix time in seconds 1111111109Time step in seconds 30
- Expected, and what Toolmoz gave
- Code expected 68084774, Toolmoz 68084774Time step T expected 37037036, Toolmoz 37037036
- Where the expected answer comes from
- RFC 6238 appendix B: time 1111111109, T = 00000000023523EC = 37037036, SHA256 with the 32-byte seed of appendix A, TOTP 68084774
- Allowed difference
- exact
Case 5
- Inputs
- Type totpShared secret 1234567890123456789012345678901234567890123456789012345678901234Secret is written as asciiHMAC hash SHA-512Digits 8Unix time in seconds 20000000000Time step in seconds 30
- Expected, and what Toolmoz gave
- Code expected 47863826, Toolmoz 47863826
- Where the expected answer comes from
- RFC 6238 appendix B: time 20000000000, T = 0000000027BC86AA, SHA512 with the 64-byte seed of appendix A, TOTP 47863826
- Allowed difference
- exact
What this shows: the engine reproduces independently worked values for these cases. It does not prove every possible input is right. To test an answer you were given, see how to check a number; to see what is and is not checked across Toolmoz, see the accuracy ledger.