Code Monkey home page Code Monkey logo

python-random-module-cracker's Introduction

randcrack โ€“ Python random module cracker / predictor

Build Status PyPI PyPI - Python Version PyPI - Implementation

This script is able to predict python's random module random generated values.

Script was tested against Python versions from 3.5 to 3.10. Should work against other versions of Python as well, since the generator is pretty much the same in 2.7.12. Enjoy!

Installation

To install randcrack, simply:

$ pip install randcrack

How it works

The generator is based upon Mersenne Twister, which is able to generate numbers with excellent statistical properties(indistinguishable from truly random). However, this generator was not designed to be cryptographycally secure. You should NEVER use in critical applications as a PRNG for your crypto scheme. You can learn more about this generator on Wikipedia.

This cracker works as the following way. It obtains first 624 32 bit numbers from the generator and obtains the most likely state of Mersenne Twister matrix, which is the internal state. From this point generator should be synchronized with the cracker.

How to use

It is important to feed cracker exactly 32-bit integers generated by the generator due to the fact that they will be generated anyway, but dropped if you don't request for them. As well, you must feed the cracker exactly after new seed is presented, or after 624*32 bits are generated since every 624 32-bit numbers generator shifts it's state and cracker is designed to be fed from the begining of some state.

Implemented methods

Cracker has one method for feeding: submit(n). After submitting 624 integers it won't take any more and will be ready for predicting new numbers.

Cracker can predict new numbers with following methods, which work exactly the same as their siblings from the random module but without predict_ prefix. These are: predict_getrandbits, predict_randbelow, predict_randrange, predict_randint, predict_choice and predict_random

Here's an example usage:

import random, time
from randcrack import RandCrack

random.seed(time.time())

rc = RandCrack()

for i in range(624):
	rc.submit(random.getrandbits(32))
	# Could be filled with random.randint(0,4294967294) or random.randrange(0,4294967294)

print("Random result: {}\nCracker result: {}"
	.format(random.randrange(0, 4294967295), rc.predict_randrange(0, 4294967295)))

Output

Random result: 127160928
Cracker result: 127160928

python-random-module-cracker's People

Contributors

mcfx avatar messageup avatar oplik0 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

python-random-module-cracker's Issues

random.random() is not based on /dev/urandom

The README states: Note: Cracker does not implement prediction of random() function since it is based on the os.urandom module which is based on /dev/urandom - however, at least in current versions of CPython, this is not true. You can find the implementation of this function for Python 3.10 here: https://github.com/python/cpython/blob/60adc4b92a8a6fe115a023c8f639a6de4730fac1/Modules/_randommodule.c#L153-L177
It's basically these two lines:

uint32_t a=genrand_uint32(self)>>5, b=genrand_uint32(self)>>6;
return PyFloat_FromDouble((a*67108864.0+b)*(1.0/9007199254740992.0));

with genrand_uint32 being the MT random generator, the same as in getrandbits(). One needs to use SystemRandom to get the randomness from the os directly.

There is a slight loss of information about the state here, as in total 11 bits are zeroed, so I'm not sure if it can be used to crack the generator anyway, but it might be a good idea to correct the README at least, and I'll try to add a prediction generator at least.

Not absolute accuracy

Mersenne Twister is a determenistic algorithm, in particular in CPython's implementation. Something must be wrong in the code. I ask for help in finding the problem in randcrack's code.

Understanding python random cracker

Hello,

I am a student and I dont understand one thing. My project was to research and compare two random number generators. I chose Java's LCG and python's mersenne twister.
Could you explain to me why your (python) RNG prediction loses accuracy over time. I have researched more cracks on Mersenne twister, and they explained that if you have the first 624 integers, you are able to find the seed, as that is where the seed number possibility ends. Is python somehow buffering its seed every step after 624, or what is the issue?

Accuracy in README seems inaccurate.

According to the README.md,

Accuracy

Cracker is not absolutely accurate. It is able to perform close to 100% accurate on first 624 32-bit generations, ~99.5% on the first 1 000, ~95% on the first 10 000 and then figures drop to ~50% accurate to generation 50 000.

but I think this is the value of total (or accumulated) accuracy.

When I plot the accuracy of recent 100 predictions, the plot drops much faster than the total accuracy. And IMHO this is a more appropriate measure when discussing prediction accuracy.

a

Though I do not think what is written in README.md is wrong, I think it is a bit confusive.

Very low accuracy for small interval

import random, time
from randcrack import RandCrack

random.seed(10)

rc = RandCrack()

for i in range(624):
	rc.submit(random.randrange(0,5))
	# Could be filled with random.randint(0,4294967294) or random.randrange(0,4294967294)

for i in range(20):
	print("Random result: {}\nCracker result: {}".format(random.randrange(0,5), rc.predict_randrange(0,5)))


Random result: 4
Cracker result: 2
Random result: 4
Cracker result: 4
Random result: 0
Cracker result: 2
Random result: 3
Cracker result: 0
Random result: 2
Cracker result: 0
Random result: 3
Cracker result: 4
Random result: 1
Cracker result: 0
Random result: 0
Cracker result: 0
Random result: 3
Cracker result: 0
Random result: 3
Cracker result: 0
Random result: 0
Cracker result: 4
Random result: 0
Cracker result: 2
Random result: 3
Cracker result: 0
Random result: 1
Cracker result: 0
Random result: 0
Cracker result: 0
Random result: 3
Cracker result: 0
Random result: 4
Cracker result: 4
Random result: 0
Cracker result: 0
Random result: 0
Cracker result: 4
Random result: 4
Cracker result: 2
Press any key to continue . . .

Only 25% accuracy.

unable to import randcrack

from randcrack import RandCrack

ModuleNotFoundError Traceback (most recent call last)
in
----> 1 from randcrack import randcrack

ModuleNotFoundError: No module named 'randcrack'


from randcrack import RandCrack
this code is not working after installing randcrack using pip on python 3.6. using jupyter notebook.
can you please help me out?

randcrack doesn't work using too many requests

Hello,
I noticed that predictor doesn't work on getrandbits when we request too many requests. You can see that using

#!/bin/env python3

import random, time
from randcrack import RandCrack

random.seed(time.time())

rc = RandCrack()

for i in range(624):
	rc.submit(random.getrandbits(32))
	# Could be filled with random.randint(0,4294967294) or random.randrange(0,4294967294)

for i in range(15000):
    if random.getrandbits(32) != rc.predict_getrandbits(32):
        print("not ok, i = ", i)

I installed using pip3 so I've the last version.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.