基本上我想要做的是从文件中读取一个数字,将值递增1,然后将数字写回同一个文件。使用fork()应该让两个进程都访问文件但是使用锁来轮流。我一直遇到分段错误。
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
void appendValue(FILE *, int *);
int readValue(FILE *, int *);
void lockFile(FILE *);
void unlockFile(FILE *);
void whatProcess(pid_t *pID);
int main(void) {
pid_t pID;
pID = fork();
int value = 0, counter = 0;
int *valPtr = &value;
pid_t *pidPtr = &pID;
FILE *file = fopen("output.txt", "a+");
lockFile(file);
while(counter < 1000) {
whatProcess(pidPtr);
value = readValue(file, valPtr);
value++;
appendValue(file, valPtr);
rewind(file);
counter++;
}
unlockFile(file);
fclose(file);
printf("\n");
return 0;
}
void whatProcess(pid_t *pID) {
if(*pID > 0) {
printf("\n --- In Parent ---");
} else if(*pID == 0) {
printf("\n --- In Child ---");
} else {
printf("\n --- fork() Failed ---");
}
}
void lockFile(FILE *file) {
int lock;
lock = lockf(fileno(file), F_LOCK, 0);
while(lock != 0) {}
if(lock == 0) {
printf("\nPID %d: Lock Successful", getpid());
} else {
printf("\nPID %d: Lock Unsuccessful", getpid());
}
}
void unlockFile(FILE *file) {
int lock;
lock = lockf(fileno(file), F_LOCK, 0);
while(lock != 0) {}
if(lock == 0) {
printf("\nPID %d: Unlock Successful", getpid());
} else {
printf("\nPID %d: Unlock Unsuccessful", getpid());
}
}
void appendValue(FILE *file, int *value) {
fprintf(file, "%d\n", *value);
}
int readValue(FILE *file, int *value) {
while(!feof(file)) {
fscanf(file, "%d", value);
}
return *value;
}
答案 0 :(得分:2)
fscanf
中的readValue
正在写入未分配的位置。您将value
作为指针传递,因此无需使用运算符的地址。
int readValue(FILE *file, int *value) {
fscanf(file, "%d", value);
printf("\nreadValue(): %d", *value);
return *value;
}
或者,甚至更好:
int readValue(FILE *file, int *value) {
if (fscanf(file, "%d", value) == 1) {
printf("\nreadValue(): %d", *value);
return 0;
}
return -1;
}
您当前的功能并不表示它是成功还是失败。添加状态返回值(零,-1很常见)或省略错误检查并改为执行此操作:
int readValue(FILE *file) {
int buf;
if (fscanf(file, "%d", &buf) == 1) {
printf("\nreadValue(): %d", buf);
} else {
perror("readValue(): fscanf failed");
}
return buf; /* could be a garbage value, use at own risk */
}