0031-Omxdec-fix-jpg-decode-output-is-empty.patch 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159
  1. From 38c34580eb49891a440babb80b2cb1cf811d936e Mon Sep 17 00:00:00 2001
  2. From: Som Qin <som.qin@starfivetech.com>
  3. Date: Tue, 29 Aug 2023 21:21:32 +0800
  4. Subject: [PATCH 2/2] Omxdec: fix jpg decode output is empty
  5. Signed-off-by: Som Qin <som.qin@starfivetech.com>
  6. ---
  7. libavcodec/omxdec.c | 71 ++++++++++++++++++++++++++++++---------------
  8. 1 file changed, 48 insertions(+), 23 deletions(-)
  9. diff --git a/libavcodec/omxdec.c b/libavcodec/omxdec.c
  10. index 18bd954..6cb0d98 100755
  11. --- a/libavcodec/omxdec.c
  12. +++ b/libavcodec/omxdec.c
  13. @@ -391,31 +391,55 @@ static void append_buffer(pthread_mutex_t *mutex, pthread_cond_t *cond,
  14. pthread_mutex_unlock(mutex);
  15. }
  16. -static OMX_BUFFERHEADERTYPE *get_buffer(pthread_mutex_t *mutex, pthread_cond_t *cond,
  17. - int* array_size, OMX_BUFFERHEADERTYPE **array,
  18. - int wait_sec)
  19. +static OMX_BUFFERHEADERTYPE *get_input_buffer(OMXCodecContext *s, int wait_sec)
  20. {
  21. struct timespec abstime;
  22. OMX_BUFFERHEADERTYPE *buffer;
  23. - pthread_mutex_lock(mutex);
  24. - if (wait_sec > 0 && !*array_size) {
  25. + pthread_mutex_lock(&s->input_mutex);
  26. + if (wait_sec > 0 && !s->num_free_in_buffers) {
  27. clock_gettime(CLOCK_REALTIME, &abstime);
  28. abstime.tv_sec += wait_sec;
  29. - pthread_cond_timedwait(cond, mutex, &abstime);
  30. + pthread_cond_timedwait(&s->input_cond, &s->input_mutex, &abstime);
  31. } else if (wait_sec < 0) {
  32. - while (!*array_size)
  33. + while (!s->num_free_in_buffers)
  34. {
  35. - pthread_cond_wait(cond, mutex);
  36. + pthread_cond_wait(&s->input_cond, &s->input_mutex);
  37. }
  38. }
  39. - if (*array_size > 0) {
  40. - buffer = array[0];
  41. - (*array_size)--;
  42. - memmove(&array[0], &array[1], (*array_size) * sizeof(OMX_BUFFERHEADERTYPE*));
  43. + if (s->num_free_in_buffers > 0) {
  44. + buffer = s->free_in_buffers[0];
  45. + (s->num_free_in_buffers)--;
  46. + memmove(&s->free_in_buffers[0], &s->free_in_buffers[1], s->num_free_in_buffers * sizeof(OMX_BUFFERHEADERTYPE*));
  47. } else {
  48. buffer = NULL;
  49. }
  50. - pthread_mutex_unlock(mutex);
  51. + pthread_mutex_unlock(&s->input_mutex);
  52. + return buffer;
  53. +}
  54. +
  55. +static OMX_BUFFERHEADERTYPE *get_output_buffer(OMXCodecContext *s, int wait_sec)
  56. +{
  57. + struct timespec abstime;
  58. + OMX_BUFFERHEADERTYPE *buffer;
  59. + pthread_mutex_lock(&s->output_mutex);
  60. + if (wait_sec > 0 && !s->num_done_out_buffers) {
  61. + clock_gettime(CLOCK_REALTIME, &abstime);
  62. + abstime.tv_sec += wait_sec;
  63. + pthread_cond_timedwait(&s->output_cond, &s->output_mutex, &abstime);
  64. + } else if (wait_sec < 0) {
  65. + while (!s->num_done_out_buffers)
  66. + {
  67. + pthread_cond_wait(&s->output_cond, &s->output_mutex);
  68. + }
  69. + }
  70. + if (s->num_done_out_buffers > 0) {
  71. + buffer = s->done_out_buffers[0];
  72. + (s->num_done_out_buffers)--;
  73. + memmove(&s->done_out_buffers[0], &s->done_out_buffers[1], s->num_done_out_buffers * sizeof(OMX_BUFFERHEADERTYPE*));
  74. + } else {
  75. + buffer = NULL;
  76. + }
  77. + pthread_mutex_unlock(&s->output_mutex);
  78. return buffer;
  79. }
  80. @@ -488,12 +512,15 @@ static OMX_ERRORTYPE event_handler(OMX_HANDLETYPE component, OMX_PTR app_data, O
  81. av_log(s->avctx, AV_LOG_VERBOSE, "w:%d, h:%d, fmt:%d\n", s->dec_out_width, s->dec_out_height, s->dec_pix_fmt);
  82. if (!s->num_out_buffers) {
  83. + pthread_mutex_lock(&s->output_mutex);
  84. s->num_out_buffers = out_port_params.nBufferCountActual;
  85. s->out_buffer_headers = av_mallocz(sizeof(OMX_BUFFERHEADERTYPE*) * s->num_out_buffers);
  86. s->done_out_buffers = av_mallocz(sizeof(OMX_BUFFERHEADERTYPE*) * s->num_out_buffers);
  87. - if (!s->out_buffer_headers || !s->done_out_buffers)
  88. + if (!s->out_buffer_headers || !s->done_out_buffers) {
  89. + pthread_mutex_unlock(&s->output_mutex);
  90. return AVERROR(ENOMEM);
  91. + }
  92. OMX_SendCommand(s->handle, OMX_CommandPortEnable, 1, NULL);
  93. @@ -502,6 +529,7 @@ static OMX_ERRORTYPE event_handler(OMX_HANDLETYPE component, OMX_PTR app_data, O
  94. if (err != OMX_ErrorNone) {
  95. av_log(s->avctx, AV_LOG_ERROR, "err %x (%d) on line %d\n", err, err, __LINE__);
  96. + pthread_mutex_unlock(&s->output_mutex);
  97. return AVERROR_UNKNOWN;
  98. }
  99. s->num_out_buffers = num;
  100. @@ -512,6 +540,7 @@ static OMX_ERRORTYPE event_handler(OMX_HANDLETYPE component, OMX_PTR app_data, O
  101. for (; num < s->num_out_buffers; num++)
  102. s->done_out_buffers[s->num_done_out_buffers++] = s->out_buffer_headers[num];
  103. }
  104. + pthread_mutex_unlock(&s->output_mutex);
  105. }
  106. }
  107. }
  108. @@ -966,15 +995,13 @@ static av_cold void cleanup(OMXCodecContext *s)
  109. wait_for_state(s, OMX_StateIdle);
  110. OMX_SendCommand(s->handle, OMX_CommandStateSet, OMX_StateLoaded, NULL);
  111. for (i = 0; i < s->num_in_buffers; i++) {
  112. - buffer = get_buffer(&s->input_mutex, &s->input_cond,
  113. - &s->num_free_in_buffers, s->free_in_buffers, -1);
  114. + buffer = get_input_buffer(s, -1);
  115. if (s->input_zerocopy)
  116. buffer->pBuffer = NULL;
  117. OMX_FreeBuffer(s->handle, s->in_port, buffer);
  118. }
  119. - while (buffer = get_buffer(&s->output_mutex, &s->output_cond,
  120. - &s->num_done_out_buffers, s->done_out_buffers, 0)) {
  121. + while (buffer = get_output_buffer(s, 0)) {
  122. OMX_FreeBuffer(s->handle, s->out_port, buffer);
  123. s->num_out_buffers--;
  124. }
  125. @@ -1236,8 +1263,7 @@ static int omx_decode_frame(AVCodecContext *avctx, void *data,
  126. //VPU init and fill buffer slow, so empty buf sleep to send before get vpu fill buf.
  127. // if(!s->first_get_outbuffer)
  128. // av_usleep(100000);
  129. - buffer = get_buffer(&s->input_mutex, &s->input_cond,
  130. - &s->num_free_in_buffers, s->free_in_buffers, 10);
  131. + buffer = get_input_buffer(s, 10);
  132. if (!buffer) {
  133. av_log(avctx, AV_LOG_ERROR, "get_buffer NULL\n");
  134. @@ -1289,9 +1315,8 @@ static int omx_decode_frame(AVCodecContext *avctx, void *data,
  135. // If not flushing, just poll the queue if there's finished packets.
  136. // If flushing, do a blocking wait until we either get a completed
  137. // packet, or get EOS.
  138. - buffer = get_buffer(&s->output_mutex, &s->output_cond,
  139. - &s->num_done_out_buffers, s->done_out_buffers,
  140. - 0);
  141. + int wait_sec = ((avctx->codec->id == AV_CODEC_ID_MJPEG) && (!s->decode_flag))? 2 : 0;
  142. + buffer = get_output_buffer(s, wait_sec);
  143. if (!buffer) {
  144. break;
  145. --
  146. 2.25.1