Index: libs/openzap/src/ozmod/ozmod_isdn/ozmod_isdn.c
===================================================================
--- libs/openzap/src/ozmod/ozmod_isdn/ozmod_isdn.c	(revision 530)
+++ libs/openzap/src/ozmod/ozmod_isdn/ozmod_isdn.c	(working copy)
@@ -72,7 +72,6 @@
 	Q931ie_CalledNum *ptrCalledNum;
 	Q931ie_Display Display, *ptrDisplay;
 	Q931ie_HLComp HLComp;			/* High-Layer Compatibility IE */
-	Q931ie_SendComplete SComplete;		/* Sending Complete IE */
 	Q931ie_ProgInd Progress;		/* Progress Indicator IE */
 	zap_status_t status = ZAP_FAIL;
 	zap_isdn_data_t *isdn_data = span->signal_data;
@@ -177,12 +176,6 @@
 	HLComp.HLCharID  = 1;	/* Telephony = 1, Fax G2+3 = 4, Fax G4 = 65 (Class I)/ 68 (Class II or III) */
 	gen->HLComp = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &HLComp);
 
-	/*
-	 * Sending complete IE (or some NT stuff waits forever in Q.931 overlap dial state...)
-	 */
-	SComplete.IEId = Q931ie_SENDING_COMPLETE;
-//	gen->SendComplete = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &SComplete);
-
 	caller_data->call_state = ZAP_CALLER_STATE_DIALING;
 	Q931Rx43(&isdn_data->q931, (L3UCHAR *) gen, gen->Size);
 	
@@ -299,6 +292,7 @@
 	zap_isdn_data_t *isdn_data = span->signal_data;
 	Q931mes_Generic *gen = (Q931mes_Generic *) msg;
 	int chan_id = 0;
+	int chan_hunt = 0;
 	zap_channel_t *zchan = NULL;
 	zap_caller_data_t *caller_data = NULL;
 
@@ -309,6 +303,14 @@
 			chan_id = chanid->ChanSlot;
 		else
 			chan_id = chanid->InfoChanSel;
+
+		/* "any" channel specified */
+		if(chanid->InfoChanSel == 3) {
+			chan_hunt++;
+		}
+	} else if (ZAP_SPAN_IS_NT(span)) {
+		/* no channel ie */
+		chan_hunt++;
 	}
 
 	assert(span != NULL);
@@ -346,7 +348,7 @@
 		zchan = isdn_data->channels_remote_crv[gen->CRV];
 	}
 
