static void launch_read_stream_thread(shout_context_t *context) { switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; int sanity = 10; size_t used; context->thread_running = 1; switch_threadattr_create(&thd_attr, context->memory_pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, read_stream_thread, context, context->memory_pool); while (context->thread_running && --sanity) { /* at least 1s of audio and up to 5s initialize */ switch_mutex_lock(context->audio_mutex); used = switch_buffer_inuse(context->audio_buffer); switch_mutex_unlock(context->audio_mutex); if (used >= (2 * context->samplerate)) { break; } switch_yield(500000); } }
/** * Create a new graylog2 delivery thread * @param pool to use */ static void start_deliver_graylog2_thread(switch_memory_pool_t *pool) { switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; switch_threadattr_create(&thd_attr, pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, deliver_graylog2_thread, NULL, pool); }
static void launch_monitor_thread(xml_binding_t *binding) { switch_threadattr_t *thd_attr = NULL; switch_threadattr_create(&thd_attr, globals.pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_threadattr_priority_set(thd_attr, SWITCH_PRI_IMPORTANT); switch_thread_create(&binding->thread, thd_attr, monitor_thread_run, binding, globals.pool); }
static void launch_modem_thread(modem_t *modem) { switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; switch_threadattr_create(&thd_attr, globals.pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, modem_thread, modem, globals.pool); }
switch_status_t go_up(virtual_ip_t *vip) { switch_threadattr_t *thd_attr = NULL; vip->state = ST_START; switch_threadattr_create(&thd_attr, globals.pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_threadattr_priority_increase(thd_attr); switch_thread_create(&(vip->virtual_ip_thread), thd_attr, vip_thread, vip, globals.pool); //TODO start sofia profile? return SWITCH_STATUS_SUCCESS; }
/* launch an input thread for the call leg */ void conference_loop_launch_input(conference_member_t *member, switch_memory_pool_t *pool) { switch_threadattr_t *thd_attr = NULL; if (member == NULL || member->input_thread) return; switch_threadattr_create(&thd_attr, pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); conference_utils_member_set_flag_locked(member, MFLAG_ITHREAD); if (switch_thread_create(&member->input_thread, thd_attr, conference_loop_input, member, pool) != SWITCH_STATUS_SUCCESS) { conference_utils_member_clear_flag_locked(member, MFLAG_ITHREAD); } }
bool AsyncIOServer::Start( switch_memory_pool_t *pool, int iThreadCount, const char *ip, switch_port_t port ) { bool bFlag = false; switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "AsyncIOServer::Start( " "iThreadCount : %d, " "ip : %s, " "port : %d " ") \n", iThreadCount, ip, port ); mRunning = true; mpPool = pool; mThreadCount = iThreadCount; // 创建处理队列 switch_queue_create(&mpHandleQueue, SWITCH_CORE_QUEUE_LEN, mpPool); // 创建处理线程 switch_threadattr_t *thd_handle_attr = NULL; switch_threadattr_create(&thd_handle_attr, mpPool); switch_threadattr_detach_set(thd_handle_attr, 1); switch_threadattr_stacksize_set(thd_handle_attr, SWITCH_THREAD_STACKSIZE); switch_threadattr_priority_set(thd_handle_attr, SWITCH_PRI_IMPORTANT); mpHandleThreads = (switch_thread_t**)switch_core_alloc(mpPool, mThreadCount * sizeof(switch_thread_t*)); for(int i = 0; i < mThreadCount; i++) { switch_thread_create(&mpHandleThreads[i], thd_handle_attr, ws_handle_thread, this, mpPool); } // 开始监听socket bFlag = mTcpServer.Start(mpPool, ip, port); if( bFlag ) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "AsyncIOServer::Start( success ) \n"); } else { Stop(); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "AsyncIOServer::Start( fail ) \n"); } return bFlag; }
static void do_config(switch_bool_t reload) { switch_xml_t xml = NULL, x_lists = NULL, x_list = NULL, cfg = NULL; if ((xml = switch_xml_open_cfg("hash.conf", &cfg, NULL))) { if ((x_lists = switch_xml_child(cfg, "remotes"))) { for (x_list = switch_xml_child(x_lists, "remote"); x_list; x_list = x_list->next) { const char *name = switch_xml_attr(x_list, "name"); const char *host = switch_xml_attr(x_list, "host"); const char *szport = switch_xml_attr(x_list, "port"); const char *username = switch_xml_attr(x_list, "username"); const char *password = switch_xml_attr(x_list, "password"); const char *szinterval = switch_xml_attr(x_list, "interval"); uint16_t port = 0; int interval = 0; limit_remote_t *remote; switch_threadattr_t *thd_attr = NULL; if (reload) { switch_thread_rwlock_rdlock(globals.remote_hash_rwlock); if (switch_core_hash_find(globals.remote_hash, name)) { switch_thread_rwlock_unlock(globals.remote_hash_rwlock); continue; } switch_thread_rwlock_unlock(globals.remote_hash_rwlock); } if (!zstr(szport)) { port = (uint16_t)atoi(szport); } if (!zstr(szinterval)) { interval = atoi(szinterval); } remote = limit_remote_create(name, host, port, username, password, interval); remote->state = REMOTE_DOWN; switch_threadattr_create(&thd_attr, remote->pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&remote->thread, thd_attr, limit_remote_thread, remote, remote->pool); } } switch_xml_free(xml); } }
switch_status_t rollback(virtual_ip_t * vip) { switch_status_t status = SWITCH_STATUS_SUCCESS; if (vip->node_list->nodeid != vip->node_id) { switch_threadattr_t *thd_attr = NULL; vip->rollback_node_id = vip->node_list->nodeid; vip->state = ST_RBACK; switch_threadattr_create(&thd_attr, globals.pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_threadattr_priority_increase(thd_attr); status = switch_thread_create(&(vip->rollback_thread), thd_attr, rollback_thread, vip, globals.pool); } return status; }
static switch_status_t handle_msg_bgapi(listener_t *listener, erlang_msg * msg, int arity, ei_x_buff * buf, ei_x_buff * rbuf) { char api_cmd[MAXATOMLEN]; char arg[ARGLEN]; if (arity < 3 || ei_decode_atom(buf->buff, &buf->index, api_cmd) || ei_decode_string_or_binary(buf->buff, &buf->index, ARGLEN - 1, arg)) { ei_x_encode_tuple_header(rbuf, 2); ei_x_encode_atom(rbuf, "error"); ei_x_encode_atom(rbuf, "badarg"); } else { struct api_command_struct *acs = NULL; switch_memory_pool_t *pool; switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; switch_uuid_t uuid; switch_core_new_memory_pool(&pool); acs = switch_core_alloc(pool, sizeof(*acs)); switch_assert(acs); acs->pool = pool; acs->listener = listener; acs->api_cmd = switch_core_strdup(acs->pool, api_cmd); acs->arg = switch_core_strdup(acs->pool, arg); acs->bg = 1; acs->pid = msg->from; switch_threadattr_create(&thd_attr, acs->pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_uuid_get(&uuid); switch_uuid_format(acs->uuid_str, &uuid); switch_thread_create(&thread, thd_attr, api_exec, acs, acs->pool); ei_x_encode_tuple_header(rbuf, 2); ei_x_encode_atom(rbuf, "ok"); _ei_x_encode_string(rbuf, acs->uuid_str); } return SWITCH_STATUS_SUCCESS; }
SWITCH_DECLARE(switch_status_t) switch_log_init(switch_memory_pool_t *pool, switch_bool_t colorize) { switch_threadattr_t *thd_attr;; switch_assert(pool != NULL); LOG_POOL = pool; switch_threadattr_create(&thd_attr, LOG_POOL); switch_threadattr_detach_set(thd_attr, 1); switch_queue_create(&LOG_QUEUE, SWITCH_CORE_QUEUE_LEN, LOG_POOL); #ifdef SWITCH_LOG_RECYCLE switch_queue_create(&LOG_RECYCLE_QUEUE, SWITCH_CORE_QUEUE_LEN, LOG_POOL); #endif switch_mutex_init(&BINDLOCK, SWITCH_MUTEX_NESTED, LOG_POOL); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, log_thread, NULL, LOG_POOL); while (!THREAD_RUNNING) { switch_cond_next(); } if (colorize) { #ifdef WIN32 hStdout = GetStdHandle(STD_OUTPUT_HANDLE); if (switch_core_get_console() == stdout && hStdout != INVALID_HANDLE_VALUE && GetConsoleScreenBufferInfo(hStdout, &csbiInfo)) { wOldColorAttrs = csbiInfo.wAttributes; COLORIZE = SWITCH_TRUE; } #else COLORIZE = SWITCH_TRUE; #endif } return SWITCH_STATUS_SUCCESS; }
static void launch_write_stream_thread(shout_context_t *context) { switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; int sanity = 10; if (context->err) { return; } context->thread_running = 1; switch_threadattr_create(&thd_attr, context->memory_pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, write_stream_thread, context, context->memory_pool); while (context->thread_running && context->thread_running != 2) { switch_yield(100000); if (!--sanity) break; } }
int py_thread(const char *text) { switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; switch_memory_pool_t *pool; struct switch_py_thread *pt; switch_core_new_memory_pool(&pool); assert(pool != NULL); pt = switch_core_alloc(pool, sizeof(*pt)); assert(pt != NULL); pt->pool = pool; pt->args = switch_core_strdup(pt->pool, text); switch_threadattr_create(&thd_attr, pt->pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, py_thread_run, pt, pt->pool); return 0; }
switch_status_t mod_amqp_logging_create(char *name, switch_xml_t cfg) { mod_amqp_logging_profile_t *profile = NULL; switch_xml_t params, param, connections, connection; switch_threadattr_t *thd_attr = NULL; char *exchange = NULL, *exchange_type = NULL; int exchange_durable = 1; /* durable */ switch_memory_pool_t *pool; if (switch_core_new_memory_pool(&pool) != SWITCH_STATUS_SUCCESS) { goto err; } profile = switch_core_alloc(pool, sizeof(mod_amqp_logging_profile_t)); profile->pool = pool; profile->name = switch_core_strdup(profile->pool, name); profile->running = 1; profile->conn_root = NULL; profile->conn_active = NULL; profile->log_level_mask = 0; profile->send_queue_size = 5000; if ((params = switch_xml_child(cfg, "params")) != NULL) { for (param = switch_xml_child(params, "param"); param; param = param->next) { char *var = (char *) switch_xml_attr_soft(param, "name"); char *val = (char *) switch_xml_attr_soft(param, "value"); if (!var) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Profile[%s] param missing 'name' attribute\n", profile->name); continue; } if (!val) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Profile[%s] param[%s] missing 'value' attribute\n", profile->name, var); continue; } if (!strncmp(var, "reconnect_interval_ms", 21)) { int interval = atoi(val); if ( interval && interval > 0 ) { profile->reconnect_interval_ms = interval; } } else if (!strncmp(var, "send_queue_size", 15)) { int interval = atoi(val); if ( interval && interval > 0 ) { profile->send_queue_size = interval; } } else if (!strncmp(var, "exchange-type", 13)) { exchange_type = switch_core_strdup(profile->pool, val); } else if (!strncmp(var, "exchange-name", 13)) { exchange = switch_core_strdup(profile->pool, val); } else if (!strncmp(var, "exchange-durable", 16)) { exchange_durable = switch_true(val); } else if (!strncmp(var, "log-levels", 10)) { profile->log_level_mask = switch_log_str2mask(val); } } /* params for loop */ } /* Handle defaults of string types */ profile->exchange = exchange ? exchange : switch_core_strdup(profile->pool, "TAP.Events"); profile->exchange_type = exchange_type ? exchange_type : switch_core_strdup(profile->pool, "topic"); profile->exchange_durable = exchange_durable; if ((connections = switch_xml_child(cfg, "connections")) != NULL) { for (connection = switch_xml_child(connections, "connection"); connection; connection = connection->next) { if ( ! profile->conn_root ) { /* Handle first root node */ if (mod_amqp_connection_create(&(profile->conn_root), connection, profile->pool) != SWITCH_STATUS_SUCCESS) { /* Handle connection create failure */ switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Profile[%s] failed to create connection\n", profile->name); continue; } profile->conn_active = profile->conn_root; } else { if (mod_amqp_connection_create(&(profile->conn_active->next), connection, profile->pool) != SWITCH_STATUS_SUCCESS) { /* Handle connection create failure */ switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Profile[%s] failed to create connection\n", profile->name); continue; } profile->conn_active = profile->conn_active->next; } } } profile->conn_active = NULL; if ( mod_amqp_connection_open(profile->conn_root, &(profile->conn_active), profile->name, profile->custom_attr) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Profile[%s] was unable to connect to any connection\n", profile->name); goto err; } amqp_exchange_declare(profile->conn_active->state, 1, amqp_cstring_bytes(profile->exchange), amqp_cstring_bytes(profile->exchange_type), 0, /* passive */ profile->exchange_durable, amqp_empty_table); if (mod_amqp_log_if_amqp_error(amqp_get_rpc_reply(profile->conn_active->state), "Declaring exchange")) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Profile[%s] failed to create exchange\n", profile->name); goto err; } /* Create a bounded FIFO queue for sending messages */ if (switch_queue_create(&(profile->send_queue), profile->send_queue_size, profile->pool) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cannot create send queue of size %d!\n", profile->send_queue_size); goto err; } /* Start the event send thread. This will set up the initial connection */ switch_threadattr_create(&thd_attr, profile->pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); if (switch_thread_create(&profile->logging_thread, thd_attr, mod_amqp_logging_thread, profile, profile->pool)) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cannot create 'amqp event sender' thread!\n"); goto err; } if ( switch_core_hash_insert(globals.logging_hash, name, (void *) profile) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to insert new profile [%s] into mod_amqp profile hash\n", name); goto err; } switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Profile[%s] Successfully started\n", profile->name); return SWITCH_STATUS_SUCCESS; err: /* Cleanup */ mod_amqp_logging_destroy(&profile); return SWITCH_STATUS_GENERR; }
switch_status_t mod_amqp_command_create(char *name, switch_xml_t cfg) { mod_amqp_command_profile_t *profile = NULL; switch_xml_t params, param, connections, connection; switch_threadattr_t *thd_attr = NULL; switch_memory_pool_t *pool; char *exchange = NULL, *binding_key = NULL, *queue = NULL; if (switch_core_new_memory_pool(&pool) != SWITCH_STATUS_SUCCESS) { goto err; } profile = switch_core_alloc(pool, sizeof(mod_amqp_command_profile_t)); profile->pool = pool; profile->name = switch_core_strdup(profile->pool, name); profile->running = 1; profile->reconnect_interval_ms = 1000; if ((params = switch_xml_child(cfg, "params")) != NULL) { for (param = switch_xml_child(params, "param"); param; param = param->next) { char *var = (char *) switch_xml_attr_soft(param, "name"); char *val = (char *) switch_xml_attr_soft(param, "value"); if (!var) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Profile[%s] param missing 'name' attribute\n", profile->name); continue; } if (!val) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Profile[%s] param[%s] missing 'value' attribute\n", profile->name, var); continue; } if (!strncmp(var, "reconnect_interval_ms", 21)) { int interval = atoi(val); if ( interval && interval > 0 ) { profile->reconnect_interval_ms = interval; } } else if (!strncmp(var, "exchange-name", 13)) { exchange = switch_core_strdup(profile->pool, val); } else if (!strncmp(var, "queue-name", 10)) { queue = switch_core_strdup(profile->pool, val); } else if (!strncmp(var, "binding_key", 11)) { binding_key = switch_core_strdup(profile->pool, val); } } } /* Handle defaults of string types */ profile->exchange = exchange ? exchange : switch_core_strdup(profile->pool, "TAP.Commands"); profile->queue = queue ? queue : NULL; profile->binding_key = binding_key ? binding_key : switch_core_strdup(profile->pool, "commandBindingKey"); if ((connections = switch_xml_child(cfg, "connections")) != NULL) { for (connection = switch_xml_child(connections, "connection"); connection; connection = connection->next) { if ( ! profile->conn_root ) { /* Handle first root node */ if (mod_amqp_connection_create(&(profile->conn_root), connection, profile->pool) != SWITCH_STATUS_SUCCESS) { /* Handle connection create failure */ switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Profile[%s] failed to create connection\n", profile->name); continue; } profile->conn_active = profile->conn_root; } else { if (mod_amqp_connection_create(&(profile->conn_active->next), connection, profile->pool) != SWITCH_STATUS_SUCCESS) { /* Handle connection create failure */ switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Profile[%s] failed to create connection\n", profile->name); continue; } profile->conn_active = profile->conn_active->next; } } } profile->conn_active = NULL; /* We are not going to open the command queue connection on create, but instead wait for the running thread to open it */ /* Start the worker threads */ switch_threadattr_create(&thd_attr, profile->pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); if (switch_thread_create(&profile->command_thread, thd_attr, mod_amqp_command_thread, profile, profile->pool)) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cannot create 'amqp event sender' thread!\n"); goto err; } if ( switch_core_hash_insert(globals.command_hash, name, (void *) profile) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to insert new profile [%s] into mod_amqp profile hash\n", name); goto err; } return SWITCH_STATUS_SUCCESS; err: /* Cleanup */ mod_amqp_command_destroy(&profile); return SWITCH_STATUS_GENERR; }
static switch_status_t portaudio_stream_file_open(switch_file_handle_t *handle, const char *path) { portaudio_stream_context_t *context; portaudio_stream_source_t *source; switch_memory_pool_t *pool; switch_status_t status = SWITCH_STATUS_FALSE; switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; uint32_t rate = PREFERRED_RATE; char *npath; int devNumber; int tmp; handle->pre_buffer_datalen = 0; if (switch_test_flag(handle, SWITCH_FILE_FLAG_WRITE)) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "This format does not support writing! (yet)\n"); return status; } npath = switch_core_strdup(module_pool, path); tmp = handle->samplerate; if (tmp == 8000 || tmp == 16000 || tmp == 32000 || tmp == 48000) { rate = tmp; } if (*path == '#') { devNumber = get_dev_by_number(npath + 1, 1); } else { devNumber = get_dev_by_name(npath, 1); } npath = switch_mprintf("device-%d at %d", devNumber, rate); switch_mutex_lock(globals.mutex); source = switch_core_hash_find(globals.source_hash, npath); /* dev isnt there, try to start thread */ if (!source) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, " source isnt Created, create and start thread!\n"); if (switch_core_new_memory_pool(&pool) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, " :S no pool\n"); } else { source = switch_core_alloc(pool, sizeof(*source)); if (source != NULL) { source->pool = pool; source->sourcedev = devNumber; source->sourcename = switch_core_strdup(source->pool, npath); source->rate = rate; source->interval = 20; source->channels = 1; source->timer_name = "soft"; source->prebuf = DEFAULT_PREBUFFER_SIZE; source->stopped = 0; source->ready = 0; source->samples = switch_samples_per_packet(source->rate, source->interval); switch_mutex_init(&source->mutex, SWITCH_MUTEX_NESTED, source->pool); switch_threadattr_create(&thd_attr, source->pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, read_stream_thread, source, source->pool); } } } switch_mutex_unlock(globals.mutex); switch_yield(1000000); /* dev already engaged */ if (source) { /*wait for source to be ready */ while (source->ready == 0) { switch_yield(100000); } if (switch_thread_rwlock_tryrdlock(source->rwlock) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, " error rwlock !\n"); source = NULL; } } if (source) { status = SWITCH_STATUS_SUCCESS; if ((context = switch_core_alloc(handle->memory_pool, sizeof(*context))) == 0) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, " error allocating context!\n"); status = SWITCH_STATUS_MEMERR; } else { /* everything goes fine at this point */ handle->samples = 0; handle->samplerate = source->rate; handle->channels = 1; handle->format = 0; handle->sections = 0; handle->seekable = 0; handle->speed = 0; handle->private_info = context; handle->interval = source->interval; switch_mutex_init(&context->audio_mutex, SWITCH_MUTEX_NESTED, handle->memory_pool); if (switch_buffer_create_dynamic(&context->audio_buffer, 512, 1024, 0) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Memory Error!\n"); status = SWITCH_STATUS_MEMERR; } else { /* context created... then continue */ context->source = source; context->file = handle->file; context->func = handle->func; context->line = handle->line; context->handle = handle; switch_mutex_lock(source->mutex); context->next = source->context_list; source->context_list = context; source->total++; switch_mutex_unlock(source->mutex); } } } else { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Unknown source %s\n", path); status = SWITCH_STATUS_FALSE; } return status; }
switch_status_t rtmp_tcp_init(rtmp_profile_t *profile, const char *bindaddr, rtmp_io_t **new_io, switch_memory_pool_t *pool) { char *szport; switch_sockaddr_t *sa; switch_threadattr_t *thd_attr = NULL; rtmp_io_tcp_t *io_tcp; io_tcp = (rtmp_io_tcp_t*)switch_core_alloc(pool, sizeof(rtmp_io_tcp_t)); io_tcp->base.pool = pool; io_tcp->ip = switch_core_strdup(pool, bindaddr); *new_io = (rtmp_io_t*)io_tcp; io_tcp->base.profile = profile; io_tcp->base.read = rtmp_tcp_read; io_tcp->base.write = rtmp_tcp_write; io_tcp->base.close = rtmp_tcp_close; io_tcp->base.name = "tcp"; io_tcp->base.address = switch_core_strdup(pool, io_tcp->ip); if ((szport = strchr(io_tcp->ip, ':'))) { *szport++ = '\0'; io_tcp->port = atoi(szport); } else { io_tcp->port = RTMP_DEFAULT_PORT; } if (switch_sockaddr_info_get(&sa, io_tcp->ip, SWITCH_INET, io_tcp->port, 0, pool)) { goto fail; } if (switch_socket_create(&io_tcp->listen_socket, switch_sockaddr_get_family(sa), SOCK_STREAM, SWITCH_PROTO_TCP, pool)) { goto fail; } if (switch_socket_opt_set(io_tcp->listen_socket, SWITCH_SO_REUSEADDR, 1)) { goto fail; } if (switch_socket_opt_set(io_tcp->listen_socket, SWITCH_SO_TCP_NODELAY, 1)) { goto fail; } if (switch_socket_bind(io_tcp->listen_socket, sa)) { goto fail; } if (switch_socket_listen(io_tcp->listen_socket, 10)) { goto fail; } if (switch_socket_opt_set(io_tcp->listen_socket, SWITCH_SO_NONBLOCK, TRUE)) { goto fail; } switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Listening on %s:%u (tcp)\n", io_tcp->ip, io_tcp->port); io_tcp->base.running = 1; if (switch_pollset_create(&io_tcp->pollset, 1000 /* max poll fds */, pool, 0) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "pollset_create failed\n"); goto fail; } switch_socket_create_pollfd(&(io_tcp->listen_pollfd), io_tcp->listen_socket, SWITCH_POLLIN | SWITCH_POLLERR, NULL, pool); if (switch_pollset_add(io_tcp->pollset, io_tcp->listen_pollfd) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "pollset_add failed\n"); goto fail; } switch_mutex_init(&io_tcp->mutex, SWITCH_MUTEX_NESTED, pool); switch_threadattr_create(&thd_attr, pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&io_tcp->thread, thd_attr, rtmp_io_tcp_thread, *new_io, pool); return SWITCH_STATUS_SUCCESS; fail: if (io_tcp->listen_socket) { switch_socket_close(io_tcp->listen_socket); } *new_io = NULL; switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Socket error. Couldn't listen on %s:%u\n", io_tcp->ip, io_tcp->port); return SWITCH_STATUS_FALSE; }
static void launch_thread(const char *name, const char *path, switch_xml_t directory) { local_stream_source_t *source = NULL; switch_memory_pool_t *pool; switch_xml_t param; switch_thread_t *thread; switch_threadattr_t *thd_attr = NULL; if (switch_core_new_memory_pool(&pool) != SWITCH_STATUS_SUCCESS) { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "OH OH no pool\n"); abort(); } source = switch_core_alloc(pool, sizeof(*source)); assert(source != NULL); source->pool = pool; source->name = switch_core_strdup(source->pool, name); source->location = switch_core_strdup(source->pool, path); source->rate = 8000; source->interval = 20; source->channels = 1; source->timer_name = "soft"; source->prebuf = DEFAULT_PREBUFFER_SIZE; source->stopped = 0; source->hup = 0; source->chime_freq = 30; for (param = switch_xml_child(directory, "param"); param; param = param->next) { char *var = (char *) switch_xml_attr_soft(param, "name"); char *val = (char *) switch_xml_attr_soft(param, "value"); if (!strcasecmp(var, "rate")) { int tmp = atoi(val); if (tmp == 8000 || tmp == 12000 || tmp == 16000 || tmp == 24000 || tmp == 32000 || tmp == 48000) { source->rate = tmp; } } else if (!strcasecmp(var, "shuffle")) { source->shuffle = switch_true(val); } else if (!strcasecmp(var, "prebuf")) { int tmp = atoi(val); if (tmp > 0) { source->prebuf = (uint32_t) tmp; } } else if (!strcasecmp(var, "channels")) { int tmp = atoi(val); if (tmp == 1 || tmp == 2) { source->channels = (uint8_t) tmp; } } else if (!strcasecmp(var, "chime-freq")) { int tmp = atoi(val); if (tmp > 1) { source->chime_freq = tmp; } } else if (!strcasecmp(var, "chime-max")) { int tmp = atoi(val); if (tmp > 1) { source->chime_max = tmp; } } else if (!strcasecmp(var, "chime-list")) { char *list_dup = switch_core_strdup(source->pool, val); source->chime_total = switch_separate_string(list_dup, ',', source->chime_list, (sizeof(source->chime_list) / sizeof(source->chime_list[0]))); } else if (!strcasecmp(var, "interval")) { int tmp = atoi(val); if (SWITCH_ACCEPTABLE_INTERVAL(tmp)) { source->interval = tmp; } else { switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Interval must be multiple of 10 and less than %d, Using default of 20\n", SWITCH_MAX_INTERVAL); } } else if (!strcasecmp(var, "timer-name")) { source->timer_name = switch_core_strdup(source->pool, val); } } if (source->chime_max) { source->chime_max *= source->rate; } if (source->chime_total) { source->chime_counter = source->rate * source->chime_freq; } source->samples = switch_samples_per_packet(source->rate, source->interval); switch_mutex_init(&source->mutex, SWITCH_MUTEX_NESTED, source->pool); switch_threadattr_create(&thd_attr, source->pool); switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&thread, thd_attr, read_stream_thread, source, source->pool); }
switch_memory_pool_t *switch_core_memory_init(void) { #ifndef INSTANTLY_DESTROY_POOLS switch_threadattr_t *thd_attr; #endif #ifdef PER_POOL_LOCK apr_allocator_t *my_allocator = NULL; apr_thread_mutex_t *my_mutex; #endif memset(&memory_manager, 0, sizeof(memory_manager)); #ifdef PER_POOL_LOCK if ((apr_allocator_create(&my_allocator)) != APR_SUCCESS) { abort(); } if ((apr_pool_create_ex(&memory_manager.memory_pool, NULL, NULL, my_allocator)) != APR_SUCCESS) { apr_allocator_destroy(my_allocator); my_allocator = NULL; abort(); } if ((apr_thread_mutex_create(&my_mutex, APR_THREAD_MUTEX_NESTED, memory_manager.memory_pool)) != APR_SUCCESS) { abort(); } apr_allocator_mutex_set(my_allocator, my_mutex); apr_pool_mutex_set(memory_manager.memory_pool, my_mutex); apr_allocator_owner_set(my_allocator, memory_manager.memory_pool); apr_pool_tag(memory_manager.memory_pool, "core_pool"); #else apr_pool_create(&memory_manager.memory_pool, NULL); switch_assert(memory_manager.memory_pool != NULL); #endif #ifdef USE_MEM_LOCK switch_mutex_init(&memory_manager.mem_lock, SWITCH_MUTEX_NESTED, memory_manager.memory_pool); #endif #ifdef INSTANTLY_DESTROY_POOLS { void *foo; foo = (void *) (intptr_t) pool_thread; } #else switch_queue_create(&memory_manager.pool_queue, 50000, memory_manager.memory_pool); switch_queue_create(&memory_manager.pool_recycle_queue, 50000, memory_manager.memory_pool); switch_threadattr_create(&thd_attr, memory_manager.memory_pool); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_thread_create(&pool_thread_p, thd_attr, pool_thread, NULL, memory_manager.memory_pool); while (!memory_manager.pool_thread_running) { switch_cond_next(); } #endif return memory_manager.memory_pool; }