keystone.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148
  1. // SPDX-License-Identifier: GPL-2.0-only
  2. /*
  3. * Keystone2 based boards and SOC related code.
  4. *
  5. * Copyright 2013 Texas Instruments, Inc.
  6. * Cyril Chemparathy <cyril@ti.com>
  7. * Santosh Shilimkar <santosh.shillimkar@ti.com>
  8. */
  9. #include <linux/io.h>
  10. #include <linux/dma-map-ops.h>
  11. #include <linux/init.h>
  12. #include <linux/pm_runtime.h>
  13. #include <linux/pm_clock.h>
  14. #include <linux/memblock.h>
  15. #include <linux/of.h>
  16. #include <linux/platform_device.h>
  17. #include <asm/setup.h>
  18. #include <asm/mach/map.h>
  19. #include <asm/mach/arch.h>
  20. #include <asm/mach/time.h>
  21. #include <asm/page.h>
  22. #define KEYSTONE_LOW_PHYS_START 0x80000000ULL
  23. #define KEYSTONE_LOW_PHYS_SIZE 0x80000000ULL /* 2G */
  24. #define KEYSTONE_LOW_PHYS_END (KEYSTONE_LOW_PHYS_START + \
  25. KEYSTONE_LOW_PHYS_SIZE - 1)
  26. #define KEYSTONE_HIGH_PHYS_START 0x800000000ULL
  27. #define KEYSTONE_HIGH_PHYS_SIZE 0x400000000ULL /* 16G */
  28. #define KEYSTONE_HIGH_PHYS_END (KEYSTONE_HIGH_PHYS_START + \
  29. KEYSTONE_HIGH_PHYS_SIZE - 1)
  30. static struct dev_pm_domain keystone_pm_domain = {
  31. .ops = {
  32. USE_PM_CLK_RUNTIME_OPS
  33. USE_PLATFORM_PM_SLEEP_OPS
  34. },
  35. };
  36. static struct pm_clk_notifier_block platform_domain_notifier = {
  37. .pm_domain = &keystone_pm_domain,
  38. .con_ids = { NULL },
  39. };
  40. static const struct of_device_id of_keystone_table[] = {
  41. {.compatible = "ti,k2hk"},
  42. {.compatible = "ti,k2e"},
  43. {.compatible = "ti,k2l"},
  44. { /* end of list */ },
  45. };
  46. static int __init keystone_pm_runtime_init(void)
  47. {
  48. struct device_node *np;
  49. np = of_find_matching_node(NULL, of_keystone_table);
  50. if (!np)
  51. return 0;
  52. pm_clk_add_notifier(&platform_bus_type, &platform_domain_notifier);
  53. return 0;
  54. }
  55. #ifdef CONFIG_ARM_LPAE
  56. static int keystone_platform_notifier(struct notifier_block *nb,
  57. unsigned long event, void *data)
  58. {
  59. struct device *dev = data;
  60. if (event != BUS_NOTIFY_ADD_DEVICE)
  61. return NOTIFY_DONE;
  62. if (!dev)
  63. return NOTIFY_BAD;
  64. if (!dev->of_node) {
  65. int ret = dma_direct_set_offset(dev, KEYSTONE_HIGH_PHYS_START,
  66. KEYSTONE_LOW_PHYS_START,
  67. KEYSTONE_HIGH_PHYS_SIZE);
  68. dev_err(dev, "set dma_offset%08llx%s\n",
  69. KEYSTONE_HIGH_PHYS_START - KEYSTONE_LOW_PHYS_START,
  70. ret ? " failed" : "");
  71. }
  72. return NOTIFY_OK;
  73. }
  74. static struct notifier_block platform_nb = {
  75. .notifier_call = keystone_platform_notifier,
  76. };
  77. #endif /* CONFIG_ARM_LPAE */
  78. static void __init keystone_init(void)
  79. {
  80. #ifdef CONFIG_ARM_LPAE
  81. if (PHYS_OFFSET >= KEYSTONE_HIGH_PHYS_START)
  82. bus_register_notifier(&platform_bus_type, &platform_nb);
  83. #endif
  84. keystone_pm_runtime_init();
  85. }
  86. static long long __init keystone_pv_fixup(void)
  87. {
  88. long long offset;
  89. u64 mem_start, mem_end;
  90. mem_start = memblock_start_of_DRAM();
  91. mem_end = memblock_end_of_DRAM();
  92. /* nothing to do if we are running out of the <32-bit space */
  93. if (mem_start >= KEYSTONE_LOW_PHYS_START &&
  94. mem_end <= KEYSTONE_LOW_PHYS_END)
  95. return 0;
  96. if (mem_start < KEYSTONE_HIGH_PHYS_START ||
  97. mem_end > KEYSTONE_HIGH_PHYS_END) {
  98. pr_crit("Invalid address space for memory (%08llx-%08llx)\n",
  99. mem_start, mem_end);
  100. return 0;
  101. }
  102. offset = KEYSTONE_HIGH_PHYS_START - KEYSTONE_LOW_PHYS_START;
  103. /* Populate the arch idmap hook */
  104. arch_phys_to_idmap_offset = -offset;
  105. return offset;
  106. }
  107. static const char *const keystone_match[] __initconst = {
  108. "ti,k2hk",
  109. "ti,k2e",
  110. "ti,k2l",
  111. "ti,k2g",
  112. "ti,keystone",
  113. NULL,
  114. };
  115. DT_MACHINE_START(KEYSTONE, "Keystone")
  116. #if defined(CONFIG_ZONE_DMA) && defined(CONFIG_ARM_LPAE)
  117. .dma_zone_size = SZ_2G,
  118. #endif
  119. .init_machine = keystone_init,
  120. .dt_compat = keystone_match,
  121. .pv_fixup = keystone_pv_fixup,
  122. MACHINE_END