- Edited
Hi, I was following the step in trill sensors to implement the code in the STM32. I am using nucleo-h723zg, but all the board will work the same. I am using trill flex sensor with default address (no soldering on the address part) with i2c1 channel in the stm board.
Here is my code snippet of main.c. First parts are the definition section, and the second part is the code in the main function.
uint8_t gI2cAddress = 0x48 << 1;
//uint8_t gI2cAddress = 0x48;
const unsigned int kTimeout = 100;
enum {
kOffsetCommand = 0,
kOffsetData = 4
};
enum {
kCommandNone = 0,
kCommandMode = 1,
kCommandScanSettings = 2,
kCommandPrescaler = 3,
kCommandNoiseThreshold = 4,
kCommandIdac = 5,
kCommandBaselineUpdate = 6,
kCommandMinimumSize = 7,
kCommandAdjacentCentroidNoiseThreshold = 8,
kCommandAutoScanInterval = 16,
kCommandIdentify = 255,
};
enum { kNumTouches = 30 };
enum {
kModeCentroid = 0,
kModeRaw = 1,
kModeBaseline = 2,
kModeDiff = 3
};
uint16_t firstLocation = 0;
uint16_t firstSize = 0;
`
`
uint8_t identifyBuf[] = {kOffsetCommand, kCommandIdentify};
int ret = HAL_I2C_Master_Transmit(&trillHi2c, gI2cAddress, identifyBuf, sizeof(identifyBuf), kTimeout);
if(HAL_OK != ret) {
uint32_t error = HAL_I2C_GetError(&hi2c1);
printf("I2C Transmission Error: %ld\n", error);
fprintf(stderr, "Error: send identify command, I2C Error: %d\n\r", ret);
}
HAL_Delay(10);
uint8_t receiveBuffer[4];
ret = HAL_I2C_Master_Receive(&trillHi2c, gI2cAddress, receiveBuffer, sizeof(receiveBuffer), kTimeout);
if(HAL_OK != ret) {
fprintf(stderr, "Error: receive identify command, I2C Error: %d \n\r", ret);
printf("identify: %#4x %#4x %#4x %#4x\n\r", receiveBuffer[0], receiveBuffer[1], receiveBuffer[2], receiveBuffer[3]);
}
printf("identify: %#4x %#4x %#4x %#4x\n\r", receiveBuffer[0], receiveBuffer[1], receiveBuffer[2], receiveBuffer[3]);
HAL_Delay(10);
uint8_t diffBuf[] = {kOffsetCommand, kCommandMode, kModeCentroid};
ret = HAL_I2C_Master_Transmit(&trillHi2c, gI2cAddress, diffBuf, sizeof(diffBuf), kTimeout);
if(HAL_OK != ret) {
fprintf(stderr, "Error: send mode command\n\r");
// return 1;
}
// update baseline
uint8_t updateBaselineBuffer[] = {kOffsetCommand, kCommandBaselineUpdate};
ret = HAL_I2C_Master_Transmit(&trillHi2c, gI2cAddress, updateBaselineBuffer, sizeof(updateBaselineBuffer), kTimeout);
if(HAL_OK != ret) {
fprintf(stderr, "Error: send update baseline command\n\r");
}
uint8_t transmitBuffer[] = {kOffsetData};
ret = HAL_I2C_Master_Transmit(&trillHi2c, gI2cAddress, transmitBuffer, sizeof(transmitBuffer), kTimeout);
if(HAL_OK != ret) {
fprintf(stderr, "Error: prepare to read command\n\r"); }
while(1) {
uint8_t receiveBuffer[kNumTouches * 2 * 2];
ret = HAL_I2C_Master_Receive(&trillHi2c, gI2cAddress, receiveBuffer, sizeof(receiveBuffer), kTimeout);
if(HAL_OK != ret) {
fprintf(stderr, "Error: blocking receive\n\r");
return 1;
}
for(unsigned int n = 0; n < kNumTouches; ++n)
{
uint16_t location = ((receiveBuffer[2 * n] << 8) + receiveBuffer[2 * n + 1]);
uint16_t size = ((receiveBuffer[2 * n + kNumTouches * 2] << 8) + receiveBuffer[2 * n + 1 + kNumTouches * 2]);
if(location != 0xffff)
{
if(0 == n)
{
firstLocation = location;
firstSize = size;
}
printf("[%d] %d %d, \n\r", n, location, size);
}
}
printf("\n\r reading done? \n\r ");
HAL_Delay(500);
However, it always giving "I2C Transmission Error: 32
Error: send identify command, I2C Error: 1". Of course, the other identification codes give error:
"Error: receive identify command, I2C Error: 1
identify: 0 0 0 0
identify: 0 0 0 0
Error: send mode command
Error: send update baseline command
Error: prepare to read command
Error: blocking receive"
I am pretty sure I followed the all the convention in the datasheet, but I am still getting this error. I2C1 channel gets 48MHz clock and I set the i2c as fast mode (400Hz). Could you help me to find what's wrong with the code / setup?
Or should I use DMA setting or timer? If so, could you guide me how to setup the right DMA/timer with i2c for trill flex?
Thank you!!