cancel
Showing results for 
Search instead for 
Did you mean: 

JPEG Codec Decoding does not end/complete

AWent
Associate III

Hey,

I transfered the JPEG_DecodingFromFLASH_DMA example code into program, where I try to decode and display a JPEG image which I receive via SPI (thus, the image data is storred in the Flash as well).

Board: STM32F769I-DISCO

The code is unchanged except of the parameters pointing to the data to be decoded and respectively its length in the JPEG_Decode_DMA function:

JPEG_Decode_DMA(&JPEG_Handle, (uint32_t)frame_buffer, frame_size, JPEG_OUTPUT_DATA_BUFFER);

However, when I wait for the JpegProcessingEnd, the JPEG_OutputHandler never returns a ProcessDoneFlag ('1').

do 
 {
      JpegProcessing_End = JPEG_OutputHandler(&JPEG_Handle);
  }while(JpegProcessing_End == 0);

From Debugging, I know this is because the state

Jpeg_OUT_BufferTab[JPEG_OUT_Read_BufferIndex].State == JPEG_BUFFER_FULL

will never be reaced.

Respectively, the HAL_JPEG_DataReadyCallback will bever be called wich should set the JPEG_BUFFER_FULL state.

And the JPEG_Process will not be executed which would call the Callback, if I got that correctly.

Any idea where and what I need to check to find out why the Decoding won't work?

