Changeset 5377:72f1d48ff502 in roaraudio for libroar/simple.c
- Timestamp:
- 12/23/11 22:09:58 (12 years ago)
- Branch:
- default
- Phase:
- public
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
libroar/simple.c
r5296 r5377 36 36 #include "libroar.h" 37 37 38 static int roar_simple_stream_obj (struct roar_stream * s, uint32_t rate, uint32_t channels, uint32_t bits, uint32_t codec, const char * server, int dir, const char * name, int mixer) _LIBROAR_ATTR_DEPRECATED;38 static int roar_simple_stream_obj (struct roar_stream * s, uint32_t rate, uint32_t channels, uint32_t bits, uint32_t codec, const char * server, int dir, const char * name, int mixer); 39 39 40 40 int roar_simple_connect (struct roar_connection * con, const char * server, const char * name) { … … 136 136 } 137 137 138 int roar_simple_new_stream_obj (struct roar_connection * con, struct roar_stream * s, uint32_t rate, uint32_t channels, uint32_t bits, uint32_t codec, int dir, int mixer) {139 struct roar_libroar_config * config = roar_libroar_get_config();140 char file[80] = {0};141 int fh = -1, listen = -1;142 static int count = 0;143 int type = ROAR_SOCKET_TYPE_UNIX;144 int port = 0;145 #if defined(ROAR_HAVE_IPV4) || defined(ROAR_HAVE_LIBDNET)146 int opt = 1;147 #endif148 #ifdef ROAR_HAVE_IPV4149 struct sockaddr_in socket_addr;150 socklen_t len = sizeof(struct sockaddr_in);151 #else152 struct sockaddr socket_addr;153 socklen_t len = sizeof(struct sockaddr);154 #endif155 #ifdef ROAR_HAVE_SELECT156 int confh;157 fd_set fds;158 struct timeval timeout = {10, 0};159 struct roar_message mes;160 #endif161 #ifdef ROAR_HAVE_UNIX162 int socks[2]; // for socketpair()163 #endif164 165 // make valgrind happy166 memset(&socket_addr, 0, sizeof(socket_addr));167 #ifdef ROAR_HAVE_SELECT168 memset(&mes, 0, sizeof(mes));169 #endif170 171 roar_debug_warn_sysio("roar_simple_new_stream_obj", "roar_vio_simple_new_stream_obj", NULL);172 173 if ( config != NULL ) {174 if ( config->workaround.workarounds & ROAR_LIBROAR_CONFIG_WAS_USE_EXECED ) {175 return roar_simple_new_stream_attachexeced_obj(con, s, rate, channels, bits, codec, dir, mixer);176 }177 }178 179 #ifdef ROAR_HAVE_BSDSOCKETS180 roar_libroar_nowarn();181 if ( getsockname(roar_get_connection_fh(con), (struct sockaddr *)&socket_addr, &len) == -1 ) {182 roar_libroar_warn();183 return -1;184 }185 roar_libroar_warn();186 #else187 return -1;188 #endif189 190 if ( len == 0 ) {191 #ifdef ROAR_OS_OPENBSD192 ROAR_WARN("roar_simple_new_stream_obj(*): Unknown address family: guess AF_UNIX because OS is OpenBSD");193 ((struct sockaddr*)&socket_addr)->sa_family = AF_UNIX;194 #else195 return -1;196 #endif197 }198 199 switch (((struct sockaddr*)&socket_addr)->sa_family) {200 #ifdef ROAR_HAVE_UNIX201 case AF_UNIX: type = ROAR_SOCKET_TYPE_UNIX; break;202 #endif203 #ifdef ROAR_HAVE_IPV4204 case AF_INET: type = ROAR_SOCKET_TYPE_INET; break;205 #endif206 #ifdef ROAR_HAVE_LIBDNET207 case AF_DECnet: type = ROAR_SOCKET_TYPE_DECNET; break;208 #endif209 default:210 return -1;211 break;212 }213 214 if ( type == ROAR_SOCKET_TYPE_DECNET ) {215 if ( roar_socket_get_local_nodename() ) {216 snprintf(file, 24, "%s::roar$TMP%04x%02x", roar_socket_get_local_nodename(), getpid(), count++);217 } else {218 return -1;219 }220 #ifdef ROAR_HAVE_IPV4221 } else {222 strncpy(file, inet_ntoa(socket_addr.sin_addr), sizeof(file) - 1);223 #endif224 }225 226 if ( type != ROAR_SOCKET_TYPE_UNIX ) {227 if ( (listen = roar_socket_listen(type, file, port)) == -1 ) {228 return -1;229 }230 }231 232 if ( type == ROAR_SOCKET_TYPE_INET ) {233 #ifdef ROAR_HAVE_IPV4234 len = sizeof(struct sockaddr_in);235 setsockopt(listen, SOL_SOCKET, SO_REUSEADDR, (void*)&opt, sizeof(int));236 237 if ( getsockname(listen, (struct sockaddr *)&socket_addr, &len) == -1 ) {238 return -1;239 }240 port = ROAR_NET2HOST16(socket_addr.sin_port);241 ROAR_DBG("roar_simple_new_stream_obj(*): port=%i", port);242 #else243 return -1;244 #endif245 } else if ( type == ROAR_SOCKET_TYPE_DECNET ) {246 #ifdef ROAR_HAVE_LIBDNET247 len = sizeof(struct sockaddr_in);248 setsockopt(listen, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(int));249 #else250 return -1;251 #endif252 }253 254 if ( roar_stream_new(s, rate, channels, bits, codec) == -1 ) {255 return -1;256 }257 258 if ( roar_stream_connect(con, s, dir, mixer) == -1 ) {259 return -1;260 }261 262 if ( type != ROAR_SOCKET_TYPE_UNIX ) {263 #ifdef ROAR_HAVE_SELECT264 if ( roar_stream_connect_to_ask(con, s, type, file, port) != -1 ) {265 266 FD_ZERO(&fds);267 FD_SET(listen, &fds);268 269 confh = roar_get_connection_fh(con);270 271 if ( confh != -1 ) {272 FD_SET(confh, &fds);273 }274 275 if ( select((confh > listen ? confh : listen) + 1, &fds, NULL, NULL, &timeout) < 1 ) {276 close(listen);277 278 // we don't need to check the content as we know it failed...279 if ( roar_recv_message(con, &mes, NULL) == -1 )280 return -1;281 282 if ( roar_kick(con, ROAR_OT_STREAM, s->id) == -1 )283 return -1;284 285 return roar_simple_new_stream_attachexeced_obj(con, s, rate, channels, bits, codec, dir, mixer);286 }287 288 if ( FD_ISSET(listen, &fds) ) {289 if ( (fh = accept(listen, NULL, NULL)) != -1 ) {290 /* errr, do we need we any error handling here? */291 }292 293 if ( roar_recv_message(con, &mes, NULL) == -1 ) {294 if ( fh != -1 )295 close(fh);296 fh = -1;297 } else if ( mes.cmd != ROAR_CMD_OK ) {298 if ( fh != -1 )299 close(fh);300 fh = -1;301 }302 } else {303 // we don't need to check the content as we know it failed...304 if ( roar_recv_message(con, &mes, NULL) == -1 ) {305 close(listen);306 return -1;307 }308 309 if ( mes.cmd != ROAR_CMD_OK ) {310 close(listen);311 if ( roar_kick(con, ROAR_OT_STREAM, s->id) == -1 )312 return -1;313 314 return roar_simple_new_stream_attachexeced_obj(con, s, rate, channels, bits, codec, dir, mixer);315 } else { // seems like we have a positive reply. So we retry the listen socket:316 FD_ZERO(&fds);317 FD_SET(listen, &fds);318 timeout.tv_sec = 0;319 timeout.tv_usec = 128000L;320 fh = -1;321 if ( select(listen + 1, &fds, NULL, NULL, &timeout) > 0 ) {322 if ( (fh = accept(listen, NULL, NULL)) == -1 ) {323 close(listen);324 if ( roar_kick(con, ROAR_OT_STREAM, s->id) == -1 )325 return -1;326 327 return roar_simple_new_stream_attachexeced_obj(con, s, rate, channels, bits, codec, dir, mixer);328 }329 }330 }331 }332 }333 334 close(listen);335 #else336 return -1;337 #endif338 } else { // this is type == ROAR_SOCKET_TYPE_UNIX339 #ifdef ROAR_HAVE_UNIX340 if ( socketpair(AF_UNIX, SOCK_STREAM, 0, socks) == -1 ) {341 roar_kick(con, ROAR_OT_STREAM, s->id); // we do not need to check for errors342 // as we return -1 in both whys343 return -1;344 }345 346 if ( roar_stream_passfh(con, s, socks[0]) == -1 ) {347 roar_kick(con, ROAR_OT_STREAM, s->id); // we do not need to check for errors348 // as we return -1 anyway.349 close(socks[0]);350 close(socks[1]);351 return -1;352 }353 354 close(socks[0]);355 fh = socks[1];356 #else357 roar_kick(con, ROAR_OT_STREAM, s->id);358 return -1;359 #endif360 }361 362 /*363 if ( type == ROAR_SOCKET_TYPE_UNIX ) {364 unlink(file);365 }366 */367 368 if ( fh != -1 ) {369 if ( dir == ROAR_DIR_PLAY ) {370 (void)ROAR_SHUTDOWN(fh, SHUT_RD);371 } else if ( dir == ROAR_DIR_MONITOR || dir == ROAR_DIR_RECORD ) {372 (void)ROAR_SHUTDOWN(fh, SHUT_WR);373 }374 }375 376 s->fh = fh;377 378 return fh;379 }380 381 382 138 int roar_simple_play_file(const char * file, const char * server, const char * name) { 383 139 roar_vs_t * vss;
Note: See TracChangeset
for help on using the changeset viewer.