Error on DES Encryption using Python
this code is to encrypt/decrypt the plain text(Base64)/ciphertext respectively using DES[Data Encryption Standard], giving plain text and Key as input while executing the code. And the coding is done in Python programming language.
mp = {'A': "000000",
'B': "000001",
'C': "000010",
'D': "000011",
'E': "000100",
'F': "000101",
'G': "000110",
'H': "000111",
'I': "001000",
'J': "001001",
'K': "001010",
'L': "001011",
'M': "001100",
'N': "001101",
'O': "001110",
'P': "001111",
'Q': "010000",
'R': "010001",
'S': "010010",
'T': "010011",
'U': "010100",
'V': "010101",
'W': "010110",
'X': "010111",
'Y': "011000",
'Z': "011001",
'a': "011010",
'b': "011011",
'c': "011100",
'd': "011101",
'e': "011110",
'f': "011111",
'g': "100000",
'h': "100001",
'i': "100010",
'j': "100011",
'k': "100100",
'l': "100101",
'm': "100110",
'n': "100111",
'o': "101000",
'p': "101001",
'q': "101010",
'r': "101011",
's': "101100",
't': "101101",
'u': "101110",
'v': "101111",
'w': "110000",
'x': "110001",
'y': "110010",
'z': "110011",
'0': "110100",
'1': "110101",
'2': "110110",
'3': "110111",
'4': "111000",
'5': "111001",
'6': "111010",
'7': "111011",
'8': "111100",
'9': "111101",
'+': "111110",
'/': "111111"}
bin = ""
for i in range(0,len(s)):
bin = bin + mp[s[i]]
return bin
def bintobase64(s):
mp = { "000000": 'A',
"000001": 'B',
"000010": 'C',
"000011": 'D',
"000100": 'E',
"000101": 'F',
"000110": 'G',
"000111": 'H',
"001000": 'I',
"001001": 'J',
"001010": 'K',
"001011": 'L',
"001100": 'M',
"001101": 'N',
"001110": 'O',
"001111": 'P',
"010000": 'Q',
"010001": 'R',
"010010": 'S',
"010011": 'T',
"010100": 'U',
"010101": 'V',
"010110": 'W',
"010111": 'X',
"011000": 'Y',
"011001": 'Z',
"011010": 'a',
"011011": 'b',
"011100": 'c',
"011101": 'd',
"011110": 'e',
"011111": 'f',
"100000": 'g',
"100001": 'h',
"100010": 'i',
"100011": 'j',
"100100": 'k',
"100101": 'l',
"100110": 'm',
"100111": 'n',
"101000": 'o',
"101001": 'p',
"101010": 'q',
"101011": 'r',
"101100": 's',
"101101": 't',
"101110": 'u',
"101111": 'v',
"110000": 'w',
"110001": 'x',
"110010": 'y',
"110011": 'z',
"110100": '0',
"110101": '1',
"110110": '2',
"110111": '3',
"111000": '4',
"111001": '5',
"111010": '6',
"111011": '7',
"111100": '8',
"111101": '9',
"111110": '+',
"111111": '/'}
base64 = ""
for i in range(0, len(s), 6):
ch = ""
ch = ch + s[i]
ch = ch + s[i + 1]
ch = ch + s[i + 2]
ch = ch + s[i + 3]
ch = ch + s[i + 4]
ch = ch + s[i + 5]
base64 = base64 + mp[ch]
return ch
# Binary to decimal conversion
def bin2dec(binary):
binary1 = binary
decimal, i, n = 0, 0, 0
while(binary != 0):
dec = binary % 10
decimal = decimal + dec * pow(2, i)
binary = binary//10
i += 1
return decimal
# Decimal to binary conversion
def dec2bin(num):
res = bin(num).replace("0b", "")
if(len(res)%4 != 0):
div = len(res) / 4
div = int(div)
counter =(4 * (div + 1)) - len(res)
for i in range(0, counter):
res = '0' + res
return res
# Permute function to rearrange the bits
def permute(k, arr, n):
permutation = ""
for i in range(0, n):
permutation = permutation + k[arr[i] - 1]
return permutation
# shifting the bits towards left by nth shifts
def shift_left(k, nth_shifts):
s = ""
for i in range(nth_shifts):
for j in range(1,len(k)):
s = s + k[j]
s = s + k[0]
k = s
s = ""
return k
# calculating xow of two strings of binary number a and b
def xor(a, b):
ans = ""
for i in range(len(a)):
if a[i] == b[i]:
ans = ans + "0"
else:
ans = ans + "1"
return ans
# Table of Position of 64 bits at initial level: Initial Permutation Table
initial_perm = [58, 50, 42, 34, 26, 18, 10, 2,
60, 52, 44, 36, 28, 20, 12, 4,
62, 54, 46, 38, 30, 22, 14, 6,
64, 56, 48, 40, 32, 24, 16, 8,
57, 49, 41, 33, 25, 17, 9, 1,
59, 51, 43, 35, 27, 19, 11, 3,
61, 53, 45, 37, 29, 21, 13, 5,
63, 55, 47, 39, 31, 23, 15, 7]
# Expansion D-box Table
exp_d = [32, 1 , 2 , 3 , 4 , 5 , 4 , 5,
6 , 7 , 8 , 9 , 8 , 9 , 10, 11,
12, 13, 12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21, 20, 21,
22, 23, 24, 25, 24, 25, 26, 27,
28, 29, 28, 29, 30, 31, 32, 1 ]
# Straight Permutation Table
per = [ 16, 7, 20, 21,
29, 12, 28, 17,
1, 15, 23, 26,
5, 18, 31, 10,
2, 8, 24, 14,
32, 27, 3, 9,
19, 13, 30, 6,
22, 11, 4, 25 ]
# S-box Table
sbox = [[[14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7],
[ 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8],
[ 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0],
[15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13 ]],
[[15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10],
[3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5],
[0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15],
[13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9 ]],
[ [10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8],
[13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1],
[13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7],
[1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12 ]],
[ [7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15],
[13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9],
[10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4],
[3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14] ],
[ [2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9],
[14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6],
[4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14],
[11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3 ]],
[ [12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11],
[10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8],
[9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6],
[4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13] ],
[ [4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1],
[13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6],
[1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2],
[6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12] ],
[ [13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7],
[1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2],
[7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8],
[2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11] ] ]
# Final Permutation Table
final_perm = [ 40, 8, 48, 16, 56, 24, 64, 32,
39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30,
37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28,
35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26,
33, 1, 41, 9, 49, 17, 57, 25 ]
def encrypt(pt, rkb, rk):
pt = base64tobin(pt)
# Initial Permutation
pt = permute(pt, initial_perm, 64)
print("After initial permutation", bintobase64(pt))
# Splitting
left = pt[0:32]
right = pt[32:64]
for i in range(0, 16):
# Expansion D-box: Expanding the 32 bits data into 48 bits
right_expanded = permute(right, exp_d, 48)
# XOR RoundKey[i] and right_expanded
xor_x = xor(right_expanded, rkb[i])
# S-boxex: substituting the value from s-box table by calculating row and column
sbox_str = ""
for j in range(0, 8):
row = bin2dec(int(xor_x[j * 6] + xor_x[j * 6 + 5]))
col = bin2dec(int(xor_x[j * 6 + 1] + xor_x[j * 6 + 2] + xor_x[j * 6 + 3] + xor_x[j * 6 + 4]))
val = sbox[j][row][col]
sbox_str = sbox_str + dec2bin(val)
# Straight D-box: After substituting rearranging the bits
sbox_str = permute(sbox_str, per, 32)
# XOR left and sbox_str
result = xor(left, sbox_str)
left = result
# Swapper
if(i != 15):
left, right = right, left
print("Round ", i + 1, " ", bintobase64(left), " ", bintobase64(right), " ", rk[i])
# Combination
combine = left + right
# Final permutation: final rearranging of bits to get cipher text
cipher_text = permute(combine, final_perm, 64)
return cipher_text
pt = input("give me the plain text:")
key = input("give me the key:")
# Key generation
# --hex to binary
key = base64tobin(key)
# --parity bit drop table
keyp = [57, 49, 41, 33, 25, 17, 9,
1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27,
19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15,
7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29,
21, 13, 5, 28, 20, 12, 4 ]
# getting 56 bit key from 64 bit using the parity bits
key = permute(key, keyp, 56)
# Number of bit shifts
shift_table = [1, 1, 2, 2,
2, 2, 2, 2,
1, 2, 2, 2,
2, 2, 2, 1 ]
# Key- Compression Table : Compression of key from 56 bits to 48 bits
key_comp = [14, 17, 11, 24, 1, 5,
3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8,
16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55,
30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53,
46, 42, 50, 36, 29, 32 ]
# Splitting
left = key[0:28] # rkb for RoundKeys in binary
right = key[28:56] # rk for RoundKeys in hexadecimal
rkb = []
rk = []
for i in range(0, 16):
# Shifting the bits by nth shifts by checking from shift table
left = shift_left(left, shift_table[i])
right = shift_left(right, shift_table[i])
# Combination of left and right string
combine_str = left + right
# Compression of key from 56 to 48 bits
round_key = permute(combine_str, key_comp, 48)
rkb.append(round_key)
rk.append(bintobase64(round_key))
print("Encryption")
cipher_text = bintobase64(encrypt(pt, rkb, rk))
print("Cipher Text : ",cipher_text)
print("Decryption")
rkb_rev = rkb[::-1]
rk_rev = rk[::-1]
text = bintobase64(encrypt(cipher_text, rkb_rev, rk_rev))
print("Plain Text : ",text)
I have converted the hextobin code to base64tobin code I am getting errors, please help me with my encryption/decryption.
I found the hextobin code in geeks for geeks and I have tried to convert it to base64tobin code, It is hard for me to find my errors.
Your code is a bit confusing.
the mp
dictionary has wrong binary values.
For example a = '01100001' # or '0b1100001'
and not 011010
. I don't know if you have a purpose by using this specific dictionary, but if it's not necessary, I would recommend to use the standard system python uses.
Firstly let's make your code simpler...
I guess the first mp
dictionary is in a function that converts string to binary:
def Str2Bin(c):
return '{0:08b}'.format(int(c.encode().hex(),16))
here is the way to convert a character to binary correctly. If you insist to make a dictionary (I don't think it's necessary), you can add this line in the code:
from string import printable
str2bin_dict = {Str2Bin(i):i for i in printable}
Next, I think your bintobase64
function is false.
When I try this bintobase64("111111")
I get as response this '111111'
.
The correct way is this one:
import base64
def Bin2Base64(b):
return base64.b64encode(chr(int(b,2)).encode())
and if you insist to create the mp
dictionary, you can do this:
mp = = {Bin2Base64(i):i for i in str2bin_dict.keys()}
But here is a confusion. Base64 is not like binary.
'a' -> 'YQ=='
'b' -> 'Yg=='
'ab' -> 'YWI='
I guess that you have created mp
to convert every letter to it's base64 format. You can do it, but why?
Just convert the whole text to base64 and vice versa:
import base64
base64.b64encode('Hello World'.encode()).decode() # 'SGVsbG8gV29ybGQ='
base64.b64decode('SGVsbG8gV29ybGQ='.encode()).decode() # Hello World
These are my hints. I think they are more than enough to figure out what's going on ;)