av1/encoder/encode_strategy.c
// Apply temporal filtering to key frames and encode the filtered frame.
// If the current frame is not key frame, this function is identical to
// av1_encode().
Apply temporal filtering to key frames and encode the filtered frame.
If the current frame is not key frame, this function is identical to
av1_encode().
Apply temporal filtering to key frames and encode the filtered frame . If the current frame is not key frame this function is identical to av1_encode () .
static int denoise_and_encode(AV1_COMP *const cpi, uint8_t *const dest,
                              EncodeFrameInput *const frame_input,
                              EncodeFrameParams *const frame_params,
                              EncodeFrameResults *const frame_results,
                              int *temporal_filtered) {
  if (frame_params->frame_type != KEY_FRAME ||
      !cpi->oxcf.enable_keyframe_filtering) {
    if (av1_encode(cpi, dest, frame_input, frame_params, frame_results) !=
        AOM_CODEC_OK) {
      return AOM_CODEC_ERROR;
    }
    return AOM_CODEC_OK;
  }
  const AV1EncoderConfig *const oxcf = &cpi->oxcf;
  AV1_COMMON *const cm = &cpi->common;
  const int num_planes = av1_num_planes(cm);
  const double y_noise_level = av1_estimate_noise_from_single_plane(
      frame_input->source, 0, cm->seq_params.bit_depth);
  const int apply_filtering =
      !is_stat_generation_stage(cpi) && frame_params->frame_type == KEY_FRAME &&
      !frame_params->show_existing_frame &&
      cpi->rc.frames_to_key > TF_NUM_FILTERING_FRAMES_FOR_KEY_FRAME &&
      y_noise_level > 0 && !is_lossless_requested(oxcf) &&
      oxcf->arnr_max_frames > 0;
  YV12_BUFFER_CONFIG *source_kf_buffer = frame_input->source;
  if (apply_filtering) {
    MACROBLOCKD *const xd = &cpi->td.mb.e_mbd;
    av1_init_context_buffers(cm);
    setup_mi(cpi, frame_input->source);
    av1_init_macroblockd(cm, xd, NULL);
    const int ext_mi_size = cm->mi_alloc_rows * cm->mi_alloc_cols;
    memset(cpi->mbmi_ext_frame_base, 0,
           ext_mi_size * sizeof(*cpi->mbmi_ext_frame_base));
    av1_set_speed_features_framesize_independent(cpi, oxcf->speed);
    av1_set_speed_features_framesize_dependent(cpi, oxcf->speed);
    av1_set_rd_speed_thresholds(cpi);
    av1_setup_frame_buf_refs(cm);
    av1_setup_frame_sign_bias(cm);
    av1_frame_init_quantizer(cpi);
    av1_setup_past_independence(cm);
    if (!frame_params->show_frame) {
      int arf_src_index = get_arf_src_index(&cpi->gf_group, cpi->oxcf.pass);
      av1_temporal_filter(cpi, -1 * arf_src_index, NULL);
    } else {
      av1_temporal_filter(cpi, -1, NULL);
    }
    aom_extend_frame_borders(&cpi->alt_ref_buffer, num_planes);
    frame_input->source = &cpi->alt_ref_buffer;
    aom_remove_metadata_from_frame_buffer(frame_input->source);
    aom_copy_metadata_to_frame_buffer(frame_input->source,
                                      source_kf_buffer->metadata);
    *temporal_filtered = 1;
  }
  if (oxcf->lag_in_frames > 0 && !is_stat_generation_stage(cpi) &&
      frame_params->frame_type == KEY_FRAME && frame_params->show_frame) {
    av1_configure_buffer_updates(cpi, frame_params, KEY_FRAME, 0);
    av1_set_frame_size(cpi, cm->width, cm->height);
    av1_set_speed_features_framesize_independent(cpi, oxcf->speed);
    if (cpi->oxcf.enable_tpl_model) {
      av1_tpl_setup_stats(cpi, 0, frame_params, frame_input);
    }
  }
  if (av1_encode(cpi, dest, frame_input, frame_params, frame_results) !=
      AOM_CODEC_OK) {
    return AOM_CODEC_ERROR;
  }
  if (oxcf->arnr_max_frames > 0 && *temporal_filtered) {
    cpi->source = source_kf_buffer;
    cpi->unscaled_source = source_kf_buffer;
  }
  return AOM_CODEC_OK;
}
static int denoise_and_encode ( AV1_COMP * const cpi , uint8_t * const dest , EncodeFrameInput * const frame_input , EncodeFrameParams * const frame_params , EncodeFrameResults * const frame_results , int * temporal_filtered ) { if ( frame_params -> frame_type != KEY_FRAME || ! cpi -> oxcf . enable_keyframe_filtering ) { if ( av1_encode ( cpi , dest , frame_input , frame_params , frame_results ) != AOM_CODEC_OK ) { return AOM_CODEC_ERROR ; } return AOM_CODEC_OK ; } const AV1EncoderConfig * const oxcf = & cpi -> oxcf ; AV1_COMMON * const cm = & cpi -> common ; const int num_planes = av1_num_planes ( cm ) ; const double y_noise_level = av1_estimate_noise_from_single_plane ( frame_input -> source , 0 , cm -> seq_params . bit_depth ) ; const int apply_filtering = ! is_stat_generation_stage ( cpi ) && frame_params -> frame_type == KEY_FRAME && ! frame_params -> show_existing_frame && cpi -> rc . frames_to_key > TF_NUM_FILTERING_FRAMES_FOR_KEY_FRAME && y_noise_level > 0 && ! is_lossless_requested ( oxcf ) && oxcf -> arnr_max_frames > 0 ; YV12_BUFFER_CONFIG * source_kf_buffer = frame_input -> source ; if ( apply_filtering ) { MACROBLOCKD * const xd = & cpi -> td . mb . e_mbd ; av1_init_context_buffers ( cm ) ; setup_mi ( cpi , frame_input -> source ) ; av1_init_macroblockd ( cm , xd , NULL ) ; const int ext_mi_size = cm -> mi_alloc_rows * cm -> mi_alloc_cols ; memset ( cpi -> mbmi_ext_frame_base , 0 , ext_mi_size * sizeof ( * cpi -> mbmi_ext_frame_base ) ) ; av1_set_speed_features_framesize_independent ( cpi , oxcf -> speed ) ; av1_set_speed_features_framesize_dependent ( cpi , oxcf -> speed ) ; av1_set_rd_speed_thresholds ( cpi ) ; av1_setup_frame_buf_refs ( cm ) ; av1_setup_frame_sign_bias ( cm ) ; av1_frame_init_quantizer ( cpi ) ; av1_setup_past_independence ( cm ) ; if ( ! frame_params -> show_frame ) { int arf_src_index = get_arf_src_index ( & cpi -> gf_group , cpi -> oxcf . pass ) ; av1_temporal_filter ( cpi , -1 * arf_src_index , NULL ) ; } else { av1_temporal_filter ( cpi , -1 , NULL ) ; } aom_extend_frame_borders ( & cpi -> alt_ref_buffer , num_planes ) ; frame_input -> source = & cpi -> alt_ref_buffer ; aom_remove_metadata_from_frame_buffer ( frame_input -> source ) ; aom_copy_metadata_to_frame_buffer ( frame_input -> source , source_kf_buffer -> metadata ) ; * temporal_filtered = 1 ; } if ( oxcf -> lag_in_frames > 0 && ! is_stat_generation_stage ( cpi ) && frame_params -> frame_type == KEY_FRAME && frame_params -> show_frame ) { av1_configure_buffer_updates ( cpi , frame_params , KEY_FRAME , 0 ) ; av1_set_frame_size ( cpi , cm -> width , cm -> height ) ; av1_set_speed_features_framesize_independent ( cpi , oxcf -> speed ) ; if ( cpi -> oxcf . enable_tpl_model ) { av1_tpl_setup_stats ( cpi , 0 , frame_params , frame_input ) ; } } if ( av1_encode ( cpi , dest , frame_input , frame_params , frame_results ) != AOM_CODEC_OK ) { return AOM_CODEC_ERROR ; } if ( oxcf -> arnr_max_frames > 0 && * temporal_filtered ) { cpi -> source = source_kf_buffer ; cpi -> unscaled_source = source_kf_buffer ; } return AOM_CODEC_OK ; }
Apply temporal filtering to key frames and encode the filtered frame.
Apply temporal filtering to key frames and encode the filtered frame .
// Save the pointer to the original source image. // Apply filtering to key frame and encode. // Initialization for frame motion estimation. // Use the filtered frame for encoding. // Copy metadata info to alt-ref buffer. // Set frame_input source to true source for psnr calculation.