[dahdi-commits] dahdi/linux.git branch "master" updated.

SVN commits to the DAHDI project dahdi-commits at lists.digium.com
Wed Feb 5 12:20:11 CST 2014


branch "master" has been updated
       via  d4868092bfdb9c6bdbdd38219c208139c70c44c7 (commit)
       via  06c45b7cd82437e169f091a891b848e8b1ae2311 (commit)
      from  fdca6f36ded2b31a273c63cd3d09d30b26eaee4f (commit)

Summary of changes:
 drivers/dahdi/dahdi-base.c    |   12 ++++++++--
 drivers/dahdi/xpp/card_pri.c  |   14 ++++++++---
 drivers/dahdi/xpp/xbus-core.c |    2 +-
 drivers/dahdi/xpp/xpp_dahdi.c |   53 ++++++++++++++++++++++++++++-------------
 drivers/dahdi/xpp/xpp_dahdi.h |    4 +++-
 include/dahdi/kernel.h        |    3 ++-
 6 files changed, 63 insertions(+), 25 deletions(-)


- Log -----------------------------------------------------------------
commit d4868092bfdb9c6bdbdd38219c208139c70c44c7
Author: Oron Peled <oron.peled at xorcom.com>
Date:   Sun Dec 29 13:43:14 2013 -0500

    xpp: PRI stability fixes
    
    * We didn't handle proper E1/T1 transitions after device registration.
    
    * Fix SPAN_REGISTERED(xpd):
      It now checks for DAHDI_FLAGBIT_REGISTERED as well, as this flag is
      set/clear by assign/unassign.
    
    * From set_pri_proto():
      - Always free/allocate channels
      - Always call dahdi_init_span()
    
    * Improve phonedev_cleanup() safety:
      - NULL pointers after free.
      - Zero number of channels at the end.
    
    * Refactor channel allocation out of phonedev_init():
      - Into phonedev_alloc_channels()
      - Also called from xpd_init_span() to prevent duplicated logic.
      - And called from set_pri_proto() to prevent our bug.
    
    Signed-off-by: Tzafrir Cohen <tzafrir.cohen at xorcom.com>

diff --git a/drivers/dahdi/xpp/card_pri.c b/drivers/dahdi/xpp/card_pri.c
index 3630565..c586115 100644
--- a/drivers/dahdi/xpp/card_pri.c
+++ b/drivers/dahdi/xpp/card_pri.c
@@ -611,7 +611,7 @@ static int set_pri_proto(xpd_t *xpd, enum pri_protocol set_proto)
 	}
 	priv->pri_protocol = set_proto;
 	priv->is_cas = -1;
-	phonedev->channels = pri_num_channels(set_proto);
+	phonedev_alloc_channels(xpd, pri_num_channels(set_proto));
 	phonedev->offhook_state = BITMASK(phonedev->channels);
 	CALL_PHONE_METHOD(card_pcm_recompute, xpd, 0);
 	priv->deflaw = deflaw;
@@ -1082,6 +1082,7 @@ static int pri_set_spantype(struct dahdi_span *span, enum spantypes spantype)
 	struct phonedev *phonedev = container_of(span, struct phonedev, span);
 	xpd_t *xpd = container_of(phonedev, struct xpd, phonedev);
 	enum pri_protocol set_proto = PRI_PROTO_0;
+	int ret;
 
 	XPD_INFO(xpd, "%s: %s\n", __func__, dahdi_spantype2str(spantype));
 	switch (spantype) {
@@ -1099,7 +1100,13 @@ static int pri_set_spantype(struct dahdi_span *span, enum spantypes spantype)
 			__func__, dahdi_spantype2str(spantype));
 		return -EINVAL;
 	}
-	return set_pri_proto(xpd, set_proto);
+	ret = set_pri_proto(xpd, set_proto);
+	if (ret < 0) {
+		XPD_ERR(xpd, "%s: set_pri_proto failed\n", __func__);
+		return ret;
+	}
+	dahdi_init_span(span);
+	return 0;
 }
 
 static int PRI_card_open(xpd_t *xpd, lineno_t pos)
