От: | Saddam | http://saddam.narod.ru | |
Дата: | 13.03.17 15:45 | ||
Оценка: |
#include <iostream>
#include <fstream>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <vector>
#include <array>
//#include <algorithm>
//#include <functional>
//#include <cctype>
//#include <locale>
#include <string.h>
#include <sys/wait.h>
using namespace std;
void parce(char *s, char delim, std::vector<char *> &CmdList)
{
unsigned int l=strlen(s);
unsigned int i=0;
CmdList.push_back(s);
//while (s[strlen(s)-1]==' ') s[strlen(s)-1]=0;
for (i=0;i<l;i++)
if (s[i]==delim)
{
s[i]=0;
i++;
while (s[i]==' ') {s[i]=0;i++;}
if (strlen(&s[i])) CmdList.push_back(&s[i]);
while (s[strlen(&s[i])-1]==' ') s[strlen(&s[i])-1]=0;
}
}
int main() {
std::filebuf fb;
fb.open ("/home/saddam/Pipe.log",std::ios::out);
std::ostream os(&fb);
std::vector<char *> CmdList;
char cmdLine[1024];
int iChildPID=0, subCount=0;
//cin>>cmdLine;
strcpy(cmdLine,"who | sort | uniq -c | sort -nk1");
//strcpy(cmdLine,"who | sort -nk1");
parce(cmdLine,'|',CmdList);
std::vector<int *> Pipes;
for (unsigned int i=0;i<CmdList.size()-1;i++)
{
int *Pipe=new int[2];
Pipes.push_back(Pipe);
if (0<pipe(Pipes[i]))
{
cout << "Pipe error" << endl;
return errno;
}
os << "Pipe" << i <<": " << Pipes[i][0]<<", "<<Pipes[i][1]<<endl;
}
int fd = 0;
while (!CmdList.empty())
{
std::vector<char *> ParamList;
parce(CmdList.front(),' ',ParamList);
ParamList.push_back(NULL);
if (!(iChildPID=fork()))
{
if (CmdList.size()>1)
{
dup2(Pipes[subCount][1],1);//O_CLOEXEC
close(Pipes[subCount][0]);
Pipes[subCount][1]=1;
os<<getpid()<<" Pipe(>)"<<subCount<<": "<< Pipes[subCount][0]<<", "<<Pipes[subCount][1]<<endl;
}
else
{
fd = open("/home/saddam/result.out", O_CREAT | O_RDWR );
dup2(fd,1);
os<<getpid()<<" File(>)\n";
}
if (subCount)
{
dup2(Pipes[subCount-1][0],0);
Pipes[subCount-1][0]=0;
close(Pipes[subCount-1][1]);
os<<getpid()<<" Pipe(<)"<<subCount-1<<": "<< Pipes[subCount-1][0]<<", "<<Pipes[subCount-1][1]<<endl;
}
if (-1==execvp(CmdList.front(),ParamList.data()))
return errno;
}
subCount++;
cout <<" PID:"<<iChildPID<<" Count:"<<subCount<< endl;
CmdList.erase(CmdList.begin());
}
int status=0;
cout <<"Waiting for "<<subCount<< endl;
int pid ;
for (int i=1;i<subCount;i++)
{
cout <<"Waiting for "<<subCount-i<< endl;
pid=wait(&status);
cout <<"PID: "<<pid<<" terminated \n";
}
close(fd);
cout <<"Master is finished!"<< endl; // prints !!!Hello World!!!
fb.close();
return 0;
}
От: | Masterspline | ||
Дата: | 13.03.17 21:02 | ||
Оценка: | 2 (1) |
Исправленный код | |
| |
В виде патча | |
[сcode] --- old.cpp 2017-03-13 23:59:27.729222560 +0300 +++ main.cpp 2017-03-13 23:59:11.217348891 +0300 @@ -15,13 +15,14 @@ using namespace std; -void parce(char *s, char delim, std::vector<char *> &CmdList) +void parse(char *s, char delim, std::vector<char *> &CmdList) { unsigned int l=strlen(s); unsigned int i=0; CmdList.push_back(s); //while (s[strlen(s)-1]==' ') s[strlen(s)-1]=0; for (i=0;i<l;i++) + { if (s[i]==delim) { s[i]=0; @@ -29,11 +30,12 @@ while (s[i]==' ') {s[i]=0;i++;} if (strlen(&s[i])) CmdList.push_back(&s[i]); while (s[strlen(&s[i])-1]==' ') s[strlen(&s[i])-1]=0; + } } } int main() { std::filebuf fb; — fb.open ("/home/saddam/Pipe.log",std::ios::out); + fb.open ("./Pipe.log",std::ios::out); std::ostream os(&fb); std::vector<char *> CmdList; char cmdLine[1024]; @@ -41,13 +43,13 @@ //cin>>cmdLine; strcpy(cmdLine,"who | sort | uniq -c | sort -nk1"); //strcpy(cmdLine,"who | sort -nk1"); — parce(cmdLine,'|',CmdList); + parse(cmdLine,'|',CmdList); std::vector<int *> Pipes; for (unsigned int i=0;i<CmdList.size()-1;i++) { int *Pipe=new int[2]; Pipes.push_back(Pipe); — if (0<pipe(Pipes[i])) + if ( pipe(Pipes[i]) < 0 ) { cout << "Pipe error" << endl; return errno; @@ -58,7 +60,7 @@ while (!CmdList.empty()) { std::vector<char *> ParamList; — parce(CmdList.front(),' ',ParamList); + parse(CmdList.front(),' ',ParamList); ParamList.push_back(NULL); if (!(iChildPID=fork())) { @@ -71,7 +73,7 @@ } else { — fd = open("/home/saddam/result.out", O_CREAT | O_RDWR ); + fd = open("./result.out", O_CREAT | O_RDWR ); dup2(fd,1); os<<getpid()<<" File(>)\n"; } @@ -82,13 +84,29 @@ close(Pipes[subCount-1][1]); os<<getpid()<<" Pipe(<)"<<subCount-1<<": "<< Pipes[subCount-1][0]<<", "<<Pipes[subCount-1][1]<<endl; } + for( int it = 0; it < Pipes.size(); ++it ) + { + if( it != subCount ) + { + close( close(Pipes[it][0]) ); + close( close(Pipes[it][1]) ); + } + } if (-1==execvp(CmdList.front(),ParamList.data())) + { + std::cerr << "error in execvp: " << strerror(errno) << std::endl; return errno; + } } subCount++; cout <<" PID:"<<iChildPID<<" Count:"<<subCount<< endl; CmdList.erase(CmdList.begin()); } + for( int it = 0; it < Pipes.size(); ++it ) + { + close( close(Pipes[it][0]) ); + close( close(Pipes[it][1]) ); + } int status=0; cout <<"Waiting for "<<subCount<< endl; int pid ; [/сcode] | |
От: | Saddam | http://saddam.narod.ru | |
Дата: | 13.03.17 21:35 | ||
Оценка: |
uniq: ошибка чтения '-'
sort: операция stat завершилась неудачно: -: Неправильный дескриптор файла
sort: операция stat завершилась неудачно: -: Неправильный дескриптор файла
who: ошибка записи: Обрыв канала
PID:2170 Count:1
PID:2171 Count:2
PID:2172 Count:3
PID:2173 Count:4
Waiting for 4
Waiting for 3
PID: 2172 terminated
Waiting for 2
PID: 2173 terminated
Waiting for 1
PID: 2171 terminated
Master is finished!
От: | Masterspline | ||
Дата: | 13.03.17 23:29 | ||
Оценка: | 3 (1) +1 |
Еще раз исправленный код | |
| |
От: | Masterspline | ||
Дата: | 14.03.17 04:39 | ||
Оценка: |
От: | Saddam | http://saddam.narod.ru | |
Дата: | 14.03.17 09:02 | ||
Оценка: |
От: | Saddam | http://saddam.narod.ru | |
Дата: | 14.03.17 10:37 | ||
Оценка: |
#include <iostream>
#include <fstream>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <vector>
#include <string.h>
#include <sys/wait.h>
using namespace std;
void parse(char *s, char delim, std::vector<char *> &CmdList)
{
unsigned int l=strlen(s);
unsigned int i=0;
CmdList.push_back(s);
for (i=0;i<l;i++)
{
if (s[i]==delim)
{
s[i]=0;
i++;
while (s[i]==' ') {s[i]=0;i++;}
if (strlen(&s[i])) CmdList.push_back(&s[i]);
while (s[strlen(&s[i])-1]==' ') s[strlen(&s[i])-1]=0;
}
}
}
int main() {
std::filebuf fb;
fb.open ("./Pipe.log",std::ios::out);
std::ostream os(&fb);
std::vector<char *> CmdList;
char cmdLine[1024];
int iChildPID=0, subCount=0;
//cin>>cmdLine;
strcpy(cmdLine,"who | sort | uniq -c | sort -nk1");
parse(cmdLine,'|',CmdList);
int fd = 0;
int OutPipe[2]={0,0},inFD=STDIN_FILENO;
while (!CmdList.empty())
{
std::vector<char *> ParamList;
parse(CmdList.front(),' ',ParamList);
ParamList.push_back(NULL);
if ( pipe(OutPipe) < 0 )
{
cerr << "Pipe error" << strerror(errno) << endl;
return errno;
}
if (!(iChildPID=fork()))
{
close(OutPipe[0]);
if (dup2(inFD, STDIN_FILENO) == -1) /*read from in_fd */
{
cerr << "child STDIN dup2 error" << strerror(errno) << endl;
return errno;
}
if (dup2(OutPipe[1], STDOUT_FILENO) == -1) /*write to fd[1]*/
{
cerr << "child STDOUT dup2 error" << strerror(errno) << endl;
return errno;
}
else if (close(OutPipe[1]) == -1)
{
cerr << "child CloseFD error" << strerror(errno) << endl;
return errno;
}
if (CmdList.size()==1)
{
fd = open("/home/saddam/result.out", O_CREAT | O_RDWR );
dup2(fd,1);
}
if (-1==execvp(CmdList.front(),ParamList.data()))
{
cerr << "error in execvp: " << strerror(errno) << endl;
return errno;
}
}
close(OutPipe[1]); /* parent executes the rest of commands */
close(inFD);
inFD=OutPipe[0];
subCount++;
cout <<" PID:"<<iChildPID<<" Count:"<<subCount<< endl;
CmdList.erase(CmdList.begin());
}
int status=0;
int pid ;
for (int i=0;i<subCount;i++)
{
cout <<"Waiting for "<<subCount-i<< endl;
pid=wait(&status);
cout <<"PID: "<<pid<<" terminated \n";
}
close(fd);
cout <<"Master is finished!"<< endl; // prints !!!Hello World!!!
fb.close();
return 0;
}