-	zap_log(ZAP_LOG_DEBUG, "zchan %x source isdn_data->channels_%s_crv[%#hx]\n", zchan, gen->CRVFlag ? "local" : "remote", gen->CRV);
+	zap_log(ZAP_LOG_DEBUG, "zchan %x (%d:%d) source isdn_data->channels_%s_crv[%#hx]\n", zchan, zchan ? zchan->span_id : -1, zchan ? zchan->chan_id : -1, gen->CRVFlag ? "local" : "remote", gen->CRV);
 
 
 	if (gen->ProtDisc == 3) {
@@ -491,6 +493,8 @@
 				Q931ie_CallingNum *callingnum = Q931GetIEPtr(gen->CallingNum, gen->buf);
 				Q931ie_CalledNum *callednum = Q931GetIEPtr(gen->CalledNum, gen->buf);
 				int fail = 1;
+				int fail_cause = 0;
+				int overlap_dial = 0;
 				uint32_t cplen = mlen;
 
 				if(zchan && zchan == isdn_data->channels_remote_crv[gen->CRV]) {
@@ -504,10 +508,62 @@
 				}
 				
 				zchan = NULL;
-				if (chan_id < ZAP_MAX_CHANNELS_SPAN && chan_id <= span->chan_count) {
-					zchan = &span->channels[chan_id];
+				/*
+				 * Channel selection for incoming calls:
+				 */
+				if (ZAP_SPAN_IS_NT(span) && chan_hunt) {
+					int x;
+
+					/*
+					 * In NT-mode with channel selection "any",
+					 * try to find a free channel
+					 */
+					for (x = 1; x <= span->chan_count; x++) {
+						zap_channel_t *zc = &span->channels[x];
+
+						if (!zap_test_flag(zc, ZAP_CHANNEL_INUSE) && zc->state == ZAP_CHANNEL_STATE_DOWN) {
+							zchan = zc;
+							break;
+						}
+					}
 				}
+				else if (!ZAP_SPAN_IS_NT(span) && chan_hunt) {
+					/*
+					 * In TE-mode this ("any") is invalid
+					 */
+					fail_cause = ZAP_CAUSE_CHANNEL_UNACCEPTABLE;
 
+					zap_log(ZAP_LOG_ERROR, "Invalid channel selection in incoming call (network side didn't specify a channel)\n");
+				}
+				else {
+					/*
+					 * Otherwise simply try to select the channel we've been told
+					 *
+					 * TODO: NT mode is abled to select a different channel if the one chosen
+					 *       by the TE side is already in use
+					 */
+					if (chan_id > 0 && chan_id < ZAP_MAX_CHANNELS_SPAN && chan_id <= span->chan_count) {
+						zchan = &span->channels[chan_id];
+					}
+					else {
+						/* invalid channel id */
+						fail_cause = ZAP_CAUSE_CHANNEL_UNACCEPTABLE;
+
+						zap_log(ZAP_LOG_ERROR, "Invalid channel selection in incoming call (none selected or out of bounds)\n");
+					}
+				}
+
+				if (!callednum || !strlen((char *)callednum->Digit)) {
+					if (ZAP_SPAN_IS_NT(span)) {
+						zap_log(ZAP_LOG_NOTICE, "No destination number found, assuming overlap dial\n");
+						overlap_dial++;
+					}
+					else {
+						zap_log(ZAP_LOG_ERROR, "No destination number found\n");
+						zchan = NULL;
+					}
+				}
+
 				if (zchan) {
 					if (zap_test_flag(zchan, ZAP_CHANNEL_INUSE) || zchan->state != ZAP_CHANNEL_STATE_DOWN) {
 						if (zchan->state == ZAP_CHANNEL_STATE_DOWN || zchan->state >= ZAP_CHANNEL_STATE_TERMINATING) {
@@ -552,7 +608,6 @@
 						gen->CRVFlag = !(gen->CRVFlag);
 						memcpy(zchan->caller_data.raw_data, msg, cplen);
 						zchan->caller_data.raw_data_len = cplen;
-						zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_RING);
 						fail = 0;
 					} 
 				} 
@@ -567,7 +622,7 @@
 					cause.Location = 1;
 					cause.Recom = 1;
 					//should we be casting here.. or do we need to translate value?
-					cause.Value = (unsigned char) ZAP_CAUSE_WRONG_CALL_STATE;
+					cause.Value = (unsigned char)((fail_cause) ? fail_cause : ZAP_CAUSE_WRONG_CALL_STATE);
 					*cause.Diag = '\0';
 					gen->Cause = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &cause);
 					Q931Rx43(&isdn_data->q931, (L3UCHAR *) gen, gen->Size);
@@ -583,17 +638,50 @@
 					}
 					
 				} else {
-					Q931ie_ProgInd progress;
+					Q931ie_ChanID ChanID;
 
 					/*
-					 * Setup Progress indicator
+					 * Update Channel ID IE
 					 */
-					progress.IEId = Q931ie_PROGRESS_INDICATOR;
-					progress.Size = sizeof(Q931ie_ProgInd);
-					progress.CodStand = Q931_CODING_ITU;	/* ITU */ 
-					progress.Location = 1;	/* private network serving the local user */
-					progress.ProgDesc = 1;	/* call is not end-to-end isdn = 1, in-band information available = 8 */
-					gen->ProgInd = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &progress);
+					Q931InitIEChanID(&ChanID);
+					ChanID.IntType = ZAP_SPAN_IS_BRI(zchan->span) ? 0 : 1;	/* PRI = 1, BRI = 0 */
+					ChanID.PrefExcl = ZAP_SPAN_IS_NT(zchan->span) ? 1 : 0;  /* Exclusive in NT-mode = 1, Preferred otherwise = 0 */
+					if(ChanID.IntType) {
+						ChanID.InfoChanSel = 1;		/* None = 0, See Slot = 1, Any = 3 */
+						ChanID.ChanMapType = 3;		/* B-Chan */
+						ChanID.ChanSlot = (unsigned char)zchan->chan_id;
+					} else {
+						ChanID.InfoChanSel = (unsigned char)zchan->chan_id & 0x03;	/* None = 0, B1 = 1, B2 = 2, Any = 3 */
+					}
+					gen->ChanID = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &ChanID);
+
+					if (overlap_dial) {
+						Q931ie_ProgInd progress;
+
+						/*
+						 * Setup Progress indicator
+						 */
+						progress.IEId = Q931ie_PROGRESS_INDICATOR;
+						progress.Size = sizeof(Q931ie_ProgInd);
+						progress.CodStand = Q931_CODING_ITU;	/* ITU */ 
+						progress.Location = 1;	/* private network serving the local user */
+						progress.ProgDesc = 8;	/* call is not end-to-end isdn = 1, in-band information available = 8 */
+						gen->ProgInd = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &progress);
+
+						/*
+						 * Send SETUP ACK
+						 */
+						gen->MesType = Q931mes_SETUP_ACKNOWLEDGE;
+						gen->CRVFlag = 1;	/* inbound call */
+						Q931Rx43(&isdn_data->q931, (L3UCHAR *) gen, gen->Size);
+
+						zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_DIALTONE);
+					} else {
+						/*
+						 * Advance to RING state
+						 */
+						zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_RING);
+					}
 				}
 			}
 			break;
