common.c 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570
  1. /*
  2. * arch/arm/mach-kirkwood/common.c
  3. *
  4. * Core functions for Marvell Kirkwood SoCs
  5. *
  6. * This file is licensed under the terms of the GNU General Public
  7. * License version 2. This program is licensed "as is" without any
  8. * warranty of any kind, whether express or implied.
  9. */
  10. #include <linux/kernel.h>
  11. #include <linux/init.h>
  12. #include <linux/platform_device.h>
  13. #include <linux/serial_8250.h>
  14. #include <linux/mbus.h>
  15. #include <linux/mv643xx_eth.h>
  16. #include <linux/ata_platform.h>
  17. #include <linux/spi/orion_spi.h>
  18. #include <asm/page.h>
  19. #include <asm/timex.h>
  20. #include <asm/mach/map.h>
  21. #include <asm/mach/time.h>
  22. #include <mach/kirkwood.h>
  23. #include <plat/cache-feroceon-l2.h>
  24. #include <plat/ehci-orion.h>
  25. #include <plat/mv_xor.h>
  26. #include <plat/orion_nand.h>
  27. #include <plat/time.h>
  28. #include "common.h"
  29. /*****************************************************************************
  30. * I/O Address Mapping
  31. ****************************************************************************/
  32. static struct map_desc kirkwood_io_desc[] __initdata = {
  33. {
  34. .virtual = KIRKWOOD_PCIE_IO_VIRT_BASE,
  35. .pfn = __phys_to_pfn(KIRKWOOD_PCIE_IO_PHYS_BASE),
  36. .length = KIRKWOOD_PCIE_IO_SIZE,
  37. .type = MT_DEVICE,
  38. }, {
  39. .virtual = KIRKWOOD_REGS_VIRT_BASE,
  40. .pfn = __phys_to_pfn(KIRKWOOD_REGS_PHYS_BASE),
  41. .length = KIRKWOOD_REGS_SIZE,
  42. .type = MT_DEVICE,
  43. },
  44. };
  45. void __init kirkwood_map_io(void)
  46. {
  47. iotable_init(kirkwood_io_desc, ARRAY_SIZE(kirkwood_io_desc));
  48. }
  49. /*****************************************************************************
  50. * EHCI
  51. ****************************************************************************/
  52. static struct orion_ehci_data kirkwood_ehci_data = {
  53. .dram = &kirkwood_mbus_dram_info,
  54. };
  55. static u64 ehci_dmamask = 0xffffffffUL;
  56. /*****************************************************************************
  57. * EHCI0
  58. ****************************************************************************/
  59. static struct resource kirkwood_ehci_resources[] = {
  60. {
  61. .start = USB_PHYS_BASE,
  62. .end = USB_PHYS_BASE + 0x0fff,
  63. .flags = IORESOURCE_MEM,
  64. }, {
  65. .start = IRQ_KIRKWOOD_USB,
  66. .end = IRQ_KIRKWOOD_USB,
  67. .flags = IORESOURCE_IRQ,
  68. },
  69. };
  70. static struct platform_device kirkwood_ehci = {
  71. .name = "orion-ehci",
  72. .id = 0,
  73. .dev = {
  74. .dma_mask = &ehci_dmamask,
  75. .coherent_dma_mask = 0xffffffff,
  76. .platform_data = &kirkwood_ehci_data,
  77. },
  78. .resource = kirkwood_ehci_resources,
  79. .num_resources = ARRAY_SIZE(kirkwood_ehci_resources),
  80. };
  81. void __init kirkwood_ehci_init(void)
  82. {
  83. platform_device_register(&kirkwood_ehci);
  84. }
  85. /*****************************************************************************
  86. * GE00
  87. ****************************************************************************/
  88. struct mv643xx_eth_shared_platform_data kirkwood_ge00_shared_data = {
  89. .t_clk = KIRKWOOD_TCLK,
  90. .dram = &kirkwood_mbus_dram_info,
  91. };
  92. static struct resource kirkwood_ge00_shared_resources[] = {
  93. {
  94. .name = "ge00 base",
  95. .start = GE00_PHYS_BASE + 0x2000,
  96. .end = GE00_PHYS_BASE + 0x3fff,
  97. .flags = IORESOURCE_MEM,
  98. },
  99. };
  100. static struct platform_device kirkwood_ge00_shared = {
  101. .name = MV643XX_ETH_SHARED_NAME,
  102. .id = 0,
  103. .dev = {
  104. .platform_data = &kirkwood_ge00_shared_data,
  105. },
  106. .num_resources = 1,
  107. .resource = kirkwood_ge00_shared_resources,
  108. };
  109. static struct resource kirkwood_ge00_resources[] = {
  110. {
  111. .name = "ge00 irq",
  112. .start = IRQ_KIRKWOOD_GE00_SUM,
  113. .end = IRQ_KIRKWOOD_GE00_SUM,
  114. .flags = IORESOURCE_IRQ,
  115. },
  116. };
  117. static struct platform_device kirkwood_ge00 = {
  118. .name = MV643XX_ETH_NAME,
  119. .id = 0,
  120. .num_resources = 1,
  121. .resource = kirkwood_ge00_resources,
  122. };
  123. void __init kirkwood_ge00_init(struct mv643xx_eth_platform_data *eth_data)
  124. {
  125. eth_data->shared = &kirkwood_ge00_shared;
  126. kirkwood_ge00.dev.platform_data = eth_data;
  127. platform_device_register(&kirkwood_ge00_shared);
  128. platform_device_register(&kirkwood_ge00);
  129. }
  130. /*****************************************************************************
  131. * SoC RTC
  132. ****************************************************************************/
  133. static struct resource kirkwood_rtc_resource = {
  134. .start = RTC_PHYS_BASE,
  135. .end = RTC_PHYS_BASE + SZ_16 - 1,
  136. .flags = IORESOURCE_MEM,
  137. };
  138. void __init kirkwood_rtc_init(void)
  139. {
  140. platform_device_register_simple("rtc-mv", -1, &kirkwood_rtc_resource, 1);
  141. }
  142. /*****************************************************************************
  143. * SATA
  144. ****************************************************************************/
  145. static struct resource kirkwood_sata_resources[] = {
  146. {
  147. .name = "sata base",
  148. .start = SATA_PHYS_BASE,
  149. .end = SATA_PHYS_BASE + 0x5000 - 1,
  150. .flags = IORESOURCE_MEM,
  151. }, {
  152. .name = "sata irq",
  153. .start = IRQ_KIRKWOOD_SATA,
  154. .end = IRQ_KIRKWOOD_SATA,
  155. .flags = IORESOURCE_IRQ,
  156. },
  157. };
  158. static struct platform_device kirkwood_sata = {
  159. .name = "sata_mv",
  160. .id = 0,
  161. .dev = {
  162. .coherent_dma_mask = 0xffffffff,
  163. },
  164. .num_resources = ARRAY_SIZE(kirkwood_sata_resources),
  165. .resource = kirkwood_sata_resources,
  166. };
  167. void __init kirkwood_sata_init(struct mv_sata_platform_data *sata_data)
  168. {
  169. sata_data->dram = &kirkwood_mbus_dram_info;
  170. kirkwood_sata.dev.platform_data = sata_data;
  171. platform_device_register(&kirkwood_sata);
  172. }
  173. /*****************************************************************************
  174. * SPI
  175. ****************************************************************************/
  176. static struct orion_spi_info kirkwood_spi_plat_data = {
  177. .tclk = KIRKWOOD_TCLK,
  178. };
  179. static struct resource kirkwood_spi_resources[] = {
  180. {
  181. .start = SPI_PHYS_BASE,
  182. .end = SPI_PHYS_BASE + SZ_512 - 1,
  183. .flags = IORESOURCE_MEM,
  184. },
  185. };
  186. static struct platform_device kirkwood_spi = {
  187. .name = "orion_spi",
  188. .id = 0,
  189. .resource = kirkwood_spi_resources,
  190. .dev = {
  191. .platform_data = &kirkwood_spi_plat_data,
  192. },
  193. .num_resources = ARRAY_SIZE(kirkwood_spi_resources),
  194. };
  195. void __init kirkwood_spi_init()
  196. {
  197. platform_device_register(&kirkwood_spi);
  198. }
  199. /*****************************************************************************
  200. * UART0
  201. ****************************************************************************/
  202. static struct plat_serial8250_port kirkwood_uart0_data[] = {
  203. {
  204. .mapbase = UART0_PHYS_BASE,
  205. .membase = (char *)UART0_VIRT_BASE,
  206. .irq = IRQ_KIRKWOOD_UART_0,
  207. .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
  208. .iotype = UPIO_MEM,
  209. .regshift = 2,
  210. .uartclk = KIRKWOOD_TCLK,
  211. }, {
  212. },
  213. };
  214. static struct resource kirkwood_uart0_resources[] = {
  215. {
  216. .start = UART0_PHYS_BASE,
  217. .end = UART0_PHYS_BASE + 0xff,
  218. .flags = IORESOURCE_MEM,
  219. }, {
  220. .start = IRQ_KIRKWOOD_UART_0,
  221. .end = IRQ_KIRKWOOD_UART_0,
  222. .flags = IORESOURCE_IRQ,
  223. },
  224. };
  225. static struct platform_device kirkwood_uart0 = {
  226. .name = "serial8250",
  227. .id = 0,
  228. .dev = {
  229. .platform_data = kirkwood_uart0_data,
  230. },
  231. .resource = kirkwood_uart0_resources,
  232. .num_resources = ARRAY_SIZE(kirkwood_uart0_resources),
  233. };
  234. void __init kirkwood_uart0_init(void)
  235. {
  236. platform_device_register(&kirkwood_uart0);
  237. }
  238. /*****************************************************************************
  239. * UART1
  240. ****************************************************************************/
  241. static struct plat_serial8250_port kirkwood_uart1_data[] = {
  242. {
  243. .mapbase = UART1_PHYS_BASE,
  244. .membase = (char *)UART1_VIRT_BASE,
  245. .irq = IRQ_KIRKWOOD_UART_1,
  246. .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
  247. .iotype = UPIO_MEM,
  248. .regshift = 2,
  249. .uartclk = KIRKWOOD_TCLK,
  250. }, {
  251. },
  252. };
  253. static struct resource kirkwood_uart1_resources[] = {
  254. {
  255. .start = UART1_PHYS_BASE,
  256. .end = UART1_PHYS_BASE + 0xff,
  257. .flags = IORESOURCE_MEM,
  258. }, {
  259. .start = IRQ_KIRKWOOD_UART_1,
  260. .end = IRQ_KIRKWOOD_UART_1,
  261. .flags = IORESOURCE_IRQ,
  262. },
  263. };
  264. static struct platform_device kirkwood_uart1 = {
  265. .name = "serial8250",
  266. .id = 1,
  267. .dev = {
  268. .platform_data = kirkwood_uart1_data,
  269. },
  270. .resource = kirkwood_uart1_resources,
  271. .num_resources = ARRAY_SIZE(kirkwood_uart1_resources),
  272. };
  273. void __init kirkwood_uart1_init(void)
  274. {
  275. platform_device_register(&kirkwood_uart1);
  276. }
  277. /*****************************************************************************
  278. * XOR
  279. ****************************************************************************/
  280. static struct mv_xor_platform_shared_data kirkwood_xor_shared_data = {
  281. .dram = &kirkwood_mbus_dram_info,
  282. };
  283. static u64 kirkwood_xor_dmamask = DMA_32BIT_MASK;
  284. /*****************************************************************************
  285. * XOR0
  286. ****************************************************************************/
  287. static struct resource kirkwood_xor0_shared_resources[] = {
  288. {
  289. .name = "xor 0 low",
  290. .start = XOR0_PHYS_BASE,
  291. .end = XOR0_PHYS_BASE + 0xff,
  292. .flags = IORESOURCE_MEM,
  293. }, {
  294. .name = "xor 0 high",
  295. .start = XOR0_HIGH_PHYS_BASE,
  296. .end = XOR0_HIGH_PHYS_BASE + 0xff,
  297. .flags = IORESOURCE_MEM,
  298. },
  299. };
  300. static struct platform_device kirkwood_xor0_shared = {
  301. .name = MV_XOR_SHARED_NAME,
  302. .id = 0,
  303. .dev = {
  304. .platform_data = &kirkwood_xor_shared_data,
  305. },
  306. .num_resources = ARRAY_SIZE(kirkwood_xor0_shared_resources),
  307. .resource = kirkwood_xor0_shared_resources,
  308. };
  309. static struct resource kirkwood_xor00_resources[] = {
  310. [0] = {
  311. .start = IRQ_KIRKWOOD_XOR_00,
  312. .end = IRQ_KIRKWOOD_XOR_00,
  313. .flags = IORESOURCE_IRQ,
  314. },
  315. };
  316. static struct mv_xor_platform_data kirkwood_xor00_data = {
  317. .shared = &kirkwood_xor0_shared,
  318. .hw_id = 0,
  319. .pool_size = PAGE_SIZE,
  320. };
  321. static struct platform_device kirkwood_xor00_channel = {
  322. .name = MV_XOR_NAME,
  323. .id = 0,
  324. .num_resources = ARRAY_SIZE(kirkwood_xor00_resources),
  325. .resource = kirkwood_xor00_resources,
  326. .dev = {
  327. .dma_mask = &kirkwood_xor_dmamask,
  328. .coherent_dma_mask = DMA_64BIT_MASK,
  329. .platform_data = (void *)&kirkwood_xor00_data,
  330. },
  331. };
  332. static struct resource kirkwood_xor01_resources[] = {
  333. [0] = {
  334. .start = IRQ_KIRKWOOD_XOR_01,
  335. .end = IRQ_KIRKWOOD_XOR_01,
  336. .flags = IORESOURCE_IRQ,
  337. },
  338. };
  339. static struct mv_xor_platform_data kirkwood_xor01_data = {
  340. .shared = &kirkwood_xor0_shared,
  341. .hw_id = 1,
  342. .pool_size = PAGE_SIZE,
  343. };
  344. static struct platform_device kirkwood_xor01_channel = {
  345. .name = MV_XOR_NAME,
  346. .id = 1,
  347. .num_resources = ARRAY_SIZE(kirkwood_xor01_resources),
  348. .resource = kirkwood_xor01_resources,
  349. .dev = {
  350. .dma_mask = &kirkwood_xor_dmamask,
  351. .coherent_dma_mask = DMA_64BIT_MASK,
  352. .platform_data = (void *)&kirkwood_xor01_data,
  353. },
  354. };
  355. void __init kirkwood_xor0_init(void)
  356. {
  357. platform_device_register(&kirkwood_xor0_shared);
  358. /*
  359. * two engines can't do memset simultaneously, this limitation
  360. * satisfied by removing memset support from one of the engines.
  361. */
  362. dma_cap_set(DMA_MEMCPY, kirkwood_xor00_data.cap_mask);
  363. dma_cap_set(DMA_XOR, kirkwood_xor00_data.cap_mask);
  364. platform_device_register(&kirkwood_xor00_channel);
  365. dma_cap_set(DMA_MEMCPY, kirkwood_xor01_data.cap_mask);
  366. dma_cap_set(DMA_MEMSET, kirkwood_xor01_data.cap_mask);
  367. dma_cap_set(DMA_XOR, kirkwood_xor01_data.cap_mask);
  368. platform_device_register(&kirkwood_xor01_channel);
  369. }
  370. /*****************************************************************************
  371. * XOR1
  372. ****************************************************************************/
  373. static struct resource kirkwood_xor1_shared_resources[] = {
  374. {
  375. .name = "xor 1 low",
  376. .start = XOR1_PHYS_BASE,
  377. .end = XOR1_PHYS_BASE + 0xff,
  378. .flags = IORESOURCE_MEM,
  379. }, {
  380. .name = "xor 1 high",
  381. .start = XOR1_HIGH_PHYS_BASE,
  382. .end = XOR1_HIGH_PHYS_BASE + 0xff,
  383. .flags = IORESOURCE_MEM,
  384. },
  385. };
  386. static struct platform_device kirkwood_xor1_shared = {
  387. .name = MV_XOR_SHARED_NAME,
  388. .id = 1,
  389. .dev = {
  390. .platform_data = &kirkwood_xor_shared_data,
  391. },
  392. .num_resources = ARRAY_SIZE(kirkwood_xor1_shared_resources),
  393. .resource = kirkwood_xor1_shared_resources,
  394. };
  395. static struct resource kirkwood_xor10_resources[] = {
  396. [0] = {
  397. .start = IRQ_KIRKWOOD_XOR_10,
  398. .end = IRQ_KIRKWOOD_XOR_10,
  399. .flags = IORESOURCE_IRQ,
  400. },
  401. };
  402. static struct mv_xor_platform_data kirkwood_xor10_data = {
  403. .shared = &kirkwood_xor1_shared,
  404. .hw_id = 0,
  405. .pool_size = PAGE_SIZE,
  406. };
  407. static struct platform_device kirkwood_xor10_channel = {
  408. .name = MV_XOR_NAME,
  409. .id = 2,
  410. .num_resources = ARRAY_SIZE(kirkwood_xor10_resources),
  411. .resource = kirkwood_xor10_resources,
  412. .dev = {
  413. .dma_mask = &kirkwood_xor_dmamask,
  414. .coherent_dma_mask = DMA_64BIT_MASK,
  415. .platform_data = (void *)&kirkwood_xor10_data,
  416. },
  417. };
  418. static struct resource kirkwood_xor11_resources[] = {
  419. [0] = {
  420. .start = IRQ_KIRKWOOD_XOR_11,
  421. .end = IRQ_KIRKWOOD_XOR_11,
  422. .flags = IORESOURCE_IRQ,
  423. },
  424. };
  425. static struct mv_xor_platform_data kirkwood_xor11_data = {
  426. .shared = &kirkwood_xor1_shared,
  427. .hw_id = 1,
  428. .pool_size = PAGE_SIZE,
  429. };
  430. static struct platform_device kirkwood_xor11_channel = {
  431. .name = MV_XOR_NAME,
  432. .id = 3,
  433. .num_resources = ARRAY_SIZE(kirkwood_xor11_resources),
  434. .resource = kirkwood_xor11_resources,
  435. .dev = {
  436. .dma_mask = &kirkwood_xor_dmamask,
  437. .coherent_dma_mask = DMA_64BIT_MASK,
  438. .platform_data = (void *)&kirkwood_xor11_data,
  439. },
  440. };
  441. void __init kirkwood_xor1_init(void)
  442. {
  443. platform_device_register(&kirkwood_xor1_shared);
  444. /*
  445. * two engines can't do memset simultaneously, this limitation
  446. * satisfied by removing memset support from one of the engines.
  447. */
  448. dma_cap_set(DMA_MEMCPY, kirkwood_xor10_data.cap_mask);
  449. dma_cap_set(DMA_XOR, kirkwood_xor10_data.cap_mask);
  450. platform_device_register(&kirkwood_xor10_channel);
  451. dma_cap_set(DMA_MEMCPY, kirkwood_xor11_data.cap_mask);
  452. dma_cap_set(DMA_MEMSET, kirkwood_xor11_data.cap_mask);
  453. dma_cap_set(DMA_XOR, kirkwood_xor11_data.cap_mask);
  454. platform_device_register(&kirkwood_xor11_channel);
  455. }
  456. /*****************************************************************************
  457. * Time handling
  458. ****************************************************************************/
  459. static void kirkwood_timer_init(void)
  460. {
  461. orion_time_init(IRQ_KIRKWOOD_BRIDGE, KIRKWOOD_TCLK);
  462. }
  463. struct sys_timer kirkwood_timer = {
  464. .init = kirkwood_timer_init,
  465. };
  466. /*****************************************************************************
  467. * General
  468. ****************************************************************************/
  469. static char * __init kirkwood_id(void)
  470. {
  471. switch (readl(DEVICE_ID) & 0x3) {
  472. case 0:
  473. return "88F6180";
  474. case 1:
  475. return "88F6192";
  476. case 2:
  477. return "88F6281";
  478. }
  479. return "unknown 88F6000 variant";
  480. }
  481. static int __init is_l2_writethrough(void)
  482. {
  483. return !!(readl(L2_CONFIG_REG) & L2_WRITETHROUGH);
  484. }
  485. void __init kirkwood_init(void)
  486. {
  487. printk(KERN_INFO "Kirkwood: %s, TCLK=%d.\n",
  488. kirkwood_id(), KIRKWOOD_TCLK);
  489. kirkwood_setup_cpu_mbus();
  490. #ifdef CONFIG_CACHE_FEROCEON_L2
  491. feroceon_l2_init(is_l2_writethrough());
  492. #endif
  493. }