@@ -1929,7 +1936,8 @@ static void PRI_card_pcm_tospan(xpd_t *xpd, xpacket_t *pack)
 				dchan_state(xpd, 0);
 		}
 		if (IS_SET(physical_mask, i)) {
-			r = XPD_CHAN(xpd, logical_chan)->readchunk;
+			struct dahdi_chan *chan = XPD_CHAN(xpd, logical_chan);
+			r = chan->readchunk;
 			// memset((u_char *)r, 0x5A, DAHDI_CHUNKSIZE);  // DEBUG
 			memcpy((u_char *)r, pcm, DAHDI_CHUNKSIZE);
 			pcm += DAHDI_CHUNKSIZE;
diff --git a/drivers/dahdi/xpp/xpp_dahdi.c b/drivers/dahdi/xpp/xpp_dahdi.c
index ffcd6dd..c0e441a 100644
--- a/drivers/dahdi/xpp/xpp_dahdi.c
+++ b/drivers/dahdi/xpp/xpp_dahdi.c
@@ -458,29 +458,28 @@ static void phonedev_cleanup(xpd_t *xpd)
 	unsigned int x;
 
 	for (x = 0; x < phonedev->channels; x++) {
-		if (phonedev->chans[x])
+		if (phonedev->chans[x]) {
 			KZFREE(phonedev->chans[x]);
-		if (phonedev->ec[x])
+			phonedev->chans[x] = NULL;
+		}
+		if (phonedev->ec[x]) {
 			KZFREE(phonedev->ec[x]);
+			phonedev->ec[x] = NULL;
+		}
 	}
+	phonedev->channels = 0;
 }
 
