perror scanf通过管道引起的无限循环
我一直在写一个c程序,它将数据从一个文件传输到下一个文件,但是它是无限循环的 到目前为止我所发现的。无限循环是在文件c1.c上产生的,其中perror(或stderr)跳过scanf。如果scanf真的起作用。程序无限循环沿着轨道进一步打印出perror,即使它已经超过了该部分 我的代码在下面 控制器cperror scanf通过管道引起的无限循环,c,linux,pipe,stdin,infinite-loop,C,Linux,Pipe,Stdin,Infinite Loop,我一直在写一个c程序,它将数据从一个文件传输到下一个文件,但是它是无限循环的 到目前为止我所发现的。无限循环是在文件c1.c上产生的,其中perror(或stderr)跳过scanf。如果scanf真的起作用。程序无限循环沿着轨道进一步打印出perror,即使它已经超过了该部分 我的代码在下面 控制器c #include<stdio.h> #include<stdlib.h> #include<sys/wait.h> #include<unistd.h&
#include<stdio.h>
#include<stdlib.h>
#include<sys/wait.h>
#include<unistd.h>
int main(int ac, char**av)
{
int pipez[2];
int piped[2];
int status;
pid_t pid;
if (pipe (pipez) == -1){
perror("could not make pipe");
return 1;
}
if ((pid = fork()) == -1){
perror("fork");
return 1;
}
if(pid == 0){
close(pipez[1]);
dup2(pipez[0],0);
close(pipez[0]);
execvp("./c1",av);
perror("demo);
_exit(1);
}
else{
close(pipez[0]);
dup2(pipez[1],1);
close(pipez[1]);
execvp("./c2",av);
perror("demo");
exit(1);
}
waitpid(pid,&status,0);
if(WIFEXITED(status)){
printf("[%d] TERMINATED (Status: %d)\n", pid, WEXITSTATUS(status));
}
if(pipe (piped) == -1){
perror("could not make pipe");
return 1;
}
if((pid = fork()) == -1){
perror("fork");
return 1;
}
if (pid == 0){
close(piped[1]);
dup2(piped[0],0);
close(piped[0]);
execvp("./c2", av);
perror("demo");
_exit(1);
}
else{
close(piped[0]);
dup2(piped(piped[1],1);
close(piped[1]);
execvp("./c3",av);
perror("demo");
exit(1);
}
waitpid(pid, &status, 0);
if (WIFEXITED(status)){
printf("[%d] TERMINATED (Status: %d)\n", pid, WEXITSTATUS(status));
}
return 0;
}
#包括
#包括
#包括
#包括
内部主(内部ac,字符**av)
{
int-pipez[2];
int-piped[2];
智力状态;
pid_t pid;
如果(管道(管道Z)=-1){
佩罗(“无法制造管道”);
返回1;
}
如果((pid=fork())=-1){
佩罗尔(“福克”);
返回1;
}
如果(pid==0){
关闭(pipez[1]);
dup2(pipez[0],0);
关闭(pipez[0]);
execvp(“./c1”,av);
佩罗(“演示”);
_出口(1);
}
否则{
关闭(pipez[0]);
dup2(pipez[1],1);
关闭(pipez[1]);
execvp(“./c2”,av);
佩罗(“演示”);
出口(1);
}
waitpid(pid和status,0);
如果(妻子退出(状态)){
printf(“[%d]已终止(状态:%d)\n”、pid、WEXITSTATUS(状态));
}
如果(管道(管道)=-1){
佩罗(“无法制造管道”);
返回1;
}
如果((pid=fork())=-1){
佩罗尔(“福克”);
返回1;
}
如果(pid==0){
关闭(管道[1]);
dup2(管道传输[0],0);
关闭(管道[0]);
execvp(“./c2”,av);
佩罗(“演示”);
_出口(1);
}
否则{
关闭(管道[0]);
dup2(管道式)(管道式[1],1);
关闭(管道[1]);
execvp(“./c3”,av);
佩罗(“演示”);
出口(1);
}
waitpid(pid和status,0);
如果(妻子退出(状态)){
printf(“[%d]已终止(状态:%d)\n”、pid、WEXITSTATUS(状态));
}
返回0;
}
c1.c
#包括
#包括
#包括
#定义bufsize256
//该程序正在导致无限循环,包括fflush、fgets和scanf
//它将独立运行,但将通过管道循环
int main(int a,字符**av){
字符存储[BUFSIZE];
memset(存储'\0',sizeof(存储));
while(strcmp(存储,“退出!”)!=0){
perror(“请输入下一行输入(输入'exit!'停止)\n”);//这会无限重复
fgets(商店、布袋大小、标准尺寸);
printf(“%s”,store);//这也会根据我放置的位置重复
//fflush或其他printf。重复输出以块形式出现
}
返回0;
}
c2.c
#包括
#包括
#包括
#定义bufsize256
char*strlwr(char*str);
内部主(内部ac,字符**av){
字符存储[BUFSIZE];
while(strcmp(存储,“退出!”)!=0){
scanf(“%s”,存储);
printf(“%s”,strlwr(store));
}
返回0;
}
char*strlwr(char*str){
无符号字符*p=(无符号字符*)str;
而(*p){
*p=tolower((无符号字符)*p);
p++;
}
返回str;
}
c3.c
#包括
#包括
#包括
#定义bufsize256
内部主(内部ac,字符**av){
字符存储[BUFSIZE];
int n=0;
while(strcmp(存储,“退出!”)!=0{
scanf(“%s”,存储);
printf(“第%d行:%s\n”,n,存储区);
n++;
}
返回0;
}
fgets
在存储区中保留'\n'
字符,因此,最简单的修复方法是将'\n'
添加到比较的字符串中:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define BUFSIZE 256
//This program is causing infinite loop, tried fflush and fgets and scanf
// It will run independently but will loop via the pipe
int main(int a, char**av)
{
char store[BUFSIZE];
memset(store, '\0', sizeof(store));
while (strcmp(store, "exit!\n") != 0)
{
perror("Please enter next line of input (type 'exit!' to stop) \n"); //This repeats itself infinitely
fgets(store, BUFSIZE, stdin);
printf("%s", store); // This also repeats itself dependant on where i put
// fflush or another printf. Repeated outputs occur in blocks
}
return 0;
}
顺便说一句,memset
,在这种情况下是无用的,因为fgets
完成了所有的工作,但无论如何,如果希望将缓冲区设置为nul,只需声明:
char store[BUFSIZE] = {0};
使用fgets
的最佳解决方案是(显然)始终管理左边的换行符:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define BUFSIZE 256
//This program is causing infinite loop, tried fflush and fgets and scanf
// It will run independently but will loop via the pipe
int main(void)
{
char store[BUFSIZE] = {0};
char *pos;
while (strcmp(store, "exit!") != 0)
{
perror("Please enter next line of input (type 'exit!' to stop) \n"); //This repeats itself infinitely
fgets(store, BUFSIZE, stdin);
if ((pos = strchr(store, '\n')) != NULL)
*pos = '\0';
else
fprintf(stderr, "String too long!\n");
printf("%s", store); // This also repeats itself dependant on where i put
// fflush or another printf. Repeated outputs occur in blocks
}
return 0;
}
#包括
#包括
#包括
#定义bufsize256
//该程序正在导致无限循环,包括fflush、fgets和scanf
//它将独立运行,但将通过管道循环
内部主(空)
{
字符存储[BUFSIZE]={0};
char*pos;
while(strcmp(存储,“退出!”)!=0)
{
perror(“请输入下一行输入(输入'exit!'停止)\n”);//这会无限重复
fgets(商店、布袋大小、标准尺寸);
if((pos=strchr(存储,'\n'))!=NULL)
*pos='\0';
其他的
fprintf(stderr,“字符串太长!\n”);
printf(“%s”,store);//这也会根据我放置的位置重复
//fflush或其他printf。重复输出以块形式出现
}
返回0;
}
memset(store,'/0',sizeof(store));
--->memset(store,'\0',sizeof(store));
谢谢,我在代码中已经有了它,但我必须避免在帖子中输入错误。我现在编辑了它,再次感谢!注意perror()
用于根据errno
的值在标准错误上打印错误消息-这不是一个通用提示功能。Jonathan,我使用perror是因为管道,使用使用stdout的函数只需将其发送到下一个程序/文件。但是,我会寻找替代方法,因为该程序仍然是mass打印perror&Outputs正常的替代方法是fprintf(stderr,…)
@JonathanLeffler你比我的拼写检查器快;)ThxHi伙计们,还是不走运。fgets允许我现在键入输入,但当我键入exit时!问题再次出现。如果我添加“exit”\n"对于c2,问题停止了,但它只是不断请求输入,而没有退出循环。我添加了建议的代码。也许这是管道的问题?@rowboat,正如您所看到的,我发布的代码像一个字符一样工作。单独的程序c1.c可以工作,但当通过管道放置时,它会输出重复的行,例如perror和内容当然,我认为这可能是缓冲区溢出或类似的问题。我在测试时注意到了一些事情。c1.c在第一次调用后退出循环,即使没有键入exit!。我认为另一件事是程序可能被错误地管道传输。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define BUFSIZE 256
//This program is causing infinite loop, tried fflush and fgets and scanf
// It will run independently but will loop via the pipe
int main(int a, char**av)
{
char store[BUFSIZE];
memset(store, '\0', sizeof(store));
while (strcmp(store, "exit!\n") != 0)
{
perror("Please enter next line of input (type 'exit!' to stop) \n"); //This repeats itself infinitely
fgets(store, BUFSIZE, stdin);
printf("%s", store); // This also repeats itself dependant on where i put
// fflush or another printf. Repeated outputs occur in blocks
}
return 0;
}
test.c: In function ‘main’:
test.c:242:16: warning: multi-character character constant [-Wmultichar]
memset(store, '/0', sizeof(store));
^
char store[BUFSIZE] = {0};
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define BUFSIZE 256
//This program is causing infinite loop, tried fflush and fgets and scanf
// It will run independently but will loop via the pipe
int main(void)
{
char store[BUFSIZE] = {0};
char *pos;
while (strcmp(store, "exit!") != 0)
{
perror("Please enter next line of input (type 'exit!' to stop) \n"); //This repeats itself infinitely
fgets(store, BUFSIZE, stdin);
if ((pos = strchr(store, '\n')) != NULL)
*pos = '\0';
else
fprintf(stderr, "String too long!\n");
printf("%s", store); // This also repeats itself dependant on where i put
// fflush or another printf. Repeated outputs occur in blocks
}
return 0;
}