@@ -609,6 +697,48 @@
 			}
 			break;
 
+		case Q931mes_INFORMATION:
+			{
+				if (zchan) {
+					zap_log(ZAP_LOG_CRIT, "Received INFORMATION message for channel %d\n", zchan->chan_id);
+
+					if (zchan->state == ZAP_CHANNEL_STATE_DIALTONE) {
+						char digit = '\0';
+
+						/*
+						 * overlap dial digit indication
+						 */
+						if (Q931IsIEPresent(gen->CalledNum)) {
+							Q931ie_CalledNum *callednum = Q931GetIEPtr(gen->CalledNum, gen->buf);
+							int pos;
+
+							digit = callednum->Digit[strlen((char *)callednum->Digit) - 1];
+							if (digit == '#') {
+								callednum->Digit[strlen((char *)callednum->Digit) - 1] = '\0';
+							}
+
+							/* TODO: make this more safe with strncat() */
+							pos = strlen(zchan->caller_data.cid_num.digits);
+							strcat(&zchan->caller_data.cid_num.digits[pos], (char *)callednum->Digit);
+							strcat(&zchan->caller_data.cid_name[pos],       (char *)callednum->Digit);
+							strcat(&zchan->caller_data.ani.digits[pos],     (char *)callednum->Digit);
+							strcat(&zchan->caller_data.dnis.digits[pos],    (char *)callednum->Digit);
+
+							zap_log(ZAP_LOG_DEBUG, "Received new overlap digit (%s), destination number: %s\n", callednum->Digit, zchan->caller_data.cid_num.digits);
+						}
+
+						if (Q931IsIEPresent(gen->SendComplete) || digit == '#') {
+							zap_log(ZAP_LOG_DEBUG, "Leaving overlap dial mode\n");
+
+							zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_RING);
+						}
+					}
+				} else {
+					zap_log(ZAP_LOG_CRIT, "Received INFORMATION message with no matching channel\n");
+				}
+			}
+			break;
+
 		default:
 			zap_log(ZAP_LOG_CRIT, "Received unhandled message %d (%#x)\n", (int)gen->MesType, (int)gen->MesType);
 			break;
@@ -696,10 +826,44 @@
 				gen->MesType = Q931mes_CALL_PROCEEDING;
 				gen->CRVFlag = 1;	/* inbound */
 
+				if (ZAP_SPAN_IS_NT(zchan->span)) {
+					Q931ie_ChanID ChanID;
+
+					/*
+					 * Set new Channel ID
+					 */
+					Q931InitIEChanID(&ChanID);
+					ChanID.IntType = ZAP_SPAN_IS_BRI(zchan->span) ? 0 : 1;		/* PRI = 1, BRI = 0 */
+					ChanID.PrefExcl = 1;	/* always exclusive in NT-mode */
+
+					if(ChanID.IntType) {
+						ChanID.InfoChanSel = 1;		/* None = 0, See Slot = 1, Any = 3 */
+						ChanID.ChanMapType = 3; 	/* B-Chan */
+						ChanID.ChanSlot = (unsigned char)zchan->chan_id;
+					} else {
+						ChanID.InfoChanSel = (unsigned char)zchan->chan_id & 0x03;	/* None = 0, B1 = 1, B2 = 2, Any = 3 */
+					}
+					gen->ChanID = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &ChanID);
+				}
+
 				Q931Rx43(&isdn_data->q931, (void *)gen, gen->Size);
 			}
 		}
 		break;
