Vad är en slumptalsgenerator?
En slumptalsgenerator (RNG) är ett system som producerar slumptal eller pseudoslumptal. Huruvida nästa tal faktiskt går att förutsäga beror på vilken typ av generator det handlar om. Vissa generatorer utgår från en fysisk process, vissa beräknar tal med en algoritm, och vissa algoritmer är utformade så att inte ens någon som har sett deras tidigare resultat kan förutsäga vad som kommer härnäst. Att se slumpmässigt ut och att vara oförutsägbart är två olika egenskaper, och större delen av den här artikeln handlar om just den skillnaden.
Hårdvarubaserade slumptalsgeneratorer
En hårdvarubaserad slumptalsgenerator (HRNG), även kallad en äkta slumptalsgenerator (TRNG), hämtar sina tal från en fysisk process. De äldsta fungerar framför våra ögon: ett slantsinglande, ett tärningskast eller ett rouletthjul. Mekaniken beskriver var och en av dem fullständigt, men ett välkonstruerat hjul är ändå oförutsägbart i praktiken, eftersom små skillnader i hur varje snurr startar växer till helt olika utfall.
Moderna hårdvarugeneratorer mäter istället mikroskopiska fenomen: hagelbrus och termiskt brus i elektroniska kretsar, atmosfäriskt brus eller kvanteffekter. Dessa är goda källor till entropi — mätbar oförutsägbarhet — men en fysisk källa är inte felfri av naturen: den kan ge ojämn sannolikhet, förändras över tid och sluta fungera, så dess kvalitet måste utvärderas och övervakas, och dess resultat efterbehandlas vid behov, vilket är vad standarder som NIST SP 800-90B beskriver. Hårdvarukällor används där säkerhetsgarantin är som viktigast — framför allt inom kryptografi, där de tillhandahåller det oförutsägbara råmaterialet för nycklarna bakom protokoll som Transport Layer Security (TLS).
Pseudoslumptalsgeneratorer
Alternativet till en fysisk enhet är en algoritm. En pseudoslumptalsgenerator (PRNG) producerar en sekvens som ser slumpmässig ut men som helt bestäms av ett startvärde (seed). Ger du samma startvärde till samma algoritm får du samma sekvens varje gång. Det är en svaghet när ett resultat måste vara oförutsägbart och startvärdet eller det interna tillståndet kan gissas eller rekonstrueras, men en styrka när ett resultat måste kunna upprepas — en simulering eller ett test kan köras om på identiskt sätt. PRNG är också snabba, resurssnåla och enkla att implementera, vilket är anledningen till att de flesta program förlitar sig på dem. Välkända familjer är linjär kongruensgenerator (LCG), xorshift-generatorer och Mersenne Twister.
Mersenne Twister
Mersenne Twister, som publicerades 1997 av Makoto Matsumoto och Takuji Nishimura, är en av de mest använda pseudoslumptalsgeneratorerna och standardvalet i många programmeringsspråk. Dess namn kommer från dess period — sekvensens längd innan den upprepar sig — som i standardvarianten MT19937 är Mersenneprimtalet 219937 − 1. Den klarar de flesta statistiska slumpmässighetstester och lämpar sig väl för simuleringar. Men den konstruerades inte för att bevara hemligheter: från 624 på varandra följande 32-bitars utdatavärden kan vem som helst återskapa dess interna tillstånd och förutsäga varje efterföljande värde, så den får inte användas för nycklar, lösenord eller något annat som måste förbli oförutsägbart.
Kryptografiskt säkra generatorer och entropi
Många tillämpningar behöver båda delarna samtidigt: en algoritms snabbhet och en fysisk källas oförutsägbarhet. Svaret är en kryptografiskt säker pseudoslumptalsgenerator (CSPRNG). Det är fortfarande en PRNG, men byggd så att en inblick i en del av dess resultat inte ger något praktiskt sätt att förutsäga resten, och den initieras och återinitieras regelbundet från en källa med verklig entropi. Ett startvärde från en fysisk källa gör inte en vanlig PRNG säker; algoritmen måste vara konstruerad för ändamålet. En fysisk källa som termiskt brus eller tidsmätning av hårdvaruhändelser levererar en liten mängd äkta slumpmässighet, och CSPRNG tar mycket snabbare fram en lång sekvens värden ur den. Denna kombination är vad ett operativsystem erbjuder programmen som körs på det, och det är vad ”slumptalsgenerator” i praktiken oftast syftar på idag. Den producerar krypteringsnycklar, sessions-tokens och lösenord.
Slumptal i webbläsaren
JavaScript ger en webbsida två inbyggda sätt att hämta slumpmässiga värden, och de tillhör olika klasser. Math.random() är en vanlig PRNG: språkstandarden överlåter algoritmen åt respektive webbläsare och garanterar ingenting om säkerhet — duger för en animation, men olämplig för en dragning som någon kan ifrågasätta. Det andra alternativet är Web Crypto API. Dess metod crypto.getRandomValues() returnerar kryptografiskt starka slumpvärden, framställda av en CSPRNG som förses med operativsystemets entropi.
Vår slumptalsgenerator på nätet använder Web Crypto API för varje dragning, och talen genereras i din webbläsare istället för på en server. Samma källa driver de andra generatorerna på den här webbplatsen, oavsett om du vill slå tärning, kasta mynt eller generera ett lösenord.
Från slumpmässiga bitar till ett tal i ditt intervall
En kryptografiskt säker generator är bara halva förutsättningen för en rättvis dragning. Den levererar råa bitar, och programmet måste fortfarande omvandla dem till ett tal i ditt intervall — och det är här snedvridning kan smyga sig in. Anta att källan ger värdena 0 till 9 med lika stor sannolikhet och du behöver ett tal från 0 till 5. Att ta resten vid division med 6 kan verka naturligt, men talen 0, 1, 2 och 3 kan då uppstå på två sätt medan 4 och 5 bara uppstår på ett sätt, så varje tal från 0 till 3 får 20 % chans och 4 och 5 bara 10 % var. Ett sätt att undvika denna snedvridning (modulo bias) är att förkasta de värden som inte passar och dra på nytt; våra guider om slumptal förklarar detta i detalj.
Ytterligare två saker överraskar ofta. Upprepningar är normalt: när ett heltal från 1 till 10 dras oberoende och varje tal är lika sannolikt, har talet som just drogs samma 1 på 10-chans att komma upp igen som alla andra. En dragning utan upprepningar är en annan typ av dragning, inte en mer slumpmässig sådan. Och en rättvis generator i sig gör inte hela förfarandet rättvist: deltagarlistan och antalet försök spelar lika stor roll, vilket vår artikel om hur man utser en slumpmässig vinnare förklarar.