uniphier_usb.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183
  1. /*
  2. * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved.
  3. *
  4. * SPDX-License-Identifier: BSD-3-Clause
  5. */
  6. #include <assert.h>
  7. #include <stdint.h>
  8. #include <platform_def.h>
  9. #include <arch_helpers.h>
  10. #include <drivers/io/io_block.h>
  11. #include <lib/mmio.h>
  12. #include <lib/utils_def.h>
  13. #include "uniphier.h"
  14. #define UNIPHIER_LD11_USB_DESC_BASE 0x30010000
  15. #define UNIPHIER_LD20_USB_DESC_BASE 0x30014000
  16. #define UNIPHIER_PXS3_USB_DESC_BASE 0x30014000
  17. #define UNIPHIER_SRB_OCM_CONT 0x61200000
  18. struct uniphier_ld11_trans_op {
  19. uint8_t __pad[48];
  20. };
  21. struct uniphier_ld11_op {
  22. uint8_t __pad[56];
  23. struct uniphier_ld11_trans_op *trans_op;
  24. void *__pad2;
  25. void *dev_desc;
  26. };
  27. struct uniphier_ld20_trans_op {
  28. uint8_t __pad[40];
  29. };
  30. struct uniphier_ld20_op {
  31. uint8_t __pad[192];
  32. struct uniphier_ld20_trans_op *trans_op;
  33. void *__pad2;
  34. void *dev_desc;
  35. };
  36. struct uniphier_pxs3_op {
  37. uint8_t __pad[184];
  38. struct uniphier_ld20_trans_op *trans_op;
  39. void *__pad2;
  40. void *dev_desc;
  41. };
  42. static int (*__uniphier_usb_read)(int lba, uintptr_t buf, size_t size);
  43. static void uniphier_ld11_usb_init(void)
  44. {
  45. struct uniphier_ld11_op *op = (void *)UNIPHIER_LD11_USB_DESC_BASE;
  46. op->trans_op = (void *)(op + 1);
  47. op->dev_desc = op->trans_op + 1;
  48. }
  49. static int uniphier_ld11_usb_read(int lba, uintptr_t buf, size_t size)
  50. {
  51. static int (*rom_usb_read)(uintptr_t desc, unsigned int lba,
  52. unsigned int size, uintptr_t buf);
  53. uintptr_t func_addr;
  54. func_addr = uniphier_get_soc_revision() == 1 ? 0x3880 : 0x3958;
  55. rom_usb_read = (__typeof(rom_usb_read))func_addr;
  56. return rom_usb_read(UNIPHIER_LD11_USB_DESC_BASE, lba, size, buf);
  57. }
  58. static void uniphier_ld20_usb_init(void)
  59. {
  60. struct uniphier_ld20_op *op = (void *)UNIPHIER_LD20_USB_DESC_BASE;
  61. op->trans_op = (void *)(op + 1);
  62. op->dev_desc = op->trans_op + 1;
  63. }
  64. static int uniphier_ld20_usb_read(int lba, uintptr_t buf, size_t size)
  65. {
  66. static int (*rom_usb_read)(uintptr_t desc, unsigned int lba,
  67. unsigned int size, uintptr_t buf);
  68. int ret;
  69. rom_usb_read = (__typeof(rom_usb_read))0x37f0;
  70. mmio_write_32(UNIPHIER_SRB_OCM_CONT, 0x1ff);
  71. /* ROM-API - return 1 on success, 0 on error */
  72. ret = rom_usb_read(UNIPHIER_LD20_USB_DESC_BASE, lba, size, buf);
  73. mmio_write_32(UNIPHIER_SRB_OCM_CONT, 0);
  74. return ret ? 0 : -1;
  75. }
  76. static void uniphier_pxs3_usb_init(void)
  77. {
  78. struct uniphier_pxs3_op *op = (void *)UNIPHIER_PXS3_USB_DESC_BASE;
  79. op->trans_op = (void *)(op + 1);
  80. op->dev_desc = op->trans_op + 1;
  81. }
  82. static int uniphier_pxs3_usb_read(int lba, uintptr_t buf, size_t size)
  83. {
  84. static int (*rom_usb_read)(uintptr_t desc, unsigned int lba,
  85. unsigned int size, uintptr_t buf);
  86. int ret;
  87. rom_usb_read = (__typeof(rom_usb_read))0x39e8;
  88. /* ROM-API - return 1 on success, 0 on error */
  89. ret = rom_usb_read(UNIPHIER_PXS3_USB_DESC_BASE, lba, size, buf);
  90. return ret ? 0 : -1;
  91. }
  92. struct uniphier_usb_rom_param {
  93. void (*init)(void);
  94. int (*read)(int lba, uintptr_t buf, size_t size);
  95. };
  96. static const struct uniphier_usb_rom_param uniphier_usb_rom_params[] = {
  97. [UNIPHIER_SOC_LD11] = {
  98. .init = uniphier_ld11_usb_init,
  99. .read = uniphier_ld11_usb_read,
  100. },
  101. [UNIPHIER_SOC_LD20] = {
  102. .init = uniphier_ld20_usb_init,
  103. .read = uniphier_ld20_usb_read,
  104. },
  105. [UNIPHIER_SOC_PXS3] = {
  106. .init = uniphier_pxs3_usb_init,
  107. .read = uniphier_pxs3_usb_read,
  108. },
  109. };
  110. static size_t uniphier_usb_read(int lba, uintptr_t buf, size_t size)
  111. {
  112. int ret;
  113. inv_dcache_range(buf, size);
  114. ret = __uniphier_usb_read(lba, buf, size);
  115. inv_dcache_range(buf, size);
  116. return ret ? 0 : size;
  117. }
  118. static struct io_block_dev_spec uniphier_usb_dev_spec = {
  119. .ops = {
  120. .read = uniphier_usb_read,
  121. },
  122. .block_size = 512,
  123. };
  124. int uniphier_usb_init(unsigned int soc,
  125. struct io_block_dev_spec **block_dev_spec)
  126. {
  127. const struct uniphier_usb_rom_param *param;
  128. assert(soc < ARRAY_SIZE(uniphier_usb_rom_params));
  129. param = &uniphier_usb_rom_params[soc];
  130. if (param->init)
  131. param->init();
  132. __uniphier_usb_read = param->read;
  133. *block_dev_spec = &uniphier_usb_dev_spec;
  134. return 0;
  135. }