The problem is the code:
HAL_I2C_Master_Transmit_DMA (&hi2c1, (uint16_t)(MCP4725A0_ADDR_A00<<1), (uint8_t *)buffer, 2);
Though it returns HAL_OK
but causes no response from slave device, but other version of this code: interruptive or blocking are works perfectly (Slave is DAC MCP4725 and master is STM32f746ng).
I've found the heart codes actually executing in this bad :( DMA code:
HAL_DMA_Start(&hdma_i2c1_tx, buffer, (uint32_t)&(hi2c1.Instance->TXDR), 2);
hi2c1.Instance->CR1 |= I2C_CR1_TXDMAEN;
I2C_TransferConfig(&hi2c1, (MCP4725A0_ADDR_A00<<1), (uint8_t)2, I2C_AUTOEND_MODE, I2C_GENERATE_START_WRITE);
After running these code debugger shows the state of Both DMA and I2C are busy there is no new data on TXDR
, and TXIS
and TXE
are both set. I think it means DMA does not respond to I2C TXIS
despite TXDMAEN
has been set.
Note: buffer
is placed at 0x2004,FFF4
. Which is located on 0x2004,C000-0x2004,FFFF -> <<SRAM2 (16 KB)>> on the <<512-Mbyte Block 1 SRAM>> 0x2000,0000-0x3FFF,FFFF
As STM32f7 Reference manual told, I2C TXIE
does not require to be set and setting TXDMAEN
will cause to if TXIS
set by hardware then rise request to DMA
for data transfer from memory to I2C peripheral TXDR
and this copying process cause to decrease embedded counter of I2C and after counter reaches 0 the transmission will end.
System configuration:
DMA is memory incremental byte sized in normal mode without FIFO using DMA1Stream6 memory to peripheral and the flow controller is DMA(!). I2C1 is in fast mode 7bit address, clock no stretch disabled and general call address detection enabled. HCLK clock is 150MHz on Power Regulator voltage scale 2. All catches are disabled and works on AXI flash interface. The NVIC is not important because even the first transfer does not occur.
CUBE generated code comparison with HAL example for stm32f746-discovery
HAL_I2C_Master_DMA() was exactly the same but the difference was in MspInit() I2C GPIO in example was set to PULLUP but NoPull in cube. (It must be not important since interruptive version worked). The last difference was Msp of example first enabled clock of GPIO, I2C and DMA then started to initialize their structure, but cube first enabled GPIO's clock then initiated it then enabled I2C Clock then initiated DMA then enabled DMA clock.
buffer
located? \$\endgroup\$