[svn-commits] sruffell: branch sruffell/zaptel-1.4-transcoder r4312 - /team/sruffell/zaptel...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Tue May 20 16:58:57 CDT 2008


Author: sruffell
Date: Tue May 20 16:58:56 2008
New Revision: 4312

URL: http://svn.digium.com/view/zaptel?view=rev&rev=4312
Log:
- Extend the debug network interface to allow sending commands to the
  transcoder directly.
- Update network interface for 2.6.24 kernels (NAPI changed).  

Modified:
    team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/base.c
    team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test.c
    team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test_threaded.c
    team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wcdte_net.c
    team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wctc4xxp.h

Modified: team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/base.c
URL: http://svn.digium.com/view/zaptel/team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/base.c?view=diff&rev=4312&r1=4311&r2=4312
==============================================================================
--- team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/base.c (original)
+++ team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/base.c Tue May 20 16:58:56 2008
@@ -581,7 +581,9 @@
 
 static void wcdte_capture_packet(struct wcdte *wc, const struct dte_cmd *cmd)
 {
-	wcdte_net_capture_cmd(wc, cmd);
+	if (!(cmd->flags & DO_NOT_CAPTURE)) {
+		wcdte_net_capture_cmd(wc, cmd);
+	}
 }
 
 /**
@@ -597,8 +599,7 @@
 	spin_unlock_irqrestore(&wc->cmd_list_lock, flags);
 }
 
-static void
-dte_transmit_cmd(struct wcdte *wc, struct dte_cmd *cmd)
+void dte_transmit_cmd(struct wcdte *wc, struct dte_cmd *cmd)
 {
 	int res;
 
@@ -1813,11 +1814,10 @@
 	return 0;
 }
 
-static int 
-wcdte_boot_processor(struct wcdte *wc, const struct firmware *firmware)
-{
-	unsigned int reg, ret;
-
+int  wcdte_turn_off_booted_led(struct wcdte *wc)
+{
+	int ret = 0;
+	int reg;
 #ifndef USE_TEST_HW
 	ENTERING();
 	/* Turn off auto negotiation */
@@ -1842,24 +1842,36 @@
 
 	/* Turn off booted LED */
 	wcdte_setctl(wc, 0x00A0, 0x04084000);
-
 #endif
-
 	reg = wcdte_getctl(wc, 0x00fc);
 	DTE_DEBUG(DTE_DEBUG_GENERAL, "LINK STATUS: reg(0xfc) = %X\n", reg);
 
 	reg = wcdte_getctl(wc, 0x00A0);
 
+	return ret;
+}
+
+void wcdte_turn_on_booted_led(struct wcdte *wc)
+{
+	wcdte_setctl(wc, 0x00A0, 0x04080000);
+}
+
+static int 
+wcdte_boot_processor(struct wcdte *wc, const struct firmware *firmware)
+{
+	int ret;
+
+	wcdte_turn_off_booted_led(wc);
+
 	if ((ret = wcdte_load_firmware(wc, firmware))) {
 		LEAVING();
 		return ret;
 	}
-	
 	
 	/* Turn on booted LED */
-	wcdte_setctl(wc, 0x00A0, 0x04080000);
+	wcdte_turn_on_booted_led(wc);
+
 	DTE_DEBUG(DTE_DEBUG_GENERAL, "Successfully booted DTE processor.\n");
-
 	LEAVING();
 	return 0;
 }

Modified: team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test.c
URL: http://svn.digium.com/view/zaptel/team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test.c?view=diff&rev=4312&r1=4311&r2=4312
==============================================================================
--- team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test.c (original)
+++ team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test.c Tue May 20 16:58:56 2008
@@ -148,7 +148,6 @@
 	if (ioctl(fd, ZT_TC_ALLOCATE, &fmts)) {
 		printf("Unable to attach transcoder: %s\n", strerror(errno));
 		close(fd);
-
 		return -1;
 	}
 
@@ -259,7 +258,7 @@
 					i += tctest_info.numchans[j];
  
  				if (open_transcoder(&ztp[i], AST_FORMAT_G729A, AST_FORMAT_ULAW)) {
-					continue;
+					exit(-1);
 				}
 
 				memset(packet_out, 0, sizeof(packet_out));

