add config file options support

clean up and update config file options support and allow passing control
flags through config file to turn on/off individual coding tool for tool
on and tool off testing

Change-Id: I2c68773d3bce6f7eb70990d4fbdc34fab32dcc80
diff --git a/Sample.cfg b/Sample.cfg
new file mode 100644
index 0000000..f37df0a
--- /dev/null
+++ b/Sample.cfg
@@ -0,0 +1,36 @@
+#sample config file
+super_block_size = 128                  #super block size. 0, 64 or 128
+max_partition_size = 128                #max partition size(8, 16, 32, 64, 128)
+min_partition_size = 4                  #min partition size(4, 8, 16, 32, 64)
+disable_rect_partition_type = 0         #disable rectangle partition type
+disable_ab_partition_type = 0           #disable AB partition type
+disable_1to4_partition_type = 0         #disable 1to4 and 4to1 partition type
+disable_intra_angle_delta = 0           #disable intra angle delta
+disable_paeth_intra = 0                 #disable paeth intra
+disable_smooth_intra = 0                #disable intra smooth mode
+disable_intra_edge_filter = 0           #disable intra edge filter
+disable_filter_intra = 0                #disable filter intra
+disable_ibc = 0                         #disable Intra Block Copy
+disable_cfl = 0                         #disable chroma from luma prediction
+disable_palette = 0                     #disable Palette
+disable_flip_idtx = 0                   #disable flip and identity transform
+disable_tx_64x64 = 0                    #disable 64x64 transform
+reduced_tx_type_set = 0                 #use reduced transform type set
+tx_size_search_method = 0               #0:FULL_RD, 1 : FAST_RD, 2 : USE_LARGEST
+reduced_reference_set = 0               #use reduced reference frame set
+disable_obmc = 0                        #disable OBMC
+disable_warp_motion = 0                 #disable Warped Motion
+disable_global_motion = 0               #disable global motion
+disable_ref_frame_mv = 0                #disable ref mv
+disable_dual_filter = 0                 #disable dual interpolation filter
+disable_one_sided_comp = 0              #disable one sided compound mode
+disable_masked_comp = 0                 #disable masked compound prediction
+disable_diff_wtd_comp = 0               #disable difference weighted compound mode
+disable_inter_inter_wedge = 0           #disable inter/inter wedge comp
+disable_dist_wtd_comp = 0               #disable distant weighted compound mode
+disable_inter_intra_comp = 0            #disable inter/intra compound mode.
+disable_inter_intra_wedge = 0           #disable inter/intra wedge comp
+disable_smooth_inter_intra = 0          #disable smooth inter/intra
+disable_cdef = 0                        #disable CDEF filter
+disable_lr = 0                          #disable Loop Resotoration Filter
+disable_trellis_quant = 0               #disable trellis quantizaiton
\ No newline at end of file
diff --git a/aom/aom_codec.h b/aom/aom_codec.h
index fc0df5b..6773e07 100644
--- a/aom/aom_codec.h
+++ b/aom/aom_codec.h
@@ -503,19 +503,6 @@
  */
 const char *aom_obu_type_to_string(OBU_TYPE type);
 
-/*!\brief Config Options
- *
- * This type allows to enumerate and control options defined for control
- * via config file at runtime.
- */
-typedef struct cfg_options {
-  /*!\brief Reflects if ext_partition should be enabled
-   *
-   * If this value is non-zero it enabled the feature
-   */
-  unsigned int ext_partition;
-} cfg_options_t;
-
 /*!@} - end defgroup codec*/
 #ifdef __cplusplus
 }
diff --git a/aom/aom_decoder.h b/aom/aom_decoder.h
index 70420c3..6023564 100644
--- a/aom/aom_decoder.h
+++ b/aom/aom_decoder.h
@@ -98,7 +98,6 @@
   unsigned int w;       /**< Width */
   unsigned int h;       /**< Height */
   unsigned int allow_lowbitdepth; /**< Allow use of low-bitdepth coding path */
-  cfg_options_t cfg;              /**< Options defined per config attributes */
 } aom_codec_dec_cfg_t;            /**< alias for struct aom_codec_dec_cfg */
 
 /*!\brief Initialize a decoder instance
diff --git a/aom/aom_encoder.h b/aom/aom_encoder.h
index 1ee728a..66e87b0 100644
--- a/aom/aom_encoder.h
+++ b/aom/aom_encoder.h
@@ -209,6 +209,158 @@
   AOM_KF_DISABLED = 0 /**< Encoder does not place keyframes. */
 };
 
