Chromecast: IPC messages for browser-based media pipeline.

R=xhwang@chromium.org,damienv@chromium.org,tsepez@chromium.org
BUG=408189

Review URL: https://codereview.chromium.org/797793004

Cr-Commit-Position: refs/heads/master@{#308751}
diff --git a/chromecast/chromecast.gyp b/chromecast/chromecast.gyp
index 7bf8629..b5fd7bc 100644
--- a/chromecast/chromecast.gyp
+++ b/chromecast/chromecast.gyp
@@ -410,6 +410,22 @@
             }],
           ]
         },  # end of target 'cast_crash_client'
+        {
+          'target_name': 'cast_shell_media',
+          'type': '<(component)',
+          'dependencies': [
+            'media/media.gyp:cast_media',
+            '../content/content.gyp:content',
+            '../ipc/ipc.gyp:ipc',
+          ],
+          'sources': [
+            'common/media/cma_messages.h',
+            'common/media/cma_message_generator.cc',
+            'common/media/cma_message_generator.h',
+            'common/media/cma_param_traits.cc',
+            'common/media/cma_param_traits.h',
+          ],
+        },  # end of target 'cast_shell_media'
         # This target contains all of the primary code of |cast_shell|, except
         # for |main|. This allows end-to-end tests using |cast_shell|.
         # This also includes all targets that cannot be built on Android.