+	case ZAP_CHANNEL_STATE_DIALTONE:
+		{
+/*
+			if (!zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
+				if (!zap_test_flag(zchan, ZAP_CHANNEL_OPEN)) {
+					if (zap_channel_open_chan(zchan) != ZAP_SUCCESS) {
+						zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP);
+						return;
+					}
+				}
+			}
+*/
+		}
+		break;
 	case ZAP_CHANNEL_STATE_RING:
 		{
 			if (!zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
@@ -769,7 +933,6 @@
 			Q931ie_CalledNum *ptrCalledNum;
 			Q931ie_Display Display, *ptrDisplay;
 			Q931ie_HLComp HLComp;			/* High-Layer Compatibility IE */
-			Q931ie_SendComplete SComplete;		/* Sending Complete IE */
 			Q931ie_ProgInd Progress;		/* Progress Indicator IE */
 			int codec  = 0;
 
@@ -864,12 +1027,6 @@
 			HLComp.HLCharID  = Q931_HLCHAR_TELEPHONY;	/* Telephony = 1, Fax G2+3 = 4, Fax G4 = 65 (Class I)/ 68 (Class II or III) */   /* TODO: make accessible from user layer */
 			gen->HLComp = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &HLComp);
 
-			/*
-			 * Sending complete IE (or some NT stuff waits forever in Q.931 overlap dial state...)
-			 */
-			SComplete.IEId = Q931ie_SENDING_COMPLETE;
-//			gen->SendComplete = Q931AppendIE((L3UCHAR *) gen, (L3UCHAR *) &SComplete);
-
 			Q931Rx43(&isdn_data->q931, (L3UCHAR *) gen, gen->Size);
 			isdn_data->channels_local_crv[gen->CRV] = zchan;
 		}
@@ -1053,12 +1210,194 @@
 	}
 }
 
