aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ethernet/ibm
diff options
context:
space:
mode:
authorDuc Dang <dhdang@apm.com>2012-03-04 19:58:22 -0500
committerDavid S. Miller <davem@davemloft.net>2012-03-06 17:07:42 -0500
commitae5d33723e325392c48bc0ff481d9ec8d646a0ed (patch)
treeec5c0a9b4454f0c7e6c999f64b8ec6cde52ccf7f /drivers/net/ethernet/ibm
parent8dfc2b45ffc722c4291f24f1f40c64e448b9b5b4 (diff)
powerpc/44x: Add more changes for APM821XX EMAC driver
This patch includes: Configure EMAC PHY clock source (clock from PHY or internal clock). Do not advertise PHY half duplex capability as APM821XX EMAC does not support half duplex mode. Add changes to support configuring jumbo frame for APM821XX EMAC. [ Fix coding style -DaveM ] Signed-off-by: Duc Dang <dhdang@apm.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/ibm')
-rw-r--r--drivers/net/ethernet/ibm/emac/core.c29
-rw-r--r--drivers/net/ethernet/ibm/emac/core.h13
-rw-r--r--drivers/net/ethernet/ibm/emac/emac.h2
3 files changed, 41 insertions, 3 deletions
diff --git a/drivers/net/ethernet/ibm/emac/core.c b/drivers/net/ethernet/ibm/emac/core.c
index dac7ffb4eaf1..a0fe6e3fce61 100644
--- a/drivers/net/ethernet/ibm/emac/core.c
+++ b/drivers/net/ethernet/ibm/emac/core.c
@@ -434,6 +434,11 @@ static inline u32 emac_iff2rmr(struct net_device *ndev)
434 else if (!netdev_mc_empty(ndev)) 434 else if (!netdev_mc_empty(ndev))
435 r |= EMAC_RMR_MAE; 435 r |= EMAC_RMR_MAE;
436 436
437 if (emac_has_feature(dev, EMAC_APM821XX_REQ_JUMBO_FRAME_SIZE)) {
438 r &= ~EMAC4_RMR_MJS_MASK;
439 r |= EMAC4_RMR_MJS(ndev->mtu);
440 }
441
437 return r; 442 return r;
438} 443}
439 444
@@ -965,6 +970,7 @@ static int emac_resize_rx_ring(struct emac_instance *dev, int new_mtu)
965 int rx_sync_size = emac_rx_sync_size(new_mtu); 970 int rx_sync_size = emac_rx_sync_size(new_mtu);
966 int rx_skb_size = emac_rx_skb_size(new_mtu); 971 int rx_skb_size = emac_rx_skb_size(new_mtu);
967 int i, ret = 0; 972 int i, ret = 0;
973 int mr1_jumbo_bit_change = 0;
968 974
969 mutex_lock(&dev->link_lock); 975 mutex_lock(&dev->link_lock);
970 emac_netif_stop(dev); 976 emac_netif_stop(dev);
@@ -1013,7 +1019,15 @@ static int emac_resize_rx_ring(struct emac_instance *dev, int new_mtu)
1013 } 1019 }
1014 skip: 1020 skip:
1015 /* Check if we need to change "Jumbo" bit in MR1 */ 1021 /* Check if we need to change "Jumbo" bit in MR1 */
1016 if ((new_mtu > ETH_DATA_LEN) ^ (dev->ndev->mtu > ETH_DATA_LEN)) { 1022 if (emac_has_feature(dev, EMAC_APM821XX_REQ_JUMBO_FRAME_SIZE)) {
1023 mr1_jumbo_bit_change = (new_mtu > ETH_DATA_LEN) ||
1024 (dev->ndev->mtu > ETH_DATA_LEN);
1025 } else {
1026 mr1_jumbo_bit_change = (new_mtu > ETH_DATA_LEN) ^
1027 (dev->ndev->mtu > ETH_DATA_LEN);
1028 }
1029
1030 if (mr1_jumbo_bit_change) {
1017 /* This is to prevent starting RX channel in emac_rx_enable() */ 1031 /* This is to prevent starting RX channel in emac_rx_enable() */
1018 set_bit(MAL_COMMAC_RX_STOPPED, &dev->commac.flags); 1032 set_bit(MAL_COMMAC_RX_STOPPED, &dev->commac.flags);
1019 1033
@@ -2471,6 +2485,7 @@ static int __devinit emac_init_phy(struct emac_instance *dev)
2471 2485
2472 /* Disable any PHY features not supported by the platform */ 2486 /* Disable any PHY features not supported by the platform */
2473 dev->phy.def->features &= ~dev->phy_feat_exc; 2487 dev->phy.def->features &= ~dev->phy_feat_exc;
2488 dev->phy.features &= ~dev->phy_feat_exc;
2474 2489
2475 /* Setup initial link parameters */ 2490 /* Setup initial link parameters */
2476 if (dev->phy.features & SUPPORTED_Autoneg) { 2491 if (dev->phy.features & SUPPORTED_Autoneg) {
@@ -2568,6 +2583,11 @@ static int __devinit emac_init_config(struct emac_instance *dev)
2568 if (of_device_is_compatible(np, "ibm,emac-405ex") || 2583 if (of_device_is_compatible(np, "ibm,emac-405ex") ||
2569 of_device_is_compatible(np, "ibm,emac-405exr")) 2584 of_device_is_compatible(np, "ibm,emac-405exr"))
2570 dev->features |= EMAC_FTR_440EP_PHY_CLK_FIX; 2585 dev->features |= EMAC_FTR_440EP_PHY_CLK_FIX;
2586 if (of_device_is_compatible(np, "ibm,emac-apm821xx")) {
2587 dev->features |= (EMAC_APM821XX_REQ_JUMBO_FRAME_SIZE |
2588 EMAC_FTR_APM821XX_NO_HALF_DUPLEX |
2589 EMAC_FTR_460EX_PHY_CLK_FIX);
2590 }
2571 } else if (of_device_is_compatible(np, "ibm,emac4")) { 2591 } else if (of_device_is_compatible(np, "ibm,emac4")) {
2572 dev->features |= EMAC_FTR_EMAC4; 2592 dev->features |= EMAC_FTR_EMAC4;
2573 if (of_device_is_compatible(np, "ibm,emac-440gx")) 2593 if (of_device_is_compatible(np, "ibm,emac-440gx"))
@@ -2816,6 +2836,13 @@ static int __devinit emac_probe(struct platform_device *ofdev)
2816 dev->stop_timeout = STOP_TIMEOUT_100; 2836 dev->stop_timeout = STOP_TIMEOUT_100;
2817 INIT_DELAYED_WORK(&dev->link_work, emac_link_timer); 2837 INIT_DELAYED_WORK(&dev->link_work, emac_link_timer);
2818 2838
2839 /* Some SoCs like APM821xx does not support Half Duplex mode. */
2840 if (emac_has_feature(dev, EMAC_FTR_APM821XX_NO_HALF_DUPLEX)) {
2841 dev->phy_feat_exc = (SUPPORTED_1000baseT_Half |
2842 SUPPORTED_100baseT_Half |
2843 SUPPORTED_10baseT_Half);
2844 }
2845
2819 /* Find PHY if any */ 2846 /* Find PHY if any */
2820 err = emac_init_phy(dev); 2847 err = emac_init_phy(dev);
2821 if (err != 0) 2848 if (err != 0)
diff --git a/drivers/net/ethernet/ibm/emac/core.h b/drivers/net/ethernet/ibm/emac/core.h
index bade29690c71..70074792bdef 100644
--- a/drivers/net/ethernet/ibm/emac/core.h
+++ b/drivers/net/ethernet/ibm/emac/core.h
@@ -325,7 +325,14 @@ struct emac_instance {
325 * Set if we need phy clock workaround for 460ex or 460gt 325 * Set if we need phy clock workaround for 460ex or 460gt
326 */ 326 */
327#define EMAC_FTR_460EX_PHY_CLK_FIX 0x00000400 327#define EMAC_FTR_460EX_PHY_CLK_FIX 0x00000400
328 328/*
329 * APM821xx requires Jumbo frame size set explicitly
330 */
331#define EMAC_APM821XX_REQ_JUMBO_FRAME_SIZE 0x00000800
332/*
333 * APM821xx does not support Half Duplex mode
334 */
335#define EMAC_FTR_APM821XX_NO_HALF_DUPLEX 0x00001000
329 336
330/* Right now, we don't quite handle the always/possible masks on the 337/* Right now, we don't quite handle the always/possible masks on the
331 * most optimal way as we don't have a way to say something like 338 * most optimal way as we don't have a way to say something like
@@ -353,7 +360,9 @@ enum {
353 EMAC_FTR_NO_FLOW_CONTROL_40x | 360 EMAC_FTR_NO_FLOW_CONTROL_40x |
354#endif 361#endif
355 EMAC_FTR_460EX_PHY_CLK_FIX | 362 EMAC_FTR_460EX_PHY_CLK_FIX |
356 EMAC_FTR_440EP_PHY_CLK_FIX, 363 EMAC_FTR_440EP_PHY_CLK_FIX |
364 EMAC_APM821XX_REQ_JUMBO_FRAME_SIZE |
365 EMAC_FTR_APM821XX_NO_HALF_DUPLEX,
357}; 366};
358 367
359static inline int emac_has_feature(struct emac_instance *dev, 368static inline int emac_has_feature(struct emac_instance *dev,
diff --git a/drivers/net/ethernet/ibm/emac/emac.h b/drivers/net/ethernet/ibm/emac/emac.h
index b44bd243fb58..5afcc27ceebb 100644
--- a/drivers/net/ethernet/ibm/emac/emac.h
+++ b/drivers/net/ethernet/ibm/emac/emac.h
@@ -212,6 +212,8 @@ struct emac_regs {
212#define EMAC4_RMR_RFAF_64_1024 0x00000006 212#define EMAC4_RMR_RFAF_64_1024 0x00000006
213#define EMAC4_RMR_RFAF_128_2048 0x00000007 213#define EMAC4_RMR_RFAF_128_2048 0x00000007
214#define EMAC4_RMR_BASE EMAC4_RMR_RFAF_128_2048 214#define EMAC4_RMR_BASE EMAC4_RMR_RFAF_128_2048
215#define EMAC4_RMR_MJS_MASK 0x0001fff8
216#define EMAC4_RMR_MJS(s) (((s) << 3) & EMAC4_RMR_MJS_MASK)
215 217
216/* EMACx_ISR & EMACx_ISER */ 218/* EMACx_ISR & EMACx_ISER */
217#define EMAC4_ISR_TXPE 0x20000000 219#define EMAC4_ISR_TXPE 0x20000000