1 /******************************************************************************
2  *
3  *  Copyright (C) 1999-2012 Broadcom Corporation
4  *
5  *  Licensed under the Apache License, Version 2.0 (the "License");
6  *  you may not use this file except in compliance with the License.
7  *  You may obtain a copy of the License at:
8  *
9  *  http://www.apache.org/licenses/LICENSE-2.0
10  *
11  *  Unless required by applicable law or agreed to in writing, software
12  *  distributed under the License is distributed on an "AS IS" BASIS,
13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  *  See the License for the specific language governing permissions and
15  *  limitations under the License.
16  *
17  ******************************************************************************/
18 
19 /******************************************************************************
20  *
21  *  This file contains state machine and action routines for a port of the
22  *  RFCOMM unit
23  *
24  ******************************************************************************/
25 #include <string.h>
26 #include "bt_common.h"
27 #include "bt_target.h"
28 #include "bt_utils.h"
29 #include "btm_api.h"
30 #include "btm_int.h"
31 #include "osi/include/osi.h"
32 #include "port_api.h"
33 #include "port_int.h"
34 #include "rfc_int.h"
35 #include "rfcdefs.h"
36 
37 /******************************************************************************/
38 /*            L O C A L    F U N C T I O N     P R O T O T Y P E S            */
39 /******************************************************************************/
40 static void rfc_port_sm_state_closed(tPORT* p_port, uint16_t event,
41                                      void* p_data);
42 static void rfc_port_sm_sabme_wait_ua(tPORT* p_port, uint16_t event,
43                                       void* p_data);
44 static void rfc_port_sm_opened(tPORT* p_port, uint16_t event, void* p_data);
45 static void rfc_port_sm_orig_wait_sec_check(tPORT* p_port, uint16_t event,
46                                             void* p_data);
47 static void rfc_port_sm_term_wait_sec_check(tPORT* p_port, uint16_t event,
48                                             void* p_data);
49 static void rfc_port_sm_disc_wait_ua(tPORT* p_port, uint16_t event,
50                                      void* p_data);
51 
52 static void rfc_port_uplink_data(tPORT* p_port, BT_HDR* p_buf);
53 
54 static void rfc_set_port_state(tPORT_STATE* port_pars, MX_FRAME* p_frame);
55 
56 /*******************************************************************************
57  *
58  * Function         rfc_port_sm_execute
59  *
60  * Description      This function sends port events through the state
61  *                  machine.
62  *
63  * Returns          void
64  *
65  ******************************************************************************/
rfc_port_sm_execute(tPORT * p_port,uint16_t event,void * p_data)66 void rfc_port_sm_execute(tPORT* p_port, uint16_t event, void* p_data) {
67   if (!p_port) {
68     RFCOMM_TRACE_WARNING("NULL port event %d", event);
69     return;
70   }
71 
72   switch (p_port->rfc.state) {
73     case RFC_STATE_CLOSED:
74       rfc_port_sm_state_closed(p_port, event, p_data);
75       break;
76 
77     case RFC_STATE_SABME_WAIT_UA:
78       rfc_port_sm_sabme_wait_ua(p_port, event, p_data);
79       break;
80 
81     case RFC_STATE_ORIG_WAIT_SEC_CHECK:
82       rfc_port_sm_orig_wait_sec_check(p_port, event, p_data);
83       break;
84 
85     case RFC_STATE_TERM_WAIT_SEC_CHECK:
86       rfc_port_sm_term_wait_sec_check(p_port, event, p_data);
87       break;
88 
89     case RFC_STATE_OPENED:
90       rfc_port_sm_opened(p_port, event, p_data);
91       break;
92 
93     case RFC_STATE_DISC_WAIT_UA:
94       rfc_port_sm_disc_wait_ua(p_port, event, p_data);
95       break;
96   }
97 }
98 
99 /*******************************************************************************
100  *
101  * Function         rfc_port_sm_state_closed
102  *
103  * Description      This function handles events when the port is in
104  *                  CLOSED state. This state exists when port is
105  *                  being initially established.
106  *
107  * Returns          void
108  *
109  ******************************************************************************/
rfc_port_sm_state_closed(tPORT * p_port,uint16_t event,void * p_data)110 void rfc_port_sm_state_closed(tPORT* p_port, uint16_t event, void* p_data) {
111   switch (event) {
112     case RFC_EVENT_OPEN:
113       p_port->rfc.state = RFC_STATE_ORIG_WAIT_SEC_CHECK;
114       btm_sec_mx_access_request(
115           p_port->rfc.p_mcb->bd_addr, BT_PSM_RFCOMM, true, BTM_SEC_PROTO_RFCOMM,
116           (uint32_t)(p_port->dlci / 2), &rfc_sec_check_complete, p_port);
117       return;
118 
119     case RFC_EVENT_CLOSE:
120       break;
121 
122     case RFC_EVENT_CLEAR:
123       return;
124 
125     case RFC_EVENT_DATA:
126       osi_free(p_data);
127       break;
128 
129     case RFC_EVENT_SABME:
130       /* make sure the multiplexer disconnect timer is not running (reconnect
131        * case) */
132       rfc_timer_stop(p_port->rfc.p_mcb);
133 
134       /* Open will be continued after security checks are passed */
135       p_port->rfc.state = RFC_STATE_TERM_WAIT_SEC_CHECK;
136       btm_sec_mx_access_request(p_port->rfc.p_mcb->bd_addr, BT_PSM_RFCOMM,
137                                 false, BTM_SEC_PROTO_RFCOMM,
138                                 (uint32_t)(p_port->dlci / 2),
139                                 &rfc_sec_check_complete, p_port);
140       return;
141 
142     case RFC_EVENT_UA:
143       return;
144 
145     case RFC_EVENT_DM:
146       rfc_port_closed(p_port);
147       return;
148 
149     case RFC_EVENT_UIH:
150       osi_free(p_data);
151       rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, false);
152       return;
153 
154     case RFC_EVENT_DISC:
155       rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, false);
156       return;
157 
158     case RFC_EVENT_TIMEOUT:
159       Port_TimeOutCloseMux(p_port->rfc.p_mcb);
160       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
161                          event);
162       return;
163   }
164 
165   RFCOMM_TRACE_WARNING("Port state closed Event ignored %d", event);
166   return;
167 }
168 
169 /*******************************************************************************
170  *
171  * Function         rfc_port_sm_sabme_wait_ua
172  *
173  * Description      This function handles events when SABME on the DLC was
174  *                  sent and SM is waiting for UA or DM.
175  *
176  * Returns          void
177  *
178  ******************************************************************************/
rfc_port_sm_sabme_wait_ua(tPORT * p_port,uint16_t event,void * p_data)179 void rfc_port_sm_sabme_wait_ua(tPORT* p_port, uint16_t event, void* p_data) {
180   switch (event) {
181     case RFC_EVENT_OPEN:
182     case RFC_EVENT_ESTABLISH_RSP:
183       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
184                          event);
185       return;
186 
187     case RFC_EVENT_CLOSE:
188       rfc_port_timer_start(p_port, RFC_DISC_TIMEOUT);
189       rfc_send_disc(p_port->rfc.p_mcb, p_port->dlci);
190       p_port->rfc.expected_rsp = 0;
191       p_port->rfc.state = RFC_STATE_DISC_WAIT_UA;
192       return;
193 
194     case RFC_EVENT_CLEAR:
195       rfc_port_closed(p_port);
196       return;
197 
198     case RFC_EVENT_DATA:
199       osi_free(p_data);
200       break;
201 
202     case RFC_EVENT_UA:
203       rfc_port_timer_stop(p_port);
204       p_port->rfc.state = RFC_STATE_OPENED;
205       PORT_DlcEstablishCnf(p_port->rfc.p_mcb, p_port->dlci,
206                            p_port->rfc.p_mcb->peer_l2cap_mtu, RFCOMM_SUCCESS);
207       return;
208 
209     case RFC_EVENT_DM:
210       p_port->rfc.p_mcb->is_disc_initiator = true;
211       PORT_DlcEstablishCnf(p_port->rfc.p_mcb, p_port->dlci,
212                            p_port->rfc.p_mcb->peer_l2cap_mtu, RFCOMM_ERROR);
213       rfc_port_closed(p_port);
214       return;
215 
216     case RFC_EVENT_DISC:
217       rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
218       PORT_DlcEstablishCnf(p_port->rfc.p_mcb, p_port->dlci,
219                            p_port->rfc.p_mcb->peer_l2cap_mtu, RFCOMM_ERROR);
220       rfc_port_closed(p_port);
221       return;
222 
223     case RFC_EVENT_SABME:
224       /* Continue to wait for the UA the SABME this side sent */
225       rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
226       return;
227 
228     case RFC_EVENT_UIH:
229       osi_free(p_data);
230       return;
231 
232     case RFC_EVENT_TIMEOUT:
233       p_port->rfc.state = RFC_STATE_CLOSED;
234       PORT_DlcEstablishCnf(p_port->rfc.p_mcb, p_port->dlci,
235                            p_port->rfc.p_mcb->peer_l2cap_mtu, RFCOMM_ERROR);
236       return;
237   }
238   RFCOMM_TRACE_WARNING("Port state sabme_wait_ua Event ignored %d", event);
239 }
240 
241 /*******************************************************************************
242  *
243  * Function         rfc_port_sm_term_wait_sec_check
244  *
245  * Description      This function handles events for the port in the
246  *                  WAIT_SEC_CHECK state.  SABME has been received from the
247  *                  peer and Security Manager verifes BD_ADDR, before we can
248  *                  send ESTABLISH_IND to the Port entity
249  *
250  * Returns          void
251  *
252  ******************************************************************************/
rfc_port_sm_term_wait_sec_check(tPORT * p_port,uint16_t event,void * p_data)253 void rfc_port_sm_term_wait_sec_check(tPORT* p_port, uint16_t event,
254                                      void* p_data) {
255   switch (event) {
256     case RFC_EVENT_SEC_COMPLETE:
257       if (*((uint8_t*)p_data) != BTM_SUCCESS) {
258         /* Authentication/authorization failed.  If link is still  */
259         /* up send DM and check if we need to start inactive timer */
260         if (p_port->rfc.p_mcb) {
261           rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, true);
262           p_port->rfc.p_mcb->is_disc_initiator = true;
263           port_rfc_closed(p_port, PORT_SEC_FAILED);
264         }
265       } else {
266         PORT_DlcEstablishInd(p_port->rfc.p_mcb, p_port->dlci,
267                              p_port->rfc.p_mcb->peer_l2cap_mtu);
268       }
269       return;
270 
271     case RFC_EVENT_OPEN:
272     case RFC_EVENT_CLOSE:
273       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
274                          event);
275       return;
276 
277     case RFC_EVENT_CLEAR:
278       btm_sec_abort_access_req(p_port->rfc.p_mcb->bd_addr);
279       rfc_port_closed(p_port);
280       return;
281 
282     case RFC_EVENT_DATA:
283       RFCOMM_TRACE_ERROR("Port error state Term Wait Sec event Data");
284       osi_free(p_data);
285       return;
286 
287     case RFC_EVENT_SABME:
288       /* Ignore SABME retransmission if client dares to do so */
289       return;
290 
291     case RFC_EVENT_DISC:
292       btm_sec_abort_access_req(p_port->rfc.p_mcb->bd_addr);
293       p_port->rfc.state = RFC_STATE_CLOSED;
294       rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
295 
296       PORT_DlcReleaseInd(p_port->rfc.p_mcb, p_port->dlci);
297       return;
298 
299     case RFC_EVENT_UIH:
300       osi_free(p_data);
301       return;
302 
303     case RFC_EVENT_ESTABLISH_RSP:
304       if (*((uint8_t*)p_data) != RFCOMM_SUCCESS) {
305         if (p_port->rfc.p_mcb)
306           rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, true);
307       } else {
308         rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
309         p_port->rfc.state = RFC_STATE_OPENED;
310       }
311       return;
312   }
313   RFCOMM_TRACE_WARNING("Port state term_wait_sec_check Event ignored %d",
314                        event);
315 }
316 
317 /*******************************************************************************
318  *
319  * Function         rfc_port_sm_orig_wait_sec_check
320  *
321  * Description      This function handles events for the port in the
322  *                  ORIG_WAIT_SEC_CHECK state.  RFCOMM is waiting for Security
323  *                  manager to finish before sending SABME to the peer
324  *
325  * Returns          void
326  *
327  ******************************************************************************/
rfc_port_sm_orig_wait_sec_check(tPORT * p_port,uint16_t event,void * p_data)328 void rfc_port_sm_orig_wait_sec_check(tPORT* p_port, uint16_t event,
329                                      void* p_data) {
330   switch (event) {
331     case RFC_EVENT_SEC_COMPLETE:
332       if (*((uint8_t*)p_data) != BTM_SUCCESS) {
333         p_port->rfc.p_mcb->is_disc_initiator = true;
334         PORT_DlcEstablishCnf(p_port->rfc.p_mcb, p_port->dlci, 0,
335                              RFCOMM_SECURITY_ERR);
336         rfc_port_closed(p_port);
337         return;
338       }
339       rfc_send_sabme(p_port->rfc.p_mcb, p_port->dlci);
340       rfc_port_timer_start(p_port, RFC_PORT_T1_TIMEOUT);
341       p_port->rfc.state = RFC_STATE_SABME_WAIT_UA;
342       return;
343 
344     case RFC_EVENT_OPEN:
345     case RFC_EVENT_SABME: /* Peer should not use the same dlci */
346       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
347                          event);
348       return;
349 
350     case RFC_EVENT_CLOSE:
351       btm_sec_abort_access_req(p_port->rfc.p_mcb->bd_addr);
352       rfc_port_closed(p_port);
353       return;
354 
355     case RFC_EVENT_DATA:
356       RFCOMM_TRACE_ERROR("Port error state Orig Wait Sec event Data");
357       osi_free(p_data);
358       return;
359 
360     case RFC_EVENT_UIH:
361       osi_free(p_data);
362       return;
363   }
364   RFCOMM_TRACE_WARNING("Port state orig_wait_sec_check Event ignored %d",
365                        event);
366 }
367 
368 /*******************************************************************************
369  *
370  * Function         rfc_port_sm_opened
371  *
372  * Description      This function handles events for the port in the OPENED
373  *                  state
374  *
375  * Returns          void
376  *
377  ******************************************************************************/
rfc_port_sm_opened(tPORT * p_port,uint16_t event,void * p_data)378 void rfc_port_sm_opened(tPORT* p_port, uint16_t event, void* p_data) {
379   switch (event) {
380     case RFC_EVENT_OPEN:
381       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
382                          event);
383       return;
384 
385     case RFC_EVENT_CLOSE:
386       rfc_port_timer_start(p_port, RFC_DISC_TIMEOUT);
387       rfc_send_disc(p_port->rfc.p_mcb, p_port->dlci);
388       p_port->rfc.expected_rsp = 0;
389       p_port->rfc.state = RFC_STATE_DISC_WAIT_UA;
390       return;
391 
392     case RFC_EVENT_CLEAR:
393       rfc_port_closed(p_port);
394       return;
395 
396     case RFC_EVENT_DATA:
397       /* Send credits in the frame.  Pass them in the layer specific member of
398        * the hdr. */
399       /* There might be an initial case when we reduced rx_max and credit_rx is
400        * still */
401       /* bigger.  Make sure that we do not send 255 */
402       if ((p_port->rfc.p_mcb->flow == PORT_FC_CREDIT) &&
403           (((BT_HDR*)p_data)->len < p_port->peer_mtu) &&
404           (!p_port->rx.user_fc) &&
405           (p_port->credit_rx_max > p_port->credit_rx)) {
406         ((BT_HDR*)p_data)->layer_specific =
407             (uint8_t)(p_port->credit_rx_max - p_port->credit_rx);
408         p_port->credit_rx = p_port->credit_rx_max;
409       } else {
410         ((BT_HDR*)p_data)->layer_specific = 0;
411       }
412       rfc_send_buf_uih(p_port->rfc.p_mcb, p_port->dlci, (BT_HDR*)p_data);
413       rfc_dec_credit(p_port);
414       return;
415 
416     case RFC_EVENT_UA:
417       return;
418 
419     case RFC_EVENT_SABME:
420       rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
421       return;
422 
423     case RFC_EVENT_DM:
424       PORT_DlcReleaseInd(p_port->rfc.p_mcb, p_port->dlci);
425       rfc_port_closed(p_port);
426       return;
427 
428     case RFC_EVENT_DISC:
429       p_port->rfc.state = RFC_STATE_CLOSED;
430       rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
431       if (!fixed_queue_is_empty(p_port->rx.queue)) {
432         /* give a chance to upper stack to close port properly */
433         RFCOMM_TRACE_DEBUG("port queue is not empty");
434         rfc_port_timer_start(p_port, RFC_DISC_TIMEOUT);
435       } else
436         PORT_DlcReleaseInd(p_port->rfc.p_mcb, p_port->dlci);
437       return;
438 
439     case RFC_EVENT_UIH:
440       rfc_port_uplink_data(p_port, (BT_HDR*)p_data);
441       return;
442 
443     case RFC_EVENT_TIMEOUT:
444       Port_TimeOutCloseMux(p_port->rfc.p_mcb);
445       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
446                          event);
447       return;
448   }
449   RFCOMM_TRACE_WARNING("Port state opened Event ignored %d", event);
450 }
451 
452 /*******************************************************************************
453  *
454  * Function         rfc_port_sm_disc_wait_ua
455  *
456  * Description      This function handles events when DISC on the DLC was
457  *                  sent and SM is waiting for UA or DM.
458  *
459  * Returns          void
460  *
461  ******************************************************************************/
rfc_port_sm_disc_wait_ua(tPORT * p_port,uint16_t event,void * p_data)462 void rfc_port_sm_disc_wait_ua(tPORT* p_port, uint16_t event, void* p_data) {
463   switch (event) {
464     case RFC_EVENT_OPEN:
465     case RFC_EVENT_ESTABLISH_RSP:
466       RFCOMM_TRACE_ERROR("Port error state %d event %d", p_port->rfc.state,
467                          event);
468       return;
469 
470     case RFC_EVENT_CLEAR:
471       rfc_port_closed(p_port);
472       return;
473 
474     case RFC_EVENT_DATA:
475       osi_free(p_data);
476       return;
477 
478     case RFC_EVENT_UA:
479       p_port->rfc.p_mcb->is_disc_initiator = true;
480     /* Case falls through */
481 
482     case RFC_EVENT_DM:
483       rfc_port_closed(p_port);
484       return;
485 
486     case RFC_EVENT_SABME:
487       rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, true);
488       return;
489 
490     case RFC_EVENT_DISC:
491       rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, true);
492       return;
493 
494     case RFC_EVENT_UIH:
495       osi_free(p_data);
496       rfc_send_dm(p_port->rfc.p_mcb, p_port->dlci, false);
497       return;
498 
499     case RFC_EVENT_TIMEOUT:
500       rfc_port_closed(p_port);
501       return;
502   }
503 
504   RFCOMM_TRACE_WARNING("Port state disc_wait_ua Event ignored %d", event);
505 }
506 
507 /*******************************************************************************
508  *
509  * Function         rfc_port_uplink_data
510  *
511  * Description      This function handles uplink information data frame.
512  *
513  ******************************************************************************/
rfc_port_uplink_data(tPORT * p_port,BT_HDR * p_buf)514 void rfc_port_uplink_data(tPORT* p_port, BT_HDR* p_buf) {
515   PORT_DataInd(p_port->rfc.p_mcb, p_port->dlci, p_buf);
516 }
517 
518 /*******************************************************************************
519  *
520  * Function         rfc_process_pn
521  *
522  * Description      This function handles DLC parameter negotiation frame.
523  *                  Record MTU and pass indication to the upper layer.
524  *
525  ******************************************************************************/
rfc_process_pn(tRFC_MCB * p_mcb,bool is_command,MX_FRAME * p_frame)526 void rfc_process_pn(tRFC_MCB* p_mcb, bool is_command, MX_FRAME* p_frame) {
527   tPORT* p_port;
528   uint8_t dlci = p_frame->dlci;
529 
530   if (is_command) {
531     /* Ignore if Multiplexer is being shut down */
532     if (p_mcb->state != RFC_MX_STATE_DISC_WAIT_UA) {
533       PORT_ParNegInd(p_mcb, dlci, p_frame->u.pn.mtu, p_frame->u.pn.conv_layer,
534                      p_frame->u.pn.k);
535     } else {
536       rfc_send_dm(p_mcb, dlci, false);
537       RFCOMM_TRACE_WARNING("***** MX PN while disconnecting *****");
538     }
539 
540     return;
541   }
542   /* If we are not awaiting response just ignore it */
543   p_port = port_find_mcb_dlci_port(p_mcb, dlci);
544   if ((p_port == NULL) || !(p_port->rfc.expected_rsp & RFC_RSP_PN)) return;
545 
546   p_port->rfc.expected_rsp &= ~RFC_RSP_PN;
547 
548   rfc_port_timer_stop(p_port);
549 
550   PORT_ParNegCnf(p_mcb, dlci, p_frame->u.pn.mtu, p_frame->u.pn.conv_layer,
551                  p_frame->u.pn.k);
552 }
553 
554 /*******************************************************************************
555  *
556  * Function         rfc_process_rpn
557  *
558  * Description      This function handles Remote DLC parameter negotiation
559  *                  command/response.  Pass command to the user.
560  *
561  ******************************************************************************/
rfc_process_rpn(tRFC_MCB * p_mcb,bool is_command,bool is_request,MX_FRAME * p_frame)562 void rfc_process_rpn(tRFC_MCB* p_mcb, bool is_command, bool is_request,
563                      MX_FRAME* p_frame) {
564   tPORT_STATE port_pars;
565   tPORT* p_port;
566 
567   p_port = port_find_mcb_dlci_port(p_mcb, p_frame->dlci);
568   if (p_port == NULL) {
569     /* This is the first command on the port */
570     if (is_command) {
571       memset(&port_pars, 0, sizeof(tPORT_STATE));
572       rfc_set_port_state(&port_pars, p_frame);
573 
574       PORT_PortNegInd(p_mcb, p_frame->dlci, &port_pars,
575                       p_frame->u.rpn.param_mask);
576     }
577     return;
578   }
579 
580   if (is_command && is_request) {
581     /* This is the special situation when peer just request local pars */
582     port_pars = p_port->peer_port_pars;
583     rfc_send_rpn(p_mcb, p_frame->dlci, false, &p_port->peer_port_pars, 0);
584     return;
585   }
586 
587   port_pars = p_port->peer_port_pars;
588 
589   rfc_set_port_state(&port_pars, p_frame);
590 
591   if (is_command) {
592     PORT_PortNegInd(p_mcb, p_frame->dlci, &port_pars,
593                     p_frame->u.rpn.param_mask);
594     return;
595   }
596 
597   /* If we are not awaiting response just ignore it */
598   p_port = port_find_mcb_dlci_port(p_mcb, p_frame->dlci);
599   if ((p_port == NULL) ||
600       !(p_port->rfc.expected_rsp & (RFC_RSP_RPN | RFC_RSP_RPN_REPLY)))
601     return;
602 
603   /* If we sent a request for port parameters to the peer he is replying with */
604   /* mask 0. */
605   rfc_port_timer_stop(p_port);
606 
607   if (p_port->rfc.expected_rsp & RFC_RSP_RPN_REPLY) {
608     p_port->rfc.expected_rsp &= ~RFC_RSP_RPN_REPLY;
609 
610     p_port->peer_port_pars = port_pars;
611 
612     if ((port_pars.fc_type ==
613          (RFCOMM_FC_RTR_ON_INPUT | RFCOMM_FC_RTR_ON_OUTPUT)) ||
614         (port_pars.fc_type ==
615          (RFCOMM_FC_RTC_ON_INPUT | RFCOMM_FC_RTC_ON_OUTPUT))) {
616       /* This is satisfactory port parameters.  Set mask as it was Ok */
617       p_frame->u.rpn.param_mask = RFCOMM_RPN_PM_MASK;
618     } else {
619       /* Current peer parameters are not good, try to fix them */
620       p_port->peer_port_pars.fc_type =
621           (RFCOMM_FC_RTR_ON_INPUT | RFCOMM_FC_RTR_ON_OUTPUT);
622 
623       p_port->rfc.expected_rsp |= RFC_RSP_RPN;
624       rfc_send_rpn(p_mcb, p_frame->dlci, true, &p_port->peer_port_pars,
625                    RFCOMM_RPN_PM_RTR_ON_INPUT | RFCOMM_RPN_PM_RTR_ON_OUTPUT);
626       rfc_port_timer_start(p_port, RFC_T2_TIMEOUT);
627       return;
628     }
629   } else
630     p_port->rfc.expected_rsp &= ~RFC_RSP_RPN;
631 
632   /* Check if all suggested parameters were accepted */
633   if (((p_frame->u.rpn.param_mask &
634         (RFCOMM_RPN_PM_RTR_ON_INPUT | RFCOMM_RPN_PM_RTR_ON_OUTPUT)) ==
635        (RFCOMM_RPN_PM_RTR_ON_INPUT | RFCOMM_RPN_PM_RTR_ON_OUTPUT)) ||
636       ((p_frame->u.rpn.param_mask &
637         (RFCOMM_RPN_PM_RTC_ON_INPUT | RFCOMM_RPN_PM_RTC_ON_OUTPUT)) ==
638        (RFCOMM_RPN_PM_RTC_ON_INPUT | RFCOMM_RPN_PM_RTC_ON_OUTPUT))) {
639     PORT_PortNegCnf(p_mcb, p_port->dlci, &port_pars, RFCOMM_SUCCESS);
640     return;
641   }
642 
643   /* If we were proposing RTR flow control try RTC flow control */
644   /* If we were proposing RTC flow control try no flow control */
645   /* otherwise drop the connection */
646   if (p_port->peer_port_pars.fc_type ==
647       (RFCOMM_FC_RTR_ON_INPUT | RFCOMM_FC_RTR_ON_OUTPUT)) {
648     /* Current peer parameters are not good, try to fix them */
649     p_port->peer_port_pars.fc_type =
650         (RFCOMM_FC_RTC_ON_INPUT | RFCOMM_FC_RTC_ON_OUTPUT);
651 
652     p_port->rfc.expected_rsp |= RFC_RSP_RPN;
653 
654     rfc_send_rpn(p_mcb, p_frame->dlci, true, &p_port->peer_port_pars,
655                  RFCOMM_RPN_PM_RTC_ON_INPUT | RFCOMM_RPN_PM_RTC_ON_OUTPUT);
656     rfc_port_timer_start(p_port, RFC_T2_TIMEOUT);
657     return;
658   }
659 
660   /* Other side does not support flow control */
661   if (p_port->peer_port_pars.fc_type ==
662       (RFCOMM_FC_RTC_ON_INPUT | RFCOMM_FC_RTC_ON_OUTPUT)) {
663     p_port->peer_port_pars.fc_type = RFCOMM_FC_OFF;
664     PORT_PortNegCnf(p_mcb, p_port->dlci, &port_pars, RFCOMM_SUCCESS);
665   }
666 }
667 
668 /*******************************************************************************
669  *
670  * Function         rfc_process_msc
671  *
672  * Description      This function handles Modem Status Command.
673  *                  Pass command to the user.
674  *
675  ******************************************************************************/
rfc_process_msc(tRFC_MCB * p_mcb,bool is_command,MX_FRAME * p_frame)676 void rfc_process_msc(tRFC_MCB* p_mcb, bool is_command, MX_FRAME* p_frame) {
677   tPORT_CTRL pars;
678   tPORT* p_port;
679   uint8_t modem_signals = p_frame->u.msc.signals;
680   bool new_peer_fc = false;
681 
682   p_port = port_find_mcb_dlci_port(p_mcb, p_frame->dlci);
683   if (p_port == NULL) return;
684 
685   pars.modem_signal = 0;
686 
687   if (modem_signals & RFCOMM_MSC_RTC) pars.modem_signal |= MODEM_SIGNAL_DTRDSR;
688 
689   if (modem_signals & RFCOMM_MSC_RTR) pars.modem_signal |= MODEM_SIGNAL_RTSCTS;
690 
691   if (modem_signals & RFCOMM_MSC_IC) pars.modem_signal |= MODEM_SIGNAL_RI;
692 
693   if (modem_signals & RFCOMM_MSC_DV) pars.modem_signal |= MODEM_SIGNAL_DCD;
694 
695   pars.fc = ((modem_signals & RFCOMM_MSC_FC) == RFCOMM_MSC_FC);
696 
697   pars.break_signal =
698       (p_frame->u.msc.break_present) ? p_frame->u.msc.break_duration : 0;
699   pars.discard_buffers = 0;
700   pars.break_signal_seq = RFCOMM_CTRL_BREAK_IN_SEQ; /* this is default */
701 
702   /* Check if this command is passed only to indicate flow control */
703   if (is_command) {
704     rfc_send_msc(p_mcb, p_frame->dlci, false, &pars);
705 
706     if (p_port->rfc.p_mcb->flow != PORT_FC_CREDIT) {
707       /* Spec 1.1 indicates that only FC bit is used for flow control */
708       p_port->peer_ctrl.fc = new_peer_fc = pars.fc;
709 
710       if (new_peer_fc != p_port->tx.peer_fc)
711         PORT_FlowInd(p_mcb, p_frame->dlci, (bool)!new_peer_fc);
712     }
713 
714     PORT_ControlInd(p_mcb, p_frame->dlci, &pars);
715 
716     return;
717   }
718 
719   /* If we are not awaiting response just ignore it */
720   if (!(p_port->rfc.expected_rsp & RFC_RSP_MSC)) return;
721 
722   p_port->rfc.expected_rsp &= ~RFC_RSP_MSC;
723 
724   rfc_port_timer_stop(p_port);
725 
726   PORT_ControlCnf(p_port->rfc.p_mcb, p_port->dlci, &pars);
727 }
728 
729 /*******************************************************************************
730  *
731  * Function         rfc_process_rls
732  *
733  * Description      This function handles Remote Line Status command.
734  *                  Pass command to the user.
735  *
736  ******************************************************************************/
rfc_process_rls(tRFC_MCB * p_mcb,bool is_command,MX_FRAME * p_frame)737 void rfc_process_rls(tRFC_MCB* p_mcb, bool is_command, MX_FRAME* p_frame) {
738   tPORT* p_port;
739 
740   if (is_command) {
741     PORT_LineStatusInd(p_mcb, p_frame->dlci, p_frame->u.rls.line_status);
742     rfc_send_rls(p_mcb, p_frame->dlci, false, p_frame->u.rls.line_status);
743   } else {
744     p_port = port_find_mcb_dlci_port(p_mcb, p_frame->dlci);
745 
746     /* If we are not awaiting response just ignore it */
747     if (!p_port || !(p_port->rfc.expected_rsp & RFC_RSP_RLS)) return;
748 
749     p_port->rfc.expected_rsp &= ~RFC_RSP_RLS;
750 
751     rfc_port_timer_stop(p_port);
752   }
753 }
754 
755 /*******************************************************************************
756  *
757  * Function         rfc_process_nsc
758  *
759  * Description      This function handles None Supported Command frame.
760  *
761  ******************************************************************************/
rfc_process_nsc(UNUSED_ATTR tRFC_MCB * p_mcb,UNUSED_ATTR MX_FRAME * p_frame)762 void rfc_process_nsc(UNUSED_ATTR tRFC_MCB* p_mcb,
763                      UNUSED_ATTR MX_FRAME* p_frame) {}
764 
765 /*******************************************************************************
766  *
767  * Function         rfc_process_test
768  *
769  * Description      This function handles Test frame.  If this is a command
770  *                  reply to it.  Otherwise pass response to the user.
771  *
772  ******************************************************************************/
rfc_process_test_rsp(UNUSED_ATTR tRFC_MCB * p_mcb,BT_HDR * p_buf)773 void rfc_process_test_rsp(UNUSED_ATTR tRFC_MCB* p_mcb, BT_HDR* p_buf) {
774   osi_free(p_buf);
775 }
776 
777 /*******************************************************************************
778  *
779  * Function         rfc_process_fcon
780  *
781  * Description      This function handles FCON frame.  The peer entity is able
782  *                  to receive new information
783  *
784  ******************************************************************************/
rfc_process_fcon(tRFC_MCB * p_mcb,bool is_command)785 void rfc_process_fcon(tRFC_MCB* p_mcb, bool is_command) {
786   if (is_command) {
787     rfc_cb.rfc.peer_rx_disabled = false;
788 
789     rfc_send_fcon(p_mcb, false);
790 
791     if (!p_mcb->l2cap_congested) PORT_FlowInd(p_mcb, 0, true);
792   }
793 }
794 
795 /*******************************************************************************
796  *
797  * Function         rfc_process_fcoff
798  *
799  * Description      This function handles FCOFF frame.  The peer entity is
800  *                  unable to receive new information
801  *
802  ******************************************************************************/
rfc_process_fcoff(tRFC_MCB * p_mcb,bool is_command)803 void rfc_process_fcoff(tRFC_MCB* p_mcb, bool is_command) {
804   if (is_command) {
805     rfc_cb.rfc.peer_rx_disabled = true;
806 
807     if (!p_mcb->l2cap_congested) PORT_FlowInd(p_mcb, 0, false);
808 
809     rfc_send_fcoff(p_mcb, false);
810   }
811 }
812 
813 /*******************************************************************************
814  *
815  * Function         rfc_process_l2cap_congestion
816  *
817  * Description      This function handles L2CAP congestion messages
818  *
819  ******************************************************************************/
rfc_process_l2cap_congestion(tRFC_MCB * p_mcb,bool is_congested)820 void rfc_process_l2cap_congestion(tRFC_MCB* p_mcb, bool is_congested) {
821   p_mcb->l2cap_congested = is_congested;
822 
823   if (!is_congested) {
824     rfc_check_send_cmd(p_mcb, NULL);
825   }
826 
827   if (!rfc_cb.rfc.peer_rx_disabled) {
828     if (!is_congested)
829       PORT_FlowInd(p_mcb, 0, true);
830     else
831       PORT_FlowInd(p_mcb, 0, false);
832   }
833 }
834 
835 /*******************************************************************************
836  *
837  * Function         rfc_set_port_pars
838  *
839  * Description      This function sets the tPORT_STATE structure given a
840  *                  p_frame.
841  *
842  ******************************************************************************/
843 
rfc_set_port_state(tPORT_STATE * port_pars,MX_FRAME * p_frame)844 void rfc_set_port_state(tPORT_STATE* port_pars, MX_FRAME* p_frame) {
845   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_BIT_RATE)
846     port_pars->baud_rate = p_frame->u.rpn.baud_rate;
847   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_DATA_BITS)
848     port_pars->byte_size = p_frame->u.rpn.byte_size;
849   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_STOP_BITS)
850     port_pars->stop_bits = p_frame->u.rpn.stop_bits;
851   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_PARITY)
852     port_pars->parity = p_frame->u.rpn.parity;
853   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_PARITY_TYPE)
854     port_pars->parity_type = p_frame->u.rpn.parity_type;
855   if (p_frame->u.rpn.param_mask &
856       (RFCOMM_RPN_PM_XONXOFF_ON_INPUT | RFCOMM_RPN_PM_XONXOFF_ON_OUTPUT |
857        RFCOMM_RPN_PM_RTR_ON_INPUT | RFCOMM_RPN_PM_RTR_ON_OUTPUT |
858        RFCOMM_RPN_PM_RTC_ON_INPUT | RFCOMM_RPN_PM_RTC_ON_OUTPUT))
859     port_pars->fc_type = p_frame->u.rpn.fc_type;
860   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_XON_CHAR)
861     port_pars->xon_char = p_frame->u.rpn.xon_char;
862   if (p_frame->u.rpn.param_mask & RFCOMM_RPN_PM_XOFF_CHAR)
863     port_pars->xoff_char = p_frame->u.rpn.xoff_char;
864 }
865