#endif
)
{
- bta_dm_pm_ssr(peer_addr);
+ if( ((NULL != (p = BTM_ReadLocalFeatures ())) && HCI_SNIFF_SUB_RATE_SUPPORTED(p)) &&
+ ((NULL != (p = BTM_ReadRemoteFeatures (peer_addr))) && HCI_SNIFF_SUB_RATE_SUPPORTED(p)))
+ {
+ /* If HID connection open is received and SCO is already active.
+ This will handle the case where HID connects when SCO already active */
+ if ((status == BTA_SYS_CONN_OPEN) && (id == BTA_ID_HH) && bta_dm_pm_is_sco_active())
+ {
+ APPL_TRACE_DEBUG("%s: SCO is Active, disabling SSR on HID link", __func__)
+ BTM_SetSsrParams(peer_addr, 0, 0, 0);
+ }
+ else
+ {
+ bta_dm_pm_ssr(peer_addr);
+ }
+ }
}
else
{
}
}
}
-#endif
-
- bta_dm_pm_set_mode(peer_addr, BTA_DM_PM_NO_ACTION, pm_req);
- /* perform the HID link workaround if needed
- ** 1. If SCO up/down event is received OR
- ** 2. If HID connection open is received and SCO is already active.
- ** This will handle the case where HID connects when SCO already active
- */
- if ( BTM_IsDeviceUp() &&
- ( ((status == BTA_SYS_SCO_OPEN) || (status == BTA_SYS_SCO_CLOSE)) ||
- ((status == BTA_SYS_CONN_OPEN) && (id == BTA_ID_HH) && bta_dm_pm_is_sco_active()) ) )
+ /* If SCO up/down event is received, then enable/disable SSR on active HID link */
+ if (status == BTA_SYS_SCO_OPEN || status == BTA_SYS_SCO_CLOSE)
{
- BOOLEAN bScoActive;
- if (status == BTA_SYS_CONN_OPEN)
- bScoActive = TRUE;
- else
- bScoActive = (status == BTA_SYS_SCO_OPEN);
+ const bool bScoActive = (status == BTA_SYS_SCO_OPEN);
+ APPL_TRACE_DEBUG("%s: bta_dm_pm_hid_check with bScoActive = %d", __func__, bScoActive);
bta_dm_pm_hid_check(bScoActive);
}
+#endif
+ bta_dm_pm_set_mode(peer_addr, BTA_DM_PM_NO_ACTION, pm_req);
}
{
if (bta_hh_read_ssr_param(peer_addr, &p_spec_cur->max_lat, &p_spec_cur->min_rmt_to) == BTA_HH_ERR)
continue;
+ if (p_spec_cur->max_lat == BTA_HH_SSR_MAX_LATENCY_ZERO)
+ {
+ APPL_TRACE_WARNING("%s: Max latency is 0, not sending"
+ "SSR command as device is blacklisted", __func__);
+ return;
+ }
+ else if (p_spec_cur->max_lat == BTA_HH_SSR_DISABLE_SSR)
+ {
+ APPL_TRACE_WARNING("%s: Need to disable SSR"
+ "as device is blacklisted", __func__);
+ BTM_SetSsrParams (peer_addr, 0, 0, 0);
+ return;
+ }
+ else if (p_spec_cur->max_lat > BTA_HH_SSR_MAX_LATENCY_OPTIMAL)
+ {
+ p_spec_cur->max_lat = BTA_HH_SSR_MAX_LATENCY_OPTIMAL;
+ }
+ else if (p_spec_cur->max_lat < BTA_HH_SSR_MAX_LATENCY_MIN_OPTIMAL)
+ {
+ p_spec_cur->max_lat = BTA_HH_SSR_MAX_LATENCY_MIN_OPTIMAL;
+ }
+ APPL_TRACE_DEBUG("%s: New Max Latency = %d", __func__, p_spec_cur->max_lat);
}
#endif
if (p_spec_cur->max_lat < p_spec->max_lat ||
**
** Function bta_dm_pm_hid_check
**
-** Description Disables/Enables sniff in link policy based on SCO Up/Down
+** Description Disables/Enables SSR based on SCO Up/Down
**
** Returns None
**
*******************************************************************************/
static void bta_dm_pm_hid_check(BOOLEAN bScoActive)
{
- int j;
+ BD_ADDR peer_bdaddr;
- /* if HID is active, disable the link policy */
- for(j=0; j<bta_dm_conn_srvcs.count ; j++)
+ for(int j=0; j<bta_dm_conn_srvcs.count ; j++)
{
/* check if an entry already present */
if(bta_dm_conn_srvcs.conn_srvc[j].id == BTA_ID_HH )
{
- APPL_TRACE_DEBUG ("SCO status change(Active: %d), modify HID link policy. state: %d",
- bScoActive, bta_dm_conn_srvcs.conn_srvc[j].state);
- bta_dm_pm_set_sniff_policy( bta_dm_find_peer_device(bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr), bScoActive);
-
- /* if we had disabled link policy, seems like the hid device stop retrying SNIFF after a few tries. force sniff if needed */
- if (!bScoActive)
- bta_dm_pm_set_mode(bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr, BTA_DM_PM_NO_ACTION,
- BTA_DM_PM_RESTART);
+ UINT8 *p = BTM_ReadLocalFeatures();
+ bdcpy(peer_bdaddr, bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr);
+
+ if((p != NULL && HCI_SNIFF_SUB_RATE_SUPPORTED(p))
+ &&((NULL != (p = BTM_ReadRemoteFeatures (peer_bdaddr)))
+ && HCI_SNIFF_SUB_RATE_SUPPORTED(p)))
+ {
+ if (bScoActive)
+ {
+ APPL_TRACE_DEBUG("%s: SCO_OPEN, disabling SSR", __func__);
+ BTM_SetSsrParams(peer_bdaddr, 0, 0, 0);
+ }
+ else
+ {
+ APPL_TRACE_DEBUG("%s: SCO_CLOSE, enabling SSR", __func__);
+ bta_dm_pm_ssr(peer_bdaddr);
+ }
+ }
}
}
BTA_HH_KB_GUI_MASK
};
+/* hid_blacklist_addr_prefix_for_ssr & hid_ssr_max_lat_list_for_iot are used
+ to fix IOP issues of sniff subrate feature */
+static const UINT8 hid_blacklist_addr_prefix_for_ssr[][3] = {
+ {0x00, 0x1B, 0xDC} // ISSC
+ ,{0xdc, 0x2c, 0x26} // BORND
+ ,{0x54, 0x46, 0x6B} // JW MT002
+};
+
+static const UINT16 hid_ssr_max_lat_list_for_iot[] = {
+ 0x0012 // ISSC
+ ,BTA_HH_SSR_MAX_LATENCY_ZERO // BORND
+ ,BTA_HH_SSR_DISABLE_SSR // JW MT002
+};
+
+
+/*******************************************************************************
+** Function blacklist_adjust_sniff_subrate
+**
+** Description It's used to update SSR parameter such as max latency,
+** if device is found in HID blacklist.
+**
+** Returns None
+*******************************************************************************/
+static void blacklist_adjust_sniff_subrate(BD_ADDR peer_dev, UINT16 *ssr_max_lat)
+{
+ UINT16 old_ssr_max_lat = *ssr_max_lat;
+ const int blacklist_size =
+ sizeof(hid_blacklist_addr_prefix_for_ssr)/sizeof(hid_blacklist_addr_prefix_for_ssr[0]);
+ for (int i = 0; i < blacklist_size; i++) {
+ if (hid_blacklist_addr_prefix_for_ssr[i][0] == peer_dev[0] &&
+ hid_blacklist_addr_prefix_for_ssr[i][1] == peer_dev[1] &&
+ hid_blacklist_addr_prefix_for_ssr[i][2] == peer_dev[2]) {
+ *ssr_max_lat = hid_ssr_max_lat_list_for_iot[i];
+ APPL_TRACE_WARNING("%s: Device in blacklist for ssr, max latency changed "
+ "from %d to %d", __func__, old_ssr_max_lat, *ssr_max_lat);
+ return;
+ }
+ }
+}
+
/*******************************************************************************
**
p_cb->app_id = app_id;
p_cb->dscp_info.ssr_max_latency = ssr_max_latency;
+ blacklist_adjust_sniff_subrate(p_cb->addr, &(p_cb->dscp_info.ssr_max_latency));
+
p_cb->dscp_info.ssr_min_tout = ssr_min_tout;
/* store report descriptor info */