Что не так с strcpy ()? (Ошибка сегментации) - PullRequest
2 голосов
/ 19 мая 2010

Что не так с strcpy() в этом коде?

void process_filedata(char *filename)
{
  void* content;
  const char * buffer;
  char * temp;
  char * row;
  char * col;
  int lsize,buflen,tmp,num_scan; //num_scan - number of characters scanned
  int m=0,p=0,d=0,j=0; //m - machine, p - phase, d- delimiter, j - job

  FILE *file_pointer = fopen("machinetimesnew.csv","r");

  if(file_pointer == NULL)
  {
   error_flag =  print_error("Error opening file");

   if(error_flag) exit(1);
  }
  fseek(file_pointer, 0 ,SEEK_END);
  lsize = ftell(file_pointer);
  buflen = lsize;
  rewind(file_pointer);
 // content = (char*) malloc(sizeof(char)*lsize);
  fread(content,1,lsize,file_pointer);
  buffer = (const char*) content;
  strcpy(temp,buffer);
  row = strtok(temp,"\n");
  ...............
  ...............

Я получаю ошибку сегментации ..

Ответы [ 7 ]

13 голосов
/ 19 мая 2010

Вы не выделяете места для темп. Это дикий указатель .

9 голосов
/ 20 мая 2010

На самом деле здесь три ошибки сегментации:

fread(content,1,lsize,file_pointer);
strcpy(temp,buffer);
row = strtok(temp,"\n");

Первый из них - fread(), который пытается записать в память, которая еще не существует для вашего процесса.

Второй - strcpy(), (поясняющий первый), который вы пытаетесь скопировать в указатель, который ничего не указывает. Никакая память (кроме самой ссылки на указатель) не была выделена для temp, статически или динамически.

Исправьте это, изменив temp, чтобы он выглядел следующим образом (статически):

char temp[1024];

Или используйте malloc() для динамического выделения памяти для него (а также других ваших указателей, чтобы они фактически указывали на что-то), также для content. Если вы знаете необходимый размер буфера во время компиляции, используйте статическое распределение. Если нет, используйте malloc(). «Знание» - предмет другого вопроса.

Третий - strtok(), который собирается изменить temp en situ (на месте), чего он явно не может сделать, так как temp никогда не выделялся. В любом случае, не ожидайте, что temp будет таким же, как только strtok() будет сделано с ним. По названию переменной я предполагаю, что вы это знаете.

Кроме того, Инициализация указатель не то же самое, что выделение памяти для него:

char *temp = NULL; // temp is initialized
char *temp = (char *) malloc(size); // temp is allocated if malloc returns agreeably, cast return to not break c++

Наконец, пожалуйста, привыкните использовать strncpy() вместо strcpy(), это намного безопаснее.

8 голосов
/ 19 мая 2010

С strcpy все в порядке. Вы не инициализировали temp.

3 голосов
/ 20 мая 2010

Есть еще одна ошибка. fread не добавляет нулевой символ в конец буфера. Это потому, что он имеет дело только с массивами байтов, а не с нулевыми концами строк. Так что вам нужно сделать что-то вроде этого:

content = malloc(lsize + 1);
fread(content,1,lsize,file_pointer);
content[lsize] = 0;
temp = malloc(lsize + 1);
strcpy(temp, content);

или это:

content = malloc(lsize);
fread(content,1,lsize,file_pointer);
temp = malloc(lsize + 1);
memcpy(temp, content, lsize);
temp[lsize] = 0;

(Также в реальном коде вы должны проверить результаты fread и malloc.)

2 голосов
/ 19 мая 2010

вы не выделяете память для временного секретаря

1 голос
/ 20 мая 2010

Этот фрагмент кода меня заинтриговал:

if(file_pointer == NULL)
{
   error_flag =  print_error("Error opening file");

   if(error_flag) exit(1);
}

Не следует ли завершить работу безоговорочно, если указатель файла равен NULL?

1 голос
/ 19 мая 2010

char * temp не был инициализирован, и, следовательно, вы не выделили для него памяти.

попробовать:

temp = (char *)malloc(SIZE);

где SIZE - это сколько памяти вы хотите выделить для temp

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...