Add intra-interp experiment flag

intra-interp experiment allows intra prediction to use different
interpolation filters. It was part of the ext-intra in the nextgenv2
branch.

Change-Id: I27ab692494dc79bb92e457dbf9a72988577f1c6d
diff --git a/av1/common/blockd.c b/av1/common/blockd.c
index e86338a..8a887f9 100644
--- a/av1/common/blockd.c
+++ b/av1/common/blockd.c
@@ -223,6 +223,7 @@
   54,   49,    45,   40,   35,   31,   26,   22,   17,   13,   8,    4,
 };
 
+#if CONFIG_INTRA_INTERP
 int av1_is_intra_filter_switchable(int angle) {
   assert(angle > 0 && angle < 270);
   if (angle % 45 == 0) return 0;
@@ -234,4 +235,5 @@
             0xFF) > 0;
   }
 }
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
diff --git a/av1/common/blockd.h b/av1/common/blockd.h
index 793561a..eb7f915 100644
--- a/av1/common/blockd.h
+++ b/av1/common/blockd.h
@@ -302,9 +302,12 @@
   FILTER_INTRA_MODE_INFO filter_intra_mode_info;
 #endif  // CONFIG_FILTER_INTRA
 #if CONFIG_EXT_INTRA
+  // The actual prediction angle is the base angle + (angle_delta * step).
   int8_t angle_delta[2];
+#if CONFIG_INTRA_INTERP
   // To-Do (huisu): this may be replaced by interp_filter
   INTRA_FILTER intra_filter;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 #if CONFIG_EXT_INTER
@@ -697,9 +700,11 @@
   0, 90, 180, 45, 135, 111, 157, 203, 67, 0,
 };
 
+#if CONFIG_INTRA_INTERP
 // Returns whether filter selection is needed for a given
 // intra prediction angle.
 int av1_is_intra_filter_switchable(int angle);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 #if CONFIG_EXT_TILE
diff --git a/av1/common/entropymode.c b/av1/common/entropymode.c
index cbad10a..09868dc 100644
--- a/av1/common/entropymode.c
+++ b/av1/common/entropymode.c
@@ -1636,6 +1636,7 @@
 #endif  // CONFIG_EXT_TX
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 static const aom_prob default_intra_filter_probs[INTRA_FILTERS + 1]
                                                 [INTRA_FILTERS - 1] = {
                                                   { 98, 63, 60 },
@@ -1648,6 +1649,7 @@
   -INTRA_FILTER_LINEAR,      2, -INTRA_FILTER_8TAP, 4, -INTRA_FILTER_8TAP_SHARP,
   -INTRA_FILTER_8TAP_SMOOTH,
 };
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 #if CONFIG_FILTER_INTRA
@@ -1723,7 +1725,9 @@
   av1_copy(fc->seg.tree_probs, default_segment_tree_probs);
   av1_copy(fc->seg.pred_probs, default_segment_pred_probs);
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   av1_copy(fc->intra_filter_probs, default_intra_filter_probs);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
   av1_copy(fc->filter_intra_probs, default_filter_intra_probs);
