diff --git a/UPGRADE-1.8.txt b/UPGRADE-1.8.txt
index e9bee24de555d3c097709f0dac4b506809c0fc99..643461e28d60928610723ab098a9b4e9de80df30 100644
--- a/UPGRADE-1.8.txt
+++ b/UPGRADE-1.8.txt
@@ -72,6 +72,15 @@ From 1.6.2 to 1.8:
   The new channel naming for PRI channels is:
   DAHDI/i<span>/<number>[:<subaddress>]-<sequence-number>
 
+* Added CHANNEL(dahdi_span), CHANNEL(dahdi_channel), and CHANNEL(dahdi_type)
+  so the dialplan can determine the B channel currently in use by the channel.
+  Use CHANNEL(no_media_path) to determine if the channel even has a B channel.
+
+* Added AMI event DAHDIChannel to associate a DAHDI channel with an Asterisk
+  channel so AMI applications can passively determine the B channel currently
+  in use.  Calls with "no-media" as the DAHDIChannel do not have an associated
+  B channel.  No-media calls are either on hold or call-waiting.
+
 * The ChanIsAvail application has been changed so the AVAILSTATUS variable
   no longer contains both the device state and cause code. The cause code
   is now available in the AVAILCAUSECODE variable. If existing dialplan logic
diff --git a/channels/chan_dahdi.c b/channels/chan_dahdi.c
index 4febe690b82b88bdf2a099edfb8984b3a55df1c8..4baee23b99278be6adc35802073f48b2437dc01d 100644
--- a/channels/chan_dahdi.c
+++ b/channels/chan_dahdi.c
@@ -2109,6 +2109,58 @@ static void my_deadlock_avoidance_private(void *pvt)
 	DEADLOCK_AVOIDANCE(&p->lock);
 }
 
+/*!
+ * \internal
+ * \brief Post an AMI DAHDI channel association event.
+ * \since 1.8
+ *
+ * \param p DAHDI private pointer
+ * \param chan Channel associated with the private pointer
+ *
+ * \return Nothing
+ */
+static void dahdi_ami_channel_event(struct dahdi_pvt *p, struct ast_channel *chan)
+{
+	char ch_name[20];
+
+	if (p->channel < CHAN_PSEUDO) {
+		/* No B channel */
+		snprintf(ch_name, sizeof(ch_name), "no-media (%d)", p->channel);
+	} else if (p->channel == CHAN_PSEUDO) {
+		/* Pseudo channel */
+		strcpy(ch_name, "pseudo");
+	} else {
+		/* Real channel */
+		snprintf(ch_name, sizeof(ch_name), "%d", p->channel);
+	}
+	ast_manager_event(chan, EVENT_FLAG_CALL, "DAHDIChannel",
+		"Channel: %s\r\n"
+		"Uniqueid: %s\r\n"
+		"DAHDISpan: %d\r\n"
+		"DAHDIChannel: %s\r\n",
+		chan->name,
+		chan->uniqueid,
+		p->span,
+		ch_name);
+}
+
+/*!
+ * \internal
+ * \brief Post an AMI DAHDI channel association event.
+ * \since 1.8
+ *
+ * \param pvt DAHDI private pointer
+ * \param chan Channel associated with the private pointer
+ *
+ * \return Nothing
+ */
+static void my_ami_channel_event(void *pvt, struct ast_channel *chan)
+{
+	struct dahdi_pvt *p = pvt;
+
+	dahdi_ami_channel_event(p, chan);
+}
+
 /* linear_mode = 0 - turn linear mode off, >0 - turn linear mode on
 * 	returns the last value of the linear setting 
 */ 
@@ -3294,6 +3346,7 @@ static struct sig_pri_callback dahdi_pri_callbacks =
 	.module_ref = my_module_ref,
 	.module_unref = my_module_unref,
 	.open_media = my_pri_open_media,
+	.ami_channel_event = my_ami_channel_event,
 };
 #endif	/* defined(HAVE_PRI) */
 
