I am doing a cryptography program in Python.
It consists in reading a random phrase, like HELLO
. Then it assigns it's respective ASCII values like:
H = 72, E = 79.
Then, using Pythagoras' Theorem, it creates two numbers C1
and C2
, like this:
C1 = sqrt(A^2 + (A+B)^2);
C2 = sqrt(B^2 + (A+B)^2)
where, in this case A = H
and B = E
. That would be the encryption part, but I am having problems solving the system, which will act as the decryptor.
How can I solve this system using python?
C1 = sqrt(A^2 + (A+B)^2);
C2 = sqrt(B^2 + (A+B)^2);
Of course only C1
and C2
are known.
Do I need a new module? Which one?
If you're only talking about using the two characters for encryption, that's not a good idea.
That only gives 65,536 possible variants (two ASCII characters was mentioned but I'll assume a full 8-bit octet, so 256 multiplied by 256), it's easy enough to brute-force this. First, we know that every value of A
and B
generates a unique pair C1/C2
, as per the following program which generates no duplicates:
lookup = {}
for a in range(256):
for b in range(256):
c1s = a*a + (a+b)*(a+b)
c2s = b*b + (a+b)*(a+b)
lkey = "%d:%d"%(c1s,c2s)
lookup[lkey] = 1
print(len(lookup)) # gives 65536 (256 squared)
Also, since both A
and B
are integers, so too will be C12
and C22
.
So the first step is to work out the squares of the values you're given (since sqrt
is a potentially expensive operation), taking into account the possibility of floating point inaccuracies:
c1s = int(c1 * c1 + 0.1)
c2s = int(c2 * c2 + 0.1)
Then, simply brute-force the solution:
for a in range(256):
for b in range(256):
if c1s != a*a + (a+b)*(a+b):
continue
if c2s == b*b + (a+b)*(a+b):
print(a,b)
sys.exit(0)
print("No solution")
On my machine, searching for the slowest solution (both a
and b
set to 255), it takes just a smidgeon over six hundredths of a second.
But you should keep in mind that, if an attacker has the C1/C2
values, they too can get the results that fast. And, even if they don't have it, the fact that there are only 64K possibilities means that they can try every possible value in a little over one and a quarter hours. So I wouldn't be using this method to store anything that's valuable for very long :-)