@@ -2036,10 +2040,12 @@
         mode_mv_merge_probs(pre_fc->delta_q_prob[i], counts->delta_q[i]);
 #endif
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   for (i = 0; i < INTRA_FILTERS + 1; ++i) {
     aom_tree_merge_probs(av1_intra_filter_tree, pre_fc->intra_filter_probs[i],
                          counts->intra_filter[i], fc->intra_filter_probs[i]);
   }
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
   for (i = 0; i < PLANE_TYPES; ++i) {
diff --git a/av1/common/entropymode.h b/av1/common/entropymode.h
index dd753a1..63211dc 100644
--- a/av1/common/entropymode.h
+++ b/av1/common/entropymode.h
@@ -152,7 +152,9 @@
 #endif  // CONFIG_SUPERTX
   struct segmentation_probs seg;
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   aom_prob intra_filter_probs[INTRA_FILTERS + 1][INTRA_FILTERS - 1];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
   aom_prob filter_intra_probs[PLANE_TYPES];
@@ -271,7 +273,9 @@
 #endif  // CONFIG_SUPERTX
   struct seg_counts seg;
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   unsigned int intra_filter[INTRA_FILTERS + 1][INTRA_FILTERS];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
   unsigned int filter_intra[PLANE_TYPES][2];
@@ -328,7 +332,9 @@
 #endif  // CONFIG_PALETTE
 extern const aom_tree_index av1_tx_size_tree[MAX_TX_DEPTH][TREE_SIZE(TX_SIZES)];
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 extern const aom_tree_index av1_intra_filter_tree[TREE_SIZE(INTRA_FILTERS)];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_EXT_TX
 extern const aom_tree_index av1_ext_tx_inter_tree[EXT_TX_SETS_INTER]
diff --git a/av1/common/filter.c b/av1/common/filter.c
index 3f1cdbb..0d6bc3b 100644
--- a/av1/common/filter.c
+++ b/av1/common/filter.c
@@ -194,12 +194,14 @@
 #endif  // CONFIG_EXT_INTERP
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 const InterpKernel *av1_intra_filter_kernels[INTRA_FILTERS] = {
   bilinear_filters,         // INTRA_FILTER_LINEAR
   sub_pel_filters_8,        // INTRA_FILTER_8TAP
   sub_pel_filters_8sharp,   // INTRA_FILTER_8TAP_SHARP
   sub_pel_filters_8smooth,  // INTRA_FILTER_8TAP_SMOOTH
 };
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 #if CONFIG_EXT_INTERP
diff --git a/av1/common/filter.h b/av1/common/filter.h
index 44f8f02..020d7dd 100644
--- a/av1/common/filter.h
+++ b/av1/common/filter.h
@@ -64,6 +64,7 @@
 typedef uint8_t InterpFilter;
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 typedef enum {
   INTRA_FILTER_LINEAR,
   INTRA_FILTER_8TAP,
@@ -73,6 +74,7 @@
 } INTRA_FILTER;
 
 extern const InterpKernel *av1_intra_filter_kernels[INTRA_FILTERS];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 typedef struct InterpFilterParams {
diff --git a/av1/common/pred_common.c b/av1/common/pred_common.c
index e522725..bbf21c9 100644
--- a/av1/common/pred_common.c
+++ b/av1/common/pred_common.c
@@ -96,6 +96,7 @@
 #endif
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 // Obtain the reference filter type from the above/left neighbor blocks.
 static INTRA_FILTER get_ref_intra_filter(const MB_MODE_INFO *ref_mbmi) {
   INTRA_FILTER ref_type = INTRA_FILTERS;
@@ -143,6 +144,7 @@
   else
     return INTRA_FILTERS;
 }
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 // The mode info data structure has a one element border above and to the
diff --git a/av1/common/pred_common.h b/av1/common/pred_common.h
index 71865f2..49d09fc 100644
--- a/av1/common/pred_common.h
+++ b/av1/common/pred_common.h
@@ -74,7 +74,9 @@
 #endif
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 int av1_get_pred_context_intra_interp(const MACROBLOCKD *xd);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 
 int av1_get_intra_inter_context(const MACROBLOCKD *xd);
diff --git a/av1/common/reconintra.c b/av1/common/reconintra.c
index db44a23..5a6583b 100644
--- a/av1/common/reconintra.c
+++ b/av1/common/reconintra.c
@@ -407,6 +407,7 @@
 }
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 static int intra_subpel_interp(int base, int shift, const uint8_t *ref,
                                int ref_start_idx, int ref_end_idx,
                                INTRA_FILTER filter_type) {
@@ -435,11 +436,15 @@
 
   return val;
 }
+#endif  // CONFIG_INTRA_INTERP
 
 // Directional prediction, zone 1: 0 < angle < 90
 static void dr_prediction_z1(uint8_t *dst, ptrdiff_t stride, int bs,
-                             const uint8_t *above, const uint8_t *left, int dx,
-                             int dy, INTRA_FILTER filter_type) {
+                             const uint8_t *above, const uint8_t *left,
+#if CONFIG_INTRA_INTERP
+                             INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                             int dx, int dy) {
   int r, c, x, base, shift, val;
 
   (void)left;
@@ -447,6 +452,7 @@
   assert(dy == 1);
   assert(dx < 0);
 
+#if CONFIG_INTRA_INTERP
   if (filter_type != INTRA_FILTER_LINEAR) {
     const int pad_size = SUBPEL_TAPS >> 1;
     int len;
@@ -505,8 +511,8 @@
     }
     return;
   }
+#endif  // CONFIG_INTRA_INTERP
 
-  // For linear filter, C code is faster.
   x = -dx;
   for (r = 0; r < bs; ++r, dst += stride, x -= dx) {
     base = x >> 8;
@@ -535,8 +541,11 @@
 
 // Directional prediction, zone 2: 90 < angle < 180
 static void dr_prediction_z2(uint8_t *dst, ptrdiff_t stride, int bs,
-                             const uint8_t *above, const uint8_t *left, int dx,
-                             int dy, INTRA_FILTER filter_type) {
+                             const uint8_t *above, const uint8_t *left,
+#if CONFIG_INTRA_INTERP
+                             INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                             int dx, int dy) {
   int r, c, x, y, shift1, shift2, val, base1, base2;
 
   assert(dx > 0);
@@ -549,14 +558,24 @@
     for (c = 0; c < bs; ++c, ++base1, y -= dy) {
       if (base1 >= -1) {
         shift1 = x & 0xFF;
+#if CONFIG_INTRA_INTERP
         val =
             intra_subpel_interp(base1, shift1, above, -1, bs - 1, filter_type);
+#else
+        val = above[base1] * (256 - shift1) + above[base1 + 1] * shift1;
+        val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
       } else {
         base2 = y >> 8;
         if (base2 >= 0) {
           shift2 = y & 0xFF;
+#if CONFIG_INTRA_INTERP
           val =
               intra_subpel_interp(base2, shift2, left, 0, bs - 1, filter_type);
+#else
+          val = left[base2] * (256 - shift2) + left[base2 + 1] * shift2;
+          val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
         } else {
           val = left[0];
         }
@@ -568,8 +587,11 @@
 
 // Directional prediction, zone 3: 180 < angle < 270
 static void dr_prediction_z3(uint8_t *dst, ptrdiff_t stride, int bs,
-                             const uint8_t *above, const uint8_t *left, int dx,
-                             int dy, INTRA_FILTER filter_type) {
+                             const uint8_t *above, const uint8_t *left,
+#if CONFIG_INTRA_INTERP
+                             INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                             int dx, int dy) {
   int r, c, y, base, shift, val;
 
   (void)above;
@@ -578,6 +600,7 @@
   assert(dx == 1);
   assert(dy < 0);
 
+#if CONFIG_INTRA_INTERP
   if (filter_type != INTRA_FILTER_LINEAR) {
     const int pad_size = SUBPEL_TAPS >> 1;
     int len, i;
@@ -646,8 +669,8 @@
     }
     return;
   }
+#endif  // CONFIG_INTRA_INTERP
 
-  // For linear filter, C code is faster.
   y = -dy;
   for (c = 0; c < bs; ++c, y -= dy) {
     base = y >> 8;
@@ -697,19 +720,34 @@
 }
 
 static void dr_predictor(uint8_t *dst, ptrdiff_t stride, TX_SIZE tx_size,
-                         const uint8_t *above, const uint8_t *left, int angle,
-                         INTRA_FILTER filter_type) {
+                         const uint8_t *above, const uint8_t *left,
+#if CONFIG_INTRA_INTERP
+                         INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                         int angle) {
   const int dx = get_dx(angle);
   const int dy = get_dy(angle);
   const int bs = tx_size_wide[tx_size];
   assert(angle > 0 && angle < 270);
 
   if (angle > 0 && angle < 90) {
-    dr_prediction_z1(dst, stride, bs, above, left, dx, dy, filter_type);
+    dr_prediction_z1(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                     filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                     dx, dy);
   } else if (angle > 90 && angle < 180) {
-    dr_prediction_z2(dst, stride, bs, above, left, dx, dy, filter_type);
+    dr_prediction_z2(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                     filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                     dx, dy);
   } else if (angle > 180 && angle < 270) {
-    dr_prediction_z3(dst, stride, bs, above, left, dx, dy, filter_type);
+    dr_prediction_z3(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                     filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                     dx, dy);
   } else if (angle == 90) {
     pred[V_PRED][tx_size](dst, stride, above, left);
   } else if (angle == 180) {
@@ -718,6 +756,7 @@
 }
 
 #if CONFIG_AOM_HIGHBITDEPTH
+#if CONFIG_INTRA_INTERP
 static int highbd_intra_subpel_interp(int base, int shift, const uint16_t *ref,
                                       int ref_start_idx, int ref_end_idx,
                                       INTRA_FILTER filter_type) {
@@ -746,12 +785,15 @@
 
   return val;
 }
+#endif  // CONFIG_INTRA_INTERP
 
 // Directional prediction, zone 1: 0 < angle < 90
 static void highbd_dr_prediction_z1(uint16_t *dst, ptrdiff_t stride, int bs,
                                     const uint16_t *above, const uint16_t *left,
-                                    int dx, int dy, int bd,
-                                    INTRA_FILTER filter_type) {
+#if CONFIG_INTRA_INTERP
+                                    INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                                    int dx, int dy, int bd) {
   int r, c, x, y, base, shift, val;
 
   (void)left;
@@ -766,8 +808,13 @@
       base = x >> 8;
       shift = x & 0xFF;
       if (base < 2 * bs - 1) {
+#if CONFIG_INTRA_INTERP
         val = highbd_intra_subpel_interp(base, shift, above, 0, 2 * bs - 1,
                                          filter_type);
+#else
+        val = above[base] * (256 - shift) + above[base + 1] * shift;
+        val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
         dst[c] = clip_pixel_highbd(val, bd);
       } else {
         dst[c] = above[2 * bs - 1];
@@ -780,8 +827,10 @@
 // Directional prediction, zone 2: 90 < angle < 180
 static void highbd_dr_prediction_z2(uint16_t *dst, ptrdiff_t stride, int bs,
                                     const uint16_t *above, const uint16_t *left,
-                                    int dx, int dy, int bd,
-                                    INTRA_FILTER filter_type) {
+#if CONFIG_INTRA_INTERP
+                                    INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                                    int dx, int dy, int bd) {
   int r, c, x, y, shift, val, base;
 
   assert(dx > 0);
@@ -794,16 +843,26 @@
       base = x >> 8;
       if (base >= -1) {
         shift = x & 0xFF;
+#if CONFIG_INTRA_INTERP
         val = highbd_intra_subpel_interp(base, shift, above, -1, bs - 1,
                                          filter_type);
+#else
+        val = above[base] * (256 - shift) + above[base + 1] * shift;
+        val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
       } else {
         x = c + 1;
         y = (r << 8) - x * dy;
         base = y >> 8;
         if (base >= 0) {
           shift = y & 0xFF;
+#if CONFIG_INTRA_INTERP
           val = highbd_intra_subpel_interp(base, shift, left, 0, bs - 1,
                                            filter_type);
+#else
+          val = left[base] * (256 - shift) + left[base + 1] * shift;
+          val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
         } else {
           val = left[0];
         }
@@ -817,8 +876,10 @@
 // Directional prediction, zone 3: 180 < angle < 270
 static void highbd_dr_prediction_z3(uint16_t *dst, ptrdiff_t stride, int bs,
                                     const uint16_t *above, const uint16_t *left,
-                                    int dx, int dy, int bd,
-                                    INTRA_FILTER filter_type) {
+#if CONFIG_INTRA_INTERP
+                                    INTRA_FILTER filter_type,
+#endif  // CONFIG_INTRA_INTERP
+                                    int dx, int dy, int bd) {
   int r, c, x, y, base, shift, val;
 
   (void)above;
@@ -833,8 +894,13 @@
       base = y >> 8;
       shift = y & 0xFF;
       if (base < 2 * bs - 1) {
+#if CONFIG_INTRA_INTERP
         val = highbd_intra_subpel_interp(base, shift, left, 0, 2 * bs - 1,
                                          filter_type);
+#else
+        val = left[base] * (256 - shift) + left[base + 1] * shift;
+        val = ROUND_POWER_OF_TWO(val, 8);
+#endif  // CONFIG_INTRA_INTERP
         dst[c] = clip_pixel_highbd(val, bd);
       } else {
         dst[c] = left[2 * bs - 1];
@@ -870,17 +936,32 @@
 
 static void highbd_dr_predictor(uint16_t *dst, ptrdiff_t stride, int bs,
                                 const uint16_t *above, const uint16_t *left,
-                                int angle, int bd, INTRA_FILTER filter) {
+#if CONFIG_INTRA_INTERP
+                                INTRA_FILTER filter,
+#endif  // CONFIG_INTRA_INTERP
+                                int angle, int bd) {
   const int dx = get_dx(angle);
   const int dy = get_dy(angle);
   assert(angle > 0 && angle < 270);
 
   if (angle > 0 && angle < 90) {
-    highbd_dr_prediction_z1(dst, stride, bs, above, left, dx, dy, bd, filter);
+    highbd_dr_prediction_z1(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                            filter,
+#endif  // CONFIG_INTRA_INTERP
+                            dx, dy, bd);
   } else if (angle > 90 && angle < 180) {
-    highbd_dr_prediction_z2(dst, stride, bs, above, left, dx, dy, bd, filter);
+    highbd_dr_prediction_z2(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                            filter,
+#endif  // CONFIG_INTRA_INTERP
+                            dx, dy, bd);
   } else if (angle > 180 && angle < 270) {
-    highbd_dr_prediction_z3(dst, stride, bs, above, left, dx, dy, bd, filter);
+    highbd_dr_prediction_z3(dst, stride, bs, above, left,
+#if CONFIG_INTRA_INTERP
+                            filter,
+#endif  // CONFIG_INTRA_INTERP
+                            dx, dy, bd);
   } else if (angle == 90) {
     highbd_v_predictor(dst, stride, bs, above, left, bd);
   } else if (angle == 180) {
@@ -1397,11 +1478,16 @@
 
 #if CONFIG_EXT_INTRA
   if (is_dr_mode) {
+#if CONFIG_INTRA_INTERP
     INTRA_FILTER filter = INTRA_FILTER_LINEAR;
     if (plane == 0 && av1_is_intra_filter_switchable(p_angle))
       filter = xd->mi[0]->mbmi.intra_filter;
-    highbd_dr_predictor(dst, dst_stride, bs, const_above_row, left_col, p_angle,
-                        xd->bd, filter);
+#endif  // CONFIG_INTRA_INTERP
+    highbd_dr_predictor(dst, dst_stride, bs, const_above_row, left_col,
+#if CONFIG_INTRA_INTERP
+                        filter,
+#endif  // CONFIG_INTRA_INTERP
+                        p_angle, xd->bd);
     return;
   }
 #endif  // CONFIG_EXT_INTRA
@@ -1555,11 +1641,16 @@
 #endif  // CONFIG_FILTER_INTRA
 #if CONFIG_EXT_INTRA
   if (is_dr_mode) {
+#if CONFIG_INTRA_INTERP
     INTRA_FILTER filter = INTRA_FILTER_LINEAR;
     if (plane == 0 && av1_is_intra_filter_switchable(p_angle))
       filter = xd->mi[0]->mbmi.intra_filter;
-    dr_predictor(dst, dst_stride, tx_size, const_above_row, left_col, p_angle,
-                 filter);
+#endif  // CONFIG_INTRA_INTERP
+    dr_predictor(dst, dst_stride, tx_size, const_above_row, left_col,
+#if CONFIG_INTRA_INTERP
+                 filter,
+#endif  // CONFIG_INTRA_INTERP
+                 p_angle);
     return;
   }
 #endif  // CONFIG_EXT_INTRA
diff --git a/av1/decoder/decodeframe.c b/av1/decoder/decodeframe.c
index 70948d0..e35bda6 100644
--- a/av1/decoder/decodeframe.c
+++ b/av1/decoder/decodeframe.c
@@ -4237,9 +4237,11 @@
 #endif  // CONFIG_EXT_PARTITION_TYPES
 #endif  // EC_ADAPT, DAALA_EC
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   for (i = 0; i < INTRA_FILTERS + 1; ++i)
     for (j = 0; j < INTRA_FILTERS - 1; ++j)
       av1_diff_update_prob(&r, &fc->intra_filter_probs[i][j], ACCT_STR);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // EC_ADAPT, DAALA_EC
 
   if (frame_is_intra_only(cm)) {
diff --git a/av1/decoder/decodemv.c b/av1/decoder/decodemv.c
index 7e9dd9a..5709407 100644
--- a/av1/decoder/decodemv.c
+++ b/av1/decoder/decodemv.c
@@ -653,14 +653,18 @@
                                   aom_reader *r) {
   MB_MODE_INFO *const mbmi = &xd->mi[0]->mbmi;
   const BLOCK_SIZE bsize = mbmi->sb_type;
+#if CONFIG_INTRA_INTERP
   const int ctx = av1_get_pred_context_intra_interp(xd);
   int p_angle;
+#endif  // CONFIG_INTRA_INTERP
 
+  (void)cm;
   if (bsize < BLOCK_8X8) return;
 
   if (mbmi->mode != DC_PRED && mbmi->mode != TM_PRED) {
     mbmi->angle_delta[0] =
         read_uniform(r, 2 * MAX_ANGLE_DELTAS + 1) - MAX_ANGLE_DELTAS;
+#if CONFIG_INTRA_INTERP
     p_angle = mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
     if (av1_is_intra_filter_switchable(p_angle)) {
       FRAME_COUNTS *counts = xd->counts;
@@ -670,6 +674,7 @@
     } else {
       mbmi->intra_filter = INTRA_FILTER_LINEAR;
     }
+#endif  // CONFIG_INTRA_INTERP
   }
 
   if (mbmi->uv_mode != DC_PRED && mbmi->uv_mode != TM_PRED) {
@@ -1786,7 +1791,9 @@
 #if CONFIG_EXT_INTRA
       mbmi->angle_delta[0] = 0;
       mbmi->angle_delta[1] = 0;
+#if CONFIG_INTRA_INTERP
       mbmi->intra_filter = INTRA_FILTER_LINEAR;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
       mbmi->filter_intra_mode_info.use_filter_intra_mode[0] = 0;
diff --git a/av1/encoder/bitstream.c b/av1/encoder/bitstream.c
index 92afa69..78ccf6b 100644
--- a/av1/encoder/bitstream.c
+++ b/av1/encoder/bitstream.c
@@ -110,7 +110,9 @@
 static struct av1_token global_motion_types_encodings[GLOBAL_TRANS_TYPES];
 #endif  // CONFIG_GLOBAL_MOTION
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
 static struct av1_token intra_filter_encodings[INTRA_FILTERS];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_EXT_INTER
 static struct av1_token interintra_mode_encodings[INTERINTRA_MODES];
@@ -155,7 +157,9 @@
 #endif  // CONFIG_PALETTE
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   av1_tokens_from_tree(intra_filter_encodings, av1_intra_filter_tree);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_EXT_INTER
   av1_tokens_from_tree(interintra_mode_encodings, av1_interintra_mode_tree);
@@ -1031,20 +1035,25 @@
                                    aom_writer *w) {
   const MB_MODE_INFO *const mbmi = &xd->mi[0]->mbmi;
   const BLOCK_SIZE bsize = mbmi->sb_type;
+#if CONFIG_INTRA_INTERP
   const int intra_filter_ctx = av1_get_pred_context_intra_interp(xd);
   int p_angle;
+#endif  // CONFIG_INTRA_INTERP
 
+  (void)cm;
   if (bsize < BLOCK_8X8) return;
 
   if (mbmi->mode != DC_PRED && mbmi->mode != TM_PRED) {
     write_uniform(w, 2 * MAX_ANGLE_DELTAS + 1,
                   MAX_ANGLE_DELTAS + mbmi->angle_delta[0]);
+#if CONFIG_INTRA_INTERP
     p_angle = mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
     if (av1_is_intra_filter_switchable(p_angle)) {
       av1_write_token(w, av1_intra_filter_tree,
                       cm->fc->intra_filter_probs[intra_filter_ctx],
                       &intra_filter_encodings[mbmi->intra_filter]);
     }
+#endif  // CONFIG_INTRA_INTERP
   }
 
   if (mbmi->uv_mode != DC_PRED && mbmi->uv_mode != TM_PRED) {
@@ -4201,9 +4210,11 @@
 #endif  // CONFIG_EC_ADAPT, CONFIG_DAALA_EC
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   for (i = 0; i < INTRA_FILTERS + 1; ++i)
     prob_diff_update(av1_intra_filter_tree, fc->intra_filter_probs[i],
                      counts->intra_filter[i], INTRA_FILTERS, probwt, header_bc);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #endif  // CONFIG_EC_ADAPT, CONFIG_DAALA_EC
   if (frame_is_intra_only(cm)) {
diff --git a/av1/encoder/encodeframe.c b/av1/encoder/encodeframe.c
index 47ca2fc..7bd1ee1 100644
--- a/av1/encoder/encodeframe.c
+++ b/av1/encoder/encodeframe.c
@@ -5493,6 +5493,7 @@
       }
 #endif  // CONFIG_FILTER_INTRA
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
       if (mbmi->mode != DC_PRED && mbmi->mode != TM_PRED) {
         int p_angle;
         const int intra_filter_ctx = av1_get_pred_context_intra_interp(xd);
@@ -5501,6 +5502,7 @@
         if (av1_is_intra_filter_switchable(p_angle))
           ++counts->intra_filter[intra_filter_ctx][mbmi->intra_filter];
       }
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
     }
 
diff --git a/av1/encoder/encoder.h b/av1/encoder/encoder.h
index b20b2a1..0ee5576 100644
--- a/av1/encoder/encoder.h
+++ b/av1/encoder/encoder.h
@@ -565,7 +565,9 @@
   int inter_tx_type_costs[EXT_TX_SIZES][TX_TYPES];
 #endif  // CONFIG_EXT_TX
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   int intra_filter_cost[INTRA_FILTERS + 1][INTRA_FILTERS];
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_LOOP_RESTORATION
   int switchable_restore_cost[RESTORE_SWITCHABLE_TYPES];
diff --git a/av1/encoder/rd.c b/av1/encoder/rd.c
index 012386c..2797ebc 100644
--- a/av1/encoder/rd.c
+++ b/av1/encoder/rd.c
@@ -148,9 +148,11 @@
   }
 #endif  // CONFIG_EXT_TX
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   for (i = 0; i < INTRA_FILTERS + 1; ++i)
     av1_cost_tokens(cpi->intra_filter_cost[i], fc->intra_filter_probs[i],
                     av1_intra_filter_tree);
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_LOOP_RESTORATION
   av1_cost_tokens(cpi->switchable_restore_cost, fc->switchable_restore_prob,
diff --git a/av1/encoder/rdopt.c b/av1/encoder/rdopt.c
index 3b62c1c..a701e80 100644
--- a/av1/encoder/rdopt.c
+++ b/av1/encoder/rdopt.c
@@ -2408,7 +2408,9 @@
   const int *bmode_costs = cpi->mbmode_cost[0];
 
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   mic->mbmi.intra_filter = INTRA_FILTER_LINEAR;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
   mic->mbmi.filter_intra_mode_info.use_filter_intra_mode[0] = 0;
@@ -2553,7 +2555,10 @@
 static void pick_intra_angle_routine_sby(
     const AV1_COMP *const cpi, MACROBLOCK *x, int *rate, int *rate_tokenonly,
     int64_t *distortion, int *skippable, int *best_angle_delta,
-    TX_SIZE *best_tx_size, TX_TYPE *best_tx_type, INTRA_FILTER *best_filter,
+    TX_SIZE *best_tx_size, TX_TYPE *best_tx_type,
+#if CONFIG_INTRA_INTERP
+    INTRA_FILTER *best_filter,
+#endif  // CONFIG_INTRA_INTERP
     BLOCK_SIZE bsize, int rate_overhead, int64_t *best_rd) {
   int this_rate;
   RD_STATS tokenonly_rd_stats;
@@ -2569,7 +2574,9 @@
     *best_rd = this_rd;
     *best_angle_delta = mbmi->angle_delta[0];
     *best_tx_size = mbmi->tx_size;
+#if CONFIG_INTRA_INTERP
     *best_filter = mbmi->intra_filter;
+#endif  // CONFIG_INTRA_INTERP
     *best_tx_type = mbmi->tx_type;
     *rate = this_rate;
     *rate_tokenonly = tokenonly_rd_stats.rate;
@@ -2588,9 +2595,12 @@
   MB_MODE_INFO *mbmi = &mic->mbmi;
   int this_rate;
   RD_STATS tokenonly_rd_stats;
-  int angle_delta, best_angle_delta = 0, p_angle;
+  int angle_delta, best_angle_delta = 0;
+#if CONFIG_INTRA_INTERP
+  int p_angle;
   const int intra_filter_ctx = av1_get_pred_context_intra_interp(xd);
   INTRA_FILTER filter, best_filter = INTRA_FILTER_LINEAR;
+#endif  // CONFIG_INTRA_INTERP
   const double rd_adjust = 1.2;
   int64_t this_rd;
   TX_SIZE best_tx_size = mic->mbmi.tx_size;
@@ -2602,54 +2612,62 @@
       { -1, 1 }, { -3, -1 }, { 1, 3 },
     };
     const int level1 = 3, level2 = 2;
-    int i, j, best_i = -1;
+    int i, j, best_i = -1, first_try = 1;
 
     for (i = 0; i < level1; ++i) {
+      int64_t tmp_best_rd;
       mic->mbmi.angle_delta[0] = deltas_level1[i];
+#if CONFIG_INTRA_INTERP
       p_angle =
           mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
       for (filter = INTRA_FILTER_LINEAR; filter < INTRA_FILTERS; ++filter) {
-        int64_t tmp_best_rd;
         if ((FILTER_FAST_SEARCH || !av1_is_intra_filter_switchable(p_angle)) &&
             filter != INTRA_FILTER_LINEAR)
           continue;
         mic->mbmi.intra_filter = filter;
-        tmp_best_rd =
-            (i == 0 && filter == INTRA_FILTER_LINEAR && best_rd < INT64_MAX)
-                ? (int64_t)(best_rd * rd_adjust)
-                : best_rd;
+#endif  // CONFIG_INTRA_INTERP
+        tmp_best_rd = (first_try && best_rd < INT64_MAX)
+                          ? (int64_t)(best_rd * rd_adjust)
+                          : best_rd;
         super_block_yrd(cpi, x, &tokenonly_rd_stats, bsize, tmp_best_rd);
         if (tokenonly_rd_stats.rate == INT_MAX) {
-          if (i == 0 && filter == INTRA_FILTER_LINEAR)
+          if (first_try)
             return best_rd;
           else
             continue;
         }
-        this_rate = tokenonly_rd_stats.rate + rate_overhead +
-                    cpi->intra_filter_cost[intra_filter_ctx][filter];
+        this_rate = tokenonly_rd_stats.rate + rate_overhead;
+#if CONFIG_INTRA_INTERP
+        this_rate += cpi->intra_filter_cost[intra_filter_ctx][filter];
+#endif  // CONFIG_INTRA_INTERP
         this_rd =
             RDCOST(x->rdmult, x->rddiv, this_rate, tokenonly_rd_stats.dist);
-        if (i == 0 && filter == INTRA_FILTER_LINEAR && best_rd < INT64_MAX &&
-            this_rd > best_rd * rd_adjust)
+        if (first_try && best_rd < INT64_MAX && this_rd > best_rd * rd_adjust)
           return best_rd;
+        first_try = 0;
         if (this_rd < best_rd) {
           best_i = i;
           best_rd = this_rd;
           best_angle_delta = mbmi->angle_delta[0];
           best_tx_size = mbmi->tx_size;
+#if CONFIG_INTRA_INTERP
           best_filter = mbmi->intra_filter;
+#endif  // CONFIG_INTRA_INTERP
           best_tx_type = mbmi->tx_type;
           *rate = this_rate;
           *rate_tokenonly = tokenonly_rd_stats.rate;
           *distortion = tokenonly_rd_stats.dist;
           *skippable = tokenonly_rd_stats.skip;
         }
+#if CONFIG_INTRA_INTERP
       }
+#endif  // CONFIG_INTRA_INTERP
     }
 
     if (best_i >= 0) {
       for (j = 0; j < level2; ++j) {
         mic->mbmi.angle_delta[0] = deltas_level2[best_i][j];
+#if CONFIG_INTRA_INTERP
         p_angle =
             mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
         for (filter = INTRA_FILTER_LINEAR; filter < INTRA_FILTERS; ++filter) {
@@ -2658,19 +2676,30 @@
                !av1_is_intra_filter_switchable(p_angle)) &&
               filter != INTRA_FILTER_LINEAR)
             continue;
+#endif  // CONFIG_INTRA_INTERP
           pick_intra_angle_routine_sby(
               cpi, x, rate, rate_tokenonly, distortion, skippable,
-              &best_angle_delta, &best_tx_size, &best_tx_type, &best_filter,
+              &best_angle_delta, &best_tx_size, &best_tx_type,
+#if CONFIG_INTRA_INTERP
+              &best_filter,
+#endif  // CONFIG_INTRA_INTERP
               bsize,
+#if CONFIG_INTRA_INTERP
               rate_overhead + cpi->intra_filter_cost[intra_filter_ctx][filter],
+#else
+            rate_overhead,
+#endif  // CONFIG_INTRA_INTERP
               &best_rd);
+#if CONFIG_INTRA_INTERP
         }
+#endif  // CONFIG_INTRA_INTERP
       }
     }
   } else {
     for (angle_delta = -MAX_ANGLE_DELTAS; angle_delta <= MAX_ANGLE_DELTAS;
          ++angle_delta) {
       mbmi->angle_delta[0] = angle_delta;
+#if CONFIG_INTRA_INTERP
       p_angle =
           mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
       for (filter = INTRA_FILTER_LINEAR; filter < INTRA_FILTERS; ++filter) {
@@ -2678,16 +2707,27 @@
         if ((FILTER_FAST_SEARCH || !av1_is_intra_filter_switchable(p_angle)) &&
             filter != INTRA_FILTER_LINEAR)
           continue;
+#endif  // CONFIG_INTRA_INTERP
         pick_intra_angle_routine_sby(
             cpi, x, rate, rate_tokenonly, distortion, skippable,
-            &best_angle_delta, &best_tx_size, &best_tx_type, &best_filter,
+            &best_angle_delta, &best_tx_size, &best_tx_type,
+#if CONFIG_INTRA_INTERP
+            &best_filter,
+#endif  // CONFIG_INTRA_INTERP
             bsize,
+#if CONFIG_INTRA_INTERP
             rate_overhead + cpi->intra_filter_cost[intra_filter_ctx][filter],
+#else
+          rate_overhead,
+#endif  // CONFIG_INTRA_INTERP
             &best_rd);
+#if CONFIG_INTRA_INTERP
       }
+#endif  // CONFIG_INTRA_INTERP
     }
   }
 
+#if CONFIG_INTRA_INTERP
   if (FILTER_FAST_SEARCH && *rate_tokenonly < INT_MAX) {
     mbmi->angle_delta[0] = best_angle_delta;
     p_angle = mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
@@ -2698,15 +2738,22 @@
             cpi, x, rate, rate_tokenonly, distortion, skippable,
             &best_angle_delta, &best_tx_size, &best_tx_type, &best_filter,
             bsize,
+#if CONFIG_INTRA_INTERP
             rate_overhead + cpi->intra_filter_cost[intra_filter_ctx][filter],
+#else
+            rate_overhead,
+#endif  // CONFIG_INTRA_INTERP
             &best_rd);
       }
     }
   }
+#endif  // CONFIG_INTRA_INTERP
 
   mbmi->tx_size = best_tx_size;
   mbmi->angle_delta[0] = best_angle_delta;
+#if CONFIG_INTRA_INTERP
   mic->mbmi.intra_filter = best_filter;
+#endif  // CONFIG_INTRA_INTERP
   mbmi->tx_type = best_tx_type;
   return best_rd;
 }
@@ -2857,9 +2904,11 @@
   const int cols = block_size_wide[bsize];
 #endif  // CONFIG_EXT_INTRA || CONFIG_PALETTE
 #if CONFIG_EXT_INTRA
+#if CONFIG_INTRA_INTERP
   const int intra_filter_ctx = av1_get_pred_context_intra_interp(xd);
-  int is_directional_mode, rate_overhead, best_angle_delta = 0;
   INTRA_FILTER best_filter = INTRA_FILTER_LINEAR;
+#endif  // CONFIG_INTRA_INTERP
+  int is_directional_mode, rate_overhead, best_angle_delta = 0;
   uint8_t directional_mode_skip_mask[INTRA_MODES];
   const int src_stride = x->plane[0].src.stride;
   const uint8_t *src = x->plane[0].src.buf;
@@ -2987,15 +3036,17 @@
 #endif  // CONFIG_FILTER_INTRA
 #if CONFIG_EXT_INTRA
     if (is_directional_mode) {
+#if CONFIG_INTRA_INTERP
       int p_angle;
-      this_rate +=
-          write_uniform_cost(2 * MAX_ANGLE_DELTAS + 1,
-                             MAX_ANGLE_DELTAS + mic->mbmi.angle_delta[0]);
       p_angle = mode_to_angle_map[mic->mbmi.mode] +
                 mic->mbmi.angle_delta[0] * ANGLE_STEP;
       if (av1_is_intra_filter_switchable(p_angle))
         this_rate +=
             cpi->intra_filter_cost[intra_filter_ctx][mic->mbmi.intra_filter];
+#endif  // CONFIG_INTRA_INTERP
+      this_rate +=
+          write_uniform_cost(2 * MAX_ANGLE_DELTAS + 1,
+                             MAX_ANGLE_DELTAS + mic->mbmi.angle_delta[0]);
     }
 #endif  // CONFIG_EXT_INTRA
     this_rd = RDCOST(x->rdmult, x->rddiv, this_rate, this_distortion);
@@ -3011,7 +3062,9 @@
       best_tx = mic->mbmi.tx_size;
 #if CONFIG_EXT_INTRA
       best_angle_delta = mic->mbmi.angle_delta[0];
+#if CONFIG_INTRA_INTERP
       best_filter = mic->mbmi.intra_filter;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
       beat_best_rd = 1;
@@ -3066,7 +3119,9 @@
   mic->mbmi.tx_size = best_tx;
 #if CONFIG_EXT_INTRA
   mic->mbmi.angle_delta[0] = best_angle_delta;
+#if CONFIG_INTRA_INTERP
   mic->mbmi.intra_filter = best_filter;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
   mic->mbmi.tx_type = best_tx_type;
 #if CONFIG_PALETTE
@@ -9191,14 +9246,16 @@
       }
 #if CONFIG_EXT_INTRA
       if (is_directional_mode) {
+#if CONFIG_INTRA_INTERP
         int p_angle;
         const int intra_filter_ctx = av1_get_pred_context_intra_interp(xd);
-        rate2 += write_uniform_cost(2 * MAX_ANGLE_DELTAS + 1,
-                                    MAX_ANGLE_DELTAS + mbmi->angle_delta[0]);
         p_angle =
             mode_to_angle_map[mbmi->mode] + mbmi->angle_delta[0] * ANGLE_STEP;
         if (av1_is_intra_filter_switchable(p_angle))
           rate2 += cpi->intra_filter_cost[intra_filter_ctx][mbmi->intra_filter];
+#endif  // CONFIG_INTRA_INTERP
+        rate2 += write_uniform_cost(2 * MAX_ANGLE_DELTAS + 1,
+                                    MAX_ANGLE_DELTAS + mbmi->angle_delta[0]);
       }
       if (mbmi->uv_mode != DC_PRED && mbmi->uv_mode != TM_PRED) {
         rate2 += write_uniform_cost(2 * MAX_ANGLE_DELTAS + 1,
@@ -9258,7 +9315,9 @@
 #if CONFIG_EXT_INTRA
         mbmi->angle_delta[0] = 0;
         mbmi->angle_delta[1] = 0;
+#if CONFIG_INTRA_INTERP
         mbmi->intra_filter = INTRA_FILTER_LINEAR;
+#endif  // CONFIG_INTRA_INTERP
 #endif  // CONFIG_EXT_INTRA
 #if CONFIG_FILTER_INTRA
         mbmi->filter_intra_mode_info.use_filter_intra_mode[0] = 0;