diff options
Diffstat (limited to 'drivers/net/ethernet/ibm/ibmveth.c')
-rw-r--r-- | drivers/net/ethernet/ibm/ibmveth.c | 23 |
1 files changed, 10 insertions, 13 deletions
diff --git a/drivers/net/ethernet/ibm/ibmveth.c b/drivers/net/ethernet/ibm/ibmveth.c index 302d59401065..70fd55968844 100644 --- a/drivers/net/ethernet/ibm/ibmveth.c +++ b/drivers/net/ethernet/ibm/ibmveth.c | |||
@@ -1322,7 +1322,7 @@ static const struct net_device_ops ibmveth_netdev_ops = { | |||
1322 | 1322 | ||
1323 | static int ibmveth_probe(struct vio_dev *dev, const struct vio_device_id *id) | 1323 | static int ibmveth_probe(struct vio_dev *dev, const struct vio_device_id *id) |
1324 | { | 1324 | { |
1325 | int rc, i; | 1325 | int rc, i, mac_len; |
1326 | struct net_device *netdev; | 1326 | struct net_device *netdev; |
1327 | struct ibmveth_adapter *adapter; | 1327 | struct ibmveth_adapter *adapter; |
1328 | unsigned char *mac_addr_p; | 1328 | unsigned char *mac_addr_p; |
@@ -1332,11 +1332,19 @@ static int ibmveth_probe(struct vio_dev *dev, const struct vio_device_id *id) | |||
1332 | dev->unit_address); | 1332 | dev->unit_address); |
1333 | 1333 | ||
1334 | mac_addr_p = (unsigned char *)vio_get_attribute(dev, VETH_MAC_ADDR, | 1334 | mac_addr_p = (unsigned char *)vio_get_attribute(dev, VETH_MAC_ADDR, |
1335 | NULL); | 1335 | &mac_len); |
1336 | if (!mac_addr_p) { | 1336 | if (!mac_addr_p) { |
1337 | dev_err(&dev->dev, "Can't find VETH_MAC_ADDR attribute\n"); | 1337 | dev_err(&dev->dev, "Can't find VETH_MAC_ADDR attribute\n"); |
1338 | return -EINVAL; | 1338 | return -EINVAL; |
1339 | } | 1339 | } |
1340 | /* Workaround for old/broken pHyp */ | ||
1341 | if (mac_len == 8) | ||
1342 | mac_addr_p += 2; | ||
1343 | else if (mac_len != 6) { | ||
1344 | dev_err(&dev->dev, "VETH_MAC_ADDR attribute wrong len %d\n", | ||
1345 | mac_len); | ||
1346 | return -EINVAL; | ||
1347 | } | ||
1340 | 1348 | ||
1341 | mcastFilterSize_p = (unsigned int *)vio_get_attribute(dev, | 1349 | mcastFilterSize_p = (unsigned int *)vio_get_attribute(dev, |
1342 | VETH_MCAST_FILTER_SIZE, NULL); | 1350 | VETH_MCAST_FILTER_SIZE, NULL); |
@@ -1361,17 +1369,6 @@ static int ibmveth_probe(struct vio_dev *dev, const struct vio_device_id *id) | |||
1361 | 1369 | ||
1362 | netif_napi_add(netdev, &adapter->napi, ibmveth_poll, 16); | 1370 | netif_napi_add(netdev, &adapter->napi, ibmveth_poll, 16); |
1363 | 1371 | ||
1364 | /* | ||
1365 | * Some older boxes running PHYP non-natively have an OF that returns | ||
1366 | * a 8-byte local-mac-address field (and the first 2 bytes have to be | ||
1367 | * ignored) while newer boxes' OF return a 6-byte field. Note that | ||
1368 | * IEEE 1275 specifies that local-mac-address must be a 6-byte field. | ||
1369 | * The RPA doc specifies that the first byte must be 10b, so we'll | ||
1370 | * just look for it to solve this 8 vs. 6 byte field issue | ||
1371 | */ | ||
1372 | if ((*mac_addr_p & 0x3) != 0x02) | ||
1373 | mac_addr_p += 2; | ||
1374 | |||
1375 | adapter->mac_addr = 0; | 1372 | adapter->mac_addr = 0; |
1376 | memcpy(&adapter->mac_addr, mac_addr_p, 6); | 1373 | memcpy(&adapter->mac_addr, mac_addr_p, 6); |
1377 | 1374 | ||