Experiment-3
Experiment-3
Aim:
To implement the RSA (Rivest, Shamir, Adleman) algorithm.
Theory:
RSA remains vital in modern cryptography, particularly for securing sensitive online
transactions, such as financial exchanges and encrypted emails. Despite its computational
intensity and the large key sizes required for strong security, RSA is trusted because of the
difficulty involved in breaking the encryption without the private key. However, as
computing power advances, especially with the rise of quantum computing, RSA's long-term
viability faces challenges, pushing researchers to explore alternatives or enhancements to
its security foundations.
Implementation:
In order to implement the RSA algorithm, three entities – sender, receiver, third party were
taken into consideration. Following are the codes written for the same-
pubPrivKeyPair = {
'pub_key': (0, 0),
'priv_key': (0, 0)
}
def genKeyPair():
p = sympy.randprime(10**15, 10**16)
q = sympy.randprime(10**15, 10**16)
n = p*q
totient = (p - 1)*(q - 1)
e = 65537
while sympy.gcd(e, totient) != 1:
e += 2
d = int(sympy.mod_inverse(e, totient))
return {
'pub_key': (e, n),
'priv_key': (d, n)
}
s = socket.socket()
s.bind(('localhost', 9999))
s.listen(3)
print('\nThird Party is up! @127.0.0.1:9999\n')
while True:
choiceCode = socketsets[counter%2].recv(1024).decode()
if choiceCode == 'GPKOR':
data = {
'pub_key': pubPrivKeyPair['pub_key']
}
sender.send(json.dumps(data).encode())
print('Public key of the receiver was sent to the sender...')
counter += 1
Sender entity
import socket
import json
for i in range(len(plaintext)):
encrypted_text += chr((ord(plaintext[i]) + ord(keyword[i]) - 2*97) % 26 +
97)
return encrypted_text.upper()
c = socket.socket()
c.connect(('localhost', 9999))
print('\nConnected to third party!')
print('\n------------------------Available Options------------------------\n')
print('1. Get public key of the receiver')
print('2. Send the symmetric secret key by RSA')
print('3. Send a message to the receiver')
print('4. Exit')
print('\n-----------------------------------------------------------------\n')
while True:
choice = int(input('Select an option ----> '))
if choice == 1:
c.send('GPKOR'.encode())
pubkey = json.loads(c.recv(1024).decode())
print(f"Public key of receiver: ({pubkey['pub_key'][0]},
{pubkey['pub_key'][1]})\n")
elif choice == 2:
c.send('SSKBR'.encode())
symmkey = input('Enter the secret key to be sent --> ')
integermapping = ''
for char in symmkey:
toreplace = str(ord(char))
integermapping += toreplace
print(f'Integer mapping of the key: {integermapping}')
pubkeye, pubkeyn = input('Provide public key of the receiver -->
').split(' ')
encodedmessage = pow(int(integermapping), int(pubkeye), int(pubkeyn))
print(f'The encoded message: {encodedmessage}')
c.send(str(encodedmessage).encode())
print('The message was sent successfully!\n')
elif choice == 3:
c.send('SSKBR'.encode())
pathofmessage = input('Provide the path of message file --> ')
with open(pathofmessage, 'r') as file:
data = file.read()
symmkey = input('Enter the key to be used for encoding --> ')
encodedmessage = encrypt(data, symmkey)
print(f'The message that will be sent: {encodedmessage}')
c.send(encodedmessage.encode())
print('The message was sent successfully!\n')
elif choice == 4:
print('Disconnecting....\n')
break
c.close()
print('Sender was disconnected....\n')
Receiver entity
import socket
import json
for i in range(len(ciphertext)):
decrypted_text += chr((ord(ciphertext[i]) - ord(keyword[i])) % 26 + 97)
return decrypted_text
c = socket.socket()
c.connect(('localhost', 9999))
print('\nConnected to third party!')
print('\n------------------------Available Options------------------------\n')
print('1. Get public-private key-pair')
print('2. Wait to receive a message from the sender')
print('3. Decode the message received from the sender')
print('4. Exit')
print('\n-----------------------------------------------------------------\n')
while True:
choice = int(input('Select an option ----> '))
if choice == 1:
c.send('GPPKP'.encode())
pubPrivkeys = json.loads(c.recv(1024).decode())
print(f"Public key: ({pubPrivkeys['pub_key'][0]}, {pubPrivkeys['pub_key']
[1]})")
print(f"Private key: ({pubPrivkeys['priv_key'][0]},
{pubPrivkeys['priv_key'][1]})\n")
elif choice == 2:
c.send('SSKBR'.encode())
print("Waiting for sender's message...")
message = c.recv(1024).decode()
if len(message) < 50:
print(f'The encoded secret key: {message}')
privkeyd, privkeyn = input('Provide your private key --> ').split(' ')
decodedmessage = str(pow(int(message), int(privkeyd), int(privkeyn)))
secretkey = ''
for i in range(0, len(decodedmessage), 2):
secretkey += chr(int(decodedmessage[i] + decodedmessage[i+1]))
print(f'The decoded secret key (use this to decode messages):
{secretkey}\n')
else:
print(f'The message received: {message}')
with open('encoded_message.txt', 'w') as file:
file.write(message)
print('The message was saved as encoded_message.txt...\n')
elif choice == 3:
pathofmessage = input('Enter the path of encoded message --> ')
with open(pathofmessage, 'r') as file:
data = file.read()
secretkey = input('Enter the secret key to decode the message --> ')
decodedmessage = decrypt(data, secretkey)
print(f'The decoded message: {decodedmessage}\n')
elif choice == 4:
print('Disconnecting....\n')
break
c.close()
print('Receiver was disconnected....\n')
Results:
Following is a step-by-step execution of the code as was carried out. In summary, RSA was
used to share a secret key among sender and receiver (initiated by the sender) which was
then used for the encryption and decryption of the actual message containing more than
1000 letters (using polyalphabetic cipher technique). Third party was the source of public-
private key pair generation and was responsible for mediation of communication between
the sender and the receiver.
Generating a public-private key-pair for the receiver (public key was stored in third-party
program while the private key was only displayed to the receiver)-
Getting the public key of the receiver (to be used for encryption of the secret key) from the
third-party entity-
Making the receiver listen for any messages from the sender-
Sending the secret key ‘WHOAREU’ (to be used for polyalphabetic encryption of the
message that will be sent in the future) (the secret key was first mapped to an integer which
was then operated on using the public key of the receiver to get the encoded secret key)-
Decoding the received encoded secret key on receiver’s end using the receiver’s private key
that is only known to that specific entity (thereby ensuring no one else can decrypt it other
than the entity for which the message was meant to be)-
Sending the actual message in the encoded form using the previously decided secret key-
The encoded message as received by the receiver (the message was further stored in a text
file for the record)-
Decoding the message that was stored in the file using the previously decided secret key-
Conclusion:
By performing this experiment, I was able to get a clearer picture on the RSA algorithm. I
was able to understand its working and was thus able to comprehend the complexity
associated with decrypting a message encrypted using RSA without knowing the private key.
Having understood the working of RSA, I was able to implement a simple algorithm for
generating public-private key pairs which was later used to share a secret key. The secret
key was further used for the encryption and decryption of the actual message. This scenario
was realized using socket programming. Briefly, this experiment really helped me
understand how RSA can be a powerful approach towards achieving a secure
communication over the internet.