Chromium Code Reviews| Index: webkit/glue/plugins/pepper_audio.cc |
| =================================================================== |
| --- webkit/glue/plugins/pepper_audio.cc (revision 66651) |
| +++ webkit/glue/plugins/pepper_audio.cc (working copy) |
| @@ -5,8 +5,9 @@ |
| #include "webkit/glue/plugins/pepper_audio.h" |
| #include "base/logging.h" |
| -#include "ppapi/c/dev/ppb_audio_dev.h" |
| -#include "ppapi/c/dev/ppb_audio_trusted_dev.h" |
| +#include "third_party/ppapi/c/pp_completion_callback.h" |
|
brettw
2010/11/22 18:22:09
Alphabetize the headers.
nfullagar
2010/11/23 02:48:58
Done.
|
| +#include "third_party/ppapi/c/dev/ppb_audio_dev.h" |
| +#include "third_party/ppapi/c/dev/ppb_audio_trusted_dev.h" |
| #include "webkit/glue/plugins/pepper_common.h" |
| namespace pepper { |
| @@ -77,13 +78,14 @@ |
| // PPB_Audio ------------------------------------------------------------------- |
| PP_Resource Create(PP_Instance instance_id, PP_Resource config_id, |
| - PPB_Audio_Callback callback, void* user_data) { |
| + PPB_Audio_Callback user_callback, void* user_data) { |
| PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id); |
| if (!instance) |
| return 0; |
| // TODO(neb): Require callback to be present for untrusted plugins. |
| - scoped_refptr<Audio> audio(new Audio(instance->module())); |
| - if (!audio->Init(instance->delegate(), config_id, callback, user_data)) |
| + scoped_refptr<Audio> audio(new Audio(instance->module(), instance_id)); |
| + if (!audio->Init(instance->delegate(), config_id, |
| + user_callback, user_data)) |
| return 0; |
| return audio->GetReference(); |
| } |
| @@ -118,19 +120,63 @@ |
| // PPB_AudioTrusted ------------------------------------------------------------ |
| -PP_Resource GetBuffer(PP_Resource audio_id) { |
| - // TODO(neb): Implement me! |
| - return 0; |
| +PP_Resource CreateTrusted(PP_Instance instance_id) { |
| + PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id); |
| + if (!instance) |
| + return 0; |
| + scoped_refptr<Audio> audio(new Audio(instance->module(), instance_id)); |
| + return audio->GetReference(); |
| } |
| -int GetOSDescriptor(PP_Resource audio_id) { |
| - // TODO(neb): Implement me! |
| - return -1; |
| +int32_t Open(PP_Resource audio_id, |
| + PP_Resource config_id, |
| + PP_CompletionCallback created) { |
| + scoped_refptr<Audio> audio = Resource::GetAs<Audio>(audio_id); |
| + if (!audio) { |
| + PP_RunCompletionCallback(&created, -1); |
|
brettw
2010/11/22 18:22:09
Don't hard code the error values. Use PP_ERROR_* i
nfullagar
2010/11/23 02:48:58
replaced with PP_ERROR_FAILED and removed PP_RunCo
|
| + return -1; |
| + } |
| + PP_Instance instance_id = audio->GetInstance(); |
| + PluginInstance* instance = ResourceTracker::Get()->GetInstance(instance_id); |
| + if (!instance) { |
| + PP_RunCompletionCallback(&created, -1); |
| + return -1; |
| + } |
| + // At this point we're passing ownership of |created| so |audio| will be |
| + // responsible for firing the completion callback. |
| + return audio->OpenTrusted(instance->delegate(), config_id, created); |
| } |
| +PP_Bool GetSyncSocket(PP_Resource audio_id, int* sync_socket) { |
| + scoped_refptr<Audio> audio = Resource::GetAs<Audio>(audio_id); |
| + if (audio) { |
|
brettw
2010/11/22 18:22:09
Be consistent about using {} for single-line condi
nfullagar
2010/11/23 02:48:58
Done.
|
| + return BoolToPPBool(audio->GetSyncSocket(sync_socket)); |
| + } |
| + return PP_FALSE; |
| +} |
| + |
| +PP_Bool GetSharedMemory(PP_Resource audio_id, |
| + uint64_t* shm_handle, |
| + int32_t* shm_size) { |
| + scoped_refptr<Audio> audio = Resource::GetAs<Audio>(audio_id); |
| + if (audio) { |
| + return BoolToPPBool(audio->GetSharedMemory(shm_handle, shm_size)); |
| + } |
| + return PP_FALSE; |
| +} |
| + |
| +void Close(PP_Resource audio_id) { |
| + scoped_refptr<Audio> audio = Resource::GetAs<Audio>(audio_id); |
| + if (audio) |
| + audio->CloseTrusted(); |
| +} |
| + |
| const PPB_AudioTrusted_Dev ppb_audiotrusted = { |
| - &GetBuffer, |
| - &GetOSDescriptor |
| + &CreateTrusted, |
| + &Open, |
| + &GetSyncSocket, |
| + &GetSharedMemory, |
| + &Close |
| }; |
| } // namespace |
| @@ -165,25 +211,33 @@ |
| // Audio ----------------------------------------------------------------------- |
| -Audio::Audio(PluginModule* module) |
| +Audio::Audio(PluginModule* module, PP_Instance instance_id) |
| : Resource(module), |
| playing_(false), |
| + pp_instance_(instance_id), |
| + audio_(NULL), |
| socket_(NULL), |
| shared_memory_(NULL), |
| shared_memory_size_(0), |
| + shared_memory_handle_(0), |
| callback_(NULL), |
| - user_data_(NULL) { |
| + user_data_(NULL), |
| + create_callback_pending_(false) { |
| + create_callback_ = PP_MakeCompletionCallback(NULL, NULL); |
| } |
| Audio::~Audio() { |
| // Calling ShutDown() makes sure StreamCreated cannot be called anymore. |
| audio_->ShutDown(); |
| + audio_ = NULL; |
| // Closing the socket causes the thread to exit - wait for it. |
| socket_->Close(); |
| if (audio_thread_.get()) { |
| audio_thread_->Join(); |
| audio_thread_.reset(); |
| } |
| + // Fire pending completion callback if neccessary. |
| + CloseTrusted(); |
| // Shared memory destructor will unmap the memory automatically. |
| } |
| @@ -199,21 +253,71 @@ |
| return this; |
| } |
| -bool Audio::Init(PluginDelegate* plugin_delegate, PP_Resource config_id, |
| +bool Audio::Init(PluginDelegate* plugin_delegate, |
| + PP_Resource config_id, |
| PPB_Audio_Callback callback, void* user_data) { |
| - CHECK(!audio_.get()); |
| + CHECK(!audio_); |
| config_ = Resource::GetAs<AudioConfig>(config_id); |
| if (!config_) |
| return false; |
| callback_ = callback; |
| user_data_ = user_data; |
| - // When the stream is created, we'll get called back in StreamCreated(). |
| - audio_.reset(plugin_delegate->CreateAudio(config_->sample_rate(), |
| - config_->sample_frame_count(), |
| - this)); |
| - return audio_.get() != NULL; |
| + // When the stream is created, we'll get called back on StreamCreated(). |
| + audio_ = plugin_delegate->CreateAudio(config_->sample_rate(), |
| + config_->sample_frame_count(), |
| + this); |
| + return audio_ != NULL; |
| } |
| +int32_t Audio::OpenTrusted(PluginDelegate* plugin_delegate, |
| + PP_Resource config_id, |
| + PP_CompletionCallback create_callback) { |
| + CHECK(!audio_); |
| + create_callback_ = create_callback; |
| + create_callback_pending_ = true; |
| + config_ = Resource::GetAs<AudioConfig>(config_id); |
| + if (!config_) { |
| + CloseTrusted(); |
| + return -1; |
| + } |
| + // When the stream is created, we'll get called back on StreamCreated(). |
| + audio_ = plugin_delegate->CreateAudio(config_->sample_rate(), |
| + config_->sample_frame_count(), |
| + this); |
| + if (audio_ == NULL) { |
| + CloseTrusted(); |
| + return -1; |
| + } |
| + return 0; |
| +} |
| + |
| +void Audio::CloseTrusted() { |
| + // If the completion callback hasn't fired yet, do so here |
|
brettw
2010/11/22 18:22:09
Be sure your comments are complete sentences with
nfullagar
2010/11/23 02:48:58
done (this comment continues on the next line :)
|
| + // with an error condition. |
| + if (create_callback_pending_) { |
| + PP_RunCompletionCallback(&create_callback_, -1); |
| + create_callback_pending_ = false; |
| + } |
| + // TODO(audio): what else should go here vs. ~Audio destructor |
| +} |
| + |
| +bool Audio::GetSyncSocket(int *sync_socket) { |
| + if (socket_ != NULL) { |
| + *sync_socket = static_cast<int>(socket_->handle()); |
| + return true; |
| + } |
| + return false; |
| +} |
| + |
| +bool Audio::GetSharedMemory(uint64_t* shm_handle, int32_t* shm_size) { |
| + if (shared_memory_ != NULL) { |
| + *shm_handle = shared_memory_handle_; |
| + *shm_size = shared_memory_size_; |
| + return true; |
| + } |
| + return false; |
| +} |
| + |
| bool Audio::StartPlayback() { |
| if (playing_) |
| return true; |
| @@ -249,7 +353,19 @@ |
| socket_.reset(new base::SyncSocket(socket_handle)); |
| shared_memory_.reset(new base::SharedMemory(shared_memory_handle, false)); |
| shared_memory_size_ = shared_memory_size; |
| - |
| +#if OS_LINUX || OS_MAC |
| + shared_memory_handle_ = static_cast<uint64_t>(shared_memory_handle.fd); |
| +#elif OS_WIN |
| + shared_memory_handle_ = static_cast<uint64_t>(shared_memory_handle); |
| +#else |
| + #error "Unknown OS" |
| +#endif |
| + // Trusted side of proxy can specify a callback to recieve handles on. |
| + if (create_callback_pending_) { |
| + PP_RunCompletionCallback(&create_callback_, 0); |
| + create_callback_pending_ = false; |
| + } |
| + // Recurring callback to fill audio buffers. |
| if (callback_) { |
| shared_memory_->Map(shared_memory_size_); |
| // In common case StartPlayback() was called before StreamCreated(). |
| @@ -277,4 +393,3 @@ |
| } |
| } // namespace pepper |
| - |