source: roaraudio/roarclients/roarclientpass.c @ 5961:06e7fd9e4c25

Last change on this file since 5961:06e7fd9e4c25 was 5961:06e7fd9e4c25, checked in by phi, 10 years ago

Updates of copyright and license headers

File size: 8.0 KB
Line 
1//roarclientpass.c:
2
3/*
4 *      Copyright (C) Philipp 'ph3-der-loewe' Schafft - 2010-2014
5 *
6 *  This file is part of roarclients a part of RoarAudio,
7 *  a cross-platform sound system for both, home and professional use.
8 *  See README for details.
9 *
10 *  This file is free software; you can redistribute it and/or modify
11 *  it under the terms of the GNU General Public License version 3
12 *  as published by the Free Software Foundation.
13 *
14 *  RoarAudio is distributed in the hope that it will be useful,
15 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17 *  GNU General Public License for more details.
18 *
19 *  You should have received a copy of the GNU General Public License
20 *  along with this software; see the file COPYING.  If not, write to
21 *  the Free Software Foundation, 51 Franklin Street, Fifth Floor,
22 *  Boston, MA 02110-1301, USA.
23 *
24 */
25
26/* ckport options:
27 * ckport: ignore-symbol: roar_socket_open of target libroar0 -- Used to get a clientfh.
28 */
29
30#include <roaraudio.h>
31
32void usage (void) {
33 printf("roarclientpass [OPTIONS]...\n");
34
35 printf("\nOptions:\n\n");
36
37 printf("  --server    SERVER    - Set server hostname\n"
38        "  --stdin               - Client is on stdin\n"
39        "  --stdout              - Client is on stdout\n"
40        "  --stdio               - Same as --stdin --stdout\n"
41        "  --stderr              - Client is on stderr\n"
42        "  --client-fh FH        - Client is on FH\n"
43        "  --proto PROTO         - Client uses protocol PROTO (default: RoarAudio)\n"
44        "  --byteorder BO        - Client uses byteorder BO (default: network)\n"
45        "  --listen              - This is a listen mode connection\n"
46        "  --command CMD         - Command to use: passfh or exec (default: passfh)\n"
47        "  --mode MODE           - Set mode of operation: none, listen, connect (default: none)\n"
48        "  --bind BIND           - Set host/node/path for mode listen and connect\n"
49        "  --port PORT           - Set port for mode listen and connect\n"
50//        "  --type TYPE           - Set type for mode listen and connect (default: unknown)\n"
51        "  --help                - Show this help\n"
52       );
53
54}
55
56#define _BV(x) (1<<(x))
57#define F_STDIN  _BV(ROAR_STDIN)
58#define F_STDOUT _BV(ROAR_STDOUT)
59#define F_STDERR _BV(ROAR_STDERR)
60
61int run (int client, int in, int out) {
62 struct roar_vio_calls socks[3];
63 struct roar_vio_select vios[4];
64 int alive = 1;
65 int ret;
66 ssize_t len;
67 char buf[1024];
68 int i;
69
70 roar_vio_open_fh_socket(&(socks[0]), client);
71 roar_vio_open_fh_socket(&(socks[1]), in);
72 roar_vio_open_fh_socket(&(socks[2]), out);
73
74 while (alive) {
75  ROAR_VIO_SELECT_SETVIO(&(vios[0]), &(socks[0]), ROAR_VIO_SELECT_READ);
76  ROAR_VIO_SELECT_SETVIO(&(vios[1]), &(socks[0]), ROAR_VIO_SELECT_WRITE);
77  ROAR_VIO_SELECT_SETVIO(&(vios[2]), &(socks[1]), ROAR_VIO_SELECT_READ);
78  ROAR_VIO_SELECT_SETVIO(&(vios[3]), &(socks[2]), ROAR_VIO_SELECT_WRITE);
79
80  while (1) {
81   ret = roar_vio_select(vios, 4, NULL, NULL);
82
83   if ( ret < 0 )
84    break;
85
86   if ( ret == 0 )
87    continue;
88
89   if ( vios[0].eventsa && vios[3].eventsa )
90    break;
91   if ( vios[1].eventsa && vios[2].eventsa )
92    break;
93
94   for (i = 0; i < 4; i++)
95    if ( vios[i].eventsa )
96     vios[i].eventsq |= ROAR_VIO_SELECT_NO_RETEST;
97  }
98
99  if ( ret < 0 )
100   break;
101
102
103  if ( (vios[0].eventsa & ROAR_VIO_SELECT_READ) && (vios[3].eventsa & ROAR_VIO_SELECT_WRITE) ) {
104   len = roar_vio_read(&(socks[0]), buf, sizeof(buf));
105
106   if ( len < 1 ) {
107    alive = 0;
108   } else {
109    if ( roar_vio_write(&(socks[2]), buf, len) != len )
110     break;
111   }
112  }
113
114  if ( (vios[1].eventsa & ROAR_VIO_SELECT_WRITE) && (vios[2].eventsa & ROAR_VIO_SELECT_READ) ) {
115   len = roar_vio_read(&(socks[1]), buf, sizeof(buf));
116
117   if ( len < 1 ) {
118    alive = 0;
119   } else {
120    if ( roar_vio_write(&(socks[0]), buf, len) != len )
121     break;
122   }
123  }
124 }
125
126 roar_vio_close(&(socks[0]));
127 roar_vio_close(&(socks[1]));
128 roar_vio_close(&(socks[2]));
129
130 return 0;
131}
132
133int main (int argc, char * argv[]) {
134 struct roar_connection    con;
135 struct roar_client        client;
136 const char * server    = NULL;
137 const char * k;
138 int    i;
139 int    clientfh  = -1;
140 int    cflags    = 0;
141 int    flags     = 0;
142 int    proto     = ROAR_PROTO_ROARAUDIO;
143 int    byteorder = ROAR_BYTEORDER_NETWORK;
144 int    mode      = ROAR_SOCKET_MODE_NONE;
145 int    type      = ROAR_SOCKET_TYPE_UNKNOWN;
146 const char * host      = NULL;
147 int    port      = -1;
148 enum {PASSFH, EXEC} command = PASSFH;
149
150 for (i = 1; i < argc; i++) {
151  k = argv[i];
152
153  if ( !strcmp(k, "--server") || !strcmp(k, "-s") ) {
154   ROAR_CKHAVEARGS(1);
155   server = argv[++i];
156  } else if ( !strcmp(k, "--stdin") ) {
157   cflags |= F_STDIN;
158  } else if ( !strcmp(k, "--stdout") ) {
159   cflags |= F_STDOUT;
160  } else if ( !strcmp(k, "--stderr") ) {
161   cflags |= F_STDERR;
162  } else if ( !strcmp(k, "--stdio") ) {
163   cflags |= F_STDIN|F_STDOUT;
164  } else if ( !strcmp(k, "--client-fh") ) {
165   ROAR_CKHAVEARGS(1);
166   clientfh = atoi(argv[++i]);
167  } else if ( !strcmp(k, "--proto") ) {
168   ROAR_CKHAVEARGS(1);
169   proto = roar_str2proto(argv[++i]);
170  } else if ( !strcmp(k, "--byteorder") ) {
171   ROAR_CKHAVEARGS(1);
172   byteorder = roar_str2byteorder(argv[++i]);
173  } else if ( !strcmp(k, "--listen") ) {
174   flags |= ROAR_CLIENTPASS_FLAG_LISTEN;
175  } else if ( !strcmp(k, "--command") ) {
176   ROAR_CKHAVEARGS(1);
177   k = argv[++i];
178   if ( !strcasecmp(k, "passfh") ) {
179    command = PASSFH;
180   } else if ( !strcasecmp(k, "exec") ) {
181    command = EXEC;
182   } else {
183    ROAR_ERR("unknown command: %s", k);
184    return 1;
185   }
186  } else if ( !strcmp(k, "--mode") ) {
187   ROAR_CKHAVEARGS(1);
188   k = argv[++i];
189   if ( !strcasecmp(k, "none") ) {
190    mode = ROAR_SOCKET_MODE_NONE;
191   } else if ( !strcasecmp(k, "listen") ) {
192    mode = ROAR_SOCKET_MODE_LISTEN;
193    flags |= ROAR_CLIENTPASS_FLAG_LISTEN;
194   } else if ( !strcasecmp(k, "connect") ) {
195    mode = ROAR_SOCKET_MODE_CONNECT;
196    flags |= ROAR_CLIENTPASS_FLAG_LISTEN;
197    flags -= ROAR_CLIENTPASS_FLAG_LISTEN;
198   } else {
199    ROAR_ERR("unknown mode: %s", k);
200    return 1;
201   }
202  } else if ( !strcmp(k, "--bind") ) {
203   ROAR_CKHAVEARGS(1);
204   host = argv[++i];
205  } else if ( !strcmp(k, "--port") ) {
206   ROAR_CKHAVEARGS(1);
207   port = atoi(argv[++i]);
208  } else if ( !strcmp(k, "--help") || !strcmp(k, "-h") ) {
209   usage();
210   return 0;
211  } else {
212   ROAR_ERR("unknown argument: %s", k);
213   usage();
214   return 1;
215  }
216 }
217
218 if ( cflags & F_STDERR ) {
219#ifdef ROAR_HAVE_SYSLOG
220  roar_debug_set_stderr_mode(ROAR_DEBUG_MODE_SYSLOG);
221#else
222  roar_debug_set_stderr_vio(roar_stderr);
223#endif
224 } else {
225  roar_debug_set_stderr_vio(roar_stderr);
226 }
227
228 if ( mode != ROAR_SOCKET_MODE_NONE ) {
229  if ( clientfh != -1 ) {
230   ROAR_ERR("Too may socket types given");
231   return 30;
232  }
233
234  if ( host == NULL ) {
235   ROAR_ERR("No bind address given. Use --bind.");
236   return 33;
237  }
238
239  clientfh = roar_socket_open(mode, type, host, port);
240
241  if ( clientfh == -1 ) {
242   ROAR_ERR("Unabled to open socket");
243   return 31;
244  }
245 }
246
247 if ( clientfh == -1 ) {
248  if ( cflags & F_STDIN ) {
249   clientfh = ROAR_STDIN;
250  } else if ( cflags & F_STDOUT ) {
251   clientfh = ROAR_STDOUT;
252  } else if ( cflags & F_STDERR ) {
253   clientfh = ROAR_STDERR;
254  } else {
255   ROAR_ERR("No client socket given");
256   return 32;
257  }
258 }
259
260 roar_client_new(&client);
261 roar_client_set_proto(&client, proto, byteorder);
262
263 if ( command != EXEC )
264  roar_client_set_fh(&client, clientfh);
265
266 if ( roar_simple_connect(&con, server, "roarclientpass") == -1 ) {
267  ROAR_ERR("Can not connect to server");
268  return 10;
269 }
270
271 switch (command) {
272  case PASSFH:
273    if ( roar_client_pass(&con, &client, flags) == -1 ) {
274     ROAR_ERR("Can not pass client fh to server");
275     roar_disconnect(&con);
276     return 20;
277    }
278   break;
279  case EXEC:
280    if ( roar_client_exec(&con, &client, flags) == -1 ) {
281     ROAR_ERR("Can not exec client on server");
282     roar_disconnect(&con);
283     return 20;
284    }
285
286    if ( run(client.fh, clientfh, cflags & F_STDOUT ? ROAR_STDOUT : clientfh) == -1 ) {
287     ROAR_ERR("Can not run data copy runner");
288     return 20;
289    }
290
291    return 0;
292   break;
293 }
294
295 roar_disconnect(&con);
296
297 return 0;
298}
299
300//ll
Note: See TracBrowser for help on using the repository browser.