Commit b8a5d06a authored by David S. Miller's avatar David S. Miller

Merge branch 's390-qeth-fixes'

Julian Wiedmann says:

====================
s390/qeth: fixes 2018-11-02

please apply one round of qeth fixes for -net.

Patch 1 is rather large and removes a use-after-free hazard from many of our
debug trace entries.
Patch 2 is yet another fix-up for the L3 subdriver's new IP address management
code.
Patch 3 and 4 resolve some fallout from the recent changes wrt how/when qeth
allocates its net_device.
Patch 5 makes sure we don't set reserved bits when building HW commands from
user-provided data.
And finally, patch 6 allows ethtool to play nice with new HW.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents 265ad063 54e049c2
...@@ -87,6 +87,18 @@ struct qeth_dbf_info { ...@@ -87,6 +87,18 @@ struct qeth_dbf_info {
#define SENSE_RESETTING_EVENT_BYTE 1 #define SENSE_RESETTING_EVENT_BYTE 1
#define SENSE_RESETTING_EVENT_FLAG 0x80 #define SENSE_RESETTING_EVENT_FLAG 0x80
static inline u32 qeth_get_device_id(struct ccw_device *cdev)
{
struct ccw_dev_id dev_id;
u32 id;
ccw_device_get_id(cdev, &dev_id);
id = dev_id.devno;
id |= (u32) (dev_id.ssid << 16);
return id;
}
/* /*
* Common IO related definitions * Common IO related definitions
*/ */
...@@ -97,7 +109,8 @@ struct qeth_dbf_info { ...@@ -97,7 +109,8 @@ struct qeth_dbf_info {
#define CARD_RDEV_ID(card) dev_name(&card->read.ccwdev->dev) #define CARD_RDEV_ID(card) dev_name(&card->read.ccwdev->dev)
#define CARD_WDEV_ID(card) dev_name(&card->write.ccwdev->dev) #define CARD_WDEV_ID(card) dev_name(&card->write.ccwdev->dev)
#define CARD_DDEV_ID(card) dev_name(&card->data.ccwdev->dev) #define CARD_DDEV_ID(card) dev_name(&card->data.ccwdev->dev)
#define CHANNEL_ID(channel) dev_name(&channel->ccwdev->dev) #define CCW_DEVID(cdev) (qeth_get_device_id(cdev))
#define CARD_DEVID(card) (CCW_DEVID(CARD_RDEV(card)))
/** /**
* card stuff * card stuff
...@@ -830,6 +843,11 @@ struct qeth_trap_id { ...@@ -830,6 +843,11 @@ struct qeth_trap_id {
/*some helper functions*/ /*some helper functions*/
#define QETH_CARD_IFNAME(card) (((card)->dev)? (card)->dev->name : "") #define QETH_CARD_IFNAME(card) (((card)->dev)? (card)->dev->name : "")
static inline bool qeth_netdev_is_registered(struct net_device *dev)
{
return dev->netdev_ops != NULL;
}
static inline void qeth_scrub_qdio_buffer(struct qdio_buffer *buf, static inline void qeth_scrub_qdio_buffer(struct qdio_buffer *buf,
unsigned int elements) unsigned int elements)
{ {
...@@ -973,7 +991,7 @@ int qeth_wait_for_threads(struct qeth_card *, unsigned long); ...@@ -973,7 +991,7 @@ int qeth_wait_for_threads(struct qeth_card *, unsigned long);
int qeth_do_run_thread(struct qeth_card *, unsigned long); int qeth_do_run_thread(struct qeth_card *, unsigned long);
void qeth_clear_thread_start_bit(struct qeth_card *, unsigned long); void qeth_clear_thread_start_bit(struct qeth_card *, unsigned long);
void qeth_clear_thread_running_bit(struct qeth_card *, unsigned long); void qeth_clear_thread_running_bit(struct qeth_card *, unsigned long);
int qeth_core_hardsetup_card(struct qeth_card *); int qeth_core_hardsetup_card(struct qeth_card *card, bool *carrier_ok);
void qeth_print_status_message(struct qeth_card *); void qeth_print_status_message(struct qeth_card *);
int qeth_init_qdio_queues(struct qeth_card *); int qeth_init_qdio_queues(struct qeth_card *);
int qeth_send_ipa_cmd(struct qeth_card *, struct qeth_cmd_buffer *, int qeth_send_ipa_cmd(struct qeth_card *, struct qeth_cmd_buffer *,
...@@ -1028,11 +1046,6 @@ int qeth_configure_cq(struct qeth_card *, enum qeth_cq); ...@@ -1028,11 +1046,6 @@ int qeth_configure_cq(struct qeth_card *, enum qeth_cq);
int qeth_hw_trap(struct qeth_card *, enum qeth_diags_trap_action); int qeth_hw_trap(struct qeth_card *, enum qeth_diags_trap_action);
void qeth_trace_features(struct qeth_card *); void qeth_trace_features(struct qeth_card *);
void qeth_close_dev(struct qeth_card *); void qeth_close_dev(struct qeth_card *);
int qeth_send_setassparms(struct qeth_card *, struct qeth_cmd_buffer *, __u16,
long,
int (*reply_cb)(struct qeth_card *,
struct qeth_reply *, unsigned long),
void *);
int qeth_setassparms_cb(struct qeth_card *, struct qeth_reply *, unsigned long); int qeth_setassparms_cb(struct qeth_card *, struct qeth_reply *, unsigned long);
struct qeth_cmd_buffer *qeth_get_setassparms_cmd(struct qeth_card *, struct qeth_cmd_buffer *qeth_get_setassparms_cmd(struct qeth_card *,
enum qeth_ipa_funcs, enum qeth_ipa_funcs,
......
This diff is collapsed.
...@@ -90,6 +90,7 @@ enum qeth_link_types { ...@@ -90,6 +90,7 @@ enum qeth_link_types {
QETH_LINK_TYPE_GBIT_ETH = 0x03, QETH_LINK_TYPE_GBIT_ETH = 0x03,
QETH_LINK_TYPE_OSN = 0x04, QETH_LINK_TYPE_OSN = 0x04,
QETH_LINK_TYPE_10GBIT_ETH = 0x10, QETH_LINK_TYPE_10GBIT_ETH = 0x10,
QETH_LINK_TYPE_25GBIT_ETH = 0x12,
QETH_LINK_TYPE_LANE_ETH100 = 0x81, QETH_LINK_TYPE_LANE_ETH100 = 0x81,
QETH_LINK_TYPE_LANE_TR = 0x82, QETH_LINK_TYPE_LANE_TR = 0x82,
QETH_LINK_TYPE_LANE_ETH1000 = 0x83, QETH_LINK_TYPE_LANE_ETH1000 = 0x83,
...@@ -347,6 +348,7 @@ enum qeth_card_info_port_speed { ...@@ -347,6 +348,7 @@ enum qeth_card_info_port_speed {
CARD_INFO_PORTS_100M = 0x00000006, CARD_INFO_PORTS_100M = 0x00000006,
CARD_INFO_PORTS_1G = 0x00000007, CARD_INFO_PORTS_1G = 0x00000007,
CARD_INFO_PORTS_10G = 0x00000008, CARD_INFO_PORTS_10G = 0x00000008,
CARD_INFO_PORTS_25G = 0x0000000A,
}; };
/* (SET)DELIP(M) IPA stuff ***************************************************/ /* (SET)DELIP(M) IPA stuff ***************************************************/
...@@ -436,7 +438,7 @@ struct qeth_ipacmd_setassparms { ...@@ -436,7 +438,7 @@ struct qeth_ipacmd_setassparms {
__u32 flags_32bit; __u32 flags_32bit;
struct qeth_ipa_caps caps; struct qeth_ipa_caps caps;
struct qeth_checksum_cmd chksum; struct qeth_checksum_cmd chksum;
struct qeth_arp_cache_entry add_arp_entry; struct qeth_arp_cache_entry arp_entry;
struct qeth_arp_query_data query_arp; struct qeth_arp_query_data query_arp;
struct qeth_tso_start_data tso; struct qeth_tso_start_data tso;
__u8 ip[16]; __u8 ip[16];
......
...@@ -146,11 +146,11 @@ static int qeth_l2_write_mac(struct qeth_card *card, u8 *mac) ...@@ -146,11 +146,11 @@ static int qeth_l2_write_mac(struct qeth_card *card, u8 *mac)
QETH_CARD_TEXT(card, 2, "L2Wmac"); QETH_CARD_TEXT(card, 2, "L2Wmac");
rc = qeth_l2_send_setdelmac(card, mac, cmd); rc = qeth_l2_send_setdelmac(card, mac, cmd);
if (rc == -EEXIST) if (rc == -EEXIST)
QETH_DBF_MESSAGE(2, "MAC %pM already registered on %s\n", QETH_DBF_MESSAGE(2, "MAC already registered on device %x\n",
mac, QETH_CARD_IFNAME(card)); CARD_DEVID(card));
else if (rc) else if (rc)
QETH_DBF_MESSAGE(2, "Failed to register MAC %pM on %s: %d\n", QETH_DBF_MESSAGE(2, "Failed to register MAC on device %x: %d\n",
mac, QETH_CARD_IFNAME(card), rc); CARD_DEVID(card), rc);
return rc; return rc;
} }
...@@ -163,8 +163,8 @@ static int qeth_l2_remove_mac(struct qeth_card *card, u8 *mac) ...@@ -163,8 +163,8 @@ static int qeth_l2_remove_mac(struct qeth_card *card, u8 *mac)
QETH_CARD_TEXT(card, 2, "L2Rmac"); QETH_CARD_TEXT(card, 2, "L2Rmac");
rc = qeth_l2_send_setdelmac(card, mac, cmd); rc = qeth_l2_send_setdelmac(card, mac, cmd);
if (rc) if (rc)
QETH_DBF_MESSAGE(2, "Failed to delete MAC %pM on %s: %d\n", QETH_DBF_MESSAGE(2, "Failed to delete MAC on device %u: %d\n",
mac, QETH_CARD_IFNAME(card), rc); CARD_DEVID(card), rc);
return rc; return rc;
} }
...@@ -260,9 +260,9 @@ static int qeth_l2_send_setdelvlan_cb(struct qeth_card *card, ...@@ -260,9 +260,9 @@ static int qeth_l2_send_setdelvlan_cb(struct qeth_card *card,
QETH_CARD_TEXT(card, 2, "L2sdvcb"); QETH_CARD_TEXT(card, 2, "L2sdvcb");
if (cmd->hdr.return_code) { if (cmd->hdr.return_code) {
QETH_DBF_MESSAGE(2, "Error in processing VLAN %i on %s: 0x%x.\n", QETH_DBF_MESSAGE(2, "Error in processing VLAN %u on device %x: %#x.\n",
cmd->data.setdelvlan.vlan_id, cmd->data.setdelvlan.vlan_id,
QETH_CARD_IFNAME(card), cmd->hdr.return_code); CARD_DEVID(card), cmd->hdr.return_code);
QETH_CARD_TEXT_(card, 2, "L2VL%4x", cmd->hdr.command); QETH_CARD_TEXT_(card, 2, "L2VL%4x", cmd->hdr.command);
QETH_CARD_TEXT_(card, 2, "err%d", cmd->hdr.return_code); QETH_CARD_TEXT_(card, 2, "err%d", cmd->hdr.return_code);
} }
...@@ -455,8 +455,8 @@ static int qeth_l2_request_initial_mac(struct qeth_card *card) ...@@ -455,8 +455,8 @@ static int qeth_l2_request_initial_mac(struct qeth_card *card)
rc = qeth_vm_request_mac(card); rc = qeth_vm_request_mac(card);
if (!rc) if (!rc)
goto out; goto out;
QETH_DBF_MESSAGE(2, "z/VM MAC Service failed on device %s: x%x\n", QETH_DBF_MESSAGE(2, "z/VM MAC Service failed on device %x: %#x\n",
CARD_BUS_ID(card), rc); CARD_DEVID(card), rc);
QETH_DBF_TEXT_(SETUP, 2, "err%04x", rc); QETH_DBF_TEXT_(SETUP, 2, "err%04x", rc);
/* fall back to alternative mechanism: */ /* fall back to alternative mechanism: */
} }
...@@ -468,8 +468,8 @@ static int qeth_l2_request_initial_mac(struct qeth_card *card) ...@@ -468,8 +468,8 @@ static int qeth_l2_request_initial_mac(struct qeth_card *card)
rc = qeth_setadpparms_change_macaddr(card); rc = qeth_setadpparms_change_macaddr(card);
if (!rc) if (!rc)
goto out; goto out;
QETH_DBF_MESSAGE(2, "READ_MAC Assist failed on device %s: x%x\n", QETH_DBF_MESSAGE(2, "READ_MAC Assist failed on device %x: %#x\n",
CARD_BUS_ID(card), rc); CARD_DEVID(card), rc);
QETH_DBF_TEXT_(SETUP, 2, "1err%04x", rc); QETH_DBF_TEXT_(SETUP, 2, "1err%04x", rc);
/* fall back once more: */ /* fall back once more: */
} }
...@@ -826,7 +826,8 @@ static void qeth_l2_remove_device(struct ccwgroup_device *cgdev) ...@@ -826,7 +826,8 @@ static void qeth_l2_remove_device(struct ccwgroup_device *cgdev)
if (cgdev->state == CCWGROUP_ONLINE) if (cgdev->state == CCWGROUP_ONLINE)
qeth_l2_set_offline(cgdev); qeth_l2_set_offline(cgdev);
unregister_netdev(card->dev); if (qeth_netdev_is_registered(card->dev))
unregister_netdev(card->dev);
} }
static const struct ethtool_ops qeth_l2_ethtool_ops = { static const struct ethtool_ops qeth_l2_ethtool_ops = {
...@@ -862,11 +863,11 @@ static const struct net_device_ops qeth_l2_netdev_ops = { ...@@ -862,11 +863,11 @@ static const struct net_device_ops qeth_l2_netdev_ops = {
.ndo_set_features = qeth_set_features .ndo_set_features = qeth_set_features
}; };
static int qeth_l2_setup_netdev(struct qeth_card *card) static int qeth_l2_setup_netdev(struct qeth_card *card, bool carrier_ok)
{ {
int rc; int rc;
if (card->dev->netdev_ops) if (qeth_netdev_is_registered(card->dev))
return 0; return 0;
card->dev->priv_flags |= IFF_UNICAST_FLT; card->dev->priv_flags |= IFF_UNICAST_FLT;
...@@ -919,6 +920,9 @@ static int qeth_l2_setup_netdev(struct qeth_card *card) ...@@ -919,6 +920,9 @@ static int qeth_l2_setup_netdev(struct qeth_card *card)
qeth_l2_request_initial_mac(card); qeth_l2_request_initial_mac(card);
netif_napi_add(card->dev, &card->napi, qeth_poll, QETH_NAPI_WEIGHT); netif_napi_add(card->dev, &card->napi, qeth_poll, QETH_NAPI_WEIGHT);
rc = register_netdev(card->dev); rc = register_netdev(card->dev);
if (!rc && carrier_ok)
netif_carrier_on(card->dev);
if (rc) if (rc)
card->dev->netdev_ops = NULL; card->dev->netdev_ops = NULL;
return rc; return rc;
...@@ -949,6 +953,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode) ...@@ -949,6 +953,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode)
struct qeth_card *card = dev_get_drvdata(&gdev->dev); struct qeth_card *card = dev_get_drvdata(&gdev->dev);
int rc = 0; int rc = 0;
enum qeth_card_states recover_flag; enum qeth_card_states recover_flag;
bool carrier_ok;
mutex_lock(&card->discipline_mutex); mutex_lock(&card->discipline_mutex);
mutex_lock(&card->conf_mutex); mutex_lock(&card->conf_mutex);
...@@ -956,7 +961,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode) ...@@ -956,7 +961,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode)
QETH_DBF_HEX(SETUP, 2, &card, sizeof(void *)); QETH_DBF_HEX(SETUP, 2, &card, sizeof(void *));
recover_flag = card->state; recover_flag = card->state;
rc = qeth_core_hardsetup_card(card); rc = qeth_core_hardsetup_card(card, &carrier_ok);
if (rc) { if (rc) {
QETH_DBF_TEXT_(SETUP, 2, "2err%04x", rc); QETH_DBF_TEXT_(SETUP, 2, "2err%04x", rc);
rc = -ENODEV; rc = -ENODEV;
...@@ -967,7 +972,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode) ...@@ -967,7 +972,7 @@ static int __qeth_l2_set_online(struct ccwgroup_device *gdev, int recovery_mode)
dev_info(&card->gdev->dev, dev_info(&card->gdev->dev,
"The device represents a Bridge Capable Port\n"); "The device represents a Bridge Capable Port\n");
rc = qeth_l2_setup_netdev(card); rc = qeth_l2_setup_netdev(card, carrier_ok);
if (rc) if (rc)
goto out_remove; goto out_remove;
......
This diff is collapsed.
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