-__must_check static int phonedev_init(xpd_t *xpd,
-				      const xproto_table_t *proto_table,
-				      int channels, xpp_line_t no_pcm)
+int phonedev_alloc_channels(xpd_t *xpd, int channels)
 {
 	struct phonedev *phonedev = &PHONEDEV(xpd);
+	int old_channels = phonedev->channels;
 	unsigned int x;
 
-	spin_lock_init(&phonedev->lock_recompute_pcm);
+	XPD_NOTICE(xpd, "Reallocating channels: %d -> %d\n",
+			old_channels, channels);
+	phonedev_cleanup(xpd);
 	phonedev->channels = channels;
-	phonedev->no_pcm = no_pcm;
-	phonedev->offhook_state = 0x0;	/* ONHOOK */
-	phonedev->phoneops = proto_table->phoneops;
-	phonedev->digital_outputs = 0;
-	phonedev->digital_inputs = 0;
-	atomic_set(&phonedev->dahdi_registered, 0);
-	atomic_set(&phonedev->open_counter, 0);
 	for (x = 0; x < phonedev->channels; x++) {
 		if (!
 		    (phonedev->chans[x] =
@@ -501,6 +500,29 @@ err:
 	phonedev_cleanup(xpd);
 	return -ENOMEM;
 }
+EXPORT_SYMBOL(phonedev_alloc_channels);
+
+__must_check static int phonedev_init(xpd_t *xpd,
+				      const xproto_table_t *proto_table,
+				      int channels, xpp_line_t no_pcm)
+{
+	struct phonedev *phonedev = &PHONEDEV(xpd);
+
+	spin_lock_init(&phonedev->lock_recompute_pcm);
+	phonedev->no_pcm = no_pcm;
+	phonedev->offhook_state = 0x0;	/* ONHOOK */
+	phonedev->phoneops = proto_table->phoneops;
+	phonedev->digital_outputs = 0;
+	phonedev->digital_inputs = 0;
+	atomic_set(&phonedev->dahdi_registered, 0);
+	atomic_set(&phonedev->open_counter, 0);
+	if (phonedev_alloc_channels(xpd, channels) < 0)
+		goto err;
+	return 0;
+err:
+	return -ENOMEM;
+}
+
 
 /*
  * xpd_alloc - Allocator for new XPD's
@@ -1025,12 +1047,9 @@ EXPORT_SYMBOL(xpd_set_spanname);
 static void xpd_init_span(xpd_t *xpd, unsigned offset, int cn)
 {
 	struct dahdi_span *span;
-	int i;
 
 	memset(&PHONEDEV(xpd).span, 0, sizeof(struct dahdi_span));
-	for (i = 0; i < cn; i++)
-		memset(XPD_CHAN(xpd, i), 0, sizeof(struct dahdi_chan));
-
+	phonedev_alloc_channels(xpd, cn);
 	span = &PHONEDEV(xpd).span;
 	span->deflaw = DAHDI_LAW_MULAW;	/* card_* drivers may override */
 	span->channels = cn;
diff --git a/drivers/dahdi/xpp/xpp_dahdi.h b/drivers/dahdi/xpp/xpp_dahdi.h
index ab7df50..e50c283 100644
--- a/drivers/dahdi/xpp/xpp_dahdi.h
+++ b/drivers/dahdi/xpp/xpp_dahdi.h
@@ -38,6 +38,7 @@ xpd_t *xpd_alloc(xbus_t *xbus, int unit, int subunit, int subtype, int subunits,
 		 int channels);
 void xpd_free(xpd_t *xpd);
 void xpd_remove(xpd_t *xpd);
+int phonedev_alloc_channels(xpd_t *xpd, int channels);
 void update_xpd_status(xpd_t *xpd, int alarm_flag);
 const char *xpp_echocan_name(const struct dahdi_chan *chan);
 int xpp_echocan_create(struct dahdi_chan *chan, struct dahdi_echocanparams *ecp,
@@ -64,6 +65,7 @@ void notify_rxsig(xpd_t *xpd, int pos, enum dahdi_rxsig rxsig);
 extern struct proc_dir_entry *xpp_proc_toplevel;
 #endif
 
-#define	SPAN_REGISTERED(xpd)	atomic_read(&PHONEDEV(xpd).dahdi_registered)
+#define	SPAN_REGISTERED(xpd)  (atomic_read(&PHONEDEV(xpd).dahdi_registered) && \
+		test_bit(DAHDI_FLAGBIT_REGISTERED, &PHONEDEV(xpd).span.flags))
 
 #endif /* XPP_DAHDI_H */

commit 06c45b7cd82437e169f091a891b848e8b1ae2311
Author: Tzafrir Cohen <tzafrir.cohen at xorcom.com>
Date:   Tue Jan 28 21:27:50 2014 +0200

    dahdi_get_auto_assigned_spans
    
    Commit 74e949c33aeb6cf2cf2c33364e12b227c4579ca7 exported the module
    variable dahdi.auto_assigned_spans. However this is not a good name.
    
    This commit reverts the export and replaces it with a new function to
    get the value of the variable.
    
    Signed-off-by: Tzafrir Cohen <tzafrir.cohen at xorcom.com>
    Acked-by: Russ Meyerriecks <rmeyerriecks at digium.com>

diff --git a/drivers/dahdi/dahdi-base.c b/drivers/dahdi/dahdi-base.c
index 6994f29..c8e58cf 100644
--- a/drivers/dahdi/dahdi-base.c
+++ b/drivers/dahdi/dahdi-base.c
@@ -7374,11 +7374,19 @@ int dahdi_assign_device_spans(struct dahdi_device *ddev)
 	return 0;
 }
 
-int auto_assign_spans = 1;
-EXPORT_SYMBOL(auto_assign_spans);
+static int auto_assign_spans = 1;
 static const char *UNKNOWN = "";
 
 /**
+ * dahdi_auto_assign_spans - is the parameter auto_assign_spans set?
+ */
+int dahdi_get_auto_assign_spans(void)
+{
+	return auto_assign_spans;
+}
+EXPORT_SYMBOL(dahdi_get_auto_assign_spans);
+
+/**
  * _dahdi_register_device - Registers a DAHDI device and assign its spans.
  * @ddev:	the DAHDI device
  *
diff --git a/drivers/dahdi/xpp/xbus-core.c b/drivers/dahdi/xpp/xbus-core.c
index 316d2be..8887c1e 100644
--- a/drivers/dahdi/xpp/xbus-core.c
+++ b/drivers/dahdi/xpp/xbus-core.c
@@ -1118,7 +1118,7 @@ void xbus_populate(void *data)
 	 */
 	xbus_request_sync(xbus, SYNC_MODE_PLL);
 	elect_syncer("xbus_populate(end)");	/* FIXME: try to do it later */
-	if (!auto_assign_spans)
+	if (!dahdi_get_auto_assign_spans())
 		xbus_register_dahdi_device(xbus);
 out:
 	XBUS_DBG(DEVICES, xbus, "Leaving\n");
diff --git a/include/dahdi/kernel.h b/include/dahdi/kernel.h
index dabd123..f2f9ec5 100644
--- a/include/dahdi/kernel.h
+++ b/include/dahdi/kernel.h
@@ -1280,7 +1280,8 @@ static inline void dahdi_ec_span(struct dahdi_span *span)
 }
 
 extern struct file_operations *dahdi_transcode_fops;
-extern int auto_assign_spans;
+
+int dahdi_get_auto_assign_spans(void);
 
 /* Don't use these directly -- they're not guaranteed to
    be there. */

-----------------------------------------------------------------------


-- 
dahdi/linux.git



More information about the dahdi-commits mailing list