5#ifdef HAL_I2C_MODULE_ENABLED
44stm32_i2c_id_t STM32_I2C_GetID(I2C_TypeDef *hi2c);
51 STM32I2C(I2C_HandleTypeDef *hi2c,
RawData dma_buff, uint32_t dma_enable_min_size = 3)
53 id_(STM32_I2C_GetID(hi2c->Instance)),
55 dma_enable_min_size_(dma_enable_min_size),
63 if (i2c_handle_->State != HAL_I2C_STATE_READY)
65 return ErrorCode::BUSY;
70 if (read_data.
size_ > dma_enable_min_size_)
73 HAL_I2C_Master_Receive_DMA(i2c_handle_, slave_addr,
74 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_),
76 read_buff_ = read_data;
78 if (op.
type == ReadOperation::OperationType::BLOCK)
80 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
86 auto ans = HAL_I2C_Master_Receive(i2c_handle_, slave_addr,
87 reinterpret_cast<uint8_t *
>(read_data.
addr_),
88 read_data.
size_, 20) == HAL_OK
92 if (op.
type == ReadOperation::OperationType::BLOCK)
94 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
103 if (i2c_handle_->State != HAL_I2C_STATE_READY)
105 return ErrorCode::BUSY;
112 if (write_data.
size_ > dma_enable_min_size_)
116 SCB_CleanDCache_by_Addr(
reinterpret_cast<uint32_t *
>(dma_buff_.
addr_), write_data.
size_);
118 HAL_I2C_Master_Transmit_DMA(i2c_handle_, slave_addr,
119 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_),
122 if (op.
type == WriteOperation::OperationType::BLOCK)
124 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
126 return ErrorCode::OK;
130 auto ans = HAL_I2C_Master_Transmit(i2c_handle_, slave_addr,
131 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_),
132 write_data.
size_, 20) == HAL_OK
136 if (op.
type == WriteOperation::OperationType::BLOCK)
138 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
149 if (i2c_handle_->State != HAL_I2C_STATE_READY)
151 return ErrorCode::BUSY;
156 if (read_data.
size_ > dma_enable_min_size_)
159 HAL_I2C_Mem_Read_DMA(i2c_handle_, slave_addr, mem_addr,
160 mem_addr_size == MemAddrLength::BYTE_8 ? I2C_MEMADD_SIZE_8BIT
161 : I2C_MEMADD_SIZE_16BIT,
162 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_), read_data.
size_);
163 read_buff_ = read_data;
165 if (op.
type == ReadOperation::OperationType::BLOCK)
167 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
169 return ErrorCode::OK;
174 HAL_I2C_Mem_Read(i2c_handle_, slave_addr, mem_addr,
175 mem_addr_size == MemAddrLength::BYTE_8 ? I2C_MEMADD_SIZE_8BIT
176 : I2C_MEMADD_SIZE_16BIT,
177 reinterpret_cast<uint8_t *
>(read_data.
addr_), read_data.
size_,
183 if (op.
type == ReadOperation::OperationType::BLOCK)
185 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
196 if (i2c_handle_->State != HAL_I2C_STATE_READY)
198 return ErrorCode::BUSY;
205 if (write_data.
size_ > dma_enable_min_size_)
209 SCB_CleanDCache_by_Addr(
reinterpret_cast<uint32_t *
>(dma_buff_.
addr_), write_data.
size_);
211 HAL_I2C_Mem_Write_DMA(
212 i2c_handle_, slave_addr, mem_addr,
213 mem_addr_size == MemAddrLength::BYTE_8 ? I2C_MEMADD_SIZE_8BIT
214 : I2C_MEMADD_SIZE_16BIT,
215 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_), write_data.
size_);
217 if (op.
type == WriteOperation::OperationType::BLOCK)
219 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
221 return ErrorCode::OK;
225 auto ans = HAL_I2C_Mem_Write(i2c_handle_, slave_addr, mem_addr,
226 mem_addr_size == MemAddrLength::BYTE_8
227 ? I2C_MEMADD_SIZE_8BIT
228 : I2C_MEMADD_SIZE_16BIT,
229 reinterpret_cast<uint8_t *
>(dma_buff_.
addr_),
230 write_data.
size_, 20) == HAL_OK
235 if (op.
type == WriteOperation::OperationType::BLOCK)
237 return op.
data.sem_info.sem->
Wait(op.
data.sem_info.timeout);
243 template <
typename,
typename =
void>
248 template <
typename T>
249 struct HasClockSpeed<T, std::void_t<decltype(std::declval<T>()->Init.ClockSpeed)>>
254 template <
typename T>
255 typename std::enable_if<!HasClockSpeed<T>::value>::type SetClockSpeed(
260 template <
typename T>
261 typename std::enable_if<HasClockSpeed<T>::value>::type SetClockSpeed(
262 T &i2c_handle,
const Configuration &config)
264 i2c_handle->Init.ClockSpeed = config.clock_speed;
271 SetClockSpeed<decltype(i2c_handle_)>(i2c_handle_, config);
275 return ErrorCode::NOT_SUPPORT;
278 if (HAL_I2C_Init(i2c_handle_) != HAL_OK)
280 return ErrorCode::INIT_ERR;
282 return ErrorCode::OK;
286 I2C_HandleTypeDef *i2c_handle_;
287 uint32_t dma_enable_min_size_;
297 static STM32I2C *map[STM32_I2C_NUMBER];
常量原始数据封装类。 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.
I2C()
默认构造函数。 Default constructor.
void MarkAsRunning()
标记操作为运行状态。 Marks the operation as running.
void UpdateStatus(bool in_isr, Status &&...status)
Updates operation status based on type.
union LibXR::Operation::@4 data
原始数据封装类。 A class for encapsulating raw data.
size_t size_
数据大小(字节)。 The size of the data (in bytes).
void * addr_
数据存储地址。 The storage address of the data.
ErrorCode MemWrite(uint16_t slave_addr, uint16_t mem_addr, ConstRawData write_data, WriteOperation &op, MemAddrLength mem_addr_size) override
向 I2C 设备指定寄存器写入数据。 Writes data to a specific register of an I2C device.
ErrorCode SetConfig(Configuration config) override
配置 I2C 设备参数。 Configures the I2C device settings.
ErrorCode MemRead(uint16_t slave_addr, uint16_t mem_addr, RawData read_data, ReadOperation &op, MemAddrLength mem_addr_size) override
从 I2C 设备指定寄存器读取数据。 Reads data from a specific register of an I2C device.
ErrorCode Write(uint16_t slave_addr, ConstRawData write_data, WriteOperation &op) override
向 I2C 设备写入数据。 Writes data to an I2C device.
ErrorCode Read(uint16_t slave_addr, RawData read_data, ReadOperation &op) override
读取 I2C 设备的数据。 Reads data from an I2C device.
ErrorCode Wait(uint32_t timeout=UINT32_MAX)
等待(减少)信号量 Waits (decrements) the semaphore
I2C 设备的配置信息结构体。 Configuration structure for an I2C device.