Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
att
GitHub Repository: att/ast
Path: blob/master/src/cmd/cs/css.c
1808 views
1
/***********************************************************************
2
* *
3
* This software is part of the ast package *
4
* Copyright (c) 1990-2011 AT&T Intellectual Property *
5
* and is licensed under the *
6
* Eclipse Public License, Version 1.0 *
7
* by AT&T Intellectual Property *
8
* *
9
* A copy of the License is available at *
10
* http://www.eclipse.org/org/documents/epl-v10.html *
11
* (with md5 checksum b35adb5213ca9657e911e9befb180842) *
12
* *
13
* Information and Software Systems Research *
14
* AT&T Research *
15
* Florham Park NJ *
16
* *
17
* Glenn Fowler <[email protected]> *
18
* *
19
***********************************************************************/
20
#pragma prototyped
21
/*
22
* Glenn Fowler
23
* AT&T Research
24
*
25
* css - multiplex multiple clients on one filter server
26
*/
27
28
static const char usage[] =
29
"[-?\n@(#)$Id: css (AT&T Research) 1998-05-01 $\n]"
30
USAGE_LICENSE
31
"[+NAME?css - multiplex multiple clients on one connect stream server]"
32
"[+DESCRIPTION?\bcss\b multiplexes multiple clients on one filter server."
33
" A filter server is a process that reads lines from the standard input"
34
" and writes result lines to the standard output. \aconnect-stream\a"
35
" is the connect stream path by which the filter service will be known.]"
36
37
"[t:timeout?The service will exit after a \atime\a period of client"
38
" inactivity.]:[time]"
39
40
"\n"
41
"\nconnect-stream command [ arg ... ]\n"
42
"\n"
43
44
"[+PROTOCOL?A filter service must follow a simple line oriented protocol. All"
45
" client lines are split into arguments and a number is inserted in the"
46
" second argument position. This number, followed by a space, must be"
47
" placed at the beginning of each line written by the filter server for"
48
" the given client request.]"
49
50
"[+SEE ALSO?\bcoshell\b(1), \bcs\b(1), \bss\b(1), \bcs\b(3)]"
51
;
52
53
#include <css.h>
54
#include <ctype.h>
55
#include <error.h>
56
#include <proc.h>
57
58
typedef struct
59
{
60
Csid_t id;
61
int service;
62
} Connection_t;
63
64
typedef struct
65
{
66
Cssdisc_t disc;
67
Proc_t* proc;
68
Sfio_t* tmp;
69
} State_t;
70
71
static char buf[8 * 1024];
72
73
static int
74
acceptf(Css_t* css, Cssfd_t* fp, Csid_t* ip, char** av, Cssdisc_t* disc)
75
{
76
register Connection_t* con;
77
78
NoP(av);
79
if (!(con = newof(0, Connection_t, 1, 0)))
80
return -1;
81
fp->data = con;
82
con->id = *ip;
83
return fp->fd;
84
}
85
86
static int
87
actionf(register Css_t* css, register Cssfd_t* fp, Cssdisc_t* disc)
88
{
89
register State_t* state = (State_t*)disc;
90
register Connection_t* con;
91
register char* s;
92
register char* t;
93
int n;
94
int i;
95
96
switch (fp->status)
97
{
98
case CS_POLL_CLOSE:
99
if (con = (Connection_t*)fp->data)
100
{
101
if (con->service)
102
error(ERROR_SYSTEM|3, "service termination exit");
103
free(con);
104
}
105
return 0;
106
case CS_POLL_READ:
107
con = (Connection_t*)fp->data;
108
if ((n = csread(css->state, fp->fd, buf, sizeof(buf) - 1, CS_LINE)) <= 0)
109
{
110
if (con->service)
111
error(ERROR_SYSTEM|3, "service termination exit");
112
return -1;
113
}
114
buf[n] = 0;
115
for (s = buf; isspace(*s); s++);
116
if (con->service)
117
{
118
for (i = 0; isdigit(*s); i = i * 10 + *s++ - '0');
119
for (; isspace(*s); s++);
120
if (*s && cssfd(css, i, 0))
121
{
122
n -= s - buf;
123
if (cswrite(css->state, i, s, n) != n)
124
cssfd(css, i, CS_POLL_CLOSE);
125
}
126
}
127
else if (*s == '!')
128
{
129
if ((n -= ++s - buf) > 0 && cswrite(css->state, state->proc->wfd, s, n) != n)
130
return -1;
131
}
132
else
133
{
134
for (t = s; *t && !isspace(*t); t++);
135
for (; isspace(*t); t++);
136
if (*s == 'Q' && !*t)
137
{
138
if (con->id.uid == geteuid())
139
error(3, "service quit exit");
140
}
141
else
142
{
143
n = sfprintf(state->tmp, "%-.*s%d %s", t - s, s, fp->fd, t);
144
if (!(s = sfstruse(state->tmp)))
145
return -1;
146
if (cswrite(css->state, state->proc->wfd, s, n) != n)
147
return -1;
148
}
149
}
150
return 1;
151
}
152
return 0;
153
}
154
155
static int
156
exceptf(Css_t* css, unsigned long op, unsigned long arg, Cssdisc_t* disc)
157
{
158
switch (op)
159
{
160
case CSS_INTERRUPT:
161
error(ERROR_SYSTEM|3, "%s: interrupt exit", fmtsignal(arg));
162
return 0;
163
case CSS_DORMANT:
164
error(2, "service dormant exit");
165
exit(0);
166
}
167
error(ERROR_SYSTEM|3, "poll error op=0x%08x arg=0x%08x", op, arg);
168
return -1;
169
}
170
171
172
int
173
main(int argc, char** argv)
174
{
175
Css_t* css;
176
Cssfd_t* fp;
177
Connection_t* con;
178
char* e;
179
State_t state;
180
181
NoP(argc);
182
error_info.id = "css";
183
memset(&state, 0, sizeof(state));
184
state.disc.version = CSS_VERSION;
185
state.disc.flags = CSS_DAEMON|CSS_ERROR|CSS_INTERRUPT;
186
state.disc.acceptf = acceptf;
187
state.disc.actionf = actionf;
188
state.disc.errorf = errorf;
189
state.disc.exceptf = exceptf;
190
for (;;)
191
{
192
switch (optget(argv, usage))
193
{
194
case 't':
195
state.disc.timeout = strelapsed(opt_info.arg, &e, 1);
196
if (*e)
197
error(3, "%s: invalid timeout value", opt_info.arg);
198
state.disc.flags |= CSS_DORMANT;
199
continue;
200
case '?':
201
error(ERROR_USAGE|4, "%s", opt_info.arg);
202
continue;
203
case ':':
204
error(2, "%s", opt_info.arg);
205
continue;
206
}
207
break;
208
}
209
argv += opt_info.index;
210
if (!argv[0] || !argv[1])
211
error(ERROR_USAGE|4, "%s", optusage(NiL));
212
if (!(state.tmp = sfstropen()))
213
error(ERROR_SYSTEM|3, "out of space [tmp stream]");
214
if (!(state.proc = procopen(argv[1], argv + 1, NiL, NiL, PROC_READ|PROC_WRITE)))
215
error(ERROR_SYSTEM|3, "%s: cannot execute", argv[1]);
216
if (!(css = cssopen(argv[0], &state.disc)))
217
return 1;
218
if (!(fp = cssfd(css, state.proc->rfd, CS_POLL_READ)))
219
error(ERROR_SYSTEM|3, "%s: cannot poll output", argv[1]);
220
if (!(con = newof(0, Connection_t, 1, 0)))
221
error(ERROR_SYSTEM|3, "out of space");
222
fp->data = con;
223
con->service = 1;
224
csspoll(CS_NEVER, 0);
225
return 1;
226
}
227
228