+/*!\brief Encoder Config Options
+ *
+ * This type allows to enumerate and control flags defined for encoder control
+ * via config file at runtime.
+ */
+typedef struct cfg_options {
+  /*!\brief Indicate init by cfg file
+   * 0 or 1
+   */
+  unsigned int init_by_cfg_file;
+  /*!\brief Superblock size
+   * 0, 64 or 128
+   */
+  unsigned int super_block_size;
+  /*!\brief max partition size
+   * 8, 16, 32, 64, 128
+   */
+  unsigned int max_partition_size;
+  /*!\brief min partition size
+   * 8, 16, 32, 64, 128
+   */
+  unsigned int min_partition_size;
+  /*!\brief disable AB Shape partition type
+   *
+   */
+  unsigned int disable_ab_partition_type;
+  /*!\brief disable rectangular partition type
+   *
+   */
+  unsigned int disable_rect_partition_type;
+  /*!\brief disable 1:4/4:1 partition type
+   *
+   */
+  unsigned int disable_1to4_partition_type;
+  /*!\brief disable flip and identity transform type
+   *
+   */
+  unsigned int disable_flip_idtx;
+  /*!\brief disable CDEF filter
+   *
+   */
+  unsigned int disable_cdef;
+  /*!\brief disable Loop Restoration Filter
+   *
+   */
+  unsigned int disable_lr;
+  /*!\brief disable OBMC
+   *
+   */
+  unsigned int disable_obmc;
+  /*!\brief disable Warped Motion
+   *
+   */
+  unsigned int disable_warp_motion;
+  /*!\brief disable global motion
+   *
+   */
+  unsigned int disable_global_motion;
+  /*!\brief disable dist weighted compound
+   *
+   */
+  unsigned int disable_dist_wtd_comp;
+  /*!\brief disable diff weighted compound
+   *
+   */
+  unsigned int disable_diff_wtd_comp;
+  /*!\brief disable inter/intra compound
+   *
+   */
+  unsigned int disable_inter_intra_comp;
+  /*!\brief disable masked compound
+   *
+   */
+  unsigned int disable_masked_comp;
+  /*!\brief disable one sided compound
+   *
+   */
+  unsigned int disable_one_sided_comp;
+  /*!\brief disable Palette
+   *
+   */
+  unsigned int disable_palette;
+  /*!\brief disable Intra Block Copy
+   *
+   */
+  unsigned int disable_ibc;
+  /*!\brief disable chroma from luma
+   *
+   */
+  unsigned int disable_cfl;
+  /*!\brief disable intra smooth mode
+   *
+   */
+  unsigned int disable_smooth_intra;
+  /*!\brief disable filter intra
+   *
+   */
+  unsigned int disable_filter_intra;
+  /*!\brief disable dual filter
+   *
+   */
+  unsigned int disable_dual_filter;
+  /*!\brief disable intra angle delta
+   *
+   */
+  unsigned int disable_intra_angle_delta;
+  /*!\brief specify transform size search method
+   * 0:FULLRD,1:FASTRD,2:USELARGEST
+   */
+  unsigned int tx_size_search_method;
+  /*!\brief disable intra edge filter
+   *
+   */
+  unsigned int disable_intra_edge_filter;
+  /*!\brief disable 64x64 transform
+   *
+   */
+  unsigned int disable_tx_64x64;
+  /*!\brief disable smooth inter/intra
+   *
+   */
+  unsigned int disable_smooth_inter_intra;
+  /*!\brief disable inter/inter wedge comp
+   *
+   */
+  unsigned int disable_inter_inter_wedge;
+  /*!\brief disable inter/intra wedge comp
+   *
+   */
+  unsigned int disable_inter_intra_wedge;
+  /*!\brief disable paeth intra
+   *
+   */
+  unsigned int disable_paeth_intra;
+  /*!\brief disable trellis quantizaiton
+   *
+   */
+  unsigned int disable_trellis_quant;
+  /*!\brief disable ref frame MV
+   *
+   */
+  unsigned int disable_ref_frame_mv;
+  /*!\brief use reduced reference frame set
+   *
+   */
+  unsigned int reduced_reference_set;
+  /*!\brief use reduced transform type set
+   *
+   */
+  unsigned int reduced_tx_type_set;
+} cfg_options_t;
+
 /*!\brief Encoded Frame Flags
  *
  * This type indicates a bitfield to be passed to aom_codec_encode(), defining
@@ -727,7 +879,7 @@
   /*!\brief Options defined per config file
    *
    */
