1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "media/midi/usb_midi_input_stream.h"
11 #include "base/logging.h"
12 #include "media/midi/usb_midi_device.h"
13 #include "media/midi/usb_midi_jack.h"
17 UsbMidiInputStream::JackUniqueKey::JackUniqueKey(UsbMidiDevice
* device
,
21 endpoint_number(endpoint_number
),
22 cable_number(cable_number
) {}
24 bool UsbMidiInputStream::JackUniqueKey::operator==(
25 const JackUniqueKey
& that
) const {
26 return device
== that
.device
&&
27 endpoint_number
== that
.endpoint_number
&&
28 cable_number
== that
.cable_number
;
31 bool UsbMidiInputStream::JackUniqueKey::operator<(
32 const JackUniqueKey
& that
) const {
33 if (device
!= that
.device
)
34 return device
< that
.device
;
35 if (endpoint_number
!= that
.endpoint_number
)
36 return endpoint_number
< that
.endpoint_number
;
37 return cable_number
< that
.cable_number
;
40 UsbMidiInputStream::UsbMidiInputStream(Delegate
* delegate
)
41 : delegate_(delegate
) {}
43 UsbMidiInputStream::~UsbMidiInputStream() {}
45 void UsbMidiInputStream::Add(const UsbMidiJack
& jack
) {
46 JackUniqueKey
key(jack
.device
,
47 jack
.endpoint_number(),
50 jacks_
.push_back(jack
);
51 DCHECK(jack_dictionary_
.end() == jack_dictionary_
.find(key
));
52 jack_dictionary_
.insert(std::make_pair(key
, jack_dictionary_
.size()));
55 void UsbMidiInputStream::OnReceivedData(UsbMidiDevice
* device
,
59 base::TimeTicks time
) {
60 DCHECK_EQ(0u, size
% kPacketSize
);
62 while (current
+ kPacketSize
<= size
) {
63 ProcessOnePacket(device
, endpoint_number
, &data
[current
], time
);
64 current
+= kPacketSize
;
68 void UsbMidiInputStream::ProcessOnePacket(UsbMidiDevice
* device
,
71 base::TimeTicks time
) {
72 // The first 4 bytes of the packet is accessible here.
73 uint8 code_index
= packet
[0] & 0x0f;
74 uint8 cable_number
= packet
[0] >> 4;
75 const size_t packet_size_table
[16] = {
76 0, 0, 2, 3, 3, 1, 2, 3, 3, 3, 3, 3, 2, 2, 3, 1,
78 size_t packet_size
= packet_size_table
[code_index
];
79 if (packet_size
== 0) {
80 // These CINs are reserved. Ignore them.
81 DVLOG(1) << "code index number (" << code_index
<< ") arrives "
82 << "but it is reserved.";
85 std::map
<JackUniqueKey
, size_t>::const_iterator it
=
86 jack_dictionary_
.find(JackUniqueKey(device
,
89 if (it
!= jack_dictionary_
.end())
90 delegate_
->OnReceivedData(it
->second
, &packet
[1], packet_size
, time
);