示例#1
0
/* set defaults */
static int jb_framedata_init(struct jb_framedata *framedata, struct ast_jb_conf *jb_conf)
{
	int jb_impl_type = DEFAULT_TYPE;
	/* Initialize defaults */
	framedata->timer_fd = -1;
	memcpy(&framedata->jb_conf, jb_conf, sizeof(*jb_conf));

	/* Figure out implementation type from the configuration implementation string */
	if (!ast_strlen_zero(jb_conf->impl)) {
		if (!strcasecmp(jb_conf->impl, "fixed")) {
			jb_impl_type = AST_JB_FIXED;
		} else if (!strcasecmp(jb_conf->impl, "adaptive")) {
			jb_impl_type = AST_JB_ADAPTIVE;
		} else {
			ast_log(LOG_WARNING, "Unknown Jitterbuffer type %s. Failed to create jitterbuffer.\n", jb_conf->impl);
			return -1;
		}
	}

	if (!(framedata->jb_impl = ast_jb_get_impl(jb_impl_type))) {
		return -1;
	}

	if (!(framedata->timer = ast_timer_open())) {
		return -1;
	}

	framedata->timer_fd = ast_timer_fd(framedata->timer);
	framedata->timer_interval = DEFAULT_TIMER_INTERVAL;
	ast_timer_set_rate(framedata->timer, 1000 / framedata->timer_interval);
	framedata->start_tv = ast_tvnow();

	framedata->jb_obj = framedata->jb_impl->create(&framedata->jb_conf);
	return 0;
}
/* set defaults */
static int jb_framedata_init(struct jb_framedata *framedata, const char *data, const char *value)
{
	int jb_impl_type = DEFAULT_TYPE;

	/* Initialize defaults */
	framedata->timer_fd = -1;
	jb_conf_default(&framedata->jb_conf);
	if (!(framedata->jb_impl = ast_jb_get_impl(jb_impl_type))) {
		return -1;
	}
	if (!(framedata->timer = ast_timer_open())) {
		return -1;
	}
	framedata->timer_fd = ast_timer_fd(framedata->timer);
	framedata->timer_interval = DEFAULT_TIMER_INTERVAL;
	ast_timer_set_rate(framedata->timer, 1000 / framedata->timer_interval);
	framedata->start_tv = ast_tvnow();



	/* Now check user options to see if any of the defaults need to change. */
	if (!ast_strlen_zero(data)) {
		if (!strcasecmp(data, "fixed")) {
			jb_impl_type = AST_JB_FIXED;
		} else if (!strcasecmp(data, "adaptive")) {
			jb_impl_type = AST_JB_ADAPTIVE;
		} else {
			ast_log(LOG_WARNING, "Unknown Jitterbuffer type %s. Failed to create jitterbuffer.\n", data);
			return -1;
		}
		ast_copy_string(framedata->jb_conf.impl, data, sizeof(framedata->jb_conf.impl));
	}

	if (!ast_strlen_zero(value) && strcasecmp(value, "default")) {
		char *parse = ast_strdupa(value);
		int res = 0;
		AST_DECLARE_APP_ARGS(args,
			AST_APP_ARG(max_size);
			AST_APP_ARG(resync_threshold);
			AST_APP_ARG(target_extra);
		);
示例#3
0
struct ast_channel *stasis_app_control_snoop(struct ast_channel *chan,
	enum stasis_app_snoop_direction spy, enum stasis_app_snoop_direction whisper,
	const char *app, const char *app_args, const char *snoop_id)
{
	RAII_VAR(struct stasis_app_snoop *, snoop, NULL, ao2_cleanup);
	struct ast_format_cap *caps;
	pthread_t thread;
	struct ast_assigned_ids assignedids = {
		.uniqueid = snoop_id,
	};

	if (spy == STASIS_SNOOP_DIRECTION_NONE &&
		whisper == STASIS_SNOOP_DIRECTION_NONE) {
		return NULL;
	}

	snoop = ao2_alloc_options(sizeof(*snoop), snoop_destroy, AO2_ALLOC_OPT_LOCK_NOLOCK);
	if (!snoop) {
		return NULL;
	}

	/* Allocate a buffer to store the Stasis application and arguments in */
	snoop->app = ast_str_create(64);
	if (!snoop->app) {
		return NULL;
	}

	ast_str_set(&snoop->app, 0, "%s", app);
	if (!ast_strlen_zero(app_args)) {
		ast_str_append(&snoop->app, 0, ",%s", app_args);
	}

	/* Set up a timer for the Snoop channel so it wakes up at a specific interval */
	snoop->timer = ast_timer_open();
	if (!snoop->timer) {
		return NULL;
	}
	ast_timer_set_rate(snoop->timer, 1000 / SNOOP_INTERVAL);

	/* Determine which signed linear format should be used */
	snoop_determine_format(chan, snoop);

	/* Allocate a Snoop channel and set up various parameters */
	snoop->chan = ast_channel_alloc(1, AST_STATE_UP, "", "", "", "", "", &assignedids, NULL, 0, "Snoop/%s-%08x", ast_channel_uniqueid(chan),
		(unsigned)ast_atomic_fetchadd_int((int *)&chan_idx, +1));
	if (!snoop->chan) {
		return NULL;
	}

	ast_copy_string(snoop->uniqueid, ast_channel_uniqueid(chan), sizeof(snoop->uniqueid));

	/* To keep the channel valid on the Snoop structure until it is destroyed we bump the ref up here */
	ast_channel_ref(snoop->chan);

	ast_channel_tech_set(snoop->chan, &snoop_tech);
	ao2_ref(snoop, +1);
	ast_channel_tech_pvt_set(snoop->chan, snoop);
	ast_channel_set_fd(snoop->chan, 0, ast_timer_fd(snoop->timer));

	/* The format on the Snoop channel will be this signed linear format, and it will never change */
	caps = ast_format_cap_alloc(AST_FORMAT_CAP_FLAG_DEFAULT);
	if (!caps) {
		ast_channel_unlock(snoop->chan);
		ast_hangup(snoop->chan);
		return NULL;
	}
	ast_format_cap_append(caps, snoop->spy_format, 0);
	ast_channel_nativeformats_set(snoop->chan, caps);
	ao2_ref(caps, -1);

	ast_channel_set_writeformat(snoop->chan, snoop->spy_format);
	ast_channel_set_rawwriteformat(snoop->chan, snoop->spy_format);
	ast_channel_set_readformat(snoop->chan, snoop->spy_format);
	ast_channel_set_rawreadformat(snoop->chan, snoop->spy_format);

	ast_channel_unlock(snoop->chan);

	if (spy != STASIS_SNOOP_DIRECTION_NONE) {
		if (snoop_setup_audiohook(chan, AST_AUDIOHOOK_TYPE_SPY, spy, &snoop->spy_direction, &snoop->spy)) {
			ast_hangup(snoop->chan);
			return NULL;
		}

		snoop->spy_samples = ast_format_get_sample_rate(snoop->spy_format) / (1000 / SNOOP_INTERVAL);
		snoop->spy_active = 1;
	}

	/* If whispering is enabled set up the audiohook */
	if (whisper != STASIS_SNOOP_DIRECTION_NONE) {
		if (snoop_setup_audiohook(chan, AST_AUDIOHOOK_TYPE_WHISPER, whisper, &snoop->whisper_direction, &snoop->whisper)) {
			ast_hangup(snoop->chan);
			return NULL;
		}

		snoop->whisper_active = 1;
	}

	/* Create the thread which services the Snoop channel */
	ao2_ref(snoop, +1);
	if (ast_pthread_create_detached_background(&thread, NULL, snoop_stasis_thread, snoop)) {
		ao2_cleanup(snoop);

		/* No other thread is servicing this channel so we can immediately hang it up */
		ast_hangup(snoop->chan);
		return NULL;
	}

	publish_chanspy_message(snoop, 1);

	/* The caller of this has a reference as well */
	return ast_channel_ref(snoop->chan);
}