Files
VesiScan-Basic-firmware-test/project/ble_peripheral/ble_app_bladder_patch/i2c_manager.c
jhchun a1ad2a4b5b fix: BLE TX 먹통 해결 및 메모리 안전성 개선
- binary_tx_handler를 dr_binary_tx_safe로 전체 교체 (APP_ERROR_CHECK 제거)
- data_tx_handler APP_ERROR_CHECK → DBG_PRINTF 교체
- memset/memcpy 하드코딩 크기를 define 상수로 교체 (버퍼 오버런 수정)
- SERIAL_NO_LENGTH, HW_NO_LENGTH, PASSKEY_LENGTH를 main.h로 통합
- 미사용 HW 드라이버/EEPROM 코드 삭제, TWI를 i2c_manager.c로 통합
- EEPROM → FDS 전환, 코드 리뷰 현황 문서 추가

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-16 16:39:26 +09:00

121 lines
3.4 KiB
C

/*******************************************************************************
* @file i2c_manager.c
* @brief Reliable HW↔SW I2C Switching Logic (with Mode Set Logging)
******************************************************************************/
#include "i2c_manager.h"
#include "debug_print.h"
#include "nrf_delay.h"
#include "nrf_drv_twi.h"
#include "nrfx_twi.h"
#include "boards.h"
#include "system_interface.h"
bool HW_I2C_FRQ = true;
bool SW_I2C_FRQ = false;
#define TWI_INSTANCE 0
/* TWI (I2C) 하드웨어 인스턴스 : IMU 드라이버에서 사용 - jhChun 26.03.16 */
const nrfx_twi_t m_twi = NRFX_TWI_INSTANCE(TWI_INSTANCE);
/* TWI (I2C) 해제 - jhChun 26.03.16 */
static void twi_uninitialize(void){
nrfx_twi_disable(&m_twi);
nrfx_twi_uninit(&m_twi);
}
/* TWI (I2C) 하드웨어 초기화 (SCL/SDA핀, 400kHz) - jhChun 26.03.16 */
static void twi_initialize(void){
ret_code_t err_code;
const nrfx_twi_config_t twi_config = {
.scl = ICM42670_I2C_SCL_PIN,
.sda = ICM42670_I2C_SDA_PIN,
.frequency = NRF_TWI_FREQ_400K,
.interrupt_priority = APP_IRQ_PRIORITY_HIGH,
};
err_code = nrfx_twi_init(&m_twi, &twi_config, NULL, NULL);
APP_ERROR_CHECK(err_code);
nrfx_twi_enable(&m_twi);
}
/* -------------------------------------------------------------------------- */
/* HW (TWI) 초기화 */
/* -------------------------------------------------------------------------- */
void hw_i2c_init_once(void)
{
// SW 모드일 경우 강제 해제 후 HW 전환
if (SW_I2C_FRQ)
{
//DBG_PRINTF("[I2C]SW→HW\r\n");
// SW 리소스 해제 (필요 시 추가)
SW_I2C_FRQ = false;
nrf_delay_ms(2);
}
// 이미 HW면 스킵
if (HW_I2C_FRQ)
{
// DBG_PRINTF("[I2C] HW I2C set\r\n");
return;
}
// 실제 HW 초기화
twi_initialize();
nrf_delay_ms(2);
HW_I2C_FRQ = true;
SW_I2C_FRQ = false;
// DBG_PRINTF("[I2C] HW I2C Mode set!\r\n");
}
/* -------------------------------------------------------------------------- */
/* SW (Port Bang-Bang) 초기화 */
/* -------------------------------------------------------------------------- */
void sw_i2c_init_once(void)
{
// HW 모드일 경우 강제 해제 후 SW 전환
if (HW_I2C_FRQ)
{
//DBG_PRINTF("[I2C]HW→SW\r\n");
nrfx_twi_disable(&m_twi);
nrfx_twi_uninit(&m_twi);
nrf_delay_ms(2);
HW_I2C_FRQ = false;
}
// 이미 SW 모드면 재실행 금지
if (SW_I2C_FRQ)
{
// DBG_PRINTF("[I2C] SWI2C already initialized\r\n");
return;
}
// 실제 SW 초기화
twi_uninitialize(); // TWI 라인 해제
nrf_delay_ms(1);
SW_I2C_FRQ = true;
HW_I2C_FRQ = false;
// DBG_PRINTF("[I2C] SW I2C Mode set!\r\n");
}
/* -------------------------------------------------------------------------- */
/* 전체 리셋 */
/* -------------------------------------------------------------------------- */
void i2c_reset_state(void)
{
HW_I2C_FRQ = false;
SW_I2C_FRQ = false;
DBG_PRINTF("Flags reset\r\n");
}