Modified: team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test_threaded.c
URL: http://svn.digium.com/view/zaptel/team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test_threaded.c?view=diff&rev=4312&r1=4311&r2=4312
==============================================================================
--- team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test_threaded.c (original)
+++ team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/codec_test_threaded.c Tue May 20 16:58:56 2008
@@ -208,8 +208,8 @@
 
 	if (ioctl(fd, ZT_TC_ALLOCATE, &fmt)) {
 		printf("Unable to attach transcoder: %s\n", strerror(errno));
-		close(fd);
-
+		/* close(fd); */
+		exit(-1);
 		return -1;
 	}
 

Modified: team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wcdte_net.c
URL: http://svn.digium.com/view/zaptel/team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wcdte_net.c?view=diff&rev=4312&r1=4311&r2=4312
==============================================================================
--- team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wcdte_net.c (original)
+++ team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wcdte_net.c Tue May 20 16:58:56 2008
@@ -33,11 +33,13 @@
 
 #include <linux/kernel.h>
 #include <linux/pci.h>
+#include <linux/netdevice.h>
 #include <linux/etherdevice.h>
 #include <linux/delay.h>
 
-
 #define HERE() printk(KERN_DEBUG "HERE: %s:%d\n", __FILE__, __LINE__)
+
+#define MAX_CAPTURED_PACKETS 5000
 
 static struct sk_buff * 
 wcdte_cmd_to_skb(struct net_device *netdev, const struct dte_cmd *cmd)
@@ -53,119 +55,228 @@
 	return skb;
 }
 
+static struct dte_cmd *
+wcdte_skb_to_cmd(struct wcdte *wc, const struct sk_buff *skb)
+{
+	const unsigned long alloc_flags = in_interrupt() ? GFP_ATOMIC : GFP_KERNEL;
+	struct dte_cmd *cmd;
+	/* const static char dev_mac[] = { 0x00, 0x11, 0x22, 0x33, 0x44, 0x55}; */
+	if ((cmd = __alloc_cmd(alloc_flags, 0))) {
+		int res;
+		cmd->cmdlen = skb->len;
+		if ((res = skb_copy_bits(skb, 0, cmd->cmd, cmd->cmdlen))) {
+			DTE_PRINTK(WARNING, 
+			   "Failed call to skb_copy_bits.\n");
+			free_cmd(cmd);
+			cmd = NULL;
+		}
+		/* When we set up our interface we indicated that we do not
+		 * support ARP.  Therefore, the destination MAC on packets
+		 * arriving from the kernel networking components are not
+		 * going to be correct. Let's fix that here.
+		 */
+		/* \todo let us just use whatever was in the packet already... */
+		/* memcpy(&cmd->cmd[6], dev_mac, sizeof(dev_mac)); */
+	}
+	return cmd;
+}
+
 static void wcdte_net_set_multi(struct net_device *netdev)
 {
 	struct wcdte *wc = netdev->priv;
+	DTE_DEBUG(DTE_DEBUG_GENERAL, "%s promiscuity:%d\n", 
+	   __FUNCTION__, netdev->promiscuity);
+}
+
+static int wcdte_net_up(struct net_device *netdev)
+{
+	struct wcdte *wc = netdev->priv;
 	DTE_DEBUG(DTE_DEBUG_GENERAL, "%s\n", __FUNCTION__);
-}
-
-static int wcdte_net_up(struct net_device *netdev)
+#if 1
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
+	netif_poll_enable(netdev);
+#else
+	napi_enable(&wc->napi);
+#endif
+#endif
+	return 0;
+}
+
+static int wcdte_net_down(struct net_device *netdev)
 {
 	struct wcdte *wc = netdev->priv;
 	DTE_DEBUG(DTE_DEBUG_GENERAL, "%s\n", __FUNCTION__);
-	netif_poll_enable(netdev);
+#if 1
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
+	netif_poll_disable(netdev);
+#else
+	napi_disable(&wc->napi);
+#endif
+#endif
 	return 0;
 }
 
