ఆధునిక వెబ్ భద్రతలోని ప్రాథమిక క్రిప్టోగ్రాఫిక్ ప్రోటోకాల్లలో, RFC 6238 (TOTP: సమయ-ఆధారిత వన్-టైమ్ పాస్వర్డ్ అల్గారిథమ్) దాని గణిత సరళతకు ప్రత్యేకంగా నిలుస్తుంది. దీనికి ఇంటరాక్టివ్ నెట్వర్క్ హ్యాండ్షేక్లు అవసరం లేదు, కేంద్రీకృత పబ్లిక్ కీ ఇన్ఫ్రాస్ట్రక్చర్ (PKI) అవసరం లేదు మరియు క్లౌడ్ రౌండ్-ట్రిప్లు అవసరం లేదు. కేవలం భాగస్వామ్య Base32 రహస్య కీ మరియు భౌతిక Unix సమయం యొక్క నిరంతర ముందడుగుతో, క్లయింట్ మరియు సర్వర్ 100% గణిత ఖచ్చితత్వంతో ప్రతి 30 సెకన్లకు ఒకేలా ఉండే, తాత్కాలిక 6-అంకెల ప్రమాణీకరణ టోకెన్లను గణిస్తాయి.
ఈ సమగ్ర మార్గదర్శినిలో, మేము బ్లాక్-బాక్స్ థర్డ్-పార్టీ లైబ్రరీలను (pyotp లేదా otplib వంటివి) దాటవేసి, Python, JavaScript మరియు Go లో పూర్తి RFC 6238 క్రిప్టోగ్రాఫిక్ పైప్లైన్ను మొదటి నుండి నిర్మిస్తాము మరియు అధికారిక IETF టెస్ట్ వెక్టర్లకు వ్యతిరేకంగా ప్రతి అమలును ధృవీకరిస్తాము.
01. సమయ-ఆధారిత ప్రమాణీకరణ యొక్క విశిష్టత
TOTP ని అర్థం చేసుకోవడానికి, మనం ముందుగా దాని పూర్వగామిని పరిశీలించాలి: RFC 4226 HOTP (HMAC-ఆధారిత వన్-టైమ్ పాస్వర్డ్).
HOTP లో, క్లయింట్ మరియు సర్వర్ ఒక ఈవెంట్ కౌంటర్ $C$ ని పంచుకుంటాయి. వినియోగదారు టోకెన్ను రూపొందించిన ప్రతిసారీ, కౌంటర్ పెరుగుతుంది ($C = C + 1$), మరియు టోకెన్ $\text{HMAC-SHA-1}(K, C)$ నుండి తీసుకోబడుతుంది. గణితశాస్త్రపరంగా పటిష్టంగా ఉన్నప్పటికీ, HOTP ఒక కార్యాచరణ బలహీనతను ఎదుర్కొంది: కౌంటర్ అసమతుల్యత (desynchronization). ఒక వినియోగదారు అనుకోకుండా తమ జేబులో ఉన్న హార్డ్వేర్ డాంగిల్పై బటన్ను ఐదుసార్లు నొక్కితే, క్లయింట్ కౌంటర్ $C=6$ కి చేరుకుంటుంది, అయితే ప్రమాణీకరణ సర్వర్ $C=1$ వద్దే ఉంటుంది, దీని ఫలితంగా నిరంతర లాగిన్ తిరస్కరణలు ఏర్పడతాయి.
మే 2011లో N. M'Raihi, S. Machani, M. Pei మరియు J. Rydell ద్వారా ప్రచురించబడిన RFC 6238, పెరుగుతున్న పూర్ణాంకాన్ని ప్రామాణిక Unix epoch సమయంతో భర్తీ చేయడం ద్వారా కౌంటర్ అసమతుల్యత సమస్యను పరిష్కరించింది. భౌతిక సమయం ప్రపంచవ్యాప్తంగా ఒకే విధంగా ముందుకు సాగుతుంది కాబట్టి, క్లయింట్ మరియు సర్వర్ రెండూ ఒకే ఒక్క నెట్వర్క్ ప్యాకెట్ను పంపకుండానే తమ అంతర్గత కౌంటర్లను ఏకకాలంలో ముందుకు తీసుకెళ్తాయి.
02. TOTP యొక్క 5 క్రిప్టోగ్రాఫిక్ గణిత దశలు
16-అక్షరాల Base32 సీడ్ను (ఉదా., JBSWY3DPEHPK3PXP) 6-అంకెల రోలింగ్ కోడ్గా (ఉదా., 284915) మార్చడంలో ఐదు ఖచ్చితమైన క్రిప్టోగ్రాఫిక్ దశలు ఉంటాయి:
ఎక్స్ఛేంజ్ నమోదు కీలు A-Z మరియు 2-7 అక్షరమాలను (0, 1, 8, 9 వంటి సందిగ్ధ అక్షరాలను వదిలివేసి) ఉపయోగించి RFC 4648 Base32 లో ఎన్కోడ్ చేయబడతాయి. అల్గారిథమ్ మొదట ఈ స్ట్రింగ్ను సాధారణీకరిస్తుంది, ఖాళీలను తొలగిస్తుంది మరియు ప్యాడింగ్ (=) వర్తింపజేస్తుంది, తద్వారా దాని పొడవు 8 యొక్క గుణిజంగా మారుతుంది, ఆపై దానిని ముడి బైనరీ కీ బైట్లు $K$ గా డీకోడ్ చేస్తుంది.
ప్రస్తుత Unix టైమ్స్టాంప్ (జనవరి 1, 1970 UTC నుండి గడిచిన సెకన్లు) పూర్ణాంక కౌంటర్ $T$ కి మ్యాప్ చేయబడుతుంది:
ప్రామాణిక పారామితులు $T_0 = 0$ మరియు స్టెప్ వ్యవధి $X = 30$ సెకన్లతో ఉంటుంది. ఈ పూర్ణాంకం $T$ ఆపై 8-బైట్ బిగ్-ఎండియన్ 64-బిట్ అన్సైన్డ్ పూర్ణాంకంగా ఎన్కోడ్ చేయబడుతుంది.
ముడి కీ బైట్లు $K$ ను రహస్య కీగా ఉపయోగించి, మేము 8-బైట్ బిగ్-ఎండియన్ టైమ్ బఫర్పై HMAC-SHA1 డైజెస్ట్ను గణిస్తాము, ఇది 20-బైట్ (160-బిట్) సందేశ ప్రమాణీకరణ హ్యాష్ $HS$ ను అందిస్తుంది:
20 ముడి బైట్లను పూర్ణాంకంగా మార్చడానికి, RFC 4226 డైనమిక్ ట్రంకేషన్ను నిర్దేశిస్తుంది:
- ఆఫ్సెట్ను వెలికితీయండి: చివరి బైట్ $HS[19]$ ను పరిశీలించి, దాని దిగువ 4 బిట్లను వెలికితీయడానికి
0x0Fతో మాస్క్ చేయండి, ఇది 0 మరియు 15 మధ్య ఆఫ్సెట్ విలువను ఇస్తుంది:Offset = HS[19] & 0x0F; - 4 బైట్లను విభజించండి: ఆఫ్సెట్ వద్ద ప్రారంభమయ్యే 4 వరుస బైట్లను వెలికితీయండి: $P = HS[Offset \dots Offset+3]$;
- సైన్ బిట్ను మాస్క్ చేయండి: సైన్డ్ పూర్ణాంక ఓవర్ఫ్లో సందిగ్ధతను నివారించడానికి అత్యంత ముఖ్యమైన బిట్ (MSB) ను
0x7Fతో మాస్క్ చేయండి:
BinaryCode = ((P[0] & 0x7F) << 24) | ((P[1] & 0xFF) << 16) | ((P[2] & 0xFF) << 8) | (P[3] & 0xFF)
చివరగా, ప్రామాణిక 6-అంకెల టోకెన్ల కోసం BinaryCode మాడ్యులో $10^6$ (1,000,000) తగ్గించండి. స్థిరమైన 6-అక్షరాల అవుట్పుట్ స్ట్రింగ్ను నిర్ధారించడానికి ఫలితానికి ఎడమవైపు సున్నాలను జోడించండి (left-pad):
03. రన్ చేయగల కోడ్ 1: Python 3 ప్రామాణిక లైబ్రరీ
ఈ పూర్తి అమలు ఎటువంటి pip ప్యాకేజీలు అవసరం లేకుండా Python యొక్క అంతర్నిర్మిత base64, struct, hmac మరియు hashlib మాడ్యూల్లను ఉపయోగిస్తుంది:
import base64 import hashlib import hmac import struct import timedef generate_totp(secret_base32: str, timestamp: int = None, step: int = 30, digits: int = 6) -> str: """ Generate an RFC 6238 compliant TOTP token. :param secret_base32: Shared secret key in Base32 format (e.g., ‘JBSWY3DPEHPK3PXP’) :param timestamp: Unix epoch timestamp in seconds. Defaults to time.time() :param step: Time-step window in seconds (default: 30) :param digits: Number of output digits (default: 6) :return: Left-padded OTP string (e.g., ‘045812’) """ if timestamp is None: timestamp = int(time.time())
1. Normalize Base32 string and append ’=’ padding characters
normalized_secret = secret_base32.replace(” ”, "").upper() padding_needed = (8 - len(normalized_secret) % 8) % 8 normalized_secret += ”=” * padding_needed key_bytes = base64.b32decode(normalized_secret)
2. Compute 64-bit big-endian time-step counter T
time_counter = timestamp // step time_bytes = struct.pack(“>Q”, time_counter) # 8 bytes big-endian unsigned long long
3. Calculate HMAC-SHA1 digest (20 bytes)
hmac_digest = hmac.new(key_bytes, time_bytes, hashlib.sha1).digest()
4. Perform Dynamic Truncation
offset = hmac_digest[-1] & 0x0F # Lower 4 bits of the 20th byte
Unpack 4 bytes at offset and clear MSB sign bit
binary_code = struct.unpack(“>I”, hmac_digest[offset : offset + 4])[0] & 0x7FFFFFFF
5. Modulo arithmetic and zero-fill formatting
otp_code = binary_code % (10 ** digits) return str(otp_code).zfill(digits)
if name == “main”: test_secret = “JBSWY3DPEHPK3PXP” print(f”Generated TOTP Code: {generate_totp(test_secret)}”)
04. రన్ చేయగల కోడ్ 2: JavaScript & Node.js Crypto
స్థానిక crypto.createHmac ఉపయోగించి బ్యాకెండ్ Node.js రన్టైమ్ల కోసం స్వచ్ఛమైన JavaScript అమలు:
const crypto = require('crypto');// RFC 4648 Base32 Decoder in Pure JavaScript function base32Decode(base32Str) { const alphabet = ‘ABCDEFGHIJKLMNOPQRSTUVWXYZ234567’; const cleaned = base32Str.replace(/=+$/, ”).toUpperCase().replace(/\s+/g, ”); let bits = 0, value = 0, index = 0; const output = new Uint8Array(Math.floor((cleaned.length * 5) / 8));
for (let i = 0; i < cleaned.length; i++) { const val = alphabet.indexOf(cleaned[i]); if (val === -1) continue; value = (value << 5) | val; bits += 5; if (bits >= 8) { output[index++] = (value >>> (bits - 8)) & 255; bits -= 8; } } return Buffer.from(output.buffer, 0, index); }
function generateTOTP(secretBase32, timestamp = Math.floor(Date.now() / 1000), step = 30, digits = 6) { const key = base32Decode(secretBase32); const counter = Math.floor(timestamp / step);
// Allocate 8-byte buffer in Big-Endian format const buffer = Buffer.alloc(8); buffer.writeBigUInt64BE(BigInt(counter), 0);
// Compute HMAC-SHA1 const hmac = crypto.createHmac(‘sha1’, key).update(buffer).digest();
// Dynamic Truncation const offset = hmac[hmac.length - 1] & 0x0f; const binary = ((hmac[offset] & 0x7f) << 24) | ((hmac[offset + 1] & 0xff) << 16) | ((hmac[offset + 2] & 0xff) << 8) | (hmac[offset + 3] & 0xff);
const otp = binary % (10 ** digits); return otp.toString().padStart(digits, ‘0’); }
console.log(“Calculated TOTP:”, generateTOTP(“JBSWY3DPEHPK3PXP”));
W3C Web Crypto API ద్వారా క్లయింట్-సైడ్ బ్రౌజర్ ఎగ్జిక్యూషన్:
100% ఆఫ్లైన్ భద్రతను కోరుకునే ఆధునిక వెబ్ అప్లికేషన్ల కోసం (2FA-Tool కు శక్తినిచ్చే ఖచ్చితమైన ఆర్కిటెక్చర్), W3C Web Crypto API థర్డ్-పార్టీ npm బండిల్స్ లేకుండా నేరుగా బ్రౌజర్ శాండ్బాక్స్లో అసమకాలిక, హార్డ్వేర్-యాక్సిలరేటెడ్ క్రిప్టోగ్రాఫిక్ ప్రిమిటివ్లను అందిస్తుంది:
async function generateBrowserTOTP(secretBase32, timestamp = Math.floor(Date.now() / 1000)) { const keyBytes = base32Decode(secretBase32); const counter = Math.floor(timestamp / 30);// 1. Import raw secret key into SubtleCrypto const cryptoKey = await window.crypto.subtle.importKey( “raw”, keyBytes, { name: “HMAC”, hash: { name: “SHA-1” } }, false, [“sign”] );
// 2. Encode 8-byte Big-Endian counter buffer const buffer = new ArrayBuffer(8); const view = new DataView(buffer); view.setBigUint64(0, BigInt(counter), false); // false = Big-Endian
// 3. Perform cryptographic HMAC sign const signature = await window.crypto.subtle.sign(“HMAC”, cryptoKey, buffer); const hmacResult = new Uint8Array(signature);
// 4. Dynamic Truncation const offset = hmacResult[hmacResult.length - 1] & 0x0f; const binary = ((hmacResult[offset] & 0x7f) << 24) | ((hmacResult[offset + 1] & 0xff) << 16) | ((hmacResult[offset + 2] & 0xff) << 8) | (hmacResult[offset + 3] & 0xff);
const otp = binary % 1000000; return otp.toString().padStart(6, ‘0’); }
05. రన్ చేయగల కోడ్ 3: ప్రొడక్షన్ Golang (Go)
అధిక-త్రూపుట్ మైక్రోసర్వీసెస్ Go యొక్క పటిష్టమైన ప్రామాణిక లైబ్రరీ నుండి ప్రయోజనం పొందుతాయి:
package mainimport ( “crypto/hmac” “crypto/sha1” “encoding/base32” “encoding/binary” “fmt” “math” “strings” “time” )
// GenerateTOTP computes standard RFC 6238 time-based tokens func GenerateTOTP(secretBase32 string, timestamp int64, step int64, digits int) (string, error) { // 1. Sanitize Base32 seed and decode cleaned := strings.ToUpper(strings.ReplaceAll(secretBase32, ” ”, "")) key, err := base32.StdEncoding.WithPadding(base32.NoPadding).DecodeString(cleaned) if err != nil { key, err = base32.StdEncoding.DecodeString(cleaned) if err != nil { return "", err } }
// 2. Encode 64-bit Big-Endian time-step counter counter := uint64(timestamp / step) buf := make([]byte, 8) binary.BigEndian.PutUint64(buf, counter)
// 3. Compute HMAC-SHA1 mac := hmac.New(sha1.New, key) mac.Write(buf) hash := mac.Sum(nil)
// 4. Dynamic Truncation offset := hash[len(hash)-1] & 0x0f binaryCode := binary.BigEndian.Uint32(hash[offset:offset+4]) & 0x7fffffff
// 5. Modulo arithmetic mod := uint32(math.Pow10(digits)) otp := binaryCode % mod
format := fmt.Sprintf(“%%0%dd”, digits) return fmt.Sprintf(format, otp), nil }
func main() { code, err := GenerateTOTP(“JBSWY3DPEHPK3PXP”, time.Now().Unix(), 30, 6) if err != nil { panic(err) } fmt.Printf(“Golang Computed TOTP: %s\n”, code) }
06. RFC 6238 అనుబంధం B టెస్ట్ వెక్టర్స్ ధృవీకరణ
ప్రమాణ సమ్మతిని నిరూపించడానికి, ప్రతి క్రిప్టోగ్రాఫిక్ అమలు IETF RFC 6238 అనుబంధం B లో ప్రచురించబడిన అధికారిక టెస్ట్ వెక్టర్లకు వ్యతిరేకంగా ధృవీకరించబడాలి.
అధికారిక టెస్ట్ సూట్ ASCII రహస్యం "12345678901234567890" (20 బైట్లు) ను ఉపయోగిస్తుంది, ఇది Base32 లో ఈ విధంగా ఎన్కోడ్ చేయబడుతుంది:
GEZDGNBVGY3TQOJQGEZDGNBVGY3TQOJQ (30-సెకన్ల స్టెప్లతో 8-అంకెల అవుట్పుట్ల కోసం మూల్యాంకనం చేయబడింది):
| Unix Epoch టైమ్స్టాంప్ | UTC తేదీ & సమయం | RFC అధికారిక ఆశించిన కోడ్ | అమలు ఫలితం |
|---|---|---|---|
| 59 | 1970-01-01 00:00:59 | 94287082 | ✓ ఉత్తీర్ణత (ఖచ్చితమైన సరిపోలిక) |
| 1111111109 | 2005-03-18 01:58:29 | 07081804 | ✓ ఉత్తీర్ణత (ఖచ్చితమైన సరిపోలిక) |
| 1111111111 | 2005-03-18 01:58:31 | 14050471 | ✓ ఉత్తీర్ణత (ఖచ్చితమైన సరిపోలిక) |
| 1234567890 | 2009-02-13 23:31:30 | 89005924 | ✓ ఉత్తీర్ణత (ఖచ్చితమైన సరిపోలిక) |
| 2000000000 | 2033-05-18 03:33:20 | 69279037 | ✓ ఉత్తీర్ణత (ఖచ్చితమైన సరిపోలిక) |
07. ప్రొడక్షన్ ఇంజనీరింగ్: టైమ్ స్క్యూ, రీప్లే & రేట్ పరిమితులు
అధిక-లభ్యత గల ఎంటర్ప్రైజ్ ప్రమాణీకరణ సిస్టమ్లలో TOTP ధృవీకరణను అమలు చేస్తున్నప్పుడు, మూడు భద్రతా అవసరాలను తప్పనిసరిగా అమలు చేయాలి:
మొబైల్ గడియారంలో ఉండే చిన్నపాటి తేడాల కారణంగా, సర్వర్లు [T - 1, T, T + 1] విండోను మూల్యాంకనం చేయాలి (మునుపటి 30 సెకన్లు, ప్రస్తుత 30 సెకన్లు మరియు తదుపరి 30 సెకన్లను తనిఖీ చేయడం). విండోను ఎప్పుడూ $\pm 1$ స్టెప్కు మించి విస్తరించవద్దు, ఎందుకంటే ప్రతి అదనపు స్టెప్ రీప్లే అటాక్ ఉపరితలాన్ని 30 సెకన్ల పాటు పెంచుతుంది.
విజయవంతంగా ఉపయోగించిన వెంటనే టోకెన్ తప్పనిసరిగా చెల్లనిదిగా మార్చబడాలి. Redis లేదా ఇన్-మెమరీ క్యాష్లో Last_Verified_Time_Step ను నిల్వ చేయండి. ఒక క్లయింట్ అదే 30-సెకన్ల విండోలో అదే టోకెన్ను సమర్పించడానికి ప్రయత్నిస్తే, మ్యాన్-ఇన్-ది-మిడిల్ రీప్లే దాడులను నిలువరించడానికి అభ్యర్థనను తిరస్కరించండి.
6-అంకెల కోడ్లు కేవలం 1,000,000 కలయికలను మాత్రమే కలిగి ఉంటాయి కాబట్టి, నియంత్రణ లేని ఎండ్పాయింట్లను వేగంగా బ్రూట్-ఫోర్స్ చేయవచ్చు. 3 వరుస వైఫల్యాల తర్వాత క్రమంగా ఆలస్యాలను మరియు ఖాతా లాకౌట్లను అమలు చేయండి. కోడ్లో, సైడ్-ఛానల్ టైమింగ్ విశ్లేషణను అడ్డుకోవడానికి కాన్స్టంట్-టైమ్ సమానత్వ ఫంక్షన్లను (ఉదా., Go లో crypto/subtle.ConstantTimeCompare లేదా Node.js లో crypto.timingSafeEqual) ఉపయోగించి పోలికలను నిర్వహించండి.
08. తరచుగా అడిగే ప్రశ్నలు (FAQ)
Q1: SHA-1 క్రిప్టోగ్రాఫిక్గా విచ్ఛిన్నమైనందున, TOTP ఇప్పటికీ డిఫాల్ట్గా HMAC-SHA1 ను ఎందుకు ఉపయోగిస్తుంది? ▼
ముడి SHA-1 పై జరిగే సైద్ధాంతిక కొలిజన్ దాడులు HMAC నిర్మాణాన్ని (RFC 2104) విచ్ఛిన్నం చేయవు. HMAC లో, అంతర్లీన హ్యాష్ ఫంక్షన్ అంతర్గత మరియు బాహ్య రహస్య కీలలో పొందుపరచబడి ఉంటుంది, ఇది కొలిజన్-ఆధారిత దాడులను నిర్వీర్యం చేస్తుంది. నేటి వరకు, 2FA కోసం HMAC-SHA1 సురక్షితంగా ఉంది. అంతేకాకుండా, అధిక భరోసా అవసరమైతే RFC 6238 పూర్తిగా HMAC-SHA256 మరియు HMAC-SHA512 లకు మద్దతు ఇస్తుంది.
Q2: టైమ్ జోన్లు లేదా డేలైట్ సేవింగ్ టైమ్ (DST) TOTP సమకాలీకరణను ప్రభావితం చేస్తాయా? ▼
లేదు. Unix epoch సమయం 1970-01-01 00:00:00 UTC నుండి గడిచిన సెకన్లుగా నిర్వచించబడింది. ఇది టైమ్ జోన్లు, లీప్ సెకన్లు మరియు డేలైట్ సేవింగ్ మార్పులతో సంబంధం లేకుండా ఉంటుంది. ఏదైనా ఖచ్చితమైన సమయంలో, టోక్యోలోని సర్వర్ మరియు కాలిఫోర్నియాలోని స్మార్ట్ఫోన్ ఒకే పూర్ణాంక టైమ్స్టాంప్ను కలిగి ఉంటాయి.
Q3: Steam Guard 5-అక్షరాల ప్రమాణీకరణ RFC 6238 నుండి ఎలా భిన్నంగా ఉంటుంది? ▼
Steam Guard అనేది RFC 6238 ఆధారంగా రూపొందించబడిన ఒక యాజమాన్య వేరియంట్. ఇది ఖచ్చితంగా అదే 30-సెకన్ల టైమ్-స్టెప్ మరియు HMAC-SHA1 గణనను ఉపయోగిస్తుంది, కానీ చివరి తగ్గింపు దశలో, ఇది 5-అక్షరాల స్ట్రింగ్ను ఉత్పత్తి చేయడానికి వెలికితీసిన పూర్ణాంకాన్ని కస్టమ్ 26-అక్షరాల ఆల్ఫాన్యూమరిక్ అక్షర శ్రేణి (23456789BCDFGHJKMNPQRTVWXY) ద్వారా మ్యాప్ చేస్తుంది.
100% క్లయింట్-సైడ్ TOTP కోడ్ జనరేషన్ను ప్రత్యక్షంగా అనుభవించండి
2FA-Tool W3C Web Crypto API ని ఉపయోగించి నేరుగా మీ బ్రౌజర్లో ఈ ఖచ్చితమైన క్రిప్టోగ్రాఫిక్ పైప్లైన్ను అమలు చేస్తుంది. సున్నా సర్వర్ ప్రసారాలు, సున్నా టోకెన్ నిల్వ, తక్షణ ధృవీకరణ.