Notes on Vernam Cipher

Four basic needs

Read integers (i.e., random key) from file; convert text to ASCII; do Xor on integers; generate random key integers.

Reading from a file of integers

Already done; code found in skeleton.py

to Ascii & xor

Easy-peasy; see run below; NOTE: ^ is the xor operator.

Generate random key

Since we are using 7-bit Ascii, seems best to generate random integers in range 0-127

From: see run below.

Run

> 5^6

3

> ord('5')

53

> ord('A')

65

> ord('a')

97

> random.randint(0,127)

49

> for i in range(25):

print random.randint(0,127)

116

53

10

3

76

115

105

36

26

82

113

54

109

60

119

72

64

40

5

42

120

7

7

111

92

Simple encoding algorithm

Open 3 files:

-plain text – read

-key – write

-cipher text – write

Read plain text as string.

For each character in string

-convert to ascii

-generate random integer

-perform xor of ascii and randint to produce cipher text

-write randint to key file

-write xor-value to cipher text file

abc

Simple decoding algorithm

Open 3 files:

-cipher text – read

-key – read

-recovered plain text – write

Read cipher text and key as integers

For each (cipher text, key) pair

-perform xor to recover ascii value

-convert ascii-number to ascii character (recover plain text characters)

-write recovered plain text to file

abc

The result

Here is the code and the runs.

Note: Code includes some unused imports.

Code

#imports & other python bare necessities

from copy import copy

from copy import deepcopy

import bisect

import random

import pickle

import time

random.seed()

#Note: Probably should close the files after reading

def readFile(filename):

fn=open(filename,'r')

return fn.read()

def readIntFile(filename):

return [int(s) for s in readFile(filename).split()]

def encodeVernam(plainF,keyF,cipherF):

plainChars=readFile(plainF)

keyFn=open(keyF,'w')

ciphFn=open(cipherF,'w')

for ch in plainChars:

keyInt=random.randint(0,127)

keyFn.write(str(keyInt)+' ')

ciphFn.write(str(keyInt^ord(ch))+' ')

keyFn.close()

ciphFn.close()

return 'Done!'

def decodeVernam(keyF,cipherF,recPlainF):

keys=readIntFile(keyF)

ciphs=readIntFile(cipherF)

rcpF=open(recPlainF,'w')

rcpF.write(''.join([chr(keys[i]^ciphs[i]) for i in range(len(keys))]))

rcpF.close()

return 'Done!'

print 'Ready to go'

Runs

> chr(5)

'\x05'

> chr(33)

'!'

> str(5)

'5'

> ======RESTART ======

Ready to go

> str(55)+' '

'55 '

> ======RESTART ======

Ready to go

> encodeVernam('am1.txt','key1.txt','cipher1.txt')

'Done!'

> str(['a','b','c'])

"['a', 'b', 'c']"

> map(+,['a','b','c'])

SyntaxError: invalid syntax

> sL=['a','b','c']

> eS=''

> eS.join(sL)

'abc'

> ''.join(sL)

'abc'

> ======RESTART ======

Ready to go

> decodeVernam('key1.txt','cipher1.txt','recvdPlain.txt')

'Done!'