drv_i2c.c 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. /*
  2. * Copyright (c) 2022 hpmicro
  3. *
  4. * SPDX-License-Identifier: BSD-3-Clause
  5. *
  6. */
  7. #include <rtthread.h>
  8. #include <rtdevice.h>
  9. #include <rtdbg.h>
  10. #ifdef BSP_USING_I2C
  11. #include "drv_i2c.h"
  12. #include "hpm_i2c_drv.h"
  13. #include "board.h"
  14. #ifdef RT_USING_I2C
  15. struct hpm_i2c
  16. {
  17. struct rt_i2c_bus_device bus;
  18. I2C_Type *base;
  19. clock_name_t clk_name;
  20. char *bus_name;
  21. };
  22. static struct hpm_i2c hpm_i2cs[] =
  23. {
  24. #if defined(BSP_USING_I2C0)
  25. {
  26. .base = HPM_I2C0,
  27. .bus_name = "i2c0",
  28. .clk_name = clock_i2c0,
  29. },
  30. #endif
  31. #if defined(BSP_USING_I2C1)
  32. {
  33. .base = HPM_I2C1,
  34. .bus_name = "i2c1",
  35. .clk_name = clock_i2c1,
  36. },
  37. #endif
  38. #if defined(BSP_USING_I2C2)
  39. {
  40. .base = HPM_I2C1,
  41. .bus_name = "i2c1",
  42. .clk_name = clock_i2c1,
  43. },
  44. #endif
  45. #if defined(BSP_USING_I2C3)
  46. {
  47. .base = HPM_I2C1,
  48. .bus_name = "i2c1",
  49. .clk_name = clock_i2c1,
  50. },
  51. #endif
  52. };
  53. static rt_ssize_t hpm_i2c_master_transfer(struct rt_i2c_bus_device *bus, struct rt_i2c_msg msgs[], rt_uint32_t num);
  54. struct rt_i2c_bus_device_ops hpm_i2c_ops =
  55. {
  56. hpm_i2c_master_transfer,
  57. RT_NULL,
  58. RT_NULL
  59. };
  60. static rt_ssize_t hpm_i2c_master_transfer(struct rt_i2c_bus_device *bus, struct rt_i2c_msg msgs[], rt_uint32_t num)
  61. {
  62. RT_ASSERT(bus != RT_NULL);
  63. RT_ASSERT(msgs != RT_NULL);
  64. struct rt_i2c_msg *msg;
  65. struct hpm_i2c *i2c_info = (struct hpm_i2c *)bus;
  66. hpm_stat_t i2c_stat = status_success;
  67. rt_err_t ret = -RT_ERROR;
  68. rt_uint32_t i;
  69. for (i = 0; i < num; i++)
  70. {
  71. msg = &msgs[i];
  72. if (msg->flags & RT_I2C_ADDR_10BIT)
  73. {
  74. i2c_enable_10bit_address_mode(i2c_info->base, true);
  75. }
  76. else
  77. {
  78. i2c_enable_10bit_address_mode(i2c_info->base, false);
  79. }
  80. if (msg->flags & RT_I2C_RD)
  81. {
  82. i2c_stat = i2c_master_read(i2c_info->base, msg->addr, msg->buf, msg->len);
  83. }
  84. else
  85. {
  86. i2c_stat = i2c_master_write(i2c_info->base, msg->addr, msg->buf, msg->len);
  87. }
  88. if (i2c_stat != status_success)
  89. {
  90. break;
  91. }
  92. }
  93. if (i2c_stat != status_success)
  94. {
  95. return ret;
  96. }
  97. ret = i;
  98. return ret;
  99. }
  100. int rt_hw_i2c_init(void)
  101. {
  102. rt_err_t ret = RT_EOK;
  103. hpm_stat_t stat;
  104. i2c_config_t config;
  105. rt_uint32_t freq;
  106. for (uint32_t i = 0; i < sizeof(hpm_i2cs) / sizeof(hpm_i2cs[0]); i++) {
  107. init_i2c_pins(hpm_i2cs[i].base);
  108. clock_add_to_group(hpm_i2cs[i].clk_name, 0);
  109. clock_set_source_divider(hpm_i2cs[i].clk_name, clk_src_osc24m, 1U);
  110. config.i2c_mode = i2c_mode_normal;
  111. config.is_10bit_addressing = false;
  112. freq = clock_get_frequency(hpm_i2cs[i].clk_name);
  113. stat = i2c_init_master(hpm_i2cs[i].base, freq, &config);
  114. if (stat != status_success) {
  115. LOG_E("rt i2c device %s init failed", hpm_i2cs[i].bus_name);
  116. }
  117. hpm_i2cs[i].bus.ops = &hpm_i2c_ops;
  118. ret = rt_i2c_bus_device_register(&hpm_i2cs[i].bus, hpm_i2cs[i].bus_name);
  119. if (ret != RT_EOK) {
  120. LOG_E("rt i2c device %s register failed, status=%d\n", hpm_i2cs[i].bus_name, ret);
  121. }
  122. }
  123. return ret;
  124. }
  125. INIT_DEVICE_EXPORT(rt_hw_i2c_init);
  126. #endif /* RT_USING_I2C */
  127. #endif /*BSP_USING_I2C*/