-  cfg_options_t cfg;
+  cfg_options_t encoder_cfg;
 } aom_codec_enc_cfg_t; /**< alias for struct aom_codec_enc_cfg */
 
 /*!\brief Initialize an encoder instance
diff --git a/aom/src/aom_encoder.c b/aom/src/aom_encoder.c
index 9de8c06..35d705a 100644
--- a/aom/src/aom_encoder.c
+++ b/aom/src/aom_encoder.c
@@ -24,8 +24,11 @@
 
 #include <limits.h>
 #include <string.h>
+#include "aom/aom_encoder.h"
 #include "aom/internal/aom_codec_internal.h"
 
+extern void init_config(cfg_options_t *pConfig);
+
 #define SAVE_STATUS(ctx, var) (ctx ? (ctx->err = var) : var)
 
 static aom_codec_alg_priv_t *get_alg_priv(aom_codec_ctx_t *ctx) {
@@ -167,10 +170,12 @@
     }
   }
 
+#if CONFIG_FILEOPTIONS
   /* default values */
   if (cfg) {
-    cfg->cfg.ext_partition = 1;
+    init_config(&cfg->encoder_cfg);
   }
+#endif
 
   return res;
 }
diff --git a/apps/aomdec.c b/apps/aomdec.c
index f229078..acecc90 100644
--- a/apps/aomdec.c
+++ b/apps/aomdec.c
@@ -451,7 +451,7 @@
   int opt_yv12 = 0;
   int opt_i420 = 0;
   int opt_raw = 0;
-  aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING, { 1 } };
+  aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING };
   unsigned int fixed_output_bit_depth = 0;
   unsigned int is_annexb = 0;
   int frames_corrupted = 0;
diff --git a/apps/aomenc.c b/apps/aomenc.c
index 4630157..27c85c0 100644
--- a/apps/aomenc.c
+++ b/apps/aomenc.c
@@ -160,8 +160,6 @@
     ARG_DEF(NULL, "psnr", 0, "Show PSNR in status line");
 #if CONFIG_FILEOPTIONS
 static const arg_def_t use_cfg = ARG_DEF("c", "cfg", 1, "Config file to use");
