所以我刚开始学习两周,基本上是初学者。所以我写了这个程序。但它在strncat函数中不断给出Segmentation fault错误第41行。我不确定我做错了什么。
#include <stdio.h>
#include <string.h>
#define _XOPEN_SOURCE
#include <unistd.h>
#define _GNU_SOURCE
#include <crypt.h>
#define WORD "/usr/share/dict/words"
int error(void);
int check(char *text, char *psswrd, char *salt);
int main(int argc, char *argv[])
{
if (argc != 2)
return error();
char salt[3];
salt[0] = argv[1][0];
salt[1] = argv[1][1];
salt[2] = '\0';
FILE *fptr;
char ch;
char *word;
int flag = 0;
fptr = fopen(WORD, "r");
if (fptr == NULL)
{
flag = 1;
}
else
{
do
{
ch = fgetc(fptr);
if ( ch != ' ' && ch != '\n')
{
word = strncat(word, &ch, 1);
if (strlen(word) == 8)
{
flag = check(word, argv[1], salt);
if (flag == 0)
{
printf ("%s \n", word);
return 0;
}
}
}
else
{
word = "";
}
}
while (ch != EOF);
fclose(fptr);
}
if (flag == 2)
{
printf("Password not found\n");
return 2;
}
}
int error(void)
{
printf ("Usage: ./crack <encrypted keyword>\n");
return 1;
}
int check(char *text, char *psswrd, char *salt)
{
if (strcmp(crypt(text, salt), psswrd) == 0 )
return 0;
else
return 2;
}
答案 0 :(得分:1)
您需要为“word”分配内存缓冲区:
word = malloc(MaxInputSize);
或者更好的方法是将word声明为静态数组:
word[MaxInputSize];
答案 1 :(得分:1)
做
char *word;
您已将word声明为指向char的指针,但您尚未设置word
指向的位置。只要未分配的word
可以指向任何地方并取消引用word
,即*word
会导致未定义的行为,这正是您在
word = strncat(word, &ch, 1);
为了使代码正常工作,您需要在上述步骤之前将内存分配给word
,即执行类似
word=malloc(100*sizeof *ptr); // You set word to point to a chunk of 100 bytes
假设word
指向一个100字节的块,现在
strncat(word, &ch, 1);
逻辑上不正确,因为假设word已完全填充(99个字符加上终止空字符),则无法再添加一个字符,因此在此步骤之前需要进行一些错误检查。做点什么
if strlen(word)<=98) // remember 99 is the max allowed, you gonna add 1 char
strncat(word, &ch, 1);
作为一种好的做法,您可以在使用后删除内存,即
free(word);
答案 2 :(得分:1)
您需要为word
分配内存,作为数组或使用malloc
。如果字符串很小(与堆栈大小相比),请使用数组,因为它不需要清理。
你还需要在word[0]=0;
之后设置malloc
,否则你会得到垃圾和可能的第二个分段错误。
将字符添加到字符串的规范方法是
char word[9];
char* pWord = word;
memset(word,0,sizeof(word));
...
ch = getchar();
*pWord++ = ch;
len++;
if (len >= sizeof(word)-1) ...