xref: /btstack/src/classic/avrcp_controller.c (revision cfd54eb73cd29e7bf738f261fb454a84a1bb66b0)
1 /*
2  * Copyright (C) 2016 BlueKitchen GmbH
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  * 3. Neither the name of the copyright holders nor the names of
14  *    contributors may be used to endorse or promote products derived
15  *    from this software without specific prior written permission.
16  * 4. Any redistribution, use, or modification is done solely for
17  *    personal benefit and not for any commercial purpose or for
18  *    monetary gain.
19  *
20  * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS
21  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MATTHIAS
24  * RINGWALD OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
27  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
28  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
29  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
30  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  *
33  * Please inquire about commercial licensing options at
34  * [email protected]
35  *
36  */
37 
38 #define BTSTACK_FILE__ "avrcp_controller.c"
39 
40 #include <stdint.h>
41 #include <string.h>
42 #include <inttypes.h>
43 
44 #include "btstack.h"
45 #include "classic/avrcp.h"
46 #include "classic/avrcp_controller.h"
47 
48 #define AVRCP_CMD_BUFFER_SIZE 30
49 
50 // made public in avrcp_controller.h
51 avrcp_context_t avrcp_controller_context;
52 static uint16_t transaction_id_counter = 0;
53 
54 static uint8_t avrcp_controller_get_next_transaction_label(void){
55     transaction_id_counter++;
56     if (transaction_id_counter == 16){
57         transaction_id_counter = 1;
58     }
59     return transaction_id_counter;
60 }
61 
62 static uint16_t avrcp_get_max_payload_size_for_packet_type(avrcp_packet_type_t packet_type){
63     switch (packet_type){
64         case AVRCP_SINGLE_PACKET:
65             return AVRCP_CMD_BUFFER_SIZE - 3;
66         case AVRCP_START_PACKET:
67             return AVRCP_CMD_BUFFER_SIZE - 4;
68         case AVRCP_CONTINUE_PACKET:
69         case AVRCP_END_PACKET:
70             return AVRCP_CMD_BUFFER_SIZE - 1;
71     }
72     return 0;
73 }
74 
75 static int avrcp_controller_supports_browsing(uint16_t controller_supported_features){
76     return controller_supported_features & AVRCP_FEATURE_MASK_BROWSING;
77 }
78 
79 static void avrcp_controller_emit_notification_for_event_id(uint16_t avrcp_cid, avrcp_notification_event_id_t event_id, avrcp_command_type_t ctype, const uint8_t * payload){
80     switch (event_id){
81         case AVRCP_NOTIFICATION_EVENT_PLAYBACK_POS_CHANGED:{
82             uint32_t song_position = big_endian_read_32(payload, 0);
83             uint16_t offset = 0;
84             uint8_t event[10];
85             event[offset++] = HCI_EVENT_AVRCP_META;
86             event[offset++] = sizeof(event) - 2;
87             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_PLAYBACK_POS_CHANGED;
88             little_endian_store_16(event, offset, avrcp_cid);
89             offset += 2;
90             event[offset++] = ctype;
91             little_endian_store_32(event, offset, song_position);
92             offset += 4;
93             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
94             break;
95         }
96         case AVRCP_NOTIFICATION_EVENT_PLAYBACK_STATUS_CHANGED:{
97             uint16_t offset = 0;
98             uint8_t event[7];
99             event[offset++] = HCI_EVENT_AVRCP_META;
100             event[offset++] = sizeof(event) - 2;
101             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_PLAYBACK_STATUS_CHANGED;
102             little_endian_store_16(event, offset, avrcp_cid);
103             offset += 2;
104             event[offset++] = ctype;
105             event[offset++] = payload[0];
106             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
107             break;
108         }
109         case AVRCP_NOTIFICATION_EVENT_TRACK_CHANGED:{
110             uint16_t offset = 0;
111             uint8_t event[6];
112             event[offset++] = HCI_EVENT_AVRCP_META;
113             event[offset++] = sizeof(event) - 2;
114             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_TRACK_CHANGED;
115             little_endian_store_16(event, offset, avrcp_cid);
116             offset += 2;
117             event[offset++] = ctype;
118             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
119             break;
120         }
121         case AVRCP_NOTIFICATION_EVENT_NOW_PLAYING_CONTENT_CHANGED:{
122             uint16_t offset = 0;
123             uint8_t event[6];
124             event[offset++] = HCI_EVENT_AVRCP_META;
125             event[offset++] = sizeof(event) - 2;
126             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_NOW_PLAYING_CONTENT_CHANGED;
127             little_endian_store_16(event, offset, avrcp_cid);
128             offset += 2;
129             event[offset++] = ctype;
130             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
131             break;
132         }
133         case AVRCP_NOTIFICATION_EVENT_AVAILABLE_PLAYERS_CHANGED:{
134             uint16_t offset = 0;
135             uint8_t event[6];
136             event[offset++] = HCI_EVENT_AVRCP_META;
137             event[offset++] = sizeof(event) - 2;
138             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_AVAILABLE_PLAYERS_CHANGED;
139             little_endian_store_16(event, offset, avrcp_cid);
140             offset += 2;
141             event[offset++] = ctype;
142             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
143             break;
144         }
145         case AVRCP_NOTIFICATION_EVENT_VOLUME_CHANGED:{
146             uint16_t offset = 0;
147             uint8_t event[7];
148             event[offset++] = HCI_EVENT_AVRCP_META;
149             event[offset++] = sizeof(event) - 2;
150             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_VOLUME_CHANGED;
151             little_endian_store_16(event, offset, avrcp_cid);
152             offset += 2;
153             event[offset++] = ctype;
154             event[offset++] = payload[0] & 0x7F;
155             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
156             break;
157         }
158         case AVRCP_NOTIFICATION_EVENT_UIDS_CHANGED:{
159             uint8_t event[8];
160             uint16_t offset = 0;
161             uint16_t uuid = big_endian_read_16(payload, 0);
162             event[offset++] = HCI_EVENT_AVRCP_META;
163             event[offset++] = sizeof(event) - 2;
164             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_EVENT_UIDS_CHANGED;
165             little_endian_store_16(event, offset, avrcp_cid);
166             offset += 2;
167             event[offset++] = ctype;
168             little_endian_store_16(event, offset, uuid);
169             offset += 2;
170             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
171             break;
172         }
173 
174         case AVRCP_NOTIFICATION_EVENT_TRACK_REACHED_END:{
175             uint16_t offset = 0;
176             uint8_t event[6];
177             event[offset++] = HCI_EVENT_AVRCP_META;
178             event[offset++] = sizeof(event) - 2;
179             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_EVENT_TRACK_REACHED_END;
180             little_endian_store_16(event, offset, avrcp_cid);
181             offset += 2;
182             event[offset++] = ctype;
183             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
184             break;
185         }
186         case AVRCP_NOTIFICATION_EVENT_TRACK_REACHED_START:{
187             uint16_t offset = 0;
188             uint8_t event[6];
189             event[offset++] = HCI_EVENT_AVRCP_META;
190             event[offset++] = sizeof(event) - 2;
191             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_EVENT_TRACK_REACHED_START;
192             little_endian_store_16(event, offset, avrcp_cid);
193             offset += 2;
194             event[offset++] = ctype;
195             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
196             break;
197         }
198         case AVRCP_NOTIFICATION_EVENT_BATT_STATUS_CHANGED:{
199             uint16_t offset = 0;
200             uint8_t event[7];
201             event[offset++] = HCI_EVENT_AVRCP_META;
202             event[offset++] = sizeof(event) - 2;
203             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_EVENT_BATT_STATUS_CHANGED;
204             little_endian_store_16(event, offset, avrcp_cid);
205             offset += 2;
206             event[offset++] = ctype;
207             event[offset++] = payload[0];
208             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
209             break;
210         }
211 
212         case AVRCP_NOTIFICATION_EVENT_SYSTEM_STATUS_CHANGED:{
213             uint16_t offset = 0;
214             uint8_t event[7];
215             event[offset++] = HCI_EVENT_AVRCP_META;
216             event[offset++] = sizeof(event) - 2;
217             event[offset++] = AVRCP_SUBEVENT_NOTIFICATION_EVENT_SYSTEM_STATUS_CHANGED;
218             little_endian_store_16(event, offset, avrcp_cid);
219             offset += 2;
220             event[offset++] = ctype;
221             event[offset++] = payload[0];
222             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
223             break;
224         }
225 
226         case AVRCP_NOTIFICATION_EVENT_PLAYER_APPLICATION_SETTING_CHANGED:
227         default:
228             log_info("avrcp: not implemented");
229             break;
230     }
231 }
232 
233 static void avrcp_controller_emit_repeat_and_shuffle_mode(btstack_packet_handler_t callback, uint16_t avrcp_cid, uint8_t ctype, avrcp_repeat_mode_t repeat_mode, avrcp_shuffle_mode_t shuffle_mode){
234     btstack_assert(callback != NULL);
235 
236     uint8_t event[8];
237     int pos = 0;
238     event[pos++] = HCI_EVENT_AVRCP_META;
239     event[pos++] = sizeof(event) - 2;
240     event[pos++] = AVRCP_SUBEVENT_SHUFFLE_AND_REPEAT_MODE;
241     little_endian_store_16(event, pos, avrcp_cid);
242     pos += 2;
243     event[pos++] = ctype;
244     event[pos++] = repeat_mode;
245     event[pos++] = shuffle_mode;
246     (*callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
247 }
248 
249 static void avrcp_controller_emit_now_playing_info_event_done(btstack_packet_handler_t callback, uint16_t avrcp_cid, uint8_t ctype, uint8_t status){
250     uint8_t event[7];
251     int pos = 0;
252     event[pos++] = HCI_EVENT_AVRCP_META;
253     event[pos++] = sizeof(event) - 2;
254     event[pos++] = AVRCP_SUBEVENT_NOW_PLAYING_INFO_DONE;
255     little_endian_store_16(event, pos, avrcp_cid);
256     pos += 2;
257     event[pos++] = ctype;
258     event[pos++] = status;
259     // printf_hexdump(event, pos);
260     (*callback)(HCI_EVENT_PACKET, 0, event, pos);
261 }
262 
263 static void avrcp_controller_emit_now_playing_info_event(btstack_packet_handler_t callback, uint16_t avrcp_cid, uint8_t ctype, avrcp_media_attribute_id_t attr_id, uint8_t * value, uint16_t value_len){
264     uint8_t event[HCI_EVENT_BUFFER_SIZE];
265     int pos = 0;
266     event[pos++] = HCI_EVENT_AVRCP_META;
267     // reserve one byte for subevent type and data len
268     int data_len_pos = pos;
269     pos++;
270     int subevent_type_pos = pos;
271     pos++;
272     little_endian_store_16(event, pos, avrcp_cid);
273     pos += 2;
274     event[pos++] = ctype;
275 
276     switch (attr_id){
277         case AVRCP_MEDIA_ATTR_TITLE:
278             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_TITLE_INFO;
279             event[pos++] = value_len;
280             (void)memcpy(event + pos, value, value_len);
281             break;
282         case AVRCP_MEDIA_ATTR_ARTIST:
283             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_ARTIST_INFO;
284             event[pos++] = value_len;
285             (void)memcpy(event + pos, value, value_len);
286             break;
287         case AVRCP_MEDIA_ATTR_ALBUM:
288             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_ALBUM_INFO;
289             event[pos++] = value_len;
290             (void)memcpy(event + pos, value, value_len);
291             break;
292         case AVRCP_MEDIA_ATTR_GENRE:
293             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_GENRE_INFO;
294             event[pos++] = value_len;
295             (void)memcpy(event + pos, value, value_len);
296             break;
297         case AVRCP_MEDIA_ATTR_SONG_LENGTH_MS:
298             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_SONG_LENGTH_MS_INFO;
299             if (value){
300                 little_endian_store_32(event, pos, btstack_atoi((char *)value));
301             } else {
302                 little_endian_store_32(event, pos, 0);
303             }
304             pos += 4;
305             break;
306         case AVRCP_MEDIA_ATTR_TRACK:
307             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_TRACK_INFO;
308             if (value){
309                 event[pos++] = btstack_atoi((char *)value);
310             } else {
311                 event[pos++] = 0;
312             }
313             break;
314         case AVRCP_MEDIA_ATTR_TOTAL_NUM_ITEMS:
315             event[subevent_type_pos] = AVRCP_SUBEVENT_NOW_PLAYING_TOTAL_TRACKS_INFO;
316             if (value){
317                 event[pos++] = btstack_atoi((char *)value);
318             } else {
319                 event[pos++] = 0;
320             }
321             break;
322         default:
323             break;
324     }
325     event[data_len_pos] = pos - 2;
326     (*callback)(HCI_EVENT_PACKET, 0, event, pos);
327 }
328 
329 static void avrcp_controller_emit_operation_status(btstack_packet_handler_t callback, uint8_t subevent, uint16_t avrcp_cid, uint8_t ctype, uint8_t operation_id){
330     btstack_assert(callback != NULL);
331 
332     uint8_t event[7];
333     int pos = 0;
334     event[pos++] = HCI_EVENT_AVRCP_META;
335     event[pos++] = sizeof(event) - 2;
336     event[pos++] = subevent;
337     little_endian_store_16(event, pos, avrcp_cid);
338     pos += 2;
339     event[pos++] = ctype;
340     event[pos++] = operation_id;
341     (*callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
342 }
343 
344 static void avrcp_parser_reset(avrcp_connection_t * connection){
345     connection->list_offset = 0;
346     connection->num_attributes = 0;
347     connection->num_parsed_attributes = 0;
348     connection->parser_attribute_header_pos = 0;
349     connection->num_received_fragments = 0;
350     connection->parser_state = AVRCP_PARSER_GET_ATTRIBUTE_HEADER;
351 }
352 
353 static void avrcp_parser_process_byte(uint8_t byte, avrcp_connection_t * connection, avrcp_command_type_t ctype){
354     uint16_t attribute_total_value_len;
355     uint32_t attribute_id;
356     // printf("avrcp_parser_process_byte: %02x, state %02x\n", byte, connection->parser_state);
357     switch(connection->parser_state){
358         case AVRCP_PARSER_GET_ATTRIBUTE_HEADER:
359             connection->parser_attribute_header[connection->parser_attribute_header_pos++] = byte;
360             connection->list_offset++;
361 
362             if (connection->parser_attribute_header_pos < AVRCP_ATTRIBUTE_HEADER_LEN) return;
363 
364             attribute_total_value_len = big_endian_read_16(connection->parser_attribute_header, 6);
365             connection->attribute_value_len = btstack_min(attribute_total_value_len, AVRCP_MAX_ATTRIBUTTE_SIZE);
366             if (connection->attribute_value_len > 0){
367                 // get ready for attribute value
368                 connection->parser_state = AVRCP_PARSER_GET_ATTRIBUTE_VALUE;
369                 return;
370             }
371 
372             // emit empty attribute
373             attribute_id = big_endian_read_32(connection->parser_attribute_header, 0);
374             avrcp_controller_emit_now_playing_info_event(avrcp_controller_context.avrcp_callback, connection->avrcp_cid, ctype, (avrcp_media_attribute_id_t) attribute_id, connection->attribute_value, connection->attribute_value_len);
375 
376             // done, see below
377             break;
378 
379         case AVRCP_PARSER_GET_ATTRIBUTE_VALUE:
380             connection->attribute_value[connection->attribute_value_offset++] = byte;
381             connection->list_offset++;
382 
383             if (connection->attribute_value_offset < connection->attribute_value_len) return;
384 
385             // emit (potentially partial) attribute
386             attribute_id = big_endian_read_32(connection->parser_attribute_header, 0);
387             avrcp_controller_emit_now_playing_info_event(avrcp_controller_context.avrcp_callback, connection->avrcp_cid, ctype, (avrcp_media_attribute_id_t) attribute_id, connection->attribute_value, connection->attribute_value_len);
388 
389             attribute_total_value_len = big_endian_read_16(connection->parser_attribute_header, 6);
390             if (connection->attribute_value_offset < attribute_total_value_len){
391                 // ignore rest of attribute
392                 connection->parser_state = AVRCP_PARSER_IGNORE_REST_OF_ATTRIBUTE_VALUE;
393                 return;
394             }
395 
396             // done, see below
397             break;
398 
399         case AVRCP_PARSER_IGNORE_REST_OF_ATTRIBUTE_VALUE:
400             connection->attribute_value_offset++;
401             connection->list_offset++;
402 
403             attribute_total_value_len = big_endian_read_16(connection->parser_attribute_header, 6);
404             if (connection->attribute_value_offset < attribute_total_value_len) return;
405 
406             // done, see below
407             break;
408 
409         default:
410             return;
411     }
412 
413     // attribute fully read, check if more to come
414     if (connection->list_offset < connection->list_size){
415         // more to come, reset parser
416         connection->parser_state = AVRCP_PARSER_GET_ATTRIBUTE_HEADER;
417         connection->parser_attribute_header_pos = 0;
418         connection->attribute_value_offset = 0;
419     } else {
420         // fully done
421         avrcp_parser_reset(connection);
422         avrcp_controller_emit_now_playing_info_event_done(avrcp_controller_context.avrcp_callback, connection->avrcp_cid, ctype, 0);
423     }
424 }
425 
426 static void avrcp_controller_parse_and_emit_element_attrs(uint8_t * packet, uint16_t num_bytes_to_read, avrcp_connection_t * connection, avrcp_command_type_t ctype){
427     int i;
428     for (i=0;i<num_bytes_to_read;i++){
429         avrcp_parser_process_byte(packet[i], connection, ctype);
430     }
431 }
432 
433 
434 static int avrcp_send_cmd(avrcp_connection_t * connection, avrcp_packet_type_t packet_type){
435     uint8_t  command[AVRCP_CMD_BUFFER_SIZE];
436     uint16_t pos = 0;
437 
438     // non-fragmented: transport header (1) + PID (2)
439     // fragmented:     transport header (1) + num packets (1) + PID (2)
440 
441     // transport header : transaction label | Packet_type | C/R | IPID (1 == invalid profile identifier)
442     command[pos++] = (connection->transaction_label << 4) | (packet_type << 2) | (AVRCP_COMMAND_FRAME << 1) | 0;
443 
444     if (packet_type == AVRCP_START_PACKET){
445         // num packets: (3 bytes overhead (PID, num packets) + command) / (MTU - transport header).
446         // to get number of packets using integer division, we subtract 1 from the data e.g. len = 5, packet size 5 => need 1 packet
447         command[pos++] = ((connection->cmd_operands_fragmented_len + 3 - 1) / (AVRCP_CMD_BUFFER_SIZE - 1)) + 1;
448     }
449 
450     if ((packet_type == AVRCP_SINGLE_PACKET) || (packet_type == AVRCP_START_PACKET)){
451         // Profile IDentifier (PID)
452         command[pos++] = BLUETOOTH_SERVICE_CLASS_AV_REMOTE_CONTROL >> 8;
453         command[pos++] = BLUETOOTH_SERVICE_CLASS_AV_REMOTE_CONTROL & 0x00FF;
454 
455         // command_type
456         command[pos++] = connection->command_type;
457         // subunit_type | subunit ID
458         command[pos++] = (connection->subunit_type << 3) | connection->subunit_id;
459         // opcode
460         command[pos++] = (uint8_t)connection->command_opcode;
461     }
462 
463     if (packet_type == AVRCP_SINGLE_PACKET){
464         // operands
465         (void)memcpy(command + pos, connection->cmd_operands,
466                      connection->cmd_operands_length);
467         pos += connection->cmd_operands_length;
468     } else {
469         uint16_t bytes_free = AVRCP_CMD_BUFFER_SIZE - pos;
470         uint16_t bytes_to_store = connection->cmd_operands_fragmented_len-connection->cmd_operands_fragmented_pos;
471         uint16_t bytes_to_copy = btstack_min(bytes_to_store, bytes_free);
472         (void)memcpy(command + pos,
473                      &connection->cmd_operands_fragmented_buffer[connection->cmd_operands_fragmented_pos],
474                      bytes_to_copy);
475         pos += bytes_to_copy;
476         connection->cmd_operands_fragmented_pos += bytes_to_copy;
477     }
478 
479     return l2cap_send(connection->l2cap_signaling_cid, command, pos);
480 }
481 
482 static int avrcp_send_register_notification(avrcp_connection_t * connection, uint8_t event_id){
483     uint8_t command[18];
484     uint16_t pos = 0;
485     // transport header : transaction label | Packet_type | C/R | IPID (1 == invalid profile identifier)
486     connection->transaction_label = avrcp_controller_get_next_transaction_label();
487     command[pos++] = (connection->transaction_label << 4) | (AVRCP_SINGLE_PACKET << 2) | (AVRCP_COMMAND_FRAME << 1) | 0;
488 
489     command[pos++] = BLUETOOTH_SERVICE_CLASS_AV_REMOTE_CONTROL >> 8;
490     command[pos++] = BLUETOOTH_SERVICE_CLASS_AV_REMOTE_CONTROL & 0x00FF;
491     command[pos++] = AVRCP_CTYPE_NOTIFY;
492     command[pos++] = (AVRCP_SUBUNIT_TYPE_PANEL << 3) | AVRCP_SUBUNIT_ID;
493     command[pos++] = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
494 
495     big_endian_store_24(command, pos, BT_SIG_COMPANY_ID);
496     pos += 3;
497     command[pos++] = AVRCP_PDU_ID_REGISTER_NOTIFICATION;
498     command[pos++] = 0;                       // reserved(upper 6) | packet_type -> 0
499     big_endian_store_16(command, pos, 5);     // parameter length
500     pos += 2;
501     command[pos++] = event_id;
502     big_endian_store_32(command, pos, 1);     // send notification on playback position every second, for other notifications it is ignored
503     pos += 4;
504     return l2cap_send(connection->l2cap_signaling_cid, command, pos);
505 }
506 
507 static void avrcp_press_and_hold_timeout_handler(btstack_timer_source_t * timer){
508     UNUSED(timer);
509     avrcp_connection_t * connection = (avrcp_connection_t*) btstack_run_loop_get_timer_context(timer);
510     btstack_run_loop_set_timer(&connection->press_and_hold_cmd_timer, 2000); // 2 seconds timeout
511     btstack_run_loop_add_timer(&connection->press_and_hold_cmd_timer);
512     connection->state = AVCTP_W2_SEND_PRESS_COMMAND;
513     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
514 }
515 
516 static void avrcp_press_and_hold_timer_start(avrcp_connection_t * connection){
517     btstack_run_loop_remove_timer(&connection->press_and_hold_cmd_timer);
518     btstack_run_loop_set_timer_handler(&connection->press_and_hold_cmd_timer, avrcp_press_and_hold_timeout_handler);
519     btstack_run_loop_set_timer_context(&connection->press_and_hold_cmd_timer, connection);
520     btstack_run_loop_set_timer(&connection->press_and_hold_cmd_timer, 2000); // 2 seconds timeout
521     btstack_run_loop_add_timer(&connection->press_and_hold_cmd_timer);
522 }
523 
524 static void avrcp_press_and_hold_timer_stop(avrcp_connection_t * connection){
525     connection->continuous_fast_forward_cmd = 0;
526     btstack_run_loop_remove_timer(&connection->press_and_hold_cmd_timer);
527 }
528 
529 
530 static uint8_t avrcp_controller_request_pass_through_release_control_cmd(avrcp_connection_t * connection){
531     connection->state = AVCTP_W2_SEND_RELEASE_COMMAND;
532     if (connection->continuous_fast_forward_cmd){
533         avrcp_press_and_hold_timer_stop(connection);
534     }
535     connection->cmd_operands[0] = 0x80 | connection->cmd_operands[0];
536     connection->transaction_label = avrcp_controller_get_next_transaction_label();
537     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
538     return ERROR_CODE_SUCCESS;
539 }
540 
541 static inline uint8_t avrcp_controller_request_pass_through_press_control_cmd(uint16_t avrcp_cid, avrcp_operation_id_t opid, uint16_t playback_speed, uint8_t continuous_fast_forward_cmd){
542     log_info("Send command %d", opid);
543     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
544     if (!connection){
545         log_error("Could not find a connection. avrcp cid 0x%02x", avrcp_cid);
546         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
547     }
548 
549     if (connection->state != AVCTP_CONNECTION_OPENED){
550         log_error("Connection in wrong state %d, expected %d. avrcp cid 0x%02x", connection->state, AVCTP_CONNECTION_OPENED, avrcp_cid);
551         return ERROR_CODE_COMMAND_DISALLOWED;
552     }
553     connection->state = AVCTP_W2_SEND_PRESS_COMMAND;
554     connection->command_opcode =  AVRCP_CMD_OPCODE_PASS_THROUGH;
555     connection->command_type = AVRCP_CTYPE_CONTROL;
556     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
557     connection->subunit_id =   AVRCP_SUBUNIT_ID;
558     connection->cmd_operands_length = 0;
559 
560     connection->continuous_fast_forward_cmd = continuous_fast_forward_cmd;
561     connection->cmd_operands_length = 2;
562     connection->cmd_operands[0] = opid;
563     if (playback_speed > 0){
564         connection->cmd_operands[2] = playback_speed;
565         connection->cmd_operands_length++;
566     }
567     connection->cmd_operands[1] = connection->cmd_operands_length - 2;
568 
569     if (connection->continuous_fast_forward_cmd){
570         avrcp_press_and_hold_timer_start(connection);
571     }
572 
573     connection->transaction_label = avrcp_controller_get_next_transaction_label();
574     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
575     return ERROR_CODE_SUCCESS;
576 }
577 
578 static uint8_t request_single_pass_through_press_control_cmd(uint16_t avrcp_cid, avrcp_operation_id_t opid, uint16_t playback_speed){
579     return avrcp_controller_request_pass_through_press_control_cmd(avrcp_cid, opid, playback_speed, 0);
580 }
581 
582 static uint8_t request_continuous_pass_through_press_control_cmd(uint16_t avrcp_cid, avrcp_operation_id_t opid, uint16_t playback_speed){
583     return avrcp_controller_request_pass_through_press_control_cmd(avrcp_cid, opid, playback_speed, 1);
584 }
585 
586 static int avrcp_controller_register_notification(avrcp_connection_t * connection, avrcp_notification_event_id_t event_id){
587     if (connection->notifications_to_deregister & (1 << event_id)) return 0;
588     if (connection->notifications_enabled & (1 << event_id)) return 0;
589     if (connection->notifications_to_register & (1 << event_id)) return 0;
590     connection->notifications_to_register |= (1 << event_id);
591     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
592     return 1;
593 }
594 
595 static uint8_t avrcp_controller_request_abort_continuation(avrcp_connection_t * connection){
596     connection->state = AVCTP_W2_SEND_COMMAND;
597     connection->transaction_label = avrcp_controller_get_next_transaction_label();
598     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
599     connection->command_type = AVRCP_CTYPE_CONTROL;
600     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
601     connection->subunit_id = AVRCP_SUBUNIT_ID;
602     int pos = 0;
603     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
604     pos += 3;
605     connection->cmd_operands[pos++] = AVRCP_PDU_ID_REQUEST_ABORT_CONTINUING_RESPONSE; // PDU ID
606     connection->cmd_operands[pos++] = 0;
607     // Parameter Length
608     connection->cmd_operands_length = 8;
609     big_endian_store_16(connection->cmd_operands, pos, 1);
610     pos += 2;
611     connection->cmd_operands[pos++] = AVRCP_PDU_ID_GET_ELEMENT_ATTRIBUTES;
612     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
613     return ERROR_CODE_SUCCESS;
614 }
615 
616 
617 static uint8_t avrcp_controller_request_continue_response(avrcp_connection_t * connection){
618     connection->state = AVCTP_W2_SEND_COMMAND;
619     connection->transaction_label = avrcp_controller_get_next_transaction_label();
620     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
621     connection->command_type = AVRCP_CTYPE_CONTROL;
622     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
623     connection->subunit_id = AVRCP_SUBUNIT_ID;
624     int pos = 0;
625     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
626     pos += 3;
627     connection->cmd_operands[pos++] = AVRCP_PDU_ID_REQUEST_CONTINUING_RESPONSE; // PDU ID
628     connection->cmd_operands[pos++] = 0;
629     // Parameter Length
630     connection->cmd_operands_length = 8;
631     big_endian_store_16(connection->cmd_operands, pos, 1);
632     pos += 2;
633     connection->cmd_operands[pos++] = AVRCP_PDU_ID_GET_ELEMENT_ATTRIBUTES;
634     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
635     return ERROR_CODE_SUCCESS;
636 }
637 
638 static void avrcp_controller_handle_notification(avrcp_connection_t * connection, avrcp_command_type_t ctype, uint8_t * payload){
639     uint16_t pos = 0;
640     avrcp_notification_event_id_t event_id = (avrcp_notification_event_id_t) payload[pos++];
641     uint16_t event_mask = (1 << event_id);
642     uint16_t reset_event_mask = ~event_mask;
643     switch (ctype){
644         case AVRCP_CTYPE_RESPONSE_INTERIM:
645             // register as enabled
646             connection->notifications_enabled |= event_mask;
647             break;
648         case AVRCP_CTYPE_RESPONSE_CHANGED_STABLE:
649             // received change, event is considered deregistered
650             // we are re-enabling it automatically, if it is not
651             // explicitly disabled
652             connection->notifications_enabled &= reset_event_mask;
653             if (! (connection->notifications_to_deregister & event_mask)){
654                 avrcp_controller_register_notification(connection, event_id);
655             } else {
656                 connection->notifications_to_deregister &= reset_event_mask;
657             }
658             break;
659         default:
660             connection->notifications_to_register &= reset_event_mask;
661             connection->notifications_enabled &= reset_event_mask;
662             connection->notifications_to_deregister &= reset_event_mask;
663             break;
664     }
665 
666     avrcp_controller_emit_notification_for_event_id(connection->avrcp_cid, event_id, ctype, payload+pos);
667 }
668 
669 static void avrcp_handle_l2cap_data_packet_for_signaling_connection(avrcp_connection_t * connection, uint8_t *packet, uint16_t size){
670     if (size < 6u) return;
671 
672     uint16_t pos = 3;
673     uint8_t  pdu_id;
674 
675     avrcp_frame_type_t  frame_type = (avrcp_frame_type_t)((packet[0] >> 1) & 0x01);
676     if (frame_type != AVRCP_RESPONSE_FRAME) return;
677 
678     avrcp_packet_type_t packet_type = (avrcp_packet_type_t)((packet[0] >> 2) & 0x03);
679     switch (packet_type){
680         case AVRCP_SINGLE_PACKET:
681             break;
682         default:
683             log_info("Fragmentation is not supported");
684             return;
685     }
686 
687     avrcp_command_type_t ctype = (avrcp_command_type_t) packet[pos++];
688 
689     uint8_t byte_value = packet[pos++];
690     avrcp_subunit_type_t subunit_type = (avrcp_subunit_type_t) (byte_value >> 3);
691     avrcp_subunit_type_t subunit_id   = (avrcp_subunit_type_t)   (byte_value & 0x07);
692     uint8_t opcode = packet[pos++];
693 
694     uint16_t param_length;
695 
696     switch (opcode){
697         case AVRCP_CMD_OPCODE_SUBUNIT_INFO:{
698             if (connection->state != AVCTP_W2_RECEIVE_RESPONSE) return;
699             connection->state = AVCTP_CONNECTION_OPENED;
700             // page, extention code (1)
701             pos++;
702             uint8_t unit_type = packet[pos] >> 3;
703             uint8_t max_subunit_ID = packet[pos] & 0x07;
704             log_info("SUBUNIT INFO response: ctype 0x%02x (0C), subunit_type 0x%02x (1F), subunit_id 0x%02x (07), opcode 0x%02x (30), unit_type 0x%02x, max_subunit_ID %d", ctype, subunit_type, subunit_id, opcode, unit_type, max_subunit_ID);
705             break;
706         }
707         case AVRCP_CMD_OPCODE_UNIT_INFO:{
708             if (connection->state != AVCTP_W2_RECEIVE_RESPONSE) return;
709             connection->state = AVCTP_CONNECTION_OPENED;
710             // byte value 7 (1)
711             pos++;
712             uint8_t unit_type = packet[pos] >> 3;
713             uint8_t unit = packet[pos] & 0x07;
714             pos++;
715             uint32_t company_id = big_endian_read_24(packet, pos);
716             log_info("UNIT INFO response: ctype 0x%02x (0C), subunit_type 0x%02x (1F), subunit_id 0x%02x (07), opcode 0x%02x (30), unit_type 0x%02x, unit %d, company_id 0x%06" PRIx32,
717                 ctype, subunit_type, subunit_id, opcode, unit_type, unit, company_id);
718             break;
719         }
720         case AVRCP_CMD_OPCODE_VENDOR_DEPENDENT:
721             // Company ID (3)
722             pos += 3;
723             pdu_id = packet[pos++];
724             // packet type (1)
725             pos++;
726             param_length = big_endian_read_16(packet, pos);
727             pos += 2;
728             log_info("operands length %d, remaining size %d", param_length, size - pos);
729 
730             if ((size - pos) < param_length) {
731                 log_error("Wrong packet size %d < %d", size - pos, param_length);
732                 return;
733             };
734 
735             // handle asynchronous notifications, without changing state
736             if (pdu_id == AVRCP_PDU_ID_REGISTER_NOTIFICATION){
737                 avrcp_controller_handle_notification(connection, ctype, packet+pos);
738                 break;
739             }
740 
741             if (connection->state != AVCTP_W2_RECEIVE_RESPONSE){
742                 log_info("AVRCP_CMD_OPCODE_VENDOR_DEPENDENT state %d", connection->state);
743                 return;
744             }
745             connection->state = AVCTP_CONNECTION_OPENED;
746 
747             log_info("VENDOR DEPENDENT response: pdu id 0x%02x, param_length %d, status %s", pdu_id, param_length, avrcp_ctype2str(ctype));
748             switch (pdu_id){
749                 case AVRCP_PDU_ID_GET_CURRENT_PLAYER_APPLICATION_SETTING_VALUE:{
750                     uint8_t num_attributes = packet[pos++];
751                     int i;
752                     avrcp_repeat_mode_t  repeat_mode =  AVRCP_REPEAT_MODE_INVALID;
753                     avrcp_shuffle_mode_t shuffle_mode = AVRCP_SHUFFLE_MODE_INVALID;
754                     for (i = 0; i < num_attributes; i++){
755                         uint8_t attribute_id    = packet[pos++];
756                         uint8_t value = packet[pos++];
757                         switch (attribute_id){
758                             case 0x02:
759                                 repeat_mode = (avrcp_repeat_mode_t) value;
760                                 break;
761                             case 0x03:
762                                 shuffle_mode = (avrcp_shuffle_mode_t) value;
763                                 break;
764                             default:
765                                 break;
766                         }
767                     }
768                     avrcp_controller_emit_repeat_and_shuffle_mode(avrcp_controller_context.avrcp_callback, connection->avrcp_cid, ctype, repeat_mode, shuffle_mode);
769                     break;
770                 }
771 
772                 case AVRCP_PDU_ID_SET_PLAYER_APPLICATION_SETTING_VALUE:{
773                     uint16_t offset = 0;
774                     uint8_t event[6];
775                     event[offset++] = HCI_EVENT_AVRCP_META;
776                     event[offset++] = sizeof(event) - 2;
777                     event[offset++] = AVRCP_SUBEVENT_PLAYER_APPLICATION_VALUE_RESPONSE;
778                     little_endian_store_16(event, offset, connection->avrcp_cid);
779                     offset += 2;
780                     event[offset++] = ctype;
781                     (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
782                     break;
783                 }
784 
785                 case AVRCP_PDU_ID_SET_ABSOLUTE_VOLUME:{
786                     uint16_t offset = 0;
787                     uint8_t event[7];
788                     event[offset++] = HCI_EVENT_AVRCP_META;
789                     event[offset++] = sizeof(event) - 2;
790                     event[offset++] = AVRCP_SUBEVENT_SET_ABSOLUTE_VOLUME_RESPONSE;
791                     little_endian_store_16(event, offset, connection->avrcp_cid);
792                     offset += 2;
793                     event[offset++] = ctype;
794                     event[offset++] = packet[pos++];
795                     (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
796                     break;
797                 }
798 
799                 case AVRCP_PDU_ID_GET_CAPABILITIES:{
800                     avrcp_capability_id_t capability_id = (avrcp_capability_id_t) packet[pos++];
801                     uint8_t capability_count = packet[pos++];
802                     uint16_t i;
803                     uint16_t offset = 0;
804                     uint8_t event[10];
805 
806                     switch (capability_id){
807 
808                         case AVRCP_CAPABILITY_ID_COMPANY:
809                             for (i = 0; i < capability_count; i++){
810                                 uint32_t company_id = big_endian_read_24(packet, pos);
811                                 pos += 3;
812                                 log_info("  0x%06" PRIx32 ", ", company_id);
813 
814                                 offset = 0;
815                                 event[offset++] = HCI_EVENT_AVRCP_META;
816                                 event[offset++] = sizeof(event) - 2;
817                                 event[offset++] = AVRCP_SUBEVENT_GET_CAPABILITY_COMPANY_ID;
818                                 little_endian_store_16(event, offset, connection->avrcp_cid);
819                                 offset += 2;
820                                 event[offset++] = ctype;
821                                 event[offset++] = 0;
822                                 little_endian_store_24(event, offset, company_id);
823                                 offset += 3;
824                                 (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, offset);
825                                 break;
826                             }
827 
828                             offset = 0;
829                             event[offset++] = HCI_EVENT_AVRCP_META;
830                             event[offset++] = sizeof(event) - 2;
831                             event[offset++] = AVRCP_SUBEVENT_GET_CAPABILITY_COMPANY_ID_DONE;
832                             little_endian_store_16(event, offset, connection->avrcp_cid);
833                             offset += 2;
834                             event[offset++] = ctype;
835                             event[offset++] = 0;
836                             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, offset);
837                             break;
838 
839                         case AVRCP_CAPABILITY_ID_EVENT:
840                             for (i = 0; i < capability_count; i++){
841                                 uint8_t event_id = packet[pos++];
842                                 log_info("  0x%02x %s", event_id, avrcp_event2str(event_id));
843 
844                                 offset = 0;
845                                 event[offset++] = HCI_EVENT_AVRCP_META;
846                                 event[offset++] = sizeof(event) - 2;
847                                 event[offset++] = AVRCP_SUBEVENT_GET_CAPABILITY_EVENT_ID;
848                                 little_endian_store_16(event, offset, connection->avrcp_cid);
849                                 offset += 2;
850                                 event[offset++] = ctype;
851                                 event[offset++] = 0;
852                                 event[offset++] = event_id;
853                                 (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, offset);
854                             }
855 
856                             offset = 0;
857                             event[offset++] = HCI_EVENT_AVRCP_META;
858                             event[offset++] = sizeof(event) - 2;
859                             event[offset++] = AVRCP_SUBEVENT_GET_CAPABILITY_EVENT_ID_DONE;
860                             little_endian_store_16(event, offset, connection->avrcp_cid);
861                             offset += 2;
862                             event[offset++] = ctype;
863                             event[offset++] = 0;
864                             (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
865                             break;
866                     }
867                     break;
868                 }
869 
870                 case AVRCP_PDU_ID_GET_PLAY_STATUS:{
871                     uint32_t song_length = big_endian_read_32(packet, pos);
872                     pos += 4;
873                     uint32_t song_position = big_endian_read_32(packet, pos);
874                     pos += 4;
875                     uint8_t play_status = packet[pos];
876 
877                     uint8_t event[15];
878                     int offset = 0;
879                     event[offset++] = HCI_EVENT_AVRCP_META;
880                     event[offset++] = sizeof(event) - 2;
881                     event[offset++] = AVRCP_SUBEVENT_PLAY_STATUS;
882                     little_endian_store_16(event, offset, connection->avrcp_cid);
883                     offset += 2;
884                     event[offset++] = ctype;
885                     little_endian_store_32(event, offset, song_length);
886                     offset += 4;
887                     little_endian_store_32(event, offset, song_position);
888                     offset += 4;
889                     event[offset++] = play_status;
890                     (*avrcp_controller_context.avrcp_callback)(HCI_EVENT_PACKET, 0, event, sizeof(event));
891                     break;
892                 }
893 
894                 case AVRCP_PDU_ID_GET_ELEMENT_ATTRIBUTES:{
895                     switch (packet_type){
896                         case AVRCP_START_PACKET:
897                         case AVRCP_SINGLE_PACKET:
898                             avrcp_parser_reset(connection);
899                             connection->list_size = param_length;
900                             connection->num_attributes = packet[pos++];
901 
902                             avrcp_controller_parse_and_emit_element_attrs(packet+pos, size-pos, connection, ctype);
903 
904                             if (packet_type == AVRCP_START_PACKET){
905                                 avrcp_controller_request_continue_response(connection);
906                             }
907                             break;
908                         case AVRCP_CONTINUE_PACKET:
909                         case AVRCP_END_PACKET:
910                             connection->num_received_fragments++;
911                             if (connection->num_received_fragments < connection->max_num_fragments){
912                                 avrcp_controller_parse_and_emit_element_attrs(packet+pos, size-pos, connection, ctype);
913                                 if (packet_type == AVRCP_CONTINUE_PACKET){
914                                     avrcp_controller_request_continue_response(connection);
915                                 }
916                             } else {
917                                 avrcp_controller_request_abort_continuation(connection);
918                                 avrcp_controller_emit_now_playing_info_event_done(avrcp_controller_context.avrcp_callback, connection->avrcp_cid, ctype, 1);
919                                 avrcp_parser_reset(connection);
920                             }
921                             break;
922                     }
923                 }
924                 default:
925                     break;
926             }
927             break;
928         case AVRCP_CMD_OPCODE_PASS_THROUGH:{
929             uint8_t operation_id = packet[pos++];
930             switch (connection->state){
931                 case AVCTP_W2_RECEIVE_PRESS_RESPONSE:
932                     if (connection->continuous_fast_forward_cmd){
933                         connection->state = AVCTP_W4_STOP;
934                     } else {
935                         connection->state = AVCTP_W2_SEND_RELEASE_COMMAND;
936                     }
937                     break;
938                 case AVCTP_W2_RECEIVE_RESPONSE:
939                     connection->state = AVCTP_CONNECTION_OPENED;
940                     break;
941                 default:
942                     break;
943             }
944             if (connection->state == AVCTP_W4_STOP){
945                 avrcp_controller_emit_operation_status(avrcp_controller_context.avrcp_callback, AVRCP_SUBEVENT_OPERATION_START, connection->avrcp_cid, ctype, operation_id);
946             }
947             if (connection->state == AVCTP_CONNECTION_OPENED) {
948                 // RELEASE response
949                 operation_id = operation_id & 0x7F;
950                 avrcp_controller_emit_operation_status(avrcp_controller_context.avrcp_callback, AVRCP_SUBEVENT_OPERATION_COMPLETE, connection->avrcp_cid, ctype, operation_id);
951             }
952             if (connection->state == AVCTP_W2_SEND_RELEASE_COMMAND){
953                 // PRESS response
954                 avrcp_controller_request_pass_through_release_control_cmd(connection);
955             }
956             break;
957         }
958         default:
959             break;
960     }
961 
962     // trigger pending notification reqistrations
963     if ((connection->state == AVCTP_CONNECTION_OPENED) && connection->notifications_to_register){
964         avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
965     }
966 }
967 
968 static void avrcp_controller_handle_can_send_now(avrcp_connection_t * connection){
969     switch (connection->state){
970         case AVCTP_W2_SEND_PRESS_COMMAND:
971             connection->state = AVCTP_W2_RECEIVE_PRESS_RESPONSE;
972             avrcp_send_cmd(connection, AVRCP_SINGLE_PACKET);
973             return;
974         case AVCTP_W2_SEND_COMMAND:
975         case AVCTP_W2_SEND_RELEASE_COMMAND:
976             connection->state = AVCTP_W2_RECEIVE_RESPONSE;
977             avrcp_send_cmd(connection, AVRCP_SINGLE_PACKET);
978             return;
979         case AVCTP_W2_SEND_FRAGMENTED_COMMAND:
980             if (connection->cmd_operands_fragmented_pos == 0){
981                  avrcp_send_cmd(connection, AVRCP_START_PACKET);
982                  avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
983             } else {
984                 if ((connection->cmd_operands_fragmented_len - connection->cmd_operands_fragmented_pos) > avrcp_get_max_payload_size_for_packet_type(AVRCP_CONTINUE_PACKET)){
985                      avrcp_send_cmd(connection, AVRCP_CONTINUE_PACKET);
986                      avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
987                  } else {
988                     connection->state = AVCTP_W2_RECEIVE_RESPONSE;
989                     avrcp_send_cmd(connection, AVRCP_END_PACKET);
990                  }
991             }
992             return;
993         default:
994             break;
995     }
996     // send register notification if queued
997     if (connection->notifications_to_register != 0){
998         uint8_t event_id;
999         for (event_id = 1; event_id <= AVRCP_NOTIFICATION_EVENT_VOLUME_CHANGED; event_id++){
1000             if (connection->notifications_to_register & (1<<event_id)){
1001                 connection->notifications_to_register &= ~ (1 << event_id);
1002                 avrcp_send_register_notification(connection, event_id);
1003                 return;
1004             }
1005         }
1006     }
1007 }
1008 
1009 static void avrcp_controller_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){
1010     avrcp_connection_t * connection;
1011 
1012     switch (packet_type) {
1013         case L2CAP_DATA_PACKET:
1014             connection = avrcp_get_connection_for_l2cap_signaling_cid_for_role(AVRCP_CONTROLLER, channel);
1015             avrcp_handle_l2cap_data_packet_for_signaling_connection(connection, packet, size);
1016             break;
1017 
1018         case HCI_EVENT_PACKET:
1019             switch (hci_event_packet_get_type(packet)){
1020                 case L2CAP_EVENT_CAN_SEND_NOW:
1021                     connection = avrcp_get_connection_for_l2cap_signaling_cid_for_role(AVRCP_CONTROLLER, channel);
1022                     avrcp_controller_handle_can_send_now(connection);
1023                     break;
1024             default:
1025                 break;
1026         }
1027         default:
1028             break;
1029     }
1030 }
1031 
1032 void avrcp_controller_create_sdp_record(uint8_t * service, uint32_t service_record_handle, uint16_t supported_features, const char * service_name, const char * service_provider_name){
1033     avrcp_create_sdp_record(1, service, service_record_handle, avrcp_controller_supports_browsing(supported_features), supported_features, service_name, service_provider_name);
1034 }
1035 
1036 void avrcp_controller_init(void){
1037     avrcp_controller_context.role = AVRCP_CONTROLLER;
1038     avrcp_controller_context.packet_handler = avrcp_controller_packet_handler;
1039     avrcp_register_controller_packet_handler(&avrcp_controller_packet_handler);
1040 }
1041 
1042 void avrcp_controller_register_packet_handler(btstack_packet_handler_t callback){
1043     btstack_assert(callback != NULL);
1044     avrcp_controller_context.avrcp_callback = callback;
1045 }
1046 
1047 
1048 uint8_t avrcp_controller_play(uint16_t avrcp_cid){
1049     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_PLAY, 0);
1050 }
1051 
1052 uint8_t avrcp_controller_stop(uint16_t avrcp_cid){
1053     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_STOP, 0);
1054 }
1055 
1056 uint8_t avrcp_controller_pause(uint16_t avrcp_cid){
1057     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_PAUSE, 0);
1058 }
1059 
1060 uint8_t avrcp_controller_forward(uint16_t avrcp_cid){
1061     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_FORWARD, 0);
1062 }
1063 
1064 uint8_t avrcp_controller_backward(uint16_t avrcp_cid){
1065     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_BACKWARD, 0);
1066 }
1067 
1068 uint8_t avrcp_controller_volume_up(uint16_t avrcp_cid){
1069     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_VOLUME_UP, 0);
1070 }
1071 
1072 uint8_t avrcp_controller_volume_down(uint16_t avrcp_cid){
1073     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_VOLUME_DOWN, 0);
1074 }
1075 
1076 uint8_t avrcp_controller_mute(uint16_t avrcp_cid){
1077     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_MUTE, 0);
1078 }
1079 
1080 uint8_t avrcp_controller_skip(uint16_t avrcp_cid){
1081     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_SKIP, 0);
1082 }
1083 
1084 uint8_t avrcp_controller_fast_forward(uint16_t avrcp_cid){
1085     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_FAST_FORWARD, 0);
1086 }
1087 
1088 uint8_t avrcp_controller_rewind(uint16_t avrcp_cid){
1089     return request_single_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_REWIND, 0);
1090 }
1091 
1092 /* start continuous cmds */
1093 
1094 uint8_t avrcp_controller_press_and_hold_play(uint16_t avrcp_cid){
1095     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_PLAY, 0);
1096 }
1097 uint8_t avrcp_controller_press_and_hold_stop(uint16_t avrcp_cid){
1098     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_STOP, 0);
1099 }
1100 uint8_t avrcp_controller_press_and_hold_pause(uint16_t avrcp_cid){
1101     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_PAUSE, 0);
1102 }
1103 uint8_t avrcp_controller_press_and_hold_forward(uint16_t avrcp_cid){
1104     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_FORWARD, 0);
1105 }
1106 uint8_t avrcp_controller_press_and_hold_backward(uint16_t avrcp_cid){
1107     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_BACKWARD, 0);
1108 }
1109 uint8_t avrcp_controller_press_and_hold_fast_forward(uint16_t avrcp_cid){
1110     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_FAST_FORWARD, 0);
1111 }
1112 uint8_t avrcp_controller_press_and_hold_rewind(uint16_t avrcp_cid){
1113     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_REWIND, 0);
1114 }
1115 uint8_t avrcp_controller_press_and_hold_volume_up(uint16_t avrcp_cid){
1116     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_VOLUME_UP, 0);
1117 }
1118 uint8_t avrcp_controller_press_and_hold_volume_down(uint16_t avrcp_cid){
1119     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_VOLUME_DOWN, 0);
1120 }
1121 uint8_t avrcp_controller_press_and_hold_mute(uint16_t avrcp_cid){
1122     return request_continuous_pass_through_press_control_cmd(avrcp_cid, AVRCP_OPERATION_ID_MUTE, 0);
1123 }
1124 
1125 /* stop continuous cmds */
1126 uint8_t avrcp_controller_release_press_and_hold_cmd(uint16_t avrcp_cid){
1127     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1128     if (!connection){
1129         log_error("avrcp_stop_play: could not find a connection.");
1130         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1131     }
1132     if (connection->state != AVCTP_W4_STOP) return ERROR_CODE_COMMAND_DISALLOWED;
1133     return avrcp_controller_request_pass_through_release_control_cmd(connection);
1134 }
1135 
1136 uint8_t avrcp_controller_enable_notification(uint16_t avrcp_cid, avrcp_notification_event_id_t event_id){
1137     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1138     if (!connection){
1139         log_error("avrcp_get_play_status: could not find a connection.");
1140         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1141     }
1142     avrcp_controller_register_notification(connection, event_id);
1143     return ERROR_CODE_SUCCESS;
1144 }
1145 
1146 uint8_t avrcp_controller_disable_notification(uint16_t avrcp_cid, avrcp_notification_event_id_t event_id){
1147     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1148     if (!connection){
1149         log_error("avrcp_get_play_status: could not find a connection.");
1150         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1151     }
1152     connection->notifications_to_deregister |= (1 << event_id);
1153     return ERROR_CODE_SUCCESS;
1154 }
1155 
1156 uint8_t avrcp_controller_unit_info(uint16_t avrcp_cid){
1157     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1158     if (!connection){
1159         log_error("avrcp_unit_info: could not find a connection.");
1160         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1161     }
1162     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1163     connection->state = AVCTP_W2_SEND_COMMAND;
1164 
1165     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1166     connection->command_opcode = AVRCP_CMD_OPCODE_UNIT_INFO;
1167     connection->command_type = AVRCP_CTYPE_STATUS;
1168     connection->subunit_type = AVRCP_SUBUNIT_TYPE_UNIT; //vendor unique
1169     connection->subunit_id =   AVRCP_SUBUNIT_ID_IGNORE;
1170     memset(connection->cmd_operands, 0xFF, connection->cmd_operands_length);
1171     connection->cmd_operands_length = 5;
1172     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1173     return ERROR_CODE_SUCCESS;
1174 }
1175 
1176 uint8_t avrcp_controller_subunit_info(uint16_t avrcp_cid){
1177     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1178     if (!connection){
1179         log_error("avrcp_unit_info: could not find a connection.");
1180         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1181     }
1182     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1183     connection->state = AVCTP_W2_SEND_COMMAND;
1184 
1185     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1186     connection->command_opcode = AVRCP_CMD_OPCODE_SUBUNIT_INFO;
1187     connection->command_type = AVRCP_CTYPE_STATUS;
1188     connection->subunit_type = AVRCP_SUBUNIT_TYPE_UNIT; //vendor unique
1189     connection->subunit_id =   AVRCP_SUBUNIT_ID_IGNORE;
1190     memset(connection->cmd_operands, 0xFF, connection->cmd_operands_length);
1191     connection->cmd_operands[0] = 7; // page: 0, extention_code: 7
1192     connection->cmd_operands_length = 5;
1193     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1194     return ERROR_CODE_SUCCESS;
1195 }
1196 
1197 static uint8_t avrcp_controller_get_capabilities(uint16_t avrcp_cid, uint8_t capability_id){
1198     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1199     if (!connection){
1200         log_error("avrcp_get_capabilities: could not find a connection.");
1201         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1202     }
1203     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1204     connection->state = AVCTP_W2_SEND_COMMAND;
1205 
1206     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1207     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1208     connection->command_type = AVRCP_CTYPE_STATUS;
1209     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1210     connection->subunit_id = AVRCP_SUBUNIT_ID;
1211     big_endian_store_24(connection->cmd_operands, 0, BT_SIG_COMPANY_ID);
1212     connection->cmd_operands[3] = AVRCP_PDU_ID_GET_CAPABILITIES; // PDU ID
1213     connection->cmd_operands[4] = 0;
1214     big_endian_store_16(connection->cmd_operands, 5, 1); // parameter length
1215     connection->cmd_operands[7] = capability_id;                  // capability ID
1216     connection->cmd_operands_length = 8;
1217     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1218     return ERROR_CODE_SUCCESS;
1219 }
1220 
1221 uint8_t avrcp_controller_get_supported_company_ids(uint16_t avrcp_cid){
1222     return avrcp_controller_get_capabilities(avrcp_cid, AVRCP_CAPABILITY_ID_COMPANY);
1223 }
1224 
1225 uint8_t avrcp_controller_get_supported_events(uint16_t avrcp_cid){
1226     return avrcp_controller_get_capabilities(avrcp_cid, AVRCP_CAPABILITY_ID_EVENT);
1227 }
1228 
1229 uint8_t avrcp_controller_get_play_status(uint16_t avrcp_cid){
1230     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1231     if (!connection){
1232         log_error("avrcp_get_play_status: could not find a connection.");
1233         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1234     }
1235     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1236     connection->state = AVCTP_W2_SEND_COMMAND;
1237     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1238     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1239     connection->command_type = AVRCP_CTYPE_STATUS;
1240     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1241     connection->subunit_id = AVRCP_SUBUNIT_ID;
1242     big_endian_store_24(connection->cmd_operands, 0, BT_SIG_COMPANY_ID);
1243     connection->cmd_operands[3] = AVRCP_PDU_ID_GET_PLAY_STATUS;
1244     connection->cmd_operands[4] = 0;                     // reserved(upper 6) | packet_type -> 0
1245     big_endian_store_16(connection->cmd_operands, 5, 0); // parameter length
1246     connection->cmd_operands_length = 7;
1247     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1248     return ERROR_CODE_SUCCESS;
1249 }
1250 
1251 uint8_t avrcp_controller_set_addressed_player(uint16_t avrcp_cid, uint16_t addressed_player_id){
1252     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1253     if (!connection){
1254         log_error("avrcp_get_capabilities: could not find a connection.");
1255         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1256     }
1257     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1258     connection->state = AVCTP_W2_SEND_COMMAND;
1259 
1260     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1261     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1262     connection->command_type = AVRCP_CTYPE_CONTROL;
1263     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1264     connection->subunit_id = AVRCP_SUBUNIT_ID;
1265     int pos = 0;
1266     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1267     pos += 3;
1268     connection->cmd_operands[pos++] = AVRCP_PDU_ID_SET_ADDRESSED_PLAYER; // PDU ID
1269     connection->cmd_operands[pos++] = 0;
1270 
1271     // Parameter Length
1272     big_endian_store_16(connection->cmd_operands, pos, 2);
1273     pos += 2;
1274 
1275     big_endian_store_16(connection->cmd_operands, pos, addressed_player_id);
1276     pos += 2;
1277 
1278     connection->cmd_operands_length = pos;
1279     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1280     return ERROR_CODE_SUCCESS;
1281 }
1282 
1283 uint8_t avrcp_controller_get_now_playing_info(uint16_t avrcp_cid){
1284     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1285     if (!connection){
1286         log_error("avrcp_get_capabilities: could not find a connection.");
1287         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1288     }
1289     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1290     connection->state = AVCTP_W2_SEND_COMMAND;
1291 
1292     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1293     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1294     connection->command_type = AVRCP_CTYPE_STATUS;
1295     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1296     connection->subunit_id = AVRCP_SUBUNIT_ID;
1297     int pos = 0;
1298     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1299     pos += 3;
1300     connection->cmd_operands[pos++] = AVRCP_PDU_ID_GET_ELEMENT_ATTRIBUTES; // PDU ID
1301     connection->cmd_operands[pos++] = 0;
1302 
1303     // Parameter Length
1304     big_endian_store_16(connection->cmd_operands, pos, 9);
1305     pos += 2;
1306 
1307     // write 8 bytes value
1308     memset(connection->cmd_operands + pos, 0, 8); // identifier: PLAYING
1309     pos += 8;
1310 
1311     connection->cmd_operands[pos++] = 0; // attribute count, if 0 get all attributes
1312     // every attribute is 4 bytes long
1313 
1314     connection->cmd_operands_length = pos;
1315     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1316     return ERROR_CODE_SUCCESS;
1317 }
1318 
1319 uint8_t avrcp_controller_set_absolute_volume(uint16_t avrcp_cid, uint8_t volume){
1320      avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1321     if (!connection){
1322         log_error("avrcp_get_capabilities: could not find a connection.");
1323         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1324     }
1325     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1326     connection->state = AVCTP_W2_SEND_COMMAND;
1327 
1328     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1329     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1330     connection->command_type = AVRCP_CTYPE_CONTROL;
1331     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1332     connection->subunit_id = AVRCP_SUBUNIT_ID;
1333     int pos = 0;
1334     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1335     pos += 3;
1336     connection->cmd_operands[pos++] = AVRCP_PDU_ID_SET_ABSOLUTE_VOLUME; // PDU ID
1337     connection->cmd_operands[pos++] = 0;
1338 
1339     // Parameter Length
1340     big_endian_store_16(connection->cmd_operands, pos, 1);
1341     pos += 2;
1342     connection->cmd_operands[pos++] = volume;
1343 
1344     connection->cmd_operands_length = pos;
1345     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1346     return ERROR_CODE_SUCCESS;
1347 }
1348 
1349 uint8_t avrcp_controller_query_shuffle_and_repeat_modes(uint16_t avrcp_cid){
1350     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1351     if (!connection){
1352         log_error("avrcp_get_capabilities: could not find a connection.");
1353         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1354     }
1355     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1356     connection->state = AVCTP_W2_SEND_COMMAND;
1357 
1358     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1359     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1360     connection->command_type = AVRCP_CTYPE_STATUS;
1361     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1362     connection->subunit_id = AVRCP_SUBUNIT_ID;
1363     big_endian_store_24(connection->cmd_operands, 0, BT_SIG_COMPANY_ID);
1364     connection->cmd_operands[3] = AVRCP_PDU_ID_GET_CURRENT_PLAYER_APPLICATION_SETTING_VALUE; // PDU ID
1365     connection->cmd_operands[4] = 0;
1366     big_endian_store_16(connection->cmd_operands, 5, 5); // parameter length
1367     connection->cmd_operands[7] = 4;                     // NumPlayerApplicationSettingAttributeID
1368     // PlayerApplicationSettingAttributeID1 AVRCP Spec, Appendix F, 133
1369     connection->cmd_operands[8]  = 0x01;    // equalizer  (1-OFF, 2-ON)
1370     connection->cmd_operands[9]  = 0x02;    // repeat     (1-off, 2-single track, 3-all tracks, 4-group repeat)
1371     connection->cmd_operands[10] = 0x03;    // shuffle    (1-off, 2-all tracks, 3-group shuffle)
1372     connection->cmd_operands[11] = 0x04;    // scan       (1-off, 2-all tracks, 3-group scan)
1373     connection->cmd_operands_length = 12;
1374     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1375     return ERROR_CODE_SUCCESS;
1376 }
1377 
1378 static uint8_t avrcp_controller_set_current_player_application_setting_value(uint16_t avrcp_cid, uint8_t attr_id, uint8_t attr_value){
1379     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1380     if (!connection){
1381         log_error("avrcp_get_capabilities: could not find a connection.");
1382         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1383     }
1384     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1385     connection->state = AVCTP_W2_SEND_COMMAND;
1386 
1387     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1388     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1389     connection->command_type = AVRCP_CTYPE_CONTROL;
1390     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1391     connection->subunit_id = AVRCP_SUBUNIT_ID;
1392     int pos = 0;
1393     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1394     pos += 3;
1395     connection->cmd_operands[pos++] = AVRCP_PDU_ID_SET_PLAYER_APPLICATION_SETTING_VALUE; // PDU ID
1396     connection->cmd_operands[pos++] = 0;
1397     // Parameter Length
1398     big_endian_store_16(connection->cmd_operands, pos, 3);
1399     pos += 2;
1400     connection->cmd_operands[pos++] = 2;
1401     connection->cmd_operands_length = pos;
1402     connection->cmd_operands[pos++]  = attr_id;
1403     connection->cmd_operands[pos++]  = attr_value;
1404     connection->cmd_operands_length = pos;
1405     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1406     return ERROR_CODE_SUCCESS;
1407 }
1408 
1409 uint8_t avrcp_controller_set_shuffle_mode(uint16_t avrcp_cid, avrcp_shuffle_mode_t mode){
1410     if ((mode < AVRCP_SHUFFLE_MODE_OFF) || (mode > AVRCP_SHUFFLE_MODE_GROUP)) return ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE;
1411     return avrcp_controller_set_current_player_application_setting_value(avrcp_cid, 0x03, mode);
1412 }
1413 
1414 uint8_t avrcp_controller_set_repeat_mode(uint16_t avrcp_cid, avrcp_repeat_mode_t mode){
1415     if ((mode < AVRCP_REPEAT_MODE_OFF) || (mode > AVRCP_REPEAT_MODE_GROUP)) return ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE;
1416     return avrcp_controller_set_current_player_application_setting_value(avrcp_cid, 0x02, mode);
1417 }
1418 
1419 uint8_t avrcp_controller_play_item_for_scope(uint16_t avrcp_cid, uint8_t * uid, uint16_t uid_counter, avrcp_browsing_scope_t scope){
1420     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1421     if (!connection){
1422         log_error("Could not find a connection with cid 0%02x.", avrcp_cid);
1423         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1424     }
1425     if (connection->state != AVCTP_CONNECTION_OPENED){
1426         log_error("Connection in wrong state, expected %d, received %d", AVCTP_CONNECTION_OPENED, connection->state);
1427         return ERROR_CODE_COMMAND_DISALLOWED;
1428     }
1429     connection->state = AVCTP_W2_SEND_COMMAND;
1430 
1431     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1432     connection->command_type = AVRCP_CTYPE_CONTROL;
1433     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1434     connection->subunit_id = AVRCP_SUBUNIT_ID;
1435     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1436     int pos = 0;
1437     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1438     pos += 3;
1439     connection->cmd_operands[pos++] = AVRCP_PDU_ID_PLAY_ITEM; // PDU ID
1440     // reserved
1441     connection->cmd_operands[pos++] = 0;
1442     // Parameter Length
1443     big_endian_store_16(connection->cmd_operands, pos, 11);
1444     pos += 2;
1445     connection->cmd_operands[pos++]  = scope;
1446     memset(&connection->cmd_operands[pos], 0, 8);
1447     if (uid){
1448         (void)memcpy(&connection->cmd_operands[pos], uid, 8);
1449     }
1450     pos += 8;
1451     big_endian_store_16(connection->cmd_operands, pos, uid_counter);
1452     pos += 2;
1453     connection->cmd_operands_length = pos;
1454 
1455     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1456     return ERROR_CODE_SUCCESS;
1457 }
1458 
1459 uint8_t avrcp_controller_add_item_from_scope_to_now_playing_list(uint16_t avrcp_cid, uint8_t * uid, uint16_t uid_counter, avrcp_browsing_scope_t scope){
1460     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1461     if (!connection){
1462         log_error("Could not find a connection with cid 0%02x.", avrcp_cid);
1463         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1464     }
1465     if (connection->state != AVCTP_CONNECTION_OPENED){
1466         log_error("Connection in wrong state, expected %d, received %d", AVCTP_CONNECTION_OPENED, connection->state);
1467         return ERROR_CODE_COMMAND_DISALLOWED;
1468     }
1469     connection->state = AVCTP_W2_SEND_COMMAND;
1470 
1471     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1472     connection->command_type = AVRCP_CTYPE_CONTROL;
1473     connection->subunit_type = AVRCP_SUBUNIT_TYPE_PANEL;
1474     connection->subunit_id = AVRCP_SUBUNIT_ID;
1475     connection->command_opcode = AVRCP_CMD_OPCODE_VENDOR_DEPENDENT;
1476     int pos = 0;
1477     big_endian_store_24(connection->cmd_operands, pos, BT_SIG_COMPANY_ID);
1478     pos += 3;
1479     connection->cmd_operands[pos++] = AVRCP_PDU_ID_ADD_TO_NOW_PLAYING; // PDU ID
1480     // reserved
1481     connection->cmd_operands[pos++] = 0;
1482     // Parameter Length
1483     big_endian_store_16(connection->cmd_operands, pos, 11);
1484     pos += 2;
1485     connection->cmd_operands[pos++]  = scope;
1486     memset(&connection->cmd_operands[pos], 0, 8);
1487     if (uid){
1488         (void)memcpy(&connection->cmd_operands[pos], uid, 8);
1489     }
1490     pos += 8;
1491     big_endian_store_16(connection->cmd_operands, pos, uid_counter);
1492     pos += 2;
1493     connection->cmd_operands_length = pos;
1494 
1495     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1496     return ERROR_CODE_SUCCESS;
1497 }
1498 
1499 uint8_t avrcp_controller_set_max_num_fragments(uint16_t avrcp_cid, uint8_t max_num_fragments){
1500     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1501     if (!connection){
1502         log_error("avrcp_controller_play_item: could not find a connection.");
1503         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1504     }
1505     connection->max_num_fragments = max_num_fragments;
1506     return ERROR_CODE_SUCCESS;
1507 }
1508 
1509 uint8_t avrcp_controller_send_custom_command(uint16_t avrcp_cid, avrcp_command_type_t command_type, avrcp_subunit_type_t subunit_type, avrcp_subunit_id_t subunit_id, avrcp_command_opcode_t command_opcode, const uint8_t * command_buffer, uint16_t command_len){
1510     avrcp_connection_t * connection = avrcp_get_connection_for_avrcp_cid_for_role(AVRCP_CONTROLLER, avrcp_cid);
1511     if (!connection){
1512         log_error("avrcp_controller_play_item: could not find a connection.");
1513         return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER;
1514     }
1515 
1516     if (connection->state != AVCTP_CONNECTION_OPENED) return ERROR_CODE_COMMAND_DISALLOWED;
1517     connection->state = AVCTP_W2_SEND_FRAGMENTED_COMMAND;
1518 
1519     connection->transaction_label = avrcp_controller_get_next_transaction_label();
1520     connection->command_opcode = command_opcode;
1521     connection->command_type = command_type;
1522     connection->subunit_type = subunit_type;
1523     connection->subunit_id = subunit_id;
1524     connection->cmd_operands_fragmented_buffer = command_buffer;
1525     connection->cmd_operands_fragmented_pos = 0;
1526     connection->cmd_operands_fragmented_len = command_len;
1527 
1528     avrcp_request_can_send_now(connection, connection->l2cap_signaling_cid);
1529     return ERROR_CODE_SUCCESS;
1530 }
1531