#include #include #include #include //AES key for Encryption and Decryption const unsigned char aes_key[]="0123456789abcdef"; //character alphabet of table base64 const unsigned char character_alphabet[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; //all functions used void encrypt_decrypt_file(const char*, const char*); unsigned char* encode(unsigned const char*); unsigned char* decode(unsigned const char*); //principal function int main(int argc, char **argv){ if(argc == 3){ if(!strcmp(argv[1] , "encrypt")) encrypt_decrypt_file(argv[2],"encrypt"); else if(!strcmp(argv[1] , "decrypt")) encrypt_decrypt_file(argv[2],"decrypt"); else printf("invalid options"); }else{ printf("invalid options"); } //getchar(); return 0; } void encrypt_decrypt_file(const char* path, const char* option){ //open File FILE *file; if((file = fopen(path,"r")) == NULL){ printf("cannot open this file : %s\n",path); exit(0); } //get length of content in file fseek(file,0,SEEK_END); size_t length_data = ftell(file); rewind(file); //input data unsigned char *aes_input = (unsigned char *)malloc(sizeof(unsigned char) * length_data + 1); //store content of file in aes_input int i=0; while(i < length_data){ *(aes_input + i) = getc(file); ++i; } rewind(file);i=0; *(aes_input + length_data) = '\0'; if(!strcmp(option , "encrypt")){ //(AES-128,AES-192,AES-256) bit AES_KEY enc_key; AES_set_encrypt_key(aes_key, 128, &enc_key); //init vector unsigned char iv[AES_BLOCK_SIZE + 1]; //iv Always have to be a sizeof(iv) = 16 memset(iv, 0x00, AES_BLOCK_SIZE); iv[AES_BLOCK_SIZE] = '\0'; //buffer for Encryption size_t length_enc_out = ((length_data + AES_BLOCK_SIZE) / AES_BLOCK_SIZE) * AES_BLOCK_SIZE ; if(!((length_data + AES_BLOCK_SIZE) % AES_BLOCK_SIZE)) length_enc_out = length_data; unsigned char *enc_out = (unsigned char *)malloc(sizeof(unsigned char) * length_enc_out); //CBC Encryption AES_cbc_encrypt(aes_input, enc_out, length_data, &enc_key, iv, AES_ENCRYPT); free(aes_input); //reopen the file to clean it fclose(file); file = fopen(path,"w"); length_data = 0; //we can not save the result on the file in binary format because sometimes the result can contain a character with a null ASCII value, and it will lose the encrypted result on the file because when printf a "%s" the printf will stop in the first zero ASCII value, and then the others where is go ?? ;) that is why we formatted the result in hexadecimal on a temporary file then we recover this result in format base64 then we store this final result on the final file. FILE *temporary_file = tmpfile(); for(i=0; i %02x\n",i,*(enc_out + i)); free(enc_out); } else if(!strcmp(option , "decrypt")){ //to change format the aes_input: base64 --> hex --> binary { FILE *temporary_file = tmpfile(); fprintf(temporary_file,"%s",decode(aes_input)); rewind(temporary_file); //clear aes_input to store on it binary context memset(aes_input,0x00,length_data); length_data=0; //aes_input content a binary context while(1){ int in; if(feof(temporary_file)) break; fscanf(temporary_file,"0x%x ",&in); *(aes_input + length_data) = (char)in; length_data++; } fclose(temporary_file); //reduced the size because 1 character(binary) = 4 character(hex) ex: 'a' = 0x61 aes_input = (unsigned char *)realloc(aes_input,sizeof(unsigned char) * length_data + 1); *(aes_input + length_data)= '\0'; } //(AES-128,AES-192,AES-256) bit AES_KEY dec_key; AES_set_decrypt_key(aes_key, 128, &dec_key); //init vector unsigned char iv[AES_BLOCK_SIZE + 1]; memset(iv, 0x00, AES_BLOCK_SIZE); iv[AES_BLOCK_SIZE] = '\0'; //buffer for Decryption unsigned char *dec_out = (unsigned char *)malloc(sizeof(unsigned char) * length_data); //CBC Decryption AES_cbc_encrypt(aes_input, dec_out, length_data, &dec_key, iv, AES_DECRYPT); free(aes_input); //reopen the file to clean it fclose(file); file = fopen(path,"w"); fprintf(file,"%s",dec_out); //verbose(decc_out formatted in hexadecimal) //for(int i=0; i %c\n",i,*(dec_out + i)); free(dec_out); } else{ printf("bad options"); } fclose(file); } unsigned char* encode(unsigned const char* string){ //get length of string int length_of_string = 0; while(string[length_of_string] != '\0') length_of_string++; int number_of_binary = length_of_string * 8; //multiplication by 8 so that each one character is represent on 8 bits //padding to complete the 6 bits when using base table 64 int padding=0; while(1){ if(number_of_binary % 6 == 0) break; padding++; number_of_binary++; } unsigned char* encode_data = (unsigned char*)malloc(sizeof(unsigned char) * ((number_of_binary / 6) + (padding / 2))); //after the encoding each 6 bits will present a one character //pointer to store all bits and calloc just to initialize frame with 0 int* store_result_binary = (int*)calloc(sizeof(int) , number_of_binary); //Jumping (8 bits) during when store bits in pointer int z_index = 8; for(int i=0;i0 ; i -= 6){ int j=0,power=0; double _6bit=0; while(j<6){ if(*(store_result_binary + (i - j)) == 1 ){ int powe=1; for(int k=0; k=0){ if(*(store_result_binary + (i + j)) == 1 ){ int powe=1; for(int k=0; k