+
+static int teletone_handler(teletone_generation_session_t *ts, teletone_tone_map_t *map)
+{
+	zap_buffer_t *dt_buffer = ts->user_data;
+	int wrote;
+
+	if (!dt_buffer) {
+		return -1;
+	}
+	wrote = teletone_mux_tones(ts, map);
+	zap_buffer_write(dt_buffer, ts->buffer, wrote * 2);
+	return 0;
+}
+
+static void *zap_isdn_tones_run(zap_thread_t *me, void *obj)
+{
+	zap_span_t *span = (zap_span_t *) obj;
+	zap_isdn_data_t *isdn_data = span->signal_data;
+	zap_buffer_t *dt_buffer = NULL;
+	teletone_generation_session_t ts;
+	unsigned char frame[1024];
+	int x, interval;
+	int offset = 0;
+
+	zap_log(ZAP_LOG_DEBUG, "ISDN tones thread starting.\n");
+
+	if (zap_buffer_create(&dt_buffer, 1024, 1024, 0) != ZAP_SUCCESS) {
+		snprintf(isdn_data->dchan->last_error, sizeof(isdn_data->dchan->last_error), "memory error!");
+		zap_log(ZAP_LOG_ERROR, "MEM ERROR\n");
+		goto done;
+	}
+	zap_buffer_set_loops(dt_buffer, -1);
+
+	/* get a tone generation friendly interval to avoid distortions */
+	for (x = 1; x <= span->chan_count; x++) {
+		if (span->channels[x].type != ZAP_CHAN_TYPE_DQ921) {
+			zap_channel_command(&span->channels[x], ZAP_COMMAND_GET_INTERVAL, &interval);
+			break;
+		}
+	}
+	zap_log(ZAP_LOG_NOTICE, "Tone generating interval %d\n", interval);
+
+	assert(interval != 0);
+
+	/* init teletone */
+	teletone_init_session(&ts, 0, teletone_handler, dt_buffer);
+	ts.rate     = 8000;
+	ts.duration = ts.rate;
+
+	/* main loop */
+	while(zap_running() && zap_test_flag(isdn_data, ZAP_ISDN_RUNNING)) {
+		zap_wait_flag_t flags;
+		zap_status_t status;
+		int last_chan_state = 0;
+		int gated = 0;
+
+		/*
+		 * check b-channel states and generate & send tones if neccessary
+		 */
+		for (x = 1; x <= span->chan_count; x++) {
+			zap_channel_t *zchan = &span->channels[x];
+			zap_size_t len = sizeof(frame), rlen;
+
+			if (zchan->type == ZAP_CHAN_TYPE_DQ921) {
+				continue;
+			}
+
+			/*
+			 * Generate tones based on current bchan state
+			 * (Recycle buffer content if succeeding channels share the
+			 *  same state, this saves some cpu cycles)
+			 */
+			switch (zchan->state) {
+			case ZAP_CHANNEL_STATE_DIALTONE:
+				{
+					if (last_chan_state != zchan->state) {
+						zap_buffer_zero(dt_buffer);
+						teletone_run(&ts, zchan->span->tone_map[ZAP_TONEMAP_DIAL]);
+						last_chan_state = zchan->state;
+					}
+				}
+				break;
+
+			case ZAP_CHANNEL_STATE_RING:
+				{
+					if (last_chan_state != zchan->state) {
+						zap_buffer_zero(dt_buffer);
+						teletone_run(&ts, zchan->span->tone_map[ZAP_TONEMAP_RING]);
+						last_chan_state = zchan->state;
+					}
+				}
+				break;
+
+			default:	/* Not in a tone generating state, go to next round */
+				continue;
+			}
+
+			if (!zap_test_flag(zchan, ZAP_CHANNEL_OPEN)) {
+				if (zap_channel_open_chan(zchan) != ZAP_SUCCESS) {
+					zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP);
+					continue;
+				}
+				zap_log(ZAP_LOG_NOTICE, "Successfully opened channel %d:%d\n", zchan->span_id, zchan->chan_id);
+			}
+
+			flags = ZAP_READ;
+
+			status = zap_channel_wait(zchan, &flags, (gated) ? 0 : interval);
+			switch(status) {
+			case ZAP_FAIL:
+				continue;
+
+			case ZAP_TIMEOUT:
+				gated = 1;
+				continue;
+
+			default:
+				if (!(flags & ZAP_READ)) {
+					continue;
+				}
+			}
+			gated = 1;
+
+			status = zap_channel_read(zchan, frame, &len);
+			if (status != ZAP_SUCCESS || len <= 0) {
+				continue;
+			}
+
+			if (zchan->effective_codec != ZAP_CODEC_SLIN) {
+				len *= 2;
+			}
+
+			/* seek to current offset */
+			zap_buffer_seek(dt_buffer, offset);
+
+			rlen = zap_buffer_read_loop(dt_buffer, frame, len);
+
+			if (zchan->effective_codec != ZAP_CODEC_SLIN) {
+				zio_codec_t codec_func = NULL;
+
+				if (zchan->native_codec == ZAP_CODEC_ULAW) {
+					codec_func = zio_slin2ulaw;
+				} else if (zchan->native_codec == ZAP_CODEC_ALAW) {
+					codec_func = zio_slin2alaw;
+				}
+
+				if (codec_func) {
+					status = codec_func(frame, sizeof(frame), &rlen);
+				} else {
+					snprintf(zchan->last_error, sizeof(zchan->last_error), "codec error!");
+					goto done;
+				}
+			}
+			zap_channel_write(zchan, frame, sizeof(frame), &rlen);
+		}
+
+		/*
+		 * sleep a bit if there was nothing to do
+		 */
+		if (!gated) {
+			zap_sleep(interval);
+		}
+
+		offset += (ts.rate / (1000 / interval)) << 1;
+		if (offset >= ts.rate) {
+			offset = 0;
+		}
+	}
+
+done:
+	if (ts.buffer) {
+		teletone_destroy_session(&ts);
+	}
+
+	if (dt_buffer) {
+		zap_buffer_destroy(&dt_buffer);
+	}
+
+	zap_log(ZAP_LOG_DEBUG, "ISDN tone thread ended.\n");
+	return NULL;
+}
+
 static void *zap_isdn_run(zap_thread_t *me, void *obj)
 {
 	zap_span_t *span = (zap_span_t *) obj;
 	zap_isdn_data_t *isdn_data = span->signal_data;
-	unsigned char buf[1024];
-	zap_size_t len = sizeof(buf);
+	unsigned char frame[1024];
+	zap_size_t len = sizeof(frame);
 	int errs = 0;
 
 #ifdef WIN32
@@ -1078,6 +1417,9 @@
 		check_state(span);
 		check_events(span);
 
+		/*
+		 *
+		 */
 		switch(status) {
 		case ZAP_FAIL:
 			{
@@ -1098,17 +1440,17 @@
 			{
 				errs = 0;
 				if (flags & ZAP_READ) {
-					len = sizeof(buf);
-					if (zap_channel_read(isdn_data->dchan, buf, &len) == ZAP_SUCCESS) {
+					len = sizeof(frame);
+					if (zap_channel_read(isdn_data->dchan, frame, &len) == ZAP_SUCCESS) {
 #ifdef IODEBUG
 						char bb[4096] = "";
-						print_hex_bytes(buf, len, bb, sizeof(bb));
+						print_hex_bytes(frame, len, bb, sizeof(bb));
 
-						print_bits(buf, (int)len, bb, sizeof(bb), ZAP_ENDIAN_LITTLE, 0);
+						print_bits(frame, (int)len, bb, sizeof(bb), ZAP_ENDIAN_LITTLE, 0);
 						zap_log(ZAP_LOG_DEBUG, "READ %d\n%s\n%s\n\n", (int)len, LINE, bb);
 #endif
 						
-						Q921QueueHDLCFrame(&isdn_data->q921, buf, (int)len);
+						Q921QueueHDLCFrame(&isdn_data->q921, frame, (int)len);
 						Q921Rx12(&isdn_data->q921);
 					}
 				} else {
@@ -1117,11 +1459,9 @@
 			}
 			break;
 		}
-
 	}
 	
  done:
-
 	zap_channel_close(&isdn_data->dchans[0]);
 	zap_channel_close(&isdn_data->dchans[1]);
 	zap_clear_flag(isdn_data, ZAP_ISDN_RUNNING);
@@ -1273,11 +1613,17 @@
 			ZSD_INBOUND,
 			ZSM_UNACCEPTABLE,
 			{ZAP_CHANNEL_STATE_DOWN, ZAP_END},
-			{ZAP_CHANNEL_STATE_RING, ZAP_END}
+			{ZAP_CHANNEL_STATE_DIALTONE, ZAP_CHANNEL_STATE_RING, ZAP_END}
 		},
 		{
 			ZSD_INBOUND,
 			ZSM_UNACCEPTABLE,
+			{ZAP_CHANNEL_STATE_DIALTONE, ZAP_END},
+			{ZAP_CHANNEL_STATE_RING, ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_END}
+		},
+		{
+			ZSD_INBOUND,
+			ZSM_UNACCEPTABLE,
 			{ZAP_CHANNEL_STATE_RING, ZAP_END},
 			{ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_CHANNEL_STATE_PROGRESS, ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_UP, ZAP_END}
 		},
@@ -1312,9 +1658,20 @@
 
 static zap_status_t zap_isdn_start(zap_span_t *span)
 {
+	zap_status_t ret;
+
 	zap_isdn_data_t *isdn_data = span->signal_data;
 	zap_set_flag(isdn_data, ZAP_ISDN_RUNNING);
-	return zap_thread_create_detached(zap_isdn_run, span);
+
+	ret = zap_thread_create_detached(zap_isdn_run, span);
+	if (ret != ZAP_SUCCESS) {
+		return ret;
+	}
+
+	if(ZAP_SPAN_IS_NT(span)) {
+		ret = zap_thread_create_detached(zap_isdn_tones_run, span);
+	}
+	return ret;
 }
 
 
@@ -1324,6 +1681,7 @@
 	uint32_t i, x = 0;
 	zap_channel_t *dchans[2] = {0};
 	zap_isdn_data_t *isdn_data;
+	const char *tonemap = "us";
 	char *var, *val;
 	Q931Dialect_t dialect = Q931_Dialect_National;
 	uint32_t opts = 0;
@@ -1385,6 +1743,11 @@
 				break;
 			}
 			opts = isdn_data->opts = *optp;
+		} else if (!strcasecmp(var, "tonemap")) {
+			if (!(val = va_arg(ap, char *))) {
+				break;
+			}
+			tonemap = (const char *)val;
 		}
 	}
 
