[TG3]: Improve NVRAM sizing.
[pandora-kernel.git] / drivers / net / tg3.c
index 256969e..c01bd86 100644 (file)
 #include <linux/dma-mapping.h>
 
 #include <net/checksum.h>
+#include <net/ip.h>
 
 #include <asm/system.h>
 #include <asm/io.h>
 #include <asm/byteorder.h>
 #include <asm/uaccess.h>
 
-#ifdef CONFIG_SPARC64
+#ifdef CONFIG_SPARC
 #include <asm/idprom.h>
-#include <asm/oplib.h>
-#include <asm/pbm.h>
+#include <asm/prom.h>
 #endif
 
 #if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE)
@@ -3349,7 +3349,7 @@ static int tg3_rx(struct tg3 *tp, int budget)
                        skb_reserve(copy_skb, 2);
                        skb_put(copy_skb, len);
                        pci_dma_sync_single_for_cpu(tp->pdev, dma_addr, len, PCI_DMA_FROMDEVICE);
-                       memcpy(copy_skb->data, skb->data, len);
+                       skb_copy_from_linear_data(skb, copy_skb->data, len);
                        pci_dma_sync_single_for_device(tp->pdev, dma_addr, len, PCI_DMA_FROMDEVICE);
 
                        /* We'll reuse the original ring buffer. */
@@ -3895,8 +3895,7 @@ static int tg3_start_xmit(struct sk_buff *skb, struct net_device *dev)
        entry = tp->tx_prod;
        base_flags = 0;
        mss = 0;
-       if (skb->len > (tp->dev->mtu + ETH_HLEN) &&
-           (mss = skb_shinfo(skb)->gso_size) != 0) {
+       if ((mss = skb_shinfo(skb)->gso_size) != 0) {
                int tcp_opt_len, ip_tcp_len;
 
                if (skb_header_cloned(skb) &&
@@ -3908,20 +3907,20 @@ static int tg3_start_xmit(struct sk_buff *skb, struct net_device *dev)
                if (skb_shinfo(skb)->gso_type & SKB_GSO_TCPV6)
                        mss |= (skb_headlen(skb) - ETH_HLEN) << 9;
                else {
-                       tcp_opt_len = ((skb->h.th->doff - 5) * 4);
-                       ip_tcp_len = (skb->nh.iph->ihl * 4) +
-                                    sizeof(struct tcphdr);
+                       struct iphdr *iph = ip_hdr(skb);
+
+                       tcp_opt_len = tcp_optlen(skb);
+                       ip_tcp_len = ip_hdrlen(skb) + sizeof(struct tcphdr);
 
-                       skb->nh.iph->check = 0;
-                       skb->nh.iph->tot_len = htons(mss + ip_tcp_len +
-                                                    tcp_opt_len);
+                       iph->check = 0;
+                       iph->tot_len = htons(mss + ip_tcp_len + tcp_opt_len);
                        mss |= (ip_tcp_len + tcp_opt_len) << 9;
                }
 
                base_flags |= (TXD_FLAG_CPU_PRE_DMA |
                               TXD_FLAG_CPU_POST_DMA);
 
-               skb->h.th->check = 0;
+               tcp_hdr(skb)->check = 0;
 
        }
        else if (skb->ip_summed == CHECKSUM_PARTIAL)
@@ -4053,8 +4052,8 @@ static int tg3_start_xmit_dma_bug(struct sk_buff *skb, struct net_device *dev)
        if (skb->ip_summed == CHECKSUM_PARTIAL)
                base_flags |= TXD_FLAG_TCPUDP_CSUM;
        mss = 0;
-       if (skb->len > (tp->dev->mtu + ETH_HLEN) &&
-           (mss = skb_shinfo(skb)->gso_size) != 0) {
+       if ((mss = skb_shinfo(skb)->gso_size) != 0) {
+               struct iphdr *iph;
                int tcp_opt_len, ip_tcp_len, hdr_len;
 
                if (skb_header_cloned(skb) &&
@@ -4063,8 +4062,8 @@ static int tg3_start_xmit_dma_bug(struct sk_buff *skb, struct net_device *dev)
                        goto out_unlock;
                }
 
-               tcp_opt_len = ((skb->h.th->doff - 5) * 4);
-               ip_tcp_len = (skb->nh.iph->ihl * 4) + sizeof(struct tcphdr);
+               tcp_opt_len = tcp_optlen(skb);
+               ip_tcp_len = ip_hdrlen(skb) + sizeof(struct tcphdr);
 
                hdr_len = ip_tcp_len + tcp_opt_len;
                if (unlikely((ETH_HLEN + hdr_len) > 80) &&
@@ -4074,34 +4073,31 @@ static int tg3_start_xmit_dma_bug(struct sk_buff *skb, struct net_device *dev)
                base_flags |= (TXD_FLAG_CPU_PRE_DMA |
                               TXD_FLAG_CPU_POST_DMA);
 
-               skb->nh.iph->check = 0;
-               skb->nh.iph->tot_len = htons(mss + hdr_len);
+               iph = ip_hdr(skb);
+               iph->check = 0;
+               iph->tot_len = htons(mss + hdr_len);
                if (tp->tg3_flags2 & TG3_FLG2_HW_TSO) {
-                       skb->h.th->check = 0;
+                       tcp_hdr(skb)->check = 0;
                        base_flags &= ~TXD_FLAG_TCPUDP_CSUM;
-               }
-               else {
-                       skb->h.th->check =
-                               ~csum_tcpudp_magic(skb->nh.iph->saddr,
-                                                  skb->nh.iph->daddr,
-                                                  0, IPPROTO_TCP, 0);
-               }
+               } else
+                       tcp_hdr(skb)->check = ~csum_tcpudp_magic(iph->saddr,
+                                                                iph->daddr, 0,
+                                                                IPPROTO_TCP,
+                                                                0);
 
                if ((tp->tg3_flags2 & TG3_FLG2_HW_TSO) ||
                    (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5705)) {
-                       if (tcp_opt_len || skb->nh.iph->ihl > 5) {
+                       if (tcp_opt_len || iph->ihl > 5) {
                                int tsflags;
 
-                               tsflags = ((skb->nh.iph->ihl - 5) +
-                                          (tcp_opt_len >> 2));
+                               tsflags = (iph->ihl - 5) + (tcp_opt_len >> 2);
                                mss |= (tsflags << 11);
                        }
                } else {
-                       if (tcp_opt_len || skb->nh.iph->ihl > 5) {
+                       if (tcp_opt_len || iph->ihl > 5) {
                                int tsflags;
 
-                               tsflags = ((skb->nh.iph->ihl - 5) +
-                                          (tcp_opt_len >> 2));
+                               tsflags = (iph->ihl - 5) + (tcp_opt_len >> 2);
                                base_flags |= tsflags << 12;
                        }
                }
@@ -6348,8 +6344,7 @@ static int tg3_reset_hw(struct tg3 *tp, int reset_phy)
             tp->pci_chip_rev_id != CHIPREV_ID_5705_A0) ||
            (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5750)) {
                if (tp->tg3_flags2 & TG3_FLG2_TSO_CAPABLE &&
-                   (tp->pci_chip_rev_id == CHIPREV_ID_5705_A1 ||
-                    tp->pci_chip_rev_id == CHIPREV_ID_5705_A2)) {
+                   GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5705) {
                        rdmac_mode |= RDMAC_MODE_FIFO_SIZE_128;
                } else if (!(tr32(TG3PCI_PCISTATE) & PCISTATE_BUS_SPEED_HIGH) &&
                           !(tp->tg3_flags2 & TG3_FLG2_IS_5788)) {
@@ -9291,7 +9286,7 @@ static void __devinit tg3_get_nvram_size(struct tg3 *tp)
                        return;
                }
        }
-       tp->nvram_size = 0x20000;
+       tp->nvram_size = 0x80000;
 }
 
 static void __devinit tg3_get_nvram_info(struct tg3 *tp)
@@ -9410,33 +9405,31 @@ static void __devinit tg3_get_5752_nvram_info(struct tg3 *tp)
 
 static void __devinit tg3_get_5755_nvram_info(struct tg3 *tp)
 {
-       u32 nvcfg1;
+       u32 nvcfg1, protect = 0;
 
        nvcfg1 = tr32(NVRAM_CFG1);
 
        /* NVRAM protection for TPM */
-       if (nvcfg1 & (1 << 27))
+       if (nvcfg1 & (1 << 27)) {
                tp->tg3_flags2 |= TG3_FLG2_PROTECTED_NVRAM;
+               protect = 1;
+       }
 
-       switch (nvcfg1 & NVRAM_CFG1_5752VENDOR_MASK) {
-               case FLASH_5755VENDOR_ATMEL_EEPROM_64KHZ:
-               case FLASH_5755VENDOR_ATMEL_EEPROM_376KHZ:
-                       tp->nvram_jedecnum = JEDEC_ATMEL;
-                       tp->tg3_flags |= TG3_FLAG_NVRAM_BUFFERED;
-                       tp->nvram_pagesize = ATMEL_AT24C512_CHIP_SIZE;
-
-                       nvcfg1 &= ~NVRAM_CFG1_COMPAT_BYPASS;
-                       tw32(NVRAM_CFG1, nvcfg1);
-                       break;
-               case FLASH_5752VENDOR_ATMEL_FLASH_BUFFERED:
+       nvcfg1 &= NVRAM_CFG1_5752VENDOR_MASK;
+       switch (nvcfg1) {
                case FLASH_5755VENDOR_ATMEL_FLASH_1:
                case FLASH_5755VENDOR_ATMEL_FLASH_2:
                case FLASH_5755VENDOR_ATMEL_FLASH_3:
-               case FLASH_5755VENDOR_ATMEL_FLASH_4:
                        tp->nvram_jedecnum = JEDEC_ATMEL;
                        tp->tg3_flags |= TG3_FLAG_NVRAM_BUFFERED;
                        tp->tg3_flags2 |= TG3_FLG2_FLASH;
                        tp->nvram_pagesize = 264;
+                       if (nvcfg1 == FLASH_5755VENDOR_ATMEL_FLASH_1)
+                               tp->nvram_size = (protect ? 0x3e200 : 0x80000);
+                       else if (nvcfg1 == FLASH_5755VENDOR_ATMEL_FLASH_2)
+                               tp->nvram_size = (protect ? 0x1f200 : 0x40000);
+                       else
+                               tp->nvram_size = (protect ? 0x1f200 : 0x20000);
                        break;
                case FLASH_5752VENDOR_ST_M45PE10:
                case FLASH_5752VENDOR_ST_M45PE20:
@@ -9445,6 +9438,12 @@ static void __devinit tg3_get_5755_nvram_info(struct tg3 *tp)
                        tp->tg3_flags |= TG3_FLAG_NVRAM_BUFFERED;
                        tp->tg3_flags2 |= TG3_FLG2_FLASH;
                        tp->nvram_pagesize = 256;
+                       if (nvcfg1 == FLASH_5752VENDOR_ST_M45PE10)
+                               tp->nvram_size = (protect ? 0x10000 : 0x20000);
+                       else if (nvcfg1 == FLASH_5752VENDOR_ST_M45PE20)
+                               tp->nvram_size = (protect ? 0x10000 : 0x40000);
+                       else
+                               tp->nvram_size = (protect ? 0x20000 : 0x80000);
                        break;
        }
 }
@@ -9520,6 +9519,8 @@ static void __devinit tg3_nvram_init(struct tg3 *tp)
                }
                tg3_enable_nvram_access(tp);
 
+               tp->nvram_size = 0;
+
                if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5752)
                        tg3_get_5752_nvram_info(tp);
                else if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5755)
@@ -9531,7 +9532,8 @@ static void __devinit tg3_nvram_init(struct tg3 *tp)
                else
                        tg3_get_nvram_info(tp);
 
-               tg3_get_nvram_size(tp);
+               if (tp->nvram_size == 0)
+                       tg3_get_nvram_size(tp);
 
                tg3_disable_nvram_access(tp);
                tg3_nvram_unlock(tp);
@@ -10988,24 +10990,20 @@ static int __devinit tg3_get_invariants(struct tg3 *tp)
        return err;
 }
 