-static const arg_def_t ext_partition =
-    ARG_DEF(NULL, "ext-partition", 1, "corresponds to extended partitions");
 #endif
 
 static const struct arg_enum_list test_decode_enum[] = {
@@ -1123,15 +1121,12 @@
 /* Parses global config arguments into the AvxEncoderConfig. Note that
  * argv is modified and overwrites all parsed arguments.
  */
-static void parse_global_config(struct AvxEncoderConfig *global, int argc,
-                                char ***argv) {
+static void parse_global_config(struct AvxEncoderConfig *global, char ***argv) {
   char **argi, **argj;
   struct arg arg;
   const int num_encoder = get_aom_encoder_count();
   char **argv_local = (char **)*argv;
-#if CONFIG_FILEOPTIONS
-  int argc_local = argc;
-#endif
+
   if (num_encoder < 1) die("Error: no valid encoder available\n");
 
   /* Initialize default parameters */
@@ -1142,22 +1137,17 @@
   global->csp = AOM_CSP_UNKNOWN;
 
 #if CONFIG_FILEOPTIONS
-  const char *cfg = NULL;
   int cfg_included = 0;
+  init_config(&global->encoder_config);
 #endif
+
   for (argi = argj = argv_local; (*argj = *argi); argi += arg.argv_step) {
     arg.argv_step = 1;
 
 #if CONFIG_FILEOPTIONS
     if (arg_match(&arg, &use_cfg, argi)) {
       if (cfg_included) continue;
-      cfg = arg.val;
-
-      arg_cfg(&argc_local, &argv_local, cfg);
-
-      *argj = *argi = *argv_local;
-      argj = argi = argv_local;
-      *argv = argv_local;
+      parse_cfg(arg.val, &global->encoder_config);
       cfg_included = 1;
       continue;
     }
@@ -1353,6 +1343,11 @@
 
     /* Allows removal of the application version from the EBML tags */
     stream->webm_ctx.debug = global->debug;
+
+#if CONFIG_FILEOPTIONS
+    memcpy(&stream->config.cfg.encoder_cfg, &global->encoder_config,
+           sizeof(cfg_options_t));
+#endif
   }
 
   /* Output files must be specified for each stream */
@@ -1577,10 +1572,6 @@
     } else if (arg_match(&arg, &tile_height, argi)) {
       config->cfg.tile_height_count =
           arg_parse_list(&arg, config->cfg.tile_heights, MAX_TILE_HEIGHTS);
-#if CONFIG_FILEOPTIONS
-    } else if (arg_match(&arg, &ext_partition, argi)) {
-      config->cfg.cfg.ext_partition = !!arg_parse_uint(&arg) > 0;
-#endif
     } else if (global->usage == AOM_USAGE_REALTIME &&
                arg_match(&arg, &enable_restoration, argi)) {
       if (arg_parse_uint(&arg) == 1) {
@@ -1744,6 +1735,47 @@
   SHOW(kf_mode);
   SHOW(kf_min_dist);
   SHOW(kf_max_dist);
+
+#if CONFIG_FILEOPTIONS
+#define SHOW_PARAMS(field)                    \
+  fprintf(stderr, "    %-28s = %d\n", #field, \
+          stream->config.cfg.encoder_cfg.field)
+  SHOW_PARAMS(super_block_size);
+  SHOW_PARAMS(max_partition_size);
+  SHOW_PARAMS(min_partition_size);
+  SHOW_PARAMS(disable_ab_partition_type);
+  SHOW_PARAMS(disable_rect_partition_type);
+  SHOW_PARAMS(disable_1to4_partition_type);
+  SHOW_PARAMS(disable_flip_idtx);
+  SHOW_PARAMS(disable_cdef);
+  SHOW_PARAMS(disable_lr);
+  SHOW_PARAMS(disable_obmc);
+  SHOW_PARAMS(disable_warp_motion);
+  SHOW_PARAMS(disable_global_motion);
+  SHOW_PARAMS(disable_dist_wtd_comp);
+  SHOW_PARAMS(disable_diff_wtd_comp);
+  SHOW_PARAMS(disable_inter_intra_comp);
+  SHOW_PARAMS(disable_masked_comp);
+  SHOW_PARAMS(disable_one_sided_comp);
+  SHOW_PARAMS(disable_palette);
+  SHOW_PARAMS(disable_ibc);
+  SHOW_PARAMS(disable_cfl);
+  SHOW_PARAMS(disable_smooth_intra);
+  SHOW_PARAMS(disable_filter_intra);
+  SHOW_PARAMS(disable_dual_filter);
+  SHOW_PARAMS(disable_intra_angle_delta);
+  SHOW_PARAMS(tx_size_search_method);
+  SHOW_PARAMS(disable_intra_edge_filter);
+  SHOW_PARAMS(disable_tx_64x64);
+  SHOW_PARAMS(disable_smooth_inter_intra);
+  SHOW_PARAMS(disable_inter_inter_wedge);
+  SHOW_PARAMS(disable_inter_intra_wedge);
+  SHOW_PARAMS(disable_paeth_intra);
+  SHOW_PARAMS(disable_trellis_quant);
+  SHOW_PARAMS(disable_ref_frame_mv);
+  SHOW_PARAMS(reduced_reference_set);
+  SHOW_PARAMS(reduced_tx_type_set);
+#endif
 }
 
 static void open_output_file(struct stream_state *stream,
@@ -1857,7 +1889,7 @@
 #if CONFIG_AV1_DECODER
   if (global->test_decode != TEST_DECODE_OFF) {
     const AvxInterface *decoder = get_aom_decoder_by_name(global->codec->name);
-    aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING, { 1 } };
+    aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING };
     aom_codec_dec_init(&stream->decoder, decoder->codec_interface(), &cfg, 0);
 
     if (strcmp(global->codec->name, "av1") == 0) {
@@ -2195,7 +2227,7 @@
    * codec.
    */
   argv = argv_dup(argc - 1, argv_ + 1);
-  parse_global_config(&global, argc, &argv);
+  parse_global_config(&global, &argv);
 
 #if CONFIG_FILEOPTIONS
   if (argc < 2) usage_exit();
diff --git a/apps/aomenc.h b/apps/aomenc.h
index 5e59c1a..ba7bf0a 100644
--- a/apps/aomenc.h
+++ b/apps/aomenc.h
@@ -11,6 +11,7 @@
 #ifndef AOM_APPS_AOMENC_H_
 #define AOM_APPS_AOMENC_H_
 
+#include "aom/aom_codec.h"
 #include "aom/aom_encoder.h"
 
 #ifdef __cplusplus
@@ -54,6 +55,7 @@
   int disable_warning_prompt;
   int experimental_bitstream;
   aom_chroma_sample_position_t csp;
+  cfg_options_t encoder_config;
 };
 
 #ifdef __cplusplus
diff --git a/av1/av1_cx_iface.c b/av1/av1_cx_iface.c
index 6cacd8c..875a562 100644
--- a/av1/av1_cx_iface.c
+++ b/av1/av1_cx_iface.c
@@ -586,9 +586,61 @@
   oxcf->superres_kf_qthresh = 255;
 }
 
-static aom_codec_err_t set_encoder_config(
-    AV1EncoderConfig *oxcf, const aom_codec_enc_cfg_t *cfg,
-    const struct av1_extracfg *extra_cfg) {
+#if CONFIG_FILEOPTIONS
+static void update_default_encoder_config(const cfg_options_t *cfg,
+                                          struct av1_extracfg *extra_cfg) {
+  extra_cfg->enable_cdef = (cfg->disable_cdef == 0);
+  extra_cfg->enable_restoration = (cfg->disable_lr == 0);
+  extra_cfg->superblock_size = (cfg->super_block_size == 64)
+                                   ? AOM_SUPERBLOCK_SIZE_64X64
+                                   : (cfg->super_block_size == 128)
+                                         ? AOM_SUPERBLOCK_SIZE_128X128
+                                         : AOM_SUPERBLOCK_SIZE_DYNAMIC;
+  extra_cfg->enable_warped_motion = (cfg->disable_warp_motion == 0);
+  extra_cfg->enable_dist_wtd_comp = (cfg->disable_dist_wtd_comp == 0);
+  extra_cfg->enable_diff_wtd_comp = (cfg->disable_diff_wtd_comp == 0);
+  extra_cfg->enable_dual_filter = (cfg->disable_dual_filter == 0);
+  extra_cfg->enable_angle_delta = (cfg->disable_intra_angle_delta == 0);
+  extra_cfg->enable_rect_partitions = (cfg->disable_rect_partition_type == 0);
+  extra_cfg->enable_ab_partitions = (cfg->disable_ab_partition_type == 0);
+  extra_cfg->enable_1to4_partitions = (cfg->disable_1to4_partition_type == 0);
+  extra_cfg->max_partition_size = cfg->max_partition_size;
+  extra_cfg->min_partition_size = cfg->min_partition_size;
+  extra_cfg->enable_intra_edge_filter = (cfg->disable_intra_edge_filter == 0);
+  extra_cfg->enable_tx64 = (cfg->disable_tx_64x64 == 0);
+  extra_cfg->enable_flip_idtx = (cfg->disable_flip_idtx == 0);
+  extra_cfg->enable_masked_comp = (cfg->disable_masked_comp == 0);
+  extra_cfg->enable_interintra_comp = (cfg->disable_inter_intra_comp == 0);
+  extra_cfg->enable_smooth_interintra = (cfg->disable_smooth_inter_intra == 0);
+  extra_cfg->enable_interinter_wedge = (cfg->disable_inter_inter_wedge == 0);
+  extra_cfg->enable_interintra_wedge = (cfg->disable_inter_intra_wedge == 0);
+  extra_cfg->enable_global_motion = (cfg->disable_global_motion == 0);
+  extra_cfg->enable_filter_intra = (cfg->disable_filter_intra == 0);
+  extra_cfg->enable_smooth_intra = (cfg->disable_smooth_intra == 0);
+  extra_cfg->enable_paeth_intra = (cfg->disable_paeth_intra == 0);
+  extra_cfg->enable_cfl_intra = (cfg->disable_cfl == 0);
+  extra_cfg->enable_obmc = (cfg->disable_obmc == 0);
+  extra_cfg->enable_palette = (cfg->disable_palette == 0);
+  extra_cfg->enable_intrabc = (cfg->disable_ibc == 0);
+  extra_cfg->disable_trellis_quant = cfg->disable_trellis_quant;
+  extra_cfg->allow_ref_frame_mvs = (cfg->disable_ref_frame_mv == 0);
+  extra_cfg->enable_ref_frame_mvs = (cfg->disable_ref_frame_mv == 0);
+  extra_cfg->enable_onesided_comp = (cfg->disable_one_sided_comp == 0);
+  extra_cfg->tx_size_search_method = cfg->tx_size_search_method;
+  extra_cfg->enable_reduced_reference_set = cfg->reduced_reference_set;
+  extra_cfg->reduced_tx_type_set = cfg->reduced_tx_type_set;
+}
+#endif
+
+static aom_codec_err_t set_encoder_config(AV1EncoderConfig *oxcf,
+                                          const aom_codec_enc_cfg_t *cfg,
+                                          struct av1_extracfg *extra_cfg) {
+#if CONFIG_FILEOPTIONS
+  if (cfg->encoder_cfg.init_by_cfg_file) {
+    update_default_encoder_config(&cfg->encoder_cfg, extra_cfg);
+  }
+#endif
+
   const int is_vbr = cfg->rc_end_usage == AOM_VBR;
   oxcf->profile = cfg->g_profile;
   oxcf->fwd_kf_enabled = cfg->fwd_kf_enabled;
@@ -636,7 +688,9 @@
     oxcf->init_framerate = 30;
     oxcf->timing_info_present = 0;
   }
-  oxcf->cfg = &cfg->cfg;
+#if CONFIG_FILEOPTIONS
+  oxcf->encoder_cfg = &cfg->encoder_cfg;
+#endif
 
   switch (cfg->g_pass) {
     case AOM_RC_ONE_PASS: oxcf->pass = 0; break;
@@ -670,6 +724,7 @@
   oxcf->enable_intrabc = extra_cfg->enable_intrabc;
   oxcf->enable_angle_delta = extra_cfg->enable_angle_delta;
   oxcf->disable_trellis_quant = extra_cfg->disable_trellis_quant;
+  oxcf->allow_ref_frame_mvs = extra_cfg->enable_ref_frame_mvs;
   oxcf->using_qm = extra_cfg->enable_qm;
   oxcf->qm_y = extra_cfg->qm_y;
   oxcf->qm_u = extra_cfg->qm_u;
@@ -972,7 +1027,7 @@
 }
 
 static aom_codec_err_t update_extra_cfg(aom_codec_alg_priv_t *ctx,
-                                        const struct av1_extracfg *extra_cfg) {
+                                        struct av1_extracfg *extra_cfg) {
   const aom_codec_err_t res = validate_config(ctx, &ctx->cfg, extra_cfg);
   if (res == AOM_CODEC_OK) {
     ctx->extra_cfg = *extra_cfg;
@@ -2543,7 +2598,8 @@
         0,            // tile_height_count
         { 0 },        // tile_widths
         { 0 },        // tile_heights
-        { 1 },        // config file
+        { 0, 128, 128, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+          0, 0,   0,   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },  // cfg
     } },
   { 1,
     {
@@ -2611,7 +2667,8 @@
         0,            // tile_height_count
         { 0 },        // tile_widths
         { 0 },        // tile_heights
-        { 1 },        // config file
+        { 0, 128, 128, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+          0, 0,   0,   0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },  // cfg
     } },
 };
 
diff --git a/av1/av1_dx_iface.c b/av1/av1_dx_iface.c
index 66fe5df..6b06ad4 100644
--- a/av1/av1_dx_iface.c
+++ b/av1/av1_dx_iface.c
@@ -105,8 +105,6 @@
     if (ctx->config.dec) {
       priv->cfg = *ctx->config.dec;
       ctx->config.dec = &priv->cfg;
-      // default values
-      priv->cfg.cfg.ext_partition = 1;
     }
     priv->num_grain_image_frame_buffers = 0;
     // Turn row_mt on by default.
@@ -482,7 +480,6 @@
       set_error_detail(ctx, "Failed to allocate frame_worker_data");
       return AOM_CODEC_MEM_ERROR;
     }
-    frame_worker_data->pbi->common.options = &ctx->cfg.cfg;
     frame_worker_data->worker_id = i;
     frame_worker_data->frame_context_ready = 0;
     frame_worker_data->received_frame = 0;
diff --git a/av1/common/onyxc_int.h b/av1/common/onyxc_int.h
index 06d724b..55b8173 100644
--- a/av1/common/onyxc_int.h
+++ b/av1/common/onyxc_int.h
@@ -569,7 +569,7 @@
   int64_t txcoeff_cost_timer;
   int64_t txcoeff_cost_count;
 #endif
-  const cfg_options_t *options;
+
   int is_decoding;
 } AV1_COMMON;
 
