ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/i-scream/projects/cms/source/host/c++/socket++-1.10/pipestream.C
Revision: 1.2
Committed: Mon Jun 10 14:10:44 2002 UTC (22 years, 3 months ago) by tdb
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 1.1: +0 -0 lines
State: FILE REMOVED
Error occurred while calculating annotation data.
Log Message:
Tidy up of files. These are all old things that are not only no longer used
but are also probably useless to anyone other than us. This saves checking
them out all the time, and makes the "cms/source" tree contain only current
stuff. They'll still exist in the attic's though :)

File Contents

# Content
1 // pipestream.C -*- C++ -*- socket library
2 // Copyright (C) 1992,1993,1994 Gnanasekaran Swaminathan <gs4t@virginia.edu>
3 //
4 // Permission is granted to use at your own risk and distribute this software
5 // in source and binary forms provided the above copyright
6 // notice and this paragraph are preserved on all copies.
7 // This software is provided "as is" with no express or implied warranty.
8 //
9 // Version: 17Oct95 1.10
10
11
12 #include <config.h>
13
14 #include <pipestream.h>
15 #include <unistd.h>
16 #include <sys/socket.h>
17
18 // environ is not given a declaration in sun's <unistd.h>
19 extern char** environ;
20
21 // child closes s2 and uses s1
22 // parent closes s1 and uses s2
23
24 enum domain { af_unix = 1 };
25
26 iopipestream* iopipestream::head = 0;
27
28 static sockbuf* createpipestream (const char* cmd, int mode)
29 {
30 int sockets[2];
31 if ( ::socketpair (af_unix, sockbuf::sock_stream, 0, sockets) == -1 ) {
32 sock_error ("pipestream", "socketpair");
33 return 0;
34 }
35
36 pid_t pid = vfork ();
37 if (pid == -1) {
38 sock_error ("pipestream", "fork");
39 return 0;
40 }
41
42 if (pid == 0) {
43 // child process
44 if (::close (sockets[1]) == -1)
45 sock_error ("pipestream", "child close 1");
46 if ((mode & ios::in) && ::dup2 (sockets[0], 1) == -1) {
47 sock_error ("pipestream", "child dup2 1");
48 _exit (0x70);
49 }
50 if ((mode & ios::out) && ::dup2 (sockets[0], 0) == -1) {
51 sock_error ("pipestream", "child dup2 0");
52 _exit (0x71);
53 }
54 if (::close (sockets[0]) == -1)
55 sock_error ("pipestream", "child close 0");
56 const char* argv[4];
57 argv[0] = "/bin/sh";
58 argv[1] = "-c";
59 argv[2] = cmd;
60 argv[3] = 0;
61 execve ("/bin/sh", (char**) argv, environ);
62 sock_error ("pipestream", "execve");
63 _exit (0x7f);
64 }
65 // parent process
66 sockbuf* s = new sockbuf (sockets[1]);
67 if (::close (sockets[0]) == -1)
68 sock_error ("pipestream", "parent close 0");
69 if ( !(mode & ios::out) ) s->shutdown (sockbuf::shut_write);
70 if ( !(mode & ios::in) ) s->shutdown (sockbuf::shut_read);
71 return s;
72 }
73
74 ipipestream::ipipestream (const char* cmd)
75 : ios (0)
76 {
77 init (createpipestream (cmd, ios::in));
78 }
79
80 opipestream::opipestream (const char* cmd)
81 : ios (0)
82 {
83 init (createpipestream (cmd, ios::out));
84 }
85
86 iopipestream::iopipestream (const char* cmd)
87 : ios (0), cpid(-1), next (0)
88 {
89 init (createpipestream (cmd, ios::in|ios::out));
90 }
91
92 iopipestream::iopipestream(sockbuf::type ty, int proto)
93 : ios (0), cpid(-1), next (head)
94 {
95 if ( ::socketpair(af_unix, ty, proto, sp) == -1 ) {
96 error ("iopipestream-socketpair ");
97 return;
98 }
99
100 head = this;
101 }
102
103 pid_t iopipestream::fork()
104 {
105 pid_t pid = :: vfork ();
106 if ( pid == -1 ) {
107 sock_error ("iopipestream", "fork");
108 return pid;
109 } else if (pid > 0) {
110 // parent process
111 while (head) {
112 head->cpid = pid;
113 head->init (new sockbuf (head->sp[0]));
114 if (::close (head->sp[1]) == -1)
115 sock_error ("iopipestream", "parent close 0");
116 head = head->next;
117 }
118
119 } else {
120 // child process
121 while (head) {
122 head->cpid = 0;
123 head->init (new sockbuf (head->sp[1]));
124 if (::close (head->sp[0]) == -1)
125 sock_error ("iopipestream", "child close 0");
126 head = head->next;
127 }
128 }
129 return pid;
130 }
131