【发布时间】:2012-01-17 23:35:20
【问题描述】:
我试图了解为什么我在下面的代码中指定的行出现段错误(注明:<<<SEGFAULT OCCURS HERE)。我写这篇文章的灵感来自this post。
我认为这是一个内存分配问题,但考虑到即使我将 Event 实例的指针传递给 enqueue 函数,它仍然会出现段错误。考虑到 C 是按值传递的,即使我将 main 中的事件地址(&event 未在我发布的代码中显示)传递给 enqueue 函数,它也应该指向 main 中存在的事件实例的地址,对?所以我很难理解为什么会发生分段错误。
请注意,我更多的是寻找发生这种情况的原因,而不仅仅是解决问题。毕竟,我正在努力刷新 C 语言。 :)
相关代码:
typedef struct Event_ Event;
struct Event_ {
char action[4];
long timestamp;
char* path;
char hash[9];
Event *nextEvent; // pointer to next Event instance in Queue
};
// Enqueues newEvent into queue. Returns 1 on success, 0 otherwise.
int enqueue(Event newEvent, Event **head, Event **tail) {
if (head != NULL) {
// make the old head point to the newly inserted Event,
// and the new Event to point to NULL (nothing comes before head):
(*head) -> nextEvent = &newEvent;
newEvent.nextEvent = NULL;
} else {
// first element being added to queue.
*tail = &newEvent; //<<<SEGFAULT OCCURS HERE
}
// designate the new Event as the new head:
*head = &newEvent;
return 1;
}
// Parse line and return an Event struct.
Event parseLineIntoEvent(char* line) {
Event event = {0};
char* lineSegment;
int i = 0;
lineSegment = strtok(line, " ");
while (lineSegment != NULL) {
if (i > 3) {
printf("WARNING: input format error!\n");
break;
}
if (i == 0)
strncpy(event.action, lineSegment, sizeof(event.action)-1);
else if(i == 1)
event.timestamp = atoi(lineSegment);
else if(i == 2) {
event.path = malloc(sizeof(char) * (strlen(lineSegment) + 1));
strcpy(event.path, lineSegment);
} else if(i == 3)
strncpy(event.hash, lineSegment, sizeof(event.hash)-1);
lineSegment = strtok(NULL, " ");
i++;
} // while
return event;
} // parseLineIntoEvent()
int main (int argc, const char * argv[]) {
//...
Event **head = NULL;
Event **tail = NULL;
for (; numLines > 0; numLines--) {
char *line = getLineFromStdin(); //malloced char array being returned
printf("%s\n",line);
Event event = parseLineIntoEvent(line);
if(!enqueue(event, head, tail))
printf("An error occurred when attempting to enqueue an Event.\n");
event = dequeue(head, tail);
//...
free(event.path);
free(line);
}
return 0;
}
提前致谢!
【问题讨论】:
-
enqueue函数已损坏。你通过值传递newEvent,这不会修改你传入的事件。
标签: c memory-management queue segmentation-fault parameter-passing