This repository contains the completed implementation for Assignment #2. This project is a console-based, PKI-enabled Secure Chat System in Python, demonstrating how cryptographic primitives combine to achieve Confidentiality, Integrity, Authenticity, and Non-Repudiation (CIANR).
Author: Umar Javed Roll No: 22i-1050
This project implements a secure, multi-client chat server from scratch, without using any high-level TLS/SSL abstractions. The application-layer protocol was built to satisfy all requirements from the assignment specification.
The final implementation includes:
- PKI & Mutual Authentication: A functional Root CA (
scripts/gen_ca.py) and certificate generation script (scripts/gen_cert.py). The server and client use these certificates to verify each other's identity. - Secure Registration & Login: User credentials are secured in transit using a temporary Diffie-Hellman key exchange and AES encryption. Passwords are stored in a MariaDB (MySQL) database using a unique 16-byte salt and a SHA-256 hash.
- Secure Chat Session: After login, a second Diffie-Hellman exchange creates a main session key for the chat.
- CIANR-Enabled Chat: All chat messages are encrypted (Confidentiality), signed with the sender's private RSA key (Authenticity, Integrity), and protected from replay attacks (Integrity).
- Non-Repudiation: Both client and server generate append-only transcripts and a final, signed
SessionReceiptto create a verifiable record of the chat.
securechat-skeleton/
├─ app/
│ ├─ client.py # Client workflow
│ ├─ server.py # Server workflow
│ ├─ crypto/
│ │ ├─ aes.py # AES-128-CBC + PKCS#7
│ │ ├─ dh.py # Classic DH helpers + key derivation
│ │ ├─ pki.py # X.509 validation (CA signature, validity, CN)
│ │ └─ sign.py # RSA SHA-256 sign/verify (PKCS#1 v1.5)
│ ├─ common/
│ │ └─ utils.py # Networking (send/receive) helpers
│ └─ storage/
│ ├─ db.py # MySQL user store (salted SHA-256)
│ └─ transcript.py # Append-only transcript + transcript hash
├─ scripts/
│ ├─ gen_ca.py # Create Root CA
│ └─ gen_cert.py # Issue client/server certs
├─ tests/
│ ├─ mitm_proxy.py # Proxy for Tamper & Replay attacks
│ └─ verify_transcript.py # Offline transcript/receipt verifier
├─ tests/manual/NOTES.md # Original manual testing checklist
├─ certs/ # Generated certs/keys (gitignored)
├─ transcripts/ # Generated logs/receipts (gitignored)
├─ .env.example
├─ .gitignore
├─ requirements.txt
└─ schema_dump.sql # SQL dump for GCR submission
This project was built and tested on Kali Linux with a local MariaDB server.
-
Fork and Clone: Clone your private repository.
-
Set up Python Environment:
python3 -m venv .venv && source .venv/bin/activate pip install -r requirements.txt
-
Start MariaDB (MySQL):
sudo systemctl start mariadb
-
Configure Database:
- Log in as root:
sudo mysql -u root -p - Create the user and database (use the password set in
app/storage/db.py):CREATE DATABASE secure_chat; CREATE USER 'chat_app_user'@'localhost' IDENTIFIED BY '123Password'; GRANT ALL PRIVILEGES ON secure_chat.* TO 'chat_app_user'@'localhost'; FLUSH PRIVILEGES; EXIT;
Note: The credentials (
chat_app_user,123Password,secure_chat) are hardcoded inapp/storage/db.pyas per our development. - Log in as root:
-
Create Database Tables:
python -m app.storage.db
You should see:
Database initialized. 'users' table is ready. -
Generate Certificates:
python scripts/gen_ca.py --name "FAST-NU Root CA" python scripts/gen_cert.py --cn server.local --out certs/server python scripts/gen_cert.py --cn client.local --out certs/client
-
Start the Server:
# In Terminal 1 (with .venv active) python -m app.serverServer will be listening on
localhost:12345. -
Start the Client(s):
# In Terminal 2 (with .venv active) python -m app.clientYou can now Register a new user or Login. You can run
python -m app.clientin multiple terminals to have a group chat.
All test scripts are located in the tests/ directory.
(See TestReport-A02.docx for screenshots)
- Run
sudo wiresharkand capture on thelointerface. - Use display filter:
tcp.port == 12345 - Run the client and log in.
- Right-click the stream and select Follow > TCP Stream.
- Result: All sensitive data (payload, ct) is shown as encrypted Base64.
- Generate a self-signed certificate:
openssl req -x509 -newkey rsa:2048 -nodes -keyout certs/bad_key.pem -out certs/bad_cert.pem -subj "/CN=Evil" - Edit
app/client.pyto usebad_cert.pemandbad_key.pem. - Run
app.serverandapp.client. - Result: The server prints
BAD_CERT: Invalid signatureand the client receives the error.
(Remember to revert app/client.py after this test.)
These tests use the mitm_proxy.py script.
- Start Server: (Terminal 1)
python -m app.server - Start Proxy: (Terminal 2)
python tests/mitm_proxy.py - Configure Client: Edit
app/client.pyand change the connection port to12346(the proxy). - Run Client: (Terminal 3)
python -m app.client - Perform Attack:
- Tamper: Send one message. The proxy will flip a bit, and the server will print
SIGNATURE FAILED. - Replay: Send "message one", then "message two". The proxy will replay "message one". The server will print
REPLAY DETECTED.
- Tamper: Send one message. The proxy will flip a bit, and the server will print
(Remember to change the client port back to 12345 after.)
-
Run a normal chat session (client and server) and send a few messages before typing
quit. -
This generates
.logand.jsonfiles in thetranscripts/folder. -
Run Verifier (Success):
python tests/verify_transcript.py \ --transcript transcripts/client_...log \ --receipt transcripts/receipt_client_...json \ --cert certs/client_cert.pem
Result:
FINAL RESULT: SUCCESS! -
Run Verifier (Tamper):
- Edit a character in the
.logfile. - Re-run the command from step 3.
- Result:
[FAIL] Hash Mismatch! Result: Transcript has been tampered with!
- Edit a character in the
- A ZIP of this GitHub repository.
schema_dump.sql(MySQL schema dump).- This updated README.md.
i221050-Umar Javed-Report-A02.pdfi221050-Umar Javed-TestReport-A02.pdf