[asterisk-commits] oej: branch oej/jasmin-remote-hold-1.8 r386418 - /team/oej/jasmin-remote-hold...

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Wed Apr 24 08:05:36 CDT 2013


Author: oej
Date: Wed Apr 24 08:05:32 2013
New Revision: 386418

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=386418
Log:
Adding a patch file for Krister.

Added:
    team/oej/jasmin-remote-hold-1.8/patches/
    team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff   (with props)

Added: team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff
URL: http://svnview.digium.com/svn/asterisk/team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff?view=auto&rev=386418
==============================================================================
--- team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff (added)
+++ team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff Wed Apr 24 08:05:32 2013
@@ -1,0 +1,535 @@
+Index: channels/chan_sip.c
+===================================================================
+--- channels/chan_sip.c	(.../branches/1.8)	(revision 386417)
++++ channels/chan_sip.c	(.../team/oej/jasmin-remote-hold-1.8)	(revision 386417)
+@@ -1304,7 +1304,7 @@
+ static const char *get_sdp_iterate(int* start, struct sip_request *req, const char *name);
+ static char get_sdp_line(int *start, int stop, struct sip_request *req, const char **value);
+ static int find_sdp(struct sip_request *req);
+-static int process_sdp(struct sip_pvt *p, struct sip_request *req, int t38action);
++static int process_sdp(struct sip_pvt *p, struct sip_request *req, int t38action, int oastate);
+ static int process_sdp_o(const char *o, struct sip_pvt *p);
+ static int process_sdp_c(const char *c, struct ast_sockaddr *addr);
+ static int process_sdp_a_sendonly(const char *a, int *sendonly);
+@@ -1319,6 +1319,7 @@
+ 				struct ast_str **m_buf, struct ast_str **a_buf,
+ 				int debug);
+ static enum sip_result add_sdp(struct sip_request *resp, struct sip_pvt *p, int oldsdp, int add_audio, int add_t38);
++
+ static void do_setnat(struct sip_pvt *p);
+ static void stop_media_flows(struct sip_pvt *p);
+ 
+@@ -7353,12 +7354,39 @@
+ 		res = -1;
+ 		break;
+ 	case AST_CONTROL_HOLD:
+-		ast_rtp_instance_update_source(p->rtp);
+-		ast_moh_start(ast, data, p->mohinterpret);
++		if(ast_test_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD)) {
++			if (ast_test_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS)) {
++				/* We are already put on hold, can't be more on hold */
++				ast_debug(1, "--- HOLD - Double hold???? \n");
++			} else {
++				/* Send re-invite and put the call on hold */
++				ast_set_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS);
++				ast_debug(1, "--- HOLD - Activated remote hold \n");
++				if (T38_ENABLED == p->t38.state) {
++					transmit_reinvite_with_sdp(p, TRUE, TRUE);
++				} else {
++					transmit_reinvite_with_sdp(p, FALSE, TRUE);
++				}
++			}
++		} else {
++			ast_rtp_instance_update_source(p->rtp);
++			ast_moh_start(ast, data, p->mohinterpret);
++		}
+ 		break;
+ 	case AST_CONTROL_UNHOLD:
+-		ast_rtp_instance_update_source(p->rtp);
+-		ast_moh_stop(ast);
++		if(ast_test_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS)) {
++			/* Send re-invite and put the call off hold */
++			ast_clear_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS);
++			ast_debug(1, "--- HOLD - cleared remote hold \n");
++			if (T38_ENABLED == p->t38.state) {
++				transmit_reinvite_with_sdp(p, TRUE, TRUE);
++			} else {
++				transmit_reinvite_with_sdp(p, FALSE, TRUE);
++			}
++		} else {
++			ast_rtp_instance_update_source(p->rtp);
++			ast_moh_stop(ast);
++		}
+ 		break;
+ 	case AST_CONTROL_VIDUPDATE:	/* Request a video frame update */
+ 		if (p->vrtp && !p->novideo) {
+@@ -9110,20 +9138,66 @@
+ 	return FALSE;
+ }
+ 
+-/*! \brief Change hold state for a call */
++/*! \brief Change hold state for a call 
++	We can get a hold state both as a response to our offer or in an offer 
++	\para holdstate TRUE if we're put off hold by peer
++*/
+ static void change_hold_state(struct sip_pvt *dialog, struct sip_request *req, int holdstate, int sendonly)
+ {
+-	if (sip_cfg.notifyhold && (!holdstate || !ast_test_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD)))
++	char *hold ="Off";
++	char *holdtype = "None";	/* Local, Remote, Both, None */
++	
++	/* Figure out our total hold state
++		sendonly indicates the change
++
++		3 = accept of our remote hold
++		0 = Other side put us off hold
++		1 = Other side put us on hold
++		2 = Other side made us inactive
++	*/
++	if (ast_test_flag(&dialog->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS)) {
++		/* We have put them on hold */
++		if (sendonly == 0) {
++			hold = "On";
++			holdtype = "Local";
++		} else if (sendonly == 1 || sendonly == 2) {
++			hold = "On";
++			holdtype = "Both";
++		}
++		ast_log(LOG_DEBUG, "--- Remote hold and hold %s type %s sendonly %d\n", hold, holdtype, sendonly);
++	} else {
++		/* We have no hold */
++		if (sendonly == 0) {
++			hold = "Off";
++			holdtype = "None";
++		} else if (sendonly == 1 || sendonly == 2) {
++			hold  = "On";
++			holdtype = "Remote";
++		}
++		ast_log(LOG_DEBUG, "--- Hold %s type %s sendonly %d\n", hold, holdtype, sendonly);
++	}
++	
++
++	if (sip_cfg.notifyhold && (!holdstate || !ast_test_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD))) {
++		/* XXX Check this for remote hold */
+ 		sip_peer_hold(dialog, holdstate);
+-	if (sip_cfg.callevents)
++	}
++	if (sip_cfg.callevents) {
+ 		manager_event(EVENT_FLAG_CALL, "Hold",
+ 			      "Status: %s\r\n"
++			      "Holdtype: %s\r\n"
+ 			      "Channel: %s\r\n"
+ 			      "Uniqueid: %s\r\n",
+-			      holdstate ? "On" : "Off",
++			      hold,
++			      holdtype,
+ 			      dialog->owner->name,
+ 			      dialog->owner->uniqueid);
+-	append_history(dialog, holdstate ? "Hold" : "Unhold", "%s", ast_str_buffer(req->data));
++	}
++	append_history(dialog, "Hold", "%s %s", holdtype, ast_str_buffer(req->data));
++	if (sendonly == 3) {
++		return;
++	}
++
+ 	if (!holdstate) {	/* Put off remote hold */
+ 		ast_clear_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD);	/* Clear both flags */
+ 		return;
+@@ -9137,7 +9211,7 @@
+ 		ast_set_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD_ONEDIR);
+ 	else if (sendonly == 2)	/* Inactive stream */
+ 		ast_set_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD_INACTIVE);
+-	else
++	else if (sendonly == 0)	/* We're back from peer hold */
+ 		ast_set_flag(&dialog->flags[1], SIP_PAGE2_CALL_ONHOLD_ACTIVE);
+ 	return;
+ }
+@@ -9211,12 +9285,13 @@
+ 	return ast_sockaddr_isnull(addr) || ast_sockaddr_is_any(addr);
+ }
+ 
+-/*! \brief Process SIP SDP offer, select formats and activate media channels
++/*! \brief Process SIP SDP offer/answer, select formats and activate media channels
+ 	If offer is rejected, we will not change any properties of the call
+  	Return 0 on success, a negative value on errors.
+ 	Must be called after find_sdp().
++	OAstate is 1 for new offer from remote, 0 for answer
+ */
+-static int process_sdp(struct sip_pvt *p, struct sip_request *req, int t38action)
++static int process_sdp(struct sip_pvt *p, struct sip_request *req, int t38action, int oastate)
+ {
+ 	/* Iterators for SDP parsing */
+ 	int start = req->sdp_start;
+@@ -9884,12 +9959,19 @@
+ 		ast_set_write_format(p->owner, p->owner->writeformat);
+ 	}
+ 
++	if (oastate != TRUE) {
++		/* If this is an SDP answer, don't bother with hold states */
++		/* This might be wrong though. */
++		return 0;
++	}
+ 	if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) && (!ast_sockaddr_isnull(sa) || !ast_sockaddr_isnull(vsa) || !ast_sockaddr_isnull(tsa) || !ast_sockaddr_isnull(isa)) && (!sendonly || sendonly == -1)) {
++		/* If we have been on hold and is now put off hold, make sure the other side understand it */
+ 		ast_queue_control(p->owner, AST_CONTROL_UNHOLD);
+ 		/* Activate a re-invite */
+ 		ast_queue_frame(p->owner, &ast_null_frame);
+ 		change_hold_state(p, req, FALSE, sendonly);
+ 	} else if ((sockaddr_is_null_or_any(sa) && sockaddr_is_null_or_any(vsa) && sockaddr_is_null_or_any(tsa) && sockaddr_is_null_or_any(isa)) || (sendonly && sendonly != -1)) {
++		/* We are put on hold by the other end */
+ 		ast_queue_control_data(p->owner, AST_CONTROL_HOLD,
+ 				       S_OR(p->mohsuggest, NULL),
+ 				       !ast_strlen_zero(p->mohsuggest) ? strlen(p->mohsuggest) + 1 : 0);
+@@ -9899,6 +9981,8 @@
+ 		/* Activate a re-invite */
+ 		ast_queue_frame(p->owner, &ast_null_frame);
+ 		change_hold_state(p, req, TRUE, sendonly);
++	} else if (sendonly == 3) {
++		change_hold_state(p, req, FALSE, sendonly);
+ 	}
+ 
+ 	return 0;
+@@ -10026,6 +10110,11 @@
+ 		if (*sendonly == -1)
+ 			*sendonly = 0;
+ 		found = TRUE;
++	}  else if (!strcasecmp(a, "recvonly")) {
++		/* We have put their side on hold */
++		if (*sendonly == -1)
++			*sendonly = 3;
++		found = TRUE;
+ 	}
+ 	return found;
+ }
+@@ -11864,14 +11953,34 @@
+ 		 ast_sockaddr_stringify_addr_remote(&dest));
+ 
+ 	if (add_audio) {
+-		if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_ONEDIR) {
+-			hold = "a=recvonly\r\n";
+-			doing_directmedia = FALSE;
+-		} else if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_INACTIVE) {
+-			hold = "a=inactive\r\n";
+-			doing_directmedia = FALSE;
++		/* The SIP_PAGE2_CALL_ONHOLD flag indicates if the other party has put us on hold or inactive. 
++ 		   The SIP_PAGE3_REMOTE_HOLD_STATUS flag indicates if we have put them on hold or not.
++		 */
++		if (ast_test_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD) && ast_test_flag(&p->flags[2], SIP_PAGE3_REMOTE_HOLD_STATUS)) {
++			/* We have put the channel on hold */
++			if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_ONEDIR) {
++				/* They have too */
++				hold = "a=inactive\r\n";
++				doing_directmedia = FALSE;
++			} else if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_INACTIVE) {
++				/* They have declared us inactive. We too */
++				hold = "a=inactive\r\n";
++				doing_directmedia = FALSE;
++			} else {
++				/* We put them on hold now */
++				hold = "a=sendonly\r\n";
++				doing_directmedia = FALSE;
++			}
+ 		} else {
+-			hold = "a=sendrecv\r\n";
++			if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_ONEDIR) {
++				hold = "a=recvonly\r\n";
++				doing_directmedia = FALSE;
++			} else if (ast_test_flag(&p->flags[1], SIP_PAGE2_CALL_ONHOLD) == SIP_PAGE2_CALL_ONHOLD_INACTIVE) {
++				hold = "a=inactive\r\n";
++				doing_directmedia = FALSE;
++			} else {
++				hold = "a=sendrecv\r\n";
++			}
+ 		}
+ 
+ 		capability = p->jointcapability;
+@@ -12342,6 +12451,53 @@
+ 	return 1;
+ }
+ 
++
++/* \brief Remove URI parameters at end of URI, not in username part though */
++static char *remove_uri_parameters(char *uri)
++{
++	char *atsign;
++	atsign = strchr(uri, '@');	/* First, locate the at sign */
++	if (!atsign) {
++		atsign = uri;	/* Ok hostname only, let's stick with the rest */
++	}
++	atsign = strchr(atsign, ';');	/* Locate semi colon */
++	if (atsign)
++		*atsign = '\0';	/* Kill at the semi colon */
++	return uri;
++}
++
++/*! \brief Check Contact: URI of SIP message */
++static void extract_uri(struct sip_pvt *p, struct sip_request *req)
++{
++	char stripped[SIPBUFSIZE];
++	char *c;
++
++	ast_copy_string(stripped, get_header(req, "Contact"), sizeof(stripped));
++	c = get_in_brackets(stripped);
++	/* Cut the URI at the at sign after the @, not in the username part */
++	c = remove_uri_parameters(c);
++	if (!ast_strlen_zero(c)) {
++		ast_string_field_set(p, uri, c);
++	}
++
++}
++
++/*! \brief Build contact header - the contact header we send out */
++static void build_contact(struct sip_pvt *p)
++{
++	char tmp[SIPBUFSIZE];
++	char *user = ast_uri_encode(p->exten, tmp, sizeof(tmp), 0);
++
++	if (p->socket.type == SIP_TRANSPORT_UDP) {
++		ast_string_field_build(p, our_contact, "<sip:%s%s%s>", user,
++			ast_strlen_zero(user) ? "" : "@", ast_sockaddr_stringify_remote(&p->ourip));
++	} else {
++		ast_string_field_build(p, our_contact, "<sip:%s%s%s;transport=%s>", user,
++			ast_strlen_zero(user) ? "" : "@", ast_sockaddr_stringify_remote(&p->ourip),
++			get_transport(p->socket.type));
++	}
++}
++
+ /*! \brief Transmit reinvite with SDP
+ \note 	A re-invite is basically a new INVITE with the same CALL-ID and TAG as the
+ 	INVITE that opened the SIP dialogue
+@@ -12393,52 +12549,7 @@
+ 	return send_request(p, &req, XMIT_CRITICAL, p->ocseq);
+ }
+ 
+-/* \brief Remove URI parameters at end of URI, not in username part though */
+-static char *remove_uri_parameters(char *uri)
+-{
+-	char *atsign;
+-	atsign = strchr(uri, '@');	/* First, locate the at sign */
+-	if (!atsign) {
+-		atsign = uri;	/* Ok hostname only, let's stick with the rest */
+-	}
+-	atsign = strchr(atsign, ';');	/* Locate semi colon */
+-	if (atsign)
+-		*atsign = '\0';	/* Kill at the semi colon */
+-	return uri;
+-}
+ 
+-/*! \brief Check Contact: URI of SIP message */
+-static void extract_uri(struct sip_pvt *p, struct sip_request *req)
+-{
+-	char stripped[SIPBUFSIZE];
+-	char *c;
+-
+-	ast_copy_string(stripped, get_header(req, "Contact"), sizeof(stripped));
+-	c = get_in_brackets(stripped);
+-	/* Cut the URI at the at sign after the @, not in the username part */
+-	c = remove_uri_parameters(c);
+-	if (!ast_strlen_zero(c)) {
+-		ast_string_field_set(p, uri, c);
+-	}
+-
+-}
+-
+-/*! \brief Build contact header - the contact header we send out */
+-static void build_contact(struct sip_pvt *p)
+-{
+-	char tmp[SIPBUFSIZE];
+-	char *user = ast_uri_encode(p->exten, tmp, sizeof(tmp), 0);
+-
+-	if (p->socket.type == SIP_TRANSPORT_UDP) {
+-		ast_string_field_build(p, our_contact, "<sip:%s%s%s>", user,
+-			ast_strlen_zero(user) ? "" : "@", ast_sockaddr_stringify_remote(&p->ourip));
+-	} else {
+-		ast_string_field_build(p, our_contact, "<sip:%s%s%s;transport=%s>", user,
+-			ast_strlen_zero(user) ? "" : "@", ast_sockaddr_stringify_remote(&p->ourip),
+-			get_transport(p->socket.type));
+-	}
+-}
+-
+ /*! \brief Initiate new SIP request to peer/user */
+ static void initreqprep(struct sip_request *req, struct sip_pvt *p, int sipmethod, const char * const explicit_uri)
+ {
+@@ -20772,7 +20883,7 @@
+ 		if (find_sdp(req)) {
+ 			if (p->invitestate != INV_CANCELLED)
+ 				p->invitestate = INV_EARLY_MEDIA;
+-			res = process_sdp(p, req, SDP_T38_NONE);
++			res = process_sdp(p, req, SDP_T38_NONE, FALSE);
+ 			if (!req->ignore && p->owner) {
+ 				/* Queue a progress frame only if we have SDP in 180 or 182 */
+ 				ast_queue_control(p->owner, AST_CONTROL_PROGRESS);
+@@ -20844,7 +20955,7 @@
+ 		if (find_sdp(req)) {
+ 			if (p->invitestate != INV_CANCELLED)
+ 				p->invitestate = INV_EARLY_MEDIA;
+-			res = process_sdp(p, req, SDP_T38_NONE);
++			res = process_sdp(p, req, SDP_T38_NONE, FALSE);
+ 			if (!req->ignore && p->owner) {
+ 				/* Queue a progress frame */
+ 				ast_queue_control(p->owner, AST_CONTROL_PROGRESS);
+@@ -20867,7 +20978,7 @@
+ 			ast_log(LOG_WARNING, "Unable to cancel SIP destruction.  Expect bad things.\n");
+ 		p->authtries = 0;
+ 		if (find_sdp(req)) {
+-			if ((res = process_sdp(p, req, SDP_T38_ACCEPT)) && !req->ignore)
++			if ((res = process_sdp(p, req, SDP_T38_ACCEPT, FALSE)) && !req->ignore)
+ 				if (!reinvite) {
+ 					/* This 200 OK's SDP is not acceptable, so we need to ack, then hangup */
+ 					/* For re-invites, we try to recover */
+@@ -22001,7 +22112,7 @@
+ 					if (!req->ignore && sip_cancel_destroy(p))
+ 						ast_log(LOG_WARNING, "Unable to cancel SIP destruction.  Expect bad things.\n");
+ 					if (find_sdp(req))
+-						process_sdp(p, req, SDP_T38_NONE);
++						process_sdp(p, req, SDP_T38_NONE, FALSE);
+ 					if (p->owner) {
+ 						/* Queue a progress frame */
+ 						ast_queue_control(p->owner, AST_CONTROL_PROGRESS);
+@@ -23257,7 +23368,7 @@
+ 			}
+ 			/* Handle SDP here if we already have an owner */
+ 			if (find_sdp(req)) {
+-				if (process_sdp(p, req, SDP_T38_INITIATE)) {
++				if (process_sdp(p, req, SDP_T38_INITIATE, TRUE)) {
+ 					if (!ast_strlen_zero(get_header(req, "Content-Encoding"))) {
+ 						/* Asterisk does not yet support any Content-Encoding methods.  Always
+ 						 * attempt to process the sdp, but return a 415 if a Content-Encoding header
+@@ -23323,7 +23434,7 @@
+ 
+ 		/* We have a successful authentication, process the SDP portion if there is one */
+ 		if (find_sdp(req)) {
+-			if (process_sdp(p, req, SDP_T38_INITIATE)) {
++			if (process_sdp(p, req, SDP_T38_INITIATE, TRUE)) {
+ 				/* Asterisk does not yet support any Content-Encoding methods.  Always
+ 				 * attempt to process the sdp, but return a 415 if a Content-Encoding header
+ 				 * was present after processing fails. */
+@@ -25975,7 +26086,7 @@
+ 			p->pendinginvite = 0;
+ 			acked = __sip_ack(p, seqno, 1 /* response */, 0);
+ 			if (find_sdp(req)) {
+-				if (process_sdp(p, req, SDP_T38_NONE)) {
++				if (process_sdp(p, req, SDP_T38_NONE, FALSE)) {
+ 					return -1;
+ 				}
+ 				if (ast_test_flag(&p->flags[0], SIP_DIRECT_MEDIA)) {
+@@ -27629,6 +27740,9 @@
+ 	} else if (!strcasecmp(v->name, "buggymwi")) {
+ 		ast_set_flag(&mask[1], SIP_PAGE2_BUGGY_MWI);
+ 		ast_set2_flag(&flags[1], ast_true(v->value), SIP_PAGE2_BUGGY_MWI);
++	} else if (!strcasecmp(v->name, "remotehold")) {
++		ast_set_flag(&mask[2], SIP_PAGE3_REMOTE_HOLD);
++		ast_set2_flag(&flags[2], ast_true(v->value), SIP_PAGE3_REMOTE_HOLD);
+ 	} else
+ 		res = 0;
+ 
+Index: channels/sip/include/sip.h
+===================================================================
+--- channels/sip/include/sip.h	(.../branches/1.8)	(revision 386417)
++++ channels/sip/include/sip.h	(.../team/oej/jasmin-remote-hold-1.8)	(revision 386417)
+@@ -329,10 +329,10 @@
+ #define SIP_PAGE2_T38SUPPORT_UDPTL_FEC      (2 << 17)   /*!< GDP: T.38 Fax Support (FEC error correction) */
+ #define SIP_PAGE2_T38SUPPORT_UDPTL_REDUNDANCY   (3 << 17)   /*!< GDP: T.38 Fax Support (redundancy error correction) */
+ 
+-#define SIP_PAGE2_CALL_ONHOLD               (3 << 19)   /*!< D: Call hold states: */
+-#define SIP_PAGE2_CALL_ONHOLD_ACTIVE        (1 << 19)   /*!< D: Active hold */
+-#define SIP_PAGE2_CALL_ONHOLD_ONEDIR        (2 << 19)   /*!< D: One directional hold */
+-#define SIP_PAGE2_CALL_ONHOLD_INACTIVE      (3 << 19)   /*!< D: Inactive hold */
++#define SIP_PAGE2_CALL_ONHOLD               (3 << 19)   /*!< D: Call hold states: Incoming hold */
++#define SIP_PAGE2_CALL_ONHOLD_ACTIVE        (1 << 19)   /*!< D: Active hold  Incoming hold*/
++#define SIP_PAGE2_CALL_ONHOLD_ONEDIR        (2 << 19)   /*!< D: One directional hold  Incoming hold*/
++#define SIP_PAGE2_CALL_ONHOLD_INACTIVE      (3 << 19)   /*!< D: Inactive hold  Incoming hold*/
+ 
+ #define SIP_PAGE2_RFC2833_COMPENSATE        (1 << 21)   /*!< DP: Compensate for buggy RFC2833 implementations */
+ #define SIP_PAGE2_BUGGY_MWI                 (1 << 22)   /*!< DP: Buggy CISCO MWI fix */
+@@ -359,9 +359,11 @@
+ 
+ #define SIP_PAGE3_SNOM_AOC               (1 << 0)  /*!< DPG: Allow snom aoc messages */
+ #define SIP_PAGE3_DIRECT_MEDIA_OUTGOING  (1 << 1)  /*!< DP: Only send direct media reinvites on outgoing calls */
++#define SIP_PAGE3_REMOTE_HOLD		 (1 << 15)  /*!< DPG: Do not generate hold music, send remote hold (config)*/
++#define SIP_PAGE3_REMOTE_HOLD_STATUS	 (1 << 16)  /*!< D: True if dialog is put on hold by pbx core */
+ 
+ #define SIP_PAGE3_FLAGS_TO_COPY \
+-	(SIP_PAGE3_SNOM_AOC | SIP_PAGE3_DIRECT_MEDIA_OUTGOING)
++	(SIP_PAGE3_SNOM_AOC | SIP_PAGE3_DIRECT_MEDIA_OUTGOING | SIP_PAGE3_REMOTE_HOLD)
+ 
+ /*@}*/
+ 
+Index: configs/sip.conf.sample
+===================================================================
+--- configs/sip.conf.sample	(.../branches/1.8)	(revision 386417)
++++ configs/sip.conf.sample	(.../team/oej/jasmin-remote-hold-1.8)	(revision 386417)
+@@ -315,6 +315,11 @@
+ ; a per-user or per-peer basis.
+ ;
+ ;mohsuggest=default
++
++; Instead of playing moh for a device on hold, Asterisk can forward the hold
++; and use SIP to put the device on hold. This setting is available on a device
++; level too. Defaults to no - off.
++; remotehold=yes
+ ;
+ ;parkinglot=plaza               ; Sets the default parking lot for call parking
+                                 ; This may also be set for individual users/peers
+Index: README.jasmin-remote-hold
+===================================================================
+--- README.jasmin-remote-hold	(.../branches/1.8)	(revision 0)
++++ README.jasmin-remote-hold	(.../team/oej/jasmin-remote-hold-1.8)	(revision 386417)
+@@ -0,0 +1,23 @@
++Edvina AB
++Olle E. Johansson
++
++
++
++
++
++SIP Remote Hold
++===============
++
++When a bridged channel is put on hold, Asterisk currently maintains the other channel by playing
++music on hold music. In some cases it's a better solution to forward the hold, especially when
++Asterisk operates as an end point, a phone or when one has multiple Asterisks and instead of
++forwarding audio frames wants the server closest to the other end point to generate the music.
++
++In this patch, a new configuration setting is introduced in sip.conf:
++
++remotehold = yes | no
++
++This setting applies to the [general] section as well as to individual devices or
++trunks. Wehn this setting is on, a channel will be put on hold by sending a re-invite
++with an SDP containing a=sendonly instead of generating music.
++
+
+Egenskapsändringar för: README.jasmin-remote-hold
+___________________________________________________________________
+Added: svn:mime-type
+## -0,0 +1 ##
++text/plain
+\ No newline at end of property
+Added: svn:keywords
+## -0,0 +1 ##
++Author Date Id Revision
+\ No newline at end of property
+Added: svn:eol-style
+## -0,0 +1 ##
++native
+\ No newline at end of property
+Index: .
+===================================================================
+--- .	(.../branches/1.8)	(revision 386417)
++++ .	(.../team/oej/jasmin-remote-hold-1.8)	(revision 386417)
+
+Egenskapsändringar för: .
+___________________________________________________________________
+Added: svnmerge-integrated
+## -0,0 +1 ##
++/branches/1.8:1-386268
+\ No newline at end of property
+Added: automerge-email
+## -0,0 +1 ##
++oej at edvina.net
+\ No newline at end of property
+Added: automerge
+## -0,0 +1 ##
++Is-there-life-off-net?
+\ No newline at end of property

Propchange: team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff
------------------------------------------------------------------------------
    svn:keywords = Author Date Id Revision

Propchange: team/oej/jasmin-remote-hold-1.8/patches/jasmin-remote-hold-1.8.diff
------------------------------------------------------------------------------
    svn:mime-type = text/plain




More information about the asterisk-commits mailing list