2020-06-13 03:39 AM
cubeMX : 5.6.1
cubeIDE : 1.3.1
Code Lib Version : STM32Cube_FW_F1_V1.8.0
I implemented ili9341 lcd as fsmc and found the following problem.
the problem is that when calling HAL_SRAM_Write_16b, it writes data once more.
I attach the measured fsmc waveform.
I can fix HAL_SRAM_Write_16b as follows:
HAL_StatusTypeDef HAL_SRAM_Write_16b(SRAM_HandleTypeDef * hsram, uint32_t * pAddress, uint16_t * pSrcBuffer, uint32_t BufferSize)
{
uint32_t size;
__IO uint32_t *psramaddress = pAddress; //this is bug fix: uint32_t -> uint16_t
uint16_t *psrcbuff = pSrcBuffer;
uint8_t limit;
/* Write last 16-bits if size is not 32-bits multiple */
if (limit != 0U)
{
*psramaddress = ((uint32_t)(*psrcbuff) & 0x0000FFFFU) | ((*psramaddress) & 0xFFFF0000U);
/*Here, since the data size is 32bit. but fsmc bus is 16bit. So we have to fix it here
fix code: *psramaddress = *psrcbuff;
*/
}
After fixing as above, LCD Works.
I hope it this will help.
2020-06-13 06:22 AM
Do not ever assume that a HAL function does what you think it should do.
Either the author of that function did not have the faintest idea what he was doing, or there is some nontrivial point in doing it this way that is beyond my knowledge.
I'm seriously interested in any plausible explanations (except for terminal incompetence) of doing it this way, i.e writing a halfword 0-padded to 32 bits, then reading it back and fill in the other half. Why?
__IO uint32_t *psramaddress = pAddress;
uint16_t * psrcbuff = pSrcBuffer;
/* ... */
for (size = BufferSize; size != limit; size-=2U)
{
*psramaddress = (uint32_t)(*psrcbuff);
psrcbuff++;
*psramaddress |= ((uint32_t)(*psrcbuff) << 16U);
psrcbuff++;
psramaddress++;
}
Just don't use it. This stuff should only be used as examples of antipatterns, bad practices to avoid. Cargo cult programming.
Code like this is a big red blinking neon sign on the corporate headquarters building advertising that we are cheap, using underpaid labor. Even our quality assurance is underpaid if it exists at all.