/* * Setup RTSP(S) connection */ static int iptv_rtsp_start ( iptv_mux_t *im, const char *raw, const url_t *u ) { rtsp_priv_t *rp; http_client_t *hc; udp_connection_t *rtp, *rtcp; int r; if (!(hc = http_client_connect(im, RTSP_VERSION_1_0, u->scheme, u->host, u->port, NULL))) return SM_CODE_TUNING_FAILED; if (u->user) hc->hc_rtsp_user = strdup(u->user); if (u->pass) hc->hc_rtsp_pass = strdup(u->pass); if (udp_bind_double(&rtp, &rtcp, "IPTV", "rtp", "rtcp", NULL, 0, NULL, 128*1024, 16384, 4*1024, 4*1024) < 0) { http_client_close(hc); return SM_CODE_TUNING_FAILED; } hc->hc_hdr_received = iptv_rtsp_header; hc->hc_data_received = iptv_rtsp_data; hc->hc_handle_location = 1; /* allow redirects */ hc->hc_rtsp_keep_alive_cmd = RTSP_CMD_GET_PARAMETER; /* start keep alive loop with GET_PARAMETER */ http_client_register(hc); /* register to the HTTP thread */ r = rtsp_setup(hc, u->path, u->query, NULL, ntohs(IP_PORT(rtp->ip)), ntohs(IP_PORT(rtcp->ip))); if (r < 0) { udp_close(rtcp); udp_close(rtp); http_client_close(hc); return SM_CODE_TUNING_FAILED; } rp = calloc(1, sizeof(*rp)); rp->rtcp_info = calloc(1, sizeof(iptv_rtcp_info_t)); rtcp_init(rp->rtcp_info); rp->rtcp_info->connection = rtcp; rp->hc = hc; udp_multirecv_init(&rp->um, IPTV_PKTS, IPTV_PKT_PAYLOAD); rp->path = strdup(u->path ?: ""); rp->query = strdup(u->query ?: ""); im->im_data = rp; im->mm_iptv_fd = rtp->fd; im->mm_iptv_connection = rtp; im->mm_iptv_fd2 = rtcp->fd; im->mm_iptv_connection2 = rtcp; return 0; }
static void create_everything(void) { struct control_tcp *ct; struct control_udp *cu; struct cli *cl; struct timeval tmp_tv; struct timeval redis_start, redis_stop; double redis_diff = 0; if (rtpe_config.kernel_table < 0) goto no_kernel; if (kernel_setup_table(rtpe_config.kernel_table)) { if (rtpe_config.no_fallback) { ilog(LOG_CRIT, "Userspace fallback disallowed - exiting"); exit(-1); } goto no_kernel; } no_kernel: rtpe_poller = poller_new(); if (!rtpe_poller) die("poller creation failed"); dtls_timer(rtpe_poller); if (call_init()) abort(); rwlock_init(&rtpe_config.config_lock); if (rtpe_config.max_sessions < -1) { rtpe_config.max_sessions = -1; } if (rtpe_config.redis_num_threads < 1) { #ifdef _SC_NPROCESSORS_ONLN rtpe_config.redis_num_threads = sysconf( _SC_NPROCESSORS_ONLN ); #endif if (rtpe_config.redis_num_threads < 1) { rtpe_config.redis_num_threads = REDIS_RESTORE_NUM_THREADS; } } ct = NULL; if (rtpe_config.tcp_listen_ep.port) { ct = control_tcp_new(rtpe_poller, &rtpe_config.tcp_listen_ep); if (!ct) die("Failed to open TCP control connection port"); } cu = NULL; if (rtpe_config.udp_listen_ep.port) { interfaces_exclude_port(rtpe_config.udp_listen_ep.port); cu = control_udp_new(rtpe_poller, &rtpe_config.udp_listen_ep); if (!cu) die("Failed to open UDP control connection port"); } rtpe_control_ng = NULL; if (rtpe_config.ng_listen_ep.port) { interfaces_exclude_port(rtpe_config.ng_listen_ep.port); rtpe_control_ng = control_ng_new(rtpe_poller, &rtpe_config.ng_listen_ep, rtpe_config.control_tos); if (!rtpe_control_ng) die("Failed to open UDP control connection port"); } cl = NULL; if (rtpe_config.cli_listen_ep.port) { interfaces_exclude_port(rtpe_config.cli_listen_ep.port); cl = cli_new(rtpe_poller, &rtpe_config.cli_listen_ep); if (!cl) die("Failed to open UDP CLI connection port"); } if (!is_addr_unspecified(&rtpe_config.redis_write_ep.address)) { rtpe_redis_write = redis_new(&rtpe_config.redis_write_ep, rtpe_config.redis_write_db, rtpe_config.redis_write_auth, ANY_REDIS_ROLE, rtpe_config.no_redis_required); if (!rtpe_redis_write) die("Cannot start up without running Redis %s write database! See also NO_REDIS_REQUIRED parameter.", endpoint_print_buf(&rtpe_config.redis_write_ep)); } if (!is_addr_unspecified(&rtpe_config.redis_ep.address)) { rtpe_redis = redis_new(&rtpe_config.redis_ep, rtpe_config.redis_db, rtpe_config.redis_auth, rtpe_redis_write ? ANY_REDIS_ROLE : MASTER_REDIS_ROLE, rtpe_config.no_redis_required); rtpe_redis_notify = redis_new(&rtpe_config.redis_ep, rtpe_config.redis_db, rtpe_config.redis_auth, rtpe_redis_write ? ANY_REDIS_ROLE : MASTER_REDIS_ROLE, rtpe_config.no_redis_required); if (!rtpe_redis || !rtpe_redis_notify) die("Cannot start up without running Redis %s database! See also NO_REDIS_REQUIRED parameter.", endpoint_print_buf(&rtpe_config.redis_ep)); if (!rtpe_redis_write) rtpe_redis_write = rtpe_redis; } daemonize(); wpidfile(); homer_sender_init(&rtpe_config.homer_ep, rtpe_config.homer_protocol, rtpe_config.homer_id); rtcp_init(); // must come after Homer init if (rtpe_redis) { // start redis restore timer gettimeofday(&redis_start, NULL); // restore if (redis_restore(rtpe_redis)) die("Refusing to continue without working Redis database"); // stop redis restore timer gettimeofday(&redis_stop, NULL); // print redis restore duration redis_diff += timeval_diff(&redis_stop, &redis_start) / 1000.0; ilog(LOG_INFO, "Redis restore time = %.0lf ms", redis_diff); } gettimeofday(&rtpe_latest_graphite_interval_start, NULL); timeval_from_us(&tmp_tv, (long long) rtpe_config.graphite_interval*1000000); set_graphite_interval_tv(&tmp_tv); }