ST32 og I2C write + read i en transaction

Når man skal lave en I2C læsning med ST findes der HAL funktioner til dette. Problemet med standard funktionerne er, at de færdiggør hver læsning og skrivnings transaction før næste transaction kan udføres.

Nogle peripherals kræver, at man opsætter register adressen før man laver læsningen. Samtidig kræver nogle peripherals, at det sker i en transaction.

Heldigvis har ST også en HAL funktion til dette. Det hedder ikke helt logisk HAL_I2C_Mem_Read.

Nedenstående kode viser hvordan jeg har brugt dem.

 

static const uint8_t USBHUB_I2C_ADDR = 0x58;

extern I2C_HandleTypeDef i2c1;

typedef uint8_t usbHubRegData_t;
typedef uint8_t usbHubRegAddr_t;

static void usbHubWrite(const usbHubRegAddr_t regAddr, const usbHubRegData_t regData) {
    const uint8_t byteCnt = 1;
    uint8_t txBuffer[2] = {byteCnt, regData};

     HAL_StatusTypeDef errCode = HAL_I2C_Mem_Write(&i2c1, USBHUB_I2C_ADDR, regAddr, I2C_MEMADD_SIZE_8BIT, &txBuffer[0], sizeof(txBuffer), 1000);

    if (errCode         != HAL_OK) {
        TRACE("usbHub", T_E, "USB HUB write access failed - errorCode:%d", errCode);
    }
}
 
static usbHubRegData_t usbHubRead(const usbHubRegAddr_t regAddr) {
    const uint8_t byteCnt = 1;
    uint8_t rxBuffer[2] = {byteCnt, 0x0};

    HAL_StatusTypeDef errCode = HAL_I2C_Mem_Read (&i2c1, USBHUB_I2C_ADDR, regAddr, I2C_MEMADD_SIZE_8BIT, (uint8_t *)rxBuffer, sizeof(rxBuffer), 1000);

    if (errCode         != HAL_OK) {
        TRACE("usbHub", T_E, "USB HUB write access failed - errorCode:%d", errCode);
        return 0;
    }
    return rxBuffer[1];
}

testResult_e usbHubSelftest() {
    const usbHubRegAddr_t testAddr = 0;

    usbHubRegData_t currentValue = usbHubRead(testAddr);
 
    usbHubWrite(testAddr, 0x55);
    if(usbHubRead(testAddr) != 0x55) {
        return FAILED;
    }
 
    usbHubWrite(testAddr, 0xAA);
    if(usbHubRead(testAddr) != 0xAA) {
        return FAILED;
    }

    usbHubWrite(testAddr, currentValue);
    return PASSED;
}

 

Leave a Reply

Your email address will not be published. Required fields are marked *