Create output buffers for encoding parallel frames

Create additional output buffers to write packed bitstream of frames
encoded in parallel for FPMT.

Change-Id: Iac23d148361075f62774ee4e460e27903c8a1a12
diff --git a/av1/av1_cx_iface.c b/av1/av1_cx_iface.c
index f196cde..fb9f6ce 100644
--- a/av1/av1_cx_iface.c
+++ b/av1/av1_cx_iface.c
@@ -2381,6 +2381,13 @@
 
 static aom_codec_err_t encoder_destroy(aom_codec_alg_priv_t *ctx) {
   free(ctx->cx_data);
+#if CONFIG_FRAME_PARALLEL_ENCODE
+  for (int i = 0; i < ctx->ppi->num_fp_contexts - 1; i++) {
+    if (ctx->ppi->parallel_frames_data[i].cx_data_frame) {
+      free(ctx->ppi->parallel_frames_data[i].cx_data_frame);
+    }
+  }
+#endif
 
   if (ctx->ppi) {
     AV1_PRIMARY *ppi = ctx->ppi;
@@ -2479,6 +2486,22 @@
           return AOM_CODEC_MEM_ERROR;
         }
       }
+#if CONFIG_FRAME_PARALLEL_ENCODE
+      for (int i = 0; i < cpi->ppi->num_fp_contexts - 1; i++) {
+        if (cpi->ppi->parallel_frames_data[i].cx_data_frame == NULL) {
+          cpi->ppi->parallel_frames_data[i].cx_data_sz = uncompressed_frame_sz;
+          cpi->ppi->parallel_frames_data[i].frame_display_order_hint = -1;
+          cpi->ppi->parallel_frames_data[i].frame_size = 0;
+          cpi->ppi->parallel_frames_data[i].cx_data_frame =
+              (unsigned char *)malloc(
+                  cpi->ppi->parallel_frames_data[i].cx_data_sz);
+          if (cpi->ppi->parallel_frames_data[i].cx_data_frame == NULL) {
+            cpi->ppi->parallel_frames_data[i].cx_data_sz = 0;
+            return AOM_CODEC_MEM_ERROR;
+          }
+        }
+      }
+#endif
     }
   }
 
diff --git a/av1/encoder/encoder.h b/av1/encoder/encoder.h
index 6ef21b7..68736fb 100644
--- a/av1/encoder/encoder.h
+++ b/av1/encoder/encoder.h
@@ -2080,7 +2080,36 @@
 } CoeffBufferPool;
 
 #if CONFIG_FRAME_PARALLEL_ENCODE
+/*!
+ * \brief Max number of frames that can be encoded in a parallel encode set.
+ */
 #define MAX_PARALLEL_FRAMES 4
+
+/*!
+ * \brief Structure to hold data of frame encoded in a given parallel encode
+ * set.
+ */
+typedef struct AV1_FP_OUT_DATA {
+  /*!
+   * Buffer to store packed bitstream data of a frame.
+   */
+  unsigned char *cx_data_frame;
+
+  /*!
+   * Allocated size of the cx_data_frame buffer.
+   */
+  size_t cx_data_sz;
+
+  /*!
+   * Size of data written in the cx_data_frame buffer.
+   */
+  size_t frame_size;
+
+  /*!
+   * Display order hint of frame whose packed data is in cx_data_frame buffer.
+   */
+  int frame_display_order_hint;
+} AV1_FP_OUT_DATA;
 #endif  // CONFIG_FRAME_PARALLEL_ENCODE
 
 /*!
@@ -2097,6 +2126,12 @@
    * Number of frame level contexts(cpis)
    */
   int num_fp_contexts;
+
+  /*!
+   * Array of structures to hold data of frames encoded in a given parallel
+   * encode set.
+   */
+  struct AV1_FP_OUT_DATA parallel_frames_data[MAX_PARALLEL_FRAMES - 1];
 #endif  // CONFIG_FRAME_PARALLEL_ENCODE
   /*!
    * Encode stage top level structure