-static int wcdte_net_down(struct net_device *netdev)
-{
-	struct wcdte *wc = netdev->priv;
-	DTE_DEBUG(DTE_DEBUG_GENERAL, "%s\n", __FUNCTION__);
-	netif_poll_disable(netdev);
-	return 0;
-}
-
 static int wcdte_hard_start_xmit(struct sk_buff *skb, struct net_device *netdev)
 {
 	struct wcdte *wc = netdev->priv;
-	DTE_DEBUG(DTE_DEBUG_GENERAL, "%s\n", __FUNCTION__);
+	struct dte_cmd *cmd;
+
+	/* We set DO_NOT_CAPTURE because this packet was already captured by
+	 * in code higher up in the networking stack.  We don't want to
+	 * capture it twice. 
+	 */
+	if ((cmd = wcdte_skb_to_cmd(wc, skb))) {
+		cmd->flags |= DO_NOT_CAPTURE; 
+		dte_transmit_cmd(wc, cmd);
+	}
+
 	dev_kfree_skb_any(skb);
 	return NETDEV_TX_OK;
 }
 
+static int wcdte_net_receive(struct wcdte *wc, int max)
+{
+	int count = 0;
+	struct sk_buff *skb;
+	WARN_ON(0 == max);
+	while ((skb = skb_dequeue(&wc->captured_packets))) {
+		netif_receive_skb(skb);
+		if (++count >= max) {
+			break;
+		}
+	}
+	return count;
+}
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
 static int wcdte_poll(struct net_device *netdev, int *budget)
 {
-	int res;
-	struct sk_buff *skb;
 	struct wcdte *wc = netdev->priv;
 	int count = 0;
 	int quota = min(netdev->quota, *budget);
 
-	while ((skb = skb_dequeue(&wc->captured_packets)) && (count++ < quota)) {
-		if ((res = netif_receive_skb(skb))) {
-			if (NET_RX_DROP == res ) {
-				DTE_DEBUG(DTE_DEBUG_GENERAL, 
-				   "Kernel dropped packet.\n");
-			} else {
-				DTE_DEBUG(DTE_DEBUG_GENERAL, 
-				   "ret = %d\n", res);
-			}
-		}
-	}
+	count = wcdte_net_receive(wc, quota);
 
 	*budget -=       count;
 	netdev->quota -= count;
 
-	if (skb) {
-		/* We still have socket buffers ready. */
-		return -1;
-	} else {
-		/* There were not any more buffers in the queue, so we're
-		 * done. */
+	if (!skb_queue_len(&wc->captured_packets)) {
 		netif_rx_complete(netdev);
 		return 0;
-	}
+	} else {
+		return -1;
+	}
+}
+#else
+static int wcdte_poll(struct napi_struct *napi, int budget)
+{
+	struct wcdte *wc = container_of(napi, struct wcdte, napi);
+	int count;
+
+	count = wcdte_net_receive(wc, budget);
+
+	if (!skb_queue_len(&wc->captured_packets)) {
+		netif_rx_complete(wc->netdev, &wc->napi);
+	}
+	return count;
+}
+#endif
+
+static struct net_device_stats *
+wcdte_net_get_stats(struct net_device *netdev)
+{
+	struct wcdte *wc = netdev->priv;
+	return &wc->net_stats;
+}
+
+/* Wait until this device is put into promiscuous mode, or we timeout. */
+static void wcdte_net_waitfor_promiscuous(struct wcdte *wc)
+{
+	unsigned int seconds = 15;
+	unsigned long start = jiffies;
+	struct net_device *netdev = wc->netdev;
+
+	DTE_PRINTK(INFO, 
+	   "Waiting %d seconds for adapter to be placed in " \
+	   "promiscuous mode for early trace.\n", seconds);
+
+	while (!netdev->promiscuity) {
+		if (signal_pending(current)) {
+			DTE_PRINTK(INFO, 
+			   "Aborting wait due to signal.\n");
+			break;
+		}
+		msleep(100);
+		if (time_after(jiffies, start + (seconds * HZ))) {
+			DTE_PRINTK(INFO,
+			   "Aborting wait due to timeout.\n");
+			break;
+		}
+	}
+}
+
+static int wcdte_ioctl(struct net_device *netdev, struct ifreq *ifr, int cmd)
+{
+	struct wcdte *wc = netdev->priv;
+	DTE_PRINTK(INFO, "In %s with cmd %04x\n", __FUNCTION__, cmd);
+	switch(cmd) {
+	case 0x89f0:
+		down(&wc->chansem);
+		wcdte_turn_off_booted_led(wc);
+		break;
+	case 0x89f1:
+		wcdte_turn_on_booted_led(wc);
+		up(&wc->chansem);
+		break;
+	default:
+		return -EOPNOTSUPP;
+	};
+	return 0;
 }
 
 int wcdte_net_register(struct wcdte *wc)
 {
 	int res;
 	struct net_device *netdev;
-	netdev = alloc_netdev(0, wc->board_name, ether_setup);
-	if (NULL == netdev) {
+	const char our_mac[] = { 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff};
+
+	if (!(netdev = alloc_netdev(0, wc->board_name, ether_setup))) {
 		return -ENOMEM;
 	}
 
+	memcpy(netdev->dev_addr, our_mac, sizeof(our_mac));
 	netdev->priv = wc;
 	netdev->set_multicast_list = &wcdte_net_set_multi;
 	netdev->open = &wcdte_net_up;
 	netdev->stop = &wcdte_net_down;
 	netdev->hard_start_xmit = &wcdte_hard_start_xmit;
+	netdev->get_stats = &wcdte_net_get_stats;
+	netdev->do_ioctl = &wcdte_ioctl;
+	netdev->promiscuity = 0;
+	netdev->flags |= IFF_NOARP;
+#	if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
 	netdev->poll = &wcdte_poll;
 	netdev->weight = 64;
-	set_bit(__LINK_STATE_START, &netdev->state);
+#	else
+	netif_napi_add(netdev, &wc->napi, &wcdte_poll, 64);
+#	endif
+
+	if ((res = register_netdev(netdev))) {
+		DTE_PRINTK(WARNING, 
+		   "Failed to register network device %s.\n",
+		   wc->board_name);
+		goto error_sw;
+	}
 
 	wc->netdev = netdev;
-
 	skb_queue_head_init(&wc->captured_packets);
 
-	DTE_PRINTK(DEBUG, "Creating network device %s for debug.\n", wc->board_name);
-	if ((res = register_netdev(netdev))) {
-		goto error_sw;
-	}
-
-	netif_poll_disable(netdev);
-
 	if (debug & DTE_DEBUG_NETWORK_EARLY) {
-		unsigned int seconds = 15;
-		DTE_PRINTK(INFO, 
-		   "Waiting %d seconds for adapter to be placed in " \
-		   "promiscuous mode for early trace.\n", seconds);
-		while (!netdev->promiscuity) {
-			if (signal_pending(current)) {
-				DTE_PRINTK(INFO, 
-				   "Aborting wait due to signal.\n");
-				break;
-			}
-			msleep(1000);
-			if (!(seconds--)) {
-				DTE_PRINTK(INFO,
-				   "Aborting wait due to timeout.\n");
-				break;
-			}
-		}
-	}
-
+		wcdte_net_waitfor_promiscuous(wc);
+	}
+
+	DTE_PRINTK(DEBUG, 
+	   "Created network device %s for debug.\n", wc->board_name);
 	return 0;
 
 error_sw:
@@ -198,21 +309,35 @@
 void wcdte_net_capture_cmd(struct wcdte *wc, const struct dte_cmd *cmd)
 {
 	struct sk_buff *skb;
-
-	if (!wc->netdev) {
-		return;
-	}
-
-	if (!wc->netdev->promiscuity) {
-		return;
-	}
-
-	if (!(skb = wcdte_cmd_to_skb(wc->netdev, cmd))) {
+	struct net_device *netdev = wc->netdev;
+
+	if (!netdev) {
+		return;
+	}
+
+	/* No need to capture if there isn't anyone listening. */
+	if (!(netdev->flags & IFF_UP)) {
+		return;
+	}
+	
+	/* I don't think the packet queue should ever get this long, but just
+	 * in case, we'll limit it. 
+	 */
+	if (skb_queue_len(&wc->captured_packets) > MAX_CAPTURED_PACKETS) {
+		WARN_ON_ONCE(1);
+		return;
+	}
+
+	if (!(skb = wcdte_cmd_to_skb(netdev, cmd))) {
 		return;
 	}
 
 	skb_queue_tail(&wc->captured_packets, skb);
-	netif_rx_schedule(wc->netdev);
+#	if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
+	netif_rx_schedule(netdev);
+#	else
+	netif_rx_schedule(netdev, &wc->napi);
+#	endif
 	return;
 }
 

Modified: team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wctc4xxp.h
URL: http://svn.digium.com/view/zaptel/team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wctc4xxp.h?view=diff&rev=4312&r1=4311&r2=4312
==============================================================================
--- team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wctc4xxp.h (original)
+++ team/sruffell/zaptel-1.4-transcoder/kernel/wctc4xxp/wctc4xxp.h Tue May 20 16:58:56 2008
@@ -37,6 +37,8 @@
 #include <linux/netdevice.h>
 #include <linux/completion.h>
 
+#define CONFIG_WCDTE_NETWORK_IF
+
 #define WARN() WARN_ON(1)
 #define DTE_PRINTK(_lvl, _fmt, _args...) \
 	   printk(KERN_##_lvl "%s: " _fmt, (wc)->board_name, ## _args)
@@ -64,6 +66,7 @@
 	struct list_head node;
 #define NO_AUTO_FREE_CMD 	(1 << 0)
 #define TX_COMPLETE	        (1 << 1)	
+#define DO_NOT_CAPTURE          (1 << 2)
 	unsigned long flags;
 	struct completion complete;
 	/* cmd must be the last field. */
@@ -125,8 +128,13 @@
 	spinlock_t reglock;
 	wait_queue_head_t regq;
 	unsigned long rcvflags;
+	struct semaphore chansem;
+	atomic_t open_channel_count;
+
+#define DTEF_RESET_PENDING         0x001
+#define DTEF_SHUTDOWN_PENDING      0x002
+	unsigned long flags;
 	
-	struct semaphore chansem;
 	spinlock_t cmd_list_lock;
 	struct list_head cmd_list;
 	/* This is a list to hold those commands which were flagged to not
@@ -144,27 +152,53 @@
 	unsigned char numchannels;
 	unsigned char complexname[40];
 
+	/* 
+	 * This section contains the members necessary to communicate with the
+	 * physical interface to the transcoding engine.
+	 *
+	 */
 	unsigned long iobase;
+	struct dte_descriptor_ring *txd;
+	struct dte_descriptor_ring *rxd;
 	
 #if DEFERRED_PROCESSING == WORKQUEUE
 	struct workqueue_struct *dte_wq;
 	struct work_struct dte_work;
 #endif
-
-	struct dte_descriptor_ring *txd;
-	struct dte_descriptor_ring *rxd;
+	struct work_struct reset_work;
 
 	struct zt_transcoder *uencode;
 	struct zt_transcoder *udecode;
 	struct channel_pvt *encoders;
 	struct channel_pvt *decoders;
+
 #ifdef CONFIG_DEBUG_FS
 	struct dentry *debugfs_file;
 #endif
 
+	/*
+	 * This section contains the members necessary for exporting the
+	 * network interface to the host system.  This is only used for
+	 * debugging purposes.
+	 *
+	 */
+#ifdef CONFIG_WCDTE_NETWORK_IF
 	struct sk_buff_head captured_packets;
 	struct net_device *netdev;
+	struct net_device_stats net_stats;
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,24)
+	struct napi_struct napi;
+#endif
+#endif 
+
 };
+
+static inline int wcdte_reset_pending(struct wcdte *wc) {
+	return test_bit(DTEF_RESET_PENDING, &wc->flags);
+}
+
+extern int  wcdte_turn_off_booted_led(struct wcdte *wc);
+extern void wcdte_turn_on_booted_led(struct wcdte *wc);
 
  /* \todo This macro is a candidate for removal.  It's still here because of
  * how the commands are passed to this zt_send_cmd */
@@ -181,6 +215,8 @@
 	__res;                                                               \
 })
 
-#define CONFIG_WCDTE_NETWORK_IF
+
+/* Functions exported from base.c */
+void dte_transmit_cmd(struct wcdte *, struct dte_cmd *);
 
 #endif /* __WCTC4XXP_H__ */




More information about the svn-commits mailing list