[PATCH 5/5] staging: unisys: add error messages to visornic

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



From: Tim Sell <Timothy.Sell@xxxxxxxxxx>

Add error message to genuine rare error paths, and debug messages
to enable relatively non-verbose tracing of code paths

You can enable debug messages by including this on the kernel command line:

    visornic.dyndbg=+p

or by this from the command line:

    echo "module visornic +p" > <debugfs>/dynamic_debug/control

Refer to Documentation/dynamic-debug-howto.txt for more details.

In addition to the new debug and error messages, a message like the
following will be logged every time a visornic device is probed, which
will enable you to map back-and-forth between visorbus device names
(e.g., "vbus2:dev0") and netdev names (e.g., "eth0"):

    visornic vbus2:dev0: visornic_probe success netdev=eth0

With this patch and visornic debugging enabled, you should expect to see
messages like the following in the most-common scenarios:

* driver loaded:

      visornic_init

* device probed:

      visornic vbus2:dev0: visornic_probe
      visor_thread_start
      visor_thread_start success

* network interface configured (ifconfig):

      net eth0: visornic_open
      net eth0: visornic_enable_with_timeout
      net eth0: visornic_enable_with_timeout success
      net eth0: visornic_open success

staging: unisys: More comments from Jes

Signed-off-by: Tim Sell <Timothy.Sell@xxxxxxxxxx>
Signed-off-by: David Kershner <david.kershner@xxxxxxxxxx>
Signed-off-by: Benjamin Romer <benjamin.romer@xxxxxxxxxx>
---
 drivers/staging/unisys/visornic/visornic_main.c | 127 ++++++++++++++++++++++--
 1 file changed, 116 insertions(+), 11 deletions(-)

diff --git a/drivers/staging/unisys/visornic/visornic_main.c b/drivers/staging/unisys/visornic/visornic_main.c
index 7100744..7b9821c 100644
--- a/drivers/staging/unisys/visornic/visornic_main.c
+++ b/drivers/staging/unisys/visornic/visornic_main.c
@@ -294,14 +294,18 @@ static int visor_thread_start(struct visor_thread_info *thrinfo,
 			      int (*threadfn)(void *),
 			      void *thrcontext, char *name)
 {
+	pr_debug("%s\n", __func__);
 	/* used to stop the thread */
 	init_completion(&thrinfo->has_stopped);
 	thrinfo->task = kthread_run(threadfn, thrcontext, name);
 	if (IS_ERR(thrinfo->task)) {
+		pr_debug("%s failed (%ld)\n",
+			 __func__, PTR_ERR(thrinfo->task));
 		thrinfo->id = 0;
 		return -EINVAL;
 	}
 	thrinfo->id = thrinfo->task->pid;
+	pr_debug("%s success\n", __func__);
 	return 0;
 }
 
@@ -317,10 +321,12 @@ static void visor_thread_stop(struct visor_thread_info *thrinfo)
 	if (!thrinfo->id)
 		return;	/* thread not running */
 
+	pr_debug("%s\n", __func__);
 	kthread_stop(thrinfo->task);
 	/* give up if the thread has NOT died in 1 minute */
 	if (wait_for_completion_timeout(&thrinfo->has_stopped, 60 * HZ))
 		thrinfo->id = 0;
+	pr_debug("%s success\n", __func__);
 }
 
 /* DebugFS code */
@@ -333,6 +339,7 @@ static ssize_t info_debugfs_read(struct file *file, char __user *buf,
 	struct visornic_devdata *devdata;
 	char *vbuf;
 
+	pr_debug("%s\n", __func__);
 	if (len > MAX_BUF)
 		len = MAX_BUF;
 	vbuf = kzalloc(len, GFP_KERNEL);
@@ -465,6 +472,8 @@ static ssize_t info_debugfs_read(struct file *file, char __user *buf,
 	}
 	bytes_read = simple_read_from_buffer(buf, len, offset, vbuf, str_pos);
 	kfree(vbuf);
+	pr_debug("%s success %ld\n",
+		 __func__, (long)bytes_read);
 	return bytes_read;
 }
 