@@ -1422,20 +1785,20 @@
 	Q931SetLogLevel(&isdn_data->q931, Q931_LOG_DEBUG);
 
 	isdn_data->q931.autoRestartAck = 1;
-//	isdn_data->q931.autoConnectAck = 1;
 	isdn_data->q931.autoConnectAck = 0;
 	isdn_data->q931.autoServiceAck = 1;
 	span->signal_data = isdn_data;
 	span->signal_type = ZAP_SIGTYPE_ISDN;
 	span->outgoing_call = isdn_outgoing_call;
 
-
 	if ((opts & ZAP_ISDN_OPT_SUGGEST_CHANNEL)) {
 		span->channel_request = isdn_channel_request;
 		span->suggest_chan_id = 1;
 	}
 	span->state_map = &isdn_state_map;
 
+	zap_span_load_tones(span, tonemap);
+
 	return ZAP_SUCCESS;
 }
 
Index: libs/openzap/src/isdn/Q931StateNT.c
===================================================================
--- libs/openzap/src/isdn/Q931StateNT.c	(revision 530)
+++ libs/openzap/src/isdn/Q931StateNT.c	(working copy)
@@ -361,6 +361,9 @@
             return ret;
         }
 
+	/* store TEI in call */
+	pTrunk->call[callIndex].Tei = pMes->Tei;
+
         /* Send setup indication to user */
         ret = Q931Tx34(pTrunk,(L3UCHAR*)pMes,pMes->Size);
         if(ret != Q931E_NO_ERROR)
