Aditya Bhat Aditya Bhat - 3 months ago 18
C Question

Something wrong while using crypt function in C

I am using the crypt function in C, where I am giving the command line input an encrypted word. I use the words in /usr/share/dict/words and encrypt them using the crypt function and then compare the encrypted output of the crypt function with the command line input. If the words are the same, then I give out the non-encrypted code as the output using a printf statement.
The code is given below.

#include<stdio.h>
#define _XOPEN_SOURCE
#include<unistd.h>
#include<cs50.h>
#include<string.h>
int
main(int argc, string argv[]){
char line[80];
string crypto;
if(argc>2||argc<2)
{
printf("ERROR. Enter only one crypt");
return 1;
}
string crypti=argv[1];
FILE *fr;
string as;
fr=fopen("/usr/share/dict/words","r");
if(!fr)
{
printf("File can't be read");
exit(-1);
}
while(fgets(line,80,fr)!=NULL)
{
as=crypt(line,"50");
if(strcmp(as,crypti)==0)
{
printf("%s",line);
break;
}
}
fclose(fr);
}


The code seems to work fine just for 1 input i.e when I give "./a.out 50q.zrL5e0Sak"(without quotes). However, if I use any other input for the crypt, the code seems to fail. Another example for password:encrypted password is abaca:50TZxhJSbeG1I. The word abaca is present in the list but fails to identify. I am not able to fix this code to work for all inputs.

Answer

Add the following snippet to the beginning of while (fgets...) body:

  size_t len = strlen(line);
  if (len)
    line[len-1]='\0';

There is usually a newline \n (when it was read) in the end of the buffer read by fgets.

Your original code works with "password" because only 8 first characters of the key are actually used by crypt. It would work with any word of length 8 or more as well.

Also, make sure that the output is flushed after you print the result, by adding a newline to your format string or (if you don't want to output an extra newline) calling fflush(stdout):

printf("%s\n",line);
/* or */
printf("%s",line);
fflush(stdout);
Comments