mirror of
https://github.com/openmv/openmv.git
synced 2025-11-04 14:49:50 +08:00
214 lines
6.1 KiB
C
214 lines
6.1 KiB
C
/*
|
|
* This file is part of the OpenMV project.
|
|
*
|
|
* Copyright (c) 2013-2019 Ibrahim Abdelkader <iabdalkader@openmv.io>
|
|
* Copyright (c) 2013-2019 Kwabena W. Agyeman <kwagyeman@openmv.io>
|
|
*
|
|
* This work is licensed under the MIT license, see the file LICENSE for details.
|
|
*
|
|
* SCCB (I2C like) driver.
|
|
*/
|
|
#include <stdbool.h>
|
|
#include <stddef.h>
|
|
#include STM32_HAL_H
|
|
#include "systick.h"
|
|
#include "omv_boardconfig.h"
|
|
#include "cambus.h"
|
|
#define I2C_FREQUENCY (100000)
|
|
#define I2C_TIMEOUT (100)
|
|
|
|
int cambus_init(I2C_HandleTypeDef *i2c, I2C_TypeDef *instance, uint32_t timing)
|
|
{
|
|
/* Configure I2C */
|
|
i2c->Instance = instance;
|
|
i2c->Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT;
|
|
#if !defined(STM32F4)
|
|
i2c->Init.Timing = timing;
|
|
#else
|
|
i2c->Init.ClockSpeed = I2C_FREQUENCY;
|
|
i2c->Init.DutyCycle = I2C_DUTYCYCLE_2;
|
|
#endif
|
|
i2c->Init.DualAddressMode = I2C_DUALADDRESS_DISABLED;
|
|
i2c->Init.GeneralCallMode = I2C_GENERALCALL_DISABLED;
|
|
i2c->Init.NoStretchMode = I2C_NOSTRETCH_DISABLED;
|
|
i2c->Init.OwnAddress1 = 0xFE;
|
|
i2c->Init.OwnAddress2 = 0xFE;
|
|
|
|
if (HAL_I2C_Init(i2c) != HAL_OK) {
|
|
/* Initialization Error */
|
|
return -1;
|
|
}
|
|
|
|
if (timing == I2C_TIMING_FAST) {
|
|
// Enable FAST mode plus.
|
|
if (instance == I2C1) {
|
|
#if defined(I2C_FASTMODEPLUS_I2C1)
|
|
HAL_I2CEx_EnableFastModePlus(I2C_FASTMODEPLUS_I2C1);
|
|
#endif
|
|
} else if (instance == I2C2) {
|
|
#if defined(I2C_FASTMODEPLUS_I2C2)
|
|
HAL_I2CEx_EnableFastModePlus(I2C_FASTMODEPLUS_I2C2);
|
|
#endif
|
|
} else if (instance == I2C3) {
|
|
#if defined(I2C_FASTMODEPLUS_I2C3)
|
|
HAL_I2CEx_EnableFastModePlus(I2C_FASTMODEPLUS_I2C3);
|
|
#endif
|
|
} else {
|
|
#if defined(I2C_FASTMODEPLUS_I2C4)
|
|
HAL_I2CEx_EnableFastModePlus(I2C_FASTMODEPLUS_I2C4);
|
|
#endif
|
|
}
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int cambus_deinit(I2C_HandleTypeDef *i2c)
|
|
{
|
|
if (i2c->Instance) {
|
|
HAL_I2C_DeInit(i2c);
|
|
}
|
|
i2c->Instance = NULL;
|
|
return 0;
|
|
}
|
|
|
|
int cambus_scan(I2C_HandleTypeDef *i2c)
|
|
{
|
|
for (uint8_t addr=0x09; addr<=0x77; addr++) {
|
|
if (HAL_I2C_IsDeviceReady(i2c, addr << 1, 10, I2C_TIMEOUT) == HAL_OK) {
|
|
return (addr << 1);
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
int cambus_gencall(I2C_HandleTypeDef *i2c, uint8_t cmd)
|
|
{
|
|
if (HAL_I2C_Master_Transmit(i2c, 0x00, &cmd, 1, I2C_TIMEOUT) != HAL_OK) {
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int cambus_readb(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint8_t *reg_data)
|
|
{
|
|
int ret = 0;
|
|
|
|
if((HAL_I2C_Master_Transmit(i2c, slv_addr, ®_addr, 1, I2C_TIMEOUT) != HAL_OK)
|
|
|| (HAL_I2C_Master_Receive (i2c, slv_addr, reg_data, 1, I2C_TIMEOUT) != HAL_OK)) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_writeb(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint8_t reg_data)
|
|
{
|
|
int ret=0;
|
|
uint8_t buf[] = {reg_addr, reg_data};
|
|
|
|
if(HAL_I2C_Master_Transmit(i2c, slv_addr, buf, 2, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_readb2(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint8_t *reg_data)
|
|
{
|
|
int ret=0;
|
|
if (HAL_I2C_Mem_Read(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, reg_data, 1, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_writeb2(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint8_t reg_data)
|
|
{
|
|
int ret=0;
|
|
if (HAL_I2C_Mem_Write(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, ®_data, 1, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_readw(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint16_t *reg_data)
|
|
{
|
|
int ret=0;
|
|
if (HAL_I2C_Mem_Read(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_8BIT, (uint8_t*) reg_data, 2, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
*reg_data = (*reg_data >> 8) | (*reg_data << 8);
|
|
return ret;
|
|
}
|
|
|
|
int cambus_writew(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint16_t reg_data)
|
|
{
|
|
int ret=0;
|
|
reg_data = (reg_data >> 8) | (reg_data << 8);
|
|
if (HAL_I2C_Mem_Write(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_8BIT, (uint8_t*) ®_data, 2, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_readw2(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint16_t *reg_data)
|
|
{
|
|
int ret=0;
|
|
if (HAL_I2C_Mem_Read(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, (uint8_t*) reg_data, 2, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
*reg_data = (*reg_data >> 8) | (*reg_data << 8);
|
|
return ret;
|
|
}
|
|
|
|
int cambus_writew2(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint16_t reg_data)
|
|
{
|
|
int ret=0;
|
|
reg_data = (reg_data >> 8) | (reg_data << 8);
|
|
if (HAL_I2C_Mem_Write(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, (uint8_t*) ®_data, 2, I2C_TIMEOUT) != HAL_OK) {
|
|
ret = -1;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int cambus_read_bytes(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint8_t *buf, int len)
|
|
{
|
|
if (HAL_I2C_Mem_Read(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_8BIT, buf, len, I2C_TIMEOUT) != HAL_OK) {
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int cambus_write_bytes(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint8_t reg_addr, uint8_t *buf, int len)
|
|
{
|
|
if (HAL_I2C_Mem_Write(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_8BIT, buf, len, I2C_TIMEOUT) != HAL_OK) {
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int cambus_readw_bytes(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint8_t *buf, int len)
|
|
{
|
|
if (HAL_I2C_Mem_Read(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, buf, len, I2C_TIMEOUT) != HAL_OK) {
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int cambus_writew_bytes(I2C_HandleTypeDef *i2c, uint8_t slv_addr, uint16_t reg_addr, uint8_t *buf, int len)
|
|
{
|
|
if (HAL_I2C_Mem_Write(i2c, slv_addr, reg_addr,
|
|
I2C_MEMADD_SIZE_16BIT, buf, len, I2C_TIMEOUT) != HAL_OK) {
|
|
return -1;
|
|
}
|
|
return 0;
|
|
}
|