| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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 "media/audio/cras/cras_unified.h" | 5 #include "media/audio/cras/cras_unified.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "media/audio/cras/audio_manager_cras.h" | 8 #include "media/audio/cras/audio_manager_cras.h" |
| 9 | 9 |
| 10 namespace media { | 10 namespace media { |
| (...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 151 params_.sample_rate(), | 151 params_.sample_rate(), |
| 152 params_.channels()); | 152 params_.channels()); |
| 153 if (!audio_format) { | 153 if (!audio_format) { |
| 154 LOG(WARNING) << "Error setting up audio parameters."; | 154 LOG(WARNING) << "Error setting up audio parameters."; |
| 155 callback->OnError(this); | 155 callback->OnError(this); |
| 156 return; | 156 return; |
| 157 } | 157 } |
| 158 | 158 |
| 159 // Initialize channel layout to all -1 to indicate that none of | 159 // Initialize channel layout to all -1 to indicate that none of |
| 160 // the channels is set in the layout. | 160 // the channels is set in the layout. |
| 161 int8 layout[CRAS_CH_MAX] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 }; | 161 int8_t layout[CRAS_CH_MAX] = {-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1}; |
| 162 | 162 |
| 163 // Converts to CRAS defined channels. ChannelOrder will return -1 | 163 // Converts to CRAS defined channels. ChannelOrder will return -1 |
| 164 // for channels that does not present in params_.channel_layout(). | 164 // for channels that does not present in params_.channel_layout(). |
| 165 for (size_t i = 0; i < arraysize(kChannelMap); ++i) | 165 for (size_t i = 0; i < arraysize(kChannelMap); ++i) |
| 166 layout[kChannelMap[i]] = ChannelOrder(params_.channel_layout(), | 166 layout[kChannelMap[i]] = ChannelOrder(params_.channel_layout(), |
| 167 static_cast<Channels>(i)); | 167 static_cast<Channels>(i)); |
| 168 | 168 |
| 169 if (cras_audio_format_set_channel_layout(audio_format, layout)) { | 169 if (cras_audio_format_set_channel_layout(audio_format, layout)) { |
| 170 LOG(WARNING) << "Error setting channel layout."; | 170 LOG(WARNING) << "Error setting channel layout."; |
| 171 callback->OnError(this); | 171 callback->OnError(this); |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 225 if (!client_) | 225 if (!client_) |
| 226 return; | 226 return; |
| 227 volume_ = static_cast<float>(volume); | 227 volume_ = static_cast<float>(volume); |
| 228 cras_client_set_stream_volume(client_, stream_id_, volume_); | 228 cras_client_set_stream_volume(client_, stream_id_, volume_); |
| 229 } | 229 } |
| 230 | 230 |
| 231 void CrasUnifiedStream::GetVolume(double* volume) { | 231 void CrasUnifiedStream::GetVolume(double* volume) { |
| 232 *volume = volume_; | 232 *volume = volume_; |
| 233 } | 233 } |
| 234 | 234 |
| 235 uint32 CrasUnifiedStream::GetBytesLatency( | 235 uint32_t CrasUnifiedStream::GetBytesLatency(const struct timespec& latency_ts) { |
| 236 const struct timespec& latency_ts) { | 236 uint32_t latency_usec; |
| 237 uint32 latency_usec; | |
| 238 | 237 |
| 239 // Treat negative latency (if we are too slow to render) as 0. | 238 // Treat negative latency (if we are too slow to render) as 0. |
| 240 if (latency_ts.tv_sec < 0 || latency_ts.tv_nsec < 0) { | 239 if (latency_ts.tv_sec < 0 || latency_ts.tv_nsec < 0) { |
| 241 latency_usec = 0; | 240 latency_usec = 0; |
| 242 } else { | 241 } else { |
| 243 latency_usec = (latency_ts.tv_sec * base::Time::kMicrosecondsPerSecond) + | 242 latency_usec = (latency_ts.tv_sec * base::Time::kMicrosecondsPerSecond) + |
| 244 latency_ts.tv_nsec / base::Time::kNanosecondsPerMicrosecond; | 243 latency_ts.tv_nsec / base::Time::kNanosecondsPerMicrosecond; |
| 245 } | 244 } |
| 246 | 245 |
| 247 double frames_latency = | 246 double frames_latency = |
| 248 latency_usec * params_.sample_rate() / base::Time::kMicrosecondsPerSecond; | 247 latency_usec * params_.sample_rate() / base::Time::kMicrosecondsPerSecond; |
| 249 | 248 |
| 250 return static_cast<unsigned int>(frames_latency * bytes_per_frame_); | 249 return static_cast<unsigned int>(frames_latency * bytes_per_frame_); |
| 251 } | 250 } |
| 252 | 251 |
| 253 // Static callback asking for samples. | 252 // Static callback asking for samples. |
| 254 int CrasUnifiedStream::UnifiedCallback(cras_client* client, | 253 int CrasUnifiedStream::UnifiedCallback(cras_client* client, |
| 255 cras_stream_id_t stream_id, | 254 cras_stream_id_t stream_id, |
| 256 uint8* input_samples, | 255 uint8_t* input_samples, |
| 257 uint8* output_samples, | 256 uint8_t* output_samples, |
| 258 unsigned int frames, | 257 unsigned int frames, |
| 259 const timespec* input_ts, | 258 const timespec* input_ts, |
| 260 const timespec* output_ts, | 259 const timespec* output_ts, |
| 261 void* arg) { | 260 void* arg) { |
| 262 CrasUnifiedStream* me = static_cast<CrasUnifiedStream*>(arg); | 261 CrasUnifiedStream* me = static_cast<CrasUnifiedStream*>(arg); |
| 263 return me->DispatchCallback(frames, | 262 return me->DispatchCallback(frames, |
| 264 input_samples, | 263 input_samples, |
| 265 output_samples, | 264 output_samples, |
| 266 input_ts, | 265 input_ts, |
| 267 output_ts); | 266 output_ts); |
| 268 } | 267 } |
| 269 | 268 |
| 270 // Static callback for stream errors. | 269 // Static callback for stream errors. |
| 271 int CrasUnifiedStream::StreamError(cras_client* client, | 270 int CrasUnifiedStream::StreamError(cras_client* client, |
| 272 cras_stream_id_t stream_id, | 271 cras_stream_id_t stream_id, |
| 273 int err, | 272 int err, |
| 274 void* arg) { | 273 void* arg) { |
| 275 CrasUnifiedStream* me = static_cast<CrasUnifiedStream*>(arg); | 274 CrasUnifiedStream* me = static_cast<CrasUnifiedStream*>(arg); |
| 276 me->NotifyStreamError(err); | 275 me->NotifyStreamError(err); |
| 277 return 0; | 276 return 0; |
| 278 } | 277 } |
| 279 | 278 |
| 280 // Calls the appropriate rendering function for this type of stream. | 279 // Calls the appropriate rendering function for this type of stream. |
| 281 uint32 CrasUnifiedStream::DispatchCallback(size_t frames, | 280 uint32_t CrasUnifiedStream::DispatchCallback(size_t frames, |
| 282 uint8* input_samples, | 281 uint8_t* input_samples, |
| 283 uint8* output_samples, | 282 uint8_t* output_samples, |
| 284 const timespec* input_ts, | 283 const timespec* input_ts, |
| 285 const timespec* output_ts) { | 284 const timespec* output_ts) { |
| 286 switch (stream_direction_) { | 285 switch (stream_direction_) { |
| 287 case CRAS_STREAM_OUTPUT: | 286 case CRAS_STREAM_OUTPUT: |
| 288 return WriteAudio(frames, output_samples, output_ts); | 287 return WriteAudio(frames, output_samples, output_ts); |
| 289 case CRAS_STREAM_INPUT: | 288 case CRAS_STREAM_INPUT: |
| 290 NOTREACHED() << "CrasUnifiedStream doesn't support input streams."; | 289 NOTREACHED() << "CrasUnifiedStream doesn't support input streams."; |
| 291 return 0; | 290 return 0; |
| 292 default: | 291 default: |
| 293 break; | 292 break; |
| 294 } | 293 } |
| 295 | 294 |
| 296 return 0; | 295 return 0; |
| 297 } | 296 } |
| 298 | 297 |
| 299 uint32 CrasUnifiedStream::WriteAudio(size_t frames, | 298 uint32_t CrasUnifiedStream::WriteAudio(size_t frames, |
| 300 uint8* buffer, | 299 uint8_t* buffer, |
| 301 const timespec* sample_ts) { | 300 const timespec* sample_ts) { |
| 302 DCHECK_EQ(frames, static_cast<size_t>(output_bus_->frames())); | 301 DCHECK_EQ(frames, static_cast<size_t>(output_bus_->frames())); |
| 303 | 302 |
| 304 // Determine latency and pass that on to the source. | 303 // Determine latency and pass that on to the source. |
| 305 timespec latency_ts = {0, 0}; | 304 timespec latency_ts = {0, 0}; |
| 306 cras_client_calc_playback_latency(sample_ts, &latency_ts); | 305 cras_client_calc_playback_latency(sample_ts, &latency_ts); |
| 307 | 306 |
| 308 int frames_filled = source_callback_->OnMoreData( | 307 int frames_filled = source_callback_->OnMoreData( |
| 309 output_bus_.get(), GetBytesLatency(latency_ts), 0); | 308 output_bus_.get(), GetBytesLatency(latency_ts), 0); |
| 310 | 309 |
| 311 // Note: If this ever changes to output raw float the data must be clipped and | 310 // Note: If this ever changes to output raw float the data must be clipped and |
| 312 // sanitized since it may come from an untrusted source such as NaCl. | 311 // sanitized since it may come from an untrusted source such as NaCl. |
| 313 output_bus_->ToInterleaved( | 312 output_bus_->ToInterleaved( |
| 314 frames_filled, bytes_per_frame_ / params_.channels(), buffer); | 313 frames_filled, bytes_per_frame_ / params_.channels(), buffer); |
| 315 | 314 |
| 316 return frames_filled; | 315 return frames_filled; |
| 317 } | 316 } |
| 318 | 317 |
| 319 void CrasUnifiedStream::NotifyStreamError(int err) { | 318 void CrasUnifiedStream::NotifyStreamError(int err) { |
| 320 // This will remove the stream from the client. | 319 // This will remove the stream from the client. |
| 321 if (source_callback_) | 320 if (source_callback_) |
| 322 source_callback_->OnError(this); | 321 source_callback_->OnError(this); |
| 323 } | 322 } |
| 324 | 323 |
| 325 } // namespace media | 324 } // namespace media |
| OLD | NEW |