You've already forked FFmpeg
							
							
				mirror of
				https://github.com/FFmpeg/FFmpeg.git
				synced 2025-10-30 23:18:11 +02:00 
			
		
		
		
	lavf/mov: fix huge alloc in mov_read_ctts
An invalid file may cause huge alloc. Delay expansion of ctts entries until the number of samples is known in mov_build_index. Fixes: 23 Found-by: zhao dongzhuo, AD-lab of Venustech Signed-off-by: Michael Niedermayer <michael@niedermayer.cc>
This commit is contained in:
		
				
					committed by
					
						 Michael Niedermayer
						Michael Niedermayer
					
				
			
			
				
	
			
			
			
						parent
						
							d13b8f68d7
						
					
				
				
					commit
					2d015d3bf9
				
			| @@ -2895,7 +2895,7 @@ static int mov_read_ctts(MOVContext *c, AVIOContext *pb, MOVAtom atom) | |||||||
| { | { | ||||||
|     AVStream *st; |     AVStream *st; | ||||||
|     MOVStreamContext *sc; |     MOVStreamContext *sc; | ||||||
|     unsigned int i, j, entries, ctts_count = 0; |     unsigned int i, entries, ctts_count = 0; | ||||||
|  |  | ||||||
|     if (c->fc->nb_streams < 1) |     if (c->fc->nb_streams < 1) | ||||||
|         return 0; |         return 0; | ||||||
| @@ -2928,9 +2928,8 @@ static int mov_read_ctts(MOVContext *c, AVIOContext *pb, MOVAtom atom) | |||||||
|             continue; |             continue; | ||||||
|         } |         } | ||||||
|  |  | ||||||
|         /* Expand entries such that we have a 1-1 mapping with samples. */ |         add_ctts_entry(&sc->ctts_data, &ctts_count, &sc->ctts_allocated_size, | ||||||
|         for (j = 0; j < count; j++) |                        count, duration); | ||||||
|             add_ctts_entry(&sc->ctts_data, &ctts_count, &sc->ctts_allocated_size, 1, duration); |  | ||||||
|  |  | ||||||
|         av_log(c->fc, AV_LOG_TRACE, "count=%d, duration=%d\n", |         av_log(c->fc, AV_LOG_TRACE, "count=%d, duration=%d\n", | ||||||
|                 count, duration); |                 count, duration); | ||||||
| @@ -3579,6 +3578,8 @@ static void mov_build_index(MOVContext *mov, AVStream *st) | |||||||
|     unsigned int stps_index = 0; |     unsigned int stps_index = 0; | ||||||
|     unsigned int i, j; |     unsigned int i, j; | ||||||
|     uint64_t stream_size = 0; |     uint64_t stream_size = 0; | ||||||
|  |     MOVStts *ctts_data_old = sc->ctts_data; | ||||||
|  |     unsigned int ctts_count_old = sc->ctts_count; | ||||||
|  |  | ||||||
|     if (sc->elst_count) { |     if (sc->elst_count) { | ||||||
|         int i, edit_start_index = 0, multiple_edits = 0; |         int i, edit_start_index = 0, multiple_edits = 0; | ||||||
| @@ -3647,6 +3648,28 @@ static void mov_build_index(MOVContext *mov, AVStream *st) | |||||||
|         } |         } | ||||||
|         st->index_entries_allocated_size = (st->nb_index_entries + sc->sample_count) * sizeof(*st->index_entries); |         st->index_entries_allocated_size = (st->nb_index_entries + sc->sample_count) * sizeof(*st->index_entries); | ||||||
|  |  | ||||||
|  |         if (ctts_data_old) { | ||||||
|  |             // Expand ctts entries such that we have a 1-1 mapping with samples | ||||||
|  |             if (sc->sample_count >= UINT_MAX / sizeof(*sc->ctts_data)) | ||||||
|  |                 return; | ||||||
|  |             sc->ctts_count = 0; | ||||||
|  |             sc->ctts_allocated_size = 0; | ||||||
|  |             sc->ctts_data = av_fast_realloc(NULL, &sc->ctts_allocated_size, | ||||||
|  |                                     sc->sample_count * sizeof(*sc->ctts_data)); | ||||||
|  |             if (!sc->ctts_data) { | ||||||
|  |                 av_free(ctts_data_old); | ||||||
|  |                 return; | ||||||
|  |             } | ||||||
|  |             for (i = 0; i < ctts_count_old && | ||||||
|  |                         sc->ctts_count < sc->sample_count; i++) | ||||||
|  |                 for (j = 0; j < ctts_data_old[i].count && | ||||||
|  |                             sc->ctts_count < sc->sample_count; j++) | ||||||
|  |                     add_ctts_entry(&sc->ctts_data, &sc->ctts_count, | ||||||
|  |                                    &sc->ctts_allocated_size, 1, | ||||||
|  |                                    ctts_data_old[i].duration); | ||||||
|  |             av_free(ctts_data_old); | ||||||
|  |         } | ||||||
|  |  | ||||||
|         for (i = 0; i < sc->chunk_count; i++) { |         for (i = 0; i < sc->chunk_count; i++) { | ||||||
|             int64_t next_offset = i+1 < sc->chunk_count ? sc->chunk_offsets[i+1] : INT64_MAX; |             int64_t next_offset = i+1 < sc->chunk_count ? sc->chunk_offsets[i+1] : INT64_MAX; | ||||||
|             current_offset = sc->chunk_offsets[i]; |             current_offset = sc->chunk_offsets[i]; | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user