18c2ecf20Sopenharmony_ci/*
28c2ecf20Sopenharmony_ci * Copyright (c) 2010-2011 Atheros Communications Inc.
38c2ecf20Sopenharmony_ci *
48c2ecf20Sopenharmony_ci * Permission to use, copy, modify, and/or distribute this software for any
58c2ecf20Sopenharmony_ci * purpose with or without fee is hereby granted, provided that the above
68c2ecf20Sopenharmony_ci * copyright notice and this permission notice appear in all copies.
78c2ecf20Sopenharmony_ci *
88c2ecf20Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
98c2ecf20Sopenharmony_ci * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
108c2ecf20Sopenharmony_ci * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
118c2ecf20Sopenharmony_ci * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
128c2ecf20Sopenharmony_ci * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
138c2ecf20Sopenharmony_ci * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
148c2ecf20Sopenharmony_ci * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
158c2ecf20Sopenharmony_ci */
168c2ecf20Sopenharmony_ci
178c2ecf20Sopenharmony_ci#ifndef MCI_H
188c2ecf20Sopenharmony_ci#define MCI_H
198c2ecf20Sopenharmony_ci
208c2ecf20Sopenharmony_ci#include "ar9003_mci.h"
218c2ecf20Sopenharmony_ci
228c2ecf20Sopenharmony_ci#define ATH_MCI_SCHED_BUF_SIZE		(16 * 16) /* 16 entries, 4 dword each */
238c2ecf20Sopenharmony_ci#define ATH_MCI_GPM_MAX_ENTRY		16
248c2ecf20Sopenharmony_ci#define ATH_MCI_GPM_BUF_SIZE		(ATH_MCI_GPM_MAX_ENTRY * 16)
258c2ecf20Sopenharmony_ci#define ATH_MCI_DEF_BT_PERIOD		40
268c2ecf20Sopenharmony_ci#define ATH_MCI_BDR_DUTY_CYCLE		20
278c2ecf20Sopenharmony_ci#define ATH_MCI_MAX_DUTY_CYCLE		90
288c2ecf20Sopenharmony_ci
298c2ecf20Sopenharmony_ci#define ATH_MCI_DEF_AGGR_LIMIT		6 /* in 0.24 ms */
308c2ecf20Sopenharmony_ci#define ATH_MCI_MAX_ACL_PROFILE		7
318c2ecf20Sopenharmony_ci#define ATH_MCI_MAX_SCO_PROFILE		1
328c2ecf20Sopenharmony_ci#define ATH_MCI_MAX_PROFILE		(ATH_MCI_MAX_ACL_PROFILE +\
338c2ecf20Sopenharmony_ci					 ATH_MCI_MAX_SCO_PROFILE)
348c2ecf20Sopenharmony_ci
358c2ecf20Sopenharmony_ci#define ATH_MCI_INQUIRY_PRIO         62
368c2ecf20Sopenharmony_ci#define ATH_MCI_HI_PRIO              60
378c2ecf20Sopenharmony_ci#define ATH_MCI_NUM_BT_CHANNELS      79
388c2ecf20Sopenharmony_ci#define ATH_MCI_CONCUR_TX_SWITCH      5
398c2ecf20Sopenharmony_ci
408c2ecf20Sopenharmony_ci#define MCI_GPM_SET_CHANNEL_BIT(_p_gpm, _bt_chan)			  \
418c2ecf20Sopenharmony_ci	do {								  \
428c2ecf20Sopenharmony_ci		if (_bt_chan < ATH_MCI_NUM_BT_CHANNELS) {		  \
438c2ecf20Sopenharmony_ci			*(((u8 *)(_p_gpm)) + MCI_GPM_COEX_B_CHANNEL_MAP + \
448c2ecf20Sopenharmony_ci				(_bt_chan / 8)) |= (1 << (_bt_chan & 7)); \
458c2ecf20Sopenharmony_ci		}							  \
468c2ecf20Sopenharmony_ci	} while (0)
478c2ecf20Sopenharmony_ci
488c2ecf20Sopenharmony_ci#define MCI_GPM_CLR_CHANNEL_BIT(_p_gpm, _bt_chan)			  \
498c2ecf20Sopenharmony_ci	do {								  \
508c2ecf20Sopenharmony_ci		if (_bt_chan < ATH_MCI_NUM_BT_CHANNELS) {		  \
518c2ecf20Sopenharmony_ci			*(((u8 *)(_p_gpm)) + MCI_GPM_COEX_B_CHANNEL_MAP + \
528c2ecf20Sopenharmony_ci				(_bt_chan / 8)) &= ~(1 << (_bt_chan & 7));\
538c2ecf20Sopenharmony_ci		}							  \
548c2ecf20Sopenharmony_ci	} while (0)
558c2ecf20Sopenharmony_ci
568c2ecf20Sopenharmony_ci#define INC_PROF(_mci, _info) do {		 \
578c2ecf20Sopenharmony_ci		switch (_info->type) {		 \
588c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_RFCOMM:\
598c2ecf20Sopenharmony_ci			_mci->num_other_acl++;	 \
608c2ecf20Sopenharmony_ci			break;			 \
618c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_A2DP:	 \
628c2ecf20Sopenharmony_ci			_mci->num_a2dp++;	 \
638c2ecf20Sopenharmony_ci			if (!_info->edr)	 \
648c2ecf20Sopenharmony_ci				_mci->num_bdr++; \
658c2ecf20Sopenharmony_ci			break;			 \
668c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_HID:	 \
678c2ecf20Sopenharmony_ci			_mci->num_hid++;	 \
688c2ecf20Sopenharmony_ci			break;			 \
698c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_BNEP:	 \
708c2ecf20Sopenharmony_ci			_mci->num_pan++;	 \
718c2ecf20Sopenharmony_ci			break;			 \
728c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_VOICE: \
738c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_A2DPVO:\
748c2ecf20Sopenharmony_ci			_mci->num_sco++;	 \
758c2ecf20Sopenharmony_ci			break;			 \
768c2ecf20Sopenharmony_ci		default:			 \
778c2ecf20Sopenharmony_ci			break;			 \
788c2ecf20Sopenharmony_ci		}				 \
798c2ecf20Sopenharmony_ci	} while (0)
808c2ecf20Sopenharmony_ci
818c2ecf20Sopenharmony_ci#define DEC_PROF(_mci, _info) do {		 \
828c2ecf20Sopenharmony_ci		switch (_info->type) {		 \
838c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_RFCOMM:\
848c2ecf20Sopenharmony_ci			_mci->num_other_acl--;	 \
858c2ecf20Sopenharmony_ci			break;			 \
868c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_A2DP:	 \
878c2ecf20Sopenharmony_ci			_mci->num_a2dp--;	 \
888c2ecf20Sopenharmony_ci			if (!_info->edr)	 \
898c2ecf20Sopenharmony_ci				_mci->num_bdr--; \
908c2ecf20Sopenharmony_ci			break;			 \
918c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_HID:	 \
928c2ecf20Sopenharmony_ci			_mci->num_hid--;	 \
938c2ecf20Sopenharmony_ci			break;			 \
948c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_BNEP:	 \
958c2ecf20Sopenharmony_ci			_mci->num_pan--;	 \
968c2ecf20Sopenharmony_ci			break;			 \
978c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_VOICE: \
988c2ecf20Sopenharmony_ci		case MCI_GPM_COEX_PROFILE_A2DPVO:\
998c2ecf20Sopenharmony_ci			_mci->num_sco--;	 \
1008c2ecf20Sopenharmony_ci			break;			 \
1018c2ecf20Sopenharmony_ci		default:			 \
1028c2ecf20Sopenharmony_ci			break;			 \
1038c2ecf20Sopenharmony_ci		}				 \
1048c2ecf20Sopenharmony_ci	} while (0)
1058c2ecf20Sopenharmony_ci
1068c2ecf20Sopenharmony_ci#define NUM_PROF(_mci)	(_mci->num_other_acl + _mci->num_a2dp + \
1078c2ecf20Sopenharmony_ci			 _mci->num_hid + _mci->num_pan + _mci->num_sco)
1088c2ecf20Sopenharmony_ci
1098c2ecf20Sopenharmony_cistruct ath_mci_profile_info {
1108c2ecf20Sopenharmony_ci	u8 type;
1118c2ecf20Sopenharmony_ci	u8 conn_handle;
1128c2ecf20Sopenharmony_ci	bool start;
1138c2ecf20Sopenharmony_ci	bool master;
1148c2ecf20Sopenharmony_ci	bool edr;
1158c2ecf20Sopenharmony_ci	u8 voice_type;
1168c2ecf20Sopenharmony_ci	u16 T;		/* Voice: Tvoice, HID: Tsniff,        in slots */
1178c2ecf20Sopenharmony_ci	u8 W;		/* Voice: Wvoice, HID: Sniff timeout, in slots */
1188c2ecf20Sopenharmony_ci	u8 A;		/*		  HID: Sniff attempt, in slots */
1198c2ecf20Sopenharmony_ci	struct list_head list;
1208c2ecf20Sopenharmony_ci};
1218c2ecf20Sopenharmony_ci
1228c2ecf20Sopenharmony_cistruct ath_mci_profile_status {
1238c2ecf20Sopenharmony_ci	bool is_critical;
1248c2ecf20Sopenharmony_ci	bool is_link;
1258c2ecf20Sopenharmony_ci	u8 conn_handle;
1268c2ecf20Sopenharmony_ci};
1278c2ecf20Sopenharmony_ci
1288c2ecf20Sopenharmony_cistruct ath_mci_profile {
1298c2ecf20Sopenharmony_ci	struct list_head info;
1308c2ecf20Sopenharmony_ci	DECLARE_BITMAP(status, ATH_MCI_MAX_PROFILE);
1318c2ecf20Sopenharmony_ci	u16 aggr_limit;
1328c2ecf20Sopenharmony_ci	u8 num_mgmt;
1338c2ecf20Sopenharmony_ci	u8 num_sco;
1348c2ecf20Sopenharmony_ci	u8 num_a2dp;
1358c2ecf20Sopenharmony_ci	u8 num_hid;
1368c2ecf20Sopenharmony_ci	u8 num_pan;
1378c2ecf20Sopenharmony_ci	u8 num_other_acl;
1388c2ecf20Sopenharmony_ci	u8 num_bdr;
1398c2ecf20Sopenharmony_ci	u8 voice_priority;
1408c2ecf20Sopenharmony_ci};
1418c2ecf20Sopenharmony_ci
1428c2ecf20Sopenharmony_cistruct ath_mci_buf {
1438c2ecf20Sopenharmony_ci	void *bf_addr;		/* virtual addr of desc */
1448c2ecf20Sopenharmony_ci	dma_addr_t bf_paddr;    /* physical addr of buffer */
1458c2ecf20Sopenharmony_ci	u32 bf_len;		/* len of data */
1468c2ecf20Sopenharmony_ci};
1478c2ecf20Sopenharmony_ci
1488c2ecf20Sopenharmony_cistruct ath_mci_coex {
1498c2ecf20Sopenharmony_ci	struct ath_mci_buf sched_buf;
1508c2ecf20Sopenharmony_ci	struct ath_mci_buf gpm_buf;
1518c2ecf20Sopenharmony_ci};
1528c2ecf20Sopenharmony_ci
1538c2ecf20Sopenharmony_civoid ath_mci_flush_profile(struct ath_mci_profile *mci);
1548c2ecf20Sopenharmony_ciint ath_mci_setup(struct ath_softc *sc);
1558c2ecf20Sopenharmony_civoid ath_mci_cleanup(struct ath_softc *sc);
1568c2ecf20Sopenharmony_civoid ath_mci_intr(struct ath_softc *sc);
1578c2ecf20Sopenharmony_civoid ath9k_mci_update_rssi(struct ath_softc *sc);
1588c2ecf20Sopenharmony_ci
1598c2ecf20Sopenharmony_ci#ifdef CONFIG_ATH9K_BTCOEX_SUPPORT
1608c2ecf20Sopenharmony_civoid ath_mci_enable(struct ath_softc *sc);
1618c2ecf20Sopenharmony_civoid ath9k_mci_update_wlan_channels(struct ath_softc *sc, bool allow_all);
1628c2ecf20Sopenharmony_civoid ath9k_mci_set_txpower(struct ath_softc *sc, bool setchannel,
1638c2ecf20Sopenharmony_ci			   bool concur_tx);
1648c2ecf20Sopenharmony_ci#else
1658c2ecf20Sopenharmony_cistatic inline void ath_mci_enable(struct ath_softc *sc)
1668c2ecf20Sopenharmony_ci{
1678c2ecf20Sopenharmony_ci}
1688c2ecf20Sopenharmony_cistatic inline void ath9k_mci_update_wlan_channels(struct ath_softc *sc,
1698c2ecf20Sopenharmony_ci						  bool allow_all)
1708c2ecf20Sopenharmony_ci{
1718c2ecf20Sopenharmony_ci}
1728c2ecf20Sopenharmony_cistatic inline void ath9k_mci_set_txpower(struct ath_softc *sc, bool setchannel,
1738c2ecf20Sopenharmony_ci					 bool concur_tx)
1748c2ecf20Sopenharmony_ci{
1758c2ecf20Sopenharmony_ci}
1768c2ecf20Sopenharmony_ci#endif /* CONFIG_ATH9K_BTCOEX_SUPPORT */
1778c2ecf20Sopenharmony_ci
1788c2ecf20Sopenharmony_ci#endif /* MCI_H*/
179