setup.c 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788
  1. /*
  2. * Alchemy/AMD/RMI DB1200 board setup.
  3. *
  4. * Licensed under the terms outlined in the file COPYING in the root of
  5. * this source archive.
  6. */
  7. #include <linux/init.h>
  8. #include <linux/interrupt.h>
  9. #include <linux/io.h>
  10. #include <linux/kernel.h>
  11. #include <asm/mach-au1x00/au1000.h>
  12. #include <asm/mach-db1x00/bcsr.h>
  13. #include <asm/mach-db1x00/db1200.h>
  14. const char *get_system_type(void)
  15. {
  16. return "Alchemy Db1200";
  17. }
  18. void __init board_setup(void)
  19. {
  20. unsigned long freq0, clksrc, div, pfc;
  21. unsigned short whoami;
  22. /* Set Config[OD] (disable overlapping bus transaction):
  23. * This gets rid of a _lot_ of spurious interrupts (especially
  24. * wrt. IDE); but incurs ~10% performance hit in some
  25. * cpu-bound applications.
  26. */
  27. set_c0_config(1 << 19);
  28. bcsr_init(DB1200_BCSR_PHYS_ADDR,
  29. DB1200_BCSR_PHYS_ADDR + DB1200_BCSR_HEXLED_OFS);
  30. whoami = bcsr_read(BCSR_WHOAMI);
  31. printk(KERN_INFO "Alchemy/AMD/RMI DB1200 Board, CPLD Rev %d"
  32. " Board-ID %d Daughtercard ID %d\n",
  33. (whoami >> 4) & 0xf, (whoami >> 8) & 0xf, whoami & 0xf);
  34. /* SMBus/SPI on PSC0, Audio on PSC1 */
  35. pfc = __raw_readl((void __iomem *)SYS_PINFUNC);
  36. pfc &= ~(SYS_PINFUNC_P0A | SYS_PINFUNC_P0B);
  37. pfc &= ~(SYS_PINFUNC_P1A | SYS_PINFUNC_P1B | SYS_PINFUNC_FS3);
  38. pfc |= SYS_PINFUNC_P1C; /* SPI is configured later */
  39. __raw_writel(pfc, (void __iomem *)SYS_PINFUNC);
  40. wmb();
  41. /* Clock configurations: PSC0: ~50MHz via Clkgen0, derived from
  42. * CPU clock; all other clock generators off/unused.
  43. */
  44. div = (get_au1x00_speed() + 25000000) / 50000000;
  45. if (div & 1)
  46. div++;
  47. div = ((div >> 1) - 1) & 0xff;
  48. freq0 = div << SYS_FC_FRDIV0_BIT;
  49. __raw_writel(freq0, (void __iomem *)SYS_FREQCTRL0);
  50. wmb();
  51. freq0 |= SYS_FC_FE0; /* enable F0 */
  52. __raw_writel(freq0, (void __iomem *)SYS_FREQCTRL0);
  53. wmb();
  54. /* psc0_intclk comes 1:1 from F0 */
  55. clksrc = SYS_CS_MUX_FQ0 << SYS_CS_ME0_BIT;
  56. __raw_writel(clksrc, (void __iomem *)SYS_CLKSRC);
  57. wmb();
  58. }
  59. static int __init db1200_arch_init(void)
  60. {
  61. /* GPIO7 is low-level triggered CPLD cascade */
  62. irq_set_irq_type(AU1200_GPIO7_INT, IRQF_TRIGGER_LOW);
  63. bcsr_init_irq(DB1200_INT_BEGIN, DB1200_INT_END, AU1200_GPIO7_INT);
  64. /* insert/eject pairs: one of both is always screaming. To avoid
  65. * issues they must not be automatically enabled when initially
  66. * requested.
  67. */
  68. irq_set_status_flags(DB1200_SD0_INSERT_INT, IRQ_NOAUTOEN);
  69. irq_set_status_flags(DB1200_SD0_EJECT_INT, IRQ_NOAUTOEN);
  70. irq_set_status_flags(DB1200_PC0_INSERT_INT, IRQ_NOAUTOEN);
  71. irq_set_status_flags(DB1200_PC0_EJECT_INT, IRQ_NOAUTOEN);
  72. irq_set_status_flags(DB1200_PC1_INSERT_INT, IRQ_NOAUTOEN);
  73. irq_set_status_flags(DB1200_PC1_EJECT_INT, IRQ_NOAUTOEN);
  74. return 0;
  75. }
  76. arch_initcall(db1200_arch_init);