Commit f3d242e8 authored by Frank Pavlic's avatar Frank Pavlic Committed by Jeff Garzik

[PATCH] s390: qeth driver fixes

[patch 4/4] s390: qeth driver fixes .

From: Frank Pavlic <pavlic@de.ibm.com>
	- Clear read channel first prior to using ccw_device_set_offline.
	- use QETH_DBF_TEXT instead of QETH_DBF_SPRINTF
	- invoke qeth_halt_channel and qeth_clear_channel for all channels,
	  even if halt/clear for one of the channel fails.
	- enable qeth_arp_query function for GuestLAN devices
Signed-off-by: default avatarFrank Pavlic <pavlic@de.ibm.com>

diffstat:
 qeth.h      |    2 -
 qeth_main.c |  106 +++++++++++++++++++++++++-----------------------------------
 qeth_sys.c  |   11 +++---
 3 files changed, 53 insertions(+), 66 deletions(-)
Signed-off-by: default avatarJeff Garzik <jgarzik@pobox.com>
parent 9cb90de8
...@@ -24,7 +24,7 @@ ...@@ -24,7 +24,7 @@
#include "qeth_mpc.h" #include "qeth_mpc.h"
#define VERSION_QETH_H "$Revision: 1.141 $" #define VERSION_QETH_H "$Revision: 1.142 $"
#ifdef CONFIG_QETH_IPV6 #ifdef CONFIG_QETH_IPV6
#define QETH_VERSION_IPV6 ":IPv6" #define QETH_VERSION_IPV6 ":IPv6"
......
/* /*
* *
* linux/drivers/s390/net/qeth_main.c ($Revision: 1.219 $) * linux/drivers/s390/net/qeth_main.c ($Revision: 1.224 $)
* *
* Linux on zSeries OSA Express and HiperSockets support * Linux on zSeries OSA Express and HiperSockets support
* *
...@@ -12,7 +12,7 @@ ...@@ -12,7 +12,7 @@
* Frank Pavlic (pavlic@de.ibm.com) and * Frank Pavlic (pavlic@de.ibm.com) and
* Thomas Spatzier <tspat@de.ibm.com> * Thomas Spatzier <tspat@de.ibm.com>
* *
* $Revision: 1.219 $ $Date: 2005/05/04 20:19:18 $ * $Revision: 1.224 $ $Date: 2005/05/04 20:19:18 $
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
...@@ -29,14 +29,6 @@ ...@@ -29,14 +29,6 @@
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
/***
* eye catcher; just for debugging purposes
*/
void volatile
qeth_eyecatcher(void)
{
return;
}
#include <linux/config.h> #include <linux/config.h>
#include <linux/module.h> #include <linux/module.h>
...@@ -80,7 +72,7 @@ qeth_eyecatcher(void) ...@@ -80,7 +72,7 @@ qeth_eyecatcher(void)
#include "qeth_eddp.h" #include "qeth_eddp.h"
#include "qeth_tso.h" #include "qeth_tso.h"
#define VERSION_QETH_C "$Revision: 1.219 $" #define VERSION_QETH_C "$Revision: 1.224 $"
static const char *version = "qeth S/390 OSA-Express driver"; static const char *version = "qeth S/390 OSA-Express driver";
/** /**
...@@ -2759,11 +2751,9 @@ qeth_flush_buffers(struct qeth_qdio_out_q *queue, int under_int, ...@@ -2759,11 +2751,9 @@ qeth_flush_buffers(struct qeth_qdio_out_q *queue, int under_int,
queue->card->perf_stats.outbound_do_qdio_start_time; queue->card->perf_stats.outbound_do_qdio_start_time;
#endif #endif
if (rc){ if (rc){
QETH_DBF_SPRINTF(trace, 0, "qeth_flush_buffers: do_QDIO "
"returned error (%i) on device %s.",
rc, CARD_DDEV_ID(queue->card));
QETH_DBF_TEXT(trace, 2, "flushbuf"); QETH_DBF_TEXT(trace, 2, "flushbuf");
QETH_DBF_TEXT_(trace, 2, " err%d", rc); QETH_DBF_TEXT_(trace, 2, " err%d", rc);
QETH_DBF_TEXT_(trace, 2, "%s", CARD_DDEV_ID(queue->card));
queue->card->stats.tx_errors += count; queue->card->stats.tx_errors += count;
/* this must not happen under normal circumstances. if it /* this must not happen under normal circumstances. if it
* happens something is really wrong -> recover */ * happens something is really wrong -> recover */
...@@ -2909,11 +2899,8 @@ qeth_qdio_output_handler(struct ccw_device * ccwdev, unsigned int status, ...@@ -2909,11 +2899,8 @@ qeth_qdio_output_handler(struct ccw_device * ccwdev, unsigned int status,
QETH_DBF_TEXT(trace, 6, "qdouhdl"); QETH_DBF_TEXT(trace, 6, "qdouhdl");
if (status & QDIO_STATUS_LOOK_FOR_ERROR) { if (status & QDIO_STATUS_LOOK_FOR_ERROR) {
if (status & QDIO_STATUS_ACTIVATE_CHECK_CONDITION){ if (status & QDIO_STATUS_ACTIVATE_CHECK_CONDITION){
QETH_DBF_SPRINTF(trace, 2, "On device %s: " QETH_DBF_TEXT(trace, 2, "achkcond");
"received active check " QETH_DBF_TEXT_(trace, 2, "%s", CARD_BUS_ID(card));
"condition (0x%08x).",
CARD_BUS_ID(card), status);
QETH_DBF_TEXT(trace, 2, "chkcond");
QETH_DBF_TEXT_(trace, 2, "%08x", status); QETH_DBF_TEXT_(trace, 2, "%08x", status);
netif_stop_queue(card->dev); netif_stop_queue(card->dev);
qeth_schedule_recovery(card); qeth_schedule_recovery(card);
...@@ -3356,26 +3343,32 @@ qeth_halt_channel(struct qeth_channel *channel) ...@@ -3356,26 +3343,32 @@ qeth_halt_channel(struct qeth_channel *channel)
static int static int
qeth_halt_channels(struct qeth_card *card) qeth_halt_channels(struct qeth_card *card)
{ {
int rc = 0; int rc1 = 0, rc2=0, rc3 = 0;
QETH_DBF_TEXT(trace,3,"haltchs"); QETH_DBF_TEXT(trace,3,"haltchs");
if ((rc = qeth_halt_channel(&card->read))) rc1 = qeth_halt_channel(&card->read);
return rc; rc2 = qeth_halt_channel(&card->write);
if ((rc = qeth_halt_channel(&card->write))) rc3 = qeth_halt_channel(&card->data);
return rc; if (rc1)
return qeth_halt_channel(&card->data); return rc1;
if (rc2)
return rc2;
return rc3;
} }
static int static int
qeth_clear_channels(struct qeth_card *card) qeth_clear_channels(struct qeth_card *card)
{ {
int rc = 0; int rc1 = 0, rc2=0, rc3 = 0;
QETH_DBF_TEXT(trace,3,"clearchs"); QETH_DBF_TEXT(trace,3,"clearchs");
if ((rc = qeth_clear_channel(&card->read))) rc1 = qeth_clear_channel(&card->read);
return rc; rc2 = qeth_clear_channel(&card->write);
if ((rc = qeth_clear_channel(&card->write))) rc3 = qeth_clear_channel(&card->data);
return rc; if (rc1)
return qeth_clear_channel(&card->data); return rc1;
if (rc2)
return rc2;
return rc3;
} }
static int static int
...@@ -3445,23 +3438,23 @@ qeth_mpc_initialize(struct qeth_card *card) ...@@ -3445,23 +3438,23 @@ qeth_mpc_initialize(struct qeth_card *card)
} }
if ((rc = qeth_cm_enable(card))){ if ((rc = qeth_cm_enable(card))){
QETH_DBF_TEXT_(setup, 2, "2err%d", rc); QETH_DBF_TEXT_(setup, 2, "2err%d", rc);
return rc; goto out_qdio;
} }
if ((rc = qeth_cm_setup(card))){ if ((rc = qeth_cm_setup(card))){
QETH_DBF_TEXT_(setup, 2, "3err%d", rc); QETH_DBF_TEXT_(setup, 2, "3err%d", rc);
return rc; goto out_qdio;
} }
if ((rc = qeth_ulp_enable(card))){ if ((rc = qeth_ulp_enable(card))){
QETH_DBF_TEXT_(setup, 2, "4err%d", rc); QETH_DBF_TEXT_(setup, 2, "4err%d", rc);
return rc; goto out_qdio;
} }
if ((rc = qeth_ulp_setup(card))){ if ((rc = qeth_ulp_setup(card))){
QETH_DBF_TEXT_(setup, 2, "5err%d", rc); QETH_DBF_TEXT_(setup, 2, "5err%d", rc);
return rc; goto out_qdio;
} }
if ((rc = qeth_alloc_qdio_buffers(card))){ if ((rc = qeth_alloc_qdio_buffers(card))){
QETH_DBF_TEXT_(setup, 2, "5err%d", rc); QETH_DBF_TEXT_(setup, 2, "5err%d", rc);
return rc; goto out_qdio;
} }
if ((rc = qeth_qdio_establish(card))){ if ((rc = qeth_qdio_establish(card))){
QETH_DBF_TEXT_(setup, 2, "6err%d", rc); QETH_DBF_TEXT_(setup, 2, "6err%d", rc);
...@@ -4281,7 +4274,7 @@ qeth_send_packet(struct qeth_card *card, struct sk_buff *skb) ...@@ -4281,7 +4274,7 @@ qeth_send_packet(struct qeth_card *card, struct sk_buff *skb)
int ipv = 0; int ipv = 0;
int cast_type; int cast_type;
struct qeth_qdio_out_q *queue; struct qeth_qdio_out_q *queue;
struct qeth_hdr *hdr; struct qeth_hdr *hdr = NULL;
int elements_needed = 0; int elements_needed = 0;
enum qeth_large_send_types large_send = QETH_LARGE_SEND_NO; enum qeth_large_send_types large_send = QETH_LARGE_SEND_NO;
struct qeth_eddp_context *ctx = NULL; struct qeth_eddp_context *ctx = NULL;
...@@ -4512,7 +4505,11 @@ qeth_arp_set_no_entries(struct qeth_card *card, int no_entries) ...@@ -4512,7 +4505,11 @@ qeth_arp_set_no_entries(struct qeth_card *card, int no_entries)
QETH_DBF_TEXT(trace,3,"arpstnoe"); QETH_DBF_TEXT(trace,3,"arpstnoe");
/* TODO: really not supported by GuestLAN? */ /*
* currently GuestLAN only supports the ARP assist function
* IPA_CMD_ASS_ARP_QUERY_INFO, but not IPA_CMD_ASS_ARP_SET_NO_ENTRIES;
* thus we say EOPNOTSUPP for this ARP function
*/
if (card->info.guestlan) if (card->info.guestlan)
return -EOPNOTSUPP; return -EOPNOTSUPP;
if (!qeth_is_supported(card,IPA_ARP_PROCESSING)) { if (!qeth_is_supported(card,IPA_ARP_PROCESSING)) {
...@@ -4689,14 +4686,6 @@ qeth_arp_query(struct qeth_card *card, char *udata) ...@@ -4689,14 +4686,6 @@ qeth_arp_query(struct qeth_card *card, char *udata)
QETH_DBF_TEXT(trace,3,"arpquery"); QETH_DBF_TEXT(trace,3,"arpquery");
/*
* currently GuestLAN does only deliver all zeros on query arp,
* even though arp processing is supported (according to IPA supp.
* funcs flags); since all zeros is no valueable information,
* we say EOPNOTSUPP for all ARP functions
*/
/*if (card->info.guestlan)
return -EOPNOTSUPP; */
if (!qeth_is_supported(card,/*IPA_QUERY_ARP_ADDR_INFO*/ if (!qeth_is_supported(card,/*IPA_QUERY_ARP_ADDR_INFO*/
IPA_ARP_PROCESSING)) { IPA_ARP_PROCESSING)) {
PRINT_WARN("ARP processing not supported " PRINT_WARN("ARP processing not supported "
...@@ -4902,10 +4891,9 @@ qeth_arp_add_entry(struct qeth_card *card, struct qeth_arp_cache_entry *entry) ...@@ -4902,10 +4891,9 @@ qeth_arp_add_entry(struct qeth_card *card, struct qeth_arp_cache_entry *entry)
QETH_DBF_TEXT(trace,3,"arpadent"); QETH_DBF_TEXT(trace,3,"arpadent");
/* /*
* currently GuestLAN does only deliver all zeros on query arp, * currently GuestLAN only supports the ARP assist function
* even though arp processing is supported (according to IPA supp. * IPA_CMD_ASS_ARP_QUERY_INFO, but not IPA_CMD_ASS_ARP_ADD_ENTRY;
* funcs flags); since all zeros is no valueable information, * thus we say EOPNOTSUPP for this ARP function
* we say EOPNOTSUPP for all ARP functions
*/ */
if (card->info.guestlan) if (card->info.guestlan)
return -EOPNOTSUPP; return -EOPNOTSUPP;
...@@ -4945,10 +4933,9 @@ qeth_arp_remove_entry(struct qeth_card *card, struct qeth_arp_cache_entry *entry ...@@ -4945,10 +4933,9 @@ qeth_arp_remove_entry(struct qeth_card *card, struct qeth_arp_cache_entry *entry
QETH_DBF_TEXT(trace,3,"arprment"); QETH_DBF_TEXT(trace,3,"arprment");
/* /*
* currently GuestLAN does only deliver all zeros on query arp, * currently GuestLAN only supports the ARP assist function
* even though arp processing is supported (according to IPA supp. * IPA_CMD_ASS_ARP_QUERY_INFO, but not IPA_CMD_ASS_ARP_REMOVE_ENTRY;
* funcs flags); since all zeros is no valueable information, * thus we say EOPNOTSUPP for this ARP function
* we say EOPNOTSUPP for all ARP functions
*/ */
if (card->info.guestlan) if (card->info.guestlan)
return -EOPNOTSUPP; return -EOPNOTSUPP;
...@@ -4986,10 +4973,9 @@ qeth_arp_flush_cache(struct qeth_card *card) ...@@ -4986,10 +4973,9 @@ qeth_arp_flush_cache(struct qeth_card *card)
QETH_DBF_TEXT(trace,3,"arpflush"); QETH_DBF_TEXT(trace,3,"arpflush");
/* /*
* currently GuestLAN does only deliver all zeros on query arp, * currently GuestLAN only supports the ARP assist function
* even though arp processing is supported (according to IPA supp. * IPA_CMD_ASS_ARP_QUERY_INFO, but not IPA_CMD_ASS_ARP_FLUSH_CACHE;
* funcs flags); since all zeros is no valueable information, * thus we say EOPNOTSUPP for this ARP function
* we say EOPNOTSUPP for all ARP functions
*/ */
if (card->info.guestlan || (card->info.type == QETH_CARD_TYPE_IQD)) if (card->info.guestlan || (card->info.type == QETH_CARD_TYPE_IQD))
return -EOPNOTSUPP; return -EOPNOTSUPP;
...@@ -8266,7 +8252,6 @@ qeth_init(void) ...@@ -8266,7 +8252,6 @@ qeth_init(void)
{ {
int rc=0; int rc=0;
qeth_eyecatcher();
PRINT_INFO("loading %s (%s/%s/%s/%s/%s/%s/%s %s %s)\n", PRINT_INFO("loading %s (%s/%s/%s/%s/%s/%s/%s %s %s)\n",
version, VERSION_QETH_C, VERSION_QETH_H, version, VERSION_QETH_C, VERSION_QETH_H,
VERSION_QETH_MPC_H, VERSION_QETH_MPC_C, VERSION_QETH_MPC_H, VERSION_QETH_MPC_C,
...@@ -8347,7 +8332,6 @@ __exit qeth_exit(void) ...@@ -8347,7 +8332,6 @@ __exit qeth_exit(void)
printk("qeth: removed\n"); printk("qeth: removed\n");
} }
EXPORT_SYMBOL(qeth_eyecatcher);
module_init(qeth_init); module_init(qeth_init);
module_exit(qeth_exit); module_exit(qeth_exit);
MODULE_AUTHOR("Frank Pavlic <pavlic@de.ibm.com>"); MODULE_AUTHOR("Frank Pavlic <pavlic@de.ibm.com>");
......
/* /*
* *
* linux/drivers/s390/net/qeth_sys.c ($Revision: 1.53 $) * linux/drivers/s390/net/qeth_sys.c ($Revision: 1.54 $)
* *
* Linux on zSeries OSA Express and HiperSockets support * Linux on zSeries OSA Express and HiperSockets support
* This file contains code related to sysfs. * This file contains code related to sysfs.
...@@ -20,7 +20,7 @@ ...@@ -20,7 +20,7 @@
#include "qeth_mpc.h" #include "qeth_mpc.h"
#include "qeth_fs.h" #include "qeth_fs.h"
const char *VERSION_QETH_SYS_C = "$Revision: 1.53 $"; const char *VERSION_QETH_SYS_C = "$Revision: 1.54 $";
/*****************************************************************************/ /*****************************************************************************/
/* */ /* */
...@@ -722,10 +722,13 @@ qeth_dev_layer2_store(struct device *dev, struct device_attribute *attr, const c ...@@ -722,10 +722,13 @@ qeth_dev_layer2_store(struct device *dev, struct device_attribute *attr, const c
if (!card) if (!card)
return -EINVAL; return -EINVAL;
if (card->info.type == QETH_CARD_TYPE_IQD) {
PRINT_WARN("Layer2 on Hipersockets is not supported! \n");
return -EPERM;
}
if (((card->state != CARD_STATE_DOWN) && if (((card->state != CARD_STATE_DOWN) &&
(card->state != CARD_STATE_RECOVER)) || (card->state != CARD_STATE_RECOVER)))
(card->info.type != QETH_CARD_TYPE_OSAE))
return -EPERM; return -EPERM;
i = simple_strtoul(buf, &tmp, 16); i = simple_strtoul(buf, &tmp, 16);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment