[英]Processes synchronization with message queues and signals
我必须创建三个过程:
进程之间的数据使用管道机制共享。 进程同步使用消息队列和信号。我还应该能够通过控制台将信号手动发送到每个进程。
我遇到的问题是所有进程似乎都是随机运行的。 为什么会这样,这怎么了? 应该可以...
这是正确编译的整个代码:
#include <stdio.h>
#include <unistd.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <string.h>
#include <stdlib.h>
#include <stdbool.h>
#define SIZEBUFF 256
// Signal handling for each process
void h_sig1(int signo);
void h_sig2(int signo);
void h_sig3(int signo);
void h_S4(int signo);
// Processes functions
void process1(void);
void process2(void);
void process3(void);
// helper functions
bool isInteger(double val);
static pid_t P1, P2, P3; // PIDs for each process
int P; // parent PID
int pfd12[2], pfd23[2]; // Pipes between processes 1-2 and 2-3
int providePIDY1[2], providePIDY2[2]; // provide all PIDs to 1/2 process
// message in message queue
typedef struct
{
long type;
int sigNum;
} message;
int queue_ID;
int main(void)
{
P = getpid();
// Message queue created
if ((queue_ID = msgget(IPC_PRIVATE,IPC_CREAT|0666)) < 0)
{
printf("msgget\n");
return 1;
}
if((P1 = fork()) == 0)
{
P1 = getpid();
process1();
}
else if((P2 = fork()) == 0)
{
P2 = getpid();
process2();
}
else if((P3 = fork()) == 0)
{
P3 = getpid();
process3();
}
else
{ // Sending signals from parent through operator
// Sending PIDs to process 1
close(providePIDY1[0]);
write(providePIDY1[1], &P, sizeof(int));
write(providePIDY1[1], &P1, sizeof(int));
write(providePIDY1[1], &P2, sizeof(int));
write(providePIDY1[1], &P3, sizeof(int));
close(providePIDY1[1]);
// Sending PIDs to process 2
close(providePIDY2[0]);
write(providePIDY2[1], &P, sizeof(int));
write(providePIDY2[1], &P1, sizeof(int));
write(providePIDY2[1], &P2, sizeof(int));
write(providePIDY2[1], &P3, sizeof(int));
close(providePIDY2[1]);
printf("\nProgram options:\n");
printf("Send signal - 's'(send)\n");
printf("Display processes PIDs 'p'(pids)\n");
printf("Quit program - 'q'(quit)\n");
char choice, choice2, choice3;
while(1)
{
choice = getchar();
if(choice == 's')
{
printf("Which process is receiving the signal - 1, 2, or 3?: ");
choice2 = getchar();
choice2 = getchar();
printf("\n");
if((choice2 < 1) && (choice2 > 3))
{
printf("No such process!");
continue;
}
printf("What signal to send?:\n");
printf("1-S1(end execution)\n2-S2(pause execution)\n3-S3(renew execution)?\n ");
printf("Choice: ");
choice3 = getchar();
choice3 = getchar();
switch(choice2)
{
case '1': //nie można przechwycić sygnałów SIGKILL oraz SIGSTOP (zabicia oraz zatrzymania)
if(choice3 == '1') { kill(0,SIGCONT); kill(P1,SIGUSR1); }
if(choice3 == '2') kill(P1,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
case '2':
if(choice3 == '1') { kill(0,SIGCONT); kill(P2,SIGUSR1); }
if(choice3 == '2') kill(P2,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
case '3':
if(choice3 == '1') { kill(0,SIGCONT); kill(P3,SIGUSR1); }
if(choice3 == '2') kill(P3,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
default: printf("No such operation!!! \n\n");
}
}
if(choice == 'p')
{
// do something
}
if(choice == 'q')
{
// do something
}
}
}
}
void process1(void)
{
// Receiving PIDs
close(providePIDY1[1]);
read(providePIDY1[0], &P, sizeof(int));
read(providePIDY1[0], &P1, sizeof(int));
read(providePIDY1[0], &P2, sizeof(int));
read(providePIDY1[0], &P3, sizeof(int));
close(providePIDY1[0]);
struct sigaction act1;
act1.sa_handler = h_sig1;
sigemptyset(&act1.sa_mask);
act1.sa_flags = 0;
sigaction(SIGUSR1, &act1, 0);
sigaction(SIGTSTP, &act1, 0);
sigaction(SIGALRM, &act1, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
// do something
}
void process2(void)
{
close(providePIDY2[1]);
read(providePIDY2[0], &P, sizeof(int));
read(providePIDY2[0], &P1, sizeof(int));
read(providePIDY2[0], &P2, sizeof(int));
read(providePIDY2[0], &P3, sizeof(int));
close(providePIDY2[0]);
struct sigaction act2;
act2.sa_handler = h_sig2;
sigemptyset(&act2.sa_mask);
act2.sa_flags = 0;
sigaction(SIGUSR1, &act2, 0);
sigaction(SIGTSTP, &act2, 0);
sigaction(SIGALRM, &act2, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
// do something
}
void process3(void)
{
struct sigaction act3;
act3.sa_handler = h_sig3;
sigemptyset(&act3.sa_mask);
act3.sa_flags = 0;
sigaction(SIGUSR1, &act3, 0);
sigaction(SIGTSTP, &act3, 0);
sigaction(SIGALRM, &act3, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
// do something
}
void h_sig1(int signo)
{
message msg;
msg.type = P2;
msg.sigNum = signo;
kill(P2, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P3;
kill(P3, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
}
if(signo == SIGTSTP)
{
}
if(signo == SIGALRM)
{
}
}
void h_sig2(int signo)
{
message msg;
msg.type = P1;
msg.sigNum = signo;
kill(P1, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P3;
kill(P3, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
}
if(signo == SIGTSTP)
{
}
if(signo == SIGALRM)
{
}
}
void h_sig3(int signo)
{
message msg;
msg.type = P1;
msg.sigNum = signo;
kill(P1, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P2;
kill(P2, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
}
if(signo == SIGTSTP)
{
}
if(signo == SIGALRM)
{
}
}
void h_S4(int signo)
{
int res;
message msg;
printf("\nProcess with PID=%d received signal S4", getpid());
if(signo == SIGINT)
{
res = msgrcv(queue_ID, &msg, sizeof(msg.sigNum), msg.type, 0);
if(res >= 0)
{
if(msg.sigNum == SIGUSR1)
{
}
if(msg.sigNum == SIGTSTP)
{
}
if(msg.sigNum == SIGALRM)
{
}
}
}
}
长版,要编译:
#include <stdio.h>
#include <unistd.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#include <string.h>
#include <stdlib.h>
#include <stdbool.h>
#define SIZEBUFF 200
// Signal handling for each process
void h_sig1(int signo);
void h_sig2(int signo);
void h_sig3(int signo);
void h_S4(int signo); // signal handling for the 4th signal
// Processes functions
void process1(void);
void process2(void);
void process3(void);
// helper functions
bool isInteger(double val);
static pid_t P1, P2, P3; // PIDs for each process
int P; // parent PID
int pfd12[2], pfd23[2]; // Pipes between processes 1-2 and 2-3
int providePIDY1[2], providePIDY2[2]; // provide all PIDs to 1/2 process
// message in message queue
typedef struct
{
long type;
int sigNum;
} message;
int queue_ID;
int main(void)
{
P = getpid();
if (pipe(pfd12) == -1)
{
perror("pipe failed");
exit(1);
}
if (pipe(pfd23) == -1)
{
perror("pipe failed");
exit(1);
}
// Message queue created
if ((queue_ID = msgget(IPC_PRIVATE,IPC_CREAT|0666)) < 0)
{
printf("msgget\n");
return 1;
}
if (pipe(providePIDY1) == -1)
{
perror("pipe failed");
exit(1);
}
if (pipe(providePIDY2) == -1)
{
perror("pipe failed");
exit(1);
}
if((P1 = fork()) == 0)
{
P1 = getpid();
process1();
}
else if(P1 < 0)
{
perror("fork failed");
exit(2);
}
else if((P2 = fork()) == 0)
{
P2 = getpid();
process2();
}
else if(P2 < 0)
{
perror("fork failed");
exit(2);
}
else if((P3 = fork()) == 0)
{
P3 = getpid();
process3();
}
else if(P3 < 0)
{
perror("fork failed");
exit(2);
}
else
{ // Sending signals from parent through operator
// Sending PIDs to process 1
close(providePIDY1[0]);
write(providePIDY1[1], &P, sizeof(int));
write(providePIDY1[1], &P1, sizeof(int));
write(providePIDY1[1], &P2, sizeof(int));
write(providePIDY1[1], &P3, sizeof(int));
close(providePIDY1[1]);
// Sending PIDs to process 2
close(providePIDY2[0]);
write(providePIDY2[1], &P, sizeof(int));
write(providePIDY2[1], &P1, sizeof(int));
write(providePIDY2[1], &P2, sizeof(int));
write(providePIDY2[1], &P3, sizeof(int));
close(providePIDY2[1]);
printf("\nProgram options:\n");
printf("Send signal - 's'(send)\n");
printf("Display processes PIDs 'p'(pids)\n");
printf("Quit program - 'q'(quit)\n");
char choice, choice2, choice3;
while(1)
{
choice = getchar();
if(choice == 's')
{
printf("Which process is receiving the signal - 1, 2, or 3?: ");
choice2 = getchar();
choice2 = getchar();
printf("\n");
if((choice2 < 1) && (choice2 > 3))
{
printf("No such process!");
continue;
}
printf("What signal to send?:\n");
printf("1-S1(end execution)\n2-S2(pause execution)\n3-S3(renew execution)?\n ");
printf("Choice: ");
choice3 = getchar();
choice3 = getchar();
switch(choice2)
{
case '1': //nie można przechwycić sygnałów SIGKILL oraz SIGSTOP (zabicia oraz zatrzymania)
if(choice3 == '1') { kill(0,SIGCONT); kill(P1,SIGUSR1); }
if(choice3 == '2') kill(P1,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
case '2':
if(choice3 == '1') { kill(0,SIGCONT); kill(P2,SIGUSR1); }
if(choice3 == '2') kill(P2,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
case '3':
if(choice3 == '1') { kill(0,SIGCONT); kill(P3,SIGUSR1); }
if(choice3 == '2') kill(P3,SIGTSTP);
if(choice3 == '3') { kill(0,SIGCONT); kill(P3,SIGALRM); }
break;
default: printf("No such operation!!! \n\n");
}
}
if(choice == 'p')
{
printf("\n<Processes PIDs:>\n");
printf("P(initial process)=%d\n",P);
printf("P1(process 1)=%d\n",P1);
printf("P2(process 2)=%d\n",P2);
printf("P3(process 3)=%d\n\n",P3);
}
if(choice == 'q')
{
printf("\n<Quitting program>\n");
msgctl(queue_ID, IPC_RMID, 0);
kill(0, SIGKILL);
}
}
}
}
void process1(void)
{
int dataSize;
char buff[SIZEBUFF];
// Receiving PIDs
close(providePIDY1[1]);
read(providePIDY1[0], &P, sizeof(int));
read(providePIDY1[0], &P1, sizeof(int));
read(providePIDY1[0], &P2, sizeof(int));
read(providePIDY1[0], &P3, sizeof(int));
close(providePIDY1[0]);
printf("\n<Process 1 execution in progress>\n");
/*SIGACTION*/
struct sigaction act1;
act1.sa_handler = h_sig1;
sigemptyset(&act1.sa_mask);
act1.sa_flags = 0;
sigaction(SIGUSR1, &act1, 0);
sigaction(SIGTSTP, &act1, 0);
sigaction(SIGALRM, &act1, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
close(pfd12[0]);
while(1)
{
printf("Provide expr: ");
scanf("%s", buff);
if(strcmp(buff, "0") == 0)
break;
dataSize = strlen(buff) + 1; // plus NULL
if(dataSize > 0)
write(pfd12[1], &dataSize, sizeof(int));
write(pfd12[1], &buff, sizeof(char)*dataSize);
}
dataSize = 0; // info that there's no more data
write(pfd12[1], &dataSize, sizeof(int));
close(pfd12[1]);
printf("\n---Process 1 finished execution---\n");
exit(0);
}
void process2(void)
{
int dataSize;
char buff[SIZEBUFF];
char *token, *end;
int number;
const char delim[2] = "+";
//Odebranie pidow
close(providePIDY2[1]);
read(providePIDY2[0], &P, sizeof(int));
read(providePIDY2[0], &P1, sizeof(int));
read(providePIDY2[0], &P2, sizeof(int));
read(providePIDY2[0], &P3, sizeof(int));
close(providePIDY2[0]);
printf("\n<Process 2 execution in progress>\n");
/*SIGACTION*/
struct sigaction act2;
act2.sa_handler = h_sig2;
sigemptyset(&act2.sa_mask);
act2.sa_flags = 0;
sigaction(SIGUSR1, &act2, 0);
sigaction(SIGTSTP, &act2, 0);
sigaction(SIGALRM, &act2, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
close(pfd12[1]);
read(pfd12[0], &dataSize, sizeof(int));
if(dataSize > 0)
{
sleep(3);
read(pfd12[0], buff, dataSize);
token = strtok(buff, delim);
while( token != NULL )
{
number = strtol(token, &end, 0);
if(!isInteger(number))
break;
}
}
close(pfd12[0]);
// Sending result to process 3
close(pfd23[0]);
write(pfd23[1], &buff, sizeof(int));
close(pfd23[1]);
printf("\n---Process 2 finished execution---\n");
}
void process3(void)
{
int sum = 0;
char buff[SIZEBUFF];
char* token, *end;
int number;
const char delim[2] = "+";
/*SIGACTION*/
struct sigaction act3;
act3.sa_handler = h_sig3;
sigemptyset(&act3.sa_mask);
act3.sa_flags = 0;
sigaction(SIGUSR1, &act3, 0);
sigaction(SIGTSTP, &act3, 0);
sigaction(SIGALRM, &act3, 0);
struct sigaction act;
act.sa_handler = h_S4;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
sigaction(SIGINT, &act, 0);
printf("\n<Process 3 execution in progress>");
close(pfd23[1]);
read(pfd23[0], &buff, sizeof(int));
token = strtok(buff, delim);
while( token != NULL )
{
number = strtol(token, &end, 0);
sum += number;
}
printf("Sum = %d\n", sum);
close(pfd23[0]);
printf("\n---Process 3 finished execution ---\n");
printf("\n---Program finished execution---\n");
kill(getppid(),SIGKILL);
}
/*******************************************************************************************************/
/****************************************SIGNAL HANDLING (S1-S3)***********************************************/
/*******************************************************************************************************/
void h_sig1(int signo)
{
message msg;
msg.type = P2;
msg.sigNum = signo;
kill(P2, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P3;
kill(P3, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
printf("\nProcess 1 received signal S1\n");
printf("Terminating parent process!\n");
kill(getppid(), SIGKILL);
printf("Terminating process 1!\n");
kill(getpid(), SIGKILL);
}
if(signo == SIGTSTP)
{
printf("\nProcess 1 received signal S2\n");
printf("Pausing process 1!\n");
kill(getpid(), SIGSTOP);
}
if(signo == SIGALRM)
{
printf("\nProcess 1 received signal S3\n");
printf("Renewing execution of process 1!\n");
kill(getpid(), SIGCONT);
}
}
void h_sig2(int signo)
{
message msg;
msg.type = P1;
msg.sigNum = signo;
kill(P1, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P3;
kill(P3, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
printf("\nProcess 2 received signal S1\n");
printf("Terminating parent process!\n");
kill(getppid(), SIGKILL);
printf("Terminating process 2!\n");
kill(getpid(), SIGKILL);
}
if(signo == SIGTSTP)
{
printf("\nProcess 2 received signal S2\n");
printf("Pausing process 2!\n");
kill(getpid(), SIGSTOP);
}
if(signo == SIGALRM)
{
printf("\nProcess 2 received signal S3\n");
printf("Renewing execution of process 2!\n");
kill(getpid(), SIGCONT);
}
}
void h_sig3(int signo)
{
message msg;
msg.type = P1;
msg.sigNum = signo;
kill(P1, SIGINT);
// send type of receiving signal to message queue
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
msg.type = P2;
kill(P2, SIGINT);
msgsnd(queue_ID, &msg, sizeof(msg.sigNum), 0);
if(signo == SIGUSR1)
{
printf("\nProcess 3 received signal S1\n");
printf("Terminating parent process!\n");
kill(getppid(), SIGKILL);
printf("Terminating process 3!\n");
kill(getpid(), SIGKILL);
}
if(signo == SIGTSTP)
{
printf("\nProcess 3 received signal S2\n");
printf("Pausing process 3!\n");
kill(getpid(), SIGSTOP);
}
if(signo == SIGALRM)
{
printf("\nProcess 3 received signal S3\n");
printf("Renewing execution of process 3!\n");
kill(getpid(), SIGCONT);
}
}
/*******************************************************************************************************/
/****************************************Handling S4 signal***********************************/
/*******************************************************************************************************/
void h_S4(int signo)
{
int res;
message msg;
printf("\nProcess with PID=%d received signal S4", getpid());
if(signo == SIGINT)
{
res = msgrcv(queue_ID, &msg, sizeof(msg.sigNum), msg.type, 0);
if(res >= 0)
{
if(msg.sigNum == SIGUSR1)
{
printf("Terminating process\n");
kill(getpid(),SIGKILL);
}
if(msg.sigNum == SIGTSTP)
{
printf("Pausing process\n");
kill(getpid(),SIGSTOP);
}
if(msg.sigNum == SIGALRM)
{
printf("Renewing process\n");
kill(getpid(),SIGCONT);
}
}
}
}
bool isInteger(double val)
{
int truncated = (int)val;
return (val == truncated);
}
存在一致性问题:
static pid_t P1, P2, P3; // PIDs for each process
int P; // parent PID
为什么用P
和int
而不是pid_t
? 为什么它是全局的而不是static
? 为什么用P
代替P0
? 整个应该是一个数组吗?
static pid_t P[4];
(使用数组会有好处!)
在多次调用的函数中应该存在重复:
// Sending PIDs to process 1
close(providePIDY1[0]);
write(providePIDY1[1], &P, sizeof(int));
write(providePIDY1[1], &P1, sizeof(int));
write(providePIDY1[1], &P2, sizeof(int));
write(providePIDY1[1], &P3, sizeof(int));
close(providePIDY1[1]);
// Sending PIDs to process 2
close(providePIDY2[0]);
write(providePIDY2[1], &P, sizeof(int));
write(providePIDY2[1], &P1, sizeof(int));
write(providePIDY2[1], &P2, sizeof(int));
write(providePIDY2[1], &P3, sizeof(int));
close(providePIDY2[1]);
请注意,由于P
值不是数组,因此也存在重复。 还有可能的可移植性责任。 pid_t
的大小不必与int
相同。
检查输入存在问题:
choice = getchar();
if(choice == 's')
由于choice
是一个char
,如果您不愿意对其进行测试,则可能会错误地处理EOF。 您还要在输入中至少保留换行符,并且不要跳过输入中的前导空格。 您最好先读取一行数据( fgets()
或POSIX readline()
),然后使用if (sscanf(buffer, " %c", &choice) != 1) { …handle error… }
来做得更好。人物。
您的下一个输入块很奇怪:
printf("Which process is receiving the signal - 1, 2, or 3?: ");
choice2 = getchar();
choice2 = getchar();
printf("\n");
if((choice2 < 1) && (choice2 > 3))
第一个输入读取换行符(假设没有尾随空格,等等),第二个输入得到'1'
, '2'
或'3'
。 但是,您要测试输入值是否既小于1又大于3,并且在两个条件都成立的Universe中没有已知值( NaN
值是未知值)。 您确实想要这样的东西:
if (choice2 < '1' || choice2 > '3')
确定要发送的信号(或多或少)后,您将获得另一个重复代码块,因为您使用了P1
etc而不是数组P
您的子流程中有很多重复的代码,例如读取流程编号的代码。 这些也应该在功能上。 信号处理设置可能也应该包含在一个函数中,尽管我没有花很多时间检查不同过程函数之间的差异和相似性。
您说代码应该在处理算术表达式。 您可以在主程序循环中读取有关信号处理的选择,但似乎也有process1()
也在尝试读取表达式。 这是个坏消息。 不确定哪个进程将读取任何给定的输入。
你有:
dataSize = strlen(buff) + 1; // plus NULL
if(dataSize > 0)
write(pfd12[1], &dataSize, sizeof(int));
write(pfd12[1], &buff, sizeof(char)*dataSize);
测试有点没有意义; strlen()
可以返回的最小值为0
,因此dataSize
的最小值为1
,因此条件将始终为true。 (理论上,我想,您可能输入了太多数据,以致strlen()
返回的size_t
溢出了int dataSize
,但是您没有为这个问题分配足够的空间,因此您的代码在此之前会遇到其他问题。)
在process2()
,这段代码很奇怪:
token = strtok(buff, delim);
while( token != NULL )
{
number = strtol(token, &end, 0);
if(!isInteger(number))
break;
}
在任何情况下都不会使用int number;
当您使用strtol()
扫描字符串时,它将是一个非整数。 您有溢出的风险(例如,在64位Unix系统上, sizeof(int) != sizeof(long)
)。 您可能无法解释浮点值的剩余部分(因为.
不是整数的有效部分)。 您需要重新编写该代码。
信号处理代码中有很多重复。 应该对其进行重构,以便您需要更少的功能。 从长远来看,它会更容易理解。 当结果接近单个程序中的代码克隆时,复制“粘贴”编辑是一种非常糟糕的编程方式。
我不清楚您显示的两个版本之间有什么区别; 我没有审查他们。 您应该查看如何创建MCVE( 如何创建最小,完整和可验证的示例? )或SSCCE( 简短,自包含,正确的示例 )—两个名称和相同基本思想的链接。 我不确定是否有很多代码都可以视为MCVE; 两种版本都过分杀伤力。 只需提供可编译的代码即可。
我已经在装有GCC 5.1.0的Mac OS X 10.10.3的Mac上并使用命令行在Mac上编译了第二段代码(保存在名为procsync.c
的文件中):
$ gcc -O3 -g -std=c11 -Wall -Wextra -Wmissing-prototypes -Wstrict-prototypes \
> -Wold-style-definition -Werror procsync.c -o procsync
$
令我相当惊讶的是,在那些非常严格的选项下编译的代码没有任何抱怨-这在SO代码中很少见到。
恭喜!
(但是还有其他问题需要担心。)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.