platform.c 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. /*
  2. * Copyright 2011, Netlogic Microsystems.
  3. * Copyright 2004, Matt Porter <mporter@kernel.crashing.org>
  4. *
  5. * This file is licensed under the terms of the GNU General Public
  6. * License version 2. This program is licensed "as is" without any
  7. * warranty of any kind, whether express or implied.
  8. */
  9. #include <linux/device.h>
  10. #include <linux/platform_device.h>
  11. #include <linux/kernel.h>
  12. #include <linux/init.h>
  13. #include <linux/resource.h>
  14. #include <linux/serial_8250.h>
  15. #include <linux/serial_reg.h>
  16. #include <asm/netlogic/haldefs.h>
  17. #include <asm/netlogic/xlr/iomap.h>
  18. #include <asm/netlogic/xlr/pic.h>
  19. #include <asm/netlogic/xlr/xlr.h>
  20. unsigned int nlm_xlr_uart_in(struct uart_port *p, int offset)
  21. {
  22. uint64_t uartbase;
  23. unsigned int value;
  24. /* sign extend to 64 bits, if needed */
  25. uartbase = (uint64_t)(long)p->membase;
  26. value = nlm_read_reg(uartbase, offset);
  27. /* See XLR/XLS errata */
  28. if (offset == UART_MSR)
  29. value ^= 0xF0;
  30. else if (offset == UART_MCR)
  31. value ^= 0x3;
  32. return value;
  33. }
  34. void nlm_xlr_uart_out(struct uart_port *p, int offset, int value)
  35. {
  36. uint64_t uartbase;
  37. /* sign extend to 64 bits, if needed */
  38. uartbase = (uint64_t)(long)p->membase;
  39. /* See XLR/XLS errata */
  40. if (offset == UART_MSR)
  41. value ^= 0xF0;
  42. else if (offset == UART_MCR)
  43. value ^= 0x3;
  44. nlm_write_reg(uartbase, offset, value);
  45. }
  46. #define PORT(_irq) \
  47. { \
  48. .irq = _irq, \
  49. .regshift = 2, \
  50. .iotype = UPIO_MEM32, \
  51. .flags = (UPF_SKIP_TEST | \
  52. UPF_FIXED_TYPE | UPF_BOOT_AUTOCONF),\
  53. .uartclk = PIC_CLKS_PER_SEC, \
  54. .type = PORT_16550A, \
  55. .serial_in = nlm_xlr_uart_in, \
  56. .serial_out = nlm_xlr_uart_out, \
  57. }
  58. static struct plat_serial8250_port xlr_uart_data[] = {
  59. PORT(PIC_UART_0_IRQ),
  60. PORT(PIC_UART_1_IRQ),
  61. {},
  62. };
  63. static struct platform_device uart_device = {
  64. .name = "serial8250",
  65. .id = PLAT8250_DEV_PLATFORM,
  66. .dev = {
  67. .platform_data = xlr_uart_data,
  68. },
  69. };
  70. static int __init nlm_uart_init(void)
  71. {
  72. unsigned long uartbase;
  73. uartbase = (unsigned long)nlm_mmio_base(NETLOGIC_IO_UART_0_OFFSET);
  74. xlr_uart_data[0].membase = (void __iomem *)uartbase;
  75. xlr_uart_data[0].mapbase = CPHYSADDR(uartbase);
  76. uartbase = (unsigned long)nlm_mmio_base(NETLOGIC_IO_UART_1_OFFSET);
  77. xlr_uart_data[1].membase = (void __iomem *)uartbase;
  78. xlr_uart_data[1].mapbase = CPHYSADDR(uartbase);
  79. return platform_device_register(&uart_device);
  80. }
  81. arch_initcall(nlm_uart_init);