@@ -419,6 +435,7 @@
           'dependencies': [
             'cast_crash_client',
             'cast_net',
+            'cast_shell_media',
             'cast_shell_common',
             'media/media.gyp:cast_media',
             '../ui/aura/aura.gyp:aura_test_support',
diff --git a/chromecast/common/media/DEPS b/chromecast/common/media/DEPS
new file mode 100644
index 0000000..b1e00c8
--- /dev/null
+++ b/chromecast/common/media/DEPS
@@ -0,0 +1,4 @@
+include_rules = [
+  "+chromecast/media",
+  "+media/base",
+]
diff --git a/chromecast/common/media/OWNERS b/chromecast/common/media/OWNERS
new file mode 100644
index 0000000..b4e262d
--- /dev/null
+++ b/chromecast/common/media/OWNERS
@@ -0,0 +1,25 @@
+# Changes to IPC messages require a security review to avoid introducing
+# new sandbox escapes.
+per-file *_message*.h=set noparent
+per-file *_message*.h=dcheng@chromium.org
+per-file *_message*.h=inferno@chromium.org
+per-file *_message*.h=jln@chromium.org
+per-file *_message*.h=jschuh@chromium.org
+per-file *_message*.h=kenrb@chromium.org
+per-file *_message*.h=mkwst@chromium.org
+per-file *_message*.h=nasko@chromium.org
+per-file *_message*.h=palmer@chromium.org
+per-file *_message*.h=tsepez@chromium.org
+per-file *_message*.h=wfh@chromium.org
+
+per-file *_messages.cc=set noparent
+per-file *_messages.cc=dcheng@chromium.org
+per-file *_messages.cc=inferno@chromium.org
+per-file *_messages.cc=jln@chromium.org
+per-file *_messages.cc=jschuh@chromium.org
+per-file *_messages.cc=kenrb@chromium.org
+per-file *_messages.cc=mkwst@chromium.org
+per-file *_messages.cc=nasko@chromium.org
+per-file *_messages.cc=palmer@chromium.org
+per-file *_messages.cc=tsepez@chromium.org
+per-file *_messages.cc=wfh@chromium.org
diff --git a/chromecast/common/media/cma_message_generator.cc b/chromecast/common/media/cma_message_generator.cc
new file mode 100644
index 0000000..c6ca739
--- /dev/null
+++ b/chromecast/common/media/cma_message_generator.cc
@@ -0,0 +1,33 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Get basic type definitions.
+#define IPC_MESSAGE_IMPL
+#include "chromecast/common/media/cma_message_generator.h"
+
+// Generate constructors.
+#include "ipc/struct_constructor_macros.h"
+#include "chromecast/common/media/cma_message_generator.h"
+
+// Generate destructors.
+#include "ipc/struct_destructor_macros.h"
+#include "chromecast/common/media/cma_message_generator.h"
+
+// Generate param traits write methods.
+#include "ipc/param_traits_write_macros.h"
+namespace IPC {
+#include "chromecast/common/media/cma_message_generator.h"
+}  // namespace IPC
+
+// Generate param traits read methods.
+#include "ipc/param_traits_read_macros.h"
+namespace IPC {
+#include "chromecast/common/media/cma_message_generator.h"
+}  // namespace IPC
+
+// Generate param traits log methods.
+#include "ipc/param_traits_log_macros.h"
+namespace IPC {
+#include "chromecast/common/media/cma_message_generator.h"
+}  // namespace IPC
diff --git a/chromecast/common/media/cma_message_generator.h b/chromecast/common/media/cma_message_generator.h
new file mode 100644
index 0000000..805066d
--- /dev/null
+++ b/chromecast/common/media/cma_message_generator.h
@@ -0,0 +1,8 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Multiply-included file, hence no include guard.
+
+#include "chromecast/common/media/cma_messages.h"
+
diff --git a/chromecast/common/media/cma_messages.h b/chromecast/common/media/cma_messages.h
new file mode 100644
index 0000000..279147a
--- /dev/null
+++ b/chromecast/common/media/cma_messages.h
@@ -0,0 +1,114 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// IPC messages for the Cast Media Acceleration (CMA) pipeline.
+// Multiply-included message file, hence no include guard.
+
+#include "chromecast/common/media/cma_param_traits.h"
+#include "chromecast/common/media/cma_param_traits_macros.h"
+#include "chromecast/media/cma/pipeline/load_type.h"
+#include "content/public/common/common_param_traits.h"
+#include "ipc/ipc_message_macros.h"
+#include "media/base/audio_decoder_config.h"
+#include "media/base/buffering_state.h"
+#include "media/base/pipeline_status.h"
+#include "media/base/video_decoder_config.h"
+#include "ui/gfx/ipc/gfx_param_traits.h"
+
+#undef IPC_MESSAGE_EXPORT
+#define IPC_MESSAGE_EXPORT
+#define IPC_MESSAGE_START CastMediaMsgStart
+
+// Messages sent from the renderer to the browser process.
+
+IPC_MESSAGE_CONTROL2(CmaHostMsg_CreateMedia,
+                     int /* Media pipeline ID */,
+                     chromecast::media::LoadType /* Load type */)
+IPC_MESSAGE_CONTROL1(CmaHostMsg_DestroyMedia,
+                     int /* Media pipeline ID */)
+IPC_MESSAGE_CONTROL3(CmaHostMsg_SetCdm,
+                     int /* Media pipeline ID */,
+                     int /* render_frame_id */,
+                     int /* cdm_id */)
+IPC_MESSAGE_CONTROL2(CmaHostMsg_StartPlayingFrom,
+                     int /* Media pipeline ID */,
+                     base::TimeDelta /* Timestamp */)
+IPC_MESSAGE_CONTROL1(CmaHostMsg_Flush,
+                     int /* Media pipeline ID */)
+IPC_MESSAGE_CONTROL1(CmaHostMsg_Stop,
+                     int /* Media pipeline ID */)
+IPC_MESSAGE_CONTROL2(CmaHostMsg_SetPlaybackRate,
+                     int /* Media pipeline ID */,
+                     float /* Playback rate */)
+
+IPC_MESSAGE_CONTROL3(CmaHostMsg_CreateAvPipe,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     size_t /* Fifo size */);
+IPC_MESSAGE_CONTROL3(CmaHostMsg_AudioInitialize,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     media::AudioDecoderConfig /* Audio config */)
+IPC_MESSAGE_CONTROL3(CmaHostMsg_VideoInitialize,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     media::VideoDecoderConfig /* Video config */)
+IPC_MESSAGE_CONTROL3(CmaHostMsg_SetVolume,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     float /* Volume */)
+IPC_MESSAGE_CONTROL2(CmaHostMsg_NotifyPipeWrite,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */)
+
+IPC_MESSAGE_CONTROL5(CmaHostMsg_NotifyExternalSurface,
+                     int /* Surface ID */,
+                     gfx::PointF /* Quad video top left */,
+                     gfx::PointF /* Quad video top right */,
+                     gfx::PointF /* Quad video bottim right */,
+                     gfx::PointF /* Quad video bottom left */)
+
+// Messages from the browser to the renderer process.
+
+IPC_MESSAGE_CONTROL2(CmaMsg_MediaStateChanged,
+                     int /* Media pipeline ID */,
+                     media::PipelineStatus /* Status */)
+IPC_MESSAGE_CONTROL4(CmaMsg_TimeUpdate,
+                     int /* Media pipeline ID */,
+                     base::TimeDelta /* Media time */,
+                     base::TimeDelta /* Max media time */,
+                     base::TimeTicks /* STC */)
+IPC_MESSAGE_CONTROL2(CmaMsg_BufferingNotification,
+                     int /* Media pipeline ID */,
+                     media::BufferingState /* Buffering state */)
+
+IPC_MESSAGE_CONTROL5(CmaMsg_AvPipeCreated,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     bool /* Status */,
+                     base::SharedMemoryHandle /* Shared memory */,
+                     base::FileDescriptor /* socket handle */)
+IPC_MESSAGE_CONTROL3(CmaMsg_TrackStateChanged,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     media::PipelineStatus /* Status */)
+IPC_MESSAGE_CONTROL2(CmaMsg_NotifyPipeRead,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */)
+
+IPC_MESSAGE_CONTROL2(CmaMsg_Eos,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */)
+IPC_MESSAGE_CONTROL3(CmaMsg_PlaybackError,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     media::PipelineStatus /* status */)
+IPC_MESSAGE_CONTROL3(CmaMsg_PlaybackStatistics,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     media::PipelineStatistics /* status */)
+IPC_MESSAGE_CONTROL3(CmaMsg_NaturalSizeChanged,
+                     int /* Media pipeline ID */,
+                     int /* Track ID */,
+                     gfx::Size /* Size */)
diff --git a/chromecast/common/media/cma_param_traits.cc b/chromecast/common/media/cma_param_traits.cc
new file mode 100644
index 0000000..dc86959
--- /dev/null
+++ b/chromecast/common/media/cma_param_traits.cc
@@ -0,0 +1,122 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chromecast/common/media/cma_param_traits.h"
+
+#include <vector>
+
+#include "chromecast/common/media/cma_param_traits_macros.h"
+#include "content/public/common/common_param_traits.h"
+#include "ipc/ipc_message_macros.h"
+#include "media/base/audio_decoder_config.h"
+#include "media/base/video_decoder_config.h"
+#include "ui/gfx/ipc/gfx_param_traits.h"
+
+namespace IPC {
+
+void ParamTraits<media::AudioDecoderConfig>::Write(
+    Message* m, const media::AudioDecoderConfig& p) {
+  ParamTraits<media::AudioCodec>::Write(m, p.codec());
+  ParamTraits<media::SampleFormat>::Write(m, p.sample_format());
+  ParamTraits<media::ChannelLayout>::Write(m, p.channel_layout());
+  ParamTraits<int>::Write(m, p.samples_per_second());
+  ParamTraits<bool>::Write(m, p.is_encrypted());
+  std::vector<uint8> extra_data;
+  if (p.extra_data_size() > 0) {
+    extra_data =
+        std::vector<uint8>(p.extra_data(),
+                           p.extra_data() + p.extra_data_size());
+  }
+  ParamTraits<std::vector<uint8> >::Write(m, extra_data);
+}
+
+bool ParamTraits<media::AudioDecoderConfig>::Read(
+    const Message* m, PickleIterator* iter,
+    media::AudioDecoderConfig* r) {
+  media::AudioCodec codec;
+  media::SampleFormat sample_format;
+  media::ChannelLayout channel_layout;
+  int samples_per_second;
+  bool is_encrypted;
+  if (!ParamTraits<media::AudioCodec>::Read(m, iter, &codec) ||
+      !ParamTraits<media::SampleFormat>::Read(m, iter, &sample_format) ||
+      !ParamTraits<media::ChannelLayout>::Read(m, iter, &channel_layout) ||
+      !ParamTraits<int>::Read(m, iter, &samples_per_second) ||
+      !ParamTraits<bool>::Read(m, iter, &is_encrypted)) {
+    return false;
+  }
+  std::vector<uint8> extra_data;
+  if (!ParamTraits<std::vector<uint8> >::Read(m, iter, &extra_data))
+    return false;
+  const uint8* extra_data_ptr = NULL;
+  if (extra_data.size() > 0)
+    extra_data_ptr = &extra_data[0];
+  *r = media::AudioDecoderConfig(codec, sample_format, channel_layout,
+                                 samples_per_second,
+                                 extra_data_ptr, extra_data.size(),
+                                 is_encrypted);
+  return true;
+}
+
+void ParamTraits<media::AudioDecoderConfig>::Log(
+    const media::AudioDecoderConfig& p, std::string* l) {
+  l->append(base::StringPrintf("<AudioDecoderConfig>"));
+}
+
+void ParamTraits<media::VideoDecoderConfig>::Write(
+    Message* m, const media::VideoDecoderConfig& p) {
+  ParamTraits<media::VideoCodec>::Write(m, p.codec());
+  ParamTraits<media::VideoCodecProfile>::Write(m, p.profile());
+  ParamTraits<media::VideoFrame::Format>::Write(m, p.format());
+  ParamTraits<gfx::Size>::Write(m, p.coded_size());
+  ParamTraits<gfx::Rect>::Write(m, p.visible_rect());
+  ParamTraits<gfx::Size>::Write(m, p.natural_size());
+  ParamTraits<bool>::Write(m, p.is_encrypted());
+  std::vector<uint8> extra_data;
+  if (p.extra_data_size() > 0) {
+    extra_data =
+        std::vector<uint8>(p.extra_data(),
+                           p.extra_data() + p.extra_data_size());
+  }
+  ParamTraits<std::vector<uint8> >::Write(m, extra_data);
+}
+
+bool ParamTraits<media::VideoDecoderConfig>::Read(
+    const Message* m, PickleIterator* iter,
+    media::VideoDecoderConfig* r) {
+  media::VideoCodec codec;
+  media::VideoCodecProfile profile;
+  media::VideoFrame::Format format;
+  gfx::Size coded_size;
+  gfx::Rect visible_rect;
+  gfx::Size natural_size;
+  bool is_encrypted;
+  if (!ParamTraits<media::VideoCodec>::Read(m, iter, &codec) ||
+      !ParamTraits<media::VideoCodecProfile>::Read(m, iter, &profile) ||
+      !ParamTraits<media::VideoFrame::Format>::Read(m, iter, &format) ||
+      !ParamTraits<gfx::Size>::Read(m, iter, &coded_size) ||
+      !ParamTraits<gfx::Rect>::Read(m, iter, &visible_rect) ||
+      !ParamTraits<gfx::Size>::Read(m, iter, &natural_size) ||
+      !ParamTraits<bool>::Read(m, iter, &is_encrypted)) {
+    return false;
+  }
+  std::vector<uint8> extra_data;
+  if (!ParamTraits<std::vector<uint8> >::Read(m, iter, &extra_data))
+    return false;
+  const uint8* extra_data_ptr = NULL;
+  if (extra_data.size() > 0)
+    extra_data_ptr = &extra_data[0];
+  *r = media::VideoDecoderConfig(codec, profile, format,
+                                 coded_size, visible_rect, natural_size,
+                                 extra_data_ptr, extra_data.size(),
+                                 is_encrypted);
+  return true;
+}
+
+void ParamTraits<media::VideoDecoderConfig>::Log(
+    const media::VideoDecoderConfig& p, std::string* l) {
+  l->append(base::StringPrintf("<VideoDecoderConfig>"));
+}
+
+}  // namespace IPC
diff --git a/chromecast/common/media/cma_param_traits.h b/chromecast/common/media/cma_param_traits.h
new file mode 100644
index 0000000..0bebac3
--- /dev/null
+++ b/chromecast/common/media/cma_param_traits.h
@@ -0,0 +1,35 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_H_
+#define CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_H_
+
+#include "ipc/ipc_message_utils.h"
+
+namespace media {
+class AudioDecoderConfig;
+class VideoDecoderConfig;
+}
+
+namespace IPC {
+
+template <>
+struct ParamTraits<media::AudioDecoderConfig> {
+  typedef media::AudioDecoderConfig param_type;
+  static void Write(Message* m, const param_type& p);
+  static bool Read(const Message* m, PickleIterator* iter, param_type* r);
+  static void Log(const param_type& p, std::string* l);
+};
+
+template <>
+struct ParamTraits<media::VideoDecoderConfig> {
+  typedef media::VideoDecoderConfig param_type;
+  static void Write(Message* m, const param_type& p);
+  static bool Read(const Message* m, PickleIterator* iter, param_type* r);
+  static void Log(const param_type& p, std::string* l);
+};
+
+}  // namespace IPC
+
+#endif  // CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_H_
diff --git a/chromecast/common/media/cma_param_traits_macros.h b/chromecast/common/media/cma_param_traits_macros.h
new file mode 100644
index 0000000..865fb8d
--- /dev/null
+++ b/chromecast/common/media/cma_param_traits_macros.h
@@ -0,0 +1,59 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// Singly or Multiply-included shared traits file depending on circumstances.
+// This allows the use of IPC serialization macros in more than one IPC message
+// file.
+#ifndef CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_MACROS_H_
+#define CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_MACROS_H_
+
+#include "chromecast/media/cma/pipeline/load_type.h"
+#include "ipc/ipc_message_macros.h"
+#include "ipc/param_traits_macros.h"
+#include "media/base/audio_decoder_config.h"
+#include "media/base/buffering_state.h"
+#include "media/base/channel_layout.h"
+#include "media/base/pipeline_status.h"
+#include "media/base/sample_format.h"
+#include "media/base/video_decoder_config.h"
+#include "media/base/video_frame.h"
+
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(chromecast::media::LoadType,
+                              chromecast::media::kLoadTypeURL,
+                              chromecast::media::kLoadTypeMediaStream)
+
+// TODO (gunsch): move media enum IPC code to a common location in media.
+// See crbug.com/442594 for details.
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::AudioCodec,
+                              media::AudioCodec::kUnknownAudioCodec,
+                              media::AudioCodec::kAudioCodecMax)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::BufferingState,
+                              media::BUFFERING_HAVE_NOTHING,
+                              media::BUFFERING_HAVE_ENOUGH)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::SampleFormat,
+                              media::SampleFormat::kUnknownSampleFormat,
+                              media::SampleFormat::kSampleFormatMax)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::ChannelLayout,
+                              media::ChannelLayout::CHANNEL_LAYOUT_NONE,
+                              media::ChannelLayout::CHANNEL_LAYOUT_MAX)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::PipelineStatus,
+                              media::PIPELINE_OK,
+                              media::PIPELINE_STATUS_MAX)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::VideoCodec,
+                              media::VideoCodec::kUnknownVideoCodec,
+                              media::VideoCodec::kVideoCodecMax)
+IPC_ENUM_TRAITS_MIN_MAX_VALUE(media::VideoCodecProfile,
+                              media::VIDEO_CODEC_PROFILE_MIN,
+                              media::VIDEO_CODEC_PROFILE_MAX)
+IPC_ENUM_TRAITS_MAX_VALUE(media::VideoFrame::Format,
+                          media::VideoFrame::FORMAT_MAX)
+
+IPC_STRUCT_TRAITS_BEGIN(media::PipelineStatistics)
+  IPC_STRUCT_TRAITS_MEMBER(audio_bytes_decoded)
+  IPC_STRUCT_TRAITS_MEMBER(video_bytes_decoded)
+  IPC_STRUCT_TRAITS_MEMBER(video_frames_decoded)
+  IPC_STRUCT_TRAITS_MEMBER(video_frames_dropped)
+IPC_STRUCT_TRAITS_END()
+
+#endif  // CHROMECAST_COMMON_MEDIA_CMA_PARAM_TRAITS_MACROS_H_
diff --git a/ipc/ipc_message_start.h b/ipc/ipc_message_start.h
index a44a7a7..a1465fa 100644
--- a/ipc/ipc_message_start.h
+++ b/ipc/ipc_message_start.h
@@ -115,6 +115,7 @@
   DnsPrefetchMsgStart,
   BluetoothMsgStart,
   NavigatorConnectMsgStart,
+  CastMediaMsgStart,
   LastIPCMsgStart  // Must come last.
 };