diff --git a/av1/encoder/encoder.c b/av1/encoder/encoder.c
index 8803e2d..f0046d5 100644
--- a/av1/encoder/encoder.c
+++ b/av1/encoder/encoder.c
@@ -450,22 +450,13 @@
 
 static BLOCK_SIZE select_sb_size(const AV1_COMP *const cpi) {
   const AV1_COMMON *const cm = &cpi->common;
-
   if (cpi->oxcf.superblock_size == AOM_SUPERBLOCK_SIZE_64X64)
     return BLOCK_64X64;
-#if CONFIG_FILEOPTIONS
-  if (cm->options && cm->options->ext_partition)
-#endif
-    if (cpi->oxcf.superblock_size == AOM_SUPERBLOCK_SIZE_128X128)
-      return BLOCK_128X128;
+  if (cpi->oxcf.superblock_size == AOM_SUPERBLOCK_SIZE_128X128)
+    return BLOCK_128X128;
 
   assert(cpi->oxcf.superblock_size == AOM_SUPERBLOCK_SIZE_DYNAMIC);
 
-// TODO(any): Possibly could improve this with a heuristic.
-#if CONFIG_FILEOPTIONS
-  if (cm->options && !cm->options->ext_partition) return BLOCK_64X64;
-#endif
-
   // When superres / resize is on, 'cm->width / height' can change between
   // calls, so we don't apply this heuristic there.
   // Things break if superblock size changes between the first pass and second
@@ -2715,7 +2706,6 @@
   update_film_grain_parameters(cpi, oxcf);
 
   cpi->oxcf = *oxcf;
-  cpi->common.options = oxcf->cfg;
   x->e_mbd.bd = (int)seq_params->bit_depth;
   x->e_mbd.global_motion = cm->global_motion;
 
diff --git a/av1/encoder/encoder.h b/av1/encoder/encoder.h
index bfcbb66..c91118d 100644
--- a/av1/encoder/encoder.h
+++ b/av1/encoder/encoder.h
@@ -369,7 +369,6 @@
   unsigned int full_still_picture_hdr;
   int enable_dual_filter;
   unsigned int motion_vector_unit_test;
-  const cfg_options_t *cfg;
   int enable_rect_partitions;
   int enable_ab_partitions;
   int enable_1to4_partitions;
@@ -428,6 +427,9 @@
   unsigned int tier_mask;
   // min_cr / 100 is the target minimum compression ratio for each frame.
   unsigned int min_cr;
+#if CONFIG_FILEOPTIONS
+  const cfg_options_t *encoder_cfg;
+#endif
 } AV1EncoderConfig;
 
 static INLINE int is_lossless_requested(const AV1EncoderConfig *cfg) {
diff --git a/common/args.c b/common/args.c
index 7131e24..4804a57 100644
--- a/common/args.c
+++ b/common/args.c
@@ -17,6 +17,7 @@
 
 #include "aom/aom_integer.h"
 #include "aom_ports/msvc.h"
+#include "aom/aom_codec.h"
 
 #if defined(__GNUC__) && __GNUC__
 extern void die(const char *fmt, ...) __attribute__((noreturn));
@@ -48,20 +49,39 @@
   if (end >= str) end[1] = '\0';
 }
 
