From 0ce1ae2a366451d6b28c3754abcaec9038402aa4 Mon Sep 17 00:00:00 2001
From: Matteo Brancaleoni <mbrancaleoni@espia.it>
Date: Mon, 10 Mar 2003 20:39:12 +0000
Subject: [PATCH] lun mar 10 21:39:02 CET 2003

git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@638 65c4cc65-6c06-0410-ace0-fbb531ad65f3
---
 astman/Makefile      |  4 ++--
 astman/astman.c      | 44 ++++++++++++++++++++++++++++++++++++++------
 channels/chan_mgcp.c | 20 ++++++++++++++++++++
 channels/chan_sip.c  |  6 ++++++
 channels/chan_zap.c  |  1 +
 utils/astman.c       | 44 ++++++++++++++++++++++++++++++++++++++------
 6 files changed, 105 insertions(+), 14 deletions(-)

diff --git a/astman/Makefile b/astman/Makefile
index 106affcd83..239b11b0e1 100755
--- a/astman/Makefile
+++ b/astman/Makefile
@@ -15,5 +15,5 @@ none:
 clean:
 	rm -f *.o astman
 
-astman: astman.o
-	$(CC) -o astman astman.o -lnewt
+astman: astman.o ../md5.o
+	$(CC) -o astman astman.o ../md5.o -lnewt
diff --git a/astman/astman.c b/astman/astman.c
index 6bda4ff9ce..6fa6b81182 100755
--- a/astman/astman.c
+++ b/astman/astman.c
@@ -20,6 +20,7 @@
 #include <unistd.h>
 #include <stdlib.h>
 
+#include <asterisk/md5.h>
 #include <asterisk/manager.h>
 
 #define MAX_HEADERS 80
@@ -609,18 +610,49 @@ static int login(char *hostname)
 		if (es.u.co == login) {
 			snprintf(tmp, sizeof(tmp), "Logging in '%s'...", user);
 			show_doing("Logging in", tmp);
-			manager_action("Login", 
-				"Username: %s\r\n"
-				"Secret: %s\r\n",
-					user, pass);
+			/* Check to see if the remote host supports MD5 Authentication */
+			manager_action("Challenge", "AuthType: MD5\r\n");
 			m = wait_for_response(10000);
-			hide_doing();
-			if (m) {
+			if (m && !strcasecmp(get_header(m, "Response"), "Success")) {
+				char *challenge = get_header(m, "Challenge");
+				int x;
+				int len = 0;
+				char md5key[256] = "";
+				struct MD5Context md5;
+				unsigned char digest[16];
+				MD5Init(&md5);
+				MD5Update(&md5, challenge, strlen(challenge));
+				MD5Update(&md5, pass, strlen(pass));
+				MD5Final(digest, &md5);
+				for (x=0; x<16; x++)
+					len += sprintf(md5key + len, "%2.2x", digest[x]);
+				manager_action("Login",
+						"AuthType: MD5\r\n"
+						"Username: %s\r\n"
+						"Key: %s\r\n",
+						user, md5key);
+				m = wait_for_response(10000);
+				hide_doing();
 				if (!strcasecmp(get_header(m, "Response"), "Success")) {
 					res = 0;
 				} else {
 					show_message("Login Failed", get_header(m, "Message"));
 				}
+			} else {
+				memset(m, 0, sizeof(m));
+				manager_action("Login", 
+					"Username: %s\r\n"
+					"Secret: %s\r\n",
+						user, pass);
+				m = wait_for_response(10000);
+				hide_doing();
+				if (m) {
+					if (!strcasecmp(get_header(m, "Response"), "Success")) {
+						res = 0;
+					} else {
+						show_message("Login Failed", get_header(m, "Message"));
+					}
+				}
 			}
 		}
 	}
diff --git a/channels/chan_mgcp.c b/channels/chan_mgcp.c
index 0db0e42b2e..b81a670dbf 100755
--- a/channels/chan_mgcp.c
+++ b/channels/chan_mgcp.c
@@ -39,6 +39,7 @@
 #include <netdb.h>
 #include <arpa/inet.h>
 #include <sys/signal.h>
+#include <asterisk/dsp.h>
 
 #define MGCPDUMPER
 #define DEFAULT_EXPIREY 120
