【发布时间】:2020-04-09 19:59:02
【问题描述】:
如上所述,我得到一个段。每次运行程序时出现故障(核心转储)。我究竟做错了什么?我的 Linux:Manjaro Linux(18.1.4 Juhraya,内核 5.4.2.1-MANJARO)。
代码 1 (main.c):
#include <ncurses.h>
#include "setup.c"
#include "./src/write.c"
#include "./src/read.c"
int main(){
int h,w;
int c;
char message[128];
int cursorPos = 0;
initscr();
getmaxyx(stdscr, h, w);
WINDOW *win = newwin(h,w,0,0);
noecho();
keypad(stdscr, TRUE);
wborder(win,CS_BLOCK,ACS_BLOCK,ACS_BLOCK,ACS_BLOCK,ACS_BLOCK,ACS_BLOCK,ACS_BLOCK,ACS_BLOCK);
for(int i = 0; i<w; i++){
mvwaddch(win, h-3, i, ACS_BLOCK);
}
refresh();
wrefresh(win);
for(;;){
c = getch();
wmove(win, h-2, cursorPos+2);
if(c == 10){
write(message);
for(int i = 1; i<w-1; i++){
mvwaddch(win, h-2, i, ' ');
}
for (int i = 0; i < sizeof(message); i++) {
message[i] = '\0';
}
cursorPos = 0;
}else if(c == 127){
message[cursorPos] = '\0';
mvwdelch(win, h-2, cursorPos+1);
cursorPos -= 1;
}else if(c == 27){
break;
}
else{
message[cursorPos] = c;
mvwaddch(win, h-2, cursorPos+2, message[cursorPos]);
cursorPos += 1;
}
wrefresh(win);
}
endwin();
return 0;
}
代码 2 (write.c)
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
void write(char message[128]) {
FILE *fptr;
time_t rawtime;
struct tm *info;
char buffer[80];
time( &rawtime );
info = localtime( &rawtime );
strftime(buffer,80,"%x - %I:%M:%p", info);
fptr = fopen("./chat.txt", "a");
fprintf(fptr,"%s: %s\n", buffer,message);
fclose(fptr);
}
代码 3 (read.c)
#include <stdio.h>
void read()
{
char c;
FILE *fptr;
fptr = fopen("./chat.txt","r");
if(fptr == NULL)
{
printf("Something went wrong");
}
c = fgetc(fptr);
while(c != EOF)
{
printf ("%c", c);
c = fgetc(fptr);
}
fclose(fptr);
}
对于这篇长篇文章我很抱歉,但这个分段错误确实困扰着我。我很感激任何帮助。提前谢谢!
【问题讨论】:
-
1.为什么你
#includeC 文件而不是标题? 2. 我们无法猜测确切的错误信息是什么,因此请更新您的问题。 3.更新问题后,我建议你在SO上提问,它可能属于那里更好,我会尽力协助。 -
感谢您的帮助,我会在 SO 上发布!
-
您应该使用诸如
gdb或lldb之类的调试器将搜索范围缩小到源代码中的一行。 -
疯狂猜测 - 在此:
else if(c == 127)块中,您将cursorPos分配给-1。在下一次迭代中,如果您点击了最后一个else块,您将尝试通过以下方式访问您不拥有的内存:message[cursorPos] = c;。 -
关于:
fptr = fopen("./chat.txt", "a");始终检查 (!=NULL) 返回值以确保操作成功。如果不成功,请致电perror(),以便将您的错误消息和系统认为发生错误的文本原因发送给stderr。然后,由于错误不可恢复,请调用:exit( EXIT_FAILURE );注意exit()和EXIT_FAILURE都通过stdlib.h头文件公开
标签: c segmentation-fault macos