| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "webkit/plugins/ppapi/ppb_audio_impl.h" | 5 #include "webkit/plugins/ppapi/ppb_audio_impl.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "ppapi/c/pp_completion_callback.h" | 8 #include "ppapi/c/pp_completion_callback.h" |
| 9 #include "ppapi/c/ppb_audio.h" | 9 #include "ppapi/c/ppb_audio.h" |
| 10 #include "ppapi/c/ppb_audio_config.h" | 10 #include "ppapi/c/ppb_audio_config.h" |
| (...skipping 10 matching lines...) Expand all Loading... |
| 21 using ppapi::thunk::PPB_Audio_API; | 21 using ppapi::thunk::PPB_Audio_API; |
| 22 using ppapi::thunk::PPB_AudioConfig_API; | 22 using ppapi::thunk::PPB_AudioConfig_API; |
| 23 | 23 |
| 24 namespace webkit { | 24 namespace webkit { |
| 25 namespace ppapi { | 25 namespace ppapi { |
| 26 | 26 |
| 27 // PPB_Audio_Impl -------------------------------------------------------------- | 27 // PPB_Audio_Impl -------------------------------------------------------------- |
| 28 | 28 |
| 29 PPB_Audio_Impl::PPB_Audio_Impl(PP_Instance instance) | 29 PPB_Audio_Impl::PPB_Audio_Impl(PP_Instance instance) |
| 30 : Resource(instance), | 30 : Resource(instance), |
| 31 audio_(NULL), | 31 audio_(NULL) { |
| 32 create_callback_pending_(false), | |
| 33 shared_memory_size_for_create_callback_(0) { | |
| 34 create_callback_ = PP_MakeCompletionCallback(NULL, NULL); | |
| 35 } | 32 } |
| 36 | 33 |
| 37 PPB_Audio_Impl::~PPB_Audio_Impl() { | 34 PPB_Audio_Impl::~PPB_Audio_Impl() { |
| 38 // Calling ShutDown() makes sure StreamCreated cannot be called anymore and | 35 // Calling ShutDown() makes sure StreamCreated cannot be called anymore and |
| 39 // releases the audio data associated with the pointer. Note however, that | 36 // releases the audio data associated with the pointer. Note however, that |
| 40 // until ShutDown returns, StreamCreated may still be called. This will be | 37 // until ShutDown returns, StreamCreated may still be called. This will be |
| 41 // OK since we'll just immediately clean up the data it stored later in this | 38 // OK since we'll just immediately clean up the data it stored later in this |
| 42 // destructor. | 39 // destructor. |
| 43 if (audio_) { | 40 if (audio_) { |
| 44 audio_->ShutDown(); | 41 audio_->ShutDown(); |
| 45 audio_ = NULL; | 42 audio_ = NULL; |
| 46 } | 43 } |
| 47 | |
| 48 // If the completion callback hasn't fired yet, do so here | |
| 49 // with an error condition. | |
| 50 if (create_callback_pending_) { | |
| 51 PP_RunCompletionCallback(&create_callback_, PP_ERROR_ABORTED); | |
| 52 create_callback_pending_ = false; | |
| 53 } | |
| 54 } | 44 } |
| 55 | 45 |
| 56 // static | 46 // static |
| 57 PP_Resource PPB_Audio_Impl::Create(PP_Instance instance, | 47 PP_Resource PPB_Audio_Impl::Create(PP_Instance instance, |
| 58 PP_Resource config, | 48 PP_Resource config, |
| 59 PPB_Audio_Callback audio_callback, | 49 PPB_Audio_Callback audio_callback, |
| 60 void* user_data) { | 50 void* user_data) { |
| 61 scoped_refptr<PPB_Audio_Impl> audio(new PPB_Audio_Impl(instance)); | 51 scoped_refptr<PPB_Audio_Impl> audio(new PPB_Audio_Impl(instance)); |
| 62 if (!audio->Init(config, audio_callback, user_data)) | 52 if (!audio->Init(config, audio_callback, user_data)) |
| 63 return 0; | 53 return 0; |
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 134 DCHECK(!audio_); | 124 DCHECK(!audio_); |
| 135 audio_ = plugin_delegate->CreateAudio(enter.object()->GetSampleRate(), | 125 audio_ = plugin_delegate->CreateAudio(enter.object()->GetSampleRate(), |
| 136 enter.object()->GetSampleFrameCount(), | 126 enter.object()->GetSampleFrameCount(), |
| 137 this); | 127 this); |
| 138 if (!audio_) | 128 if (!audio_) |
| 139 return PP_ERROR_FAILED; | 129 return PP_ERROR_FAILED; |
| 140 | 130 |
| 141 // At this point, we are guaranteeing ownership of the completion | 131 // At this point, we are guaranteeing ownership of the completion |
| 142 // callback. Audio promises to fire the completion callback | 132 // callback. Audio promises to fire the completion callback |
| 143 // once and only once. | 133 // once and only once. |
| 144 create_callback_ = create_callback; | 134 SetCallbackInfo(true, create_callback); |
| 145 create_callback_pending_ = true; | 135 |
| 146 return PP_OK_COMPLETIONPENDING; | 136 return PP_OK_COMPLETIONPENDING; |
| 147 } | 137 } |
| 148 | 138 |
| 149 int32_t PPB_Audio_Impl::GetSyncSocket(int* sync_socket) { | 139 int32_t PPB_Audio_Impl::GetSyncSocket(int* sync_socket) { |
| 150 if (socket_for_create_callback_.get()) { | 140 return GetSyncSocketImpl(sync_socket); |
| 151 #if defined(OS_POSIX) | |
| 152 *sync_socket = socket_for_create_callback_->handle(); | |
| 153 #elif defined(OS_WIN) | |
| 154 *sync_socket = reinterpret_cast<int>(socket_for_create_callback_->handle()); | |
| 155 #else | |
| 156 #error "Platform not supported." | |
| 157 #endif | |
| 158 return PP_OK; | |
| 159 } | |
| 160 return PP_ERROR_FAILED; | |
| 161 } | 141 } |
| 162 | 142 |
| 163 int32_t PPB_Audio_Impl::GetSharedMemory(int* shm_handle, uint32_t* shm_size) { | 143 int32_t PPB_Audio_Impl::GetSharedMemory(int* shm_handle, |
| 164 if (shared_memory_for_create_callback_.get()) { | 144 uint32_t* shm_size) { |
| 165 #if defined(OS_POSIX) | 145 return GetSharedMemoryImpl(shm_handle, shm_size); |
| 166 *shm_handle = shared_memory_for_create_callback_->handle().fd; | |
| 167 #elif defined(OS_WIN) | |
| 168 *shm_handle = reinterpret_cast<int>( | |
| 169 shared_memory_for_create_callback_->handle()); | |
| 170 #else | |
| 171 #error "Platform not supported." | |
| 172 #endif | |
| 173 *shm_size = shared_memory_size_for_create_callback_; | |
| 174 return PP_OK; | |
| 175 } | |
| 176 return PP_ERROR_FAILED; | |
| 177 } | 146 } |
| 178 | 147 |
| 179 void PPB_Audio_Impl::StreamCreated( | 148 void PPB_Audio_Impl::OnSetStreamInfo( |
| 180 base::SharedMemoryHandle shared_memory_handle, | 149 base::SharedMemoryHandle shared_memory_handle, |
| 181 size_t shared_memory_size, | 150 size_t shared_memory_size, |
| 182 base::SyncSocket::Handle socket_handle) { | 151 base::SyncSocket::Handle socket_handle) { |
| 183 if (create_callback_pending_) { | 152 SetStreamInfo(shared_memory_handle, shared_memory_size, socket_handle); |
| 184 // Trusted side of proxy can specify a callback to recieve handles. In | |
| 185 // this case we don't need to map any data or start the thread since it | |
| 186 // will be handled by the proxy. | |
| 187 shared_memory_for_create_callback_.reset( | |
| 188 new base::SharedMemory(shared_memory_handle, false)); | |
| 189 shared_memory_size_for_create_callback_ = shared_memory_size; | |
| 190 socket_for_create_callback_.reset(new base::SyncSocket(socket_handle)); | |
| 191 | |
| 192 PP_RunCompletionCallback(&create_callback_, 0); | |
| 193 create_callback_pending_ = false; | |
| 194 | |
| 195 // It might be nice to close the handles here to free up some system | |
| 196 // resources, but we can't since there's a race condition. The handles must | |
| 197 // be valid until they're sent over IPC, which is done from the I/O thread | |
| 198 // which will often get done after this code executes. We could do | |
| 199 // something more elaborate like an ACK from the plugin or post a task to | |
| 200 // the I/O thread and back, but this extra complexity doesn't seem worth it | |
| 201 // just to clean up these handles faster. | |
| 202 } else { | |
| 203 SetStreamInfo(shared_memory_handle, shared_memory_size, socket_handle); | |
| 204 } | |
| 205 } | 153 } |
| 206 | 154 |
| 207 } // namespace ppapi | 155 } // namespace ppapi |
| 208 } // namespace webkit | 156 } // namespace webkit |
| OLD | NEW |