Modify Lookahead queue API Modified Lookahead queue context and API, to facilitate multiple consumers to independently pop entries pushed into the queue. Change-Id: I20f5a1894c30bcf169f5d0b621bc4d5daa413015
diff --git a/av1/encoder/encode_strategy.c b/av1/encoder/encode_strategy.c index 808bb9b..b2238f5 100644 --- a/av1/encoder/encode_strategy.c +++ b/av1/encoder/encode_strategy.c
@@ -416,7 +416,7 @@ *code_arf = 0; struct lookahead_entry *source = - av1_lookahead_peek(cpi->lookahead, arf_src_index); + av1_lookahead_peek(cpi->lookahead, arf_src_index, ENCODE_STAGE); if (source != NULL) { cm->showable_frame = 1; @@ -454,7 +454,8 @@ static int is_forced_keyframe_pending(struct lookahead_ctx *lookahead, const int up_to_index) { for (int i = 0; i <= up_to_index; i++) { - const struct lookahead_entry *e = av1_lookahead_peek(lookahead, i); + const struct lookahead_entry *e = + av1_lookahead_peek(lookahead, i, ENCODE_STAGE); if (e == NULL) { // We have reached the end of the lookahead buffer and not early-returned // so there isn't a forced key-frame pending. @@ -495,10 +496,10 @@ if (!source) { // Get last frame source. if (cm->current_frame.frame_number > 0) { - *last_source = av1_lookahead_peek(cpi->lookahead, -1); + *last_source = av1_lookahead_peek(cpi->lookahead, -1, ENCODE_STAGE); } // Read in the source frame. - source = av1_lookahead_pop(cpi->lookahead, *flush); + source = av1_lookahead_pop(cpi->lookahead, *flush, ENCODE_STAGE); if (source == NULL) return NULL; frame_params->show_frame = 1; @@ -516,7 +517,7 @@ if (cpi->common.current_frame.frame_number == 0) return 0; const struct lookahead_entry *lookahead_src = - av1_lookahead_peek(cpi->lookahead, 0); + av1_lookahead_peek(cpi->lookahead, 0, ENCODE_STAGE); if (lookahead_src == NULL) return 1; const int is_error_resilient = @@ -1150,7 +1151,7 @@ struct lookahead_entry *source = NULL; struct lookahead_entry *last_source = NULL; if (frame_params.show_existing_frame) { - source = av1_lookahead_pop(cpi->lookahead, flush); + source = av1_lookahead_pop(cpi->lookahead, flush, ENCODE_STAGE); frame_params.show_frame = 1; } else { int show_existing_alt_ref = 0;
diff --git a/av1/encoder/firstpass.c b/av1/encoder/firstpass.c index edf4276..d5df0a7 100644 --- a/av1/encoder/firstpass.c +++ b/av1/encoder/firstpass.c
@@ -333,7 +333,7 @@ const int alt_offset = 16 - (current_frame->frame_number % 16); if (alt_offset < 16) { const struct lookahead_entry *const alt_buf = - av1_lookahead_peek(cpi->lookahead, alt_offset); + av1_lookahead_peek(cpi->lookahead, alt_offset, ENCODE_STAGE); if (alt_buf != NULL) { alt_yv12 = &alt_buf->img; }
diff --git a/av1/encoder/lookahead.c b/av1/encoder/lookahead.c index 4dd7318..7a42f17 100644 --- a/av1/encoder/lookahead.c +++ b/av1/encoder/lookahead.c
@@ -60,6 +60,8 @@ const int legacy_byte_alignment = 0; unsigned int i; ctx->max_sz = depth; + ctx->read_ctxs[ENCODE_STAGE].pop_sz = ctx->max_sz - MAX_PRE_FRAMES; + ctx->read_ctxs[ENCODE_STAGE].valid = 1; ctx->buf = calloc(depth, sizeof(*ctx->buf)); if (!ctx->buf) goto fail; for (i = 0; i < depth; i++) @@ -102,8 +104,10 @@ int subsampling_y = src->subsampling_y; int larger_dimensions, new_dimensions; - if (ctx->sz + 1 + MAX_PRE_FRAMES > ctx->max_sz) return 1; - ctx->sz++; + assert(ctx->read_ctxs[ENCODE_STAGE].valid == 1); + if (ctx->read_ctxs[ENCODE_STAGE].sz + 1 + MAX_PRE_FRAMES > ctx->max_sz) + return 1; + ctx->read_ctxs[ENCODE_STAGE].sz++; buf = pop(ctx, &ctx->write_idx); new_dimensions = width != buf->img.y_crop_width || @@ -186,35 +190,41 @@ return 0; } -struct lookahead_entry *av1_lookahead_pop(struct lookahead_ctx *ctx, - int drain) { +struct lookahead_entry *av1_lookahead_pop(struct lookahead_ctx *ctx, int drain, + COMPRESSOR_STAGE stage) { struct lookahead_entry *buf = NULL; - - if (ctx && ctx->sz && (drain || ctx->sz == ctx->max_sz - MAX_PRE_FRAMES)) { - buf = pop(ctx, &ctx->read_idx); - ctx->sz--; + if (ctx) { + struct read_ctx *read_ctx = &ctx->read_ctxs[stage]; + assert(read_ctx->valid == 1); + if (read_ctx->sz && (drain || read_ctx->sz == read_ctx->pop_sz)) { + buf = pop(ctx, &read_ctx->read_idx); + read_ctx->sz--; + } } return buf; } -struct lookahead_entry *av1_lookahead_peek(struct lookahead_ctx *ctx, - int index) { +struct lookahead_entry *av1_lookahead_peek(struct lookahead_ctx *ctx, int index, + COMPRESSOR_STAGE stage) { struct lookahead_entry *buf = NULL; - + struct read_ctx *read_ctx = NULL; if (ctx == NULL) { return buf; } + + read_ctx = &ctx->read_ctxs[stage]; + assert(read_ctx->valid == 1); if (index >= 0) { // Forward peek - if (index < ctx->sz) { - index += ctx->read_idx; + if (index < read_ctx->sz) { + index += read_ctx->read_idx; if (index >= ctx->max_sz) index -= ctx->max_sz; buf = ctx->buf + index; } } else if (index < 0) { // Backward peek if (-index <= MAX_PRE_FRAMES) { - index += (int)(ctx->read_idx); + index += (int)(read_ctx->read_idx); if (index < 0) index += (int)(ctx->max_sz); buf = ctx->buf + index; } @@ -223,7 +233,12 @@ return buf; } -unsigned int av1_lookahead_depth(struct lookahead_ctx *ctx) { +unsigned int av1_lookahead_depth(struct lookahead_ctx *ctx, + COMPRESSOR_STAGE stage) { + struct read_ctx *read_ctx = NULL; assert(ctx != NULL); - return ctx->sz; + + read_ctx = &ctx->read_ctxs[stage]; + assert(read_ctx->valid == 1); + return read_ctx->sz; }
diff --git a/av1/encoder/lookahead.h b/av1/encoder/lookahead.h index 3b2d94b..7881345 100644 --- a/av1/encoder/lookahead.h +++ b/av1/encoder/lookahead.h
@@ -31,12 +31,20 @@ // The max of past frames we want to keep in the queue. #define MAX_PRE_FRAMES 1 +enum { ENCODE_STAGE, MAX_STAGES } UENUM1BYTE(COMPRESSOR_STAGE); + +struct read_ctx { + int sz; /* Number of buffers currently in the queue */ + int read_idx; /* Read index */ + int pop_sz; /* Size to check for pop condition */ + int valid; /* Is this ctx valid? */ +}; + struct lookahead_ctx { - int max_sz; /* Absolute size of the queue */ - int sz; /* Number of buffers currently in the queue */ - int read_idx; /* Read index */ - int write_idx; /* Write index */ - struct lookahead_entry *buf; /* Buffer list */ + int max_sz; /* Absolute size of the queue */ + int write_idx; /* Write index */ + struct read_ctx read_ctxs[MAX_STAGES]; /* Read context */ + struct lookahead_entry *buf; /* Buffer list */ }; /**\brief Initializes the lookahead stage @@ -82,7 +90,8 @@ * \retval NULL, if drain set and queue is empty * \retval NULL, if drain not set and queue not of the configured depth */ -struct lookahead_entry *av1_lookahead_pop(struct lookahead_ctx *ctx, int drain); +struct lookahead_entry *av1_lookahead_pop(struct lookahead_ctx *ctx, int drain, + COMPRESSOR_STAGE stage); /**\brief Get a future source buffer to encode * @@ -91,14 +100,15 @@ * * \retval NULL, if no buffer exists at the specified index */ -struct lookahead_entry *av1_lookahead_peek(struct lookahead_ctx *ctx, - int index); +struct lookahead_entry *av1_lookahead_peek(struct lookahead_ctx *ctx, int index, + COMPRESSOR_STAGE stage); /**\brief Get the number of frames currently in the lookahead queue * * \param[in] ctx Pointer to the lookahead context */ -unsigned int av1_lookahead_depth(struct lookahead_ctx *ctx); +unsigned int av1_lookahead_depth(struct lookahead_ctx *ctx, + COMPRESSOR_STAGE stage); #ifdef __cplusplus } // extern "C"
diff --git a/av1/encoder/mbgraph.c b/av1/encoder/mbgraph.c index 0cb6286..d45bb8da 100644 --- a/av1/encoder/mbgraph.c +++ b/av1/encoder/mbgraph.c
@@ -363,7 +363,7 @@ void av1_update_mbgraph_stats(AV1_COMP *cpi) { AV1_COMMON *const cm = &cpi->common; - int i, n_frames = av1_lookahead_depth(cpi->lookahead); + int i, n_frames = av1_lookahead_depth(cpi->lookahead, ENCODE_STAGE); YV12_BUFFER_CONFIG *golden_ref = &get_ref_frame_buf(cm, GOLDEN_FRAME)->buf; assert(golden_ref != NULL); @@ -387,7 +387,8 @@ // the ARF MC search backwards, to get optimal results for MV caching for (i = 0; i < n_frames; i++) { MBGRAPH_FRAME_STATS *frame_stats = &cpi->mbgraph_stats[i]; - struct lookahead_entry *q_cur = av1_lookahead_peek(cpi->lookahead, i); + struct lookahead_entry *q_cur = + av1_lookahead_peek(cpi->lookahead, i, ENCODE_STAGE); assert(q_cur != NULL);
diff --git a/av1/encoder/temporal_filter.c b/av1/encoder/temporal_filter.c index 7b8f8b3..9be19cd 100644 --- a/av1/encoder/temporal_filter.c +++ b/av1/encoder/temporal_filter.c
@@ -1459,7 +1459,8 @@ q = ((int)av1_convert_qindex_to_q(cpi->rc.avg_frame_qindex[KEY_FRAME], cpi->common.seq_params.bit_depth)); MACROBLOCKD *mbd = &cpi->td.mb.e_mbd; - struct lookahead_entry *buf = av1_lookahead_peek(cpi->lookahead, distance); + struct lookahead_entry *buf = + av1_lookahead_peek(cpi->lookahead, distance, ENCODE_STAGE); int strength; double noiselevel; if (is_cur_buf_hbd(mbd)) { @@ -1516,7 +1517,7 @@ } const int frames_after_arf = - av1_lookahead_depth(cpi->lookahead) - distance - 1; + av1_lookahead_depth(cpi->lookahead, ENCODE_STAGE) - distance - 1; int frames_fwd = (frames - 1) >> 1; int frames_bwd = frames >> 1; @@ -1600,7 +1601,7 @@ for (frame = 0; frame < frames_to_blur; ++frame) { const int which_buffer = start_frame - frame; struct lookahead_entry *buf = - av1_lookahead_peek(cpi->lookahead, which_buffer); + av1_lookahead_peek(cpi->lookahead, which_buffer, ENCODE_STAGE); if (buf == NULL) { frames[frames_to_blur - 1 - frame] = NULL; } else {
diff --git a/av1/encoder/tpl_model.c b/av1/encoder/tpl_model.c index 3d5e909..7c5fabf 100644 --- a/av1/encoder/tpl_model.c +++ b/av1/encoder/tpl_model.c
@@ -571,7 +571,8 @@ const GF_GROUP *gf_group = &cpi->gf_group; const int frame_disp_idx = gf_group->frame_disp_idx[frame_idx]; struct lookahead_entry *buf = av1_lookahead_peek( - cpi->lookahead, frame_disp_idx - cpi->num_gf_group_show_frames); + cpi->lookahead, frame_disp_idx - cpi->num_gf_group_show_frames, + ENCODE_STAGE); return &buf->img; } } @@ -805,8 +806,8 @@ int frame_display_index = gf_index == gf_group->size ? cpi->rc.baseline_gf_interval : gf_group->frame_disp_idx[gf_index]; - struct lookahead_entry *buf = - av1_lookahead_peek(cpi->lookahead, frame_display_index - 1); + struct lookahead_entry *buf = av1_lookahead_peek( + cpi->lookahead, frame_display_index - 1, ENCODE_STAGE); if (buf == NULL) break; tpl_frame->gf_picture = &buf->img; // frame display index = frame offset within the gf group + start frame of @@ -848,8 +849,8 @@ frame_update_type == INTNL_OVERLAY_UPDATE; frame_params.frame_type = INTER_FRAME; - struct lookahead_entry *buf = - av1_lookahead_peek(cpi->lookahead, frame_display_index - 1); + struct lookahead_entry *buf = av1_lookahead_peek( + cpi->lookahead, frame_display_index - 1, ENCODE_STAGE); if (buf == NULL) break;