⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 chan_gtalk.c

📁 Asterisk中信道部分的源码 。。。。
💻 C
📖 第 1 页 / 共 5 页
字号:
	ASTOBJ_UNLOCK(client);	return chan;}/*! \brief CLI command "gtalk show channels" */static int gtalk_show_channels(int fd, int argc, char **argv){#define FORMAT  "%-30.30s  %-30.30s  %-15.15s  %-5.5s %-5.5s \n"	struct gtalk_pvt *p;	struct ast_channel *chan;	int numchans = 0;	char them[AJI_MAX_JIDLEN];	char *jid = NULL;	char *resource = NULL;	if (argc != 3)		return RESULT_SHOWUSAGE;	ast_mutex_lock(&gtalklock);	ast_cli(fd, FORMAT, "Channel", "Jabber ID", "Resource", "Read", "Write");	ASTOBJ_CONTAINER_TRAVERSE(&gtalk_list, 1, {		ASTOBJ_WRLOCK(iterator);		p = iterator->p;		while(p) {			chan = p->owner;			ast_copy_string(them, p->them, sizeof(them));			jid = them;			resource = strchr(them, '/');			if (!resource)				resource = "None";			else {				*resource = '\0';				resource ++;			}			if (chan)				ast_cli(fd, FORMAT, 					chan->name,					jid,					resource,					ast_getformatname(chan->readformat),					ast_getformatname(chan->writeformat)										);			else 				ast_log(LOG_WARNING, "No available channel\n");			numchans ++;			p = p->next;		}		ASTOBJ_UNLOCK(iterator);	});	ast_mutex_unlock(&gtalklock);	ast_cli(fd, "%d active gtalk channel%s\n", numchans, (numchans != 1) ? "s" : "");	return RESULT_SUCCESS;#undef FORMAT}/*! \brief CLI command "gtalk show channels" */static int gtalk_do_reload(int fd, int argc, char **argv){	ast_verbose("IT DOES WORK!\n");	return RESULT_SUCCESS;}static int gtalk_parser(void *data, ikspak *pak){	struct gtalk *client = ASTOBJ_REF((struct gtalk *) data);	if (iks_find_with_attrib(pak->x, "session", "type", "initiate")) {		/* New call */		gtalk_newcall(client, pak);	} else if (iks_find_with_attrib(pak->x, "session", "type", "candidates") || iks_find_with_attrib(pak->x, "session", "type", "transport-info")) {		if (option_debug > 2)			ast_log(LOG_DEBUG, "About to add candidate!\n");		gtalk_add_candidate(client, pak);		if (option_debug > 2)			ast_log(LOG_DEBUG, "Candidate Added!\n");	} else if (iks_find_with_attrib(pak->x, "session", "type", "accept")) {		gtalk_is_answered(client, pak);	} else if (iks_find_with_attrib(pak->x, "session", "type", "transport-accept")) {		gtalk_is_accepted(client, pak);	} else if (iks_find_with_attrib(pak->x, "session", "type", "content-info") || iks_find_with_attrib(pak->x, "gtalk", "action", "session-info")) {		gtalk_handle_dtmf(client, pak);	} else if (iks_find_with_attrib(pak->x, "session", "type", "terminate")) {		gtalk_hangup_farend(client, pak);	} else if (iks_find_with_attrib(pak->x, "session", "type", "reject")) {		gtalk_hangup_farend(client, pak);	}	ASTOBJ_UNREF(client, gtalk_member_destroy);	return IKS_FILTER_EAT;}/* Not using this anymore probably take out soon static struct gtalk_candidate *gtalk_create_candidate(char *args){	char *name, *type, *preference, *protocol;	struct gtalk_candidate *res;	res = malloc(sizeof(struct gtalk_candidate));	memset(res, 0, sizeof(struct gtalk_candidate));	if (args)		name = args;	if ((args = strchr(args, ','))) {		*args = '\0';		args++;		preference = args;	}	if ((args = strchr(args, ','))) {		*args = '\0';		args++;		protocol = args;	}	if ((args = strchr(args, ','))) {		*args = '\0';		args++;		type = args;	}	if (name)		ast_copy_string(res->name, name, sizeof(res->name));	if (preference) {		res->preference = atof(preference);	}	if (protocol) {		if (!strcasecmp("udp", protocol))			res->protocol = AJI_PROTOCOL_UDP;		if (!strcasecmp("ssltcp", protocol))			res->protocol = AJI_PROTOCOL_SSLTCP;	}	if (type) {		if (!strcasecmp("stun", type))			res->type = AJI_CONNECT_STUN;		if (!strcasecmp("local", type))			res->type = AJI_CONNECT_LOCAL;		if (!strcasecmp("relay", type))			res->type = AJI_CONNECT_RELAY;	}	return res;}*/static int gtalk_create_member(char *label, struct ast_variable *var, int allowguest,								struct ast_codec_pref prefs, char *context,								struct gtalk *member){	struct aji_client *client;	if (!member)		ast_log(LOG_WARNING, "Out of memory.\n");	ast_copy_string(member->name, label, sizeof(member->name));	ast_copy_string(member->user, label, sizeof(member->user));	ast_copy_string(member->context, context, sizeof(member->context));	member->allowguest = allowguest;	member->prefs = prefs;	while (var) {#if 0		struct gtalk_candidate *candidate = NULL;#endif		if (!strcasecmp(var->name, "username"))			ast_copy_string(member->user, var->value, sizeof(member->user));		else if (!strcasecmp(var->name, "disallow"))			ast_parse_allow_disallow(&member->prefs, &member->capability, var->value, 0);		else if (!strcasecmp(var->name, "allow"))			ast_parse_allow_disallow(&member->prefs, &member->capability, var->value, 1);		else if (!strcasecmp(var->name, "context"))			ast_copy_string(member->context, var->value, sizeof(member->context));#if 0		else if (!strcasecmp(var->name, "candidate")) {			candidate = gtalk_create_candidate(var->value);			if (candidate) {				candidate->next = member->ourcandidates;				member->ourcandidates = candidate;			}		}#endif		else if (!strcasecmp(var->name, "connection")) {			if ((client = ast_aji_get_client(var->value))) {				member->connection = client;				iks_filter_add_rule(client->f, gtalk_parser, member, 						    IKS_RULE_TYPE, IKS_PAK_IQ, 						    IKS_RULE_FROM_PARTIAL, member->user,						    IKS_RULE_NS, "http://www.google.com/session",						    IKS_RULE_DONE);			} else {				ast_log(LOG_ERROR, "connection referenced not found!\n");				return 0;			}		}		var = var->next;	}	if (member->connection && member->user)		member->buddy = ASTOBJ_CONTAINER_FIND(&member->connection->buddies, member->user);	else {		ast_log(LOG_ERROR, "No Connection or Username!\n");	}	return 1;}static int gtalk_load_config(void){	char *cat = NULL;	struct ast_config *cfg = NULL;	char context[AST_MAX_CONTEXT];	int allowguest = 1;	struct ast_variable *var;	struct gtalk *member;	struct ast_codec_pref prefs;	struct aji_client_container *clients;	struct gtalk_candidate *global_candidates = NULL;	struct hostent *hp;	struct ast_hostent ahp;	cfg = ast_config_load(GOOGLE_CONFIG);	if (!cfg)		return 0;	/* Copy the default jb config over global_jbconf */	memcpy(&global_jbconf, &default_jbconf, sizeof(struct ast_jb_conf));	cat = ast_category_browse(cfg, NULL);	for (var = ast_variable_browse(cfg, "general"); var; var = var->next) {		/* handle jb conf */		if (!ast_jb_read_conf(&global_jbconf, var->name, var->value))			continue;		if (!strcasecmp(var->name, "allowguest"))			allowguest =				(ast_true(ast_variable_retrieve(cfg, "general", "allowguest"))) ? 1 : 0;		else if (!strcasecmp(var->name, "disallow"))			ast_parse_allow_disallow(&prefs, &global_capability, var->value, 0);		else if (!strcasecmp(var->name, "allow"))			ast_parse_allow_disallow(&prefs, &global_capability, var->value, 1);		else if (!strcasecmp(var->name, "context"))			ast_copy_string(context, var->value, sizeof(context));		else if (!strcasecmp(var->name, "bindaddr")) {			if (!(hp = ast_gethostbyname(var->value, &ahp))) {				ast_log(LOG_WARNING, "Invalid address: %s\n", var->value);			} else {				memcpy(&bindaddr.sin_addr, hp->h_addr, sizeof(bindaddr.sin_addr));			}		}/*  Idea to allow for custom candidates  *//*		else if (!strcasecmp(var->name, "candidate")) {			candidate = gtalk_create_candidate(var->value);			if (candidate) {				candidate->next = global_candidates;				global_candidates = candidate;			}		}*/	}	while (cat) {		if (strcasecmp(cat, "general")) {			var = ast_variable_browse(cfg, cat);			member = (struct gtalk *) malloc(sizeof(struct gtalk));			memset(member, 0, sizeof(struct gtalk));			ASTOBJ_INIT(member);			ASTOBJ_WRLOCK(member);			if (!strcasecmp(cat, "guest")) {				ast_copy_string(member->name, "guest", sizeof(member->name));				ast_copy_string(member->user, "guest", sizeof(member->user));				ast_copy_string(member->context, context, sizeof(member->context));				member->allowguest = allowguest;				member->prefs = prefs;				while (var) {					if (!strcasecmp(var->name, "disallow"))						ast_parse_allow_disallow(&member->prefs, &member->capability,												 var->value, 0);					else if (!strcasecmp(var->name, "allow"))						ast_parse_allow_disallow(&member->prefs, &member->capability,												 var->value, 1);					else if (!strcasecmp(var->name, "context"))						ast_copy_string(member->context, var->value,										sizeof(member->context));/*  Idea to allow for custom candidates  *//*					else if (!strcasecmp(var->name, "candidate")) {						candidate = gtalk_create_candidate(var->value);						if (candidate) {							candidate->next = member->ourcandidates;							member->ourcandidates = candidate;						}					}*/					var = var->next;				}				ASTOBJ_UNLOCK(member);				clients = ast_aji_get_clients();				if (clients) {					ASTOBJ_CONTAINER_TRAVERSE(clients, 1, {						ASTOBJ_WRLOCK(iterator);						ASTOBJ_WRLOCK(member);						member->connection = NULL;						iks_filter_add_rule(iterator->f, gtalk_parser, member, IKS_RULE_TYPE, IKS_PAK_IQ, IKS_RULE_NS, "http://www.google.com/session", IKS_RULE_DONE);						iks_filter_add_rule(iterator->f, gtalk_parser, member, IKS_RULE_TYPE, IKS_PAK_IQ, IKS_RULE_NS, "http://jabber.org/protocol/gtalk", IKS_RULE_DONE);						ASTOBJ_UNLOCK(member);						ASTOBJ_UNLOCK(iterator);					});					ASTOBJ_CONTAINER_LINK(&gtalk_list, member);					ASTOBJ_UNREF(member, gtalk_member_destroy);				} else {					ASTOBJ_UNLOCK(member);					ASTOBJ_UNREF(member, gtalk_member_destroy);				}			} else {				ASTOBJ_UNLOCK(member);				if (gtalk_create_member(cat, var, allowguest, prefs, context, member))					ASTOBJ_CONTAINER_LINK(&gtalk_list, member);				ASTOBJ_UNREF(member, gtalk_member_destroy);			}		}		cat = ast_category_browse(cfg, cat);	}	gtalk_free_candidates(global_candidates);	return 1;}/*! \brief Load module into PBX, register channel */static int load_module(void){	char *jabber_loaded = ast_module_helper("", "res_jabber.so", 0, 0, 0, 0);	free(jabber_loaded);	if (!jabber_loaded) {		/* If embedded, check for a different module name */		jabber_loaded = ast_module_helper("", "res_jabber", 0, 0, 0, 0);		free(jabber_loaded);		if (!jabber_loaded) {			ast_log(LOG_ERROR, "chan_gtalk.so depends upon res_jabber.so\n");			return AST_MODULE_LOAD_DECLINE;		}	}#ifdef HAVE_GNUTLS	        gcry_control (GCRYCTL_SET_THREAD_CBS, &gcry_threads_pthread);#endif /* HAVE_GNUTLS */	ASTOBJ_CONTAINER_INIT(&gtalk_list);	if (!gtalk_load_config()) {		ast_log(LOG_ERROR, "Unable to read config file %s. Not loading module.\n", GOOGLE_CONFIG);		return 0;	}	sched = sched_context_create();	if (!sched) 		ast_log(LOG_WARNING, "Unable to create schedule context\n");	io = io_context_create();	if (!io) 		ast_log(LOG_WARNING, "Unable to create I/O context\n");	if (ast_find_ourip(&__ourip, bindaddr)) {		ast_log(LOG_WARNING, "Unable to get own IP address, Gtalk disabled\n");		return 0;	}	ast_rtp_proto_register(&gtalk_rtp);	ast_cli_register_multiple(gtalk_cli, sizeof(gtalk_cli) / sizeof(gtalk_cli[0]));	/* Make sure we can register our channel type */	if (ast_channel_register(&gtalk_tech)) {		ast_log(LOG_ERROR, "Unable to register channel class %s\n", gtalk_tech.type);		return -1;	}	return 0;}/*! \brief Reload module */static int reload(void){	return 0;}/*! \brief Unload the gtalk channel from Asterisk */static int unload_module(void){	struct gtalk_pvt *privates = NULL;	ast_cli_unregister_multiple(gtalk_cli, sizeof(gtalk_cli) / sizeof(gtalk_cli[0]));	/* First, take us out of the channel loop */	ast_channel_unregister(&gtalk_tech);	ast_rtp_proto_unregister(&gtalk_rtp);	if (!ast_mutex_lock(&gtalklock)) {		/* Hangup all interfaces if they have an owner */		ASTOBJ_CONTAINER_TRAVERSE(&gtalk_list, 1, {			ASTOBJ_WRLOCK(iterator);			privates = iterator->p;			while(privates) {				if (privates->owner)					ast_softhangup(privates->owner, AST_SOFTHANGUP_APPUNLOAD);				privates = privates->next;			}			iterator->p = NULL;			ASTOBJ_UNLOCK(iterator);		});		ast_mutex_unlock(&gtalklock);	} else {		ast_log(LOG_WARNING, "Unable to lock the monitor\n");		return -1;	}	ASTOBJ_CONTAINER_DESTROYALL(&gtalk_list, gtalk_member_destroy);	ASTOBJ_CONTAINER_DESTROY(&gtalk_list);	return 0;}AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_DEFAULT, "Gtalk Channel Driver",		.load = load_module,		.unload = unload_module,		.reload = reload,	       );

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -