1 /* 2 * Copyright (C) 2005 Sven Luther <sl@bplan-gmbh.de> 3 * Thanks to : 4 * Dale Farnsworth <dale@farnsworth.org> 5 * Mark A. Greer <mgreer@mvista.com> 6 * Nicolas DET <nd@bplan-gmbh.de> 7 * Benjamin Herrenschmidt <benh@kernel.crashing.org> 8 * And anyone else who helped me on this. 9 */ 10 11 #include <linux/types.h> 12 #include <linux/init.h> 13 #include <linux/ioport.h> 14 #include <linux/device.h> 15 #include <linux/platform_device.h> 16 #include <linux/mv643xx.h> 17 #include <linux/pci.h> 18 19 #define PEGASOS2_MARVELL_REGBASE (0xf1000000) 20 #define PEGASOS2_MARVELL_REGSIZE (0x00004000) 21 #define PEGASOS2_SRAM_BASE (0xf2000000) 22 #define PEGASOS2_SRAM_SIZE (256*1024) 23 24 #define PEGASOS2_SRAM_BASE_ETH0 (PEGASOS2_SRAM_BASE) 25 #define PEGASOS2_SRAM_BASE_ETH1 (PEGASOS2_SRAM_BASE_ETH0 + (PEGASOS2_SRAM_SIZE / 2) ) 26 27 28 #define PEGASOS2_SRAM_RXRING_SIZE (PEGASOS2_SRAM_SIZE/4) 29 #define PEGASOS2_SRAM_TXRING_SIZE (PEGASOS2_SRAM_SIZE/4) 30 31 #undef BE_VERBOSE 32 33 static struct resource mv643xx_eth_shared_resources[] = { 34 [0] = { 35 .name = "ethernet shared base", 36 .start = 0xf1000000 + MV643XX_ETH_SHARED_REGS, 37 .end = 0xf1000000 + MV643XX_ETH_SHARED_REGS + 38 MV643XX_ETH_SHARED_REGS_SIZE - 1, 39 .flags = IORESOURCE_MEM, 40 }, 41 }; 42 43 static struct platform_device mv643xx_eth_shared_device = { 44 .name = MV643XX_ETH_SHARED_NAME, 45 .id = 0, 46 .num_resources = ARRAY_SIZE(mv643xx_eth_shared_resources), 47 .resource = mv643xx_eth_shared_resources, 48 }; 49 50 static struct resource mv643xx_eth0_resources[] = { 51 [0] = { 52 .name = "eth0 irq", 53 .start = 9, 54 .end = 9, 55 .flags = IORESOURCE_IRQ, 56 }, 57 }; 58 59 60 static struct mv643xx_eth_platform_data eth0_pd = { 61 .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH0, 62 .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, 63 .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, 64 65 .rx_sram_addr = PEGASOS2_SRAM_BASE_ETH0 + PEGASOS2_SRAM_TXRING_SIZE, 66 .rx_sram_size = PEGASOS2_SRAM_RXRING_SIZE, 67 .rx_queue_size = PEGASOS2_SRAM_RXRING_SIZE/16, 68 }; 69 70 static struct platform_device eth0_device = { 71 .name = MV643XX_ETH_NAME, 72 .id = 0, 73 .num_resources = ARRAY_SIZE(mv643xx_eth0_resources), 74 .resource = mv643xx_eth0_resources, 75 .dev = { 76 .platform_data = ð0_pd, 77 }, 78 }; 79 80 static struct resource mv643xx_eth1_resources[] = { 81 [0] = { 82 .name = "eth1 irq", 83 .start = 9, 84 .end = 9, 85 .flags = IORESOURCE_IRQ, 86 }, 87 }; 88 89 static struct mv643xx_eth_platform_data eth1_pd = { 90 .tx_sram_addr = PEGASOS2_SRAM_BASE_ETH1, 91 .tx_sram_size = PEGASOS2_SRAM_TXRING_SIZE, 92 .tx_queue_size = PEGASOS2_SRAM_TXRING_SIZE/16, 93 94 .rx_sram_addr = PEGASOS2_SRAM_BASE_ETH1 + PEGASOS2_SRAM_TXRING_SIZE, 95 .rx_sram_size = PEGASOS2_SRAM_RXRING_SIZE, 96 .rx_queue_size = PEGASOS2_SRAM_RXRING_SIZE/16, 97 }; 98 99 static struct platform_device eth1_device = { 100 .name = MV643XX_ETH_NAME, 101 .id = 1, 102 .num_resources = ARRAY_SIZE(mv643xx_eth1_resources), 103 .resource = mv643xx_eth1_resources, 104 .dev = { 105 .platform_data = ð1_pd, 106 }, 107 }; 108 109 static struct platform_device *mv643xx_eth_pd_devs[] __initdata = { 110 &mv643xx_eth_shared_device, 111 ð0_device, 112 ð1_device, 113 }; 114 115 /***********/ 116 /***********/ 117 #define MV_READ(offset,val) { val = readl(mv643xx_reg_base + offset); } 118 #define MV_WRITE(offset,data) writel(data, mv643xx_reg_base + offset) 119 120 static void __iomem *mv643xx_reg_base; 121 122 static int Enable_SRAM(void) 123 { 124 u32 ALong; 125 126 if (mv643xx_reg_base == NULL) 127 mv643xx_reg_base = ioremap(PEGASOS2_MARVELL_REGBASE, 128 PEGASOS2_MARVELL_REGSIZE); 129 130 if (mv643xx_reg_base == NULL) 131 return -ENOMEM; 132 133 #ifdef BE_VERBOSE 134 printk("Pegasos II/Marvell MV64361: register remapped from %p to %p\n", 135 (void *)PEGASOS2_MARVELL_REGBASE, (void *)mv643xx_reg_base); 136 #endif 137 138 MV_WRITE(MV64340_SRAM_CONFIG, 0); 139 140 MV_WRITE(MV64340_INTEGRATED_SRAM_BASE_ADDR, PEGASOS2_SRAM_BASE >> 16); 141 142 MV_READ(MV64340_BASE_ADDR_ENABLE, ALong); 143 ALong &= ~(1 << 19); 144 MV_WRITE(MV64340_BASE_ADDR_ENABLE, ALong); 145 146 ALong = 0x02; 147 ALong |= PEGASOS2_SRAM_BASE & 0xffff0000; 148 MV_WRITE(MV643XX_ETH_BAR_4, ALong); 149 150 MV_WRITE(MV643XX_ETH_SIZE_REG_4, (PEGASOS2_SRAM_SIZE-1) & 0xffff0000); 151 152 MV_READ(MV643XX_ETH_BASE_ADDR_ENABLE_REG, ALong); 153 ALong &= ~(1 << 4); 154 MV_WRITE(MV643XX_ETH_BASE_ADDR_ENABLE_REG, ALong); 155 156 #ifdef BE_VERBOSE 157 printk("Pegasos II/Marvell MV64361: register unmapped\n"); 158 printk("Pegasos II/Marvell MV64361: SRAM at %p, size=%x\n", (void*) PEGASOS2_SRAM_BASE, PEGASOS2_SRAM_SIZE); 159 #endif 160 161 iounmap(mv643xx_reg_base); 162 mv643xx_reg_base = NULL; 163 164 return 1; 165 } 166 167 168 /***********/ 169 /***********/ 170 int mv643xx_eth_add_pds(void) 171 { 172 int ret = 0; 173 static struct pci_device_id pci_marvell_mv64360[] = { 174 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, PCI_DEVICE_ID_MARVELL_MV64360) }, 175 { } 176 }; 177 178 #ifdef BE_VERBOSE 179 printk("Pegasos II/Marvell MV64361: init\n"); 180 #endif 181 182 if (pci_dev_present(pci_marvell_mv64360)) { 183 ret = platform_add_devices(mv643xx_eth_pd_devs, 184 ARRAY_SIZE(mv643xx_eth_pd_devs)); 185 186 if ( Enable_SRAM() < 0) 187 { 188 eth0_pd.tx_sram_addr = 0; 189 eth0_pd.tx_sram_size = 0; 190 eth0_pd.rx_sram_addr = 0; 191 eth0_pd.rx_sram_size = 0; 192 193 eth1_pd.tx_sram_addr = 0; 194 eth1_pd.tx_sram_size = 0; 195 eth1_pd.rx_sram_addr = 0; 196 eth1_pd.rx_sram_size = 0; 197 198 #ifdef BE_VERBOSE 199 printk("Pegasos II/Marvell MV64361: Can't enable the " 200 "SRAM\n"); 201 #endif 202 } 203 } 204 205 #ifdef BE_VERBOSE 206 printk("Pegasos II/Marvell MV64361: init is over\n"); 207 #endif 208 209 return ret; 210 } 211 212 device_initcall(mv643xx_eth_add_pds); 213