@@ -520,6 +529,8 @@ visornic_serverdown_complete(struct work_struct *work)
 			       serverdown_completion);
 	netdev = devdata->netdev;
 
+	dev_dbg(&netdev->dev, "%s\n", __func__);
+
 	/* Stop using datachan */
 	visor_thread_stop(&devdata->threadinfo);
 
@@ -547,6 +558,7 @@ visornic_serverdown_complete(struct work_struct *work)
 
 	devdata->server_down = true;
 	devdata->server_change_state = false;
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 }
 
 /**
@@ -560,13 +572,17 @@ visornic_serverdown_complete(struct work_struct *work)
 static int
 visornic_serverdown(struct visornic_devdata *devdata)
 {
+	dev_dbg(&devdata->dev->device, "%s\n", __func__);
 	if (!devdata->server_down && !devdata->server_change_state) {
 		devdata->server_change_state = true;
 		queue_work(visornic_serverdown_workqueue,
 			   &devdata->serverdown_completion);
 	} else if (devdata->server_change_state) {
+		dev_dbg(&devdata->dev->device, "%s changing state\n",
+			__func__);
 		return -EINVAL;
 	}
+	dev_dbg(&devdata->dev->device, "%s success\n", __func__);
 	return 0;
 }
 
@@ -676,6 +692,8 @@ visornic_disable_with_timeout(struct net_device *netdev, const int timeout)
 	unsigned long flags;
 	int wait = 0;
 
+	dev_dbg(&netdev->dev, "%s\n", __func__);
+
 	/* stop the transmit queue so nothing more can be transmitted */
 	netif_stop_queue(netdev);
 
@@ -701,6 +719,8 @@ visornic_disable_with_timeout(struct net_device *netdev, const int timeout)
 			break;
 		if (devdata->server_down || devdata->server_change_state) {
 			spin_unlock_irqrestore(&devdata->priv_lock, flags);
+			dev_dbg(&netdev->dev, "%s server went away\n",
+				__func__);
 			return -EIO;
 		}
 		set_current_state(TASK_INTERRUPTIBLE);
@@ -743,6 +763,7 @@ visornic_disable_with_timeout(struct net_device *netdev, const int timeout)
 			break;
 		}
 
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 	return 0;
 }
 
@@ -810,12 +831,17 @@ visornic_enable_with_timeout(struct net_device *netdev, const int timeout)
 	unsigned long flags;
 	int wait = 0;
 
+	dev_dbg(&netdev->dev, "%s\n", __func__);
+
 	/* NOTE: the other end automatically unposts the rcv buffers when it
 	 * gets a disable.
 	 */
 	i = init_rcv_bufs(netdev, devdata);
-	if (i < 0)
+	if (i < 0) {
+		dev_err(&netdev->dev,
+			"%s failed to init rcv bufs (%d)\n", __func__, i);
 		return i;
+	}
 
 	spin_lock_irqsave(&devdata->priv_lock, flags);
 	devdata->enabled = 1;
@@ -838,6 +864,8 @@ visornic_enable_with_timeout(struct net_device *netdev, const int timeout)
 			break;
 		if (devdata->server_down || devdata->server_change_state) {
 			spin_unlock_irqrestore(&devdata->priv_lock, flags);
+			dev_dbg(&netdev->dev, "%s server went away\n",
+				__func__);
 			return -EIO;
 		}
 		set_current_state(TASK_INTERRUPTIBLE);
@@ -848,8 +876,10 @@ visornic_enable_with_timeout(struct net_device *netdev, const int timeout)
 
 	spin_unlock_irqrestore(&devdata->priv_lock, flags);
 
