int main(int argc, char **argv) { int err, option_index, c, clientlen, counter; unsigned char rcv_plaintext[AES_BLOCK_SIZE]; unsigned char rcv_ciphertext[AES_BLOCK_SIZE]; unsigned char send_plaintext[AES_BLOCK_SIZE]; unsigned char send_ciphertext[AES_BLOCK_SIZE]; aes_context enc_ctx, dec_ctx; in_addr_t ip_addr; struct sockaddr_in server_addr; FILE *c_file, *d_file, *m_file; ssize_t read_size, write_size; struct sockaddr_in client_addr; tls_msg err_msg, send_msg, rcv_msg; mpz_t client_exp, client_mod; fd_set readfds; struct timeval tv; c_file = d_file = m_file = NULL; mpz_init(client_exp); mpz_init(client_mod); /* * This section is networking code that you don't need to worry about. * Look further down in the function for your part. */ memset(&ip_addr, 0, sizeof(in_addr_t)); option_index = 0; err = 0; static struct option long_options[] = { {"ip", required_argument, 0, 'i'}, {"cert", required_argument, 0, 'c'}, {"exponent", required_argument, 0, 'd'}, {"modulus", required_argument, 0, 'm'}, {0, 0, 0, 0}, }; while (1) { c = getopt_long(argc, argv, "c:i:d:m:", long_options, &option_index); if (c < 0) { break; } switch(c) { case 0: usage(); break; case 'c': c_file = fopen(optarg, "r"); if (c_file == NULL) { perror("Certificate file error"); exit(1); } break; case 'd': d_file = fopen(optarg, "r"); if (d_file == NULL) { perror("Exponent file error"); exit(1); } break; case 'i': ip_addr = inet_addr(optarg); break; case 'm': m_file = fopen(optarg, "r"); if (m_file == NULL) { perror("Modulus file error"); exit(1); } break; case '?': usage(); break; default: usage(); break; } } if (d_file == NULL || c_file == NULL || m_file == NULL) { usage(); } if (argc != 9) { usage(); } mpz_inp_str(client_exp, d_file, 0); mpz_inp_str(client_mod, m_file, 0); signal(SIGTERM, kill_handler); sockfd = socket(AF_INET, SOCK_STREAM, 0); if (sockfd < 0) { perror("Could not open socket"); exit(1); } memset(&server_addr, 0, sizeof(struct sockaddr_in)); server_addr.sin_family = AF_INET; server_addr.sin_addr.s_addr = ip_addr; server_addr.sin_port = htons(HANDSHAKE_PORT); err = connect(sockfd, (struct sockaddr *) &server_addr, sizeof(server_addr)); if (err < 0) { perror("Could not bind socket"); cleanup(); } // YOUR CODE HERE // IMPLEMENT THE TLS HANDSHAKE int send_message_int, receive_messge_int; /* error handling (To be continued) */ // ******************************************************************** // ******************************************************************** // ******************************************************************** // Whenever send or receive, need to check this feedback int feedback; // =============== [Send] Client Hello ======================= hello_message client_hello_message; int client_random; int server_random; memset(&client_hello_message, 0, sizeof(hello_message)); client_random = random_int(); printf("client_random: %d\n", client_random); client_hello_message.type = CLIENT_HELLO; client_hello_message.random = client_random; client_hello_message.cipher_suite = TLS_RSA_WITH_AES_128_ECB_SHA256; feedback = send_tls_message(sockfd, &client_hello_message, sizeof(hello_message)); if (feedback != ERR_OK){ perror("[CLIENT_HELLO]: can't send tls message"); cleanup(); } // =============== [Receive] Sever Hello ======================= hello_message server_hello_message; memset(&server_hello_message, 0, sizeof(hello_message)); feedback = receive_tls_message(sockfd, &server_hello_message, sizeof(hello_message), SERVER_HELLO); if (feedback != ERR_OK){ perror("[SERVER_HELLO]: can't receive tls message"); cleanup(); } server_random = server_hello_message.random; printf("server_random: %d\n", server_random); // =============== [Send] Client Certificate ================ mpz_t client_certificate_mpz; cert_message client_certificate; int byte_read; mpz_init(client_certificate_mpz); // May need to verify whether we connect to the correct server(i.e.torus.ce.berkeley.edu). memset(&client_certificate, 0, sizeof(cert_message)); client_certificate.type = CLIENT_CERTIFICATE; fread(client_certificate.cert, RSA_MAX_LEN, 1, c_file); //printf("Client Certificate: %s\n", client_certificate.cert); feedback = send_tls_message(sockfd, &client_certificate, CERT_MSG_SIZE); if (feedback != ERR_OK){ perror("[CLIENT CERTIFICATE]: can't send tls message"); cleanup(); } // =============== [Receive] Server Certificate ================ cert_message server_certificate; mpz_t decrypted_sever_cert_mpz; mpz_t ca_exponent; mpz_t ca_modulus; mpz_t server_public_key_exponent; mpz_t server_public_key_modulus; char decrypted_server_cert [RSA_MAX_LEN]; memset(&server_certificate, 0, sizeof(cert_message)); mpz_init(decrypted_sever_cert_mpz); mpz_init(ca_exponent); mpz_init(ca_modulus); mpz_init(server_public_key_exponent); mpz_init(server_public_key_modulus); memset(decrypted_server_cert, 0, RSA_MAX_LEN); feedback = receive_tls_message(sockfd, &server_certificate, sizeof(cert_message), SERVER_CERTIFICATE); if (feedback != ERR_OK){ perror("[SERVER CERTIFICATE]: can't receive tls message"); cleanup(); } // May need to verify whether we connect to the correct server(i.e.torus.ce.berkeley.edu). // Decrypt Server Certificate mpz_set_str(ca_exponent, CA_EXPONENT, 0); mpz_set_str(ca_modulus, CA_MODULUS, 0); decrypt_cert(decrypted_sever_cert_mpz, &server_certificate, ca_exponent, ca_modulus); mpz_get_ascii(decrypted_server_cert, decrypted_sever_cert_mpz); // Convert mpz to char array //printf("decrypted_server_cert: %s\n", decrypted_server_cert); get_cert_exponent(server_public_key_exponent, decrypted_server_cert); get_cert_modulus(server_public_key_modulus, decrypted_server_cert); // =============== [Send] E_server_public_key (Premaster Secret) ================ // Construct encrypted(premaster secret) mpz_t premaster_secret_encrypted, premaster_secret_mpz; int premaster_secret; char premaster[16]; ps_msg encrypted_ps_message; mpz_init(premaster_secret_encrypted); mpz_init(premaster_secret_mpz); memset(&encrypted_ps_message, 0, sizeof(ps_msg)); // Generate and Covert Premaster Secret to mpz sleep(3); premaster_secret = random_int(); printf("premaster_secret: %d\n", premaster_secret); sprintf(premaster, "%d", premaster_secret); mpz_set_str(premaster_secret_mpz, premaster, 10); // perform_rsa(premaster_secret_encrypted, premaster_secret_mpz, server_public_key_exponent, server_public_key_modulus); // ps_msg *encrypted_ps_message; // encrypted_ps_message = (ps_msg*) malloc(sizeof(ps_msg)); // encrypted_ps_message->type = PREMASTER_SECRET; // mpz_get_ascii(encrypted_ps_message->ps, premaster_secret_encrypted); // send_tls_message(sockfd, encrypted_ps_message, sizeof(ps_msg)); // ps_msg encrypted_server_ms_message; // memset(&encrypted_server_ms_message, 0, sizeof(ps_msg)); // receive_messge_int = receive_tls_message(sockfd, &encrypted_server_ms_message, sizeof(ps_msg), PREMASTER_SECRET); // if (receive_messge_int == ERR_FAILURE) { // perror("Could not get the master secret"); // cleanup(); // } // gmp_printf("premaster_secret_mpz: %Zd\n", premaster_secret_mpz); // gmp_printf("server_public_key_exponent: %Zx\n", server_public_key_exponent); // gmp_printf("server_public_key_modulus: %Zx\n", server_public_key_modulus); perform_rsa(premaster_secret_encrypted, premaster_secret_mpz, server_public_key_exponent, server_public_key_modulus); encrypted_ps_message.type = PREMASTER_SECRET; mpz_get_str(encrypted_ps_message.ps, 16, premaster_secret_encrypted); feedback = send_tls_message(sockfd, &encrypted_ps_message, sizeof(ps_msg)); if (feedback != ERR_OK) { perror("[E_server_public_key (Premaster secret)]: can't send tls message"); cleanup(); } // =============== [Receive] E_client_public_key (Master Secret) ================ ps_msg encrypted_server_ms_message; mpz_t decrypted_ms; mpz_t master_secret_mpz; unsigned long long master_secret_long; unsigned char master_secret[SHA_BLOCK_SIZE]; int result; memset(&encrypted_server_ms_message, 0, sizeof(ps_msg)); mpz_init(decrypted_ms); memset(master_secret, 0, SHA_BLOCK_SIZE); mpz_init(master_secret_mpz); feedback = receive_tls_message(sockfd, &encrypted_server_ms_message, sizeof(ps_msg), VERIFY_MASTER_SECRET); if (feedback != ERR_OK) { perror("[E_client_public_key (master secret)]: can't receive tls message"); cleanup(); } decrypt_verify_master_secret(decrypted_ms, &encrypted_server_ms_message, client_exp, client_mod); compute_master_secret(premaster_secret, client_random, server_random, master_secret); char* master_secret_str = hex_to_str(master_secret, SHA_BLOCK_SIZE); mpz_set_str(master_secret_mpz, master_secret_str, 16); result = mpz_cmp(master_secret_mpz, decrypted_ms); printf("%d", result); if (result != 0) { perror("Decrypted server master secret doesn't match computed master secret!"); cleanup(); } if (client_random != premaster_secret && server_random != premaster_secret){ //printf("1\n"); }else{ //printf("0\n"); } //printf("result: %d\n", result); free(master_secret_str); close(sockfd); mpz_clear(client_exp); mpz_clear(client_mod); mpz_clear(client_certificate_mpz); mpz_clear(decrypted_sever_cert_mpz); mpz_clear(ca_exponent); mpz_clear(ca_modulus); mpz_clear(premaster_secret_encrypted); mpz_clear(server_public_key_exponent); mpz_clear(server_public_key_modulus); mpz_clear(premaster_secret_mpz); mpz_clear(decrypted_ms); mpz_clear(master_secret_mpz); cleanup(); return 0; }
int main(int argc, char **argv) { int err, option_index, c, clientlen, counter; unsigned char rcv_plaintext[AES_BLOCK_SIZE]; unsigned char rcv_ciphertext[AES_BLOCK_SIZE]; unsigned char send_plaintext[AES_BLOCK_SIZE]; unsigned char send_ciphertext[AES_BLOCK_SIZE]; aes_context enc_ctx, dec_ctx; in_addr_t ip_addr; struct sockaddr_in server_addr; FILE *c_file, *d_file, *m_file; ssize_t read_size, write_size; struct sockaddr_in client_addr; tls_msg err_msg, send_msg, rcv_msg; mpz_t client_exp, client_mod; fd_set readfds; struct timeval tv; c_file = d_file = m_file = NULL; mpz_init(client_exp); mpz_init(client_mod); /* * This section is networking code that you don't need to worry about. * Look further down in the function for your part. */ memset(&ip_addr, 0, sizeof(in_addr_t)); option_index = 0; err = 0; static struct option long_options[] = { {"ip", required_argument, 0, 'i'}, {"cert", required_argument, 0, 'c'}, {"exponent", required_argument, 0, 'd'}, {"modulus", required_argument, 0, 'm'}, {0, 0, 0, 0}, }; while (1) { c = getopt_long(argc, argv, "c:i:d:m:", long_options, &option_index); if (c < 0) { break; } switch(c) { case 0: usage(); break; case 'c': c_file = fopen(optarg, "r"); if (c_file == NULL) { perror("Certificate file error"); exit(1); } break; case 'd': d_file = fopen(optarg, "r"); if (d_file == NULL) { perror("Exponent file error"); exit(1); } break; case 'i': ip_addr = inet_addr(optarg); break; case 'm': m_file = fopen(optarg, "r"); if (m_file == NULL) { perror("Modulus file error"); exit(1); } break; case '?': usage(); break; default: usage(); break; } } if (d_file == NULL || c_file == NULL || m_file == NULL) { usage(); } if (argc != 9) { usage(); } mpz_inp_str(client_exp, d_file, 0); mpz_inp_str(client_mod, m_file, 0); signal(SIGTERM, kill_handler); sockfd = socket(AF_INET, SOCK_STREAM, 0); if (sockfd < 0) { perror("Could not open socket"); exit(1); } memset(&server_addr, 0, sizeof(struct sockaddr_in)); server_addr.sin_family = AF_INET; server_addr.sin_addr.s_addr = ip_addr; server_addr.sin_port = htons(HANDSHAKE_PORT); err = connect(sockfd, (struct sockaddr *) &server_addr, sizeof(server_addr)); if (err < 0) { perror("Could not bind socket"); cleanup(); } // YOUR CODE HERE // IMPLEMENT THE TLS HANDSHAKE // send client hello hello_message client_hello_msg = {CLIENT_HELLO, random_int(), TLS_RSA_WITH_AES_128_ECB_SHA256}; err = send_tls_message(sockfd, &client_hello_msg, HELLO_MSG_SIZE); if (err == ERR_FAILURE) { exit(1); } // receive server hello hello_message server_hello_msg; err = receive_tls_message(sockfd, &server_hello_msg, HELLO_MSG_SIZE, SERVER_HELLO); if (err == ERR_FAILURE) { exit(1); } // send client certificate cert_message client_cert_msg; client_cert_msg.type = CLIENT_CERTIFICATE; fgets(client_cert_msg.cert, RSA_MAX_LEN, c_file); err = send_tls_message(sockfd, &client_cert_msg, CERT_MSG_SIZE); if (err == ERR_FAILURE) { exit(1); } //receive server certificate cert_message server_cert_msg; err = receive_tls_message(sockfd, &server_cert_msg, CERT_MSG_SIZE, SERVER_CERTIFICATE); if (err == ERR_FAILURE) { exit(1); } mpz_t cert_plaintext; mpz_init(cert_plaintext); mpz_t ca_key_exp; mpz_init(ca_key_exp); mpz_t ca_key_mod; mpz_init(ca_key_mod); mpz_set_str(ca_key_exp, CA_EXPONENT, 0); mpz_set_str(ca_key_mod, CA_MODULUS, 0); decrypt_cert(cert_plaintext, &server_cert_msg, ca_key_exp, ca_key_mod); char cert_plaintext_string[RSA_MAX_LEN]; mpz_get_ascii(cert_plaintext_string, cert_plaintext); mpz_t exponentNum; mpz_init(exponentNum); mpz_t modNum; mpz_init(modNum); get_cert_exponent(exponentNum, cert_plaintext_string); get_cert_modulus(modNum, cert_plaintext_string); mpz_t premaster_secret_int; mpz_init(premaster_secret_int); int p_secret_int = random_int(); mpz_t p_secret; mpz_init(p_secret); mpz_add_ui(p_secret, p_secret, p_secret_int); perform_rsa(premaster_secret_int, p_secret, exponentNum, modNum); ps_msg premaster_secret; premaster_secret.type = PREMASTER_SECRET; mpz_get_str(premaster_secret.ps, 16, premaster_secret_int); // send premaster secret err = send_tls_message(sockfd, &premaster_secret, PS_MSG_SIZE); if (err == ERR_FAILURE) { exit(1); } ps_msg master_secret; // receive master secret err = receive_tls_message(sockfd, &master_secret, PS_MSG_SIZE, VERIFY_MASTER_SECRET); if (err == ERR_FAILURE) { exit(1); } mpz_t decrypted_master_secret; mpz_init(decrypted_master_secret); mpz_t key_exp; mpz_init(key_exp); mpz_t key_mod; mpz_init(key_mod); fseek (d_file, 0, SEEK_END); long length = ftell (d_file); fseek (d_file, 0, SEEK_SET); char private_key[length]; fgets(private_key, length, d_file); mpz_set_str(key_exp, private_key, 0); fseek (m_file, 0, SEEK_END); length = ftell (m_file); fseek (m_file, 0, SEEK_SET); char modulus[length]; fgets(modulus, length, m_file); mpz_set_str(key_mod, modulus, 0); decrypt_verify_master_secret(decrypted_master_secret, &master_secret, key_exp, key_mod); char decrypted_master_secret_char[16]; mpz_get_str(decrypted_master_secret_char, 16, decrypted_master_secret); unsigned char computed_master_secret[16]; compute_master_secret(p_secret_int, client_hello_msg.random, server_hello_msg.random, computed_master_secret); if (strcasecmp(decrypted_master_secret_char, hex_to_str(computed_master_secret, 16)) == 0) { printf("Begin messages.\n"); } /* * START ENCRYPTED MESSAGES */ memset(send_plaintext, 0, AES_BLOCK_SIZE); memset(send_ciphertext, 0, AES_BLOCK_SIZE); memset(rcv_plaintext, 0, AES_BLOCK_SIZE); memset(rcv_ciphertext, 0, AES_BLOCK_SIZE); memset(&rcv_msg, 0, TLS_MSG_SIZE); aes_init(&enc_ctx); aes_init(&dec_ctx); // YOUR CODE HERE // SET AES KEYS if (aes_setkey_enc (&enc_ctx, computed_master_secret, 128)){ printf("setting key didn't work n***a\n"); } if (aes_setkey_dec (&dec_ctx, computed_master_secret, 128)){ printf("setting key didn't work n***a\n"); } fcntl(STDIN_FILENO, F_SETFL, O_NONBLOCK); /* Send and receive data. */ while (1) { FD_ZERO(&readfds); FD_SET(STDIN_FILENO, &readfds); FD_SET(sockfd, &readfds); tv.tv_sec = 2; tv.tv_usec = 10; select(sockfd+1, &readfds, NULL, NULL, &tv); if (FD_ISSET(STDIN_FILENO, &readfds)) { counter = 0; memset(&send_msg, 0, TLS_MSG_SIZE); send_msg.type = ENCRYPTED_MESSAGE; memset(send_plaintext, 0, AES_BLOCK_SIZE); read_size = read(STDIN_FILENO, send_plaintext, AES_BLOCK_SIZE); while (read_size > 0 && counter + AES_BLOCK_SIZE < TLS_MSG_SIZE - INT_SIZE) { if (read_size > 0) { err = aes_crypt_ecb(&enc_ctx, AES_ENCRYPT, send_plaintext, send_ciphertext); memcpy(send_msg.msg + counter, send_ciphertext, AES_BLOCK_SIZE); counter += AES_BLOCK_SIZE; } memset(send_plaintext, 0, AES_BLOCK_SIZE); read_size = read(STDIN_FILENO, send_plaintext, AES_BLOCK_SIZE); } write_size = write(sockfd, &send_msg, INT_SIZE+counter+AES_BLOCK_SIZE); if (write_size < 0) { perror("Could not write to socket"); cleanup(); } } else if (FD_ISSET(sockfd, &readfds)) { memset(&rcv_msg, 0, TLS_MSG_SIZE); memset(rcv_ciphertext, 0, AES_BLOCK_SIZE); read_size = read(sockfd, &rcv_msg, TLS_MSG_SIZE); if (read_size > 0) { if (rcv_msg.type != ENCRYPTED_MESSAGE) { goto out; } memcpy(rcv_ciphertext, rcv_msg.msg, AES_BLOCK_SIZE); counter = 0; while (counter < read_size - INT_SIZE - AES_BLOCK_SIZE) { aes_crypt_ecb(&dec_ctx, AES_DECRYPT, rcv_ciphertext, rcv_plaintext); printf("%s", rcv_plaintext); counter += AES_BLOCK_SIZE; memcpy(rcv_ciphertext, rcv_msg.msg+counter, AES_BLOCK_SIZE); } printf("\n"); } } } out: close(sockfd); return 0; }
int main(int argc, char **argv) { int err, option_index, c, clientlen, counter; unsigned char rcv_plaintext[AES_BLOCK_SIZE]; unsigned char rcv_ciphertext[AES_BLOCK_SIZE]; unsigned char send_plaintext[AES_BLOCK_SIZE]; unsigned char send_ciphertext[AES_BLOCK_SIZE]; aes_context enc_ctx, dec_ctx; in_addr_t ip_addr; struct sockaddr_in server_addr; FILE *c_file, *d_file, *m_file; ssize_t read_size, write_size; struct sockaddr_in client_addr; tls_msg err_msg, send_msg, rcv_msg; mpz_t client_exp, client_mod; fd_set readfds; struct timeval tv; c_file = d_file = m_file = NULL; mpz_init(client_exp); mpz_init(client_mod); /* * This section is networking code that you don't need to worry about. * Look further down in the function for your part. */ memset(&ip_addr, 0, sizeof(in_addr_t)); option_index = 0; err = 0; static struct option long_options[] = { {"ip", required_argument, 0, 'i'}, {"cert", required_argument, 0, 'c'}, {"exponent", required_argument, 0, 'd'}, {"modulus", required_argument, 0, 'm'}, {0, 0, 0, 0}, }; while (1) { c = getopt_long(argc, argv, "c:i:d:m:", long_options, &option_index); if (c < 0) { break; } switch(c) { case 0: usage(); break; case 'c': c_file = fopen(optarg, "r"); if (c_file == NULL) { perror("Certificate file error"); exit(1); } break; case 'd': d_file = fopen(optarg, "r"); if (d_file == NULL) { perror("Exponent file error"); exit(1); } break; case 'i': ip_addr = inet_addr(optarg); break; case 'm': m_file = fopen(optarg, "r"); if (m_file == NULL) { perror("Modulus file error"); exit(1); } break; case '?': usage(); break; default: usage(); break; } } if (d_file == NULL || c_file == NULL || m_file == NULL) { usage(); } if (argc != 9) { usage(); } mpz_inp_str(client_exp, d_file, 0); mpz_inp_str(client_mod, m_file, 0); signal(SIGTERM, kill_handler); sockfd = socket(AF_INET, SOCK_STREAM, 0); if (sockfd < 0) { perror("Could not open socket"); exit(1); } memset(&server_addr, 0, sizeof(struct sockaddr_in)); server_addr.sin_family = AF_INET; server_addr.sin_addr.s_addr = ip_addr; server_addr.sin_port = htons(HANDSHAKE_PORT); err = connect(sockfd, (struct sockaddr *) &server_addr, sizeof(server_addr)); if (err < 0) { perror("Could not bind socket"); cleanup(); } // YOUR CODE HERE // IMPLEMENT THE TLS HANDSHAKE // Client Hello and Setup hello_message client_hello_send[HELLO_MSG_SIZE]; (*client_hello_send).type = CLIENT_HELLO; (*client_hello_send).random = random_int(); (*client_hello_send).cipher_suite = TLS_RSA_WITH_AES_128_ECB_SHA256; send_tls_message(sockfd, client_hello_send, HELLO_MSG_SIZE); // Server Hello & Setup hello_message server_hello_rcv[HELLO_MSG_SIZE]; receive_tls_message(sockfd, server_hello_rcv, HELLO_MSG_SIZE, SERVER_HELLO); // Client Certificate cert_message client_cert_send[CERT_MSG_SIZE]; (*client_cert_send).type = CLIENT_CERTIFICATE; fread((*client_cert_send).cert, RSA_MAX_LEN, 1, c_file); //Printing the client certificate message //printf("%s\n",(*client_cert_send).cert); send_tls_message(sockfd, client_cert_send, CERT_MSG_SIZE); // Server Certificate cert_message server_cert_rcv[CERT_MSG_SIZE]; receive_tls_message(sockfd, server_cert_rcv, CERT_MSG_SIZE, SERVER_CERTIFICATE); mpz_t decrypted_cert; mpz_t ca_exp; mpz_t ca_mod; mpz_init(decrypted_cert); mpz_init(ca_exp); mpz_init(ca_mod); mpz_set_str(ca_exp, CA_EXPONENT, 0); mpz_set_str(ca_mod, CA_MODULUS, 0); // Decrypt Server Certificate decrypt_cert(decrypted_cert, server_cert_rcv, ca_exp, ca_mod); char output_str[CERT_MSG_SIZE]; mpz_get_ascii(output_str, decrypted_cert); // Extracting keys from certificate mpz_t public_exp; mpz_t public_mod; mpz_init(public_exp); mpz_init(public_mod); get_cert_exponent(public_exp, output_str); get_cert_modulus(public_mod, output_str); <<<<<<< HEAD