(I wasn't able to test the original example code, because its too large for my uVision Licence)

18 REPLIES 18

Where is output buffer placed?

JPEG_OUTPUT_DATA_BUFFER is placed at address 0xC0200000.

/* Exported constants --------------------------------------------------------*/
#define LCD_FRAME_BUFFER         0xC0000000
#define JPEG_OUTPUT_DATA_BUFFER  0xC0200000 

The Jpeg_OUT_BufferTab(s) are located starting at 0x20000000 (stated by the debugger)

ROM/RAM configurations are:

ROM1: Start: 0x8000000, Size: 0x200000

RAM1: Start: 0x20000000, Size: 0x80000

Should be all similar to all the JPEG Decoding examples.

Did you initialize external SDRAM memrory?

Yes, by using the BSP_SDRAM_Init which is implied in the LCD_Init.

Can you share your project in archive?

Charlie CHEN
Associate III

Hi @AWent​ ,

I got the same problem, can you share how you resolve it?

I`m stock in the code,and can`t get out.

do 
 {
      JpegProcessing_End = JPEG_OutputHandler(&JPEG_Handle);
  }while(JpegProcessing_End == 0);

hope you can see this!!

Thank you!

I had the same problem, as well. In my case, I was decoding from RAM rather than a file directly... Make sure that the length of the data you pass to the Decode function is an even multiple of 32 bytes (the size of the MDMA transfer). Otherwise, it will get stuck trying to read an additional block of data before decoding the last few bytes, leaving you stuck forever. In my case, I just padded the length using

padding = FileSize % 32;

(and adding padding to the length)

Hi @RGari​ ,

Thanks for your reply!

The MDMA length like this one?

void HAL_JPEG_MspInit(JPEG_HandleTypeDef* hjpeg)
{
  if(hjpeg->Instance==JPEG)
  {
  /* USER CODE BEGIN JPEG_MspInit 0 */
 
  /* USER CODE END JPEG_MspInit 0 */
    /* Peripheral clock enable */
    __HAL_RCC_JPEG_CLK_ENABLE();
 
    /* JPEG MDMA Init */
    /* JPEG_OUTFIFO_TH Init */
    hmdma_jpeg_outfifo_th.Instance = MDMA_Channel1;
    hmdma_jpeg_outfifo_th.Init.Request = MDMA_REQUEST_JPEG_OUTFIFO_TH;
    hmdma_jpeg_outfifo_th.Init.TransferTriggerMode = MDMA_BUFFER_TRANSFER;
    hmdma_jpeg_outfifo_th.Init.Priority = MDMA_PRIORITY_HIGH;
    hmdma_jpeg_outfifo_th.Init.Endianness = MDMA_LITTLE_ENDIANNESS_PRESERVE;
    hmdma_jpeg_outfifo_th.Init.SourceInc = MDMA_SRC_INC_DISABLE;
    hmdma_jpeg_outfifo_th.Init.DestinationInc = MDMA_DEST_INC_BYTE;
    hmdma_jpeg_outfifo_th.Init.SourceDataSize = MDMA_SRC_DATASIZE_WORD;
    hmdma_jpeg_outfifo_th.Init.DestDataSize = MDMA_DEST_DATASIZE_BYTE;
    hmdma_jpeg_outfifo_th.Init.DataAlignment = MDMA_DATAALIGN_PACKENABLE;
    hmdma_jpeg_outfifo_th.Init.BufferTransferLength = 32;
    hmdma_jpeg_outfifo_th.Init.SourceBurst = MDMA_SOURCE_BURST_32BEATS;
    hmdma_jpeg_outfifo_th.Init.DestBurst = MDMA_DEST_BURST_32BEATS;
    hmdma_jpeg_outfifo_th.Init.SourceBlockAddressOffset = 0;
    hmdma_jpeg_outfifo_th.Init.DestBlockAddressOffset = 0;
    if (HAL_MDMA_Init(&hmdma_jpeg_outfifo_th) != HAL_OK)
    {
      Error_Handler();
    }
 
    __HAL_LINKDMA(hjpeg,hdmaout,hmdma_jpeg_outfifo_th);
 
    /* JPEG_INFIFO_TH Init */
    hmdma_jpeg_infifo_th.Instance = MDMA_Channel0;
    hmdma_jpeg_infifo_th.Init.Request = MDMA_REQUEST_JPEG_INFIFO_TH;
    hmdma_jpeg_infifo_th.Init.TransferTriggerMode = MDMA_BUFFER_TRANSFER;
    hmdma_jpeg_infifo_th.Init.Priority = MDMA_PRIORITY_HIGH;
    hmdma_jpeg_infifo_th.Init.Endianness = MDMA_LITTLE_ENDIANNESS_PRESERVE;
    hmdma_jpeg_infifo_th.Init.SourceInc = MDMA_SRC_INC_BYTE;
    hmdma_jpeg_infifo_th.Init.DestinationInc = MDMA_DEST_INC_DISABLE;
    hmdma_jpeg_infifo_th.Init.SourceDataSize = MDMA_SRC_DATASIZE_BYTE;
    hmdma_jpeg_infifo_th.Init.DestDataSize = MDMA_DEST_DATASIZE_WORD;
    hmdma_jpeg_infifo_th.Init.DataAlignment = MDMA_DATAALIGN_PACKENABLE;
    hmdma_jpeg_infifo_th.Init.BufferTransferLength = 16;
    hmdma_jpeg_infifo_th.Init.SourceBurst = MDMA_SOURCE_BURST_32BEATS;
    hmdma_jpeg_infifo_th.Init.DestBurst = MDMA_DEST_BURST_32BEATS;
    hmdma_jpeg_infifo_th.Init.SourceBlockAddressOffset = 0;
    hmdma_jpeg_infifo_th.Init.DestBlockAddressOffset = 0;
    if (HAL_MDMA_Init(&hmdma_jpeg_infifo_th) != HAL_OK)
    {
      Error_Handler();
    }
 
    __HAL_LINKDMA(hjpeg,hdmain,hmdma_jpeg_infifo_th);
 
    /* JPEG interrupt Init */
    HAL_NVIC_SetPriority(JPEG_IRQn, 0, 0);
    HAL_NVIC_EnableIRQ(JPEG_IRQn);
  /* USER CODE BEGIN JPEG_MspInit 1 */
 
  /* USER CODE END JPEG_MspInit 1 */
  }
 
}

Where the padding can I add in?

By the way ,Is the function do..while needed?

Cause I face the new problem without the function.

New topic I post :https://community.st.com/s/question/0D50X0000Bucts0SQA/using-fatfs-with-jpeg-codec-and-show-on-lcd-panel

Hope you can help!

Appreciate that!

RGari
Associate III

Sorry for the delay...

The padding gets added to the image size in the call to HAL_JPEG_Decode_DMA:

padding=filesize % 32;

int rc=HAL_JPEG_Decode_DMA(&hjpeg, imageAddr, filesize+padding, JPEG_DECODEBUF_ADDR, CHUNK_SIZE_OUT);

filesize is the size of the JPG file (we read it off of disk into a RAM buffer elsewhere in the code). Note that we also make sure the buffer pointed to by imageAddr is at least filesize+padding, too, so you don't risk stepping on other data in the heap or even hard faulting.