shithub: libvpx

Download patch

ref: c580428928260781d80ada0a39bb7e4b00a5f443
parent: 6865af63786ab9a41773cb9efc2c763f4fff7329
parent: bae652245d46e1b500e5c2ca5c2fd451dab291da
author: Pengchong Jin <pengchong@google.com>
date: Mon Jul 28 10:49:05 EDT 2014

Merge "Store block-wise statistics obtained in the first pass"

--- a/vp9/encoder/vp9_firstpass.c
+++ b/vp9/encoder/vp9_firstpass.c
@@ -599,7 +599,8 @@
 
 #if CONFIG_FP_MB_STATS
       if (cpi->use_fp_mb_stats) {
-        // TODO(pengchong): store some related block statistics here
+        // initialization
+        cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] = 0;
       }
 #endif
 
@@ -700,6 +701,33 @@
         // Start by assuming that intra mode is best.
         best_ref_mv.as_int = 0;
 
+#if CONFIG_FP_MB_STATS
+        if (cpi->use_fp_mb_stats) {
+          // intra predication statistics
+          cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] = 0;
+          cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+              FPMB_DCINTRA_MASK;
+          cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] &=
+              (~FPMB_NONZERO_MOTION_MASK);
+          if (this_error > FPMB_ERROR_LEVEL4_TH) {
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                FPMB_ERROR_LEVEL4_MASK;
+          } else if (this_error > FPMB_ERROR_LEVEL3_TH) {
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                FPMB_ERROR_LEVEL3_MASK;
+          } else if (this_error > FPMB_ERROR_LEVEL2_TH) {
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                FPMB_ERROR_LEVEL2_MASK;
+          } else if (this_error > FPMB_ERROR_LEVEL1_TH) {
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                FPMB_ERROR_LEVEL1_MASK;
+          } else {
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                FPMB_ERROR_LEVEL0_MASK;
+          }
+        }
+#endif
+
         if (motion_error <= this_error) {
           // Keep a count of cases where the inter and intra were very close
           // and very low. This helps with scene cut detection for example in
@@ -730,12 +758,40 @@
 
 #if CONFIG_FP_MB_STATS
           if (cpi->use_fp_mb_stats) {
-            // TODO(pengchong): save some related block statistics here
+            // inter predication statistics
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] = 0;
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] &=
+                (~FPMB_DCINTRA_MASK);
+            cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] &=
+                (~FPMB_NONZERO_MOTION_MASK);
+            if (this_error > FPMB_ERROR_LEVEL4_TH) {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_ERROR_LEVEL4_MASK;
+            } else if (this_error > FPMB_ERROR_LEVEL3_TH) {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_ERROR_LEVEL3_MASK;
+            } else if (this_error > FPMB_ERROR_LEVEL2_TH) {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_ERROR_LEVEL2_MASK;
+            } else if (this_error > FPMB_ERROR_LEVEL1_TH) {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_ERROR_LEVEL1_MASK;
+            } else {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_ERROR_LEVEL0_MASK;
+            }
           }
 #endif
 
           if (mv.as_int) {
             ++mvcount;
+
+#if CONFIG_FP_MB_STATS
+            if (cpi->use_fp_mb_stats) {
+              cpi->twopass.frame_mb_stats_buf[mb_row * cm->mb_cols + mb_col] |=
+                  FPMB_NONZERO_MOTION_MASK;
+            }
+#endif
 
             // Non-zero vector, was it different from the last non zero vector?
             if (mv.as_int != lastmv_as_int)
--- a/vp9/encoder/vp9_firstpass.h
+++ b/vp9/encoder/vp9_firstpass.h
@@ -19,6 +19,20 @@
 #endif
 
 #if CONFIG_FP_MB_STATS
+
+#define FPMB_DCINTRA_MASK 0x01
+#define FPMB_NONZERO_MOTION_MASK 0x02
+#define FPMB_ERROR_LEVEL0_MASK 0x04
+#define FPMB_ERROR_LEVEL1_MASK 0x10
+#define FPMB_ERROR_LEVEL2_MASK 0x20
+#define FPMB_ERROR_LEVEL3_MASK 0x40
+#define FPMB_ERROR_LEVEL4_MASK 0x80
+
+#define FPMB_ERROR_LEVEL1_TH 2000
+#define FPMB_ERROR_LEVEL2_TH 8000
+#define FPMB_ERROR_LEVEL3_TH 24000
+#define FPMB_ERROR_LEVEL4_TH 48000
+
 typedef struct {
   uint8_t *mb_stats_start;
   uint8_t *mb_stats_end;