[TG3]: Prescaler fix
authorMatt Carlson <mcarlson@broadcom.com>
Tue, 13 Nov 2007 05:18:04 +0000 (21:18 -0800)
committerDavid S. Miller <davem@davemloft.net>
Tue, 13 Nov 2007 05:18:04 +0000 (21:18 -0800)
Internal hardware timers become inaccurate after link events.  Clock
frequency switches performed by the CPMU fail to adjust timer
prescalers.  The fix is to detect core clock frequency changes during
link events and adjust the timer prescalers accordingly.

Signed-off-by: Matt Carlson <mcarlson@broadcom.com>
Signed-off-by: Michael Chan <mchan@broadcom.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
drivers/net/tg3.c
drivers/net/tg3.h

index bb3b734351706eba6dc5b35ba6342854b9c0b107..ecd64a224e95219d926cc57f6fe923ee0539e16b 100644 (file)
@@ -3154,6 +3154,22 @@ static int tg3_setup_phy(struct tg3 *tp, int force_reset)
                err = tg3_setup_copper_phy(tp, force_reset);
        }
 
+       if (tp->pci_chip_rev_id == CHIPREV_ID_5784_A0) {
+               u32 val, scale;
+
+               val = tr32(TG3_CPMU_CLCK_STAT) & CPMU_CLCK_STAT_MAC_CLCK_MASK;
+               if (val == CPMU_CLCK_STAT_MAC_CLCK_62_5)
+                       scale = 65;
+               else if (val == CPMU_CLCK_STAT_MAC_CLCK_6_25)
+                       scale = 6;
+               else
+                       scale = 12;
+
+               val = tr32(GRC_MISC_CFG) & ~GRC_MISC_CFG_PRESCALAR_MASK;
+               val |= (scale << GRC_MISC_CFG_PRESCALAR_SHIFT);
+               tw32(GRC_MISC_CFG, val);
+       }
+
        if (tp->link_config.active_speed == SPEED_1000 &&
            tp->link_config.active_duplex == DUPLEX_HALF)
                tw32(MAC_TX_LENGTHS,
index 5b799ff2c4d6b9730a56a629d9380e3b66d198bc..d325ab59b391b095f39e7c0f8f939cbeee2dc8fb 100644 (file)
 #define TG3_CPMU_HST_ACC               0x0000361c
 #define  CPMU_HST_ACC_MACCLK_MASK       0x001f0000
 #define  CPMU_HST_ACC_MACCLK_6_25       0x00130000
-/* 0x3620 --> 0x365c unused */
+/* 0x3620 --> 0x3630 unused */
+
+#define TG3_CPMU_CLCK_STAT             0x00003630
+#define  CPMU_CLCK_STAT_MAC_CLCK_MASK   0x001f0000
+#define  CPMU_CLCK_STAT_MAC_CLCK_62_5   0x00000000
+#define  CPMU_CLCK_STAT_MAC_CLCK_12_5   0x00110000
+#define  CPMU_CLCK_STAT_MAC_CLCK_6_25   0x00130000
+/* 0x3634 --> 0x365c unused */
 
 #define TG3_CPMU_MUTEX_REQ             0x0000365c
 #define  CPMU_MUTEX_REQ_DRIVER          0x00001000