mirror of
				https://github.com/nyanmisaka/ffmpeg-rockchip.git
				synced 2025-10-31 12:36:41 +08:00 
			
		
		
		
	Merge commit '676da248cad49debc40720baa13214f0b94dcc71'
* commit '676da248cad49debc40720baa13214f0b94dcc71': vmd: refactor the inner decode loop Conflicts: libavcodec/vmdav.c Merged-by: Michael Niedermayer <michaelni@gmx.at>
This commit is contained in:
		| @@ -270,91 +270,95 @@ static int vmd_decode(VmdVideoContext *s, AVFrame *frame) | ||||
|             return AVERROR_INVALIDDATA; | ||||
|         } | ||||
|     } | ||||
|     if (s->size > 0) { | ||||
|         /* originally UnpackFrame in VAG's code */ | ||||
|         bytestream2_init(&gb, gb.buffer, s->buf + s->size - gb.buffer); | ||||
|         if (bytestream2_get_bytes_left(&gb) < 1) | ||||
|             return AVERROR_INVALIDDATA; | ||||
|         meth = bytestream2_get_byteu(&gb); | ||||
|         if (meth & 0x80) { | ||||
|             lz_unpack(gb.buffer, bytestream2_get_bytes_left(&gb), | ||||
|                       s->unpack_buffer, s->unpack_buffer_size); | ||||
|             meth &= 0x7F; | ||||
|             bytestream2_init(&gb, s->unpack_buffer, s->unpack_buffer_size); | ||||
|         } | ||||
|  | ||||
|         dp = &frame->data[0][frame_y * frame->linesize[0] + frame_x]; | ||||
|         pp = &s->prev_frame.data[0][frame_y * s->prev_frame.linesize[0] + frame_x]; | ||||
|         switch (meth) { | ||||
|         case 1: | ||||
|             for (i = 0; i < frame_height; i++) { | ||||
|                 ofs = 0; | ||||
|                 do { | ||||
|                     len = bytestream2_get_byte(&gb); | ||||
|                     if (len & 0x80) { | ||||
|                         len = (len & 0x7F) + 1; | ||||
|                         if (ofs + len > frame_width || bytestream2_get_bytes_left(&gb) < len) | ||||
|                             return AVERROR_INVALIDDATA; | ||||
|                         bytestream2_get_bufferu(&gb, &dp[ofs], len); | ||||
|                         ofs += len; | ||||
|                     } else { | ||||
|                         /* interframe pixel copy */ | ||||
|                         if (ofs + len + 1 > frame_width || !s->prev_frame.data[0]) | ||||
|                             return AVERROR_INVALIDDATA; | ||||
|                         memcpy(&dp[ofs], &pp[ofs], len + 1); | ||||
|                         ofs += len + 1; | ||||
|                     } | ||||
|                 } while (ofs < frame_width); | ||||
|                 if (ofs > frame_width) { | ||||
|                     av_log(s->avctx, AV_LOG_ERROR, "offset > width (%d > %d)\n", | ||||
|                         ofs, frame_width); | ||||
|                     return AVERROR_INVALIDDATA; | ||||
|     if (!s->size) | ||||
|         return 0; | ||||
|  | ||||
|     /* originally UnpackFrame in VAG's code */ | ||||
|     if (bytestream2_get_bytes_left(&gb) < 1) | ||||
|         return AVERROR_INVALIDDATA; | ||||
|     meth = bytestream2_get_byteu(&gb); | ||||
|     if (meth & 0x80) { | ||||
|         lz_unpack(gb.buffer, bytestream2_get_bytes_left(&gb), | ||||
|                   s->unpack_buffer, s->unpack_buffer_size); | ||||
|         meth &= 0x7F; | ||||
|         bytestream2_init(&gb, s->unpack_buffer, s->unpack_buffer_size); | ||||
|     } | ||||
|  | ||||
|     dp = &frame->data[0][frame_y * frame->linesize[0] + frame_x]; | ||||
|     pp = &s->prev_frame.data[0][frame_y * s->prev_frame.linesize[0] + frame_x]; | ||||
|     switch (meth) { | ||||
|     case 1: | ||||
|         for (i = 0; i < frame_height; i++) { | ||||
|             ofs = 0; | ||||
|             do { | ||||
|                 len = bytestream2_get_byte(&gb); | ||||
|                 if (len & 0x80) { | ||||
|                     len = (len & 0x7F) + 1; | ||||
|                     if (ofs + len > frame_width || | ||||
|                         bytestream2_get_bytes_left(&gb) < len) | ||||
|                         return AVERROR_INVALIDDATA; | ||||
|                     bytestream2_get_bufferu(&gb, &dp[ofs], len); | ||||
|                     ofs += len; | ||||
|                 } else { | ||||
|                     /* interframe pixel copy */ | ||||
|                     if (ofs + len + 1 > frame_width || !s->prev_frame.data[0]) | ||||
|                         return AVERROR_INVALIDDATA; | ||||
|                     memcpy(&dp[ofs], &pp[ofs], len + 1); | ||||
|                     ofs += len + 1; | ||||
|                 } | ||||
|                 dp += frame->linesize[0]; | ||||
|                 pp += s->prev_frame.linesize[0]; | ||||
|             } while (ofs < frame_width); | ||||
|             if (ofs > frame_width) { | ||||
|                 av_log(s->avctx, AV_LOG_ERROR, | ||||
|                        "offset > width (%d > %d)\n", | ||||
|                        ofs, frame_width); | ||||
|                 return AVERROR_INVALIDDATA; | ||||
|             } | ||||
|             break; | ||||
|  | ||||
|         case 2: | ||||
|             for (i = 0; i < frame_height; i++) { | ||||
|                 bytestream2_get_buffer(&gb, dp, frame_width); | ||||
|                 dp += frame->linesize[0]; | ||||
|                 pp += s->prev_frame.linesize[0]; | ||||
|             } | ||||
|             break; | ||||
|  | ||||
|         case 3: | ||||
|             for (i = 0; i < frame_height; i++) { | ||||
|                 ofs = 0; | ||||
|                 do { | ||||
|                     len = bytestream2_get_byte(&gb); | ||||
|                     if (len & 0x80) { | ||||
|                         len = (len & 0x7F) + 1; | ||||
|                         if (bytestream2_get_byte(&gb) == 0xFF) | ||||
|                             len = rle_unpack(gb.buffer, &dp[ofs], | ||||
|                                              len, bytestream2_get_bytes_left(&gb), | ||||
|                                              frame_width - ofs); | ||||
|                         else | ||||
|                             bytestream2_get_buffer(&gb, &dp[ofs], len); | ||||
|                         bytestream2_skip(&gb, len); | ||||
|                     } else { | ||||
|                         /* interframe pixel copy */ | ||||
|                         if (ofs + len + 1 > frame_width || !s->prev_frame.data[0]) | ||||
|                             return AVERROR_INVALIDDATA; | ||||
|                         memcpy(&dp[ofs], &pp[ofs], len + 1); | ||||
|                         ofs += len + 1; | ||||
|                     } | ||||
|                 } while (ofs < frame_width); | ||||
|                 if (ofs > frame_width) { | ||||
|                     av_log(s->avctx, AV_LOG_ERROR, "offset > width (%d > %d)\n", | ||||
|                         ofs, frame_width); | ||||
|                     return AVERROR_INVALIDDATA; | ||||
|                 } | ||||
|                 dp += frame->linesize[0]; | ||||
|                 pp += s->prev_frame.linesize[0]; | ||||
|             } | ||||
|             break; | ||||
|             dp += frame->linesize[0]; | ||||
|             pp += s->prev_frame.linesize[0]; | ||||
|         } | ||||
|         break; | ||||
|  | ||||
|     case 2: | ||||
|         for (i = 0; i < frame_height; i++) { | ||||
|             bytestream2_get_buffer(&gb, dp, frame_width); | ||||
|             dp += frame->linesize[0]; | ||||
|             pp += s->prev_frame.linesize[0]; | ||||
|         } | ||||
|         break; | ||||
|  | ||||
|     case 3: | ||||
|         for (i = 0; i < frame_height; i++) { | ||||
|             ofs = 0; | ||||
|             do { | ||||
|                 len = bytestream2_get_byte(&gb); | ||||
|                 if (len & 0x80) { | ||||
|                     len = (len & 0x7F) + 1; | ||||
|                     if (bytestream2_get_byte(&gb) == 0xFF) | ||||
|                         len = rle_unpack(gb.buffer, &dp[ofs], | ||||
|                                          len, bytestream2_get_bytes_left(&gb), | ||||
|                                          frame_width - ofs); | ||||
|                     else | ||||
|                         bytestream2_get_buffer(&gb, &dp[ofs], len); | ||||
|                     bytestream2_skip(&gb, len); | ||||
|                 } else { | ||||
|                     /* interframe pixel copy */ | ||||
|                     if (ofs + len + 1 > frame_width || !s->prev_frame.data[0]) | ||||
|                         return AVERROR_INVALIDDATA; | ||||
|                     memcpy(&dp[ofs], &pp[ofs], len + 1); | ||||
|                     ofs += len + 1; | ||||
|                 } | ||||
|             } while (ofs < frame_width); | ||||
|             if (ofs > frame_width) { | ||||
|                 av_log(s->avctx, AV_LOG_ERROR, | ||||
|                        "offset > width (%d > %d)\n", | ||||
|                        ofs, frame_width); | ||||
|                 return AVERROR_INVALIDDATA; | ||||
|             } | ||||
|             dp += frame->linesize[0]; | ||||
|             pp += s->prev_frame.linesize[0]; | ||||
|         } | ||||
|         break; | ||||
|     } | ||||
|     return 0; | ||||
| } | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Michael Niedermayer
					Michael Niedermayer