8#include "ch32_gpio.hpp"
12CH32I2C* CH32I2C::map_[CH32_I2C_NUMBER] = {
nullptr};
17constexpr uint32_t CH32_I2C_ERROR_FLAGS =
18 ((I2C_FLAG_BERR & 0xFFFFu) | (I2C_FLAG_ARLO & 0xFFFFu) | (I2C_FLAG_AF & 0xFFFFu) |
19 (I2C_FLAG_OVR & 0xFFFFu) | (I2C_FLAG_PECERR & 0xFFFFu) |
20 (I2C_FLAG_TIMEOUT & 0xFFFFu) | (I2C_FLAG_SMBALERT & 0xFFFFu));
24static inline void ch32_i2c_enable_clocks(ch32_i2c_id_t
id)
26 RCC_APB1PeriphClockCmd(CH32_I2C_RCC_PERIPH_MAP[
id], ENABLE);
27 RCC_AHBPeriphClockCmd(CH32_I2C_RCC_PERIPH_MAP_DMA[
id], ENABLE);
31 uint16_t scl_pin, GPIO_TypeDef* sda_port, uint16_t sda_pin,
32 uint32_t pin_remap, uint32_t dma_enable_min_size,
33 uint32_t default_clock_hz,
bool ten_bit_addr)
35 instance_(ch32_i2c_get_instance_id(id)),
36 dma_rx_channel_(CH32_I2C_RX_DMA_CHANNEL_MAP[id]),
37 dma_tx_channel_(CH32_I2C_TX_DMA_CHANNEL_MAP[id]),
39 dma_enable_min_size_(dma_enable_min_size),
45 ten_bit_addr_(ten_bit_addr)
47 ASSERT(instance_ !=
nullptr);
48 ASSERT(dma_buff_.
addr_ !=
nullptr && dma_buff_.
size_ > 0);
53 ch32_i2c_enable_clocks(id_);
57 GPIO_InitTypeDef gpio = {};
58 gpio.GPIO_Speed = GPIO_Speed_50MHz;
59 gpio.GPIO_Mode = GPIO_Mode_AF_OD;
61 RCC_APB2PeriphClockCmd(ch32_get_gpio_periph(scl_port_), ENABLE);
62 RCC_APB2PeriphClockCmd(ch32_get_gpio_periph(sda_port_), ENABLE);
64 GPIO_SetBits(scl_port_, scl_pin_);
65 GPIO_SetBits(sda_port_, sda_pin_);
67 gpio.GPIO_Pin = scl_pin_;
68 GPIO_Init(scl_port_, &gpio);
70 gpio.GPIO_Pin = sda_pin_;
71 GPIO_Init(sda_port_, &gpio);
75 RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO, ENABLE);
76 GPIO_PinRemapConfig(pin_remap, ENABLE);
84 ch32_dma_callback_t cb = [](
void* arg)
86 ch32_dma_register_callback(ch32_dma_get_id(dma_rx_channel_), cb,
this);
88 DMA_InitTypeDef di = {};
89 DMA_DeInit(dma_rx_channel_);
90 di.DMA_PeripheralBaseAddr = (uint32_t)&instance_->DATAR;
91 di.DMA_MemoryBaseAddr = (uint32_t)dma_buff_.
addr_;
92 di.DMA_DIR = DMA_DIR_PeripheralSRC;
93 di.DMA_BufferSize = 0;
94 di.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
95 di.DMA_MemoryInc = DMA_MemoryInc_Enable;
96 di.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
97 di.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
98 di.DMA_Mode = DMA_Mode_Normal;
99 di.DMA_Priority = DMA_Priority_High;
100 di.DMA_M2M = DMA_M2M_Disable;
101 DMA_Init(dma_rx_channel_, &di);
102 DMA_ITConfig(dma_rx_channel_, DMA_IT_TC, ENABLE);
103 NVIC_EnableIRQ(CH32_DMA_IRQ_MAP[ch32_dma_get_id(dma_rx_channel_)]);
108 ch32_dma_callback_t cb = [](
void* arg)
109 {
reinterpret_cast<CH32I2C*
>(arg)->TxDmaIRQHandler(); };
110 ch32_dma_register_callback(ch32_dma_get_id(dma_tx_channel_), cb,
this);
112 DMA_InitTypeDef di = {};
113 DMA_DeInit(dma_tx_channel_);
114 di.DMA_PeripheralBaseAddr = (uint32_t)&instance_->DATAR;
115 di.DMA_MemoryBaseAddr = (uint32_t)dma_buff_.
addr_;
116 di.DMA_DIR = DMA_DIR_PeripheralDST;
117 di.DMA_BufferSize = 0;
118 di.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
119 di.DMA_MemoryInc = DMA_MemoryInc_Enable;
120 di.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
121 di.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
122 di.DMA_Mode = DMA_Mode_Normal;
123 di.DMA_Priority = DMA_Priority_VeryHigh;
124 di.DMA_M2M = DMA_M2M_Disable;
125 DMA_Init(dma_tx_channel_, &di);
126 DMA_ITConfig(dma_tx_channel_, DMA_IT_TC, ENABLE);
127 NVIC_EnableIRQ(CH32_DMA_IRQ_MAP[ch32_dma_get_id(dma_tx_channel_)]);
132 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
133 NVIC_EnableIRQ(CH32_I2C_ER_IRQ_MAP[id_]);
144 I2C_Cmd(instance_, DISABLE);
145 I2C_DeInit(instance_);
147 I2C_InitTypeDef init = {};
149 init.I2C_Mode = I2C_Mode_I2C;
150 init.I2C_DutyCycle = I2C_DutyCycle_2;
151 init.I2C_OwnAddress1 = 0;
152 init.I2C_Ack = I2C_Ack_Enable;
153 init.I2C_AcknowledgedAddress =
154 ten_bit_addr_ ? I2C_AcknowledgedAddress_10bit : I2C_AcknowledgedAddress_7bit;
156 I2C_Init(instance_, &init);
157 I2C_Cmd(instance_, ENABLE);
160 I2C_AcknowledgeConfig(instance_, ENABLE);
161 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
166bool CH32I2C::WaitEvent(uint32_t evt, uint32_t timeout_us)
171 if ((instance_->STAR1 & CH32_I2C_ERROR_FLAGS) != 0u)
175 if (I2C_CheckEvent(instance_, evt) == READY)
183bool CH32I2C::WaitFlag(uint32_t flag, FlagStatus st, uint32_t timeout_us)
188 if ((flag != I2C_FLAG_BUSY) && ((instance_->STAR1 & CH32_I2C_ERROR_FLAGS) != 0u))
192 if (I2C_GetFlagStatus(instance_, flag) == st)
200ErrorCode CH32I2C::WaitEventOrRecover(uint32_t evt, uint32_t timeout_us)
202 if (WaitEvent(evt, timeout_us))
206 RecoverAfterImmediateFailure();
210ErrorCode CH32I2C::WaitFlagOrRecover(uint32_t flag, FlagStatus st, uint32_t timeout_us)
212 if (WaitFlag(flag, st, timeout_us))
216 RecoverAfterImmediateFailure();
220void CH32I2C::ClearAddrFlag()
222 volatile uint16_t tmp1 = instance_->STAR1;
223 volatile uint16_t tmp2 = instance_->STAR2;
228ErrorCode CH32I2C::MasterStartAndAddress10Bit(uint16_t addr10, uint8_t final_dir)
230 addr10 = Addr10Clamp(addr10);
233 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BUSY, RESET); ec !=
ErrorCode::OK)
239 I2C_GenerateSTART(instance_, ENABLE);
240 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_MODE_SELECT); ec !=
ErrorCode::OK)
247 const uint8_t HEADER =
static_cast<uint8_t
>(0xF0 | ((addr10 >> 7) & 0x06));
248 I2C_Send7bitAddress(instance_, HEADER, I2C_Direction_Transmitter);
251 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_MODE_ADDRESS10); ec !=
ErrorCode::OK)
257 I2C_SendData(instance_,
static_cast<uint8_t
>(addr10 & 0xFF));
260 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED);
267 if (final_dir == I2C_Direction_Transmitter)
273 I2C_GenerateSTART(instance_, ENABLE);
274 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_MODE_SELECT); ec !=
ErrorCode::OK)
279 I2C_Send7bitAddress(instance_, HEADER, I2C_Direction_Receiver);
280 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED);
290ErrorCode CH32I2C::MasterStartAndAddress(uint16_t slave_addr, uint8_t dir)
295 const uint8_t ADDR8 = Addr7ToAddr8(slave_addr);
297 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BUSY, RESET); ec !=
ErrorCode::OK)
302 I2C_GenerateSTART(instance_, ENABLE);
303 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_MODE_SELECT); ec !=
ErrorCode::OK)
308 I2C_Send7bitAddress(instance_, ADDR8, dir);
310 if (dir == I2C_Direction_Transmitter)
312 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED);
320 if (
auto ec = WaitEventOrRecover(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED);
332 return MasterStartAndAddress10Bit(slave_addr, dir);
335ErrorCode CH32I2C::SendMemAddr(uint16_t mem_addr, MemAddrLength len)
337 if (len == MemAddrLength::BYTE_16)
339 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_TXE, SET); ec !=
ErrorCode::OK)
343 I2C_SendData(instance_,
static_cast<uint8_t
>((mem_addr >> 8) & 0xFF));
344 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_TXE, SET); ec !=
ErrorCode::OK)
348 I2C_SendData(instance_,
static_cast<uint8_t
>(mem_addr & 0xFF));
352 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_TXE, SET); ec !=
ErrorCode::OK)
356 I2C_SendData(instance_,
static_cast<uint8_t
>(mem_addr & 0xFF));
359 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BTF, SET); ec !=
ErrorCode::OK)
366ErrorCode CH32I2C::PollingWriteBytes(
const uint8_t* data, uint32_t len)
368 for (uint32_t i = 0; i < len; ++i)
370 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_TXE, SET); ec !=
ErrorCode::OK)
374 I2C_SendData(instance_, data[i]);
376 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BTF, SET); ec !=
ErrorCode::OK)
383ErrorCode CH32I2C::PollingReadBytes(uint8_t* data, uint32_t len)
393 I2C_AcknowledgeConfig(instance_, DISABLE);
394 I2C_GenerateSTOP(instance_, ENABLE);
395 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_RXNE, SET); ec !=
ErrorCode::OK)
399 data[0] = I2C_ReceiveData(instance_);
400 I2C_AcknowledgeConfig(instance_, ENABLE);
407 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Next);
408 I2C_AcknowledgeConfig(instance_, DISABLE);
410 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BTF, SET); ec !=
ErrorCode::OK)
414 I2C_GenerateSTOP(instance_, ENABLE);
416 data[0] = I2C_ReceiveData(instance_);
417 data[1] = I2C_ReceiveData(instance_);
419 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
420 I2C_AcknowledgeConfig(instance_, ENABLE);
425 I2C_AcknowledgeConfig(instance_, ENABLE);
426 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
431 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_RXNE, SET); ec !=
ErrorCode::OK)
435 data[idx++] = I2C_ReceiveData(instance_);
440 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_BTF, SET); ec !=
ErrorCode::OK)
444 I2C_AcknowledgeConfig(instance_, DISABLE);
445 data[idx++] = I2C_ReceiveData(instance_);
446 I2C_GenerateSTOP(instance_, ENABLE);
447 data[idx++] = I2C_ReceiveData(instance_);
449 if (
auto ec = WaitFlagOrRecover(I2C_FLAG_RXNE, SET); ec !=
ErrorCode::OK)
453 data[idx++] = I2C_ReceiveData(instance_);
455 I2C_AcknowledgeConfig(instance_, ENABLE);
459void CH32I2C::StartTxDma(uint32_t len)
461 dma_tx_channel_->MADDR =
reinterpret_cast<uint32_t
>(dma_buff_.
addr_);
462 dma_tx_channel_->CNTR = len;
464 I2C_DMACmd(instance_, ENABLE);
465 DMA_Cmd(dma_tx_channel_, ENABLE);
468void CH32I2C::StartRxDma(uint32_t len)
471 I2C_AcknowledgeConfig(instance_, ENABLE);
472 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
474 dma_rx_channel_->MADDR =
reinterpret_cast<uint32_t
>(dma_buff_.
addr_);
475 dma_rx_channel_->CNTR = len;
477 I2C_DMALastTransferCmd(instance_, ENABLE);
478 I2C_DMACmd(instance_, ENABLE);
479 DMA_Cmd(dma_rx_channel_, ENABLE);
484 I2C_DMACmd(instance_, DISABLE);
485 I2C_DMALastTransferCmd(instance_, DISABLE);
486 DMA_Cmd(dma_tx_channel_, DISABLE);
487 DMA_Cmd(dma_rx_channel_, DISABLE);
490 I2C_AcknowledgeConfig(instance_, ENABLE);
491 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
493 I2C_GenerateSTOP(instance_, ENABLE);
499 if (read_op_.
type == ReadOperation::OperationType::BLOCK)
501 (void)block_wait_.TryPost(
true, ec);
510 if (write_op_.
type == WriteOperation::OperationType::BLOCK)
512 (void)block_wait_.TryPost(
true, ec);
521void CH32I2C::RecoverAfterImmediateFailure()
524 I2C_ITConfig(instance_, I2C_IT_ERR, DISABLE);
525 I2C_DMACmd(instance_, DISABLE);
526 I2C_DMALastTransferCmd(instance_, DISABLE);
527 DMA_Cmd(dma_tx_channel_, DISABLE);
528 DMA_Cmd(dma_rx_channel_, DISABLE);
529 dma_tx_channel_->CNTR = 0;
530 dma_rx_channel_->CNTR = 0;
532 DMA_ClearITPendingBit(CH32_I2C_TX_DMA_IT_MAP[id_]);
533 DMA_ClearITPendingBit(CH32_I2C_RX_DMA_IT_MAP[id_]);
535 const uint32_t err_its[] = {I2C_IT_BERR, I2C_IT_ARLO, I2C_IT_AF, I2C_IT_OVR,
536 I2C_IT_PECERR, I2C_IT_TIMEOUT, I2C_IT_SMBALERT};
537 for (uint32_t it : err_its)
539 I2C_ClearITPendingBit(instance_, it);
542 I2C_GenerateSTOP(instance_, ENABLE);
549 I2C_AcknowledgeConfig(instance_, ENABLE);
550 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
557 read_buff_ = {
nullptr, 0};
558 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
565 if (write_data.
size_ == 0)
567 if (op.
type != WriteOperation::OperationType::BLOCK)
581 I2C_ITConfig(instance_, I2C_IT_ERR, DISABLE);
583 ErrorCode ec = MasterStartAndAddress(slave_addr, I2C_Direction_Transmitter);
590 if (write_data.
size_ <= dma_enable_min_size_)
592 ec = PollingWriteBytes(
reinterpret_cast<const uint8_t*
>(write_data.
addr_),
594 I2C_GenerateSTOP(instance_, ENABLE);
595 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
597 if (op.
type != WriteOperation::OperationType::BLOCK)
610 if (op.
type == WriteOperation::OperationType::BLOCK)
612 block_wait_.Start(*op.
data.sem_info.sem);
614 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
615 StartTxDma(write_data.
size_);
618 if (op.
type == WriteOperation::OperationType::BLOCK)
620 return block_wait_.Wait(op.
data.sem_info.timeout);
628 if (read_data.
size_ == 0)
630 if (op.
type != ReadOperation::OperationType::BLOCK)
644 I2C_ITConfig(instance_, I2C_IT_ERR, DISABLE);
646 ErrorCode ec = MasterStartAndAddress(slave_addr, I2C_Direction_Receiver);
653 if (read_data.
size_ <= dma_enable_min_size_)
655 ec = PollingReadBytes(
reinterpret_cast<uint8_t*
>(read_data.
addr_), read_data.
size_);
656 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
657 if (op.
type != ReadOperation::OperationType::BLOCK)
666 read_buff_ = read_data;
669 if (op.
type == ReadOperation::OperationType::BLOCK)
671 block_wait_.Start(*op.
data.sem_info.sem);
673 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
674 StartRxDma(read_data.
size_);
677 if (op.
type == ReadOperation::OperationType::BLOCK)
679 return block_wait_.Wait(op.
data.sem_info.timeout);
686 MemAddrLength mem_addr_size,
bool in_isr)
688 if (write_data.
size_ == 0)
690 if (op.
type != WriteOperation::OperationType::BLOCK)
704 I2C_ITConfig(instance_, I2C_IT_ERR, DISABLE);
706 ErrorCode ec = MasterStartAndAddress(slave_addr, I2C_Direction_Transmitter);
712 ec = SendMemAddr(mem_addr, mem_addr_size);
715 I2C_GenerateSTOP(instance_, ENABLE);
716 if (op.
type != WriteOperation::OperationType::BLOCK)
723 if (write_data.
size_ <= dma_enable_min_size_)
725 ec = PollingWriteBytes(
reinterpret_cast<const uint8_t*
>(write_data.
addr_),
727 I2C_GenerateSTOP(instance_, ENABLE);
728 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
730 if (op.
type != WriteOperation::OperationType::BLOCK)
742 if (op.
type == WriteOperation::OperationType::BLOCK)
744 block_wait_.Start(*op.
data.sem_info.sem);
746 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
747 StartTxDma(write_data.
size_);
750 if (op.
type == WriteOperation::OperationType::BLOCK)
752 return block_wait_.Wait(op.
data.sem_info.timeout);
760 if (read_data.
size_ == 0)
762 if (op.
type != ReadOperation::OperationType::BLOCK)
776 I2C_ITConfig(instance_, I2C_IT_ERR, DISABLE);
779 ErrorCode ec = MasterStartAndAddress(slave_addr, I2C_Direction_Transmitter);
785 ec = SendMemAddr(mem_addr, mem_addr_size);
788 I2C_GenerateSTOP(instance_, ENABLE);
789 if (op.
type != ReadOperation::OperationType::BLOCK)
799 const uint8_t ADDR8 = Addr7ToAddr8(slave_addr);
801 I2C_GenerateSTART(instance_, ENABLE);
802 if (!WaitEvent(I2C_EVENT_MASTER_MODE_SELECT))
804 I2C_GenerateSTOP(instance_, ENABLE);
806 if (op.
type != ReadOperation::OperationType::BLOCK)
813 I2C_Send7bitAddress(instance_, ADDR8, I2C_Direction_Receiver);
814 if (!WaitEvent(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED))
816 I2C_GenerateSTOP(instance_, ENABLE);
818 if (op.
type != ReadOperation::OperationType::BLOCK)
828 const uint16_t ADDR10 = Addr10Clamp(slave_addr);
829 const uint8_t HEADER =
static_cast<uint8_t
>(0xF0 | ((ADDR10 >> 7) & 0x06));
831 I2C_GenerateSTART(instance_, ENABLE);
832 if (!WaitEvent(I2C_EVENT_MASTER_MODE_SELECT))
834 I2C_GenerateSTOP(instance_, ENABLE);
836 if (op.
type != ReadOperation::OperationType::BLOCK)
843 I2C_Send7bitAddress(instance_, HEADER, I2C_Direction_Receiver);
844 if (!WaitEvent(I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED))
846 I2C_GenerateSTOP(instance_, ENABLE);
848 if (op.
type != ReadOperation::OperationType::BLOCK)
858 if (read_data.
size_ <= dma_enable_min_size_)
860 ec = PollingReadBytes(
reinterpret_cast<uint8_t*
>(read_data.
addr_), read_data.
size_);
861 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
862 if (op.
type != ReadOperation::OperationType::BLOCK)
871 read_buff_ = read_data;
874 if (op.
type == ReadOperation::OperationType::BLOCK)
876 block_wait_.Start(*op.
data.sem_info.sem);
878 I2C_ITConfig(instance_, I2C_IT_ERR, ENABLE);
879 StartRxDma(read_data.
size_);
882 if (op.
type == ReadOperation::OperationType::BLOCK)
884 return block_wait_.Wait(op.
data.sem_info.timeout);
889void CH32I2C::TxDmaIRQHandler()
891 if (DMA_GetITStatus(CH32_I2C_TX_DMA_IT_MAP[id_]) == RESET)
895 DMA_ClearITPendingBit(CH32_I2C_TX_DMA_IT_MAP[id_]);
897 DMA_Cmd(dma_tx_channel_, DISABLE);
898 I2C_DMACmd(instance_, DISABLE);
900 if (recovering_ || !busy_)
905 (void)WaitFlag(I2C_FLAG_BTF, SET, 20000);
906 I2C_GenerateSTOP(instance_, ENABLE);
909 if (write_op_.
type == WriteOperation::OperationType::BLOCK)
921 if (DMA_GetITStatus(CH32_I2C_RX_DMA_IT_MAP[id_]) == RESET)
925 DMA_ClearITPendingBit(CH32_I2C_RX_DMA_IT_MAP[id_]);
927 DMA_Cmd(dma_rx_channel_, DISABLE);
928 I2C_DMACmd(instance_, DISABLE);
929 I2C_DMALastTransferCmd(instance_, DISABLE);
931 if (recovering_ || !busy_)
936 I2C_GenerateSTOP(instance_, ENABLE);
938 if (read_buff_.
size_ > 0)
941 read_buff_.
size_ = 0;
945 I2C_AcknowledgeConfig(instance_, ENABLE);
946 I2C_NACKPositionConfig(instance_, I2C_NACKPosition_Current);
949 if (read_op_.
type == ReadOperation::OperationType::BLOCK)
961 bool has_err =
false;
963 const uint32_t ITS[] = {I2C_IT_BERR, I2C_IT_ARLO, I2C_IT_AF, I2C_IT_OVR,
964 I2C_IT_TIMEOUT, I2C_IT_PECERR, I2C_IT_SMBALERT};
966 for (uint32_t it : ITS)
968 if (I2C_GetITStatus(instance_, it) == SET)
970 I2C_ClearITPendingBit(instance_, it);
975 if (has_err && busy_ && !recovering_)
985 void i2_c1_er_irq_handler(
void) __attribute__((interrupt(
"WCH-Interrupt-fast")));
986 void i2_c1_er_irq_handler(
void)
988 auto* p = LibXR::CH32I2C::map_[ch32_i2c_get_id(I2C1)];
991 p->ErrorIRQHandler();
997 void i2_c2_er_irq_handler(
void) __attribute__((interrupt(
"WCH-Interrupt-fast")));
998 void i2_c2_er_irq_handler(
void)
1000 auto* p = LibXR::CH32I2C::map_[ch32_i2c_get_id(I2C2)];
1003 p->ErrorIRQHandler();
ErrorCode MemWrite(uint16_t slave_addr, uint16_t mem_addr, ConstRawData write_data, WriteOperation &op, MemAddrLength mem_addr_size, bool in_isr) override
向 I2C 设备指定寄存器写入数据。 Writes data to a specific register of an I2C device.
ErrorCode MemRead(uint16_t slave_addr, uint16_t mem_addr, RawData read_data, ReadOperation &op, MemAddrLength mem_addr_size, bool in_isr) override
从 I2C 设备指定寄存器读取数据。 Reads data from a specific register of an I2C device.
void RxDmaIRQHandler()
DMA 回调入口 / DMA callbacks from CH32 DMA driver.
void ErrorIRQHandler()
错误中断回调 / I2C error IRQ callback
ErrorCode Write(uint16_t slave_addr, ConstRawData write_data, WriteOperation &op, bool in_isr) override
向 I2C 设备写入数据。 Writes data to an I2C device.
ErrorCode Read(uint16_t slave_addr, RawData read_data, ReadOperation &op, bool in_isr) override
读取 I2C 设备的数据。 Reads data from an I2C device.
CH32I2C(ch32_i2c_id_t id, RawData dma_buff, GPIO_TypeDef *scl_port, uint16_t scl_pin, GPIO_TypeDef *sda_port, uint16_t sda_pin, uint32_t pin_remap=0, uint32_t dma_enable_min_size=3, uint32_t default_clock_hz=400000, bool ten_bit_addr=false)
构造 I2C 驱动对象 / Construct I2C driver object
ErrorCode SetConfig(Configuration config) override
配置 I2C 设备参数。 Configures the I2C device settings.
static constexpr uint32_t K_DEFAULT_TIMEOUT_US
默认超时(微秒) / Default timeout in microseconds
常量原始数据封装类。 A class for encapsulating constant raw data.
size_t size_
数据大小(字节)。 The size of the data (in bytes).
const void * addr_
数据存储地址(常量)。 The storage address of the data (constant).
I2C(Inter-Integrated Circuit)接口类。 I2C (Inter-Integrated Circuit) interface class.
static void FastCopy(void *dst, const void *src, size_t size)
快速内存拷贝 / Fast memory copy
union LibXR::Operation::@5 data
void UpdateStatus(bool in_isr, Status &&status)
Updates operation status based on type.
void MarkAsRunning()
标记操作为运行状态。 Marks the operation as running.
原始数据封装类。 A class for encapsulating raw data.
size_t size_
数据大小(字节)。 The size of the data (in bytes).
void * addr_
数据存储地址。 The storage address of the data.
static MicrosecondTimestamp GetMicroseconds()
获取当前时间的微秒级时间戳。 Gets the current timestamp in microseconds.
@ FAILED
操作失败 | Operation failed
@ OK
操作成功 | Operation successful
I2C 设备的配置信息结构体。 Configuration structure for an I2C device.
uint32_t clock_speed
I2C 通信时钟速率(单位:Hz)。 The I2C clock speed (in Hz).