Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(658)

Side by Side Diff: media/audio/win/audio_low_latency_output_win.cc

Issue 2478893002: Revert of Support floating-point audio output for Windows7+ (Closed)
Patch Set: Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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/win/audio_low_latency_output_win.h" 5 #include "media/audio/win/audio_low_latency_output_win.h"
6 6
7 #include <Functiondiscoverykeys_devpkey.h> 7 #include <Functiondiscoverykeys_devpkey.h>
8 8
9 #include <climits>
10
11 #include "base/command_line.h" 9 #include "base/command_line.h"
12 #include "base/logging.h" 10 #include "base/logging.h"
13 #include "base/macros.h" 11 #include "base/macros.h"
14 #include "base/metrics/histogram.h" 12 #include "base/metrics/histogram.h"
15 #include "base/strings/utf_string_conversions.h" 13 #include "base/strings/utf_string_conversions.h"
16 #include "base/time/time.h" 14 #include "base/time/time.h"
17 #include "base/trace_event/trace_event.h" 15 #include "base/trace_event/trace_event.h"
18 #include "base/win/scoped_propvariant.h" 16 #include "base/win/scoped_propvariant.h"
19 #include "media/audio/audio_device_description.h" 17 #include "media/audio/audio_device_description.h"
20 #include "media/audio/win/audio_manager_win.h" 18 #include "media/audio/win/audio_manager_win.h"
21 #include "media/audio/win/avrt_wrapper_win.h" 19 #include "media/audio/win/avrt_wrapper_win.h"
22 #include "media/audio/win/core_audio_util_win.h" 20 #include "media/audio/win/core_audio_util_win.h"
23 #include "media/base/audio_sample_types.h"
24 #include "media/base/limits.h" 21 #include "media/base/limits.h"
25 #include "media/base/media_switches.h" 22 #include "media/base/media_switches.h"
26 23
27 using base::win::ScopedComPtr; 24 using base::win::ScopedComPtr;
28 using base::win::ScopedCOMInitializer; 25 using base::win::ScopedCOMInitializer;
29 using base::win::ScopedCoMem; 26 using base::win::ScopedCoMem;
30 27
31 namespace media { 28 namespace media {
32 29
33 // The number of bits in a float sample.
34 static const int kBitsPerFloatSample = sizeof(float) * CHAR_BIT;
35
36 // static 30 // static
37 AUDCLNT_SHAREMODE WASAPIAudioOutputStream::GetShareMode() { 31 AUDCLNT_SHAREMODE WASAPIAudioOutputStream::GetShareMode() {
38 const base::CommandLine* cmd_line = base::CommandLine::ForCurrentProcess(); 32 const base::CommandLine* cmd_line = base::CommandLine::ForCurrentProcess();
39 if (cmd_line->HasSwitch(switches::kEnableExclusiveAudio)) 33 if (cmd_line->HasSwitch(switches::kEnableExclusiveAudio))
40 return AUDCLNT_SHAREMODE_EXCLUSIVE; 34 return AUDCLNT_SHAREMODE_EXCLUSIVE;
41 return AUDCLNT_SHAREMODE_SHARED; 35 return AUDCLNT_SHAREMODE_SHARED;
42 } 36 }
43 37
44 // static 38 // static
45 int WASAPIAudioOutputStream::HardwareSampleRate(const std::string& device_id) { 39 int WASAPIAudioOutputStream::HardwareSampleRate(const std::string& device_id) {
(...skipping 25 matching lines...) Expand all
71 opened_(false), 65 opened_(false),
72 volume_(1.0), 66 volume_(1.0),
73 packet_size_frames_(0), 67 packet_size_frames_(0),
74 packet_size_bytes_(0), 68 packet_size_bytes_(0),
75 endpoint_buffer_size_frames_(0), 69 endpoint_buffer_size_frames_(0),
76 device_id_(device_id), 70 device_id_(device_id),
77 device_role_(device_role), 71 device_role_(device_role),
78 share_mode_(GetShareMode()), 72 share_mode_(GetShareMode()),
79 num_written_frames_(0), 73 num_written_frames_(0),
80 source_(NULL), 74 source_(NULL),
81 audio_bus_(AudioBus::Create(AudioParameters( 75 audio_bus_(AudioBus::Create(params)) {
82 params.format(),
83 params.channel_layout(),
84 params.sample_rate(),
85 // Ignore the given bits per sample because we're outputting
86 // floats.
87 kBitsPerFloatSample,
88 params.frames_per_buffer()))) {
89 DCHECK(manager_); 76 DCHECK(manager_);
90 77
91 // The empty string is used to indicate a default device and the 78 // The empty string is used to indicate a default device and the
92 // |device_role_| member controls whether that's the default or default 79 // |device_role_| member controls whether that's the default or default
93 // communications device. 80 // communications device.
94 DCHECK_NE(device_id_, AudioDeviceDescription::kDefaultDeviceId); 81 DCHECK_NE(device_id_, AudioDeviceDescription::kDefaultDeviceId);
95 DCHECK_NE(device_id_, AudioDeviceDescription::kCommunicationsDeviceId); 82 DCHECK_NE(device_id_, AudioDeviceDescription::kCommunicationsDeviceId);
96 83
97 DVLOG(1) << "WASAPIAudioOutputStream::WASAPIAudioOutputStream()"; 84 DVLOG(1) << "WASAPIAudioOutputStream::WASAPIAudioOutputStream()";
98 DVLOG_IF(1, share_mode_ == AUDCLNT_SHAREMODE_EXCLUSIVE) 85 DVLOG_IF(1, share_mode_ == AUDCLNT_SHAREMODE_EXCLUSIVE)
99 << "Core Audio (WASAPI) EXCLUSIVE MODE is enabled."; 86 << "Core Audio (WASAPI) EXCLUSIVE MODE is enabled.";
100 87
101 // Load the Avrt DLL if not already loaded. Required to support MMCSS. 88 // Load the Avrt DLL if not already loaded. Required to support MMCSS.
102 bool avrt_init = avrt::Initialize(); 89 bool avrt_init = avrt::Initialize();
103 DCHECK(avrt_init) << "Failed to load the avrt.dll"; 90 DCHECK(avrt_init) << "Failed to load the avrt.dll";
104 91
105 // Set up the desired render format specified by the client. We use the 92 // Set up the desired render format specified by the client. We use the
106 // WAVE_FORMAT_EXTENSIBLE structure to ensure that multiple channel ordering 93 // WAVE_FORMAT_EXTENSIBLE structure to ensure that multiple channel ordering
107 // and high precision data can be supported. 94 // and high precision data can be supported.
108 95
109 // Begin with the WAVEFORMATEX structure that specifies the basic format. 96 // Begin with the WAVEFORMATEX structure that specifies the basic format.
110 WAVEFORMATEX* format = &format_.Format; 97 WAVEFORMATEX* format = &format_.Format;
111 format->wFormatTag = WAVE_FORMAT_EXTENSIBLE; 98 format->wFormatTag = WAVE_FORMAT_EXTENSIBLE;
112 format->nChannels = params.channels(); 99 format->nChannels = params.channels();
113 format->nSamplesPerSec = params.sample_rate(); 100 format->nSamplesPerSec = params.sample_rate();
114 format->wBitsPerSample = kBitsPerFloatSample; 101 format->wBitsPerSample = params.bits_per_sample();
115 format->nBlockAlign = (format->wBitsPerSample / 8) * format->nChannels; 102 format->nBlockAlign = (format->wBitsPerSample / 8) * format->nChannels;
116 format->nAvgBytesPerSec = format->nSamplesPerSec * format->nBlockAlign; 103 format->nAvgBytesPerSec = format->nSamplesPerSec * format->nBlockAlign;
117 format->cbSize = sizeof(WAVEFORMATEXTENSIBLE) - sizeof(WAVEFORMATEX); 104 format->cbSize = sizeof(WAVEFORMATEXTENSIBLE) - sizeof(WAVEFORMATEX);
118 105
119 // Add the parts which are unique to WAVE_FORMAT_EXTENSIBLE. 106 // Add the parts which are unique to WAVE_FORMAT_EXTENSIBLE.
120 format_.Samples.wValidBitsPerSample = kBitsPerFloatSample; 107 format_.Samples.wValidBitsPerSample = params.bits_per_sample();
121 format_.dwChannelMask = CoreAudioUtil::GetChannelConfig(device_id, eRender); 108 format_.dwChannelMask = CoreAudioUtil::GetChannelConfig(device_id, eRender);
122 format_.SubFormat = KSDATAFORMAT_SUBTYPE_IEEE_FLOAT; 109 format_.SubFormat = KSDATAFORMAT_SUBTYPE_PCM;
123 110
124 // Store size (in different units) of audio packets which we expect to 111 // Store size (in different units) of audio packets which we expect to
125 // get from the audio endpoint device in each render event. 112 // get from the audio endpoint device in each render event.
126 packet_size_frames_ = params.frames_per_buffer(); 113 packet_size_frames_ = params.frames_per_buffer();
127 packet_size_bytes_ = params.GetBytesPerBuffer(); 114 packet_size_bytes_ = params.GetBytesPerBuffer();
128 DVLOG(1) << "Number of bytes per audio frame : " << format->nBlockAlign; 115 DVLOG(1) << "Number of bytes per audio frame : " << format->nBlockAlign;
129 DVLOG(1) << "Number of audio frames per packet: " << packet_size_frames_; 116 DVLOG(1) << "Number of audio frames per packet: " << packet_size_frames_;
130 DVLOG(1) << "Number of bytes per packet : " << packet_size_bytes_; 117 DVLOG(1) << "Number of bytes per packet : " << packet_size_bytes_;
131 DVLOG(1) << "Number of milliseconds per packet: " 118 DVLOG(1) << "Number of milliseconds per packet: "
132 << params.GetBufferDuration().InMillisecondsF(); 119 << params.GetBufferDuration().InMillisecondsF();
(...skipping 417 matching lines...) Expand 10 before | Expand all | Expand 10 after
550 } 537 }
551 538
552 // Read a data packet from the registered client source and 539 // Read a data packet from the registered client source and
553 // deliver a delay estimate in the same callback to the client. 540 // deliver a delay estimate in the same callback to the client.
554 541
555 int frames_filled = 542 int frames_filled =
556 source_->OnMoreData(delay, delay_timestamp, 0, audio_bus_.get()); 543 source_->OnMoreData(delay, delay_timestamp, 0, audio_bus_.get());
557 uint32_t num_filled_bytes = frames_filled * format_.Format.nBlockAlign; 544 uint32_t num_filled_bytes = frames_filled * format_.Format.nBlockAlign;
558 DCHECK_LE(num_filled_bytes, packet_size_bytes_); 545 DCHECK_LE(num_filled_bytes, packet_size_bytes_);
559 546
547 // Note: If this ever changes to output raw float the data must be
548 // clipped and sanitized since it may come from an untrusted
549 // source such as NaCl.
550 const int bytes_per_sample = format_.Format.wBitsPerSample >> 3;
560 audio_bus_->Scale(volume_); 551 audio_bus_->Scale(volume_);
561 audio_bus_->ToInterleaved<Float32SampleTypeTraits>( 552 audio_bus_->ToInterleaved(
562 frames_filled, reinterpret_cast<float*>(audio_data)); 553 frames_filled, bytes_per_sample, audio_data);
563 554
564 // Release the buffer space acquired in the GetBuffer() call. 555 // Release the buffer space acquired in the GetBuffer() call.
565 // Render silence if we were not able to fill up the buffer totally. 556 // Render silence if we were not able to fill up the buffer totally.
566 DWORD flags = (num_filled_bytes < packet_size_bytes_) ? 557 DWORD flags = (num_filled_bytes < packet_size_bytes_) ?
567 AUDCLNT_BUFFERFLAGS_SILENT : 0; 558 AUDCLNT_BUFFERFLAGS_SILENT : 0;
568 audio_render_client_->ReleaseBuffer(packet_size_frames_, flags); 559 audio_render_client_->ReleaseBuffer(packet_size_frames_, flags);
569 560
570 num_written_frames_ += packet_size_frames_; 561 num_written_frames_ += packet_size_frames_;
571 } 562 }
572 563
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
666 657
667 // Ensure that we don't quit the main thread loop immediately next 658 // Ensure that we don't quit the main thread loop immediately next
668 // time Start() is called. 659 // time Start() is called.
669 ResetEvent(stop_render_event_.Get()); 660 ResetEvent(stop_render_event_.Get());
670 } 661 }
671 662
672 source_ = NULL; 663 source_ = NULL;
673 } 664 }
674 665
675 } // namespace media 666 } // namespace media
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698