-	if (!devdata->enab_dis_acked)
+	if (!devdata->enab_dis_acked) {
+		dev_err(&netdev->dev, "%s missing ACK\n", __func__);
 		return -EIO;
+	}
 
 	/* find an open slot in the array to save off VisorNic references
 	 * for debug
@@ -861,6 +891,7 @@ visornic_enable_with_timeout(struct net_device *netdev, const int timeout)
 		}
 	}
 
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 	return 0;
 }
 
@@ -882,6 +913,7 @@ visornic_timeout_reset(struct work_struct *work)
 	devdata = container_of(work, struct visornic_devdata, timeout_reset);
 	netdev = devdata->netdev;
 
+	dev_dbg(&netdev->dev, "%s\n", __func__);
 	netif_stop_queue(netdev);
 	response = visornic_disable_with_timeout(netdev, 100);
 	if (response)
@@ -896,6 +928,7 @@ visornic_timeout_reset(struct work_struct *work)
 
 call_serverdown:
 	visornic_serverdown(devdata);
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 }
 
 /**
@@ -908,6 +941,7 @@ call_serverdown:
 static int
 visornic_open(struct net_device *netdev)
 {
+	dev_dbg(&netdev->dev, "%s\n", __func__);
 	visornic_enable_with_timeout(netdev, VISORNIC_INFINITE_RESPONSE_WAIT);
 
 	/* start the interface's transmit queue, allowing it to accept
@@ -915,6 +949,7 @@ visornic_open(struct net_device *netdev)
 	 */
 	netif_start_queue(netdev);
 
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 	return 0;
 }
 
@@ -928,9 +963,11 @@ visornic_open(struct net_device *netdev)
 static int
 visornic_close(struct net_device *netdev)
 {
+	dev_dbg(&netdev->dev, "%s\n", __func__);
 	netif_stop_queue(netdev);
 	visornic_disable_with_timeout(netdev, VISORNIC_INFINITE_RESPONSE_WAIT);
 
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 	return 0;
 }
 
@@ -961,6 +998,8 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 	    devdata->server_change_state) {
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		devdata->busy_cnt++;
+		dev_dbg(&netdev->dev,
+			"%s busy - queue stopped\n", __func__);
 		return NETDEV_TX_BUSY;
 	}
 
@@ -979,6 +1018,9 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 	if (firstfraglen < ETH_HEADER_SIZE) {
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		devdata->busy_cnt++;
+		dev_err(&netdev->dev,
+			"%s busy - first frag too small (%d)\n",
+			__func__, firstfraglen);
 		return NETDEV_TX_BUSY;
 	}
 
@@ -1018,6 +1060,9 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 		netif_stop_queue(netdev);
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		devdata->busy_cnt++;
+		dev_dbg(&netdev->dev,
+			"%s busy - waiting for iovm to catch up\n",
+			__func__);
 		return NETDEV_TX_BUSY;
 	}
 	if (devdata->queuefullmsg_logged)
@@ -1058,6 +1103,8 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 	if (cmdrsp->net.xmt.num_frags == -1) {
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		devdata->busy_cnt++;
+		dev_err(&netdev->dev,
+			"%s busy - copy frags failed\n", __func__);
 		return NETDEV_TX_BUSY;
 	}
 
@@ -1066,6 +1113,8 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 		netif_stop_queue(netdev);
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		devdata->busy_cnt++;
+		dev_dbg(&netdev->dev,
+			"%s busy - signalinsert failed\n", __func__);
 		return NETDEV_TX_BUSY;
 	}
 
@@ -1098,6 +1147,9 @@ visornic_xmit(struct sk_buff *skb, struct net_device *netdev)
 					   * netif_wake_queue() after lower
 					   * threshold
 					   */
+		dev_dbg(&netdev->dev,
+			"%s busy - invoking iovm flow control\n",
+			__func__);
 		devdata->flow_control_upper_hits++;
 	}
 	spin_unlock_irqrestore(&devdata->priv_lock, flags);
@@ -1200,16 +1252,20 @@ visornic_xmit_timeout(struct net_device *netdev)
 	struct visornic_devdata *devdata = netdev_priv(netdev);
 	unsigned long flags;
 