@@ -122,6 +123,7 @@ struct mgcp_endpoint {
 	char cxident[80];
 	char callid[80];
 	int hascallerid;
+	int dtmfinband;
 	int amaflags;
 	int type;
 	int group;
@@ -132,6 +134,7 @@ struct mgcp_endpoint {
 	int needdestroy;
 	int capability;
 	int outgoing;
+	struct ast_dsp *vad;
 	struct ast_channel *owner;
 	struct ast_rtp *rtp;
 	struct sockaddr_in tmpdest;
@@ -327,6 +330,9 @@ static int mgcp_hangup(struct ast_channel *ast)
 		ast_log(LOG_DEBUG, "Asked to hangup channel not connected\n");
 		return 0;
 	}
+	if ((p->dtmfinband) && (p->vad != NULL)){
+	    ast_dsp_free(p->vad);
+	}
 	ast_pthread_mutex_lock(&p->lock);
 	p->owner = NULL;
 	if (strlen(p->cxident))
@@ -515,6 +521,12 @@ static struct ast_channel *mgcp_new(struct mgcp_endpoint *i, int state)
 		if (i->rtp)
 			tmp->fds[0] = ast_rtp_fd(i->rtp);
 		tmp->type = type;
+		if (i->dtmfinband) {
+		    i->vad = ast_dsp_new();
+		    ast_dsp_set_features(i->vad,DSP_FEATURE_DTMF_DETECT);
+		} else {
+		    i->vad = NULL;
+		}
 		ast_setstate(tmp, state);
 		if (state == AST_STATE_RING)
 			tmp->rings = 1;
@@ -617,6 +629,9 @@ static int rtpready(struct ast_rtp *rtp, struct ast_frame *f, void *data)
 					ast_set_read_format(p->owner, p->owner->readformat);
 					ast_set_write_format(p->owner, p->owner->writeformat);
 				}
+				if (p->dtmfinband) {
+				    f = ast_dsp_process(p->owner,p->vad,f,0);
+				}
 			}
 			ast_queue_frame(p->owner, f, 0);
 			pthread_mutex_unlock(&p->owner->lock);
@@ -1478,6 +1493,7 @@ struct mgcp_gateway *build_gateway(char *cat, struct ast_variable *v)
 	char context[AST_MAX_EXTENSION] = "default";
 	char language[80] = "";
 	char callerid[AST_MAX_EXTENSION] = "";
+	int inbanddtmf = 0;
 	int nat = 0;
 
 	gw = malloc(sizeof(struct mgcp_gateway));
@@ -1519,6 +1535,8 @@ struct mgcp_gateway *build_gateway(char *cat, struct ast_variable *v)
 				gw->addr.sin_port = htons(atoi(v->value));
 			} else if (!strcasecmp(v->name, "context")) {
 				strncpy(context, v->value, sizeof(context) - 1);
+			} else if (!strcasecmp(v->name, "inbanddtmf")) {
+				inbanddtmf = atoi(v->value);
 			} else if (!strcasecmp(v->name, "nat")) {
 				nat = ast_true(v->value);
 			} else if (!strcasecmp(v->name, "callerid")) {
@@ -1540,6 +1558,7 @@ struct mgcp_gateway *build_gateway(char *cat, struct ast_variable *v)
 					strncpy(e->language, language, sizeof(e->language) - 1);
 					e->capability = capability;
 					e->parent = gw;
+					e->dtmfinband = inbanddtmf;
 					e->nat = nat;
 					strncpy(e->name, v->value, sizeof(e->name) - 1);
 					if (!strcasecmp(v->name, "trunk"))
@@ -1555,6 +1574,7 @@ struct mgcp_gateway *build_gateway(char *cat, struct ast_variable *v)
 		}
 		
 	}
