为什么当我按 CTRL+C 时程序读取零字节?(C-Posix)



我的程序必须这样做: 用户必须通过命令行传递文件的 N 个绝对路径名。然后第 i 个线程(0<=i<= N(必须在第 i 个文件中写入用户使用 scanf(或 fgets(传递的字符串。如果按 CTRL+C,程序必须打印用户使用 scanf 传递的所有字符串。

当我运行它并为 N 个文件中的 1 个插入一个字符串并按 CTRL+C 时,在函数中按 on按函数读取返回 0(我认为在这种情况下并不表示文件指针在文件末尾(,它只打印字符串"字符串:">

法典:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <pthread.h>
#include <string.h>
#include <signal.h>
pthread_mutex_t mutex;
int fdGlobal;
void* writer (int* arg) {
int fd_in = *(arg);
char buffer[100];  
pthread_mutex_lock(&mutex);
printf("Write the string that you want to insert in the filen");
scanf("%s", &buffer);
write(fd_in, &buffer, strlen(buffer));
write(fdGlobal, &buffer, strlen(buffer));
printf("Finishedn");
pthread_mutex_unlock(&mutex); 
}
void onPress(int sig) {
char buff[100];
printf("I'm going to print all strings passed in files...n");
int rd = read(fdGlobal, &buff, sizeof(buff));
if (rd == -1) perror("Error in the read of global filen");
printf("I read %d bytesn", rd);
printf("Strings: %sn", buff);
exit(0);
}
void main (int argc, char* argv[]) {
int fds[argc-1];
pthread_t tid[argc-1];
int i, mu;
if (argc<=1) {
printf("Insert a number >=1 of  pathname/sn");
}
for ( i = 1 ; i<argc; i++) {
if (argv[i][0] != '/') {
printf("Insert a pathnamen");
}
}
signal(SIGINT, onPress);
fdGlobal = open("globalFile.txt", O_CREAT|O_RDWR, 0666);
if (fdGlobal == -1) perror("Error in the open of global filen"); 
mu = pthread_mutex_init(&mutex, NULL);
if (mu < 0) perror("Error in the creation of mutexn");
for (i=0; i<argc-1; i++) {
fds[i] = open(argv[i+1], O_CREAT|O_WRONLY, 0666);
if (fds[i] < 0 ) perror("Error in the open of the filen");
pthread_create ( &tid[i], NULL, (void*) writer, &(fds[i]) );
}
for (i=0; i<argc-1; i++) {
pthread_join(tid[i], NULL);
}
}

您的代码在异步信号安全、缓冲区大小和(非(并发性方面存在许多问题,但到目前为止,您描述的症状的最可能原因:

函数 read 返回 0

是你认为文件指针不在文件末尾是错误的。

实际上,read()返回 0 是一个积极的指标,表明文件偏移量当前位于(或超过(文件末尾。 如果文件是新创建的,那么我认为没有任何理由认为偏移量会在其他任何地方。 即使文件已经存在,您也需要将文件偏移量移回开头,以读取在程序当前运行中写入的数据。 例如,您可以通过对lseek()的适当调用来执行此操作。

最新更新