-#ifdef CONFIG_SPARC64
+#ifdef CONFIG_SPARC
 static int __devinit tg3_get_macaddr_sparc(struct tg3 *tp)
 {
        struct net_device *dev = tp->dev;
        struct pci_dev *pdev = tp->pdev;
-       struct pcidev_cookie *pcp = pdev->sysdata;
-
-       if (pcp != NULL) {
-               unsigned char *addr;
-               int len;
-
-               addr = of_get_property(pcp->prom_node, "local-mac-address",
-                                       &len);
-               if (addr && len == 6) {
-                       memcpy(dev->dev_addr, addr, 6);
-                       memcpy(dev->perm_addr, dev->dev_addr, 6);
-                       return 0;
-               }
+       struct device_node *dp = pci_device_to_OF_node(pdev);
+       const unsigned char *addr;
+       int len;
+
+       addr = of_get_property(dp, "local-mac-address", &len);
+       if (addr && len == 6) {
+               memcpy(dev->dev_addr, addr, 6);
+               memcpy(dev->perm_addr, dev->dev_addr, 6);
+               return 0;
        }
        return -ENODEV;
 }
@@ -11026,7 +11024,7 @@ static int __devinit tg3_get_device_address(struct tg3 *tp)
        u32 hi, lo, mac_offset;
        int addr_ok = 0;
 
-#ifdef CONFIG_SPARC64
+#ifdef CONFIG_SPARC
        if (!tg3_get_macaddr_sparc(tp))
                return 0;
 #endif