+	dev_dbg(&netdev->dev, "%s\n", __func__);
 	spin_lock_irqsave(&devdata->priv_lock, flags);
 	/* Ensure that a ServerDown message hasn't been received */
 	if (!devdata->enabled ||
 	    (devdata->server_down && !devdata->server_change_state)) {
+		dev_dbg(&netdev->dev, "%s no processing\n",
+			__func__);
 		spin_unlock_irqrestore(&devdata->priv_lock, flags);
 		return;
 	}
 	spin_unlock_irqrestore(&devdata->priv_lock, flags);
 
 	queue_work(visornic_timeout_reset_workqueue, &devdata->timeout_reset);
+	dev_dbg(&netdev->dev, "%s success\n", __func__);
 }
 
 /**
@@ -1800,9 +1856,13 @@ static int visornic_probe(struct visor_device *dev)
 	int channel_offset = 0;
 	u64 features;
 
+	dev_dbg(&dev->device, "%s\n", __func__);
 	netdev = alloc_etherdev(sizeof(struct visornic_devdata));
-	if (!netdev)
+	if (!netdev) {
+		dev_err(&dev->device,
+			"%s alloc_etherdev failed\n", __func__);
 		return -ENOMEM;
+	}
 
 	netdev->netdev_ops = &visornic_dev_ops;
 	netdev->watchdog_timeo = (5 * HZ);
@@ -1814,11 +1874,17 @@ static int visornic_probe(struct visor_device *dev)
 				  vnic.macaddr);
 	err = visorbus_read_channel(dev, channel_offset, netdev->dev_addr,
 				    ETH_ALEN);
-	if (err < 0)
+	if (err < 0) {
+		dev_err(&dev->device,
+			"%s failed to get mac addr from chan (%d)\n",
+			__func__, err);
 		goto cleanup_netdev;
+	}
 
 	devdata = devdata_initialize(netdev_priv(netdev), dev);
 	if (!devdata) {
+		dev_err(&dev->device,
+			"%s devdata_initialize failed\n", __func__);
 		err = -ENOMEM;
 		goto cleanup_netdev;
 	}
@@ -1834,8 +1900,12 @@ static int visornic_probe(struct visor_device *dev)
 				  vnic.num_rcv_bufs);
 	err = visorbus_read_channel(dev, channel_offset,
 				    &devdata->num_rcv_bufs, 4);
-	if (err)
+	if (err) {
+		dev_err(&dev->device,
+			"%s failed to get #rcv bufs from chan (%d)\n",
+			__func__, err);
 		goto cleanup_netdev;
+	}
 
 	devdata->rcvbuf = kmalloc(sizeof(struct sk_buff *) *
 				  devdata->num_rcv_bufs, GFP_KERNEL);
@@ -1876,38 +1946,58 @@ static int visornic_probe(struct visor_device *dev)
 	channel_offset = offsetof(struct spar_io_channel_protocol,
 				  vnic.mtu);
 	err = visorbus_read_channel(dev, channel_offset, &netdev->mtu, 4);
-	if (err)
+	if (err) {
+		dev_err(&dev->device,
+			"%s failed to get mtu from chan (%d)\n",
+			__func__, err);
 		goto cleanup_xmit_cmdrsp;
+	}
 
 	/* TODO: Setup Interrupt information */
 	/* Let's start our threads to get responses */
 	channel_offset = offsetof(struct spar_io_channel_protocol,
 				  channel_header.features);
 	err = visorbus_read_channel(dev, channel_offset, &features, 8);
-	if (err)
+	if (err) {
+		dev_err(&dev->device,
+			"%s failed to get features from chan (%d)\n",
+			__func__, err);
 		goto cleanup_xmit_cmdrsp;
+	}
 
 	features |= ULTRA_IO_CHANNEL_IS_POLLING;
 	err = visorbus_write_channel(dev, channel_offset, &features, 8);
-	if (err)
+	if (err) {
+		dev_err(&dev->device,
+			"%s failed to set features in chan (%d)\n",
+			__func__, err);
 		goto cleanup_xmit_cmdrsp;
+	}
 
 	devdata->thread_wait_ms = 2;
 	visor_thread_start(&devdata->threadinfo, process_incoming_rsps,
 			   devdata, "vnic_incoming");
 
 	err = register_netdev(netdev);
