Thread: XOR Encryption

  1. #1
    Registered User
    Join Date
    Apr 2011
    Posts
    8

    XOR Encryption

    This is one of my first real programs that does anything. I have it pieced together and it is a rough model at the moment. It isn't user friendly yet so bear with me. The file you are encrypting must exist before hand. When I Run Decrypt it Decrypts the first 30 or so characters but then the rest is Jibberish. Please be kind I'm beginning. I also found out having a decrypt function was unnecessary because I can reuse the encrypt.

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <ctype.h>
    #include <math.h>
    
    void filename_accept(char fileName[]);
    void firstpass_encrypt(char string[], char key[],int size);
    //void firstpass_decrypt(char key[], char string[], int size);
    
    int position;
    int main()
    {
        FILE *myfile;
    	FILE *encryptedfile;
    	char fileName[50];
    	char userchoice[10];
    	char key[63]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
    	char c;
    	int i = 0;
    
    	startagain: ;
    	filename_accept(fileName);
        myfile = fopen(fileName,"r");
    
    	fseek(myfile, 0L, SEEK_END);
    	int size = ftell(myfile);
    
    	int linelen = size;
    	char*string = (char*)malloc(size*sizeof(string));
    	if (string == NULL)
    		{
    			printf("\nMemory Overflow");
    			exit(-1);
    		}
        /*printf("This is the length %i", size);*/
    	fseek(myfile, 0L, SEEK_SET);
    
    	while((c = fgetc(myfile)) != EOF)
    		string[i++] = c;
    
    		BackToTop: ;
    		printf("The file we are working with is ");
    		printf(fileName);
    		printf("\nAll input is case sensitive until next version!\n");
    		printf("\nWould you like to Encrypt or Decrypt?  \nPlease type one of the following: \n 1 Encrypt for Encrypt \n 2 Decrypt for Decrypt\n 3 Quit to terminate program ");
    		printf("\n 4 Type again to open a different file.\n");
    			fflush(stdin);
    			if (fgets(userchoice, sizeof userchoice, stdin) != NULL);
    			{
    				char *newline = strchr(userchoice, '\n');   //search for newline
    				if (newline != NULL)
    					*newline = '\0';         //overwrite  newline
    			}
    
    			int strcheck1 = strcmp(userchoice, "Encrypt");
    			int strcheck2 = strcmp(userchoice, "Decrypt");
    			int strcheck3 = strcmp(userchoice, "quit");
    			int strcheck4 = strcmp(userchoice, "Again");
    
    			if(strcheck1 == 0)
    			{
    				firstpass_encrypt(string, key, size);
        			/*printf("%c", string[position]);*/
                	strcat(userchoice, ".txt");                        //adds .txt format to it
    				encryptedfile = fopen(userchoice, "w");
    				for(int x=0; x <= size; x++)
    					fprintf(encryptedfile, "%c", string[x]);
    				printf("\nYour file has been encrypted.");
    				fclose(encryptedfile);
    			}
    			else if(strcheck2 == 0)
    			{
    				firstpass_encrypt(key, string, size);
    				strcat(userchoice, ".txt");
    				encryptedfile = fopen(userchoice, "w");
    				for (int x=0; x <= size; x++)
    					fprintf(encryptedfile, "%c", string[x]);
    				printf("\nYour file has been decrypted");
    				fclose(encryptedfile);
    			}
    			else if(strcheck3 == 0)
    				return 0;
    
    			else if(strcheck4 == 0)
    				goto startagain;
    
    			else
    			{
    				printf("%i", strcheck1);
    				printf("%i", strcheck2);
    				printf("\nInvalid Input.  Please follow the specified format");
    				goto BackToTop;
    			}
    
    
    
    	//printf("\n\n%i", position);
    
    	free(string);
    	fclose(myfile);
    	fclose(encryptedfile);
    	system("pause");
        return 0;
    }
    
    
    void filename_accept(char fileName[])    /*Reads in file name*/
    {
    	printf("\nEnter file you would like to open:\n");
    	gets(fileName);
    }
    
    void firstpass_encrypt(char string[], char key[],int size)
    {
    	for(position=0; position < size; position++)
    		{
    			if(string[position] == '\0')
    				break;
    			else
    			string[position]=string[position]^key[position%64];
    		}
    }
    
    /*void firstpass_decrypt(char key[], char string[], int size)
    {
    	for(position = 0; position < size;position++)
    		{
    			if (string[position] == '\0')
    				break;
    			else
    				string[position]=key[position%64]^string[position];
    		}
    }*/

  2. #2
    Registered User
    Join Date
    Jan 2009
    Posts
    1,485
    Your key seems to only have 62 characters, yet you use modulus 64 to find an index in the key.

  3. #3
    Registered User
    Join Date
    Apr 2011
    Posts
    8
    I changed the modulus and it still decrypts the first 30 or so characters and then the jibberish remains.

  4. #4

  5. #5
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    What happens if you xor 'a' with 'a'?


    Quzah.
    Hope is the first step on the road to disappointment.

  6. #6
    Lurking whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    9,612
    gets(), gotos and fflush(stdin); ...

    My 2 cents: You need to stop relying on things that are easy like this.



    How is it that you know how to write functions yet you rely on goto all the time to control the flow of the program? You should be using loops and functions more, even if you think it's trivial.

    Also, implement a one time pad if you really want to keep it simple and a secret...

    edit - Well damn.

  7. #7
    Registered User
    Join Date
    Apr 2011
    Posts
    8
    memcpy. I feel like you are driving at a point. The Fflush was probably unnecessary. I'm guessing.

  8. #8
    Registered User
    Join Date
    Jan 2009
    Posts
    1,485
    Quote Originally Posted by gooseantlers View Post
    I changed the modulus and it still decrypts the first 30 or so characters and then the jibberish remains.
    Another possibility is that the encrypted file contains a '\0' character, you have set up your decryption function to break at '\0'.

  9. #9
    Registered User
    Join Date
    Apr 2011
    Posts
    8
    whiteflags. What do you mean one time pad? I guess I just found it very simple to do the goto at the moment. As to why I know how to write functions and don't use them enough. I just wrote the program continuously through and was going to begin chopping the program up into functions by identifying what could be reused in the functions. Thanks for the advice. Would you indulge me as to white it is necessary in this case to use loops for the control structures?

  10. #10
    Registered User
    Join Date
    Apr 2011
    Posts
    8
    Subsonics. I removed that break statement and just had it execute the XOR and no changes. I'm truly stumped.

  11. #11
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    You should open the files in binary mode ("rb", "wb").

    You should check to make sure the files actually opened.

    This should be sizeof(char) instead of sizeof(string)
    Code:
    	char*string = (char*)malloc(size*sizeof(string));
    You don't want the semicolon at the end of this line
    Code:
    			if (fgets(userchoice, sizeof userchoice, stdin) != NULL);
    (although what if it is NULL?)

    You want this to be x < size
    Code:
    				for(int x=0; x <= size; x++)
    And most important of all, under the decrpyt algorithm you have
    Code:
    				firstpass_encrypt(key, string, size);
    but you want
    Code:
    				firstpass_encrypt(string, key, size);
    (same as for encrypt).
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  12. #12
    Registered User
    Join Date
    Apr 2011
    Posts
    8
    oogbooga. Thanks man. That got me on the right track. I will change my control structures over to loops instead of gotos and create more functions to get better more readable code. It messes up a little bit now. I think I'm on the right track to fix it. Thanks a bunch again

  13. #13
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    No problem. But take note of quzah's post.
    E.g., try encrypting and decrypting:
    Code:
    ABCDEFGHIJKLMNOPQRSTUVWXYZ
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  14. #14
    Registered User
    Join Date
    Jan 2009
    Posts
    1,485
    That should work as long as he doesn't break for \0.

  15. #15
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    But he is breaking for 0!
    So he should change his code to this:
    Code:
    void firstpass_encrypt(char string[], char key[],int size)
    {
    	for(position=0; position < size; position++)
    		{
    			string[position]=string[position]^key[position%62];
    		}
    }
    Also, position shouldn't be global.
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Encryption
    By 4658dan in forum C Programming
    Replies: 6
    Last Post: 12-10-2010, 01:59 PM
  2. Which encryption to use?
    By BobMcGee123 in forum A Brief History of Cprogramming.com
    Replies: 11
    Last Post: 03-02-2009, 12:12 AM
  3. XOR Encryption
    By Raigne in forum C++ Programming
    Replies: 6
    Last Post: 05-11-2007, 06:05 AM
  4. Encryption
    By L_U_K_E in forum C++ Programming
    Replies: 12
    Last Post: 04-30-2006, 01:27 PM
  5. RSA Encryption
    By minesweeper in forum Tech Board
    Replies: 6
    Last Post: 08-30-2003, 01:48 PM