Index: libs/openzap/src/isdn/include/Q931.h
===================================================================
--- libs/openzap/src/isdn/include/Q931.h	(revision 530)
+++ libs/openzap/src/isdn/include/Q931.h	(working copy)
@@ -563,9 +563,10 @@
 *****************************************************************************/
 typedef struct
 {
-    L3UINT			Size;           /* Size of message in bytes             */
+    L3UINT          Size;           /* Size of message in bytes             */
     L3UCHAR         ProtDisc;       /* Protocol Discriminator               */
     L3UCHAR         MesType;        /* Message type                         */
+    L3UCHAR         Tei;            /* TEI                                  */
     L3UCHAR         CRVFlag;        /* Call reference value flag            */
     L3INT           CRV;            /* Call reference value                 */
 
Index: libs/openzap/src/isdn/Q931.c
===================================================================
--- libs/openzap/src/isdn/Q931.c	(revision 530)
+++ libs/openzap/src/isdn/Q931.c	(working copy)
@@ -378,6 +378,10 @@
 		/* Message Type */
 		m->MesType = Mes[IOff++];
 
+		/* Store tei */
+		m->Tei = tei;
+
+#if 0
 		/* d'oh a little ugly but this saves us from:
 		 *	a) doing Q.921 work in the lower levels (extracting the TEI ourselves)
 		 *	b) adding a tei parameter to _all_ Proc functions
@@ -391,8 +395,9 @@
 				pTrunk->call[callIndex].Tei = tei;
 			}
 		}
+#endif
 
-		Q931Log(pTrunk, Q931_LOG_DEBUG, "Received message from Q.921 (ind %d, tei %d, size %d)\nMesType: %d, CRVFlag %d (%s), CRV %d (Dialect: %d)\n", ind, tei, Size,
+		Q931Log(pTrunk, Q931_LOG_DEBUG, "Received message from Q.921 (ind %d, tei %d, size %d)\nMesType: %d, CRVFlag %d (%s), CRV %d (Dialect: %d)\n", ind, m->Tei, Size,
 						 m->MesType, m->CRVFlag, m->CRVFlag ? "Terminator" : "Originator", m->CRV, pTrunk->Dialect);
 
 		RetCode = Q931Umes[pTrunk->Dialect][m->MesType](pTrunk, Mes, (Q931mes_Generic *)pTrunk->L3Buf, IOff, Size - L2HSize);
Index: libs/openzap/src/zap_buffer.c
===================================================================
--- libs/openzap/src/zap_buffer.c	(revision 530)
+++ libs/openzap/src/zap_buffer.c	(working copy)
@@ -108,6 +108,27 @@
 	return buffer->used;
 }
 
+zap_size_t zap_buffer_seek(zap_buffer_t *buffer, zap_size_t datalen)
+{
+	zap_size_t reading = 0;
+
+	assert(buffer != NULL);
+
+	if (buffer->used < 1) {
+		buffer->used = 0;
+		return 0;
+	} else if (buffer->used >= datalen) {
+		reading = datalen;
+	} else {
+		reading = buffer->used;
+	}
+
+	buffer->used = buffer->actually_used - reading;
+	buffer->head = buffer->data + reading;
+
+	return reading;
+}
+
 zap_size_t zap_buffer_toss(zap_buffer_t *buffer, zap_size_t datalen)
 {
 	zap_size_t reading = 0;
@@ -137,13 +158,13 @@
 zap_size_t zap_buffer_read_loop(zap_buffer_t *buffer, void *data, zap_size_t datalen)
 {
 	zap_size_t len;
-	if ((len = zap_buffer_read(buffer, data, datalen)) == 0) {
+	if ((len = zap_buffer_read(buffer, data, datalen)) < datalen) {
 		if (buffer->loops == 0) {
 			return 0;
 		}
 		buffer->head = buffer->data;
 		buffer->used = buffer->actually_used;
-		len = zap_buffer_read(buffer, data, datalen);
+		len = zap_buffer_read(buffer, data + len, datalen - len);
 		buffer->loops--;
 	}
 	return len;
Index: libs/openzap/src/include/zap_buffer.h
===================================================================
--- libs/openzap/src/include/zap_buffer.h	(revision 530)
+++ libs/openzap/src/include/zap_buffer.h	(working copy)
@@ -122,6 +122,13 @@
  */
 void zap_buffer_destroy(zap_buffer_t **buffer);
 
+/*! \brief Seek to offset from the beginning of the buffer
+ * \param buffer buffer to seek
+ * \param datalen offset in bytes
+ * \return new position
+ */
+zap_size_t zap_buffer_seek(zap_buffer_t *buffer, zap_size_t datalen);
+
 /** @} */
 
 zap_size_t zap_buffer_zwrite(zap_buffer_t *buffer, const void *data, zap_size_t datalen);
Index: libs/openzap/mod_openzap/mod_openzap.c
===================================================================
--- libs/openzap/mod_openzap/mod_openzap.c	(revision 530)
+++ libs/openzap/mod_openzap/mod_openzap.c	(working copy)
@@ -698,6 +698,9 @@
 				zap_set_flag_locked(tech_pvt->zchan, ZAP_CHANNEL_PROGRESS);
 				zap_set_flag_locked(tech_pvt->zchan, ZAP_CHANNEL_MEDIA);
 			} else {
+				if (tech_pvt->zchan->state < ZAP_CHANNEL_STATE_PROGRESS) {
+					zap_set_state_locked_wait(tech_pvt->zchan, ZAP_CHANNEL_STATE_PROGRESS);
+				}
 				zap_set_state_locked_wait(tech_pvt->zchan, ZAP_CHANNEL_STATE_PROGRESS_MEDIA);
 			}
 		}
@@ -707,6 +710,12 @@
 			if (switch_channel_test_flag(channel, CF_OUTBOUND)) {
 				zap_set_flag_locked(tech_pvt->zchan, ZAP_CHANNEL_ANSWERED);
 			} else {
+				if (tech_pvt->zchan->state < ZAP_CHANNEL_STATE_PROGRESS) {
+					zap_set_state_locked_wait(tech_pvt->zchan, ZAP_CHANNEL_STATE_PROGRESS);
+				}
+				if (tech_pvt->zchan->state < ZAP_CHANNEL_STATE_PROGRESS_MEDIA) {
+					zap_set_state_locked_wait(tech_pvt->zchan, ZAP_CHANNEL_STATE_PROGRESS_MEDIA);
+				}
 				zap_set_state_locked_wait(tech_pvt->zchan, ZAP_CHANNEL_STATE_UP);
 			}
 		}