-int arg_cfg(int *argc, char ***argv, const char *file) {
-  char **argv_local = (char **)*argv;
-  char **argv_org = (char **)*argv;
+void init_config(cfg_options_t *pConfig) {
+  memset(pConfig, 0, sizeof(cfg_options_t));
+  pConfig->super_block_size = 0;  // Dynamic
+  pConfig->max_partition_size = 128;
+  pConfig->min_partition_size = 4;
+  pConfig->disable_trellis_quant = 3;
+}
+
+static const char sbsize_warning_string[] =
+    "super_block_size has to be 64 or 128.";
+static const char minpart_warning_string[] =
+    "min_partition_size has to be smaller or equal to max_partition_size.";
+static const char maxpart_warning_string[] =
+    "max_partition_size has to be smaller or equal to super_block_size.";
+
+int parse_cfg(const char *file, cfg_options_t *pConfig) {
   char line[1024 * 10];
   FILE *f = fopen(file, "r");
   if (!f) return 1;
 
+#define GET_PARAMS(field)          \
+  if (strcmp(left, #field) == 0) { \
+    pConfig->field = atoi(right);  \
+    continue;                      \
+  }
+
   while (fgets(line, sizeof(line) - 1, f)) {
     char *actual_line = ignore_front_spaces(line);
     char *left, *right, *comment;
     size_t length = strlen(actual_line);
 
     if (length == 0 || actual_line[0] == '#') continue;
-    right = strchr(actual_line, ':');
+    right = strchr(actual_line, '=');
     if (right == NULL) continue;
     right[0] = '\0';
 
@@ -74,23 +94,62 @@
     ignore_end_spaces(left);
     ignore_end_spaces(right);
 
-    char **new_args = argv_dup(*argc, (const char **)argv_local);
-    char *new_line = (char *)malloc(sizeof(*new_line) * 128);
+    GET_PARAMS(super_block_size);
+    GET_PARAMS(max_partition_size);
+    GET_PARAMS(min_partition_size);
+    GET_PARAMS(disable_ab_partition_type);
+    GET_PARAMS(disable_rect_partition_type);
+    GET_PARAMS(disable_1to4_partition_type);
+    GET_PARAMS(disable_flip_idtx);
+    GET_PARAMS(disable_cdef);
+    GET_PARAMS(disable_lr);
+    GET_PARAMS(disable_obmc);
+    GET_PARAMS(disable_warp_motion);
+    GET_PARAMS(disable_global_motion);
+    GET_PARAMS(disable_dist_wtd_comp);
+    GET_PARAMS(disable_diff_wtd_comp);
+    GET_PARAMS(disable_inter_intra_comp);
+    GET_PARAMS(disable_masked_comp);
+    GET_PARAMS(disable_one_sided_comp);
+    GET_PARAMS(disable_palette);
+    GET_PARAMS(disable_ibc);
+    GET_PARAMS(disable_cfl);
+    GET_PARAMS(disable_smooth_intra);
+    GET_PARAMS(disable_filter_intra);
+    GET_PARAMS(disable_dual_filter);
+    GET_PARAMS(disable_intra_angle_delta);
+    GET_PARAMS(tx_size_search_method);
+    GET_PARAMS(disable_intra_edge_filter);
+    GET_PARAMS(disable_tx_64x64);
+    GET_PARAMS(disable_smooth_inter_intra);
+    GET_PARAMS(disable_inter_inter_wedge);
+    GET_PARAMS(disable_inter_intra_wedge);
+    GET_PARAMS(disable_paeth_intra);
+    GET_PARAMS(disable_trellis_quant);
+    GET_PARAMS(disable_ref_frame_mv);
+    GET_PARAMS(reduced_reference_set);
+    GET_PARAMS(reduced_tx_type_set);
 
-    if (argv_local != argv_org) free(argv_local);
-
-    if (!strcmp(right, "ON"))
-      snprintf(new_line, sizeof(*new_line) * 128, "--%s", left);
-    else
-      snprintf(new_line, sizeof(*new_line) * 128, "--%s=%s", left, right);
-
-    new_args[(*argc) - 1] = new_args[(*argc) - 2];
-    new_args[(*argc) - 2] = new_line;
-    argv_local = new_args;
-    *argv = new_args;
-    (*argc)++;
+    fprintf(stderr, "\nInvalid parameter: %s", left);
+    exit(-1);
   }
+
+  if (pConfig->super_block_size != 128 && pConfig->super_block_size != 64) {
+    fprintf(stderr, "\n%s", sbsize_warning_string);
+    exit(-1);
+  }
+  if (pConfig->min_partition_size > pConfig->max_partition_size) {
+    fprintf(stderr, "\n%s", minpart_warning_string);
+    exit(-1);
+  }
+  if (pConfig->max_partition_size > pConfig->super_block_size) {
+    fprintf(stderr, "\n%s", maxpart_warning_string);
+    exit(-1);
+  }
+
   fclose(f);
+  pConfig->init_by_cfg_file = 1;
+
   return 0;
 }
 
@@ -209,10 +268,6 @@
   return 0;
 }
 
-struct aom_rational {
-  int num; /**< fraction numerator */
-  int den; /**< fraction denominator */
-};
 struct aom_rational arg_parse_rational(const struct arg *arg) {
   long int rawval;
   char *endptr;
diff --git a/common/args.h b/common/args.h
index 6a26642..edbf6f7 100644
--- a/common/args.h
+++ b/common/args.h
@@ -12,6 +12,8 @@
 #ifndef AOM_COMMON_ARGS_H_
 #define AOM_COMMON_ARGS_H_
 #include <stdio.h>
+#include "aom/aom_codec.h"
+#include "aom/aom_encoder.h"
 
 #ifdef __cplusplus
 extern "C" {
@@ -50,7 +52,10 @@
 int arg_match(struct arg *arg_, const struct arg_def *def, char **argv);
 char *ignore_front_spaces(const char *str);
 void ignore_end_spaces(char *str);
-int arg_cfg(int *argc, char ***argv, const char *file);
+
+int parse_cfg(const char *file, cfg_options_t *pConfig);
+void init_config(cfg_options_t *pConfig);
+
 const char *arg_next(struct arg *arg);
 void arg_show_usage(FILE *fp, const struct arg_def *const *defs);
 char **argv_dup(int argc, const char **argv);
diff --git a/examples/av1_dec_fuzzer.cc b/examples/av1_dec_fuzzer.cc
index 15752a0..1cddc8c 100644
--- a/examples/av1_dec_fuzzer.cc
+++ b/examples/av1_dec_fuzzer.cc
@@ -38,9 +38,7 @@
   aom_codec_ctx_t codec;
   // Set thread count in the range [1, 64].
   const unsigned int threads = (data[IVF_FILE_HDR_SZ] & 0x3f) + 1;
-  aom_codec_dec_cfg_t cfg = {
-    threads, 0, 0, !FORCE_HIGHBITDEPTH_DECODING, { 1 }
-  };
+  aom_codec_dec_cfg_t cfg = { threads, 0, 0, !FORCE_HIGHBITDEPTH_DECODING };
   if (aom_codec_dec_init(&codec, codec_interface, &cfg, 0)) {
     return 0;
   }
diff --git a/test/invalid_file_test.cc b/test/invalid_file_test.cc
index c21453c..a8a42eb 100644
--- a/test/invalid_file_test.cc
+++ b/test/invalid_file_test.cc
@@ -100,7 +100,7 @@
 
   void RunTest() {
     const DecodeParam input = GET_PARAM(1);
-    aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING, { 1 } };
+    aom_codec_dec_cfg_t cfg = { 0, 0, 0, !FORCE_HIGHBITDEPTH_DECODING };
     cfg.threads = input.threads;
     const std::string filename = input.filename;
     libaom_test::IVFVideoSource decode_video(filename);