@@ -6792,6 +6845,41 @@ static int dahdi_func_read(struct ast_channel *chan, const char *function, char
 		ast_mutex_lock(&p->lock);
 		snprintf(buf, len, "%f", p->txgain);
 		ast_mutex_unlock(&p->lock);
+	} else if (!strcasecmp(data, "dahdi_channel")) {
+		ast_mutex_lock(&p->lock);
+		snprintf(buf, len, "%d", p->channel);
+		ast_mutex_unlock(&p->lock);
+	} else if (!strcasecmp(data, "dahdi_span")) {
+		ast_mutex_lock(&p->lock);
+		snprintf(buf, len, "%d", p->span);
+		ast_mutex_unlock(&p->lock);
+	} else if (!strcasecmp(data, "dahdi_type")) {
+		ast_mutex_lock(&p->lock);
+		switch (p->sig) {
+#if defined(HAVE_OPENR2)
+		case SIG_MFCR2:
+			ast_copy_string(buf, "mfc/r2", len);
+			break;
+#endif	/* defined(HAVE_OPENR2) */
+#if defined(HAVE_PRI)
+		case SIG_PRI_LIB_HANDLE_CASES:
+			ast_copy_string(buf, "pri", len);
+			break;
+#endif	/* defined(HAVE_PRI) */
+		case 0:
+			ast_copy_string(buf, "pseudo", len);
+			break;
+#if defined(HAVE_SS7)
+		case SIG_SS7:
+			ast_copy_string(buf, "ss7", len);
+			break;
+#endif	/* defined(HAVE_SS7) */
+		default:
+			/* The only thing left is analog ports. */
+			ast_copy_string(buf, "analog", len);
+			break;
+		}
+		ast_mutex_unlock(&p->lock);
 #if defined(HAVE_PRI)
 #if defined(HAVE_PRI_REVERSE_CHARGE)
 	} else if (!strcasecmp(data, "reversecharge")) {
@@ -9530,6 +9618,7 @@ static struct ast_channel *dahdi_new(struct dahdi_pvt *i, int state, int startpb
 
 	ast_module_ref(ast_module_info->self);
 
+	dahdi_ami_channel_event(i, tmp);
 	if (startpbx) {
 #ifdef HAVE_OPENR2
 		if (i->mfcr2call) {
@@ -13089,6 +13178,7 @@ static int dahdi_new_pri_nobch_channel(struct sig_pri_span *pri)
 		nobch_channel = CHAN_PSEUDO - 1;
 	}
 	pvt->channel = nobch_channel;
+	pvt->span = pri->span;
 	chan->channel = pvt->channel;
 
 	dahdi_nobch_insert(pri, pvt);
diff --git a/channels/sig_pri.c b/channels/sig_pri.c
index 05d0fa4fe40bce2306329595d1d126e2eda077a2..4425b188e8da8d5f3250901c590e6374d4b71346 100644
--- a/channels/sig_pri.c
+++ b/channels/sig_pri.c
@@ -932,6 +932,24 @@ static void sig_pri_open_media(struct sig_pri_chan *p)
 	}
 }
 
+/*!
+ * \internal
+ * \brief Post an AMI B channel association event.
+ * \since 1.8
+ *
+ * \param p Channel private control structure.
+ *
+ * \note Assumes the private and owner are locked.
+ *
+ * \return Nothing
+ */
+static void sig_pri_ami_channel_event(struct sig_pri_chan *p)
+{
+	if (p->calls->ami_channel_event) {
+		p->calls->ami_channel_event(p->chan_pvt, p->owner);
+	}
+}
+
 struct ast_channel *sig_pri_request(struct sig_pri_chan *p, enum sig_pri_law law, const struct ast_channel *requestor, int transfercapability)
 {
 	struct ast_channel *ast;
@@ -1333,6 +1351,10 @@ static int pri_fixup_principle(struct sig_pri_span *pri, int principle, q931_cal
 			sig_pri_open_media(new_chan);
 		}
 
+		if (new_chan->owner) {
+			sig_pri_ami_channel_event(new_chan);
+		}
+
 		sig_pri_unlock_private(old_chan);
 		if (new_chan->owner) {
 			ast_channel_unlock(new_chan->owner);
diff --git a/channels/sig_pri.h b/channels/sig_pri.h
index 2d41664c07dbb90ccc4741cca31116da9705105a..f4aef912d22898abb5aa6bbcaa28b9aa1c31500b 100644
--- a/channels/sig_pri.h
+++ b/channels/sig_pri.h
@@ -200,6 +200,16 @@ struct sig_pri_callback {
 
 	void (* const open_media)(void *pvt);
 
+	/*!
+	 * \brief Post an AMI B channel association event.
+	 *
+	 * \param pvt Private structure of the user of this module.
+	 * \param chan Channel associated with the private pointer
+	 *
+	 * \return Nothing
+	 */
+	void (* const ami_channel_event)(void *pvt, struct ast_channel *chan);
+
 	/*! Reference the parent module. */
 	void (*module_ref)(void);
 	/*! Unreference the parent module. */
diff --git a/funcs/func_channel.c b/funcs/func_channel.c
index 4ae08efc2ab89bc9a3996ca008314120fd19d29a..dcc0190b4b0966a89a4cc529bc43cb4efbd298b0 100644
--- a/funcs/func_channel.c
+++ b/funcs/func_channel.c
@@ -224,6 +224,22 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
 				</enumlist>
 				<para><emphasis>chan_dahdi</emphasis> provides the following additional options:</para>
 				<enumlist>
+					<enum name="dahdi_channel">
+						<para>R/O DAHDI channel related to this channel.</para>
+					</enum>
+					<enum name="dahdi_span">
+						<para>R/O DAHDI span related to this channel.</para>
+					</enum>
+					<enum name="dahdi_type">
+						<para>R/O DAHDI channel type, one of:</para>
+						<enumlist>
+							<enum name="analog" />
+							<enum name="mfc/r2" />
+							<enum name="pri" />
+							<enum name="pseudo" />
+							<enum name="ss7" />
+						</enumlist>
+					</enum>
 					<enum name="keypad_digits">
 						<para>R/O PRI Keypad digits that came in with the SETUP message.</para>
 					</enum>