ucspi-tcp6 1.13.02
ucspi-tcp6
Loading...
Searching...
No Matches
recordio.c
Go to the documentation of this file.
1#include <unistd.h>
2#include "sig.h"
3#include "buffer.h"
4#include "logmsg.h"
5#include "str.h"
6#include "byte.h"
7#include "exit.h"
8#include "fd.h"
9#include "fmt.h"
10#include "iopause.h"
11#include "pathexec.h"
12
13#define WHO "recordio"
14
15char pid[FMT_ULONG];
16
17char recordbuf[512];
18buffer ssrecord = BUFFER_INIT(write,2,recordbuf,sizeof(recordbuf));
19
20void record(char *buf,int len,char *direction) /* 1 <= len <= 256 */
21{
22 int i;
23
24 while (len) {
25 buffer_puts(&ssrecord,pid);
26 buffer_puts(&ssrecord,direction);
27
28 i = byte_chr(buf,len,'\n');
29 buffer_put(&ssrecord,buf,i);
30
31 if (i == len) {
32 buffer_puts(&ssrecord,"+\n");
33 buffer_flush(&ssrecord);
34 return;
35 }
36
37 buffer_puts(&ssrecord," \n");
38 buffer_flush(&ssrecord);
39 buf += i + 1;
40 len -= i + 1;
41 }
42}
43
44int leftstatus = 0;
45char leftbuf[256];
48
50char rightbuf[256];
53
54void doit(int fdleft,int fdright) /* copy 0 -> fdleft, copy fdright -> 1 */
55{
56 struct taia stamp;
57 struct taia deadline;
58 iopause_fd x[4];
59 int xlen;
60 iopause_fd *io0;
61 iopause_fd *ioleft;
62 iopause_fd *io1;
63 iopause_fd *ioright;
64 int r, riop;
65
66 for (;;) {
67 xlen = 0;
68
69 io0 = 0;
70 if (leftstatus == 0) {
71 io0 = &x[xlen++];
72 io0->fd = 0;
73 io0->events = IOPAUSE_READ;
74 }
75 ioleft = 0;
76 if (leftstatus == 1) {
77 ioleft = &x[xlen++];
78 ioleft->fd = fdleft;
79 ioleft->events = IOPAUSE_WRITE;
80 }
81
82 ioright = 0;
83 if (rightstatus == 0) {
84 ioright = &x[xlen++];
85 ioright->fd = fdright;
86 ioright->events = IOPAUSE_READ;
87 }
88 io1 = 0;
89 if (rightstatus == 1) {
90 io1 = &x[xlen++];
91 io1->fd = 1;
92 io1->events = IOPAUSE_WRITE;
93 }
94
95 taia_now(&stamp);
96 taia_uint(&deadline,3600);
97 taia_add(&deadline,&stamp,&deadline);
98 riop = iopause(x,xlen,&deadline,&stamp);
99
100 if (riop > 0 && io0 && io0->revents) {
101 r = read(0,leftbuf,sizeof(leftbuf));
102 if (r <= 0) {
103 leftstatus = -1;
104 close(fdleft);
105 buffer_puts(&ssrecord,pid);
106 buffer_puts(&ssrecord," < [EOF]\n");
107 buffer_flush(&ssrecord);
108 }
109 else {
110 leftstatus = 1; leftpos = 0; leftlen = r;
111 record(leftbuf,r," < ");
112 }
113 }
114
115 if (ioleft && ioleft->revents) {
116 r = write(fdleft,leftbuf + leftpos,leftlen - leftpos);
117 if (r == -1) break;
118 leftpos += r;
119 if (leftpos == leftlen) leftstatus = 0;
120 }
121
122 if (ioright && ioright->revents) {
123 r = read(fdright,rightbuf,sizeof(rightbuf));
124 if (r <= 0) {
125 buffer_puts(&ssrecord,pid);
126 buffer_puts(&ssrecord," > [EOF]\n");
127 buffer_flush(&ssrecord);
128 break;
129 }
130 rightstatus = 1; rightpos = 0; rightlen = r;
131 record(rightbuf,r," > ");
132 }
133
134 if (io1 && io1->revents) {
136 if (r == -1) break;
137 rightpos += r;
138 if (rightpos == rightlen) rightstatus = 0;
139 }
140 }
141
142 _exit(0);
143}
144
145int main(int argc,char * const *argv,char * const *envp)
146{
147 int piin[2];
148 int piout[2];
149
150 pid[fmt_ulong(pid,getpid())] = 0;
151
152 if (argc < 2) {
153 logmsg(WHO,100,USAGE,"program [ arg ... ]");
154 }
155
156 if (pipe(piin) == -1)
157 logmsg(WHO,111,FATAL,"unable to create pipe");
158 if (pipe(piout) == -1)
159 logmsg(WHO,111,FATAL,"unable to create pipe");
160
161 switch(fork()) {
162 case -1:
163 logmsg(WHO,111,FATAL,"unable to fork");
164 case 0:
165 sig_ignore(sig_pipe);
166 close(piin[0]);
167 close(piout[1]);
168 doit(piin[1],piout[0]);
169 }
170
171 close(piin[1]);
172 close(piout[0]);
173 if (fd_move(0,piin[0]) == -1)
174 logmsg(WHO,111,FATAL,"unable to move descriptors");
175 if (fd_move(1,piout[1]) == -1)
176 logmsg(WHO,111,FATAL,"unable to move descriptors");
177
178 pathexec_run(argv[1],argv + 1,envp);
179 logmsg(WHO,111,FATAL,B("unable to run: ",argv[1]));
180
181 return 111;
182}
int rightpos
Definition: recordio.c:52
char leftbuf[256]
Definition: recordio.c:45
int leftpos
Definition: recordio.c:47
char rightbuf[256]
Definition: recordio.c:50
int rightlen
Definition: recordio.c:51
void record(char *buf, int len, char *direction)
Definition: recordio.c:20
int leftlen
Definition: recordio.c:46
char pid[FMT_ULONG]
Definition: recordio.c:15
void doit(int fdleft, int fdright)
Definition: recordio.c:54
#define WHO
Definition: recordio.c:13
int rightstatus
Definition: recordio.c:49
char recordbuf[512]
Definition: recordio.c:17
int leftstatus
Definition: recordio.c:44
buffer ssrecord
Definition: recordio.c:18
int main()
Definition: addcr.c:4
int pipe(int[2])
int fork()
int read(int, char *, int)
int close(int)
int write(int, char *, int)