| OLD | NEW |
| 1 // Copyright 2017 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 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/midi/dynamically_initialized_midi_manager_win.h" | 5 #include "media/midi/dynamically_initialized_midi_manager_win.h" |
| 6 | 6 |
| 7 #include <windows.h> | 7 #include <windows.h> |
| 8 | 8 |
| 9 #include <ks.h> |
| 10 #include <ksmedia.h> |
| 9 #include <mmreg.h> | 11 #include <mmreg.h> |
| 10 #include <mmsystem.h> | 12 #include <mmsystem.h> |
| 11 | 13 |
| 12 #include <algorithm> | 14 #include <algorithm> |
| 13 #include <string> | 15 #include <string> |
| 14 | 16 |
| 15 #include "base/bind_helpers.h" | 17 #include "base/bind_helpers.h" |
| 16 #include "base/callback.h" | 18 #include "base/callback.h" |
| 17 #include "base/logging.h" | 19 #include "base/logging.h" |
| 18 #include "base/memory/ptr_util.h" | 20 #include "base/memory/ptr_util.h" |
| 19 #include "base/strings/string16.h" | 21 #include "base/strings/string16.h" |
| 20 #include "base/strings/stringprintf.h" | 22 #include "base/strings/stringprintf.h" |
| 21 #include "base/strings/utf_string_conversions.h" | 23 #include "base/strings/utf_string_conversions.h" |
| 22 #include "base/synchronization/lock.h" | 24 #include "base/synchronization/lock.h" |
| 25 #include "device/usb/usb_ids.h" |
| 23 #include "media/midi/message_util.h" | 26 #include "media/midi/message_util.h" |
| 24 #include "media/midi/midi_port_info.h" | 27 #include "media/midi/midi_port_info.h" |
| 25 #include "media/midi/midi_service.h" | 28 #include "media/midi/midi_service.h" |
| 26 | 29 |
| 27 namespace midi { | 30 namespace midi { |
| 28 | 31 |
| 29 // Forward declaration of PortManager for anonymous functions and internal | 32 // Forward declaration of PortManager for anonymous functions and internal |
| 30 // classes to use it. | 33 // classes to use it. |
| 31 class DynamicallyInitializedMidiManagerWin::PortManager { | 34 class DynamicallyInitializedMidiManagerWin::PortManager { |
| 32 public: | 35 public: |
| (...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 180 midiInClose(handle); | 183 midiInClose(handle); |
| 181 } | 184 } |
| 182 | 185 |
| 183 void FinalizeOutPort(HMIDIOUT handle) { | 186 void FinalizeOutPort(HMIDIOUT handle) { |
| 184 // Resets inflight buffers. This will cancel sending data that system | 187 // Resets inflight buffers. This will cancel sending data that system |
| 185 // holds and were not sent yet. | 188 // holds and were not sent yet. |
| 186 midiOutReset(handle); | 189 midiOutReset(handle); |
| 187 midiOutClose(handle); | 190 midiOutClose(handle); |
| 188 } | 191 } |
| 189 | 192 |
| 193 // Gets manufacturer name in string from identifiers. |
| 194 std::string GetManufacturerName(uint16_t id, const GUID& guid) { |
| 195 if (IS_COMPATIBLE_USBAUDIO_MID(&guid)) { |
| 196 const char* name = |
| 197 device::UsbIds::GetVendorName(EXTRACT_USBAUDIO_MID(&guid)); |
| 198 if (name) |
| 199 return std::string(name); |
| 200 } |
| 201 if (id == MM_MICROSOFT) |
| 202 return "Microsoft Corporation"; |
| 203 |
| 204 // TODO(crbug.com/472341): Support other manufacture IDs. |
| 205 return ""; |
| 206 } |
| 207 |
| 190 // All instances of Port subclasses are always accessed behind a lock of | 208 // All instances of Port subclasses are always accessed behind a lock of |
| 191 // *GetTaskLock(). Port and subclasses implementation do not need to | 209 // *GetTaskLock(). Port and subclasses implementation do not need to |
| 192 // consider thread safety. | 210 // consider thread safety. |
| 193 class Port { | 211 class Port { |
| 194 public: | 212 public: |
| 195 Port(const std::string& type, | 213 Port(const std::string& type, |
| 196 uint32_t device_id, | 214 uint32_t device_id, |
| 197 uint16_t manufacturer_id, | 215 uint16_t manufacturer_id, |
| 198 uint16_t product_id, | 216 uint16_t product_id, |
| 199 uint32_t driver_version, | 217 uint32_t driver_version, |
| 200 const std::string& product_name) | 218 const std::string& product_name, |
| 219 const GUID& manufacturer_guid) |
| 201 : index_(0u), | 220 : index_(0u), |
| 202 type_(type), | 221 type_(type), |
| 203 device_id_(device_id), | 222 device_id_(device_id), |
| 204 manufacturer_id_(manufacturer_id), | 223 manufacturer_id_(manufacturer_id), |
| 205 product_id_(product_id), | 224 product_id_(product_id), |
| 206 driver_version_(driver_version), | 225 driver_version_(driver_version), |
| 207 product_name_(product_name) { | 226 product_name_(product_name) { |
| 208 info_.manufacturer = "unknown"; // TODO(toyoshim): Use USB information. | 227 info_.manufacturer = |
| 228 GetManufacturerName(manufacturer_id, manufacturer_guid); |
| 209 info_.name = product_name_; | 229 info_.name = product_name_; |
| 210 info_.version = base::StringPrintf("%d.%d", HIBYTE(driver_version_), | 230 info_.version = base::StringPrintf("%d.%d", HIBYTE(driver_version_), |
| 211 LOBYTE(driver_version_)); | 231 LOBYTE(driver_version_)); |
| 212 info_.state = mojom::PortState::DISCONNECTED; | 232 info_.state = mojom::PortState::DISCONNECTED; |
| 213 } | 233 } |
| 214 | 234 |
| 215 virtual ~Port() {} | 235 virtual ~Port() {} |
| 216 | 236 |
| 217 bool operator==(const Port& other) const { | 237 bool operator==(const Port& other) const { |
| 218 // Should not use |device_id| for comparison because it can be changed on | 238 // Should not use |device_id| for comparison because it can be changed on |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 278 InPort(DynamicallyInitializedMidiManagerWin* manager, | 298 InPort(DynamicallyInitializedMidiManagerWin* manager, |
| 279 int instance_id, | 299 int instance_id, |
| 280 UINT device_id, | 300 UINT device_id, |
| 281 const MIDIINCAPS2W& caps) | 301 const MIDIINCAPS2W& caps) |
| 282 : Port("input", | 302 : Port("input", |
| 283 device_id, | 303 device_id, |
| 284 caps.wMid, | 304 caps.wMid, |
| 285 caps.wPid, | 305 caps.wPid, |
| 286 caps.vDriverVersion, | 306 caps.vDriverVersion, |
| 287 base::WideToUTF8( | 307 base::WideToUTF8( |
| 288 base::string16(caps.szPname, wcslen(caps.szPname)))), | 308 base::string16(caps.szPname, wcslen(caps.szPname))), |
| 309 caps.ManufacturerGuid), |
| 289 manager_(manager), | 310 manager_(manager), |
| 290 in_handle_(kInvalidInHandle), | 311 in_handle_(kInvalidInHandle), |
| 291 instance_id_(instance_id) {} | 312 instance_id_(instance_id) {} |
| 292 | 313 |
| 293 static std::vector<std::unique_ptr<InPort>> EnumerateActivePorts( | 314 static std::vector<std::unique_ptr<InPort>> EnumerateActivePorts( |
| 294 DynamicallyInitializedMidiManagerWin* manager, | 315 DynamicallyInitializedMidiManagerWin* manager, |
| 295 int instance_id) { | 316 int instance_id) { |
| 296 std::vector<std::unique_ptr<InPort>> ports; | 317 std::vector<std::unique_ptr<InPort>> ports; |
| 297 const UINT num_devices = midiInGetNumDevs(); | 318 const UINT num_devices = midiInGetNumDevs(); |
| 298 for (UINT device_id = 0; device_id < num_devices; ++device_id) { | 319 for (UINT device_id = 0; device_id < num_devices; ++device_id) { |
| (...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 393 | 414 |
| 394 class DynamicallyInitializedMidiManagerWin::OutPort final : public Port { | 415 class DynamicallyInitializedMidiManagerWin::OutPort final : public Port { |
| 395 public: | 416 public: |
| 396 OutPort(UINT device_id, const MIDIOUTCAPS2W& caps) | 417 OutPort(UINT device_id, const MIDIOUTCAPS2W& caps) |
| 397 : Port("output", | 418 : Port("output", |
| 398 device_id, | 419 device_id, |
| 399 caps.wMid, | 420 caps.wMid, |
| 400 caps.wPid, | 421 caps.wPid, |
| 401 caps.vDriverVersion, | 422 caps.vDriverVersion, |
| 402 base::WideToUTF8( | 423 base::WideToUTF8( |
| 403 base::string16(caps.szPname, wcslen(caps.szPname)))), | 424 base::string16(caps.szPname, wcslen(caps.szPname))), |
| 425 caps.ManufacturerGuid), |
| 404 software_(caps.wTechnology == MOD_SWSYNTH), | 426 software_(caps.wTechnology == MOD_SWSYNTH), |
| 405 out_handle_(kInvalidOutHandle) {} | 427 out_handle_(kInvalidOutHandle) {} |
| 406 | 428 |
| 407 static std::vector<std::unique_ptr<OutPort>> EnumerateActivePorts() { | 429 static std::vector<std::unique_ptr<OutPort>> EnumerateActivePorts() { |
| 408 std::vector<std::unique_ptr<OutPort>> ports; | 430 std::vector<std::unique_ptr<OutPort>> ports; |
| 409 const UINT num_devices = midiOutGetNumDevs(); | 431 const UINT num_devices = midiOutGetNumDevs(); |
| 410 for (UINT device_id = 0; device_id < num_devices; ++device_id) { | 432 for (UINT device_id = 0; device_id < num_devices; ++device_id) { |
| 411 MIDIOUTCAPS2W caps; | 433 MIDIOUTCAPS2W caps; |
| 412 MMRESULT result = midiOutGetDevCaps( | 434 MMRESULT result = midiOutGetDevCaps( |
| 413 device_id, reinterpret_cast<LPMIDIOUTCAPSW>(&caps), sizeof(caps)); | 435 device_id, reinterpret_cast<LPMIDIOUTCAPSW>(&caps), sizeof(caps)); |
| (...skipping 410 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 824 const std::vector<uint8_t>& data) { | 846 const std::vector<uint8_t>& data) { |
| 825 CHECK_GT(port_manager_->outputs()->size(), port_index); | 847 CHECK_GT(port_manager_->outputs()->size(), port_index); |
| 826 (*port_manager_->outputs())[port_index]->Send(data); | 848 (*port_manager_->outputs())[port_index]->Send(data); |
| 827 // |client| will be checked inside MidiManager::AccumulateMidiBytesSent. | 849 // |client| will be checked inside MidiManager::AccumulateMidiBytesSent. |
| 828 PostReplyTask( | 850 PostReplyTask( |
| 829 base::Bind(&DynamicallyInitializedMidiManagerWin::AccumulateMidiBytesSent, | 851 base::Bind(&DynamicallyInitializedMidiManagerWin::AccumulateMidiBytesSent, |
| 830 base::Unretained(this), client, data.size())); | 852 base::Unretained(this), client, data.size())); |
| 831 } | 853 } |
| 832 | 854 |
| 833 } // namespace midi | 855 } // namespace midi |
| OLD | NEW |