+
 	if (!ntohl(gw->addr.sin_addr.s_addr) && !gw->dynamic) {
 		ast_log(LOG_WARNING, "Gateway '%s' lacks IP address and isn't dynamic\n", gw->name);
 		free(gw);
diff --git a/channels/chan_sip.c b/channels/chan_sip.c
index 81c760bec9..99148bff7d 100755
--- a/channels/chan_sip.c
+++ b/channels/chan_sip.c
@@ -288,6 +288,7 @@ static int sip_do_register(struct sip_registry *r);
 struct sip_registry *registrations;
 
 static int sipsock  = -1;
+static int globalnat = 0;
 
 static struct sockaddr_in bindaddr;
 
@@ -1128,6 +1129,7 @@ static struct sip_pvt *sip_alloc(char *callid, struct sockaddr_in *sin)
 	p->rtp = ast_rtp_new(NULL, NULL);
 	p->branch = rand();	
 	p->tag = rand();
+	p->nat = globalnat;
 	/* Start with 101 instead of 1 */
 	p->ocseq = 101;
 	if (!p->rtp) {
@@ -3996,6 +3998,8 @@ static int reload_config(void)
 		return 0;
 	}
 	
+	globalnat = 0;
+	
 	sip_prefs_free();
 	
 	memset(&bindaddr, 0, sizeof(bindaddr));
@@ -4009,6 +4013,8 @@ static int reload_config(void)
 			strncpy(context, v->value, sizeof(context)-1);
 		} else if (!strcasecmp(v->name, "language")) {
 			strncpy(language, v->value, sizeof(language)-1);
+		} else if (!strcasecmp(v->name, "nat")) {
+			globalnat = ast_true(v->value);
 		} else if (!strcasecmp(v->name, "maxexpirey")) {
 			max_expirey = atoi(v->value);
 			if (max_expirey < 1)
diff --git a/channels/chan_zap.c b/channels/chan_zap.c
index 4d308c3c41..560755069c 100755
--- a/channels/chan_zap.c
+++ b/channels/chan_zap.c
@@ -5931,6 +5931,7 @@ static int zap_show_channel(int fd, int argc, char **argv)
 			ast_cli(fd, "Default law: %s\n", tmp->law == ZT_LAW_MULAW ? "ulaw" : tmp->law == ZT_LAW_ALAW ? "alaw" : "unknown");
 			ast_cli(fd, "Fax Handled: %s\n", tmp->faxhandled ? "yes" : "no");
 			ast_cli(fd, "Pulse phone: %s\n", tmp->pulsedial ? "yes" : "no");
+			ast_cli(fd, "Echo Cancellation: %d taps%s, currently %s\n", tmp->echocancel, tmp->echocanbridged ? "" : " unless TDM bridged", tmp->echocanon ? "ON" : "OFF");
 			if (tmp->master)
 				ast_cli(fd, "Master Channel: %d\n", tmp->master->channel);
 			for (x=0;x<MAX_SLAVES;x++) {
diff --git a/utils/astman.c b/utils/astman.c
index 6bda4ff9ce..6fa6b81182 100755
--- a/utils/astman.c
+++ b/utils/astman.c
@@ -20,6 +20,7 @@
 #include <unistd.h>
 #include <stdlib.h>
 
+#include <asterisk/md5.h>
 #include <asterisk/manager.h>
 
 #define MAX_HEADERS 80
@@ -609,18 +610,49 @@ static int login(char *hostname)
 		if (es.u.co == login) {
 			snprintf(tmp, sizeof(tmp), "Logging in '%s'...", user);
 			show_doing("Logging in", tmp);
-			manager_action("Login", 
-				"Username: %s\r\n"
-				"Secret: %s\r\n",
-					user, pass);
+			/* Check to see if the remote host supports MD5 Authentication */
+			manager_action("Challenge", "AuthType: MD5\r\n");
 			m = wait_for_response(10000);
-			hide_doing();
-			if (m) {
+			if (m && !strcasecmp(get_header(m, "Response"), "Success")) {
+				char *challenge = get_header(m, "Challenge");
+				int x;
+				int len = 0;
+				char md5key[256] = "";
+				struct MD5Context md5;
+				unsigned char digest[16];
+				MD5Init(&md5);
+				MD5Update(&md5, challenge, strlen(challenge));
+				MD5Update(&md5, pass, strlen(pass));
+				MD5Final(digest, &md5);
+				for (x=0; x<16; x++)
+					len += sprintf(md5key + len, "%2.2x", digest[x]);
+				manager_action("Login",
+						"AuthType: MD5\r\n"
+						"Username: %s\r\n"
+						"Key: %s\r\n",
+						user, md5key);
+				m = wait_for_response(10000);
+				hide_doing();
 				if (!strcasecmp(get_header(m, "Response"), "Success")) {
 					res = 0;
 				} else {
 					show_message("Login Failed", get_header(m, "Message"));
 				}
+			} else {
+				memset(m, 0, sizeof(m));
+				manager_action("Login", 
+					"Username: %s\r\n"
+					"Secret: %s\r\n",
+						user, pass);
+				m = wait_for_response(10000);
+				hide_doing();
+				if (m) {
+					if (!strcasecmp(get_header(m, "Response"), "Success")) {
+						res = 0;
+					} else {
+						show_message("Login Failed", get_header(m, "Message"));
+					}
+				}
 			}
 		}
 	}
-- 
GitLab