-	if (err)
+	if (err) {
+		dev_err(&dev->device,
+			"%s register_netdev failed (%d)\n", __func__, err);
 		goto cleanup_thread_stop;
+	}
 
 	/* create debgug/sysfs directories */
 	devdata->eth_debugfs_dir = debugfs_create_dir(netdev->name,
 						      visornic_debugfs_dir);
 	if (!devdata->eth_debugfs_dir) {
+		dev_err(&dev->device,
+			"%s debugfs_create_dir %s failed\n",
+			__func__, netdev->name);
 		err = -ENOMEM;
 		goto cleanup_thread_stop;
 	}
 
+	dev_info(&dev->device, "%s success netdev=%s\n",
+		 __func__, netdev->name);
 	return 0;
 
 cleanup_thread_stop:
@@ -1955,8 +2045,11 @@ static void visornic_remove(struct visor_device *dev)
 {
 	struct visornic_devdata *devdata = dev_get_drvdata(&dev->device);
 
-	if (!devdata)
+	if (!devdata) {
+		dev_err(&dev->device, "%s no devdata\n", __func__);
 		return;
+	}
+	dev_dbg(&dev->device, "%s\n", __func__);
 	dev_set_drvdata(&dev->device, NULL);
 	host_side_disappeared(devdata);
 	kref_put(&devdata->kref, devdata_release);
@@ -1980,8 +2073,10 @@ static int visornic_pause(struct visor_device *dev,
 {
 	struct visornic_devdata *devdata = dev_get_drvdata(&dev->device);
 
+	dev_dbg(&dev->device, "%s\n", __func__);
 	visornic_serverdown(devdata);
 	complete_func(dev, 0);
+	dev_dbg(&dev->device, "%s success\n", __func__);
 	return 0;
 }
 
@@ -2003,10 +2098,13 @@ static int visornic_resume(struct visor_device *dev,
 	unsigned long flags;
 
 	devdata = dev_get_drvdata(&dev->device);
-	if (!devdata)
+	if (!devdata) {
+		dev_err(&dev->device, "%s no devdata\n", __func__);
 		return -EINVAL;
+	}
 
 	netdev = devdata->netdev;
+	dev_dbg(&dev->device, "%s\n", __func__);
 
 	if (devdata->server_down && !devdata->server_change_state) {
 		devdata->server_change_state = true;
@@ -2032,10 +2130,13 @@ static int visornic_resume(struct visor_device *dev,
 		 */
 		send_enbdis(netdev, 1, devdata);
 	} else if (devdata->server_change_state) {
+		dev_err(&dev->device, "%s server_change_state\n",
+			__func__);
 		return -EIO;
 	}
 
 	complete_func(dev, 0);
+	dev_dbg(&dev->device, "%s success\n", __func__);
 	return 0;
 }
 
@@ -2051,6 +2152,8 @@ static int visornic_init(void)
 	struct dentry *ret;
 	int err = -ENOMEM;
 
+	pr_debug("%s\n", __func__);
+
 	/* create workqueue for serverdown completion */
 	visornic_serverdown_workqueue =
 		create_singlethread_workqueue("visornic_serverdown");
@@ -2116,6 +2219,8 @@ cleanup_debugfs:
  */
 static void visornic_cleanup(void)
 {
+	pr_debug("%s\n", __func__);
+
 	if (visornic_serverdown_workqueue) {
 		flush_workqueue(visornic_serverdown_workqueue);
 		destroy_workqueue(visornic_serverdown_workqueue);
-- 
2.1.4

_______________________________________________
devel mailing list
devel@xxxxxxxxxxxxxxxxxxxxxx
http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel



[Index of Archives]     [Linux Driver Backports]     [DMA Engine]     [Linux GPIO]     [Linux SPI]     [Video for Linux]     [Linux USB Devel]     [Linux Coverity]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]
  Powered by Linux