mirror of
https://github.com/Telecominfraproject/wlan-ap.git
synced 2025-10-30 18:07:52 +00:00
Compare commits
13 Commits
v3.0.2-rc1
...
v3.0.2-rc2
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ca1eabfbd5 | ||
|
|
c22767540e | ||
|
|
dff6a6e3d8 | ||
|
|
a7c9a5f780 | ||
|
|
f8eca25f7e | ||
|
|
be59b10acc | ||
|
|
1ec29f6705 | ||
|
|
3ae0a1f1d5 | ||
|
|
f362b7139e | ||
|
|
bdd2074d78 | ||
|
|
98ef44fc34 | ||
|
|
9bb982460a | ||
|
|
22126a3410 |
@@ -0,0 +1,459 @@
|
||||
From 1c3438fec4bad13a676617915ff56af54e7b4542 Mon Sep 17 00:00:00 2001
|
||||
From: Jouni Malinen <j@w1.fi>
|
||||
Date: Sat, 2 Apr 2022 13:12:43 +0300
|
||||
Subject: [PATCH] RADIUS ACL/PSK check during 4-way handshake
|
||||
|
||||
Add an alternative sequence for performing the RADIUS ACL check and PSK
|
||||
fetch. The previously used (macaddr_acl=2, wpa_psk_radius=2) combination
|
||||
does this during IEEE 802.11 Authentication frame exchange while the new
|
||||
option (wpa_psk_radius=3) does this during the 4-way handshake. This
|
||||
allows some more information to be provided to the RADIUS authentication
|
||||
server.
|
||||
|
||||
Signed-off-by: Jouni Malinen <j@w1.fi>
|
||||
---
|
||||
hostapd/config_file.c | 3 +-
|
||||
hostapd/hostapd.conf | 5 ++-
|
||||
src/ap/ap_config.c | 4 ++-
|
||||
src/ap/ap_config.h | 5 +--
|
||||
src/ap/ieee802_11.c | 5 ++-
|
||||
src/ap/ieee802_11.h | 2 ++
|
||||
src/ap/ieee802_11_auth.c | 76 ++++++++++++++++++++++++++++++++++++----
|
||||
src/ap/ieee802_11_auth.h | 5 ++-
|
||||
src/ap/wpa_auth.c | 51 ++++++++++++++++++++++++++-
|
||||
src/ap/wpa_auth.h | 9 ++++-
|
||||
src/ap/wpa_auth_glue.c | 25 ++++++++++++-
|
||||
src/ap/wpa_auth_i.h | 1 +
|
||||
12 files changed, 172 insertions(+), 19 deletions(-)
|
||||
|
||||
--- a/hostapd/config_file.c
|
||||
+++ b/hostapd/config_file.c
|
||||
@@ -2858,7 +2858,8 @@ static int hostapd_config_fill(struct ho
|
||||
bss->wpa_psk_radius = atoi(pos);
|
||||
if (bss->wpa_psk_radius != PSK_RADIUS_IGNORED &&
|
||||
bss->wpa_psk_radius != PSK_RADIUS_ACCEPTED &&
|
||||
- bss->wpa_psk_radius != PSK_RADIUS_REQUIRED) {
|
||||
+ bss->wpa_psk_radius != PSK_RADIUS_REQUIRED &&
|
||||
+ bss->wpa_psk_radius != PSK_RADIUS_DURING_4WAY_HS) {
|
||||
wpa_printf(MSG_ERROR,
|
||||
"Line %d: unknown wpa_psk_radius %d",
|
||||
line, bss->wpa_psk_radius);
|
||||
--- a/hostapd/hostapd.conf
|
||||
+++ b/hostapd/hostapd.conf
|
||||
@@ -1635,12 +1635,15 @@ own_ip_addr=127.0.0.1
|
||||
#wpa_psk_file=/etc/hostapd.wpa_psk
|
||||
|
||||
# Optionally, WPA passphrase can be received from RADIUS authentication server
|
||||
-# This requires macaddr_acl to be set to 2 (RADIUS)
|
||||
+# This requires macaddr_acl to be set to 2 (RADIUS) for wpa_psk_radius values
|
||||
+# 1 and 2.
|
||||
# 0 = disabled (default)
|
||||
# 1 = optional; use default passphrase/psk if RADIUS server does not include
|
||||
# Tunnel-Password
|
||||
# 2 = required; reject authentication if RADIUS server does not include
|
||||
# Tunnel-Password
|
||||
+# 3 = ask RADIUS server during 4-way handshake if there is no locally
|
||||
+# configured PSK/passphrase for the STA
|
||||
#wpa_psk_radius=0
|
||||
|
||||
# Set of accepted key management algorithms (WPA-PSK, WPA-EAP, or both). The
|
||||
--- a/src/ap/ap_config.c
|
||||
+++ b/src/ap/ap_config.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd / Configuration helper functions
|
||||
- * Copyright (c) 2003-2014, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2003-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -1245,6 +1245,7 @@ static int hostapd_config_check_bss(stru
|
||||
|
||||
if (full_config && bss->wpa &&
|
||||
bss->wpa_psk_radius != PSK_RADIUS_IGNORED &&
|
||||
+ bss->wpa_psk_radius != PSK_RADIUS_DURING_4WAY_HS &&
|
||||
bss->macaddr_acl != USE_EXTERNAL_RADIUS_AUTH) {
|
||||
wpa_printf(MSG_ERROR, "WPA-PSK using RADIUS enabled, but no "
|
||||
"RADIUS checking (macaddr_acl=2) enabled.");
|
||||
@@ -1254,6 +1255,7 @@ static int hostapd_config_check_bss(stru
|
||||
if (full_config && bss->wpa && (bss->wpa_key_mgmt & WPA_KEY_MGMT_PSK) &&
|
||||
bss->ssid.wpa_psk == NULL && bss->ssid.wpa_passphrase == NULL &&
|
||||
bss->ssid.wpa_psk_file == NULL &&
|
||||
+ bss->wpa_psk_radius != PSK_RADIUS_DURING_4WAY_HS &&
|
||||
(bss->wpa_psk_radius != PSK_RADIUS_REQUIRED ||
|
||||
bss->macaddr_acl != USE_EXTERNAL_RADIUS_AUTH)) {
|
||||
wpa_printf(MSG_ERROR, "WPA-PSK enabled, but PSK or passphrase "
|
||||
--- a/src/ap/ap_config.h
|
||||
+++ b/src/ap/ap_config.h
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd / Configuration definitions and helpers functions
|
||||
- * Copyright (c) 2003-2015, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2003-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -367,7 +367,8 @@ struct hostapd_bss_config {
|
||||
enum {
|
||||
PSK_RADIUS_IGNORED = 0,
|
||||
PSK_RADIUS_ACCEPTED = 1,
|
||||
- PSK_RADIUS_REQUIRED = 2
|
||||
+ PSK_RADIUS_REQUIRED = 2,
|
||||
+ PSK_RADIUS_DURING_4WAY_HS = 3,
|
||||
} wpa_psk_radius;
|
||||
int wpa_pairwise;
|
||||
int group_cipher; /* wpa_group value override from configuation */
|
||||
--- a/src/ap/ieee802_11.c
|
||||
+++ b/src/ap/ieee802_11.c
|
||||
@@ -2348,9 +2348,8 @@ static int ieee802_11_allowed_address(st
|
||||
}
|
||||
|
||||
|
||||
-static int
|
||||
-ieee802_11_set_radius_info(struct hostapd_data *hapd, struct sta_info *sta,
|
||||
- int res, struct radius_sta *info)
|
||||
+int ieee802_11_set_radius_info(struct hostapd_data *hapd, struct sta_info *sta,
|
||||
+ int res, struct radius_sta *info)
|
||||
{
|
||||
u32 session_timeout = info->session_timeout;
|
||||
u32 acct_interim_interval = info->acct_interim_interval;
|
||||
--- a/src/ap/ieee802_11.h
|
||||
+++ b/src/ap/ieee802_11.h
|
||||
@@ -220,4 +220,6 @@ void auth_sae_process_commit(void *eloop
|
||||
u8 * hostapd_eid_rsnxe(struct hostapd_data *hapd, u8 *eid, size_t len);
|
||||
u8 * hostapd_get_rsne(struct hostapd_data *hapd, u8 *pos, size_t len);
|
||||
u8 * hostapd_get_rsnxe(struct hostapd_data *hapd, u8 *pos, size_t len);
|
||||
+int ieee802_11_set_radius_info(struct hostapd_data *hapd, struct sta_info *sta,
|
||||
+ int res, struct radius_sta *info);
|
||||
#endif /* IEEE802_11_H */
|
||||
--- a/src/ap/ieee802_11_auth.c
|
||||
+++ b/src/ap/ieee802_11_auth.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd / IEEE 802.11 authentication (ACL)
|
||||
- * Copyright (c) 2003-2012, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2003-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -20,6 +20,8 @@
|
||||
#include "hostapd.h"
|
||||
#include "ap_config.h"
|
||||
#include "ap_drv_ops.h"
|
||||
+#include "sta_info.h"
|
||||
+#include "wpa_auth.h"
|
||||
#include "ieee802_11.h"
|
||||
#include "ieee802_1x.h"
|
||||
#include "ieee802_11_auth.h"
|
||||
@@ -43,6 +45,8 @@ struct hostapd_acl_query_data {
|
||||
u8 *auth_msg; /* IEEE 802.11 authentication frame from station */
|
||||
size_t auth_msg_len;
|
||||
struct hostapd_acl_query_data *next;
|
||||
+ bool radius_psk;
|
||||
+ int akm;
|
||||
};
|
||||
|
||||
|
||||
@@ -153,6 +157,13 @@ static int hostapd_radius_acl_query(stru
|
||||
goto fail;
|
||||
}
|
||||
|
||||
+ if (query->akm &&
|
||||
+ !radius_msg_add_attr_int32(msg, RADIUS_ATTR_WLAN_AKM_SUITE,
|
||||
+ wpa_akm_to_suite(query->akm))) {
|
||||
+ wpa_printf(MSG_DEBUG, "Could not add WLAN-AKM-Suite");
|
||||
+ goto fail;
|
||||
+ }
|
||||
+
|
||||
if (radius_client_send(hapd->radius, msg, RADIUS_AUTH, addr) < 0)
|
||||
goto fail;
|
||||
return 0;
|
||||
@@ -566,17 +577,40 @@ hostapd_acl_recv_radius(struct radius_ms
|
||||
cache->next = hapd->acl_cache;
|
||||
hapd->acl_cache = cache;
|
||||
|
||||
+ if (query->radius_psk) {
|
||||
+ struct sta_info *sta;
|
||||
+ bool success = cache->accepted == HOSTAPD_ACL_ACCEPT;
|
||||
+
|
||||
+ sta = ap_get_sta(hapd, query->addr);
|
||||
+ if (!sta || !sta->wpa_sm) {
|
||||
+ wpa_printf(MSG_DEBUG,
|
||||
+ "No STA/SM entry found for the RADIUS PSK response");
|
||||
+ goto done;
|
||||
+ }
|
||||
+#ifdef NEED_AP_MLME
|
||||
+ if (success &&
|
||||
+ (ieee802_11_set_radius_info(hapd, sta, cache->accepted,
|
||||
+ info) < 0 ||
|
||||
+ ap_sta_bind_vlan(hapd, sta) < 0))
|
||||
+ success = false;
|
||||
+#endif /* NEED_AP_MLME */
|
||||
+ wpa_auth_sta_radius_psk_resp(sta->wpa_sm, success);
|
||||
+ } else {
|
||||
#ifdef CONFIG_DRIVER_RADIUS_ACL
|
||||
- hostapd_drv_set_radius_acl_auth(hapd, query->addr, cache->accepted,
|
||||
- info->session_timeout);
|
||||
+ hostapd_drv_set_radius_acl_auth(hapd, query->addr,
|
||||
+ cache->accepted,
|
||||
+ info->session_timeout);
|
||||
#else /* CONFIG_DRIVER_RADIUS_ACL */
|
||||
#ifdef NEED_AP_MLME
|
||||
- /* Re-send original authentication frame for 802.11 processing */
|
||||
- wpa_printf(MSG_DEBUG, "Re-sending authentication frame after "
|
||||
- "successful RADIUS ACL query");
|
||||
- ieee802_11_mgmt(hapd, query->auth_msg, query->auth_msg_len, NULL);
|
||||
+ /* Re-send original authentication frame for 802.11 processing
|
||||
+ */
|
||||
+ wpa_printf(MSG_DEBUG,
|
||||
+ "Re-sending authentication frame after successful RADIUS ACL query");
|
||||
+ ieee802_11_mgmt(hapd, query->auth_msg, query->auth_msg_len,
|
||||
+ NULL);
|
||||
#endif /* NEED_AP_MLME */
|
||||
#endif /* CONFIG_DRIVER_RADIUS_ACL */
|
||||
+ }
|
||||
|
||||
done:
|
||||
if (prev == NULL)
|
||||
@@ -658,3 +692,31 @@ void hostapd_free_psk_list(struct hostap
|
||||
os_free(prev);
|
||||
}
|
||||
}
|
||||
+
|
||||
+
|
||||
+#ifndef CONFIG_NO_RADIUS
|
||||
+void hostapd_acl_req_radius_psk(struct hostapd_data *hapd, const u8 *addr,
|
||||
+ int key_mgmt, const u8 *anonce,
|
||||
+ const u8 *eapol, size_t eapol_len)
|
||||
+{
|
||||
+ struct hostapd_acl_query_data *query;
|
||||
+
|
||||
+ query = os_zalloc(sizeof(*query));
|
||||
+ if (!query)
|
||||
+ return;
|
||||
+
|
||||
+ query->radius_psk = true;
|
||||
+ query->akm = key_mgmt;
|
||||
+ os_get_reltime(&query->timestamp);
|
||||
+ os_memcpy(query->addr, addr, ETH_ALEN);
|
||||
+ if (hostapd_radius_acl_query(hapd, addr, query)) {
|
||||
+ wpa_printf(MSG_DEBUG,
|
||||
+ "Failed to send Access-Request for RADIUS PSK/ACL query");
|
||||
+ hostapd_acl_query_free(query);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ query->next = hapd->acl_queries;
|
||||
+ hapd->acl_queries = query;
|
||||
+}
|
||||
+#endif /* CONFIG_NO_RADIUS */
|
||||
--- a/src/ap/ieee802_11_auth.h
|
||||
+++ b/src/ap/ieee802_11_auth.h
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd / IEEE 802.11 authentication (ACL)
|
||||
- * Copyright (c) 2003-2005, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2003-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -36,5 +36,8 @@ void hostapd_free_psk_list(struct hostap
|
||||
void hostapd_acl_expire(struct hostapd_data *hapd);
|
||||
void hostapd_copy_psk_list(struct hostapd_sta_wpa_psk_short **psk,
|
||||
struct hostapd_sta_wpa_psk_short *src);
|
||||
+void hostapd_acl_req_radius_psk(struct hostapd_data *hapd, const u8 *addr,
|
||||
+ int key_mgmt, const u8 *anonce,
|
||||
+ const u8 *eapol, size_t eapol_len);
|
||||
|
||||
#endif /* IEEE802_11_AUTH_H */
|
||||
--- a/src/ap/wpa_auth.c
|
||||
+++ b/src/ap/wpa_auth.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* IEEE 802.11 RSN / WPA Authenticator
|
||||
- * Copyright (c) 2004-2019, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2004-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -1465,6 +1465,12 @@ static void wpa_send_eapol_timeout(void
|
||||
struct wpa_authenticator *wpa_auth = eloop_ctx;
|
||||
struct wpa_state_machine *sm = timeout_ctx;
|
||||
|
||||
+ if (sm->waiting_radius_psk) {
|
||||
+ wpa_auth_logger(wpa_auth, sm->addr, LOGGER_DEBUG,
|
||||
+ "Ignore EAPOL-Key timeout while waiting for RADIUS PSK");
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
sm->pending_1_of_4_timeout = 0;
|
||||
wpa_auth_logger(wpa_auth, sm->addr, LOGGER_DEBUG, "EAPOL-Key timeout");
|
||||
sm->TimeoutEvt = true;
|
||||
@@ -3003,6 +3009,19 @@ SM_STATE(WPA_PTK, PTKCALCNEGOTIATING)
|
||||
break;
|
||||
}
|
||||
|
||||
+ if (!ok && wpa_key_mgmt_wpa_psk_no_sae(sm->wpa_key_mgmt) &&
|
||||
+ wpa_auth->conf.radius_psk && wpa_auth->cb->request_radius_psk &&
|
||||
+ !sm->waiting_radius_psk) {
|
||||
+ wpa_printf(MSG_DEBUG, "No PSK available - ask RADIUS server");
|
||||
+ wpa_auth->cb->request_radius_psk(wpa_auth->cb_ctx, sm->addr,
|
||||
+ sm->wpa_key_mgmt,
|
||||
+ sm->ANonce,
|
||||
+ sm->last_rx_eapol_key,
|
||||
+ sm->last_rx_eapol_key_len);
|
||||
+ sm->waiting_radius_psk = 1;
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
if (!ok) {
|
||||
wpa_auth_logger(sm->wpa_auth, sm->addr, LOGGER_DEBUG,
|
||||
"invalid MIC in msg 2/4 of 4-Way Handshake");
|
||||
@@ -3758,6 +3777,11 @@ SM_STEP(WPA_PTK)
|
||||
} else if (wpa_auth_uses_sae(sm) && sm->pmksa) {
|
||||
SM_ENTER(WPA_PTK, PTKSTART);
|
||||
#endif /* CONFIG_SAE */
|
||||
+ } else if (wpa_key_mgmt_wpa_psk_no_sae(sm->wpa_key_mgmt) &&
|
||||
+ wpa_auth->conf.radius_psk) {
|
||||
+ wpa_printf(MSG_DEBUG,
|
||||
+ "INITPSK: No PSK yet available for STA - use RADIUS later");
|
||||
+ SM_ENTER(WPA_PTK, PTKSTART);
|
||||
} else {
|
||||
wpa_auth_logger(wpa_auth, sm->addr, LOGGER_INFO,
|
||||
"no PSK configured for the STA");
|
||||
@@ -5661,3 +5685,28 @@ void wpa_auth_set_ocv_override_freq(stru
|
||||
}
|
||||
|
||||
#endif /* CONFIG_TESTING_OPTIONS */
|
||||
+
|
||||
+
|
||||
+void wpa_auth_sta_radius_psk_resp(struct wpa_state_machine *sm, bool success)
|
||||
+{
|
||||
+ if (!sm->waiting_radius_psk) {
|
||||
+ wpa_printf(MSG_DEBUG,
|
||||
+ "Ignore RADIUS PSK response for " MACSTR
|
||||
+ " that did not wait one",
|
||||
+ MAC2STR(sm->addr));
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ wpa_printf(MSG_DEBUG, "RADIUS PSK response for " MACSTR " (%s)",
|
||||
+ MAC2STR(sm->addr), success ? "success" : "fail");
|
||||
+ sm->waiting_radius_psk = 0;
|
||||
+
|
||||
+ if (success) {
|
||||
+ /* Try to process the EAPOL-Key msg 2/4 again */
|
||||
+ sm->EAPOLKeyReceived = true;
|
||||
+ } else {
|
||||
+ sm->Disconnect = true;
|
||||
+ }
|
||||
+
|
||||
+ eloop_register_timeout(0, 0, wpa_sm_call_step, sm, NULL);
|
||||
+}
|
||||
--- a/src/ap/wpa_auth.h
|
||||
+++ b/src/ap/wpa_auth.h
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd - IEEE 802.11i-2004 / WPA Authenticator
|
||||
- * Copyright (c) 2004-2017, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2004-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -273,6 +273,8 @@ struct wpa_auth_config {
|
||||
* PTK derivation regardless of advertised capabilities.
|
||||
*/
|
||||
bool force_kdk_derivation;
|
||||
+
|
||||
+ bool radius_psk;
|
||||
};
|
||||
|
||||
typedef enum {
|
||||
@@ -320,6 +322,9 @@ struct wpa_auth_callbacks {
|
||||
void (*store_ptksa)(void *ctx, const u8 *addr, int cipher,
|
||||
u32 life_time, const struct wpa_ptk *ptk);
|
||||
void (*clear_ptksa)(void *ctx, const u8 *addr, int cipher);
|
||||
+ void (*request_radius_psk)(void *ctx, const u8 *addr, int key_mgmt,
|
||||
+ const u8 *anonce,
|
||||
+ const u8 *eapol, size_t eapol_len);
|
||||
#ifdef CONFIG_IEEE80211R_AP
|
||||
struct wpa_state_machine * (*add_sta)(void *ctx, const u8 *sta_addr);
|
||||
int (*add_sta_ft)(void *ctx, const u8 *sta_addr);
|
||||
@@ -567,4 +572,6 @@ void wpa_auth_set_ocv_override_freq(stru
|
||||
enum wpa_auth_ocv_override_frame frame,
|
||||
unsigned int freq);
|
||||
|
||||
+void wpa_auth_sta_radius_psk_resp(struct wpa_state_machine *sm, bool success);
|
||||
+
|
||||
#endif /* WPA_AUTH_H */
|
||||
--- a/src/ap/wpa_auth_glue.c
|
||||
+++ b/src/ap/wpa_auth_glue.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* hostapd / WPA authenticator glue code
|
||||
- * Copyright (c) 2002-2012, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2002-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -29,6 +29,7 @@
|
||||
#include "ap_drv_ops.h"
|
||||
#include "ap_config.h"
|
||||
#include "ieee802_11.h"
|
||||
+#include "ieee802_11_auth.h"
|
||||
#include "pmksa_cache_auth.h"
|
||||
#include "wpa_auth.h"
|
||||
#include "wpa_auth_glue.h"
|
||||
@@ -214,6 +215,8 @@ static void hostapd_wpa_auth_conf(struct
|
||||
wconf->force_kdk_derivation = conf->force_kdk_derivation;
|
||||
#endif /* CONFIG_TESTING_OPTIONS */
|
||||
#endif /* CONFIG_PASN */
|
||||
+
|
||||
+ wconf->radius_psk = conf->wpa_psk_radius == PSK_RADIUS_DURING_4WAY_HS;
|
||||
}
|
||||
|
||||
|
||||
@@ -1435,6 +1438,23 @@ static void hostapd_wpa_unregister_ft_ou
|
||||
#endif /* CONFIG_IEEE80211R_AP */
|
||||
|
||||
|
||||
+#ifndef CONFIG_NO_RADIUS
|
||||
+static void hostapd_request_radius_psk(void *ctx, const u8 *addr, int key_mgmt,
|
||||
+ const u8 *anonce,
|
||||
+ const u8 *eapol, size_t eapol_len)
|
||||
+{
|
||||
+ struct hostapd_data *hapd = ctx;
|
||||
+
|
||||
+ wpa_printf(MSG_DEBUG, "RADIUS PSK request for " MACSTR " key_mgmt=0x%x",
|
||||
+ MAC2STR(addr), key_mgmt);
|
||||
+ wpa_hexdump(MSG_DEBUG, "ANonce", anonce, WPA_NONCE_LEN);
|
||||
+ wpa_hexdump(MSG_DEBUG, "EAPOL", eapol, eapol_len);
|
||||
+ hostapd_acl_req_radius_psk(hapd, addr, key_mgmt, anonce, eapol,
|
||||
+ eapol_len);
|
||||
+}
|
||||
+#endif /* CONFIG_NO_RADIUS */
|
||||
+
|
||||
+
|
||||
int hostapd_setup_wpa(struct hostapd_data *hapd)
|
||||
{
|
||||
struct wpa_auth_config _conf;
|
||||
@@ -1478,6 +1498,9 @@ int hostapd_setup_wpa(struct hostapd_dat
|
||||
.set_session_timeout = hostapd_wpa_auth_set_session_timeout,
|
||||
.get_session_timeout = hostapd_wpa_auth_get_session_timeout,
|
||||
#endif /* CONFIG_IEEE80211R_AP */
|
||||
+#ifndef CONFIG_NO_RADIUS
|
||||
+ .request_radius_psk = hostapd_request_radius_psk,
|
||||
+#endif /* CONFIG_NO_RADIUS */
|
||||
};
|
||||
const u8 *wpa_ie;
|
||||
size_t wpa_ie_len;
|
||||
--- a/src/ap/wpa_auth_i.h
|
||||
+++ b/src/ap/wpa_auth_i.h
|
||||
@@ -89,6 +89,7 @@ struct wpa_state_machine {
|
||||
unsigned int rx_eapol_key_secure:1;
|
||||
unsigned int update_snonce:1;
|
||||
unsigned int alt_snonce_valid:1;
|
||||
+ unsigned int waiting_radius_psk:1;
|
||||
#ifdef CONFIG_IEEE80211R_AP
|
||||
unsigned int ft_completed:1;
|
||||
unsigned int pmk_r1_name_valid:1;
|
||||
@@ -0,0 +1,350 @@
|
||||
From 24763e3cd0a564eb71f3c501bbb4fbb0d7070762 Mon Sep 17 00:00:00 2001
|
||||
From: Jouni Malinen <j@w1.fi>
|
||||
Date: Fri, 15 Apr 2022 17:31:48 +0300
|
||||
Subject: [PATCH] RADIUS: Attributes with Extended Types (RFC 6929)
|
||||
|
||||
Supported extended types for RADIUS attributes for the cases defined in
|
||||
RFC 6929.
|
||||
|
||||
Signed-off-by: Jouni Malinen <j@w1.fi>
|
||||
---
|
||||
src/radius/radius.c | 195 ++++++++++++++++++++++++++++++++++++++------
|
||||
src/radius/radius.h | 26 +++++-
|
||||
2 files changed, 193 insertions(+), 28 deletions(-)
|
||||
|
||||
diff --git a/src/radius/radius.c b/src/radius/radius.c
|
||||
index be16e27b9..a64228067 100644
|
||||
--- a/src/radius/radius.c
|
||||
+++ b/src/radius/radius.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* RADIUS message processing
|
||||
- * Copyright (c) 2002-2009, 2011-2015, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2002-2009, 2011-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -159,7 +159,8 @@ static const char *radius_code_string(u8 code)
|
||||
|
||||
|
||||
struct radius_attr_type {
|
||||
- u8 type;
|
||||
+ u16 type; /* 0..255 for basic types;
|
||||
+ * (241 << 8) | <ext-type> for extended types */
|
||||
char *name;
|
||||
enum {
|
||||
RADIUS_ATTR_UNDIST, RADIUS_ATTR_TEXT, RADIUS_ATTR_IP,
|
||||
@@ -260,11 +261,31 @@ static const struct radius_attr_type radius_attrs[] =
|
||||
RADIUS_ATTR_HEXDUMP },
|
||||
{ RADIUS_ATTR_WLAN_GROUP_MGMT_CIPHER, "WLAN-Group-Mgmt-Pairwise-Cipher",
|
||||
RADIUS_ATTR_HEXDUMP },
|
||||
+ { RADIUS_ATTR_EXT_TYPE_1, "Extended-Type-1", RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_TYPE_2, "Extended-Type-2", RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_TYPE_3, "Extended-Type-3", RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_TYPE_4, "Extended-Type-4", RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_LONG_EXT_TYPE_1, "Long-Extended-Type-1",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_LONG_EXT_TYPE_2, "Long-Extended-Type-2",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_1, "Extended-Vendor-Specific-1",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_2, "Extended-Vendor-Specific-2",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_3, "Extended-Vendor-Specific-3",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_4, "Extended-Vendor-Specific-4",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_5, "Extended-Vendor-Specific-5",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
+ { RADIUS_ATTR_EXT_VENDOR_SPECIFIC_6, "Extended-Vendor-Specific-6",
|
||||
+ RADIUS_ATTR_UNDIST },
|
||||
};
|
||||
#define RADIUS_ATTRS ARRAY_SIZE(radius_attrs)
|
||||
|
||||
|
||||
-static const struct radius_attr_type *radius_get_attr_type(u8 type)
|
||||
+static const struct radius_attr_type * radius_get_attr_type(u16 type)
|
||||
{
|
||||
size_t i;
|
||||
|
||||
@@ -277,23 +298,60 @@ static const struct radius_attr_type *radius_get_attr_type(u8 type)
|
||||
}
|
||||
|
||||
|
||||
+static bool radius_is_long_ext_type(u8 type)
|
||||
+{
|
||||
+ return type == RADIUS_ATTR_LONG_EXT_TYPE_1 ||
|
||||
+ type == RADIUS_ATTR_LONG_EXT_TYPE_2;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static bool radius_is_ext_type(u8 type)
|
||||
+{
|
||||
+ return type >= RADIUS_ATTR_EXT_TYPE_1 &&
|
||||
+ type <= RADIUS_ATTR_LONG_EXT_TYPE_2;
|
||||
+}
|
||||
+
|
||||
+
|
||||
static void radius_msg_dump_attr(struct radius_attr_hdr *hdr)
|
||||
{
|
||||
+ struct radius_attr_hdr_ext *ext = NULL;
|
||||
const struct radius_attr_type *attr;
|
||||
int len;
|
||||
unsigned char *pos;
|
||||
char buf[1000];
|
||||
|
||||
- attr = radius_get_attr_type(hdr->type);
|
||||
+ if (hdr->length < sizeof(struct radius_attr_hdr))
|
||||
+ return;
|
||||
|
||||
- wpa_printf(MSG_INFO, " Attribute %d (%s) length=%d",
|
||||
- hdr->type, attr ? attr->name : "?Unknown?", hdr->length);
|
||||
+ if (radius_is_ext_type(hdr->type)) {
|
||||
+ if (hdr->length < 4) {
|
||||
+ wpa_printf(MSG_INFO,
|
||||
+ " Invalid attribute %d (too short for extended type)",
|
||||
+ hdr->type);
|
||||
+ return;
|
||||
+ }
|
||||
|
||||
- if (attr == NULL || hdr->length < sizeof(struct radius_attr_hdr))
|
||||
- return;
|
||||
+ ext = (struct radius_attr_hdr_ext *) hdr;
|
||||
+ }
|
||||
+
|
||||
+ if (ext) {
|
||||
+ attr = radius_get_attr_type((ext->type << 8) | ext->ext_type);
|
||||
+ wpa_printf(MSG_INFO, " Attribute %d.%d (%s) length=%d",
|
||||
+ ext->type, ext->ext_type,
|
||||
+ attr ? attr->name : "?Unknown?", ext->length);
|
||||
+ pos = (unsigned char *) (ext + 1);
|
||||
+ len = ext->length - sizeof(struct radius_attr_hdr_ext);
|
||||
+ } else {
|
||||
+ attr = radius_get_attr_type(hdr->type);
|
||||
+ wpa_printf(MSG_INFO, " Attribute %d (%s) length=%d",
|
||||
+ hdr->type, attr ? attr->name : "?Unknown?",
|
||||
+ hdr->length);
|
||||
+ pos = (unsigned char *) (hdr + 1);
|
||||
+ len = hdr->length - sizeof(struct radius_attr_hdr);
|
||||
+ }
|
||||
|
||||
- len = hdr->length - sizeof(struct radius_attr_hdr);
|
||||
- pos = (unsigned char *) (hdr + 1);
|
||||
+ if (!attr)
|
||||
+ return;
|
||||
|
||||
switch (attr->data_type) {
|
||||
case RADIUS_ATTR_TEXT:
|
||||
@@ -627,22 +685,54 @@ static int radius_msg_add_attr_to_array(struct radius_msg *msg,
|
||||
}
|
||||
|
||||
|
||||
-struct radius_attr_hdr *radius_msg_add_attr(struct radius_msg *msg, u8 type,
|
||||
- const u8 *data, size_t data_len)
|
||||
+struct radius_attr_hdr * radius_msg_add_attr(struct radius_msg *msg, u16 type,
|
||||
+ const u8 *data, size_t data_len)
|
||||
{
|
||||
- size_t buf_needed;
|
||||
- struct radius_attr_hdr *attr;
|
||||
+ size_t buf_needed, max_len;
|
||||
+ struct radius_attr_hdr *attr = NULL;
|
||||
+ struct radius_attr_hdr_ext *ext;
|
||||
+ u8 ext_type = 0;
|
||||
|
||||
if (TEST_FAIL())
|
||||
return NULL;
|
||||
|
||||
- if (data_len > RADIUS_MAX_ATTR_LEN) {
|
||||
- wpa_printf(MSG_ERROR, "radius_msg_add_attr: too long attribute (%lu bytes)",
|
||||
- (unsigned long) data_len);
|
||||
- return NULL;
|
||||
+ if (type > 255) {
|
||||
+ if (!radius_is_ext_type(type >> 8)) {
|
||||
+ wpa_printf(MSG_ERROR,
|
||||
+ "%s: Undefined extended type %d.%d",
|
||||
+ __func__, type >> 8, type & 0xff);
|
||||
+ return NULL;
|
||||
+ }
|
||||
+ ext_type = type & 0xff;
|
||||
+ type >>= 8;
|
||||
+ } else if (radius_is_ext_type(type)) {
|
||||
+ wpa_printf(MSG_ERROR, "%s: Unexpected extended type use for %d",
|
||||
+ __func__, type);
|
||||
}
|
||||
|
||||
- buf_needed = sizeof(*attr) + data_len;
|
||||
+ if (radius_is_long_ext_type(type)) {
|
||||
+ size_t hdr_len = sizeof(struct radius_attr_hdr_ext) + 1;
|
||||
+ size_t plen = 255 - hdr_len;
|
||||
+ size_t num;
|
||||
+
|
||||
+ max_len = 4096;
|
||||
+ num = (data_len + plen - 1) / plen;
|
||||
+ if (num == 0)
|
||||
+ num = 1;
|
||||
+ buf_needed = num * hdr_len + data_len;
|
||||
+ } else if (radius_is_ext_type(type)) {
|
||||
+ max_len = RADIUS_MAX_EXT_ATTR_LEN;
|
||||
+ buf_needed = sizeof(struct radius_attr_hdr_ext) + data_len;
|
||||
+ } else {
|
||||
+ max_len = RADIUS_MAX_ATTR_LEN;
|
||||
+ buf_needed = sizeof(*attr) + data_len;
|
||||
+ }
|
||||
+ if (data_len > max_len) {
|
||||
+ wpa_printf(MSG_ERROR,
|
||||
+ "%s: too long attribute (%zu > %zu bytes)",
|
||||
+ __func__, data_len, max_len);
|
||||
+ return NULL;
|
||||
+ }
|
||||
|
||||
if (wpabuf_tailroom(msg->buf) < buf_needed) {
|
||||
/* allocate more space for message buffer */
|
||||
@@ -651,13 +741,44 @@ struct radius_attr_hdr *radius_msg_add_attr(struct radius_msg *msg, u8 type,
|
||||
msg->hdr = wpabuf_mhead(msg->buf);
|
||||
}
|
||||
|
||||
- attr = wpabuf_put(msg->buf, sizeof(struct radius_attr_hdr));
|
||||
- attr->type = type;
|
||||
- attr->length = sizeof(*attr) + data_len;
|
||||
- wpabuf_put_data(msg->buf, data, data_len);
|
||||
-
|
||||
- if (radius_msg_add_attr_to_array(msg, attr))
|
||||
- return NULL;
|
||||
+ if (radius_is_long_ext_type(type)) {
|
||||
+ size_t plen = 255 - sizeof(struct radius_attr_hdr_ext) - 1;
|
||||
+ size_t alen;
|
||||
+
|
||||
+ do {
|
||||
+ alen = data_len > plen ? plen : data_len;
|
||||
+ ext = wpabuf_put(msg->buf,
|
||||
+ sizeof(struct radius_attr_hdr_ext));
|
||||
+ if (!attr)
|
||||
+ attr = (struct radius_attr_hdr *) ext;
|
||||
+ ext->type = type;
|
||||
+ ext->length = sizeof(*ext) + 1 + alen;
|
||||
+ ext->ext_type = ext_type;
|
||||
+ wpabuf_put_u8(msg->buf, data_len > alen ? 0x80 : 0);
|
||||
+ wpabuf_put_data(msg->buf, data, data_len);
|
||||
+ data += alen;
|
||||
+ data_len -= alen;
|
||||
+ if (radius_msg_add_attr_to_array(
|
||||
+ msg, (struct radius_attr_hdr *) ext))
|
||||
+ return NULL;
|
||||
+ } while (data_len > 0);
|
||||
+ } else if (radius_is_ext_type(type)) {
|
||||
+ ext = wpabuf_put(msg->buf, sizeof(struct radius_attr_hdr_ext));
|
||||
+ attr = (struct radius_attr_hdr *) ext;
|
||||
+ ext->type = type;
|
||||
+ ext->length = sizeof(*ext) + data_len;
|
||||
+ ext->ext_type = ext_type;
|
||||
+ wpabuf_put_data(msg->buf, data, data_len);
|
||||
+ if (radius_msg_add_attr_to_array(msg, attr))
|
||||
+ return NULL;
|
||||
+ } else {
|
||||
+ attr = wpabuf_put(msg->buf, sizeof(struct radius_attr_hdr));
|
||||
+ attr->type = type;
|
||||
+ attr->length = sizeof(*attr) + data_len;
|
||||
+ wpabuf_put_data(msg->buf, data, data_len);
|
||||
+ if (radius_msg_add_attr_to_array(msg, attr))
|
||||
+ return NULL;
|
||||
+ }
|
||||
|
||||
return attr;
|
||||
}
|
||||
@@ -1285,6 +1406,28 @@ int radius_msg_add_wfa(struct radius_msg *msg, u8 subtype, const u8 *data,
|
||||
}
|
||||
|
||||
|
||||
+int radius_msg_add_ext_vs(struct radius_msg *msg, u16 type, u32 vendor_id,
|
||||
+ u8 vendor_type, const u8 *data, size_t len)
|
||||
+{
|
||||
+ struct radius_attr_hdr *attr;
|
||||
+ u8 *buf, *pos;
|
||||
+ size_t alen;
|
||||
+
|
||||
+ alen = 4 + 1 + len;
|
||||
+ buf = os_malloc(alen);
|
||||
+ if (!buf)
|
||||
+ return 0;
|
||||
+ pos = buf;
|
||||
+ WPA_PUT_BE32(pos, vendor_id);
|
||||
+ pos += 4;
|
||||
+ *pos++ = vendor_type;
|
||||
+ os_memcpy(pos, data, len);
|
||||
+ attr = radius_msg_add_attr(msg, type, buf, alen);
|
||||
+ os_free(buf);
|
||||
+ return attr != NULL;
|
||||
+}
|
||||
+
|
||||
+
|
||||
int radius_user_password_hide(struct radius_msg *msg,
|
||||
const u8 *data, size_t data_len,
|
||||
const u8 *secret, size_t secret_len,
|
||||
diff --git a/src/radius/radius.h b/src/radius/radius.h
|
||||
index fb8148180..490c8d1f6 100644
|
||||
--- a/src/radius/radius.h
|
||||
+++ b/src/radius/radius.h
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* RADIUS message processing
|
||||
- * Copyright (c) 2002-2009, 2012, 2014-2015, Jouni Malinen <j@w1.fi>
|
||||
+ * Copyright (c) 2002-2009, 2012, 2014-2022, Jouni Malinen <j@w1.fi>
|
||||
*
|
||||
* This software may be distributed under the terms of the BSD license.
|
||||
* See README for more details.
|
||||
@@ -46,7 +46,15 @@ struct radius_attr_hdr {
|
||||
/* followed by length-2 octets of attribute value */
|
||||
} STRUCT_PACKED;
|
||||
|
||||
+struct radius_attr_hdr_ext {
|
||||
+ u8 type;
|
||||
+ u8 length; /* including this header */
|
||||
+ u8 ext_type;
|
||||
+ /* followed by length-3 octets of attribute value */
|
||||
+} STRUCT_PACKED;
|
||||
+
|
||||
#define RADIUS_MAX_ATTR_LEN (255 - sizeof(struct radius_attr_hdr))
|
||||
+#define RADIUS_MAX_EXT_ATTR_LEN (255 - sizeof(struct radius_attr_hdr_ext))
|
||||
|
||||
enum { RADIUS_ATTR_USER_NAME = 1,
|
||||
RADIUS_ATTR_USER_PASSWORD = 2,
|
||||
@@ -113,6 +121,18 @@ enum { RADIUS_ATTR_USER_NAME = 1,
|
||||
RADIUS_ATTR_WLAN_GROUP_CIPHER = 187,
|
||||
RADIUS_ATTR_WLAN_AKM_SUITE = 188,
|
||||
RADIUS_ATTR_WLAN_GROUP_MGMT_CIPHER = 189,
|
||||
+ RADIUS_ATTR_EXT_TYPE_1 = 241,
|
||||
+ RADIUS_ATTR_EXT_TYPE_2 = 242,
|
||||
+ RADIUS_ATTR_EXT_TYPE_3 = 243,
|
||||
+ RADIUS_ATTR_EXT_TYPE_4 = 244,
|
||||
+ RADIUS_ATTR_LONG_EXT_TYPE_1 = 245,
|
||||
+ RADIUS_ATTR_LONG_EXT_TYPE_2 = 246,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_1 = (241 << 8) | 26,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_2 = (242 << 8) | 26,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_3 = (243 << 8) | 26,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_4 = (244 << 8) | 26,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_5 = (245 << 8) | 26,
|
||||
+ RADIUS_ATTR_EXT_VENDOR_SPECIFIC_6 = (246 << 8) | 26,
|
||||
};
|
||||
|
||||
|
||||
@@ -257,7 +277,7 @@ int radius_msg_verify_acct_req(struct radius_msg *msg, const u8 *secret,
|
||||
int radius_msg_verify_das_req(struct radius_msg *msg, const u8 *secret,
|
||||
size_t secret_len,
|
||||
int require_message_authenticator);
|
||||
-struct radius_attr_hdr * radius_msg_add_attr(struct radius_msg *msg, u8 type,
|
||||
+struct radius_attr_hdr * radius_msg_add_attr(struct radius_msg *msg, u16 type,
|
||||
const u8 *data, size_t data_len);
|
||||
struct radius_msg * radius_msg_parse(const u8 *data, size_t len);
|
||||
int radius_msg_add_eap(struct radius_msg *msg, const u8 *data,
|
||||
@@ -284,6 +304,8 @@ int radius_msg_add_mppe_keys(struct radius_msg *msg,
|
||||
const u8 *recv_key, size_t recv_key_len);
|
||||
int radius_msg_add_wfa(struct radius_msg *msg, u8 subtype, const u8 *data,
|
||||
size_t len);
|
||||
+int radius_msg_add_ext_vs(struct radius_msg *msg, u16 type, u32 vendor_id,
|
||||
+ u8 vendor_type, const u8 *data, size_t len);
|
||||
int radius_user_password_hide(struct radius_msg *msg,
|
||||
const u8 *data, size_t data_len,
|
||||
const u8 *secret, size_t secret_len,
|
||||
--
|
||||
2.25.1
|
||||
|
||||
@@ -0,0 +1,102 @@
|
||||
From b94371af8402f60218716552e571ca72cff4e3c0 Mon Sep 17 00:00:00 2001
|
||||
From: Jouni Malinen <j@w1.fi>
|
||||
Date: Fri, 15 Apr 2022 17:36:25 +0300
|
||||
Subject: [PATCH] RADIUS attributes for EAPOL-Key message details
|
||||
|
||||
Use vendor specific RADIUS attributes for sending ANonce and EAPOL-Key
|
||||
msg 2/4 for the wpa_psk_radius=3 case. The vendor specific attributes
|
||||
for this are defined in FreeRADIUS as follows:
|
||||
|
||||
BEGIN-VENDOR FreeRADIUS format=Extended-Vendor-Specific-5
|
||||
ATTRIBUTE FreeRADIUS-802.1X-Anonce 1 octets[32]
|
||||
ATTRIBUTE FreeRADIUS-802.1X-EAPoL-Key-Msg 2 octets
|
||||
END-VENDOR FreeRADIUS
|
||||
|
||||
Signed-off-by: Jouni Malinen <j@w1.fi>
|
||||
---
|
||||
src/ap/ieee802_11_auth.c | 29 +++++++++++++++++++++++++++++
|
||||
src/radius/radius.h | 7 +++++++
|
||||
2 files changed, 36 insertions(+)
|
||||
|
||||
diff --git a/src/ap/ieee802_11_auth.c b/src/ap/ieee802_11_auth.c
|
||||
index a54d7616e..4277d82cb 100644
|
||||
--- a/src/ap/ieee802_11_auth.c
|
||||
+++ b/src/ap/ieee802_11_auth.c
|
||||
@@ -47,6 +47,9 @@ struct hostapd_acl_query_data {
|
||||
struct hostapd_acl_query_data *next;
|
||||
bool radius_psk;
|
||||
int akm;
|
||||
+ u8 *anonce;
|
||||
+ u8 *eapol;
|
||||
+ size_t eapol_len;
|
||||
};
|
||||
|
||||
|
||||
@@ -102,6 +105,8 @@ static void hostapd_acl_query_free(struct hostapd_acl_query_data *query)
|
||||
if (!query)
|
||||
return;
|
||||
os_free(query->auth_msg);
|
||||
+ os_free(query->anonce);
|
||||
+ os_free(query->eapol);
|
||||
os_free(query);
|
||||
}
|
||||
|
||||
@@ -164,6 +169,24 @@ static int hostapd_radius_acl_query(struct hostapd_data *hapd, const u8 *addr,
|
||||
goto fail;
|
||||
}
|
||||
|
||||
+ if (query->anonce &&
|
||||
+ !radius_msg_add_ext_vs(msg, RADIUS_ATTR_EXT_VENDOR_SPECIFIC_5,
|
||||
+ RADIUS_VENDOR_ID_FREERADIUS,
|
||||
+ RADIUS_VENDOR_ATTR_FREERADIUS_802_1X_ANONCE,
|
||||
+ query->anonce, WPA_NONCE_LEN)) {
|
||||
+ wpa_printf(MSG_DEBUG, "Could not add FreeRADIUS-802.1X-Anonce");
|
||||
+ goto fail;
|
||||
+ }
|
||||
+
|
||||
+ if (query->eapol &&
|
||||
+ !radius_msg_add_ext_vs(msg, RADIUS_ATTR_EXT_VENDOR_SPECIFIC_5,
|
||||
+ RADIUS_VENDOR_ID_FREERADIUS,
|
||||
+ RADIUS_VENDOR_ATTR_FREERADIUS_802_1X_EAPOL_KEY_MSG,
|
||||
+ query->eapol, query->eapol_len)) {
|
||||
+ wpa_printf(MSG_DEBUG, "Could not add FreeRADIUS-802.1X-EAPoL-Key-Msg");
|
||||
+ goto fail;
|
||||
+ }
|
||||
+
|
||||
if (radius_client_send(hapd->radius, msg, RADIUS_AUTH, addr) < 0)
|
||||
goto fail;
|
||||
return 0;
|
||||
@@ -703,6 +726,12 @@ void hostapd_acl_req_radius_psk(struct hostapd_data *hapd, const u8 *addr,
|
||||
query->akm = key_mgmt;
|
||||
os_get_reltime(&query->timestamp);
|
||||
os_memcpy(query->addr, addr, ETH_ALEN);
|
||||
+ if (anonce)
|
||||
+ query->anonce = os_memdup(anonce, WPA_NONCE_LEN);
|
||||
+ if (eapol) {
|
||||
+ query->eapol = os_memdup(eapol, eapol_len);
|
||||
+ query->eapol_len = eapol_len;
|
||||
+ }
|
||||
if (hostapd_radius_acl_query(hapd, addr, query)) {
|
||||
wpa_printf(MSG_DEBUG,
|
||||
"Failed to send Access-Request for RADIUS PSK/ACL query");
|
||||
diff --git a/src/radius/radius.h b/src/radius/radius.h
|
||||
index 490c8d1f6..177c64a66 100644
|
||||
--- a/src/radius/radius.h
|
||||
+++ b/src/radius/radius.h
|
||||
@@ -208,6 +208,13 @@ enum { RADIUS_VENDOR_ATTR_MS_MPPE_SEND_KEY = 16,
|
||||
RADIUS_VENDOR_ATTR_MS_MPPE_RECV_KEY = 17
|
||||
};
|
||||
|
||||
+/* FreeRADIUS vendor-specific attributes */
|
||||
+#define RADIUS_VENDOR_ID_FREERADIUS 11344
|
||||
+/* Extended-Vendor-Specific-5 (245.26; long extended header) */
|
||||
+enum {
|
||||
+ RADIUS_VENDOR_ATTR_FREERADIUS_802_1X_ANONCE = 1,
|
||||
+ RADIUS_VENDOR_ATTR_FREERADIUS_802_1X_EAPOL_KEY_MSG = 2,
|
||||
+};
|
||||
|
||||
/* Hotspot 2.0 - WFA Vendor-specific RADIUS Attributes */
|
||||
#define RADIUS_VENDOR_ID_WFA 40808
|
||||
--
|
||||
2.25.1
|
||||
|
||||
@@ -0,0 +1,32 @@
|
||||
--- a/src/ap/ieee802_11_auth.c
|
||||
+++ b/src/ap/ieee802_11_auth.c
|
||||
@@ -578,6 +578,8 @@ hostapd_acl_recv_radius(struct radius_ms
|
||||
os_memcpy(info->radius_cui, buf, len);
|
||||
}
|
||||
|
||||
+ radius_msg_get_wispr(msg, info->bandwidth);
|
||||
+
|
||||
if (hapd->conf->wpa_psk_radius == PSK_RADIUS_REQUIRED &&
|
||||
!info->psk)
|
||||
cache->accepted = HOSTAPD_ACL_REJECT;
|
||||
--- a/src/ap/ieee802_11_auth.h
|
||||
+++ b/src/ap/ieee802_11_auth.h
|
||||
@@ -23,6 +23,7 @@ struct radius_sta {
|
||||
struct hostapd_sta_wpa_psk_short *psk;
|
||||
char *identity;
|
||||
char *radius_cui;
|
||||
+ u32 bandwidth[2];
|
||||
};
|
||||
|
||||
int hostapd_check_acl(struct hostapd_data *hapd, const u8 *addr,
|
||||
--- a/src/ap/ieee802_11.c
|
||||
+++ b/src/ap/ieee802_11.c
|
||||
@@ -2406,6 +2406,8 @@ int ieee802_11_set_radius_info(struct ho
|
||||
ap_sta_no_session_timeout(hapd, sta);
|
||||
}
|
||||
|
||||
+ os_memcpy(sta->bandwidth, info->bandwidth, sizeof(sta->bandwidth));
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -156,6 +156,8 @@ ath11k-macs)
|
||||
ath11k_generate_macs_eww631_b1
|
||||
;;
|
||||
edgecore,eap104|\
|
||||
edgecore,oap101-6e|\
|
||||
edgecore,oap101e-6e|\
|
||||
optimcloud,d60|\
|
||||
optimcloud,d60-5g|\
|
||||
optimcloud,d50|\
|
||||
|
||||
@@ -43,8 +43,10 @@ qcom_setup_macs()
|
||||
[ -z "$mac" ] && return;
|
||||
wan_mac=$(macaddr_canonicalize $mac)
|
||||
lan_mac=$(macaddr_add "$wan_mac" 1)
|
||||
ucidef_set_network_device_mac eth0 $lan_mac
|
||||
ucidef_set_network_device_mac eth1 $wan_mac
|
||||
ucidef_set_network_device_mac eth0 $wan_mac
|
||||
ucidef_set_network_device_mac eth1 $lan_mac
|
||||
ip link set eth0 address $wan_mac
|
||||
ip link set eth1 address $lan_mac
|
||||
ucidef_set_label_macaddr $wan_mac
|
||||
;;
|
||||
*)
|
||||
|
||||
82
feeds/ipq95xx/ftm/Makefile
Executable file
82
feeds/ipq95xx/ftm/Makefile
Executable file
@@ -0,0 +1,82 @@
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG:=ftm
|
||||
PKG_NAME:=$(PKG)
|
||||
PKG_RELEASE:=1
|
||||
|
||||
LOCAL_SRC:=$(TOPDIR)/qca/src/common-tools/ftm
|
||||
|
||||
PKG_VERSION:=12.3
|
||||
|
||||
#PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/$(PKG_NAME)
|
||||
SECTION:=QCA
|
||||
CATEGORY:=QTI software
|
||||
URL:=http://www.qca.qualcomm.com
|
||||
MAINTAINER:=Qualcomm Atheros
|
||||
TITLE:= QCA ftm utils
|
||||
DEPENDS:= @TARGET_ipq_ipq807x||TARGET_ipq_ipq807x_64||TARGET_ipq_ipq60xx||TARGET_ipq_ipq60xx_64||TARGET_ipq_ipq50xx||TARGET_ipq_ipq50xx_64||TARGET_ipq807x||TARGET_ipq50xx||TARGET_ipq60xx||TARGET_ipq95xx||TARGET_ipq53xx +libnl +libtcmd +qca-diag +librt +kmod-diag-char
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/description/Default
|
||||
FTM Package Support for QCA WIFI 11 drivers
|
||||
endef
|
||||
|
||||
TARGET_CFLAGS += -DCONFIG_FTM_WLAN -DDEBUG -DFTM_DEBUG -DWIN_AP_HOST
|
||||
TARGET_CFLAGS += -I$(STAGING_DIR)/usr/include/qca-diag
|
||||
TARGET_CFLAGS += -MMD -O2 -Wall -g
|
||||
TARGET_CFLAGS += -I$(STAGING_DIR)/usr/include
|
||||
TARGET_CFLAGS += -fpie
|
||||
TARGET_LDFLAGS += -ldiag -lnl-3 -lnl-genl-3 -lrt -ltcmd
|
||||
TARGET_CSRCS := ftm_main.c ftm_wlan.c ftm_write_to_flash.c
|
||||
TARGET_LDFLAGS += -pie
|
||||
|
||||
ifeq ($(CONFIG_FEATURE_IPQ_PROVISION_SUPPORT),y)
|
||||
TARGET_CFLAGS += -I$(STAGING_DIR)/usr/include/qti-mfg-provision
|
||||
TARGET_CFLAGS += -DWIN_AP_AFC
|
||||
TARGET_LDFLAGS += -lprovision
|
||||
endif
|
||||
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-mac80211),)
|
||||
TARGET_CFLAGS+=-DWIN_AP_HOST_OPEN=1
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_FEATURE_QCA_IOT),y)
|
||||
TARGET_CFLAGS += -DIPQ_AP_HOST_IOT -DIPQ_AP_HOST_IOT_QCA402X -ggdb3 -DCONFIG_DAEMON_MODE
|
||||
TARGET_CSRCS += ftm_iot.c
|
||||
TARGET_LDFLAGS += -lpthread
|
||||
TARGET_CFLAGS += -I$(STAGING_DIR)/usr/include/qca-iot
|
||||
TARGET_LDFLAGS += -ldiag_demo
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_FEATURE_IPQ_IOT_SUPPORT),y)
|
||||
TARGET_CFLAGS += -DIPQ_AP_HOST_IOT -DIPQ_AP_HOST_IOT_IPQ -ggdb3 -I$(STAGING_DIR)/usr/include/btdaemon
|
||||
TARGET_CSRCS += ftm_iot.c
|
||||
TARGET_LDFLAGS += -lpthread -lbtdaemon
|
||||
endif
|
||||
|
||||
define Build/Compile
|
||||
$(MAKE) -C $(PKG_BUILD_DIR) \
|
||||
CC="$(TARGET_CC)" \
|
||||
CFLAGS="$(TARGET_CFLAGS)" \
|
||||
LDFLAGS="$(TARGET_LDFLAGS)" \
|
||||
CSRCS="$(TARGET_CSRCS)"
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/install
|
||||
$(INSTALL_DIR) $(1)/usr/sbin
|
||||
$(INSTALL_DIR) $(1)/etc/init.d
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/ftm $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) ./files/ftm.init $(1)/etc/init.d/ftm
|
||||
$(INSTALL_DIR) $(1)/lib/wifi
|
||||
$(INSTALL_BIN) ./files/compress_vart.sh $(1)/lib/compress_vart.sh
|
||||
ifneq (, $(findstring ipq95xx, $(CONFIG_TARGET_BOARD)))
|
||||
$(INSTALL_DIR) $(1)/sbin
|
||||
$(INSTALL_BIN) ./files/ftm_qcc710_start.sh $(1)/sbin/ftm_qcc710_start
|
||||
endif
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,ftm))
|
||||
75
feeds/ipq95xx/ftm/files/compress_vart.sh
Executable file
75
feeds/ipq95xx/ftm/files/compress_vart.sh
Executable file
@@ -0,0 +1,75 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright (c) 2020 Qualcomm Technologies, Inc.
|
||||
#
|
||||
# All Rights Reserved.
|
||||
# Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
#
|
||||
#
|
||||
|
||||
[ -e /lib/functions.sh ] && . /lib/functions.sh
|
||||
[ -e /lib/ipq806x.sh ] && . /lib/ipq806x.sh
|
||||
[ -e /lib/functions/boot.sh ] && . /lib/functions/boot.sh
|
||||
|
||||
low_mem_compress_art()
|
||||
{
|
||||
local mtdblock=$(find_mtd_part 0:ART)
|
||||
|
||||
if [ -z "$mtdblock" ]; then
|
||||
# read from mmc
|
||||
mtdblock=$(find_mmc_part 0:ART)
|
||||
fi
|
||||
|
||||
[ -n "$mtdblock" ] || return
|
||||
|
||||
local apmp="/tmp"
|
||||
|
||||
lzma -zvfk -4 ${apmp}/virtual_art.bin 2> /dev/null || {
|
||||
echo "Error Compressing Virtual ART" > /dev/console
|
||||
return
|
||||
}
|
||||
|
||||
dd if=${apmp}/virtual_art.bin.lzma of=${mtdblock}
|
||||
echo "Success compressing Virtual ART(${mtdblock})" > /dev/console
|
||||
return
|
||||
}
|
||||
|
||||
normal_art()
|
||||
{
|
||||
local mtdblock=$(find_mtd_part 0:ART)
|
||||
|
||||
if [ -z "$mtdblock" ]; then
|
||||
# read from mmc
|
||||
mtdblock=$(find_mmc_part 0:ART)
|
||||
fi
|
||||
|
||||
[ -n "$mtdblock" ] || return
|
||||
|
||||
local apmp="/tmp"
|
||||
|
||||
dd if=${apmp}/virtual_art.bin of=${mtdblock}
|
||||
echo "Success writing to ART(${mtdblock})" > /dev/console
|
||||
return
|
||||
}
|
||||
|
||||
write_caldata()
|
||||
{
|
||||
local board
|
||||
[ -f /tmp/sysinfo/board_name ] && {
|
||||
board=ap$(cat /tmp/sysinfo/board_name | awk -F 'ap' '{print$2}')
|
||||
}
|
||||
|
||||
if [ -e /sys/firmware/devicetree/base/compressed_art ]
|
||||
then
|
||||
echo "Compressed ART Supported Platform $board " > /dev/console
|
||||
low_mem_compress_art
|
||||
else
|
||||
echo "Non Compressed ART Platform $board " > /dev/console
|
||||
normal_art
|
||||
fi
|
||||
}
|
||||
|
||||
if [ "$1" = "write_caldata" ]
|
||||
then
|
||||
write_caldata
|
||||
fi
|
||||
99
feeds/ipq95xx/ftm/files/ftm.init
Executable file
99
feeds/ipq95xx/ftm/files/ftm.init
Executable file
@@ -0,0 +1,99 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
#
|
||||
# Copyright (c) 2013, 2017, 2020 Qualcomm Technologies, Inc.
|
||||
#
|
||||
# All Rights Reserved.
|
||||
# Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
#
|
||||
# 2013 Qualcomm Atheros, Inc.
|
||||
#
|
||||
# All Rights Reserved.
|
||||
# Qualcomm Atheros Confidential and Proprietary
|
||||
#
|
||||
|
||||
[ -e /lib/functions.sh ] && . /lib/functions.sh
|
||||
[ -e /lib/ipq806x.sh ] && . /lib/ipq806x.sh
|
||||
[ -e /lib/functions/boot.sh ] && . /lib/functions/boot.sh
|
||||
|
||||
START=97
|
||||
SERVICE_DAEMONIZE=1
|
||||
SERVICE_WRITE_PID=1
|
||||
|
||||
MTD_ART_PART_NAME="art"
|
||||
|
||||
compressed_art_read() {
|
||||
local mtdblock=$(find_mtd_part 0:ART)
|
||||
|
||||
if [ -z "$mtdblock" ]; then
|
||||
#read from mmc
|
||||
mtdblock=$(find_mmc_part 0:ART)
|
||||
fi
|
||||
|
||||
[ -n "$mtdblock" ] || return
|
||||
|
||||
local apmp="/tmp"
|
||||
|
||||
dd if=${mtdblock} of=${apmp}/virtual_art.bin.lzma
|
||||
lzma -fdv --single-stream ${apmp}/virtual_art.bin.lzma || {
|
||||
# Create dummy virtual_art.bin file of size 512K
|
||||
dd if=/dev/zero of=${apmp}/virtual_art.bin bs=1024 count=512
|
||||
}
|
||||
echo "Uncompressed and Copied ART content from ${mtdblock} to /tmp/virtual_art.bin" > /dev/console
|
||||
}
|
||||
|
||||
raw_art_read() {
|
||||
local mtdblock=$(find_mtd_part 0:ART)
|
||||
|
||||
if [ -z "$mtdblock" ]; then
|
||||
#read from mmc
|
||||
mtdblock=$(find_mmc_part 0:ART)
|
||||
fi
|
||||
|
||||
[ -n "$mtdblock" ] || return
|
||||
|
||||
local apmp="/tmp"
|
||||
|
||||
dd if=${mtdblock} of=${apmp}/virtual_art.bin
|
||||
echo "Copy ART caldata from ${mtdblock} to /tmp/virtual_art.bin" > /dev/console
|
||||
}
|
||||
|
||||
retrieve_caldata() {
|
||||
local board
|
||||
[ -f /tmp/sysinfo/board_name ] && {
|
||||
board=ap$(cat /tmp/sysinfo/board_name | awk -F 'ap' '{print$2}')
|
||||
}
|
||||
echo "**** Platform Name: $board *****" > /dev/console
|
||||
|
||||
if [ -e /sys/firmware/devicetree/base/compressed_art ]
|
||||
then
|
||||
compressed_art_read
|
||||
else
|
||||
raw_art_read
|
||||
fi
|
||||
}
|
||||
|
||||
|
||||
start() {
|
||||
local emmc_flash=""
|
||||
local nor_flash=""
|
||||
|
||||
emmc_flash=$(find_mmc_part 0:ART 2> /dev/null)
|
||||
mtd_name=$(grep -i -w ${MTD_ART_PART_NAME} /proc/mtd | cut -f1 -d:)
|
||||
nor_flash=`find /sys/bus/spi/devices/*/mtd -name ${mtd_name} 2> /dev/null`
|
||||
|
||||
if [ -n "$emmc_flash" ]; then
|
||||
[ -L /dev/caldata ] || \
|
||||
ln -s $emmc_flash /dev/caldata
|
||||
elif [ -n "$nor_flash" ]; then
|
||||
[ -L /dev/caldata ] || \
|
||||
ln -s /dev/${mtd_name//mtd/mtdblock} /dev/caldata
|
||||
elif [ -n "$mtd_name" ]; then
|
||||
[ -L /dev/caldata ] || \
|
||||
ln -s /dev/${mtd_name//mtd/mtdblock} /dev/caldata
|
||||
fi
|
||||
retrieve_caldata
|
||||
}
|
||||
|
||||
stop() {
|
||||
[ -L /dev/caldata ] && rm /dev/caldata
|
||||
}
|
||||
86
feeds/ipq95xx/ftm/files/ftm_qcc710_start.sh
Executable file
86
feeds/ipq95xx/ftm/files/ftm_qcc710_start.sh
Executable file
@@ -0,0 +1,86 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright (c) 2021 Qualcomm Technologies, Inc.
|
||||
#
|
||||
# All Rights Reserved.
|
||||
# Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
#
|
||||
#
|
||||
|
||||
# QCC710 v1.0 reset for BT bringup
|
||||
qcc710_reset() {
|
||||
reset_gpio_pin=$(cat /proc/device-tree/soc/pinctrl@1000000/QCC710_pins/QCC710_reset/pins | sed s/"gpio"//)
|
||||
[[ -z $reset_gpio_pin ]] && return
|
||||
gpio_base=$(cat /sys/class/gpio/gpiochip*/base | head -n1)
|
||||
gpio_reset=$(( gpio_base + reset_gpio_pin ))
|
||||
if [[ ! -e /sys/class/gpio/gpio$gpio_reset ]]; then
|
||||
[ -z ${SLEEP} ] && echo -e "Enter sleep value for reset. Options:\n10 \n1" && read -p "Enter : " SLEEP
|
||||
[ -z ${SLEEP} ] && SLEEP=10
|
||||
echo $gpio_reset > /sys/class/gpio/export
|
||||
echo out > /sys/class/gpio/gpio$gpio_reset/direction
|
||||
echo "Performing QCC710 reset ...." > /dev/console
|
||||
{ echo 1 > /sys/class/gpio/gpio$gpio_reset/value ; \
|
||||
sleep $SLEEP; \
|
||||
echo 0 > /sys/class/gpio/gpio$gpio_reset/value; \
|
||||
echo "QCC710 reset complete ...." > /dev/console; }
|
||||
fi
|
||||
}
|
||||
|
||||
while [ -n "$1" ]; do
|
||||
case "$1" in
|
||||
-h|--help) HELP=1; break;;
|
||||
-a|--ipaddr) SERVERIP="$2";shift;;
|
||||
-s|--sleep) SLEEP="$2";shift;;
|
||||
-r|--baud-rate) BAUDRATE="$2";shift;;
|
||||
-*)
|
||||
echo "Invalid option: $1"
|
||||
ERROR=1;
|
||||
break
|
||||
;;
|
||||
*)break;;
|
||||
esac
|
||||
shift
|
||||
done
|
||||
[ -n "$HELP" -o -n "$ERROR" ] && {
|
||||
cat <<EOF
|
||||
Usage: $0 [-h] [-a SERVERIP] [-r baud-rate] [-s sleep]
|
||||
ftm_qcc710_start options:
|
||||
-h print this help
|
||||
-a ipaddr of the server for diag connection
|
||||
-r baudrate
|
||||
-s sleep
|
||||
|
||||
Example:
|
||||
ftm_qcc710_start -a <serverip> -r <baud-rate> -s <sleep>
|
||||
|
||||
version 1 : ./sbin/ftm_qcc710_start -a 192.168.1.121 -r 2000000 -s 10
|
||||
version 2 : ./sbin/ftm_qcc710_start -a 192.168.1.121 -r 115200 -s 1
|
||||
EOF
|
||||
# If we requested the help flag, then exit normally.
|
||||
# Else, it's probably an error so report it as such.
|
||||
[ -n "$HELP" ] && exit 0
|
||||
exit 1
|
||||
}
|
||||
|
||||
[ -z ${SERVERIP} ] && SERVERIP=$(grep -oh "serverip.*#" /proc/cmdline | awk -F '#' '{print $2}')
|
||||
[ -z ${SERVERIP} ] && read -p "No serverip in cmdline, please enter the serverip : " SERVERIP
|
||||
[ -z ${BAUDRATE} ] && echo -e "Enter baudrate for stack bringup. Options:\n2000000\n115200" && read -p "Enter : " BAUDRATE
|
||||
[ -z ${BAUDRATE} ] && BAUDRATE=2000000
|
||||
qcc710_reset
|
||||
DIAG_PID=$(ps | grep diag_socket_app | grep -v grep | awk '{print $1}')
|
||||
while [ -n "$DIAG_PID" ]
|
||||
do
|
||||
kill -s SIGTERM $DIAG_PID
|
||||
DIAG_PID=$(ps | grep diag_socket_app | grep -v grep | awk '{print $1}')
|
||||
done
|
||||
echo "Stopped previous instances of diag_socket_app process"
|
||||
[ -z "$DIAG_PID" ] && /usr/sbin/diag_socket_app -a $SERVERIP -p 2500 &
|
||||
|
||||
FTM_PID=$(ps | grep "ftm " | grep -v grep | awk '{print $1}')
|
||||
while [ -n "$FTM_PID" ]
|
||||
do
|
||||
kill -s SIGTERM $FTM_PID
|
||||
FTM_PID=$(ps | grep "ftm " | grep -v grep | awk '{print $1}')
|
||||
done
|
||||
echo "Stopped previous instances ftm process"
|
||||
[ -z "$FTM_PID" ] && /usr/sbin/ftm -n -dd -r $BAUDRATE
|
||||
133
feeds/ipq95xx/ftm/src/Android.mk
Executable file
133
feeds/ipq95xx/ftm/src/Android.mk
Executable file
@@ -0,0 +1,133 @@
|
||||
ifeq ($(call is-vendor-board-platform,QCOM),true)
|
||||
|
||||
# Build only if board has BT/FM/WLAN
|
||||
ifeq ($(findstring true, $(BOARD_HAVE_QCOM_FM) $(BOARD_HAVE_BLUETOOTH) $(BOARD_HAS_ATH_WLAN_AR6320)),true)
|
||||
|
||||
LOCAL_PATH:= $(call my-dir)
|
||||
|
||||
BDROID_DIR:= system/bt
|
||||
ifeq ($(TARGET_SUPPORTS_WEARABLES),true)
|
||||
QTI_DIR := hardware/qcom/bt/msm8909/libbt-vendor
|
||||
else
|
||||
QTI_DIR := hardware/qcom/bt/libbt-vendor
|
||||
endif
|
||||
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
LOCAL_C_INCLUDES := $(TARGET_OUT_HEADERS)/diag/include \
|
||||
LOCAL_C_INCLUDES += vendor/qcom/proprietary/diag/src \
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/common/inc \
|
||||
LOCAL_C_INCLUDES += vendor/qcom/proprietary/bt/hci_qcomm_init \
|
||||
LOCAL_C_INCLUDES += vendor/qcom/opensource/fm/helium \
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include \
|
||||
LOCAL_C_INCLUDES += $(BDROID_DIR)/hci/include \
|
||||
LOCAL_C_INCLUDES += $(QTI_DIR)/include
|
||||
ifeq ($(TARGET_SUPPORTS_WEARABLES),true)
|
||||
LOCAL_C_INCLUDES += device/qcom/msm8909w/opensource/bluetooth/tools/hidl_client/inc
|
||||
else
|
||||
LOCAL_C_INCLUDES += vendor/qcom/opensource/bluetooth/tools/hidl_client/inc
|
||||
endif
|
||||
|
||||
LOCAL_ADDITIONAL_DEPENDENCIES := $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr
|
||||
|
||||
LOCAL_CFLAGS:= \
|
||||
-DANDROID \
|
||||
-DDEBUG
|
||||
|
||||
#LOCAL_CFLAGS += -include bionic/libc/include/sys/socket.h
|
||||
#LOCAL_CFLAGS += -include bionic/libc/include/netinet/in.h
|
||||
|
||||
ifneq ($(DISABLE_BT_FTM),true)
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_BT
|
||||
endif
|
||||
|
||||
ifeq ($(BOARD_HAVE_QCOM_FM),true)
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_FM
|
||||
endif
|
||||
|
||||
ifeq ($(BOARD_HAS_QCA_FM_SOC), "cherokee")
|
||||
LOCAL_CFLAGS += -DFM_SOC_TYPE_CHEROKEE
|
||||
endif
|
||||
|
||||
ifneq ($(BOARD_ANT_WIRELESS_DEVICE), )
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_ANT
|
||||
endif
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_NFC
|
||||
|
||||
ifeq ($(BOARD_HAVE_BLUETOOTH_BLUEZ), true)
|
||||
LOCAL_CFLAGS += -DHAS_BLUEZ_BUILDCFG
|
||||
endif # BOARD_HAVE_BLUETOOTH_BLUEZ
|
||||
|
||||
LOCAL_SRC_FILES:= \
|
||||
ftm_main.c \
|
||||
ftm_nfc.c \
|
||||
ftm_nfcnq.c \
|
||||
ftm_nfcqti.c \
|
||||
ftm_nfcnq_fwdl.c \
|
||||
ftm_nfcnq_test.c
|
||||
|
||||
ifneq ($(DISABLE_BT_FTM),true)
|
||||
LOCAL_SRC_FILES += \
|
||||
ftm_bt.c \
|
||||
ftm_bt_power_pfal_linux.c \
|
||||
ftm_bt_hci_pfal_linux.c \
|
||||
ftm_bt_persist.cpp
|
||||
endif
|
||||
|
||||
ifeq ($(call is-platform-sdk-version-at-least,23),true)
|
||||
LOCAL_CFLAGS += -DANDROID_M
|
||||
endif
|
||||
|
||||
ifeq ($(BOARD_HAVE_QCOM_FM),true)
|
||||
ifeq ($(BOARD_HAS_QCA_FM_SOC), "cherokee")
|
||||
LOCAL_SRC_FILES += ftm_fm.c ftm_fm_pfal_linux_3990.c
|
||||
else
|
||||
LOCAL_SRC_FILES += ftm_fm.c ftm_fm_pfal_linux.c
|
||||
endif
|
||||
endif
|
||||
|
||||
ifneq ($(BOARD_ANT_WIRELESS_DEVICE), )
|
||||
LOCAL_SRC_FILES += ftm_ant.c
|
||||
endif
|
||||
|
||||
ifeq ($(findstring true, $(BOARD_HAS_ATH_WLAN) $(BOARD_HAS_ATH_WLAN_AR6320)),true)
|
||||
LOCAL_CFLAGS += -DBOARD_HAS_ATH_WLAN_AR6320
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_WLAN
|
||||
LOCAL_CFLAGS += -DCONFIG_FTM_WLAN_AUTOLOAD
|
||||
LOCAL_STATIC_LIBRARIES += libtcmd
|
||||
LOCAL_SHARED_LIBRARIES += libnl
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/libtcmd
|
||||
LOCAL_SRC_FILES += ftm_wlan.c
|
||||
endif
|
||||
|
||||
LOCAL_SHARED_LIBRARIES += libdl
|
||||
|
||||
ifneq ($(DISABLE_BT_FTM),true)
|
||||
LOCAL_SHARED_LIBRARIES += libbt-hidlclient
|
||||
endif
|
||||
|
||||
LOCAL_MODULE_PATH := $(TARGET_OUT_VENDOR_EXECUTABLES)
|
||||
LOCAL_MODULE:= ftmdaemon
|
||||
LOCAL_CLANG := true
|
||||
ifeq ($(PRODUCT_VENDOR_MOVE_ENABLED),true)
|
||||
LOCAL_PROPRIETARY_MODULE := true
|
||||
endif
|
||||
LOCAL_MODULE_TAGS := optional
|
||||
LOCAL_SHARED_LIBRARIES += libdiag
|
||||
LOCAL_SHARED_LIBRARIES += libcutils liblog libhardware
|
||||
|
||||
ifneq ($(DISABLE_BT_FTM),true)
|
||||
LOCAL_SHARED_LIBRARIES += libbtnv
|
||||
endif
|
||||
|
||||
# By default NV persist gets used
|
||||
LOCAL_CFLAGS += -DBT_NV_SUPPORT
|
||||
|
||||
LDFLAGS += -ldl
|
||||
|
||||
include $(BUILD_EXECUTABLE)
|
||||
include $(call all-makefiles-under,$(LOCAL_PATH))
|
||||
|
||||
endif # filter
|
||||
endif # is-vendor-board-platform
|
||||
181
feeds/ipq95xx/ftm/src/LICENSE
Executable file
181
feeds/ipq95xx/ftm/src/LICENSE
Executable file
@@ -0,0 +1,181 @@
|
||||
This text file is provided to comply with the attribution requirements of
|
||||
the licenses herein, but see NOTICE for license terms of this software.
|
||||
The Apache 2.0 license can be found at
|
||||
http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
12
feeds/ipq95xx/ftm/src/Makefile
Executable file
12
feeds/ipq95xx/ftm/src/Makefile
Executable file
@@ -0,0 +1,12 @@
|
||||
#CC := $(ATH_CROSS_COMPILE_TYPE)gcc
|
||||
TARGET_TYPE ?= AR9888
|
||||
TARGET_VERS ?= v2
|
||||
|
||||
#Sources to compile
|
||||
CSRCS := ftm_main.c ftm_wlan.c ftm_write_to_flash.c
|
||||
|
||||
all:
|
||||
$(CC) $(CFLAGS) $(LDFLAGS) -g3 -Wall \
|
||||
$(CSRCS) -o ftm
|
||||
clean:
|
||||
rm -f ftm
|
||||
86
feeds/ipq95xx/ftm/src/Makefile.am
Executable file
86
feeds/ipq95xx/ftm/src/Makefile.am
Executable file
@@ -0,0 +1,86 @@
|
||||
AM_CFLAGS = -Wall \
|
||||
-g -O0 \
|
||||
$(DIAG_CFLAGS)
|
||||
|
||||
AM_CPPFLAGS = -Wall \
|
||||
-g -O0 \
|
||||
$(DIAG_CFLAGS)
|
||||
|
||||
AM_CFLAGS += -I${WORKSPACE}/system/bt/hci/include
|
||||
AM_CFLAGS += -I${WORKSPACE}/vendor/qcom/proprietary/bt/hci_qcomm_init/
|
||||
|
||||
AM_CPPFLAGS += -I${WORKSPACE}/system/bt/hci/include
|
||||
AM_CPPFLAGS += -I${WORKSPACE}/vendor/qcom/proprietary/bt/hci_qcomm_init/
|
||||
|
||||
if DEBUG
|
||||
AM_CFLAGS += -DDEBUG
|
||||
AM_CPPFLAGS += -DDEBUG
|
||||
endif
|
||||
|
||||
requiredlibs = -lrt $(DIAG_LIBS)
|
||||
|
||||
if USE_GLIB
|
||||
AM_CFLAGS += -DUSE_GLIB $(GLIB_CFLAGS)
|
||||
AM_CPPFLAGS += -DUSE_GLIB $(GLIB_CFLAGS)
|
||||
requiredlibs += $(GLIB_LIBS)
|
||||
endif
|
||||
|
||||
#By default build for MDM_LE
|
||||
AM_CFLAGS += -DMDM_LE
|
||||
AM_CPPFLAGS += -DMDM_LE
|
||||
|
||||
if MDM_ROME
|
||||
AM_CFLAGS += -DBT_SOC_TYPE_ROME
|
||||
AM_CPPFLAGS += -DBT_SOC_TYPE_ROME
|
||||
else
|
||||
if MDM_PRONTO
|
||||
AM_CFLAGS += -DHCI_USE_MCT
|
||||
AM_CPPFLAGS += -DHCI_USE_MCT
|
||||
endif
|
||||
endif
|
||||
|
||||
c_sources = ftm_main.c
|
||||
|
||||
if CONFIG_FTM_BT
|
||||
AM_CFLAGS += -DCONFIG_FTM_BT -DBT_NV_SUPPORT
|
||||
AM_CPPFLAGS += -DCONFIG_FTM_BT -DBT_NV_SUPPORT
|
||||
c_sources += ftm_bt.c
|
||||
c_sources += ftm_bt_power_pfal_linux.c
|
||||
c_sources += ftm_bt_hci_pfal_linux.c
|
||||
c_sources += ftm_bt_persist.cpp
|
||||
endif
|
||||
|
||||
if CONFIG_FTM_FM
|
||||
AM_CFLAGS += -DCONFIG_FTM_FM
|
||||
c_sources += ftm_fm.c
|
||||
c_sources += ftm_fm_pfal_linux.c
|
||||
endif
|
||||
|
||||
if CONFIG_FTM_ANT
|
||||
AM_CFLAGS += -DCONFIG_FTM_ANT
|
||||
c_sources += ftm_ant.c
|
||||
endif
|
||||
|
||||
if CONFIG_FTM_NFC
|
||||
AM_CFLAGS += -DCONFIG_FTM_NFC
|
||||
c_sources += ftm_nfc.c
|
||||
c_sources += ftm_nfcnq.c
|
||||
c_sources += ftm_nfcqti.c
|
||||
c_sources += ftm_nfcnq_fwdl.c
|
||||
c_sources += ftm_nfcnq_test.c
|
||||
endif
|
||||
|
||||
if CONFIG_FTM_WLAN
|
||||
|
||||
AM_CFLAGS += -DCONFIG_FTM_WLAN -DCONFIG_FTM_WLAN_AUTOLOAD
|
||||
AM_CFLAGS += $(LIBNL_CFLAGS) $(ATH6KL_UTILS_CFLAGS)
|
||||
AM_CPPFLAGS += $(LIBNL_CFLAGS) $(ATH6KL_UTILS_CFLAGS)
|
||||
|
||||
requiredlibs += $(ATH6KL_UTILS_LIBS) $(LIBNL_LIBS)
|
||||
|
||||
c_sources += ftm_wlan.c
|
||||
endif
|
||||
|
||||
ftmdaemon_SOURCES = $(c_sources)
|
||||
ftmdaemon_LDADD = -ldl $(requiredlibs) -lbtnv
|
||||
bin_PROGRAMS = ftmdaemon
|
||||
72
feeds/ipq95xx/ftm/src/NOTICE
Executable file
72
feeds/ipq95xx/ftm/src/NOTICE
Executable file
@@ -0,0 +1,72 @@
|
||||
This NOTICE file contains certain notices of software components included
|
||||
with the software that Qualcomm Technologies, Inc. ("Qualcomm Technologies")
|
||||
is required to provide you. Notwithstanding anything in the notices in this
|
||||
file, your use of these software components together with the
|
||||
Qualcomm Technologies software (Qualcomm Technologies software hereinafter
|
||||
referred to as "Software") is subject to the terms of your license from
|
||||
Qualcomm Technologies. Compliance with all copyright laws and software
|
||||
license agreements included in the notice section of this file are the
|
||||
responsibility of the user. Except as may be granted by separate express
|
||||
written agreement, this file provides no license to any patents,
|
||||
trademarks, copyrights, or other intellectual property.
|
||||
|
||||
Copyright (c) 2016 Qualcomm Technologies, Inc.
|
||||
All rights reserved.
|
||||
Qualcomm is a registered trademark and registered service mark of
|
||||
QUALCOMM Incorporated. All other trademarks and service marks are the
|
||||
property of their respective owners.
|
||||
________________________________________
|
||||
NOTICES
|
||||
________________________________________
|
||||
|
||||
Copyright (C) 2010 The Android Open Source Project
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
________________________________________
|
||||
|
||||
Copyright (C) 2015 NXP Semiconductors
|
||||
The original Work has been changed by NXP Semiconductors.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
________________________________________
|
||||
|
||||
Copyright (C) 2015 The Android Open Source Project
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
________________________________________
|
||||
|
||||
Note: Any files for which the above Apache License notices are required
|
||||
to be provided are not contributions.
|
||||
|
||||
A copy of the Apache 2.0 license is included in the file LICENSE
|
||||
for attribution purposes only.
|
||||
149
feeds/ipq95xx/ftm/src/configure.ac
Executable file
149
feeds/ipq95xx/ftm/src/configure.ac
Executable file
@@ -0,0 +1,149 @@
|
||||
# -*- Autoconf -*-
|
||||
|
||||
# configure.ac -- Autoconf script for ftm.
|
||||
#
|
||||
|
||||
# Process this file with autoconf to produce a configure script
|
||||
|
||||
# Requires autoconf tool later than 2.61
|
||||
AC_PREREQ(2.61)
|
||||
# Initialize the ftm package version 1.0.0
|
||||
AC_INIT([ftm],1.0.0)
|
||||
# Does not strictly follow GNU Coding standards
|
||||
AM_INIT_AUTOMAKE([foreign])
|
||||
# Disables auto rebuilding of configure, Makefile.ins
|
||||
AM_MAINTAINER_MODE
|
||||
# defines some macros variable to be included by source
|
||||
AC_CONFIG_HEADERS([config.h])
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
|
||||
# Checks for programs.
|
||||
AC_PROG_CC
|
||||
AC_PROG_CXX
|
||||
AM_PROG_CC_C_O
|
||||
AC_PROG_LIBTOOL
|
||||
AC_PROG_AWK
|
||||
AC_PROG_CPP
|
||||
AC_PROG_INSTALL
|
||||
AC_PROG_LN_S
|
||||
AC_PROG_MAKE_SET
|
||||
|
||||
# Checks for libraries.
|
||||
PKG_CHECK_MODULES([DIAG], [diag])
|
||||
AC_SUBST([DIAG_CFLAGS])
|
||||
AC_SUBST([DIAG_LIBS])
|
||||
|
||||
has_libnl_ver=0
|
||||
# libnl-2 provides only libnl-2.0.pc file, so we check for separate libnl-genl-3.0.pc
|
||||
# pkg-config file just for libnl-3.0 case.
|
||||
#
|
||||
PKG_CHECK_MODULES([LIBNL], [libnl-3.0 >= 3.0 libnl-genl-3.0 >= 3.0], [has_libnl_ver=3], [
|
||||
PKG_CHECK_MODULES([LIBNL], [libnl-2.0 >= 2.0], [has_libnl_ver=2], [
|
||||
PKG_CHECK_MODULES([LIBNL], [libnl-1], [has_libnl_ver=1], [has_libnl_ver=0])])])
|
||||
|
||||
if (test "$has_libnl_ver" -eq 0); then
|
||||
AC_MSG_ERROR(libnl and libnl-genl are required but were not found)
|
||||
fi
|
||||
|
||||
if (test "$has_libnl_ver" -gt 1); then
|
||||
AC_DEFINE([HAVE_LIBNL20], [1], [Define if you have libnl-2.0 or higher])
|
||||
fi
|
||||
|
||||
AC_SUBST([LIBNL_CFLAGS])
|
||||
AC_SUBST([LIBNL_LIBS])
|
||||
|
||||
PKG_CHECK_MODULES([ATH6KL_UTILS], [ath6kl-utils])
|
||||
AC_SUBST([ATH6KL_UTILS_CFLAGS])
|
||||
AC_SUBST([ATH6KL_UTILS_LIBS])
|
||||
|
||||
AC_ARG_WITH([glib],
|
||||
AC_HELP_STRING([--with-glib],
|
||||
[enable glib, building FTM Daemon which use glib]))
|
||||
|
||||
if (test "x${with_glib}" = "xyes"); then
|
||||
PKG_CHECK_MODULES(GTHREAD, gthread-2.0 >= 2.16, dummy=yes,
|
||||
AC_MSG_ERROR(GThread >= 2.16 is required))
|
||||
PKG_CHECK_MODULES(GLIB, glib-2.0 >= 2.16, dummy=yes,
|
||||
AC_MSG_ERROR(GLib >= 2.16 is required))
|
||||
GLIB_CFLAGS="$GLIB_CFLAGS $GTHREAD_CFLAGS"
|
||||
GLIB_LIBS="$GLIB_LIBS $GTHREAD_LIBS"
|
||||
|
||||
AC_SUBST(GLIB_CFLAGS)
|
||||
AC_SUBST(GLIB_LIBS)
|
||||
fi
|
||||
AM_CONDITIONAL(USE_GLIB, test "x${with_glib}" = "xyes")
|
||||
|
||||
AC_ARG_ENABLE([debug],
|
||||
[ --enable-debug Turn on debugging],
|
||||
[case "${enableval}" in
|
||||
yes) debug=true ;;
|
||||
no) debug=false ;;
|
||||
*) AC_MSG_ERROR([bad value ${enableval} for --enable-debug]) ;;
|
||||
esac],[debug=false])
|
||||
|
||||
AM_CONDITIONAL([DEBUG], [test x$debug = xtrue])
|
||||
|
||||
AC_ARG_ENABLE([all],
|
||||
[ --enable-all Enable all FTM functionality],
|
||||
[case "${enableval}" in
|
||||
yes) all=true ;;
|
||||
no) all=false ;;
|
||||
*) AC_MSG_ERROR([bad value ${enableval} for --enable-all]) ;;
|
||||
esac],[all=false])
|
||||
|
||||
AM_CONDITIONAL([CONFIG_FTM_BT], [test x$all = xtrue])
|
||||
AM_CONDITIONAL([CONFIG_FTM_FM], [test x$all = xtrue])
|
||||
AM_CONDITIONAL([CONFIG_FTM_ANT], [test x$all = xtrue])
|
||||
AM_CONDITIONAL([CONFIG_FTM_NFC], [test x$all = xtrue])
|
||||
|
||||
AC_ARG_ENABLE([wlan],
|
||||
[ --enable-wlan Enable WLAN FTM functionality],
|
||||
[case "${enableval}" in
|
||||
yes) wlan=true ;;
|
||||
no) wlan=false ;;
|
||||
*) AC_MSG_ERROR([bad value ${enableval} for --enable-wlan]) ;;
|
||||
esac],[wlan=false])
|
||||
|
||||
AM_CONDITIONAL([CONFIG_FTM_WLAN], [test x$wlan = xtrue -o x$all = xtrue])
|
||||
|
||||
AC_ARG_ENABLE([bt],
|
||||
[ --enable-bt Enable BT FTM functionality],
|
||||
[case "${enableval}" in
|
||||
yes) bt=true ;;
|
||||
no) bt=false ;;
|
||||
*) AC_MSG_ERROR([bad value ${enableval} for --enable-bt]) ;;
|
||||
esac],[bt=false])
|
||||
|
||||
AM_CONDITIONAL([CONFIG_FTM_BT], [test x$bt = xtrue -o x$all = xtrue])
|
||||
|
||||
|
||||
AC_ARG_ENABLE(target,
|
||||
[AS_HELP_STRING([--enable-target=TARGET], [Specify the target product to build])],
|
||||
[TARGET=$enableval],
|
||||
[TARGET=none]
|
||||
)
|
||||
AM_CONDITIONAL([MDM_ROME], [test "x$TARGET" = "xmdm9607" -o "x$TARGET" = "xmdm9635" -o "x$TARGET" = "xmdm9640" -o "x$TARGET" = "xmdmcalifornium"])
|
||||
AM_CONDITIONAL([MDM_PRONTO], [test "x$TARGET" = "xapq8009" -o "x$TARGET" = "xapq8017" -o "x$TARGET" = "xapq8053"])
|
||||
|
||||
# Checks for typedefs, structures, and compiler characteristics.
|
||||
AC_HEADER_STDBOOL
|
||||
AC_HEADER_STDC
|
||||
AC_C_INLINE
|
||||
AC_TYPE_INT64_T
|
||||
AC_TYPE_PID_T
|
||||
AC_TYPE_SIZE_T
|
||||
AC_TYPE_SSIZE_T
|
||||
AC_TYPE_UINT16_T
|
||||
AC_TYPE_UINT32_T
|
||||
AC_TYPE_UINT8_T
|
||||
|
||||
# Checks for library functions.
|
||||
AC_FUNC_ERROR_AT_LINE
|
||||
AC_FUNC_FORK
|
||||
AC_FUNC_MALLOC
|
||||
|
||||
AC_CONFIG_FILES([ \
|
||||
Makefile \
|
||||
])
|
||||
AC_OUTPUT
|
||||
|
||||
585
feeds/ipq95xx/ftm/src/ftm_ant.c
Executable file
585
feeds/ipq95xx/ftm/src/ftm_ant.c
Executable file
@@ -0,0 +1,585 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM ANT Source File
|
||||
|
||||
Description
|
||||
FTM platform independent processing of packet data
|
||||
|
||||
# Copyright (c) 2010-2012 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
05/16/12 ankurn Adding support for ANT commands
|
||||
11/28/12 c_ssugas implements efficent method for Ant cmd transfer
|
||||
and implements Rx thread for event handling.
|
||||
===========================================================================*/
|
||||
#include "event.h"
|
||||
#include "msg.h"
|
||||
#include "log.h"
|
||||
|
||||
#include "diag_lsm.h"
|
||||
#include "diagpkt.h"
|
||||
#include "diagcmd.h"
|
||||
#include "diag.h"
|
||||
#include "termios.h"
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <stdlib.h>
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
#include <stdbool.h>
|
||||
#include <dlfcn.h>
|
||||
#include "bt_vendor_qcom.h"
|
||||
#include "ftm_ant_common.h"
|
||||
#include "ftm_bt.h"
|
||||
#include <string.h>
|
||||
#include "hidl_client.h"
|
||||
|
||||
#ifdef ANDROID
|
||||
#include <cutils/properties.h>
|
||||
#endif
|
||||
|
||||
#ifdef ANDROID
|
||||
extern int soc_type;
|
||||
#endif
|
||||
|
||||
#define ANT_CTRL_PACKET_TYPE 0x0c
|
||||
#define ANT_DATA_PACKET_TYPE 0x0e
|
||||
|
||||
#define UNUSED(x) (void)(x)
|
||||
|
||||
int init_transport_ant(int on);
|
||||
// The following functions are dummy implementations of the callbacks required by libbt-vendor.
|
||||
static void vendor_fwcfg_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_scocfg_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_lpm_vnd_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_audio_state_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void* vendor_alloc(int size) {
|
||||
UNUSED(size);
|
||||
return NULL;
|
||||
}
|
||||
static void vendor_dealloc(void *p_buf) {
|
||||
UNUSED(p_buf);
|
||||
}
|
||||
static uint8_t vendor_xmit_cb(uint16_t opcode, void *p_buf, tINT_CMD_CBACK p_cback) {
|
||||
UNUSED(opcode);
|
||||
UNUSED(p_buf);
|
||||
UNUSED(p_cback);
|
||||
return 0;
|
||||
}
|
||||
static void vendor_epilog_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_a2dp_offload_cb(bt_vendor_op_result_t result, bt_vendor_opcode_t op, unsigned char handle) {
|
||||
UNUSED(result);
|
||||
UNUSED(op);
|
||||
UNUSED(handle);
|
||||
}
|
||||
|
||||
// This struct is used to regsiter the dummy callbacks with libbt-vendor
|
||||
static bt_vendor_interface_t *vendor_interface=NULL;
|
||||
static const bt_vendor_callbacks_t vendor_callbacks = {
|
||||
sizeof(bt_vendor_callbacks_t),
|
||||
vendor_fwcfg_cb,
|
||||
vendor_scocfg_cb,
|
||||
vendor_lpm_vnd_cb,
|
||||
vendor_audio_state_cb,
|
||||
vendor_alloc,
|
||||
vendor_dealloc,
|
||||
vendor_xmit_cb,
|
||||
vendor_epilog_cb,
|
||||
vendor_a2dp_offload_cb
|
||||
};
|
||||
|
||||
/* Transport file descriptor */
|
||||
int fd_transport_ant_cmd;
|
||||
extern int first_ant_command;
|
||||
/* Reader thread handle */
|
||||
pthread_t ant_cmd_thread_hdl;
|
||||
/* Pipe file descriptors for cancelling read operation */
|
||||
int ant_pipefd[2];
|
||||
|
||||
/* Enable FTM_DEBUG to turn on Debug messages */
|
||||
//#define FTM_DEBUG
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_ant_readerthread
|
||||
|
||||
DESCRIPTION
|
||||
Thread Routine to perfom asynchrounous handling of events coming on Smd
|
||||
descriptor. It invokes a callback to the FTM ANT layer to intiate a request
|
||||
to read event bytes.
|
||||
|
||||
DEPENDENCIES
|
||||
The LifeTime of ReaderThraad is dependent on the status returned by the
|
||||
call to ftm_ant_qcomm_handle_event
|
||||
|
||||
RETURN VALUE
|
||||
RETURN NULL
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void *ftm_ant_readerthread(void *ptr)
|
||||
{
|
||||
boolean status = FALSE;
|
||||
int retval;
|
||||
fd_set readfds;
|
||||
int buf;
|
||||
|
||||
UNUSED(ptr);
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_readerthread --> \n");
|
||||
#endif
|
||||
do
|
||||
{
|
||||
FD_ZERO(&readfds);
|
||||
FD_SET(fd_transport_ant_cmd, &readfds);
|
||||
FD_SET(ant_pipefd[0],&readfds);
|
||||
retval = select((fd_transport_ant_cmd>ant_pipefd[0]?fd_transport_ant_cmd
|
||||
:ant_pipefd[0]) + 1, &readfds, NULL, NULL, NULL);
|
||||
if(retval == -1)
|
||||
{
|
||||
printf("select failed\n");
|
||||
break;
|
||||
}
|
||||
if(FD_ISSET(ant_pipefd[0],&readfds))
|
||||
{
|
||||
#ifdef FTM_DEBUG
|
||||
printf("Pipe descriptor set\n");
|
||||
#endif
|
||||
read(ant_pipefd[0],&buf,1);
|
||||
if(buf == 1)
|
||||
break;
|
||||
}
|
||||
if(FD_ISSET(fd_transport_ant_cmd,&readfds))
|
||||
{
|
||||
#ifdef FTM_DEBUG
|
||||
printf("Read descriptor set\n");
|
||||
#endif
|
||||
status = ftm_ant_qcomm_handle_event();
|
||||
if(TRUE != status)
|
||||
break;
|
||||
}
|
||||
}
|
||||
while(1);
|
||||
#ifdef FTM_DEBUG
|
||||
printf("\nReader thread exited\n");
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_ant_open_channel
|
||||
|
||||
DESCRIPTION
|
||||
Open the SMD transport associated with ANT
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
int value indicating success or failure
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
static bool ftm_ant_open_channel()
|
||||
{
|
||||
struct termios term_port;
|
||||
int opts;
|
||||
|
||||
printf("%s: \n",__func__ );
|
||||
switch (soc_type)
|
||||
{
|
||||
case BT_SOC_ROME:
|
||||
case BT_SOC_CHEROKEE:
|
||||
case BT_SOC_NAPIER:
|
||||
//Use hidl_client_initialize for chip initialization
|
||||
if (hidl_client_initialize(MODE_ANT,&fd_transport_ant_cmd) == false) {
|
||||
printf("%s: HIDL client initialization failed, opening port with init_transpor_ant\n", __func__);
|
||||
//Use libbt-vendor for chip initialization
|
||||
fd_transport_ant_cmd = init_transport_ant(TRUE);
|
||||
if (fd_transport_ant_cmd == -1) {
|
||||
printf("%s: ANT Device open Failed, fd:%d: \n", __func__, fd_transport_ant_cmd);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case BT_SOC_AR3K:
|
||||
case BT_SOC_SMD:
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_open_channel --> \n");
|
||||
#endif
|
||||
|
||||
fd_transport_ant_cmd = open(APPS_RIVA_ANT_CMD_CH, (O_RDWR));
|
||||
if (fd_transport_ant_cmd == -1) {
|
||||
printf("Ant Device open Failed= %d\n ", fd_transport_ant_cmd);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Blocking Read
|
||||
opts = fcntl(fd_transport_ant_cmd, F_GETFL);
|
||||
if (opts < 0) {
|
||||
perror("fcntl(F_GETFL)");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
opts = opts & (~O_NONBLOCK);
|
||||
if (fcntl(fd_transport_ant_cmd, F_SETFL, opts) < 0) {
|
||||
perror("fcntl(F_SETFL)");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
if (tcgetattr(fd_transport_ant_cmd, &term_port) < 0)
|
||||
close(fd_transport_ant_cmd);
|
||||
cfmakeraw(&term_port);
|
||||
if (tcsetattr(fd_transport_ant_cmd, TCSANOW, &term_port) < 0) {
|
||||
printf("\n Error while setting attributes\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
tcflush(fd_transport_ant_cmd, TCIFLUSH);
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_open_channel success \n");
|
||||
#endif
|
||||
break;
|
||||
default:
|
||||
ALOGE("%s:Unknown soc type.",__func__);
|
||||
return false;
|
||||
}
|
||||
if (pipe(ant_pipefd) == -1)
|
||||
{
|
||||
printf("pipe create error");
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
/* Creating read thread which listens for various masks & pkt requests */
|
||||
pthread_create( &ant_cmd_thread_hdl, NULL, ftm_ant_readerthread, NULL);
|
||||
return true;
|
||||
}
|
||||
|
||||
int init_transport_ant(int on) {
|
||||
|
||||
void *so_handle;
|
||||
unsigned char bdaddr[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06};
|
||||
int fd[CH_MAX], powerstate, ret = -1;
|
||||
char ref_count[PROPERTY_VALUE_MAX];
|
||||
int value;
|
||||
|
||||
if (on) {
|
||||
so_handle = dlopen("libbt-vendor.so", RTLD_NOW);
|
||||
if (!so_handle)
|
||||
{
|
||||
ALOGE("Failed to load vendor component");
|
||||
return -1;
|
||||
}
|
||||
|
||||
vendor_interface = (bt_vendor_interface_t *) dlsym(so_handle, "BLUETOOTH_VENDOR_LIB_INTERFACE");
|
||||
if (!vendor_interface)
|
||||
{
|
||||
ALOGE("Failed to accesst bt vendor interface");
|
||||
return -1;
|
||||
}
|
||||
|
||||
vendor_interface->init(&vendor_callbacks, bdaddr);
|
||||
|
||||
ALOGI("Turn On BT power");
|
||||
powerstate = BT_VND_PWR_ON;
|
||||
ret = vendor_interface->op(BT_VND_OP_POWER_CTRL, &powerstate);
|
||||
if (ret < 0)
|
||||
{
|
||||
ALOGE("Failed to turn on power from bt vendor interface");
|
||||
return -1;
|
||||
}
|
||||
for (int i = 0; i < CH_MAX; i++)
|
||||
fd[i] = -1;
|
||||
|
||||
#ifdef ANDROID
|
||||
if (soc_type == BT_SOC_ROME || soc_type == BT_SOC_CHEROKEE || soc_type == BT_SOC_NAPIER) {
|
||||
/*call ANT_USERIAL_OPEN to get ANT handle*/
|
||||
ret = vendor_interface->op((bt_vendor_opcode_t)BT_VND_OP_ANT_USERIAL_OPEN, fd);
|
||||
}
|
||||
#else
|
||||
#ifdef BT_SOC_TYPE_ROME
|
||||
/*call ANT_USERIAL_OPEN to get ANT handle*/
|
||||
ret = vendor_interface->op((bt_vendor_opcode_t)BT_VND_OP_ANT_USERIAL_OPEN, fd);
|
||||
#endif
|
||||
#endif
|
||||
ALOGE("ret value: %d", ret);
|
||||
if (ret != 1)
|
||||
{
|
||||
ALOGE("Failed to get fd from bt vendor interface");
|
||||
return -1;
|
||||
} else {
|
||||
ALOGE("FD: %x", fd[0]);
|
||||
return fd[0];
|
||||
}
|
||||
} else {
|
||||
if (vendor_interface) {
|
||||
ALOGE("Close and cleanup the interfaces");
|
||||
|
||||
#ifdef ANDROID
|
||||
if (soc_type == BT_SOC_ROME || soc_type == BT_SOC_CHEROKEE || soc_type == BT_SOC_NAPIER) {
|
||||
int ret = vendor_interface->op((bt_vendor_opcode_t)BT_VND_OP_ANT_USERIAL_CLOSE, NULL);
|
||||
}
|
||||
#else
|
||||
#ifdef BT_SOC_TYPE_ROME
|
||||
int ret = vendor_interface->op((bt_vendor_opcode_t)BT_VND_OP_ANT_USERIAL_CLOSE, NULL);
|
||||
#endif
|
||||
#endif
|
||||
|
||||
ALOGE("ret value: %d", ret);
|
||||
ALOGI("Turn off BT power");
|
||||
powerstate = BT_VND_PWR_OFF;
|
||||
ret = vendor_interface->op(BT_VND_OP_POWER_CTRL, &powerstate);
|
||||
if (ret < 0)
|
||||
{
|
||||
ALOGE("Failed to turn off power from bt vendor interface");
|
||||
return -1;
|
||||
}
|
||||
vendor_interface->cleanup();
|
||||
vendor_interface = NULL;
|
||||
return 0;
|
||||
} else {
|
||||
|
||||
ALOGE("Not able to find vendor interface handle");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_log_send_msg
|
||||
|
||||
DESCRIPTION
|
||||
Processes the buffer sent and sends it to the libdiag for sending the Cmd
|
||||
response
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
NIL
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void ftm_ant_log_send_msg(const uint8 *pEventBuf,int event_bytes)
|
||||
{
|
||||
int result = log_status(LOG_FTM_VER_2_C);
|
||||
ftm_ant_log_pkt_type* ftm_ant_log_pkt_ptr = NULL;
|
||||
|
||||
if((pEventBuf == NULL) || (event_bytes == 0))
|
||||
return;
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_log_send_msg --> \n");
|
||||
#endif
|
||||
if(result == 1)
|
||||
{
|
||||
ftm_ant_log_pkt_ptr = (ftm_ant_log_pkt_type *)log_alloc(LOG_FTM_VER_2_C,
|
||||
FTM_ANT_LOG_HEADER_SIZE + (event_bytes-1));
|
||||
if(ftm_ant_log_pkt_ptr != NULL)
|
||||
{
|
||||
/* FTM ANT Log PacketID */
|
||||
ftm_ant_log_pkt_ptr->ftm_log_id = FTM_ANT_LOG_PKT_ID;
|
||||
memcpy((void *)ftm_ant_log_pkt_ptr->data,(void *)pEventBuf,event_bytes);
|
||||
log_commit( ftm_ant_log_pkt_ptr );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_ant_dispatch
|
||||
|
||||
DESCRIPTION
|
||||
Dispatch routine for the various FM Rx/Tx commands. Copies the data into
|
||||
a global union data structure before calling the processing routine
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
A Packed structre pointer including the response to the FTM FM packet
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void * ftm_ant_dispatch(ftm_ant_pkt_type *ant_ftm_pkt, uint16 pkt_len)
|
||||
{
|
||||
ftm_ant_generic_sudo_res *rsp;
|
||||
int err = 0, i;
|
||||
int data_len = ant_ftm_pkt->cmd_data_len;
|
||||
bool resp = false;
|
||||
unsigned char *pdata = NULL, *ptemp;
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_dispatch --> \n");
|
||||
#endif
|
||||
|
||||
UNUSED(pkt_len);
|
||||
|
||||
if (first_ant_command == 0) {
|
||||
first_ant_command = 1;
|
||||
ftm_ant_open_channel();
|
||||
}
|
||||
|
||||
rsp = (ftm_ant_generic_sudo_res*)diagpkt_subsys_alloc( DIAG_SUBSYS_FTM
|
||||
, FTM_ANT_CMD_CODE
|
||||
, sizeof(ftm_ant_generic_sudo_res)
|
||||
);
|
||||
if(rsp == NULL)
|
||||
{
|
||||
printf("%s Failed to allocate resource",__func__);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
switch (soc_type) {
|
||||
//Rome shares the same UART transport for ANT and BT. Hence, to differenciate the
|
||||
//packets by controller, adding one extra byte for ANT data and control packets
|
||||
case BT_SOC_ROME:
|
||||
case BT_SOC_CHEROKEE:
|
||||
case BT_SOC_NAPIER:
|
||||
data_len = data_len + 1;
|
||||
pdata = (unsigned char *) malloc(data_len);
|
||||
if (pdata == NULL) {
|
||||
ALOGE("Failed to allocate the memory for ANT command packet");
|
||||
rsp->result = FTM_ANT_FAIL;
|
||||
return (void *) rsp;
|
||||
}
|
||||
//To be compatible with Legacy, SMD based PLs, send all the packets
|
||||
//with cmd opcode 0x0c
|
||||
pdata[0] = 0x0c;
|
||||
memcpy(pdata+1, ant_ftm_pkt->data, data_len-1);
|
||||
err = write(fd_transport_ant_cmd, pdata, data_len);
|
||||
ptemp = pdata;
|
||||
break;
|
||||
case BT_SOC_AR3K:
|
||||
case BT_SOC_SMD:
|
||||
/* Send the packet to controller and send a dummy response back to host*/
|
||||
err = write(fd_transport_ant_cmd, ant_ftm_pkt->data, data_len);
|
||||
ptemp = ant_ftm_pkt->data;
|
||||
break;
|
||||
default:
|
||||
ALOGE("%s:Unknown soc type", __func__);
|
||||
break;
|
||||
}
|
||||
if (err == data_len) {
|
||||
rsp->result = FTM_ANT_SUCCESS;
|
||||
printf("ANT CMD: ");
|
||||
for (i = 1; i<data_len; i++) {
|
||||
printf("%02X ", ptemp[i]);
|
||||
}
|
||||
printf("\n");
|
||||
} else {
|
||||
rsp->result = FTM_ANT_FAIL;
|
||||
printf("FTM ANT write fail len: %d\n", err);
|
||||
}
|
||||
if (pdata)
|
||||
free(pdata);
|
||||
return (void *)rsp;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_qcomm_handle_event
|
||||
|
||||
DESCRIPTION
|
||||
Routine called by the HAL layer reader thread to process the HCI events
|
||||
The post conditions of each event is covered in a state machine pattern
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
boolean ftm_ant_qcomm_handle_event ()
|
||||
{
|
||||
boolean status = TRUE;
|
||||
int nbytes,i,len =0;
|
||||
int event_type;
|
||||
ftm_ant_generic_res *res = (ftm_ant_generic_res *)diagpkt_subsys_alloc(
|
||||
DIAG_SUBSYS_FTM
|
||||
, FTM_ANT_CMD_CODE
|
||||
, sizeof(ftm_ant_generic_res)
|
||||
);
|
||||
if(res == NULL)
|
||||
{
|
||||
printf("%s Failed to allocate res",__func__);
|
||||
tcflush(fd_transport_ant_cmd, TCIFLUSH);
|
||||
return FALSE;
|
||||
}
|
||||
#ifdef FTM_DEBUG
|
||||
printf("ftm_ant_hci_qcomm_handle_event --> \n");
|
||||
#endif
|
||||
|
||||
/* Read length and event type of Ant Resp event*/
|
||||
nbytes = read(fd_transport_ant_cmd, (void *)res->evt, 2);
|
||||
if(nbytes <= 0) {
|
||||
status = FALSE;
|
||||
printf("ftm_ant_qcomm_handle_event read fail len=%d\n", nbytes);
|
||||
return status;
|
||||
}
|
||||
event_type = res->evt[0];
|
||||
len = res->evt[1];
|
||||
#ifdef FTM_DEBUG
|
||||
printf(" event type =%d\n",event_type);
|
||||
printf("length of event =%d\n",len);
|
||||
#endif
|
||||
/* Read out the Ant Resp event*/
|
||||
if (len <= (int)sizeof(res->evt))
|
||||
{
|
||||
nbytes = read(fd_transport_ant_cmd, (void *)res->evt, len);
|
||||
if (nbytes != len) {
|
||||
res->result = FTM_ANT_FAIL;
|
||||
status = FALSE;
|
||||
printf("ftm_ant_qcomm_handle_event read fail len=%d\n", nbytes);
|
||||
}
|
||||
else {
|
||||
res->result = FTM_ANT_SUCCESS;
|
||||
printf("ANT EVT: ");
|
||||
for (i=0; i<nbytes; i++) {
|
||||
printf("%02X ", res->evt[i]);
|
||||
}
|
||||
printf("\n");
|
||||
ftm_ant_log_send_msg(res->evt, nbytes);
|
||||
tcflush(fd_transport_ant_cmd, TCIOFLUSH);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
res->result = FTM_ANT_FAIL;
|
||||
status = FALSE;
|
||||
printf("ftm_ant_qcomm_handle_event read fail len=%d is more than sizeof(res->evt)=%d\n", len, (int)sizeof(res->evt));
|
||||
}
|
||||
return status;
|
||||
}
|
||||
124
feeds/ipq95xx/ftm/src/ftm_ant_common.h
Executable file
124
feeds/ipq95xx/ftm/src/ftm_ant_common.h
Executable file
@@ -0,0 +1,124 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM FM Common Header File
|
||||
|
||||
Description
|
||||
Global Data declarations of the ftm ant component.
|
||||
|
||||
# Copyright (c) 2012,2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
05/16/2012 ankurn Adding support for ANT+
|
||||
11/28/12 c_ssugas Adds data structures and macro for ant log event support.
|
||||
===========================================================================*/
|
||||
|
||||
#ifdef CONFIG_FTM_ANT
|
||||
|
||||
#include "diagpkt.h"
|
||||
#include "log.h"
|
||||
#include "ftm_bt_common.h"
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
#define APPS_RIVA_ANT_CMD_CH "/dev/smd5"
|
||||
#define APPS_RIVA_ANT_DATA_CH "/dev/smd6"
|
||||
|
||||
#define FTM_ANT_CMD_CODE 94
|
||||
#define OPCODE_OFFSET 5
|
||||
|
||||
#define FTM_ANT_LOG_HEADER_SIZE (sizeof(ftm_ant_log_pkt_type) - 1)
|
||||
#define FTM_ANT_LOG_PKT_ID 0x0D
|
||||
|
||||
/* FTM Log Packet - Used to send back the event of a ANT Command */
|
||||
typedef PACKED struct
|
||||
{
|
||||
log_hdr_type hdr;
|
||||
word ftm_log_id; /* FTM log id */
|
||||
byte data[1]; /* Variable length payload,
|
||||
look at FTM log id for contents */
|
||||
} ftm_ant_log_pkt_type;
|
||||
|
||||
/* Generic result, used for any command that only returns an error code */
|
||||
typedef enum {
|
||||
FTM_ANT_FAIL,
|
||||
FTM_ANT_SUCCESS,
|
||||
} ftm_ant_api_result_type;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
} ftm_ant_generic_sudo_res;
|
||||
|
||||
|
||||
/* Generic Response */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header; /*Diag header*/
|
||||
uint8 evt[18]; /*allocates memory to hold longest valid event */
|
||||
char result; /* result */
|
||||
}__attribute__((packed)) ftm_ant_generic_res;
|
||||
|
||||
/* FTM ANT request type */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_cmd_code_type cmd_code;
|
||||
diagpkt_subsys_id_type subsys_id;
|
||||
diagpkt_subsys_cmd_code_type subsys_cmd_code;
|
||||
uint8 cmd_id; /* command id (required) */
|
||||
uint8 cmd_data_len;
|
||||
byte data[1];
|
||||
}__attribute__((packed))ftm_ant_pkt_type;
|
||||
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_ant_dispatch
|
||||
|
||||
DESCRIPTION
|
||||
Dispatch routine for the various ANT commands. Copies the data into
|
||||
a global union data structure before calling the processing routine
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
A Packed structre pointer including the response to the FTM ANT packet
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
void * ftm_ant_dispatch(ftm_ant_pkt_type *ftm_ant_pkt, uint16 length );
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_ant_qcomm_handle_event
|
||||
|
||||
DESCRIPTION
|
||||
Handler for the various ANT Events received. Sends data as log packets
|
||||
using diag to upper layers.
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Status value TRUE if event received successfuly
|
||||
otherwise returns status value FALSE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
boolean ftm_ant_qcomm_handle_event ();
|
||||
|
||||
#endif /* CONFIG_FTM_ANT */
|
||||
2013
feeds/ipq95xx/ftm/src/ftm_bt.c
Executable file
2013
feeds/ipq95xx/ftm/src/ftm_bt.c
Executable file
File diff suppressed because it is too large
Load Diff
289
feeds/ipq95xx/ftm/src/ftm_bt.h
Executable file
289
feeds/ipq95xx/ftm/src/ftm_bt.h
Executable file
@@ -0,0 +1,289 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT Task Header File
|
||||
|
||||
Description
|
||||
Global Data declarations of the ftm bt component.
|
||||
|
||||
# Copyright (c) 2010-2011, 2013-2014 by Qualcomm Technologies, Inc.
|
||||
# All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
09/28/11 rrr Moved peristent NV item related APIs to CPP,
|
||||
for having BD address being programmed twice if previous
|
||||
BD address was random generated.
|
||||
09/03/11 agaja Added support for NV_READ and NV_WRITE Commands to write
|
||||
onto Persist File system
|
||||
02/08/11 braghave Changes to read the HCI commands from a binary file for
|
||||
non-Android case
|
||||
06/18/10 rakeshk Created a header file to hold the definitons for ftm bt
|
||||
task
|
||||
===========================================================================*/
|
||||
|
||||
#ifdef CONFIG_FTM_BT
|
||||
|
||||
#include "diagpkt.h"
|
||||
#include <sys/types.h>
|
||||
#ifdef USE_LIBSOCCFG
|
||||
#include "btqsocnvm.h"
|
||||
#include "btqsocnvmutils.h"
|
||||
#endif
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
** Definitions and Declarations
|
||||
** ------------------------------------------------------------------------- */
|
||||
|
||||
#define FTM_BT_CMD_CODE 4 /* BT FTM Command code */
|
||||
#define FTM_FM_CMD_CODE 28 /* FM FTM Command code */
|
||||
#define HCI_EVT_HDR_SIZE 3
|
||||
#define HCI_ACL_HDR_SIZE 5
|
||||
#define PROTOCOL_BYTE_SIZE 1
|
||||
#define HC_VS_MAX_CMD_EVENT 260
|
||||
#define HC_VS_MAX_ACL 1200
|
||||
#define FTM_BT_HCI_USER_CMD 0
|
||||
#define BT_FTM_CMD_RSP_LEN 1100
|
||||
#define FTM_BT_DRV_START_TEST 0xA
|
||||
|
||||
/* MACROS for pin connectivty test*/
|
||||
#define BT_CMD_SLIM_TEST 0xBFAC
|
||||
#define LOOP_BACK_EVT_OGF 0x02
|
||||
#define LOOP_BACK_EVT_OCF 0x18
|
||||
#define LOOP_BACK_EVT_STATUS 0x00
|
||||
#define LOOP_BACK_EVT_OGF_BIT 0x04
|
||||
#define LOOP_BACK_EVT_OCF_BIT 0x05
|
||||
#define LOOP_BACK_EVT_STATUS_BIT 0x06
|
||||
|
||||
|
||||
#define FTM_BT_LOG_HEADER_SIZE (sizeof(ftm_bt_log_pkt_type) - 1)
|
||||
|
||||
|
||||
/* Vendor Specific command codes */
|
||||
#define BT_QSOC_EDL_CMD_OPCODE (0xFC00)
|
||||
#define BT_QSOC_NVM_ACCESS_OPCODE (0xFC0B)
|
||||
|
||||
#define BT_QSOC_EDL_CMD_CODE (0x00)
|
||||
#define BT_QSOC_NVM_ACCESS_CODE (0x0B)
|
||||
#define BT_QSOC_VS_EDL_APPVER_RESP (0x02)
|
||||
|
||||
#ifndef HC_VS_MAX_CMD_EVENT
|
||||
#define HC_VS_MAX_CMD_EVENT 260
|
||||
#endif /* HC_VS_MAX_CMD_EVENT */
|
||||
|
||||
#define BT_QSOC_MAX_NVM_CMD_SIZE 0x64 /* Maximum size config (NVM) cmd */
|
||||
#define BT_QSOC_MAX_BD_ADDRESS_SIZE 0x06 /**< Length of BT Address */
|
||||
|
||||
#ifndef HCI_CMD_HDR_SIZE
|
||||
#define HCI_CMD_HDR_SIZE 4
|
||||
#endif /* HCI_CMD_HDR_SIZE */
|
||||
|
||||
#ifndef HCI_EVT_HDR_SIZE
|
||||
#define HCI_EVT_HDR_SIZE 3
|
||||
#endif /* HCI_EVT_HDR_SIZE */
|
||||
|
||||
#define FTM_BT_LOG_PKT_ID 0x01
|
||||
|
||||
|
||||
#define BT_HCI_CMD_PKT 0x01
|
||||
#define BT_HCI_ACL_PKT 0x02
|
||||
#define BT_HCI_EVT_PKT 0x04
|
||||
|
||||
#define BT_HCI_CMD_CMPLT_EVT 0x0E
|
||||
#define FM_HCI_EVT_PKT 0x14
|
||||
#define FM_HCI_CMD_PKT 0x11
|
||||
|
||||
extern int boardtype;
|
||||
|
||||
/* VS command structure */
|
||||
typedef struct
|
||||
{
|
||||
uint8 vs_cmd_len;
|
||||
uint8 vs_cmd_data[BT_QSOC_MAX_NVM_CMD_SIZE];
|
||||
} bt_qsoc_cfg_tbl_struct_type;
|
||||
|
||||
/* First Commamd structure - Used to store the First command for later
|
||||
* processing
|
||||
*/
|
||||
struct first_cmd
|
||||
{
|
||||
uint8 *cmd_buf;
|
||||
int cmd_len;
|
||||
};
|
||||
|
||||
/* FTM Global State - Enum defines the various states of the FTM
|
||||
* module
|
||||
*/
|
||||
typedef enum ftm_state
|
||||
{
|
||||
FTM_SOC_NOT_INITIALISED,
|
||||
FTM_SOC_READ_APP_VER,
|
||||
FTM_SOC_READ_HW_VER,
|
||||
FTM_SOC_POKE8_TBL_INIT,
|
||||
FTM_SOC_DOWNLOAD_NVM,
|
||||
FTM_SOC_DOWNLOAD_NVM_EFS,
|
||||
FTM_SOC_SLEEP_DISABLE,
|
||||
FTM_SOC_RESET,
|
||||
FTM_SOC_INITIALISED
|
||||
}ftm_state;
|
||||
/* FTM CMD status */
|
||||
typedef enum ftm_log_packet_type
|
||||
{
|
||||
FTM_USER_CMD_PASS,
|
||||
FTM_USER_CMD_FAIL,
|
||||
FTM_HCI_EVENT
|
||||
}ftm_log_packet_type;
|
||||
|
||||
/* FTM Log Packet - Used to send back the event of a HCI Command */
|
||||
typedef PACKED struct
|
||||
{
|
||||
log_hdr_type hdr;
|
||||
byte data[1]; /* Variable length payload,
|
||||
look at FTM log id for contents */
|
||||
} ftm_bt_log_pkt_type;
|
||||
|
||||
|
||||
/* FTM (BT) PKT Header */
|
||||
typedef PACKED struct
|
||||
{
|
||||
word cmd_id; /* command id (required) */
|
||||
word cmd_data_len; /* request pkt data length, excluding the diag and ftm headers
|
||||
(optional, set to 0 if not used)*/
|
||||
word cmd_rsp_pkt_size; /* rsp pkt size, size of response pkt if different then req pkt
|
||||
(optional, set to 0 if not used)*/
|
||||
} ftm_bt_cmd_header_type;
|
||||
|
||||
/* Bluetooth FTM packet */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
ftm_bt_cmd_header_type ftm_hdr;
|
||||
byte data[1];
|
||||
} ftm_bt_pkt_type;
|
||||
|
||||
/* SoC Cfg open Struct*/
|
||||
#ifdef USE_LIBSOCCFG
|
||||
typedef struct
|
||||
{
|
||||
bt_qsoc_config_params_struct_type run_time_params;
|
||||
bt_qsoc_enum_nvm_mode nvm_mode;
|
||||
bt_qsoc_enum_type soc_type;
|
||||
}ftm_bt_soc_runtime_cfg_type;
|
||||
#endif
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_err_timedout
|
||||
|
||||
DESCRIPTION
|
||||
This routine triggers the shutdown of the HCI and Power resources in case
|
||||
a HCI command previously sent times out.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN NIL
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
void ftm_bt_err_timedout();
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_dispatch
|
||||
|
||||
DESCRIPTION
|
||||
Processes the BT FTM packet and dispatches the command to FTM HCI driver
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
NIL,The error in the Command Processing is sent to the DIAG App on PC via
|
||||
log packets
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void ftm_bt_dispatch(void *ftm_bt_pkt ,int cmd_len );
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION bt_hci_send_ftm_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the HCI cmd and invokes the sub routines to intialise
|
||||
the SoC if needed based on the state of the FTM module
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
boolean ftm_bt_hci_send_cmd
|
||||
(
|
||||
uint8 * cmd_buf, /* pointer to Cmd */
|
||||
uint16 cmd_len /* Cmd length */
|
||||
);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION bt_hci_hal_vs_sendcmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the VS HCI cmd and constucts the HCI packet before
|
||||
calling bt_hci_send_ftm_cmd routine
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_hal_vs_sendcmd
|
||||
(
|
||||
uint16 opcode, /* Opcode */
|
||||
uint8 *pCmdBuffer, /* Pointer to Payload*/
|
||||
uint8 nSize /* Cmd Size */
|
||||
);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION isLatestTarget
|
||||
|
||||
DESCRIPTION
|
||||
For all the target/solution which has Bluedroid as stack and libbt-vendor as
|
||||
vendor initialization component considered as latest target
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean isLatestTarget();
|
||||
char *get_current_time(void);
|
||||
#endif /* CONFIG_FTM_BT */
|
||||
115
feeds/ipq95xx/ftm/src/ftm_bt_common.h
Executable file
115
feeds/ipq95xx/ftm/src/ftm_bt_common.h
Executable file
@@ -0,0 +1,115 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT Commom Header File
|
||||
|
||||
Description
|
||||
The header file includes helper enums for request_status and bt_power_state.
|
||||
|
||||
# Copyright (c) 2010-2011, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
09/28/11 rrr Common utility API abstracted,
|
||||
06/18/10 rakeshk Created a header file to hold the helper enums for
|
||||
request_status and bt_power_state
|
||||
========================================================================*/
|
||||
|
||||
#ifdef CONFIG_FTM_BT
|
||||
|
||||
#include "event.h"
|
||||
#include "msg.h"
|
||||
#include "log.h"
|
||||
|
||||
#include "diag_lsm.h"
|
||||
#include <sys/types.h>
|
||||
|
||||
#ifndef __FTM_BT_COMMON_H__
|
||||
|
||||
#define __FTM_BT_COMMON_H__
|
||||
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
|
||||
/* request_status - enum to encapuslate the status of a HAL request*/
|
||||
typedef enum request_status
|
||||
{
|
||||
STATUS_SUCCESS,
|
||||
STATUS_FAIL,
|
||||
STATUS_NO_RESOURCES,
|
||||
STATUS_SHORT_WRITE,
|
||||
STATUS_SHORT_READ
|
||||
}request_status;
|
||||
|
||||
/* request_status - enum to encapuslate the possible statea of BT power*/
|
||||
typedef enum bt_power_state
|
||||
{
|
||||
BT_OFF = 0x30, /* Its the value 0 to be input to rfkill driver */
|
||||
BT_ON = 0x31 /* ASCII value for '1'*/
|
||||
}bt_power_state;
|
||||
|
||||
typedef enum
|
||||
{
|
||||
FTM_BT_DRV_NO_ERR = 0,
|
||||
FTM_BT_DRV_CONN_TEST_FAILS,
|
||||
FTM_BT_DRV_QSOC_POWERUP_FAILS,
|
||||
FTM_BT_DRV_RX_PKT_TYPE_NOT_SUPPORTED,
|
||||
FTM_BT_DRV_SIO_OPEN_FAILS,
|
||||
FTM_BT_DRV_NO_SOC_RSP_TOUT,
|
||||
FTM_BT_DRV_BAD_NVM,
|
||||
#ifdef BT_NV_SUPPORT
|
||||
FTM_BT_NV_READ_FAIL,
|
||||
FTM_BT_NV_WRITE_FAIL,
|
||||
#endif
|
||||
FTM_BT_DRV_UNKNOWN_ERR
|
||||
} ftm_bt_drv_err_state_type;
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_qcomm_handle_event
|
||||
|
||||
DESCRIPTION
|
||||
Routine called by the HAL layer reader thread to process the HCI events
|
||||
The post conditions of each event is covered in a state machine pattern
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_qcomm_handle_event();
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_log_send_msg
|
||||
|
||||
DESCRIPTION
|
||||
Processes the buffer sent and sends it to the libdiag for sending the Cmd
|
||||
response
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
NIL
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
void ftm_log_send_msg(const uint8 *pEventBuf,int event_bytes);
|
||||
#endif //__FTM_BT_COMMON_H__
|
||||
#endif /* CONFIG_FTM_BT */
|
||||
161
feeds/ipq95xx/ftm/src/ftm_bt_hci_hal.h
Executable file
161
feeds/ipq95xx/ftm/src/ftm_bt_hci_hal.h
Executable file
@@ -0,0 +1,161 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT HCI PFAL Header File
|
||||
|
||||
Description
|
||||
Warpper API definitions of the ftm bt hci hal component.
|
||||
|
||||
# Copyright (c) 2010 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created a header file to hold the wrapper HAL
|
||||
definitions for HCI UART control
|
||||
===========================================================================*/
|
||||
|
||||
#include "ftm_bt_common.h"
|
||||
#include "ftm_bt_hci_pfal.h"
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_set_transport
|
||||
|
||||
DESCRIPTION
|
||||
sets the type of transport based on the msm type
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
returns the type of transport
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_hal_set_transport()
|
||||
{
|
||||
return ftm_bt_hci_pfal_set_transport();
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_deinit_transport
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which intiatea a De-intialise of UART/SMD
|
||||
resources with PFAL layer and returns the status of the PFAL operation
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_hal_deinit_transport()
|
||||
{
|
||||
return ftm_bt_hci_pfal_deinit_transport();
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_init_transport
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which intiatea a intialise of UART/SMD
|
||||
resources with PFAL layer and returns the status of the PFAL operation
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_hal_init_transport (int mode)
|
||||
{
|
||||
return ftm_bt_hci_pfal_init_transport(mode);
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_nwrite
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which intiates a write operation
|
||||
with the PFAL layer and returns the status of the PFAL operation.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_hal_nwrite(uint8 *buf, int size)
|
||||
{
|
||||
return ftm_bt_hci_pfal_nwrite(buf,size);
|
||||
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_nread
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which intiates a read operation
|
||||
with the PFAL layer and returns the status of the PFAL operation.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_hal_nread(uint8 *buf, int size)
|
||||
{
|
||||
return ftm_bt_hci_pfal_nread(buf,size);
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_hal_changebaudrate
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which intiatea a UART baud rate change
|
||||
with the PFAL layer and returns the status of the PFAL request.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
TRUE if SUCCESS, else FAIL
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_hal_changebaudrate (uint32 new_baud)
|
||||
{
|
||||
return ftm_bt_hci_pfal_changebaudrate(new_baud);
|
||||
}
|
||||
|
||||
177
feeds/ipq95xx/ftm/src/ftm_bt_hci_pfal.h
Executable file
177
feeds/ipq95xx/ftm/src/ftm_bt_hci_pfal.h
Executable file
@@ -0,0 +1,177 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT HCI PFAL Header File
|
||||
|
||||
Description
|
||||
PFAL API declarations of the ftm bt hci pfal component.
|
||||
|
||||
# Copyright (c) 2010 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created a header file to hold the PFAL declarations for
|
||||
HCI UART programming
|
||||
===========================================================================*/
|
||||
#include "ftm_bt_common.h"
|
||||
|
||||
#ifndef __FTM_BT_HCI_PFAL_H__
|
||||
#define __FTM_BT_HCI_PFAL_H__
|
||||
|
||||
#define PIN_CON_CMD_OGF 0xFC
|
||||
#define PIN_CON_CMD_OCF 0x0C
|
||||
#define PIN_CON_CMD_SUB_OP 0x38
|
||||
#define PIN_CON_INTERFACE_ID 0x01
|
||||
#define PIN_CON_EVENT_LEN 0x06
|
||||
#define EXT_PIN_CON_LEN 0x02
|
||||
|
||||
#define PIN_CON_CMD_OCF_BIT 0x01
|
||||
#define PIN_CON_CMD_OGF_BIT 0x02
|
||||
#define PIN_CON_CMD_SUBOP_BIT 0x04
|
||||
#define PIN_CON_CMD_INTER_BIT 0x05
|
||||
|
||||
#define PIN_CON_EVT_OGF_BIT 0x05
|
||||
#define PIN_CON_EVT_OCF_BIT 0x04
|
||||
#define PIN_CON_EVT_SUB_OP_BIT 0x07
|
||||
#define PIN_CON_INTERFACE_ID_EVT_BIT 0x08
|
||||
#define PIN_CON_EVENT_LEN_BIT 0x02
|
||||
#define PIN_CON_EVT_STATUS_BIT 0x06
|
||||
|
||||
#define LOG_TAG "ftmdaemon"
|
||||
|
||||
#define PRI_INFO " I"
|
||||
#define PRI_WARN " W"
|
||||
#define PRI_ERROR " E"
|
||||
#define PRI_DEBUG " D"
|
||||
#define PRI_VERB " V"
|
||||
|
||||
#define ALOG(pri, tag, fmt, arg...) fprintf(stderr, tag pri ": " fmt"\n", ##arg)
|
||||
#define ALOGV(fmt, arg...) ALOG(PRI_VERB, LOG_TAG, fmt, ##arg)
|
||||
#define ALOGD(fmt, arg...) ALOG(PRI_DEBUG, LOG_TAG, fmt, ##arg)
|
||||
#define ALOGI(fmt, arg...) ALOG(PRI_INFO, LOG_TAG, fmt, ##arg)
|
||||
#define ALOGW(fmt, arg...) ALOG(PRI_WARN, LOG_TAG, fmt, ##arg)
|
||||
#define ALOGE(fmt, arg...) ALOG(PRI_ERROR, LOG_TAG, fmt, ##arg)
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_set_transport
|
||||
|
||||
DESCRIPTION
|
||||
sets the type of transport based on the msm type
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
returns the type of transport
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_pfal_set_transport(void);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_deinit_transport
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to de-intialise the UART/SMD resource.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_deinit_transport();
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_init_transport
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to intialise the UART/SMD resources.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_init_transport ();
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_nwrite
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to write the data in the argument to the UART/SMD
|
||||
port intialised.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_nwrite(uint8 *buf, int size);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_nread
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to read data from the UART/SMD port intialised into
|
||||
the buffer passed in argument.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_nread(uint8 *buf, int size);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_changebaudrate
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to intiate a change in baud rate
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
TRUE if SUCCESS, else FALSE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_pfal_changebaudrate (uint32 new_baud);
|
||||
|
||||
#endif //__FTM_BT_HCI_PFAL_H__
|
||||
674
feeds/ipq95xx/ftm/src/ftm_bt_hci_pfal_linux.c
Executable file
674
feeds/ipq95xx/ftm/src/ftm_bt_hci_pfal_linux.c
Executable file
@@ -0,0 +1,674 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM Platform specfic HCI UART/SMD File
|
||||
|
||||
Description
|
||||
Platform specific routines to program the UART/SMD descriptors
|
||||
|
||||
# Copyright (c) 2010-2011, 2013 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/07/11 bneti Add support smd support for msm8960
|
||||
06/18/10 rakeshk Created a source file to implement platform specific
|
||||
routines for UART
|
||||
07/07/10 rakeshk Removed the conversion of 3.2 Mbps baud rate
|
||||
01/07/10 rakeshk Added support for verbose logging of Cmd and events
|
||||
===========================================================================*/
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/select.h>
|
||||
#include <termios.h>
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
#include <dlfcn.h>
|
||||
#include "bt_vendor_lib.h"
|
||||
#include "ftm_bt_hci_pfal.h"
|
||||
#include "ftm_common.h"
|
||||
#include <string.h>
|
||||
#include "log.h"
|
||||
#include <cutils/properties.h>
|
||||
#include "hidl_client.h"
|
||||
|
||||
#ifdef ANDROID
|
||||
#define VENDOR_LIB "libbt-vendor.so"
|
||||
#else
|
||||
#define VENDOR_LIB "libbt-vendor.so.0"
|
||||
#endif
|
||||
|
||||
uint8_t is_slim_bus_test = 0;
|
||||
#define UNUSED(x) (void)(x)
|
||||
|
||||
/*identify the transport type*/
|
||||
static char *transport_dev;
|
||||
|
||||
typedef enum {
|
||||
BT_SOC_DEFAULT = 0,
|
||||
BT_SOC_SMD = BT_SOC_DEFAULT,
|
||||
BT_SOC_AR3K,
|
||||
BT_SOC_ROME,
|
||||
BT_SOC_CHEROKEE,
|
||||
BT_SOC_NAPIER,
|
||||
/* Add chipset type here */
|
||||
BT_SOC_RESERVED
|
||||
} bt_soc_type;
|
||||
|
||||
static void vendor_fwcfg_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_scocfg_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_lpm_vnd_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_audio_state_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void* vendor_alloc(int size) {
|
||||
UNUSED(size);
|
||||
return NULL;
|
||||
}
|
||||
static void vendor_dealloc(void *p_buf) {
|
||||
UNUSED(p_buf);
|
||||
}
|
||||
static uint8_t vendor_xmit_cb(uint16_t opcode, void *p_buf, tINT_CMD_CBACK p_cback) {
|
||||
UNUSED(opcode);
|
||||
UNUSED(p_buf);
|
||||
UNUSED(p_cback);
|
||||
return 0;
|
||||
}
|
||||
static void vendor_epilog_cb(bt_vendor_op_result_t result) {
|
||||
UNUSED(result);
|
||||
}
|
||||
static void vendor_a2dp_offload_cb(bt_vendor_op_result_t result, bt_vendor_opcode_t op, unsigned char handle) {
|
||||
UNUSED(result);
|
||||
UNUSED(op);
|
||||
UNUSED(handle);
|
||||
}
|
||||
|
||||
|
||||
bt_vendor_interface_t *vendor_interface=NULL;
|
||||
static const bt_vendor_callbacks_t vendor_callbacks = {
|
||||
sizeof(bt_vendor_callbacks_t),
|
||||
vendor_fwcfg_cb,
|
||||
vendor_scocfg_cb,
|
||||
vendor_lpm_vnd_cb,
|
||||
vendor_audio_state_cb,
|
||||
vendor_alloc,
|
||||
vendor_dealloc,
|
||||
vendor_xmit_cb,
|
||||
vendor_epilog_cb,
|
||||
vendor_a2dp_offload_cb
|
||||
};
|
||||
|
||||
|
||||
/*BT HS UART TTY DEVICE */
|
||||
#define BT_HS_UART_DEVICE "/dev/ttyHS0"
|
||||
|
||||
/*BT RIVA-SMD CHANNELS */
|
||||
#define APPS_RIVA_BT_ACL_CH "/dev/smd2"
|
||||
#define APPS_RIVA_BT_CMD_CH "/dev/smd3"
|
||||
|
||||
/* Variables to identify the platform */
|
||||
char transport_type[PROPERTY_VALUE_MAX];
|
||||
static boolean is_transportSMD;
|
||||
|
||||
extern int soc_type;
|
||||
|
||||
/* Reader thread handle */
|
||||
pthread_t hci_cmd_thread_hdl;
|
||||
/* Pipe file descriptors for cancelling read operation */
|
||||
int pipefd[2];
|
||||
/* Transport file descriptor */
|
||||
int fd_transport;
|
||||
/* Starting baud rate to init the tty device */
|
||||
int starting_baud = 115200;
|
||||
/* Verbose output monitoring variable */
|
||||
int verbose = 1;
|
||||
/* Defintion to convert integer baud rate to the
|
||||
* Data type understood by tty device
|
||||
*/
|
||||
#define BAUDCLAUS(i) case (i): return ( B##i )
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION convert_baud
|
||||
|
||||
DESCRIPTION
|
||||
Routine to convert the integer baud rate to type speed_t
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
Converted Baud rate, else default 0
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
static speed_t convert_baud(uint32 baud_rate)
|
||||
{
|
||||
switch (baud_rate)
|
||||
{
|
||||
BAUDCLAUS(50);
|
||||
BAUDCLAUS(75);
|
||||
BAUDCLAUS(110);
|
||||
BAUDCLAUS(134);
|
||||
BAUDCLAUS(150);
|
||||
BAUDCLAUS(200);
|
||||
BAUDCLAUS(300);
|
||||
BAUDCLAUS(600);
|
||||
BAUDCLAUS(1200);
|
||||
BAUDCLAUS(1800);
|
||||
BAUDCLAUS(2400);
|
||||
BAUDCLAUS(4800);
|
||||
BAUDCLAUS(9600);
|
||||
BAUDCLAUS(19200);
|
||||
BAUDCLAUS(38400);
|
||||
BAUDCLAUS(57600);
|
||||
BAUDCLAUS(115200);
|
||||
BAUDCLAUS(230400);
|
||||
BAUDCLAUS(460800);
|
||||
BAUDCLAUS(500000);
|
||||
BAUDCLAUS(576000);
|
||||
BAUDCLAUS(921600);
|
||||
BAUDCLAUS(1000000);
|
||||
BAUDCLAUS(1152000);
|
||||
BAUDCLAUS(1500000);
|
||||
BAUDCLAUS(2000000);
|
||||
BAUDCLAUS(2500000);
|
||||
BAUDCLAUS(3000000);
|
||||
BAUDCLAUS(3500000);
|
||||
BAUDCLAUS(4000000);
|
||||
|
||||
default: return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_readerthread
|
||||
|
||||
DESCRIPTION
|
||||
Thread Routine to perfom asynchrounous handling of events coming on Uart/Smd
|
||||
descriptor. It invokes a callback to the FTM BT layer to intiate a request
|
||||
to read event bytes.
|
||||
|
||||
DEPENDENCIES
|
||||
The LifeTime of ReaderThraad is dependent on the status returned by the
|
||||
call to ftm_bt_hci_qcomm_handle_event
|
||||
|
||||
RETURN VALUE
|
||||
RETURN NIL
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void *ftm_readerthread(void *ptr)
|
||||
{
|
||||
UNUSED(ptr);
|
||||
boolean status = FALSE;
|
||||
int retval;
|
||||
fd_set readfds;
|
||||
int buf;
|
||||
|
||||
do
|
||||
{
|
||||
FD_ZERO(&readfds);
|
||||
FD_SET(fd_transport, &readfds);
|
||||
FD_SET(pipefd[0],&readfds);
|
||||
retval = select((pipefd[0] > fd_transport? pipefd[0] : fd_transport) + 1,
|
||||
&readfds, NULL, NULL, NULL);
|
||||
if(retval == -1)
|
||||
{
|
||||
printf("select failed\n");
|
||||
break;
|
||||
}
|
||||
if(FD_ISSET(pipefd[0],&readfds))
|
||||
{
|
||||
#ifdef FTM_DEBUG
|
||||
printf("Pipe descriptor set\n");
|
||||
#endif
|
||||
read(pipefd[0],&buf,1);
|
||||
if(buf == 1)
|
||||
break;
|
||||
}
|
||||
if(FD_ISSET(fd_transport,&readfds))
|
||||
{
|
||||
#ifdef FTM_DEBUG
|
||||
printf("Read descriptor set\n");
|
||||
#endif
|
||||
status = ftm_bt_hci_qcomm_handle_event();
|
||||
if(TRUE != status)
|
||||
break;
|
||||
}
|
||||
}
|
||||
while(1);
|
||||
#ifdef FTM_DEBUG
|
||||
printf("\nReader thread exited\n");
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_pfal_set_transport
|
||||
|
||||
DESCRIPTION
|
||||
sets the type of transport based on the msm type
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
returns the type of transport
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_pfal_set_transport(void)
|
||||
{
|
||||
if (soc_type == BT_SOC_ROME || soc_type == BT_SOC_CHEROKEE || soc_type == BT_SOC_NAPIER) {
|
||||
strlcpy(transport_type, "uart", sizeof(transport_type));
|
||||
printf("[%s]: Transport type is: %s\n", __FUNCTION__, transport_type);
|
||||
is_transportSMD = 0;
|
||||
transport_dev = BT_HS_UART_DEVICE;
|
||||
} else {
|
||||
strlcpy(transport_type, "smd", sizeof(transport_type));
|
||||
printf("[%s]: Transport type is: %s\n", __FUNCTION__, transport_type);
|
||||
is_transportSMD = 1;
|
||||
transport_dev = APPS_RIVA_BT_CMD_CH;
|
||||
}
|
||||
return is_transportSMD;
|
||||
}
|
||||
|
||||
|
||||
int init_transport_bdroid(boolean on) {
|
||||
|
||||
void *so_handle;
|
||||
unsigned char bdaddr[] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06};
|
||||
request_status st;
|
||||
int fd[CH_MAX], powerstate, ret;
|
||||
|
||||
if (on) {
|
||||
so_handle = dlopen(VENDOR_LIB, RTLD_NOW);
|
||||
if (!so_handle)
|
||||
{
|
||||
ALOGE("Failed to load vendor component %s", dlerror());
|
||||
return -1;
|
||||
}
|
||||
|
||||
vendor_interface = (bt_vendor_interface_t *) dlsym(so_handle, "BLUETOOTH_VENDOR_LIB_INTERFACE");
|
||||
if (!vendor_interface)
|
||||
{
|
||||
ALOGE("Failed to accesst bt vendor interface");
|
||||
return -1;
|
||||
}
|
||||
|
||||
vendor_interface->init(&vendor_callbacks, bdaddr);
|
||||
|
||||
ALOGI("Turn On BT power");
|
||||
powerstate = BT_VND_PWR_ON;
|
||||
ret = vendor_interface->op(BT_VND_OP_POWER_CTRL, &powerstate);
|
||||
if (ret < 0)
|
||||
{
|
||||
ALOGE("Failed to turn on power from bt vendor interface");
|
||||
return -1;
|
||||
}
|
||||
ret = vendor_interface->op(BT_VND_OP_USERIAL_OPEN, fd);
|
||||
ALOGE("ret value: %d", ret);
|
||||
/* This is just a hack; needs to be removed */
|
||||
ret = 1;
|
||||
ALOGE("setting ret value to 1 manually");
|
||||
if (ret != 1)
|
||||
{
|
||||
ALOGE("Failed to get fd from bt vendor interface");
|
||||
return -1;
|
||||
} else {
|
||||
ALOGE("FD: %x", fd[0]);
|
||||
return fd[0];
|
||||
}
|
||||
} else {
|
||||
if (vendor_interface) {
|
||||
ALOGE("Close and cleanup the interfaces");
|
||||
int ret = vendor_interface->op(BT_VND_OP_USERIAL_CLOSE, NULL);
|
||||
|
||||
ALOGE("ret value: %d", ret);
|
||||
vendor_interface->cleanup();
|
||||
return 0;
|
||||
} else {
|
||||
|
||||
ALOGE("Not able to find vendor interface handle");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_deinit_transport
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to de-intialise the UART/SMD resource.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Closes the TTY/SMD file descriptor and sets the descriptor value to -1
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
The Close of the descriptor will trigger a failure in the Reader Thread
|
||||
and hence cause a Deinit of the ReaderThread
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_deinit_transport()
|
||||
{
|
||||
int buf = 1;
|
||||
write(pipefd[1],&buf,1);
|
||||
if(!isLatestTarget())
|
||||
{
|
||||
close(fd_transport);
|
||||
fd_transport = -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
//Use libbt-vendor for chip de-initialization
|
||||
init_transport_bdroid(FALSE);
|
||||
}
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_init_uart
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to intialise the UART/SMD resources.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Opens the TTY/SMD device file descriptor, congiures the TTY/SMD device for CTS/RTS
|
||||
flow control,sets 115200 for TTY as the default baudrate and starts the Reader
|
||||
Thread
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_init_transport(int mode)
|
||||
{
|
||||
struct termios term;
|
||||
if(isLatestTarget())
|
||||
{
|
||||
printf("%s: ",__func__ );
|
||||
//Use hidl_client_initialize for chip initialization
|
||||
if (hidl_client_initialize(mode, &fd_transport) == false) {
|
||||
printf("%s: HIDL client initialization failed \n", __func__);
|
||||
return STATUS_NO_RESOURCES;
|
||||
}
|
||||
printf("%s: , fd:%d: ", __func__, fd_transport);
|
||||
}
|
||||
else
|
||||
{
|
||||
fd_transport = open(transport_dev, (O_RDWR | O_NOCTTY));
|
||||
|
||||
if (-1 == fd_transport)
|
||||
{
|
||||
return STATUS_NO_RESOURCES;
|
||||
}
|
||||
|
||||
if (tcflush(fd_transport, TCIOFLUSH) < 0)
|
||||
{
|
||||
close(fd_transport);
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
|
||||
if (tcgetattr(fd_transport, &term) < 0)
|
||||
{
|
||||
close(fd_transport);
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
|
||||
cfmakeraw(&term);
|
||||
/* Set RTS/CTS HW Flow Control*/
|
||||
term.c_cflag |= (CRTSCTS | CLOCAL);
|
||||
|
||||
if (tcsetattr(fd_transport, TCSANOW, &term) < 0)
|
||||
{
|
||||
close(fd_transport);
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
|
||||
/* Configure the /dev/ttyHS0 device to operate at 115200.
|
||||
no need for msm8960 as it is using smd as transport
|
||||
*/
|
||||
if (!is_transportSMD)
|
||||
if (ftm_bt_hci_pfal_changebaudrate(starting_baud) == FALSE)
|
||||
{
|
||||
close(fd_transport);
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
}
|
||||
if (pipe(pipefd) == -1)
|
||||
{
|
||||
printf("pipe create error");
|
||||
return STATUS_FAIL;
|
||||
}
|
||||
if(mode != MODE_FM) {
|
||||
/* Creating read thread which listens for various masks & pkt requests */
|
||||
pthread_create( &hci_cmd_thread_hdl, NULL, ftm_readerthread, NULL);
|
||||
}
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_nwrite
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to write the data in the argument to the UART/SMD
|
||||
port intialised.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Write the buffer to the tty device and ensure it is completely written
|
||||
In case of short write report error to the BT FTM layer.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_nwrite(uint8 *buf, int size)
|
||||
{
|
||||
int tx_bytes = 0, nwrite;
|
||||
int i = 0, buf_size = size;
|
||||
uint8 loop_back_cmd[6] = {0x1, 0x02, 0x18, 0x01, 0x01};
|
||||
/*hci packet is not required to carry the Packet indicator (for UART interfaces) for msm8960
|
||||
as it is using share memory interface */
|
||||
int hci_uart_pkt_ind = 0;
|
||||
|
||||
if(fd_transport < 0)
|
||||
return STATUS_NO_RESOURCES;
|
||||
if ( buf[PIN_CON_CMD_OGF_BIT] == PIN_CON_CMD_OGF &&
|
||||
buf[PIN_CON_CMD_OCF_BIT] == PIN_CON_CMD_OCF &&
|
||||
(size > PIN_CON_CMD_SUBOP_BIT) &&
|
||||
buf[PIN_CON_CMD_SUBOP_BIT] == PIN_CON_CMD_SUB_OP &&
|
||||
(size > PIN_CON_CMD_INTER_BIT) &&
|
||||
buf[PIN_CON_CMD_INTER_BIT] == PIN_CON_INTERFACE_ID)
|
||||
{
|
||||
is_slim_bus_test = 1;
|
||||
printf("\nPinConnectivityTest: Sending loopback command to SOC before initiasing slimbus\n");
|
||||
strlcpy(buf, loop_back_cmd, size);
|
||||
}
|
||||
do
|
||||
{
|
||||
nwrite = write(fd_transport, (buf + hci_uart_pkt_ind + tx_bytes), (size - hci_uart_pkt_ind - tx_bytes));
|
||||
|
||||
if (nwrite < 0)
|
||||
{
|
||||
printf("Error while writing ->\n");
|
||||
return STATUS_SHORT_WRITE;
|
||||
}
|
||||
if (nwrite == 0)
|
||||
{
|
||||
printf("ftm_bt_hci_pfal_nwrite: zero-length write\n");
|
||||
return STATUS_SHORT_WRITE;
|
||||
}
|
||||
|
||||
tx_bytes += nwrite;
|
||||
size -= nwrite;
|
||||
} while (tx_bytes < size - hci_uart_pkt_ind);
|
||||
|
||||
if (verbose == 1)
|
||||
{
|
||||
printf("[%s] %s: CMD:", get_current_time(), __FUNCTION__);
|
||||
for (i = 0; i < buf_size; i++)
|
||||
{
|
||||
printf(" %02X", buf[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_nread
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to read data from the UART/SMD port intialised into
|
||||
the buffer passed in argument.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Read from the tty device into the buffer and ensure the read request is
|
||||
completed, in case of short read report error to the BT FTM layer.
|
||||
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_hci_pfal_nread(uint8 *buf, int size)
|
||||
{
|
||||
int rx_bytes = 0, nread;
|
||||
|
||||
if(fd_transport < 0)
|
||||
return STATUS_NO_RESOURCES;
|
||||
|
||||
do
|
||||
{
|
||||
nread = read(fd_transport, (buf + rx_bytes), (size - rx_bytes));
|
||||
if (nread < 0)
|
||||
{
|
||||
printf("Error while reading ->\n");
|
||||
return STATUS_SHORT_READ;
|
||||
}
|
||||
|
||||
rx_bytes += nread;
|
||||
|
||||
} while (rx_bytes < size);
|
||||
|
||||
return STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_hci_pfal_changebaudrate
|
||||
|
||||
DESCRIPTION
|
||||
Platform specific routine to intiate a change in baud rate
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Convert the Baud rate passed to the speed_t type and program the
|
||||
Baud rate change after ensuring all transmit is drained at the
|
||||
current baud rate
|
||||
|
||||
DEPENDENCIES
|
||||
It is expected that the Upper layer will intiate a Flow Off to the
|
||||
BT SoC, to signal the stop of receive if the baud rate change is
|
||||
initiated while SoC init is in progress
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
TRUE if SUCCESS, else FALSE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_hci_pfal_changebaudrate (uint32 new_baud)
|
||||
{
|
||||
struct termios term;
|
||||
boolean status = TRUE;
|
||||
speed_t baud_code;
|
||||
speed_t actual_baud_code;
|
||||
|
||||
if (tcgetattr(fd_transport, &term) < 0)
|
||||
{
|
||||
printf("Can't get port settings\n");
|
||||
status = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
baud_code = convert_baud(new_baud);
|
||||
(void) cfsetospeed(&term, baud_code);
|
||||
if (tcsetattr(fd_transport, TCSADRAIN, &term) < 0) /* don't change speed until last write done */
|
||||
{
|
||||
printf("bt_hci_qcomm_pfal_changebaudrate: tcsetattr:\n");
|
||||
status = FALSE;
|
||||
}
|
||||
/* make sure that we reportedly got the speed we tried to set */
|
||||
if (1 < verbose)
|
||||
{
|
||||
if (tcgetattr(fd_transport, &term) < 0)
|
||||
{
|
||||
printf("bt_hci_qcomm_pfal_changebaudrate: tcgetattr:\n");
|
||||
status = FALSE;
|
||||
}
|
||||
if (baud_code != (actual_baud_code = cfgetospeed(&term)))
|
||||
{
|
||||
printf("bt_hci_qcomm_pfal_changebaudrate: new baud %u FAILED, got 0x%x\n", new_baud, actual_baud_code);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("bt_hci_qcomm_pfal_changebaudrate: new baud %u SUCCESS, got 0x%x\n", new_baud, actual_baud_code);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
278
feeds/ipq95xx/ftm/src/ftm_bt_persist.cpp
Executable file
278
feeds/ipq95xx/ftm/src/ftm_bt_persist.cpp
Executable file
@@ -0,0 +1,278 @@
|
||||
/*==========================================================================
|
||||
|
||||
BT persist NV items access source file
|
||||
|
||||
Description
|
||||
Read/Write APIs for retreiving NV items from persist memory.
|
||||
|
||||
# Copyright (c) 2011-12 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
05/25/12 jav Added FTM log that will display bt address while testing.
|
||||
09/27/11 rrr Moved persist related API for c/c++ compatibility, needed
|
||||
for random BD address to be persistent across target
|
||||
reboots.
|
||||
==========================================================================*/
|
||||
|
||||
#include "ftm_bt_persist.h"
|
||||
#include <semaphore.h>
|
||||
|
||||
#ifdef BT_NV_SUPPORT
|
||||
#include "bt_nv.h"
|
||||
|
||||
/* Semaphore shared by the Event handler and main thread */
|
||||
extern sem_t semaphore_cmd_complete;
|
||||
/*Flag to manage the verbose output */
|
||||
extern int verbose;
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_send_nv_read_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the nv read command
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_send_nv_read_cmd
|
||||
(
|
||||
uint8 * cmd_buf, /* pointer to Cmd */
|
||||
uint16 cmd_len /* Cmd length */
|
||||
)
|
||||
{
|
||||
nv_persist_item_type my_nv_item;
|
||||
nv_persist_stat_enum_type cmd_result;
|
||||
boolean result = TRUE;
|
||||
|
||||
if(cmd_len >1)
|
||||
{
|
||||
switch(*(cmd_buf+1))
|
||||
{
|
||||
case NV_BD_ADDR_I:
|
||||
cmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_READ_F, NV_BD_ADDR_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
if (verbose > 0)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to get BD_ADDR from NV, code %d\n", cmd_result);
|
||||
}
|
||||
/* Send fail response */
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* copy bytes */
|
||||
event_buf_nv_read_response[0] = FTM_BT_CMD_NV_READ;
|
||||
event_buf_nv_read_response[1] = NV_BD_ADDR_I;
|
||||
event_buf_nv_read_response[7] = my_nv_item.bd_addr[5];
|
||||
event_buf_nv_read_response[6] = my_nv_item.bd_addr[4];
|
||||
event_buf_nv_read_response[5] = my_nv_item.bd_addr[3];
|
||||
event_buf_nv_read_response[4] = my_nv_item.bd_addr[2];
|
||||
event_buf_nv_read_response[3] = my_nv_item.bd_addr[1];
|
||||
event_buf_nv_read_response[2] = my_nv_item.bd_addr[0];
|
||||
/* send BD_ADDR in the response */
|
||||
fprintf (stderr, "nv_cmd_remote got NV_BD_ADDR_I from NV: %x:%x:%x:%x:%x:%x\n",
|
||||
(unsigned int) my_nv_item.bd_addr[5], (unsigned int) my_nv_item.bd_addr[4],
|
||||
(unsigned int) my_nv_item.bd_addr[3], (unsigned int) my_nv_item.bd_addr[2],
|
||||
(unsigned int) my_nv_item.bd_addr[1], (unsigned int) my_nv_item.bd_addr[0]);
|
||||
|
||||
ftm_log_send_msg((const uint8 *)event_buf_nv_read_response,nv_read_response_size);
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
|
||||
case NV_BT_SOC_REFCLOCK_TYPE_I:
|
||||
cmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_READ_F, NV_BT_SOC_REFCLOCK_TYPE_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
if (verbose > 0)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to get BD_ADDR from NV, code %d\n", cmd_result);
|
||||
}
|
||||
/* Send fail response */
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
event_buf_nv_read_response[0] = FTM_BT_CMD_NV_READ;
|
||||
event_buf_nv_read_response[1] = NV_BT_SOC_REFCLOCK_TYPE_I;
|
||||
event_buf_nv_read_response[2] = (uint8) my_nv_item.bt_soc_refclock_type ;
|
||||
event_buf_nv_read_response[7] = 0x0;
|
||||
event_buf_nv_read_response[6] = 0x0;
|
||||
event_buf_nv_read_response[5] = 0x0;
|
||||
event_buf_nv_read_response[4] = 0x0;
|
||||
event_buf_nv_read_response[3] = 0x0;
|
||||
fprintf (stderr, "nv_cmd_remote got NV_BT_SOC_REFCLOCK_TYPE_I from NV: 0x%x\n",
|
||||
(unsigned int) my_nv_item.bt_soc_refclock_type);
|
||||
ftm_log_send_msg((const uint8 *)event_buf_nv_read_response,nv_read_response_size);
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
|
||||
case NV_BT_SOC_CLK_SHARING_TYPE_I:
|
||||
cmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_READ_F, NV_BT_SOC_CLK_SHARING_TYPE_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
if (verbose > 0)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to get CLK_SHARING from NV, code %d\n", cmd_result);
|
||||
}
|
||||
/* Send fail response */
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
event_buf_nv_read_response[0] = FTM_BT_CMD_NV_READ;
|
||||
event_buf_nv_read_response[1] = NV_BT_SOC_CLK_SHARING_TYPE_I;
|
||||
event_buf_nv_read_response[2] = (uint8) my_nv_item.bt_soc_clk_sharing_type ;
|
||||
event_buf_nv_read_response[7] = 0x0;
|
||||
event_buf_nv_read_response[6] = 0x0;
|
||||
event_buf_nv_read_response[5] = 0x0;
|
||||
event_buf_nv_read_response[4] = 0x0;
|
||||
event_buf_nv_read_response[3] = 0x0;
|
||||
fprintf (stderr, "nv_cmd_remote got NV_BT_SOC_CLK_SHARING_TYPE_I from NV: 0x%x\n",
|
||||
(unsigned int) my_nv_item.bt_soc_refclock_type);
|
||||
ftm_log_send_msg((const uint8 *)event_buf_nv_read_response,nv_read_response_size);
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
}
|
||||
if(result == FALSE)
|
||||
ftm_log_send_msg(event_buf_nv_read_response_fail,nv_read_response_size_fail);
|
||||
|
||||
sem_post(&semaphore_cmd_complete);
|
||||
return result;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_send_nv_write_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the nv write command
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_send_nv_write_cmd
|
||||
(
|
||||
uint8 * cmd_buf, /* pointer to Cmd */
|
||||
uint16 cmd_len /* Cmd length */
|
||||
)
|
||||
{
|
||||
nv_persist_item_type my_nv_item;
|
||||
nv_persist_stat_enum_type cmd_result;
|
||||
boolean result = TRUE;
|
||||
if(cmd_len >1)
|
||||
{
|
||||
switch(*(cmd_buf+1))
|
||||
{
|
||||
case NV_BD_ADDR_I:
|
||||
memcpy(&my_nv_item.bd_addr, (cmd_buf+2), NV_BD_ADDR_SIZE);
|
||||
cmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_WRITE_F, NV_BD_ADDR_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
if (verbose > 0)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to get BD_ADDR from NV, code %d\n", cmd_result);
|
||||
}
|
||||
/* Send fail response */
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
|
||||
case NV_BT_SOC_REFCLOCK_TYPE_I:
|
||||
switch (*(cmd_buf+2))
|
||||
{
|
||||
case NV_PS_BT_SOC_REFCLOCK_32MHZ:
|
||||
case NV_PS_BT_SOC_REFCLOCK_19P2MHZ:
|
||||
my_nv_item.bt_soc_refclock_type = (nv_ps_bt_soc_refclock_enum_type)(*(cmd_buf+2)) ;
|
||||
break;
|
||||
default:
|
||||
fprintf (stderr, "Invalid Ref Clock option\n");
|
||||
result = FALSE;
|
||||
}
|
||||
if (result != FALSE)
|
||||
{
|
||||
cmd_result= (nv_persist_stat_enum_type)bt_nv_cmd(NV_WRITE_F, NV_BT_SOC_REFCLOCK_TYPE_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to write SOC_REFCLOCK_TYPE to NV, code %d\n", cmd_result);
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case NV_BT_SOC_CLK_SHARING_TYPE_I:
|
||||
switch (*(cmd_buf+2))
|
||||
{
|
||||
case NV_PS_BT_SOC_CLOCK_SHARING_ENABLED:
|
||||
case NV_PS_BT_SOC_CLOCK_SHARING_DISABLED:
|
||||
my_nv_item.bt_soc_clk_sharing_type = (nv_ps_bt_soc_clock_sharing_enum_type)(*(cmd_buf+2)) ;
|
||||
break;
|
||||
default:
|
||||
fprintf (stderr, "Invalid Clock Sharing option\n");
|
||||
result = FALSE;
|
||||
}
|
||||
if (result != FALSE)
|
||||
{
|
||||
cmd_result= (nv_persist_stat_enum_type)bt_nv_cmd(NV_WRITE_F, NV_BT_SOC_CLK_SHARING_TYPE_I, &my_nv_item);
|
||||
if (NV_SUCCESS != cmd_result)
|
||||
{
|
||||
fprintf (stderr, "nv_cmd_remote failed to write SOC_CLK_SHARING_TYPE to NV, code %d\n", cmd_result);
|
||||
result = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
result = TRUE;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(result == FALSE)
|
||||
{
|
||||
ftm_log_send_msg(event_buf_bt_nv_write_fail,nv_write_response_size);
|
||||
sem_post(&semaphore_cmd_complete);
|
||||
}
|
||||
else
|
||||
{
|
||||
ftm_log_send_msg((const uint8 *)event_buf_bt_nv_write_pass,nv_write_response_size);
|
||||
sem_post(&semaphore_cmd_complete);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
#endif /* End of BT_NV_SUPPORT */
|
||||
113
feeds/ipq95xx/ftm/src/ftm_bt_persist.h
Executable file
113
feeds/ipq95xx/ftm/src/ftm_bt_persist.h
Executable file
@@ -0,0 +1,113 @@
|
||||
#ifndef _FTM_BT_PERSIST_H_
|
||||
#define _FTM_BT_PERSIST_H_
|
||||
|
||||
/*==========================================================================
|
||||
|
||||
BT persist NV items access source file
|
||||
|
||||
Description
|
||||
Read/Write APIs for retreiving NV items from persist memory.
|
||||
|
||||
# Copyright (c) 2011 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
09/27/11 rrr Moved persist related API for c/c++ compatibility, needed
|
||||
for random BD address to be persistent across target
|
||||
reboots.
|
||||
==========================================================================*/
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include "ftm_bt_common.h"
|
||||
#include <string.h>
|
||||
|
||||
|
||||
#ifdef BT_NV_SUPPORT
|
||||
|
||||
#define FTM_BT_CMD_NV_READ 0xB
|
||||
#define FTM_BT_CMD_NV_WRITE 0xC
|
||||
|
||||
const uint8 nv_read_response_size = 8;
|
||||
const uint8 nv_read_response_size_fail = 2;
|
||||
const uint8 nv_write_response_size = 2;
|
||||
|
||||
/* NV Write Responses */
|
||||
const uint8 event_buf_bt_nv_write_pass[2] = { FTM_BT_CMD_NV_WRITE, FTM_BT_DRV_NO_ERR};
|
||||
const uint8 event_buf_bt_nv_write_fail[2] = { FTM_BT_CMD_NV_WRITE, FTM_BT_NV_WRITE_FAIL};
|
||||
|
||||
/* NV Read Responses */
|
||||
const uint8 event_buf_nv_read_response_fail[8] =
|
||||
{
|
||||
FTM_BT_CMD_NV_READ, FTM_BT_NV_READ_FAIL, 0x0, 0x0,0x0,0x0,0x0,0x0
|
||||
};
|
||||
|
||||
uint8 event_buf_nv_read_response[8];
|
||||
#endif /* BT_NV_SUPPORT */
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_send_nv_read_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the nv read command
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_send_nv_read_cmd
|
||||
(
|
||||
uint8 * cmd_buf, /* pointer to Cmd */
|
||||
uint16 cmd_len /* Cmd length */
|
||||
);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_send_nv_write_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Helper Routine to process the nv write command
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean ftm_bt_send_nv_write_cmd
|
||||
(
|
||||
uint8 * cmd_buf, /* pointer to Cmd */
|
||||
uint16 cmd_len /* Cmd length */
|
||||
);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* _FTM_BT_PERSIST_H_ */
|
||||
|
||||
76
feeds/ipq95xx/ftm/src/ftm_bt_power_hal.h
Executable file
76
feeds/ipq95xx/ftm/src/ftm_bt_power_hal.h
Executable file
@@ -0,0 +1,76 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT POWER HAL Header File
|
||||
|
||||
Description
|
||||
Wrapper API definitions of the ftm bt power hal component.
|
||||
|
||||
# Copyright (c) 2010 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created a header file to include the wrapper API
|
||||
definitions for BT power control
|
||||
07/07/10 rakeshk Modified the function name of BT power set HAL routine
|
||||
===========================================================================*/
|
||||
#include "ftm_bt_common.h"
|
||||
#include "ftm_bt_power_pfal.h"
|
||||
|
||||
|
||||
#ifndef __FTM_BT_POWER_HAL_H__
|
||||
#define __FTM_BT_POWER_HAL_H__
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_power_hal_set
|
||||
|
||||
DESCRIPTION
|
||||
Platform independent wrapper API which sets a BT power from PFAL
|
||||
layer and returns the status of the PFAL operation.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_power_hal_set(bt_power_state state)
|
||||
{
|
||||
return ftm_bt_power_pfal_set(state);
|
||||
}
|
||||
/*===========================================================================
|
||||
FtUNCTION ftm_bt_power_hal_check
|
||||
|
||||
DESCRIPTION
|
||||
|
||||
Platform independent wrapper API which gets the BT power from PFAL
|
||||
layer and returns the current state of the BT HW.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
Current BT power state
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
bt_power_state ftm_bt_power_hal_check()
|
||||
{
|
||||
return ftm_bt_power_pfal_check();
|
||||
}
|
||||
|
||||
#endif //__FTM_BT_POWER_HAL_H__
|
||||
71
feeds/ipq95xx/ftm/src/ftm_bt_power_pfal.h
Executable file
71
feeds/ipq95xx/ftm/src/ftm_bt_power_pfal.h
Executable file
@@ -0,0 +1,71 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT POWER PFAL Header File
|
||||
|
||||
Description
|
||||
PFAL API declarations of the ftm bt power pfal component.
|
||||
|
||||
# Copyright (c) 2010 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created a header file to hold the PFAL declarations for
|
||||
BT power programming
|
||||
07/07/10 rakeshk Modified the function name of BT power set PFAL routine
|
||||
===========================================================================*/
|
||||
#include "ftm_bt_common.h"
|
||||
|
||||
#ifndef __FTM_BT_POWER_PFAL_H__
|
||||
#define __FTM_BT_POWER_PFAL_H__
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_power_pfal_set
|
||||
|
||||
DESCRIPTION
|
||||
Platform dependent interface API which sets the BT power
|
||||
and returns the status of the toggle operation.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_power_pfal_set(bt_power_state state);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_power_pfal_check
|
||||
|
||||
DESCRIPTION
|
||||
|
||||
Platform dependent interface API which intiates a BT power read/check
|
||||
and returns the current state of the BT HW.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
Current BT power state
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
bt_power_state ftm_bt_power_pfal_check();
|
||||
|
||||
#endif
|
||||
|
||||
197
feeds/ipq95xx/ftm/src/ftm_bt_power_pfal_linux.c
Executable file
197
feeds/ipq95xx/ftm/src/ftm_bt_power_pfal_linux.c
Executable file
@@ -0,0 +1,197 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM Platform specfic BT power File
|
||||
|
||||
Description
|
||||
Platform specific routines to toggle/read the BT power state
|
||||
|
||||
# Copyright (c) 2010-2011 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created a source file to implement platform specific
|
||||
routines for BT power.
|
||||
07/07/10 rakeshk Added routine to find the sysfs entry for bluetooth in
|
||||
runtime
|
||||
07/07/10 rakeshk Added call to init the rfkill state path in case of first
|
||||
read
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include "ftm_bt_power_pfal.h"
|
||||
#include <string.h>
|
||||
|
||||
/* Bluetooth Rfkill Entry for Android */
|
||||
static char *rfkill_state_path = NULL;
|
||||
/*===========================================================================
|
||||
FUNCTION init_rfkill_path
|
||||
|
||||
DESCRIPTION
|
||||
Opens the sysfs entry for different types of rfkill and finds the one
|
||||
which matches Bluetooth by iterating through the rfkill entries
|
||||
and checking for bluetooth
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
TRUE if SUCCESS, else FALSE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean init_rfkill_path()
|
||||
{
|
||||
int fd;
|
||||
int readsize;
|
||||
int rfkillid;
|
||||
char rfkill_path[64];
|
||||
char buf[16];
|
||||
|
||||
for (rfkillid = 0; ; rfkillid++)
|
||||
{
|
||||
/* Open the different rfkill type entries and check if type macthes bluetooth */
|
||||
snprintf(rfkill_path, sizeof(rfkill_path), "/sys/class/rfkill/rfkill%d/type", rfkillid);
|
||||
fd = open(rfkill_path, O_RDONLY);
|
||||
if (fd < 0)
|
||||
{
|
||||
printf("open(%s) failed: \n", rfkill_path);
|
||||
return FALSE;
|
||||
}
|
||||
readsize = read(fd, &buf, sizeof(buf));
|
||||
close(fd);
|
||||
|
||||
if (memcmp(buf, "bluetooth", 9) == 0)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
asprintf(&rfkill_state_path, "/sys/class/rfkill/rfkill%d/state", rfkillid);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_power_pfal_set
|
||||
|
||||
DESCRIPTION
|
||||
Platform dependent interface API which sets the BT power state
|
||||
and returns the status of the toggle operation.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Opens the rfkill entry for Bleutooth and initiates a write of the value
|
||||
passed as argument.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
STATUS_SUCCESS if SUCCESS, else other reasons
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
request_status ftm_bt_power_pfal_set(bt_power_state state)
|
||||
{
|
||||
int sz;
|
||||
int fd = -1;
|
||||
request_status ret = STATUS_FAIL;
|
||||
const char buffer = state;
|
||||
if(rfkill_state_path == NULL)
|
||||
{
|
||||
if(init_rfkill_path() != TRUE)
|
||||
goto out;
|
||||
}
|
||||
|
||||
fd = open(rfkill_state_path, O_WRONLY);
|
||||
if (fd < 0)
|
||||
{
|
||||
ret = STATUS_NO_RESOURCES;
|
||||
goto out;
|
||||
}
|
||||
sz = write(fd, &buffer, 1);
|
||||
if (sz < 0)
|
||||
{
|
||||
goto out;
|
||||
}
|
||||
ret = STATUS_SUCCESS;
|
||||
|
||||
out:
|
||||
if (fd >= 0)
|
||||
close(fd);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_bt_power_pfal_check
|
||||
|
||||
DESCRIPTION
|
||||
|
||||
Platform dependent interface API which intiates a BT power read/check
|
||||
and returns the current state of the BT HW.
|
||||
|
||||
PLATFORM SPECIFIC DESCRIPTION
|
||||
Opens the rfkill entry for Bleutooth and initiates a read on the rfkill
|
||||
descriptor.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN VALUE
|
||||
Current BT power state
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
bt_power_state ftm_bt_power_pfal_check()
|
||||
{
|
||||
int sz;
|
||||
bt_power_state state= BT_OFF;
|
||||
int fd = -1;
|
||||
char buffer = '0';
|
||||
|
||||
if(rfkill_state_path == NULL)
|
||||
{
|
||||
if(init_rfkill_path() != TRUE)
|
||||
goto out;
|
||||
}
|
||||
fd = open(rfkill_state_path, O_RDONLY);
|
||||
if (fd < 0)
|
||||
{
|
||||
goto out;
|
||||
}
|
||||
sz = read(fd, &buffer, 1);
|
||||
if (sz < 0)
|
||||
{
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
if (fd >= 0)
|
||||
close(fd);
|
||||
state = (bt_power_state)buffer;
|
||||
return state;
|
||||
}
|
||||
|
||||
141
feeds/ipq95xx/ftm/src/ftm_common.h
Executable file
141
feeds/ipq95xx/ftm/src/ftm_common.h
Executable file
@@ -0,0 +1,141 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM BT HCI PFAL Header File
|
||||
|
||||
Description
|
||||
Queue insert/delete routines and data structures
|
||||
|
||||
# Copyright (c) 2010-2011, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
06/18/10 rakeshk Created
|
||||
11/09/10 rakeshk Added two APIs to perform read/write of BT Top level
|
||||
I2C registers
|
||||
===========================================================================*/
|
||||
|
||||
#if defined(CONFIG_FTM_BT) || defined(CONFIG_FTM_FM)
|
||||
#include <ftm_bt_common.h>
|
||||
#include "ftm_bt.h"
|
||||
#include <semaphore.h>
|
||||
#include <pthread.h>
|
||||
/* Semaphore shared by the Event handler and main thread */
|
||||
extern sem_t semaphore_cmd_complete;
|
||||
/* Structure used by the FTM BT/FM component to
|
||||
* queue the FTM packet contents
|
||||
*/
|
||||
|
||||
pthread_mutex_t fm_event_lock;
|
||||
pthread_cond_t fm_event_cond;
|
||||
extern int fm_passthrough;
|
||||
|
||||
typedef struct cmdQ
|
||||
{
|
||||
int command_id;/*Command id */
|
||||
void *data; /* Command data */
|
||||
boolean bt_command; /* whether BT or FM command */
|
||||
int cmd_len; /* Command length */
|
||||
struct cmdQ *next; /* pointer to next CmdQ item */
|
||||
}cmdQ;
|
||||
|
||||
/* Callback declaration for BT FTM packet processing */
|
||||
void *bt_ftm_diag_dispatch(void *req_pkt, uint16 pkt_len);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION qinsert_cmd
|
||||
|
||||
DESCRIPTION
|
||||
Command Queue insert routine. Add the FTM BT packet to the Queue
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURNS FALSE without adding queue entry in failure
|
||||
to allocate a new Queue item
|
||||
else returns TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
increments the number of commands queued
|
||||
|
||||
===========================================================================*/
|
||||
boolean qinsert_cmd(ftm_bt_pkt_type *ftm_bt_pkt);
|
||||
/*===========================================================================
|
||||
FUNCTION dequeue_send
|
||||
|
||||
DESCRIPTION
|
||||
Command Queue delete and calls HCI send routine. Dequeues the HCI data from
|
||||
the queue and sends it to HCI HAL layer.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN NIL
|
||||
|
||||
SIDE EFFECTS
|
||||
decrements the number of command queued
|
||||
|
||||
===========================================================================*/
|
||||
void dequeue_send();
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION i2c_write
|
||||
|
||||
DESCRIPTION
|
||||
Helper function to construct the I@C request to be sent to the FM I2C
|
||||
driver
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
-1 in failure,positive or zero in success
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int i2c_write
|
||||
(
|
||||
int fd,
|
||||
unsigned char offset,
|
||||
const unsigned char* buf,
|
||||
unsigned char len,
|
||||
unsigned int slave_addr
|
||||
);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION i2c_read
|
||||
|
||||
DESCRIPTION
|
||||
Helper function to construct the I2C request to read data from the FM I2C
|
||||
driver
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
-1 in failure,positive or zero in success
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int i2c_read
|
||||
(
|
||||
int fd,
|
||||
unsigned char offset,
|
||||
const unsigned char* buf,
|
||||
unsigned char len,
|
||||
unsigned int slave_addr
|
||||
);
|
||||
#endif
|
||||
43
feeds/ipq95xx/ftm/src/ftm_dbg.h
Executable file
43
feeds/ipq95xx/ftm/src/ftm_dbg.h
Executable file
@@ -0,0 +1,43 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM WLAN Source File
|
||||
|
||||
# Copyright (c) 2013-2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
#ifndef _FTM_DBG_H_
|
||||
#define _FTM_DBG_H_
|
||||
#include <stdint.h>
|
||||
|
||||
#define FTM_DBG_ERROR 0x00000001
|
||||
#define FTM_DBG_INFO 0x00000002
|
||||
#define FTM_DBG_TRACE 0x00000004
|
||||
|
||||
#define FTM_DBG_DEFAULT (FTM_DBG_ERROR)
|
||||
|
||||
extern unsigned int g_dbg_level;
|
||||
|
||||
struct ftm_config
|
||||
{
|
||||
int total_num_slots;
|
||||
uint32_t slot_id[4];
|
||||
uint32_t slot_size[4];
|
||||
};
|
||||
extern struct ftm_config ftm_cfg;
|
||||
|
||||
#ifdef DEBUG
|
||||
void current_time();
|
||||
#define DPRINTF(_level, _x...)\
|
||||
do {\
|
||||
if (g_dbg_level & (_level))\
|
||||
{\
|
||||
fprintf(stderr, _x);\
|
||||
}\
|
||||
} while (0);
|
||||
|
||||
#else
|
||||
#define DPRINTF(_level, x...) do { } while (0);
|
||||
#endif
|
||||
|
||||
#endif /* _FTM_DBG_H_ */
|
||||
3804
feeds/ipq95xx/ftm/src/ftm_fm.c
Executable file
3804
feeds/ipq95xx/ftm/src/ftm_fm.c
Executable file
File diff suppressed because it is too large
Load Diff
993
feeds/ipq95xx/ftm/src/ftm_fm_common.h
Executable file
993
feeds/ipq95xx/ftm/src/ftm_fm_common.h
Executable file
@@ -0,0 +1,993 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM FM Common Header File
|
||||
|
||||
Description
|
||||
Global Data declarations of the ftm fm component.
|
||||
|
||||
# Copyright (c) 2010-2012, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
08/03/2011 uppalas Adding support for new ftm commands
|
||||
06/18/10 rakeshk Created a header file to hold the definitons for ftm fm
|
||||
task
|
||||
07/06/10 rakeshk Clean roomed the data structures and defined data
|
||||
structures to be passed to the PFAL layers
|
||||
01/11/11 rakeshk Added support for new FTM APIS
|
||||
02/09/11 rakeshk Added support for BLER FTM APIs
|
||||
04/03/11 ananthk Added support for FM FTM Transmit APIs
|
||||
===========================================================================*/
|
||||
#ifdef CONFIG_FTM_FM
|
||||
|
||||
#include "diagpkt.h"
|
||||
#include "log.h"
|
||||
#include <sys/types.h>
|
||||
|
||||
#define FTM_FM_LOG_PKT_ID 65
|
||||
#define FTM_FM_CMD_CODE 28
|
||||
#define LOG_FTM_FM_C ((uint16) 0x14CC)
|
||||
#define FEATURE_FTM_FM_DEBUG
|
||||
#define DEFAULT_DATA_SIZE 249
|
||||
|
||||
/* FM6500 A0 chip version.
|
||||
**/
|
||||
#define FM6500_A0_VERSION (0x01010013)
|
||||
/**
|
||||
* * FM6500 2.0 chip version.
|
||||
**/
|
||||
#define FMQSOCCOM_FM6500_20_VERSION (0x01010010)
|
||||
/**
|
||||
* * FM6500 2.1 chip version.
|
||||
**/
|
||||
#define FMQSOCCOM_FM6500_21_VERSION (0x02010204)
|
||||
/**
|
||||
* WCN 2243 1.0's FM chip version.
|
||||
*/
|
||||
#define FMQSOCCOM_FM6500_WCN2243_10_VERSION (0x0302010A)
|
||||
/**
|
||||
* WCN 2243 2.0's FM chip version.
|
||||
*/
|
||||
#define FMQSOCCOM_FM6500_WCN2243_20_VERSION (0x04020205)
|
||||
|
||||
extern int chipVersion;
|
||||
|
||||
/* RDS Group processing parameters */
|
||||
#define FM_RX_RDS_GRP_RT_EBL 1
|
||||
#define FM_RX_RDS_GRP_PS_EBL 2
|
||||
#define FM_RX_RDS_GRP_AF_EBL 4
|
||||
#ifdef FM_SOC_TYPE_CHEROKEE
|
||||
#define FM_RX_RDS_GRP_PS_SIMPLE_EBL 8
|
||||
#define FM_RX_RDS_GRP_ECC_EBL 32
|
||||
#define FM_RX_RDS_GRP_PTYN_EBL 64
|
||||
#define FM_RX_RDS_GRP_RT_PLUS_EBL 128
|
||||
#else
|
||||
#define FM_RX_RDS_GRP_PS_SIMPLE_EBL 16
|
||||
#endif
|
||||
|
||||
|
||||
/* lower and upper band limits of regions */
|
||||
#define REGION_US_EU_BAND_LOW 87500
|
||||
#define REGION_US_EU_BAND_HIGH 107900
|
||||
#define REGION_JAPAN_STANDARD_BAND_LOW 76000
|
||||
#define REGION_JAPAN_STANDARD_BAND_HIGH 90000
|
||||
#define REGION_JAPAN_WIDE_BAND_LOW 90000
|
||||
#define REGION_JAPAN_WIDE_BAND_HIGH 108000
|
||||
#define V4L2_CID_PRIVATE_BASE 0x08000000
|
||||
#define MAX_RDS_PS_LENGTH 108
|
||||
#define MAX_RDS_RT_LENGTH 64
|
||||
#define V4L2_CID_PRIVATE_IRIS_RDS_GRP_COUNTERS_EXT 0x08000042
|
||||
|
||||
typedef enum {
|
||||
V4L2_CID_PRIVATE_IRIS_HLSI = (V4L2_CID_PRIVATE_BASE + 0x1d),
|
||||
V4L2_CID_PRIVATE_IRIS_SOFT_MUTE,
|
||||
V4L2_CID_PRIVATE_IRIS_RIVA_ACCS_ADDR,
|
||||
V4L2_CID_PRIVATE_IRIS_RIVA_ACCS_LEN,
|
||||
V4L2_CID_PRIVATE_IRIS_RIVA_PEEK,
|
||||
V4L2_CID_PRIVATE_IRIS_RIVA_POKE,
|
||||
V4L2_CID_PRIVATE_IRIS_SSBI_ACCS_ADDR,
|
||||
V4L2_CID_PRIVATE_IRIS_SSBI_PEEK,
|
||||
V4L2_CID_PRIVATE_IRIS_SSBI_POKE,
|
||||
V4L2_CID_PRIVATE_IRIS_TX_TONE,
|
||||
V4L2_CID_PRIVATE_IRIS_RDS_GRP_COUNTERS,
|
||||
V4L2_CID_PRIVATE_IRIS_SET_NOTCH_FILTER,
|
||||
V4L2_CID_PRIVATE_IRIS_AGC_CTRL = 0x08000043,
|
||||
V4L2_CID_PRIVATE_IRIS_AGC_STATE,
|
||||
V4L2_CID_PRIVATE_IRIS_READ_DEFAULT = 0x00980928,//using private CIDs under userclass
|
||||
V4L2_CID_PRIVATE_IRIS_WRITE_DEFAULT,
|
||||
}v4l2_cid_private_iris_t_copy;
|
||||
typedef enum
|
||||
{
|
||||
/* Total no. of PS names that can be transmitted : 12
|
||||
Width of each transmitted PS name is : 8
|
||||
Total no. of PS characters that can be transmitted : (12*8 = 96)
|
||||
*/
|
||||
MAX_TX_PS_LEN = 96,
|
||||
MAX_TX_PS_RPT_CNT = 15,
|
||||
}FmTxPSFeatures;
|
||||
|
||||
/* FTM FM command IDs */
|
||||
typedef enum
|
||||
{
|
||||
#ifdef FEATURE_FTM_FM_DEBUG
|
||||
FTM_FM_RX_SET_POWER_MODE = 13,
|
||||
FTM_FM_RX_SET_SIGNAL_THRESHOLD = 14,
|
||||
FTM_FM_RX_GET_RSSI_LIMIT = 16,
|
||||
FTM_FM_RX_GET_PS_INFO = 17,
|
||||
FTM_FM_RX_GET_RT_INFO = 18,
|
||||
FTM_FM_RX_GET_AF_INFO = 19,
|
||||
FTM_FM_RX_SEARCH_STATIONS = 20,
|
||||
FTM_FM_RX_SEARCH_RDS_STATIONS = 21,
|
||||
FTM_FM_RX_SEARCH_STATIONS_LIST = 22,
|
||||
FTM_FM_RX_CANCEL_SEARCH = 23,
|
||||
FTM_FM_RX_RDS_GROUP_PROC_OPTIONS = 25,
|
||||
FTM_FM_RX_RDS_PI_MATCH_OPTIONS = 26,
|
||||
FTM_FM_TX_GET_PS_FEATURES = 36,
|
||||
FTM_FM_TX_TX_PS_INFO = 38,
|
||||
FTM_FM_TX_STOP_PS_INFO_TX = 39,
|
||||
FTM_FM_TX_TX_RT_INFO = 40,
|
||||
FTM_FM_TX_STOP_RT_INFO_TX = 41,
|
||||
FTM_FM_RX_GET_SIGNAL_THRESHOLD = 46,
|
||||
FTM_FM_FMWAN_REG_RD = 51,
|
||||
FTM_FM_RX_GET_DEFAULTS = 62,
|
||||
FTM_FM_RX_SET_DEFAULTS = 63,
|
||||
FTM_FM_RX_GET_SINR_SAMPLES = 64,
|
||||
FTM_FM_RX_SET_SINR_SAMPLES = 65,
|
||||
FTM_FM_RX_GET_SINR_THRESHOLD = 66,
|
||||
FTM_FM_RX_SET_SINR_THRESHOLD = 67,
|
||||
FTM_FM_RX_GET_ONCHANNEL_TH = 68,
|
||||
FTM_FM_RX_SET_ONCHANNEL_TH = 69,
|
||||
FTM_FM_RX_GET_OFFCHANNEL_TH = 70,
|
||||
FTM_FM_RX_SET_OFFCHANNEL_TH = 71,
|
||||
FTM_FM_TX_PWR_LVL_CFG = 72,
|
||||
#endif /* FEATURE_FTM_FM_DEBUG */
|
||||
|
||||
FTM_FM_RX_ENABLE_RECEIVER = 7,
|
||||
FTM_FM_RX_DISABLE_RECEIVER = 8,
|
||||
FTM_FM_RX_CONFIGURE_RECEIVER = 9,
|
||||
FTM_FM_RX_SET_MUTE_MODE = 10,
|
||||
FTM_FM_RX_SET_STEREO_MODE = 11,
|
||||
FTM_FM_RX_SET_STATION = 12,
|
||||
FTM_FM_RX_GET_STATION_PARAMETERS = 15,
|
||||
FTM_FM_RX_RDS_GROUP_OPTIONS = 24,
|
||||
FTM_FM_TX_ENABLE_TRANSMITTER = 33,
|
||||
FTM_FM_TX_DISABLE_TRANSMITTER = 34,
|
||||
FTM_FM_TX_CONFIGURE_TRANSMITTER = 35,
|
||||
FTM_FM_TX_SET_STATION = 37,
|
||||
FTM_FM_TX_TX_RDS_GROUPS = 42,
|
||||
FTM_FM_TX_TX_CONT_RDS_GROUPS = 43,
|
||||
FTM_FM_TX_TX_RDS_CTRL = 44,
|
||||
FTM_FM_TX_GET_RDS_GROUP_BUF_SIZE = 45,
|
||||
FTM_FM_BUS_WRITE = 47,
|
||||
FTM_FM_BUS_READ = 48,
|
||||
FTM_FM_NOTIFY_WAN = 49,
|
||||
FTM_FM_NOTIFY_FM = 50,
|
||||
FTM_FM_ROUTE_AUDIO = 52,
|
||||
FTM_FM_RX_SET_AF_THRESHOLD = 53,
|
||||
FTM_FM_RX_SET_RSSI_CHECK_TIMER = 54,
|
||||
FTM_FM_RX_SET_RDS_PI_TIMER = 55,
|
||||
FTM_FM_RX_GET_AF_THRESHOLD = 56,
|
||||
FTM_FM_RX_GET_RSSI_CHECK_TIMER = 57,
|
||||
FTM_FM_RX_GET_RDS_PI_TIMER = 58,
|
||||
FTM_FM_RX_GET_RDS_ERR_COUNT = 59,
|
||||
FTM_FM_RX_RESET_RDS_ERR_COUNT = 60,
|
||||
FTM_FM_TX_SEARCH_STATIONS = 61,
|
||||
FTM_FM_SET_HLSI = 100,
|
||||
FTM_FM_SET_SOFT_MUTE = 101,
|
||||
FTM_FM_SET_ANTENNA = 102,
|
||||
FTM_FM_SET_NOTCH_FILTER = 103,
|
||||
FTM_FM_READ_RDS_GRP_CNTRS = 104,
|
||||
FTM_FM_SET_TONE_GENERATION = 105,
|
||||
FTM_FM_PEEK_SSBI = 106,
|
||||
FTM_FM_POKE_SSBI = 107,
|
||||
FTM_FM_PEEK_RIVA_WORD = 108,
|
||||
FTM_FM_POKE_RIVA_WORD = 109,
|
||||
FTM_FM_ENABLE_AUDIO = 111,
|
||||
FTM_FM_DISABLE_AUDIO = 112,
|
||||
FTM_FM_VOLUME_SETTING = 113,
|
||||
FTM_FM_READ_RDS_GRP_CNTRS_EXT = 114,
|
||||
FTM_FM_SET_GET_RESET_AGC = 115,
|
||||
FTM_FM_MAX
|
||||
} ftm_fm_sub_cmd_type;
|
||||
|
||||
#define XFR_CTRL_OFFSET 0x1F
|
||||
/* Wait time for ensuring XFR is generated */
|
||||
#define WAIT_ON_ISR_DELAY 15000 //15 ms
|
||||
#define AFTH_OFFSET 0x2E
|
||||
#define CHCOND_OFFSET 0x22
|
||||
#define RDSTIMEOUT_OFFSET 0x25
|
||||
#define FM_SLAVE_ADDR 0x2A
|
||||
#define RDSERR_OFFSET 0x24
|
||||
#define RDSRESET_OFFSET 0x20
|
||||
#define BLOCKS_PER_GROUP 0x04
|
||||
#define FTM_FM_RDS_COUNT 0x11
|
||||
|
||||
|
||||
#define MAX_RIVA_DATA_LEN 245
|
||||
#define MAX_RIVA_PEEK_RSP_SIZE 251
|
||||
#define SSBI_PEEK_DATA_SIZE 1
|
||||
|
||||
#define IRIS_BUF_PEEK 6
|
||||
#define IRIS_BUF_SSBI_PEEK IRIS_BUF_PEEK+1
|
||||
#define IRIS_BUF_RDS_CNTRS IRIS_BUF_SSBI_PEEK+1
|
||||
#define IRIS_BUF_RD_DEFAULT IRIS_BUF_RDS_CNTRS+1
|
||||
#ifdef FM_SOC_TYPE_CHEROKEE
|
||||
#define RDS_GRP_CNTRS_SIZE 48
|
||||
#else
|
||||
#define RDS_GRP_CNTRS_SIZE 36
|
||||
#endif
|
||||
/* Generic result, used for any command that only returns an error code */
|
||||
typedef enum
|
||||
{
|
||||
FTM_FM_SUCCESS,
|
||||
FTM_FAIL,
|
||||
FTM_FILE_DOES_NOT_EXIST,
|
||||
FTM_MMC_ERROR,
|
||||
FTM_FM_UNRECOGNIZED_CMD,
|
||||
FTM_NO_RESOURCES,
|
||||
FTM_FM_PENDING,
|
||||
FTM_INVALID_PARAM,
|
||||
FTM_FM_DISALLOWED,
|
||||
FTM_TEST_NOT_IMPLEMENTED,
|
||||
FTM_CUST_HW_ID_UNKNOWN,
|
||||
FTM_FM_BUS_WRITE_ERROR,
|
||||
FTM_FM_BUS_READ_ERROR,
|
||||
FTM_FM_CLIENT_MAX,
|
||||
|
||||
} ftm_fm_api_result_type;
|
||||
|
||||
/* FM power state enum */
|
||||
typedef enum
|
||||
{
|
||||
FM_POWER_OFF,
|
||||
FM_POWER_TRANSITION,
|
||||
FM_RX_ON,
|
||||
FM_TX_ON
|
||||
}fm_power_state;
|
||||
|
||||
/* FM command status enum */
|
||||
typedef enum
|
||||
{
|
||||
FM_CMD_SUCCESS,
|
||||
FM_CMD_PENDING,
|
||||
FM_CMD_NO_RESOURCES,
|
||||
FM_CMD_INVALID_PARAM,
|
||||
FM_CMD_DISALLOWED,
|
||||
FM_CMD_UNRECOGNIZED_CMD,
|
||||
FM_CMD_FAILURE
|
||||
}fm_cmd_status_type;
|
||||
|
||||
/**
|
||||
* FM event result.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
FM_EV_SUCCESS = 0,
|
||||
/**< Event indicates success. */
|
||||
|
||||
FM_EV_FAILURE = 1,
|
||||
/**< Event is a response to a command that failed */
|
||||
|
||||
FM_EV_CMD_DISALLOWED = 2,
|
||||
/**< Event is a response to a command that was disallowed. */
|
||||
|
||||
FM_EV_CMD_INVALID_PARAM = 3
|
||||
/**< Event is a response to a command that contained an invalid parameter. */
|
||||
|
||||
} FmEvResultType;
|
||||
|
||||
/**
|
||||
* FM Receiver event names.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
/* -----------------------------------------------
|
||||
1 -> FM Receiver initialization events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_ENABLE_RECEIVER = 0,
|
||||
|
||||
FM_RX_EV_DISABLE_RECEIVER,
|
||||
|
||||
FM_RX_EV_CFG_RECEIVER,
|
||||
|
||||
/* -----------------------------------------------
|
||||
2 -> FM receiver control events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_MUTE_MODE_SET,
|
||||
|
||||
FM_RX_EV_STEREO_MODE_SET,
|
||||
|
||||
FM_RX_EV_RADIO_STATION_SET,
|
||||
|
||||
FM_RX_EV_PWR_MODE_SET,
|
||||
|
||||
FM_RX_EV_SET_SIGNAL_THRESHOLD,
|
||||
|
||||
/* -----------------------------------------------
|
||||
3 -> FM receiver status events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_RADIO_TUNE_STATUS,
|
||||
|
||||
FM_RX_EV_STATION_PARAMETERS,
|
||||
|
||||
FM_RX_EV_RDS_LOCK_STATUS,
|
||||
|
||||
FM_RX_EV_STEREO_STATUS,
|
||||
|
||||
FM_RX_EV_SERVICE_AVAILABLE,
|
||||
|
||||
FM_RX_EV_GET_SIGNAL_THRESHOLD,
|
||||
|
||||
/* -----------------------------------------------
|
||||
4 -> FM search status events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_SEARCH_IN_PROGRESS,
|
||||
|
||||
FM_RX_EV_SEARCH_RDS_IN_PROGRESS,
|
||||
|
||||
FM_RX_EV_SEARCH_LIST_IN_PROGRESS,
|
||||
|
||||
FM_RX_EV_SEARCH_COMPLETE,
|
||||
|
||||
FM_RX_EV_SEARCH_RDS_COMPLETE,
|
||||
|
||||
FM_RX_EV_SEARCH_LIST_COMPLETE,
|
||||
|
||||
FM_RX_EV_SEARCH_CANCELLED,
|
||||
|
||||
/* -----------------------------------------------
|
||||
5 -> FM RDS status events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_RDS_GROUP_DATA,
|
||||
|
||||
FM_RX_EV_RDS_PS_INFO,
|
||||
|
||||
FM_RX_EV_RDS_RT_INFO,
|
||||
|
||||
FM_RX_EV_RDS_AF_INFO,
|
||||
|
||||
FM_RX_EV_RDS_PI_MATCH_AVAILABLE,
|
||||
|
||||
/* -----------------------------------------------
|
||||
6 -> FM RDS control events
|
||||
----------------------------------------------- */
|
||||
|
||||
FM_RX_EV_RDS_GROUP_OPTIONS_SET,
|
||||
|
||||
FM_RX_EV_RDS_PROC_REG_DONE,
|
||||
|
||||
FM_RX_EV_RDS_PI_MATCH_REG_DONE,
|
||||
|
||||
FM_RX_EV_MAX_EVENT
|
||||
|
||||
} FmRxEventType;
|
||||
|
||||
typedef enum radio_band_type
|
||||
{
|
||||
FM_US_EU = 0x0,
|
||||
FM_JAPAN_STANDARD = 0x1,
|
||||
FM_JAPAN_WIDE = 0x2,
|
||||
FM_USER_DEFINED = 0x4
|
||||
}radio_band_type;
|
||||
|
||||
typedef enum emphasis_type
|
||||
{
|
||||
FM_RX_EMP75 = 0x0,
|
||||
FM_RX_EMP50 = 0x1
|
||||
}emphasis_type;
|
||||
|
||||
typedef enum channel_space_type
|
||||
{
|
||||
FM_RX_SPACE_200KHZ = 0x0,
|
||||
FM_RX_SPACE_100KHZ = 0x1,
|
||||
FM_RX_SPACE_50KHZ = 0x2
|
||||
}channel_space_type;
|
||||
|
||||
typedef enum rds_system_type
|
||||
{
|
||||
FM_RX_RDBS_SYSTEM = 0x0,
|
||||
FM_RX_RDS_SYSTEM = 0x1,
|
||||
FM_RX_NO_RDS_SYSTEM = 0x2
|
||||
}rds_sytem_type;
|
||||
|
||||
typedef struct band_limit_freq
|
||||
{
|
||||
uint32 lower_limit;
|
||||
uint32 upper_limit;
|
||||
}band_limit_freq;
|
||||
|
||||
|
||||
typedef enum rds_sync_type
|
||||
{
|
||||
FM_RDS_NOT_SYNCED = 0x0,
|
||||
FM_RDS_SYNCED = 0x1
|
||||
}rds_sync_type;
|
||||
|
||||
typedef enum stereo_type
|
||||
{
|
||||
FM_RX_MONO = 0x0,
|
||||
FM_RX_STEREO = 0x1
|
||||
}stereo_type;
|
||||
|
||||
typedef enum fm_service_available
|
||||
{
|
||||
FM_SERVICE_NOT_AVAILABLE = 0x0,
|
||||
FM_SERVICE_AVAILABLE = 0x1
|
||||
}fm_service_available;
|
||||
|
||||
typedef enum mute_type
|
||||
{
|
||||
FM_RX_NO_MUTE = 0x00,
|
||||
FM_RX_MUTE_RIGHT = 0x01,
|
||||
FM_RX_MUTE_LEFT = 0x02,
|
||||
FM_RX_MUTE_BOTH = 0x03
|
||||
}mute_type;
|
||||
|
||||
typedef enum antenna_type
|
||||
{
|
||||
WIRED_HS,
|
||||
PWB_ANT
|
||||
}antenna_type;
|
||||
|
||||
typedef enum audio_output
|
||||
{
|
||||
HEADSET,
|
||||
SPEAKER,
|
||||
} audio_output;
|
||||
/**
|
||||
* RDS/RBDS Program Type type.
|
||||
*/
|
||||
typedef uint8 fm_prgm_type;
|
||||
|
||||
/**
|
||||
* RDS/RBDS Program Identification type.
|
||||
*/
|
||||
typedef uint16 fm_prgmid_type;
|
||||
/**
|
||||
* RDS/RBDS Program Services type.
|
||||
*/
|
||||
typedef char fm_prm_services;
|
||||
/**
|
||||
* RDS/RBDS Radio Text type.
|
||||
*/
|
||||
/*
|
||||
* FM RX RIVA peek request
|
||||
*/
|
||||
typedef struct fm_riva_peek_word
|
||||
{
|
||||
uint8 subOpcode;
|
||||
uint32 startaddress;
|
||||
uint8 payload_length;/*In Bytes*/
|
||||
uint8 data[MAX_RIVA_DATA_LEN];
|
||||
}__attribute__((packed))fm_riva_peek_word;
|
||||
|
||||
/*
|
||||
* FM RX RIVA poke request
|
||||
*/
|
||||
typedef struct fm_riva_poke_word
|
||||
{
|
||||
uint8 subOpcode;
|
||||
uint32 startaddress;
|
||||
uint8 payload_length;/*In Bytes*/
|
||||
uint8 data[MAX_RIVA_DATA_LEN];
|
||||
}__attribute__((packed))fm_riva_poke_word ;
|
||||
|
||||
|
||||
/*
|
||||
* FM RX SSBI peek/poke request
|
||||
*/
|
||||
typedef struct fm_ssbi_poke_reg
|
||||
{
|
||||
uint16 startaddress;
|
||||
uint8 data;
|
||||
}__attribute__((packed))fm_ssbi_poke_reg;
|
||||
|
||||
/*
|
||||
* fm Set Get Reset AGC request
|
||||
*/
|
||||
typedef struct fm_set_get_reset_agc_req
|
||||
{
|
||||
uint8 ucCtrl;
|
||||
uint8 ucGainState;
|
||||
}__attribute__((packed))fm_set_get_reset_agc_req;
|
||||
|
||||
typedef struct fm_set_get_reset_agc_params
|
||||
{
|
||||
uint8 ucCurrentGainState;
|
||||
uint8 ucGainStateChange1;
|
||||
uint8 ucGainStateChange2;
|
||||
uint8 ucGainStateChange3;
|
||||
}__attribute__((packed))fm_set_get_reset_agc_params;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
uint8 status ;
|
||||
uint8 data_length ;
|
||||
uint8 data[DEFAULT_DATA_SIZE];
|
||||
}__attribute__((packed)) readDefaults_data;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
uint8 status ;
|
||||
uint8 data_length ;
|
||||
uint8 data[DEFAULT_DATA_SIZE];
|
||||
}__attribute__((packed)) default_read_rsp;
|
||||
|
||||
/*RDS Group counters*/
|
||||
typedef struct fm_rds_grp_cntrsparams
|
||||
{
|
||||
uint32 totalRdsSBlockErrors;
|
||||
uint32 totalRdsGroups;
|
||||
uint32 totalRdsGroup0;
|
||||
uint32 totalRdsGroup2;
|
||||
uint32 totalRdsBlockB;
|
||||
uint32 totalRdsProcessedGroup0;
|
||||
uint32 totalRdsProcessedGroup2;
|
||||
uint32 totalRdsGroupFiltered;
|
||||
uint32 totalRdsChangeFiltered;
|
||||
}__attribute__((packed)) fm_rds_grp_cntrsparams;
|
||||
|
||||
/*RDS Group counters extended */
|
||||
typedef struct fm_rds_grpcntrs_extendedparams
|
||||
{
|
||||
uint32 totalRdsSyncLoss;
|
||||
uint32 totalRdsNotSync;
|
||||
uint32 totalRdsSyncInt;
|
||||
}__attribute__((packed)) fm_rds_grpcntrs_extendedparams;
|
||||
|
||||
typedef char fm_radiotext_info;
|
||||
/**
|
||||
* FM Global Paramaters struct.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
uint32 current_station_freq;/*a frequency in kHz the band range*/
|
||||
uint8 service_available;
|
||||
uint8 rssi; /* rssi range from 0-100*/
|
||||
uint8 stype;
|
||||
uint8 rds_sync_status;
|
||||
uint8 mute_status;
|
||||
uint8 ssbi_peek_data;
|
||||
fm_prgmid_type pgm_id; /* Program Id */
|
||||
fm_prgm_type pgm_type; /* Program type */
|
||||
fm_prm_services pgm_services[MAX_RDS_PS_LENGTH];
|
||||
fm_radiotext_info radio_text[MAX_RDS_RT_LENGTH];/* RT maximum is 64 bytes */
|
||||
fm_riva_poke_word riva_data_access_params;
|
||||
fm_set_get_reset_agc_params set_get_reset_agc_params;
|
||||
fm_rds_grp_cntrsparams rds_group_counters;
|
||||
fm_rds_grpcntrs_extendedparams rds_group_counters_extended;
|
||||
readDefaults_data default_read_data;
|
||||
uint8 fm_ps_length;
|
||||
uint8 fm_rt_length;
|
||||
uint8 sinr_samples;
|
||||
char sinr_threshold;
|
||||
uint8 On_channel_threshold;
|
||||
uint8 Off_channel_threshold;
|
||||
}fm_station_params_available;
|
||||
/**
|
||||
* FM Config Request structure.
|
||||
*/
|
||||
typedef struct fm_config_data
|
||||
{
|
||||
uint8 band;
|
||||
uint8 emphasis;
|
||||
uint8 spacing;
|
||||
uint8 rds_system;
|
||||
band_limit_freq bandlimits;
|
||||
uint8 is_fm_tx_on;
|
||||
}fm_config_data;
|
||||
|
||||
/*
|
||||
* FM RDS Options Config Request
|
||||
*/
|
||||
typedef struct fm_rds_options
|
||||
{
|
||||
uint32 rds_group_mask;
|
||||
uint32 rds_group_buffer_size;
|
||||
uint8 rds_change_filter;
|
||||
}fm_rds_options;
|
||||
/*
|
||||
* FM RX Search stations request
|
||||
*/
|
||||
typedef struct fm_search_stations
|
||||
{
|
||||
uint8 search_mode;
|
||||
uint8 dwell_period;
|
||||
uint8 search_dir;
|
||||
}fm_search_stations;
|
||||
|
||||
/*
|
||||
* FM RX Search DDS stations request
|
||||
*/
|
||||
typedef struct fm_search_rds_stations
|
||||
{
|
||||
uint8 search_mode;
|
||||
uint8 dwell_period;
|
||||
uint8 search_dir;
|
||||
uint8 program_type;
|
||||
uint16 program_id;
|
||||
}fm_search_rds_stations;
|
||||
|
||||
/*
|
||||
* FM RX Search station lists request
|
||||
*/
|
||||
typedef struct fm_search_list_stations
|
||||
{
|
||||
uint8 search_mode;
|
||||
uint8 search_dir;
|
||||
uint32 srch_list_max;
|
||||
/**< Maximum number of stations that can be returned from a search. */
|
||||
uint8 program_type;
|
||||
}fm_search_list_stations;
|
||||
|
||||
/*
|
||||
* FM RX I2C request
|
||||
*/
|
||||
typedef struct fm_i2c_params
|
||||
{
|
||||
uint8 slaveaddress;
|
||||
uint8 offset;
|
||||
uint8 payload_length;
|
||||
uint8 data[64];
|
||||
}fm_i2c_params;
|
||||
|
||||
/* Structure containing the RDS PS Info to be transmitted */
|
||||
typedef struct _tsFtmFmRdsTxPsType
|
||||
{
|
||||
uint32 ulPSStrLen;
|
||||
/**< The size of the cTxPSStrPtr buffer.
|
||||
*/
|
||||
|
||||
uint32 ucTxPSRptCnt;
|
||||
/**< The number of times each 8 character string is repeated before the next
|
||||
string is transmitted.
|
||||
*/
|
||||
|
||||
uint16 tusTxPi;
|
||||
/**< RDS/RBDS Program Identification to use for Program Service transmissions.
|
||||
*/
|
||||
|
||||
uint8 tucTxPSPty;
|
||||
/**< The RDS/RBDS Program Type to transmit.
|
||||
*/
|
||||
|
||||
const char cTxPSStrPtr[108];
|
||||
/**< A pointer to a buffer containing the Program Service string to transmit
|
||||
(must be null terminated).
|
||||
*/
|
||||
|
||||
} tsFtmFmRdsTxPsType;
|
||||
|
||||
typedef struct _tsFtmFmRdsTxRtType
|
||||
{
|
||||
uint32 ulRTStrLen;
|
||||
/**< The size of the cTxRTStrPtr buffer.
|
||||
*/
|
||||
|
||||
uint16 tusTxPi;
|
||||
/**< RDS/RBDS Program Identification to use for RadioText transmissions.
|
||||
*/
|
||||
|
||||
uint8 tucTxRTPty;
|
||||
/**< The RDS/RBDS Program Type to transmit.
|
||||
*/
|
||||
|
||||
const char cTxRTStrPtr[65];
|
||||
/**< A pointer to a buffer containing the RadioText string to transmit
|
||||
(must be null terminated).
|
||||
*/
|
||||
|
||||
} tsFtmFmRdsTxRtType;
|
||||
|
||||
typedef struct _ftm_def_data_rd_req
|
||||
{
|
||||
uint8 mode;
|
||||
uint8 length;
|
||||
uint8 param_len;
|
||||
uint8 param;
|
||||
} __attribute__((packed))ftm_fm_def_data_rd_req;
|
||||
|
||||
typedef struct _ftm_def_data_wr_req
|
||||
{
|
||||
uint8 mode;
|
||||
uint8 length;
|
||||
uint8 data[DEFAULT_DATA_SIZE];
|
||||
} __attribute__((packed))ftm_fm_def_data_wr_req;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 length; /*RDS PS string length*/
|
||||
uint8 string[MAX_RDS_PS_LENGTH]; /* RDS string */
|
||||
}__attribute__((packed)) fmrdsps_response;
|
||||
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 length; /*RDS PS string length*/
|
||||
uint8 string[MAX_RDS_RT_LENGTH]; /* RDS string */
|
||||
}__attribute__((packed)) fmrdsrt_response;
|
||||
|
||||
|
||||
/**
|
||||
* FM All Request Union type.
|
||||
*/
|
||||
typedef union fm_cfg_request
|
||||
{
|
||||
fm_config_data cfg_param;
|
||||
uint8 mute_param;
|
||||
uint8 stereo_param;
|
||||
uint32 freq;
|
||||
fm_rds_options rds_options;
|
||||
uint8 power_mode;
|
||||
uint8 signal_threshold;
|
||||
fm_search_stations search_stations_options;
|
||||
fm_search_rds_stations search_rds_stations_options;
|
||||
fm_search_list_stations search_list_stations_options;
|
||||
fm_i2c_params i2c_params;
|
||||
uint32 rds_group_options;
|
||||
uint16 rx_af_threshold;
|
||||
uint8 rx_rssi_checktimer;
|
||||
uint rx_rds_pi_timer;
|
||||
tsFtmFmRdsTxPsType tuFmPSParams;
|
||||
tsFtmFmRdsTxRtType tuFmRTParams;
|
||||
uint8 soft_mute_param;
|
||||
uint8 antenna_type;
|
||||
uint8 tx_tone_param;
|
||||
uint8 rds_grp_counters;
|
||||
uint8 rds_grp_counters_ext;
|
||||
uint8 hlsi;
|
||||
uint8 sinr_samples;
|
||||
char sinr_threshold;
|
||||
uint8 On_channel_threshold;
|
||||
uint8 Off_channel_threshold;
|
||||
uint8 notch;
|
||||
fm_riva_peek_word riva_peek_params;
|
||||
fm_riva_poke_word riva_data_access_params;
|
||||
fm_ssbi_poke_reg ssbi_access_params;
|
||||
fm_set_get_reset_agc_req set_get_agc_req_parameters;
|
||||
ftm_fm_def_data_rd_req rd_default;
|
||||
ftm_fm_def_data_wr_req wr_default;
|
||||
uint8 tx_pwr_cfg;
|
||||
uint8 audio_output;
|
||||
uint8 audio_vlm;
|
||||
}fm_cfg_request;
|
||||
|
||||
/* FTM FM request type */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_cmd_code_type cmd_code;
|
||||
diagpkt_subsys_id_type subsys_id;
|
||||
diagpkt_subsys_cmd_code_type subsys_cmd_code;
|
||||
uint16 cmd_id; /* command id (required) */
|
||||
uint16 cmd_data_len;
|
||||
uint16 cmd_rsp_pkt_size;
|
||||
byte data[1];
|
||||
}__attribute__((packed))ftm_fm_pkt_type;
|
||||
|
||||
/* Set MuteMode Response */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 mutemode;
|
||||
}__attribute__((packed)) mutemode_response;
|
||||
|
||||
/* Set StereoMode Response */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 stereomode;
|
||||
}__attribute__((packed)) stereomode_response;
|
||||
|
||||
/* I2C Response */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint32 length; /*length of data read */
|
||||
uint8 data[64]; /* I2C read dat buffer */
|
||||
}__attribute__((packed)) fmbusread_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 sub_opcode;
|
||||
uint32 start_address;
|
||||
uint8 length; /*length of data read */
|
||||
uint8 data[MAX_RIVA_DATA_LEN]; /* read dat buffer */
|
||||
}__attribute__((packed)) rivaData_response;
|
||||
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 data;
|
||||
}__attribute__((packed)) ssbiPeek_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint8 uccurrentgainstate;
|
||||
uint8 ucgainstatechange1;
|
||||
uint8 ucgainstatechange2;
|
||||
uint8 ucgainstatechange3;
|
||||
}__attribute__((packed)) set_get_reset_agc_response;
|
||||
|
||||
/*Read RDS Group counters responce*/
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
fm_rds_grp_cntrsparams read_rds_cntrs;
|
||||
}__attribute__((packed)) ReadRDSCntrs_responce;
|
||||
|
||||
/*Read RDS Group counters response*/
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
fm_rds_grpcntrs_extendedparams read_rds_cntrs_ext;
|
||||
}__attribute__((packed)) ReadRDSCntrs_ext_response;
|
||||
|
||||
|
||||
/* Generic Response */
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
}__attribute__((packed)) generic_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint16 afthreshold;
|
||||
} fmrxsetafthreshold_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 sinr_sample;
|
||||
} getsinrsamples_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
char sinr_threshold;
|
||||
} getsinrthreshold_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 sinr_on_th;
|
||||
} getonchannelthreshold_response;
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 sinr_off_th;
|
||||
} getoffchannelthreshold_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 rssitimer;
|
||||
} fmrxsetrssichecktimer_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 rdspitimer;
|
||||
} fmrxsetrdspitimer_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint8 threshold;
|
||||
} threshold_response;
|
||||
|
||||
typedef PACKED struct
|
||||
{
|
||||
diagpkt_subsys_header_type header ;
|
||||
char result ;
|
||||
uint32 rdserrcount;
|
||||
uint32 numofblocks;
|
||||
} rds_err_count_response;
|
||||
|
||||
/* Custom response for Get station parameters request */
|
||||
struct fm_rx_get_station_parameters_response_t
|
||||
{
|
||||
diagpkt_subsys_header_type header ; /*Diag header*/
|
||||
char result ;/* result */
|
||||
uint32 stationFreq;
|
||||
/* The currently tuned frequency in kHz (Example: 96500 -> 96.5Mhz)*/
|
||||
uint8 servAvble;
|
||||
/* The current service available indicator for the current station */
|
||||
uint8 rssi;
|
||||
/* The current signal strength level (0-100 range). */
|
||||
uint8 stereoProgram;
|
||||
/* The current mono/stereo indicator for this station */
|
||||
uint8 rdsSyncStatus;
|
||||
/* The current RDS/RBDS synchronization status */
|
||||
uint8 muteMode;
|
||||
/* The current FM mute mode */
|
||||
}__attribute__((packed));
|
||||
|
||||
/* FTM Log Packet - Used to send back the event of a HCI Command */
|
||||
typedef PACKED struct
|
||||
{
|
||||
log_hdr_type hdr;
|
||||
byte EvName;
|
||||
/* Event ID indicates which event is being returned. */
|
||||
byte EvResult;
|
||||
byte data[1]; /* Variable length payload,
|
||||
look at FTM log id for contents */
|
||||
} ftm_fm_log_pkt_type;
|
||||
#define FTM_FM_LOG_HEADER_SIZE (sizeof (ftm_fm_log_pkt_type) - 1)
|
||||
|
||||
typedef struct fm_rx_get_station_parameters_response_t fm_rx_get_station_parameters_response;
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_fm_dispatch
|
||||
|
||||
DESCRIPTION
|
||||
Dispatch routine for the various FM Rx/Tx commands. Copies the data into
|
||||
a global union data structure before calling the processing routine
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
A Packed structre pointer including the response to the FTM FM packet
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
void * ftm_fm_dispatch(ftm_fm_pkt_type *ftm_fm_pkt, uint16 length );
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION ftm_fm_enable_audio
|
||||
|
||||
DESCRIPTION
|
||||
This function is used to take the audio output mode from QRCT.
|
||||
|
||||
DEPENDENCIES
|
||||
none
|
||||
|
||||
===========================================================================*/
|
||||
PACKED void* ftm_fm_enable_audio( void );
|
||||
PACKED void* ftm_fm_disable_audio( void );
|
||||
PACKED void* ftm_fm_setting_volume(void);
|
||||
|
||||
#endif /* CONFIG_FTM_FM */
|
||||
1178
feeds/ipq95xx/ftm/src/ftm_fm_pfal.h
Executable file
1178
feeds/ipq95xx/ftm/src/ftm_fm_pfal.h
Executable file
File diff suppressed because it is too large
Load Diff
3668
feeds/ipq95xx/ftm/src/ftm_fm_pfal_linux.c
Executable file
3668
feeds/ipq95xx/ftm/src/ftm_fm_pfal_linux.c
Executable file
File diff suppressed because it is too large
Load Diff
3338
feeds/ipq95xx/ftm/src/ftm_fm_pfal_linux_3990.c
Executable file
3338
feeds/ipq95xx/ftm/src/ftm_fm_pfal_linux_3990.c
Executable file
File diff suppressed because it is too large
Load Diff
549
feeds/ipq95xx/ftm/src/ftm_iot.c
Executable file
549
feeds/ipq95xx/ftm/src/ftm_iot.c
Executable file
@@ -0,0 +1,549 @@
|
||||
/*
|
||||
*Copyright (c) 2018-2020, 2022 Qualcomm Technologies, Inc.
|
||||
*
|
||||
*All Rights Reserved.
|
||||
*Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
/* IPQ-QCA402X specific file */
|
||||
|
||||
#ifdef IPQ_AP_HOST_IOT
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <sys/ioctl.h>
|
||||
#include <mtd/mtd-user.h>
|
||||
#include "comdef.h"
|
||||
#include "diagcmd.h"
|
||||
#include "ftm_wlan.h"
|
||||
#include "ftm_dbg.h"
|
||||
#include "ftm_iot.h"
|
||||
#ifdef IPQ_AP_HOST_IOT_QCA402X
|
||||
#include "diag_api.h"
|
||||
#endif /* IPQ_AP_HOST_IOT_QCA402X */
|
||||
#ifdef IPQ_AP_HOST_IOT_IPQ
|
||||
#include "btdaemon.h"
|
||||
#endif /* IPQ50XX, IPQ95XX */
|
||||
|
||||
#define NHDLC_TERM 126
|
||||
#define NHDLC_VERSION 1
|
||||
#define NHDLC_TERM_SIZE 1
|
||||
#define FLASH_CMD_ID_POS 1
|
||||
#define MAX_BUF_SIZE 2048
|
||||
#define WAIT_TIME_MS 100
|
||||
#define SUBSYS_CMD_ID_POS 2
|
||||
#define RESERVED_CMD_ID 0
|
||||
#define DUT_INTERFACE_SELECT 1
|
||||
#define DUT_INTERFACE_ID_POS 4
|
||||
#define DUT_INTERFACE_SELECT_POS 10
|
||||
#define DIAG_HDR_LEN (sizeof(diag_nonhdlc_hdr_t) + NHDLC_TERM_SIZE)
|
||||
#define FTM_IOT_LOG_HEADER_SIZE sizeof(ftm_iot_log_pkt_type)
|
||||
|
||||
#define MEMSET_RESET_VALUE 0
|
||||
#define DIAG_HEADER_SIZE 12
|
||||
|
||||
extern void diagpkt_free(void *pkt);
|
||||
|
||||
void print_array(uint8_t *addr, int len)
|
||||
{
|
||||
int i;
|
||||
int line = 1;
|
||||
for (i = 0; i < len; i++) {
|
||||
if (i == (line * 80)) {
|
||||
DPRINTF(FTM_DBG_TRACE, "\n");
|
||||
line++;
|
||||
}
|
||||
DPRINTF(FTM_DBG_TRACE, "%02X ", addr[i]);
|
||||
}
|
||||
DPRINTF(FTM_DBG_TRACE, "\n");
|
||||
}
|
||||
#ifdef IPQ_AP_HOST_IOT_QCA402X
|
||||
/*===========================================================================
|
||||
FUNCTION iot_thr_func_qca402x
|
||||
|
||||
DESCRIPTION
|
||||
Continously polls QCA402X for asynchronous data responses and
|
||||
logs receievd asynchronous data responses to Diag module using
|
||||
log-submit()
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns NULL on failure. Function also exits with NULL return value
|
||||
when main indicates that this thread should be stopped
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
void *iot_thr_func_qca402x(void *hdl)
|
||||
{
|
||||
int bytes = 0;
|
||||
void *rsp2 = NULL;
|
||||
int diag_hdr_len = DIAG_HDR_LEN ;
|
||||
void *new_iot_ftm_rsp2_pkt = NULL;
|
||||
|
||||
if (!hdl) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Invalid iotd handle\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
new_iot_ftm_rsp2_pkt = malloc(MAX_BUF_SIZE);
|
||||
if (!new_iot_ftm_rsp2_pkt) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate response packet \n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
while(1) {
|
||||
|
||||
if (thread_stop == 1) {
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: Exiting thread.\n");
|
||||
break;
|
||||
}
|
||||
|
||||
memset(new_iot_ftm_rsp2_pkt, MEMSET_RESET_VALUE, MAX_BUF_SIZE);
|
||||
sem_wait(&iot_sem);
|
||||
|
||||
/*If we recieve a response from QCA402X, allocate a buffer using diag alloc with correct
|
||||
subsystem code and length */
|
||||
while ((bytes = diag_recv(hdl, (uint8_t *)new_iot_ftm_rsp2_pkt,
|
||||
MAX_BUF_SIZE,
|
||||
WAIT_TIME_MS)) >= 0) {
|
||||
if (bytes > MAX_BUF_SIZE || bytes <= diag_hdr_len) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate async log response packet\n");
|
||||
free (new_iot_ftm_rsp2_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
rsp2 = diagpkt_subsys_alloc(DIAG_SUBSYS_FTM, ftm_iot_cmd_code, (bytes - diag_hdr_len));
|
||||
if (!rsp2) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate async log response packet\n");
|
||||
free (new_iot_ftm_rsp2_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Remove NHDLC header from recieved packet and store contents in
|
||||
buffer allocated above */
|
||||
memcpy(rsp2, (new_iot_ftm_rsp2_pkt + diag_hdr_len - NHDLC_TERM_SIZE),
|
||||
(bytes - diag_hdr_len));
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: Asynchronous Data response has been sent.\n");
|
||||
print_array((uint8_t *)rsp2, (bytes - diag_hdr_len) );
|
||||
|
||||
/*Remove an additional 4 bytes of header and log packet to diag module
|
||||
asynchronously for further processing*/
|
||||
log_submit(rsp2 + diag_hdr_len - NHDLC_TERM_SIZE);
|
||||
diagpkt_free (rsp2);
|
||||
memset(new_iot_ftm_rsp2_pkt, MEMSET_RESET_VALUE, MAX_BUF_SIZE);
|
||||
}
|
||||
|
||||
sem_post(&iot_sem_async);
|
||||
}
|
||||
|
||||
free (new_iot_ftm_rsp2_pkt);
|
||||
diagpkt_free (rsp2);
|
||||
pthread_exit(NULL);
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_iot_dispatch_qca402x
|
||||
|
||||
DESCRIPTION
|
||||
Function processes WIN IOT specific requests and relays to
|
||||
QCA402x FTM layer for further processing. Recieves response
|
||||
buffer from QCA402x and returns buffer meant for diag call back
|
||||
|
||||
This function handles NHDLC to HDLC translation and vice-versa
|
||||
before sending and receivng buffers to QCA402X FTM layer
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns back buffer that is meant for diag callback
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
void *ftm_iot_dispatch_qca402x(void *iot_ftm_pkt, int pkt_len, void *hdl)
|
||||
{
|
||||
int diag_hdr_len = DIAG_HDR_LEN;
|
||||
int ret = 0;
|
||||
byte *payload_ptr = NULL;
|
||||
void *rsp1 = NULL;
|
||||
ftm_iot_req_pkt_type *new_iot_ftm_pkt = NULL;
|
||||
void *new_iot_ftm_rsp_pkt = NULL;
|
||||
char command[50] = {'\0'};
|
||||
uint16_t *ftm_iot_flash_ptr = NULL;
|
||||
uint16 ftm_iot_flash_cmd_code = 0;
|
||||
/* The new packet length will be length of original request packet
|
||||
+ size of NHDLC header + 1 byte of termination character */
|
||||
int new_pkt_len = pkt_len + diag_hdr_len;
|
||||
|
||||
if (!iot_ftm_pkt || !pkt_len || !hdl) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Invalid ftm iot request packet or iotd handle\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
new_iot_ftm_pkt = malloc(sizeof(ftm_iot_req_pkt_type) + pkt_len + NHDLC_TERM_SIZE);
|
||||
if (!new_iot_ftm_pkt) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not create new ftm iot request packet\n");
|
||||
return NULL;
|
||||
}
|
||||
memset(new_iot_ftm_pkt, MEMSET_RESET_VALUE, (sizeof(ftm_iot_req_pkt_type) + pkt_len + NHDLC_TERM_SIZE));
|
||||
|
||||
new_iot_ftm_rsp_pkt = malloc(MAX_BUF_SIZE);
|
||||
if (!new_iot_ftm_rsp_pkt) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not create new ftm iot response packet\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
return NULL;
|
||||
}
|
||||
memset(new_iot_ftm_rsp_pkt, MEMSET_RESET_VALUE, MAX_BUF_SIZE);
|
||||
|
||||
/* Add Non-HDLC header to request packet
|
||||
and populate NHDLC header*/
|
||||
new_iot_ftm_pkt->hdr.start = NHDLC_TERM;
|
||||
new_iot_ftm_pkt->hdr.version = NHDLC_VERSION;
|
||||
new_iot_ftm_pkt->hdr.length = pkt_len;
|
||||
memcpy(&(new_iot_ftm_pkt->payload), iot_ftm_pkt, pkt_len);
|
||||
payload_ptr = (byte *) &(new_iot_ftm_pkt->payload);
|
||||
*( payload_ptr + pkt_len) = NHDLC_TERM;
|
||||
ftm_iot_cmd_code = *(payload_ptr + SUBSYS_CMD_ID_POS);
|
||||
ftm_iot_dut_interface_code = *(payload_ptr + DUT_INTERFACE_ID_POS);
|
||||
ftm_iot_reserved_code = *(payload_ptr + SUBSYS_CMD_ID_POS + 1);
|
||||
ftm_iot_flash_ptr = (uint16_t *) &(new_iot_ftm_pkt->payload);
|
||||
ftm_iot_flash_cmd_code = *(ftm_iot_flash_ptr + FLASH_CMD_ID_POS);
|
||||
/*Print packet after adding headers */
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: Request Packet of size %d bytes sent:\n", new_pkt_len);
|
||||
print_array((uint8_t *)new_iot_ftm_pkt, new_pkt_len);
|
||||
|
||||
/*If the request packet it a DUT interface selection command,
|
||||
update interface number and return a response packet that
|
||||
is an encho of the request packet. ( In the case of multiple
|
||||
QCA402x DUT attaches on IPQ platforms) */
|
||||
if (((ftm_iot_cmd_code == MFG_CMD_ID_BLE_HCI) || (ftm_iot_cmd_code == MFG_CMD_ID_I15P4_HMI))
|
||||
&& (ftm_iot_dut_interface_code == DUT_INTERFACE_SELECT)
|
||||
&& (ftm_iot_reserved_code == RESERVED_CMD_ID)){
|
||||
interface = *(payload_ptr + DUT_INTERFACE_SELECT_POS) - 1;
|
||||
if (interface < 0) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Invalid DUT interface selection command\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
rsp1 = diagpkt_subsys_alloc(DIAG_SUBSYS_FTM, ftm_iot_cmd_code, pkt_len);
|
||||
if (!rsp1){
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate response packet for interface selection\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(rsp1, iot_ftm_pkt, pkt_len);
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: The DUT interface selected is %d \n",interface);
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: DUT interface resp packet of size %d bytes sent:\n",pkt_len);
|
||||
print_array((uint8_t *)rsp1, pkt_len);
|
||||
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
|
||||
/*This resp pointer will be freed by diag later*/
|
||||
return rsp1;
|
||||
}
|
||||
|
||||
/*If the request packet is a MFG PROG command,
|
||||
launch flash script and return a response packet that indicates
|
||||
flashing mode of QCA402x is enabled or disabled */
|
||||
if ((ftm_iot_flash_cmd_code == MFG_CMD_ID_MISC_PROG_MODE)){
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_FLASH_ON){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh flash on", sizeof(command));
|
||||
}
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_FLASH_OFF){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh flash off", sizeof(command));
|
||||
}
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_USB_OFF){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh usb-select off", sizeof(command));
|
||||
}
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_USB_ON){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh usb-select on", sizeof(command));
|
||||
}
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_EDL_OFF){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh edl off", sizeof(command));
|
||||
}
|
||||
|
||||
if (ftm_iot_dut_interface_code == MFG_EDL_ON){
|
||||
strlcpy(command, "/usr/bin/qca402x_flash.sh edl on", sizeof(command));
|
||||
}
|
||||
|
||||
/*Return with NULL if string is empty or packet length is less than
|
||||
10 for a DUT interface selection command to make sure there will be
|
||||
no out of bound access */
|
||||
if ( (command[0] == '\0') || (pkt_len <= DUT_INTERFACE_ID_POS) ) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Error: Invalid MFG Program command\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
system(command);
|
||||
DPRINTF(FTM_DBG_TRACE, "\n FTMd: Sent system command: %s \n", command);
|
||||
|
||||
/* Check of size for packet pointed to by payload_ptr has been done above
|
||||
using pkt_len to make sure there is no out of bound access */
|
||||
|
||||
*(payload_ptr + DUT_INTERFACE_ID_POS) = MFG_PROG_RESP;
|
||||
|
||||
rsp1 = diagpkt_subsys_alloc(DIAG_SUBSYS_FTM, ftm_iot_cmd_code, pkt_len);
|
||||
if (!rsp1){
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate response packet for MFG flash commands\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(rsp1, payload_ptr, pkt_len);
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: MFG Flash resp packet of size %d bytes sent:\n",pkt_len);
|
||||
print_array((uint8_t *)rsp1, pkt_len);
|
||||
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
|
||||
/*This resp pointer will be freed by diag later*/
|
||||
return rsp1;
|
||||
}
|
||||
|
||||
sem_wait(&iot_sem_async);
|
||||
/* Call IPQ-QCA402x diag APIs */
|
||||
ret = diag_send(hdl, interface, (uint8_t *)new_iot_ftm_pkt, new_pkt_len);
|
||||
if ((ret < 0) || (ret > MAX_BUF_SIZE)) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not send the request packet to QCA402x \n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ret = diag_recv(hdl, (uint8_t *)new_iot_ftm_rsp_pkt, MAX_BUF_SIZE, WAIT_TIME_MS);
|
||||
if ((ret < 0) || (ret > MAX_BUF_SIZE) || (ret <= diag_hdr_len)) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not recieve packet from QCA402x\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE,"Received Command Response of %d bytes\n",ret);
|
||||
print_array((uint8_t *)new_iot_ftm_rsp_pkt, ret);
|
||||
|
||||
rsp1 = diagpkt_subsys_alloc(DIAG_SUBSYS_FTM, ftm_iot_cmd_code, (ret - diag_hdr_len));
|
||||
if (!rsp1){
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate response packet\n");
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(rsp1, (new_iot_ftm_rsp_pkt + diag_hdr_len - NHDLC_TERM_SIZE), (ret - diag_hdr_len));
|
||||
|
||||
free (new_iot_ftm_pkt);
|
||||
free (new_iot_ftm_rsp_pkt);
|
||||
sem_post(&iot_sem);
|
||||
|
||||
/*This resp pointer will be freed by diag module later*/
|
||||
return (void *)rsp1;
|
||||
}
|
||||
#endif /* IPQ_AP_HOST_IOT_QCA402X */
|
||||
|
||||
#ifdef IPQ_AP_HOST_IOT_IPQ
|
||||
/*===========================================================================
|
||||
FUNCTION iot_thr_func_ipq
|
||||
|
||||
DESCRIPTION
|
||||
Continously polls IPQ BTSS for asynchronous data responses and
|
||||
logs received asynchronous data responses to Diag module using
|
||||
log-submit()
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns NULL on failure. Function also exits with NULL return value
|
||||
when main indicates that this thread should be stopped
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
void *iot_thr_func_ipq(void *hdl)
|
||||
{
|
||||
int bytes_read = 0, handle = 0;
|
||||
void *buffer = NULL;
|
||||
void *rsp = NULL;
|
||||
struct timespec ts;
|
||||
ftm_bt_rsp_pkt_type *ftm_async_pkt;
|
||||
|
||||
buffer = malloc(MAX_BUF_SIZE);
|
||||
if (!buffer)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate memory to the buffer \n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memset(buffer, MEMSET_RESET_VALUE, MAX_BUF_SIZE);
|
||||
|
||||
if(hdl == NULL || *((int*)hdl) < 0)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "\n Invalid Handle received from BTSS \n");
|
||||
free(buffer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
handle = *((int*)hdl);
|
||||
while(1)
|
||||
{
|
||||
if (thread_stop == 1) {
|
||||
DPRINTF(FTM_DBG_TRACE, "FTMd: Exiting thread.\n");
|
||||
break;
|
||||
}
|
||||
|
||||
if (clock_gettime(CLOCK_REALTIME, &ts) == -1)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "clock_gettime");
|
||||
free(buffer);
|
||||
return NULL;
|
||||
}
|
||||
ts.tv_sec += user_sem_wait_timeout;
|
||||
sem_timedwait(&iot_sem, &ts);
|
||||
while((bytes_read = bt_daemon_receive(handle, &buffer)) > 0)
|
||||
{
|
||||
/*
|
||||
* Checking for log status on the packets received
|
||||
* ignore the received packets incase of disabled logging
|
||||
*/
|
||||
if(log_status(LOG_BT_HCI_EV_C))
|
||||
{
|
||||
rsp = log_alloc(LOG_BT_HCI_EV_C, (DIAG_HEADER_SIZE + bytes_read));
|
||||
if (!rsp)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "Could not allocate rsp packet \n");
|
||||
free(buffer);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ftm_async_pkt = (ftm_bt_rsp_pkt_type*)rsp;
|
||||
memcpy(ftm_async_pkt->buf, buffer, bytes_read);
|
||||
DPRINTF(FTM_DBG_TRACE, "\n Printing the Async Packet sent to QDART\n");
|
||||
print_array((uint8_t *)rsp, (DIAG_HEADER_SIZE + bytes_read));
|
||||
|
||||
log_submit(rsp);
|
||||
log_free(rsp);
|
||||
memset(buffer, MEMSET_RESET_VALUE, MAX_BUF_SIZE);
|
||||
}
|
||||
}
|
||||
sem_post(&iot_sem_async);
|
||||
}
|
||||
free(buffer);
|
||||
pthread_exit(NULL);
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_iot_dispatch_ipq
|
||||
|
||||
DESCRIPTION
|
||||
Function processes WIN IOT specific requests and relays to
|
||||
BTSS for further processing. Constructs response packet
|
||||
and returns buffer meant for callback.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns back buffer that is meant for diag callback
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
void *ftm_iot_dispatch_ipq(void *iot_ftm_pkt, int pkt_len, int *hdl)
|
||||
{
|
||||
void *rsp = NULL;
|
||||
struct timespec ts;
|
||||
int bytes_sent = -1;
|
||||
|
||||
if(hdl == NULL || *hdl < 0)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "\n Invalid Handle received from BTSS \n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!iot_ftm_pkt)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "Invalid iot_ftm_pkt received \n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (clock_gettime(CLOCK_REALTIME, &ts) == -1)
|
||||
{
|
||||
perror("clock_gettime");
|
||||
return NULL;
|
||||
}
|
||||
ts.tv_sec += user_sem_wait_timeout;
|
||||
sem_timedwait(&iot_sem_async, &ts);
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "\n Request Packet received for IPQ BT\n");
|
||||
print_array((uint8_t *)iot_ftm_pkt, pkt_len);
|
||||
|
||||
bytes_sent = bt_daemon_send(*hdl, iot_ftm_pkt);
|
||||
if(bytes_sent < 0)
|
||||
{
|
||||
perror("Unable to send Request Packet to IPQ BT");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Constructing ACK Packet */
|
||||
rsp = diagpkt_subsys_alloc(DIAG_SUBSYS_FTM, ftm_iot_cmd_code, pkt_len);
|
||||
if (!rsp)
|
||||
{
|
||||
DPRINTF(FTM_DBG_ERROR, "\n Unable to allocate diag response packet \n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(rsp, iot_ftm_pkt, pkt_len);
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "\n ACK Packet constructed in FTM layer\n");
|
||||
print_array((uint8_t *)rsp, pkt_len);
|
||||
|
||||
sem_post(&iot_sem);
|
||||
|
||||
/*This rsp pointer will be freed by diag later */
|
||||
return rsp;
|
||||
}
|
||||
#endif /* IPQ50XX, IPQ95XX */
|
||||
|
||||
void *ftm_iot_dispatch(void *iot_ftm_pkt, int pkt_len, void *hdl)
|
||||
{
|
||||
void* retValue = NULL;
|
||||
#ifdef IPQ_AP_HOST_IOT_QCA402X
|
||||
retValue = ftm_iot_dispatch_qca402x(iot_ftm_pkt, pkt_len ,hdl);
|
||||
#endif
|
||||
#ifdef IPQ_AP_HOST_IOT_IPQ
|
||||
retValue = ftm_iot_dispatch_ipq(iot_ftm_pkt, pkt_len ,(int *)hdl);
|
||||
#endif /* IPQ50XX, IPQ95XX */
|
||||
return retValue;
|
||||
}
|
||||
|
||||
#endif /*ifdef IPQ_AP_HOST_IOT*/
|
||||
132
feeds/ipq95xx/ftm/src/ftm_iot.h
Executable file
132
feeds/ipq95xx/ftm/src/ftm_iot.h
Executable file
@@ -0,0 +1,132 @@
|
||||
/*
|
||||
*Copyright (c) 2018-2020, 2022 Qualcomm Technologies, Inc.
|
||||
*
|
||||
*All Rights Reserved.
|
||||
*Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
/* IPQ-QCA402X specific file */
|
||||
#ifdef IPQ_AP_HOST_IOT
|
||||
|
||||
#include <semaphore.h>
|
||||
#include <time.h>
|
||||
#include "diagpkt.h"
|
||||
#include "log.h"
|
||||
|
||||
#define MFG_CMD_ID_BLE_HCI 4
|
||||
#define MFG_CMD_ID_I15P4_HMI 5
|
||||
#define MFG_CMD_ID_OTP_INVALID 256
|
||||
#define MFG_CMD_ID_OTP_SET_BITS 257
|
||||
#define MFG_CMD_ID_OTP_WRITE_BYTE 258
|
||||
#define MFG_CMD_ID_OTP_READ_BYTE 259
|
||||
#define MFG_CMD_ID_OTP_TLV_INIT 260
|
||||
#define MFG_CMD_ID_OTP_TLV_READ 261
|
||||
#define MFG_CMD_ID_OTP_TLV_WRITE 262
|
||||
#define MFG_CMD_ID_OTP_TLV_STATUS 263
|
||||
#define MFG_CMD_ID_OTP_TLV_DELETE 264
|
||||
|
||||
#define MFG_CMD_ID_RAWFLASH_INVALID 288
|
||||
#define MFG_CMD_ID_RAWFLASH_CLEAR_BITS 289
|
||||
#define MFG_CMD_ID_RAWFLASH_WRITE 290
|
||||
#define MFG_CMD_ID_RAWFLASH_READ 291
|
||||
#define MFG_CMD_ID_RAWFLASH_ERASE 292
|
||||
#define MFG_CMD_ID_RAWFLASH_DISABLE_MFG 293
|
||||
|
||||
#define MFG_CMD_ID_FS_INVALID 304
|
||||
#define MFG_CMD_ID_FS_READ 305
|
||||
#define MFG_CMD_ID_FS_WRITE 306
|
||||
#define MFG_CMD_ID_FS_DELETE 307
|
||||
#define MFG_CMD_ID_FS_LIST_SETUP 308
|
||||
#define MFG_CMD_ID_FS_LIST_NEXT 309
|
||||
#define MFG_CMD_ID_FS_MOUNT 310
|
||||
#define MFG_CMD_ID_FS_UNMOUNT 311
|
||||
|
||||
/* Add more MFG tool commands for QCA402x. These
|
||||
command are interpreted internally within QCA402x */
|
||||
#define MFG_CMD_ID_MISC_REBOOT 352
|
||||
#define MFG_CMD_ID_MISC_ADDR_READ 353
|
||||
#define MFG_CMD_ID_MISC_ADDR_WRITE 354
|
||||
#define MFG_CMD_ID_MISC_HWSS_DONE 355
|
||||
#define MFG_CMD_ID_MISC_XTAL_CAP_SET 356
|
||||
#define MFG_CMD_ID_MISC_PART_SZ_GET 357
|
||||
|
||||
/* Add MFG tool command to enable flashing of QCA402x
|
||||
by putting QCA402x in EDL mode and selecting USB mux
|
||||
select option to tie USB port 81 on IPQ402x to QCA402x */
|
||||
#define MFG_CMD_ID_MISC_PROG_MODE 358
|
||||
|
||||
/*Command to invalidate specified QCA402x Imageset */
|
||||
#define MFG_CMD_ID_MISC_FWUP 359
|
||||
/* Add MFG tool PROG_MODE subcommands to enable flashing
|
||||
of QCA402x on IPQ807x. Interpretation of sub-commands is as
|
||||
follows:
|
||||
|
||||
MFG_FLASH_ON - Put QCA402x into reset state, Put QCA402x in
|
||||
EDL mode and enable USB port to be tied to QCA402x
|
||||
|
||||
MFG_FLASH_OFF - Pull QCA402x out of EDL mode and Pull QCA402x
|
||||
out of reset
|
||||
|
||||
MFG_EDL_ON - Put QCA402x in EDL mode
|
||||
|
||||
MFG_FLASH_OFF - Pull QCA402x out of EDL mode
|
||||
|
||||
MFG_USB_ON - Enable USB port to be tied to QCA402x
|
||||
|
||||
MFG_USB_OFF - Enable USB port to be tied to IPQ807x
|
||||
|
||||
MFG_PROG_RESP - Expected response field
|
||||
*/
|
||||
|
||||
enum flash_state {
|
||||
MFG_PROG_RESP,
|
||||
MFG_FLASH_ON,
|
||||
MFG_FLASH_OFF,
|
||||
MFG_EDL_ON,
|
||||
MFG_EDL_OFF,
|
||||
MFG_USB_ON,
|
||||
MFG_USB_OFF
|
||||
};
|
||||
|
||||
typedef struct
|
||||
{
|
||||
uint8 start;
|
||||
uint8 version;
|
||||
uint16 length;
|
||||
} PACKED_STRUCT diag_nonhdlc_hdr_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
diag_nonhdlc_hdr_t hdr;
|
||||
byte payload[0];
|
||||
} PACKED_STRUCT ftm_iot_req_pkt_type;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
log_hdr_type hdr;
|
||||
byte buf[1];
|
||||
} PACKED_STRUCT ftm_bt_rsp_pkt_type;
|
||||
|
||||
/* Two semaphores are used to handle sequencing of requests, ack responses
|
||||
and multiple asynchronous data responses from QCA402x */
|
||||
|
||||
sem_t iot_sem;
|
||||
sem_t iot_sem_async;
|
||||
|
||||
int ftm_iot_cmd_code;
|
||||
int ftm_iot_dut_interface_code;
|
||||
int ftm_iot_reserved_code;
|
||||
int interface;
|
||||
int thread_stop;
|
||||
extern int user_sem_wait_timeout;
|
||||
|
||||
void *ftm_iot_dispatch(void *iot_ftm_pkt, int pkt_len, void *hdl);
|
||||
#ifdef IPQ_AP_HOST_IOT_QCA402X
|
||||
void *ftm_iot_dispatch_qca402x(void *iot_ftm_pkt, int pkt_len, void *hdl);
|
||||
void *iot_thr_func_qca402x(void *hdl);
|
||||
#endif
|
||||
#ifdef IPQ_AP_HOST_IOT_IPQ
|
||||
void *ftm_iot_dispatch_ipq(void *iot_ftm_pkt, int pkt_len, int *hdl);
|
||||
void *iot_thr_func_ipq(void *hdl);
|
||||
#endif /* IPQ50XX, IPQ95XX */
|
||||
#endif /*ifdef IPQ_AP_HOST_IOT*/
|
||||
1060
feeds/ipq95xx/ftm/src/ftm_main.c
Executable file
1060
feeds/ipq95xx/ftm/src/ftm_main.c
Executable file
File diff suppressed because it is too large
Load Diff
108
feeds/ipq95xx/ftm/src/ftm_nfc.c
Executable file
108
feeds/ipq95xx/ftm/src/ftm_nfc.c
Executable file
@@ -0,0 +1,108 @@
|
||||
/*=========================================================================
|
||||
NFC FTM C File
|
||||
Description
|
||||
This file contains the definitions of the function used to check
|
||||
which chip is present on the device.
|
||||
|
||||
Copyright (c) 2013-2015 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
|
||||
===========================================================================*/
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
===========================================================================*/
|
||||
|
||||
#include "ftm_nfc.h"
|
||||
|
||||
CHIP_TYPE chipType = UNDEFINED_CHIP_TYPE;
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION checkChip
|
||||
|
||||
DESCRIPTION
|
||||
Checks whether it can open the NQ Kernel, if not, it means
|
||||
the device has a QTI chip.
|
||||
|
||||
PARAMETERS
|
||||
None
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
===========================================================================*/
|
||||
void checkChip( void )
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
ret = ftm_nq_nfc_open( ); // can you open the NQ Kernel?
|
||||
|
||||
if( ret > 0 ) // yes
|
||||
{
|
||||
printf( "%s: NQ CHIP \n", __func__ );
|
||||
chipType = NQ_CHIP; // so it's an NQ Chip
|
||||
|
||||
ret = ftm_nq_nfc_close( ); // close the handle
|
||||
if( ret != 0 ) // not successful?
|
||||
{
|
||||
printf( "%s: Could not close the File Handle for NQ Chip \n", __func__ );
|
||||
chipType = CHIP_ERROR; // something is wrong
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf( "%s: QTI CHIP \n", __func__ );
|
||||
chipType = QTI_CHIP;
|
||||
}
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_dispatch
|
||||
|
||||
DESCRIPTION
|
||||
Dispatches QRCT commands and Chip Replies/Notifications/Data
|
||||
to the required FTM NFC Chip Handler
|
||||
|
||||
PARAMETERS
|
||||
ftm_nfc_pkt_type *nfc_ftm_pkt - FTM Packet
|
||||
uint16 pkt_len - FTM Packet Length
|
||||
|
||||
RETURN VALUE
|
||||
void *
|
||||
|
||||
===========================================================================*/
|
||||
void* ftm_nfc_dispatch( ftm_nfc_pkt_type *nfc_ftm_pkt, uint16 pkt_len )
|
||||
{
|
||||
ftm_nfc_pkt_type *reply = NULL;
|
||||
|
||||
if( UNDEFINED_CHIP_TYPE == chipType )
|
||||
{
|
||||
printf( "%s: Checking Chip Type \n", __func__ );
|
||||
checkChip( );
|
||||
}
|
||||
|
||||
switch( chipType )
|
||||
{
|
||||
case NQ_CHIP:
|
||||
if( nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id == FTM_NFC_REQ_CHIP_TYPE )
|
||||
reply = PrepareRsp( nfc_ftm_pkt );
|
||||
else
|
||||
reply = ftm_nfc_dispatch_nq( nfc_ftm_pkt, pkt_len );
|
||||
break;
|
||||
|
||||
case QTI_CHIP:
|
||||
if( nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id == FTM_NFC_REQ_CHIP_TYPE )
|
||||
reply = PrepareRsp( nfc_ftm_pkt );
|
||||
else
|
||||
reply = ftm_nfc_dispatch_qti( nfc_ftm_pkt, pkt_len );
|
||||
break;
|
||||
|
||||
default:
|
||||
printf( "%s: ERROR - THIS SHOULD HAVE NEVER BEEN REACHED, CHIP TYPE %d", __func__, chipType );
|
||||
break;
|
||||
}
|
||||
|
||||
return reply;
|
||||
}
|
||||
37
feeds/ipq95xx/ftm/src/ftm_nfc.h
Executable file
37
feeds/ipq95xx/ftm/src/ftm_nfc.h
Executable file
@@ -0,0 +1,37 @@
|
||||
/*=========================================================================
|
||||
NFC FTM HEADER File
|
||||
Description
|
||||
This file contains the definitions of the function used to check
|
||||
which chip is present on the device.
|
||||
|
||||
Copyright (c) 2013-2016 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
#ifndef _FTM_NFC
|
||||
#define _FTM_NFC
|
||||
|
||||
#include "ftm_nfcnq.h"
|
||||
|
||||
#define NFC_QCA1990 // Defnition to enable the NFC FTM inclusion
|
||||
|
||||
typedef enum _CHIP_TYPE{
|
||||
UNDEFINED_CHIP_TYPE = 0,
|
||||
QTI_CHIP = 1,
|
||||
NQ_CHIP = 2,
|
||||
CHIP_ERROR = 3,
|
||||
MAXIMUM_CHIP_TYPE = 4,
|
||||
} CHIP_TYPE;
|
||||
|
||||
extern CHIP_TYPE chipType;
|
||||
|
||||
void* ftm_nfc_dispatch(ftm_nfc_pkt_type *ftm_nfc_pkt, uint16 pkt_len);
|
||||
|
||||
void* ftm_nfc_dispatch_qti(ftm_nfc_pkt_type *ftm_nfc_pkt, uint16 pkt_len);
|
||||
|
||||
void ftm_nfc_dispatch_nq_fwdl();
|
||||
|
||||
void ftm_nfc_dispatch_nq_test(int argc, char **argv);
|
||||
#endif // _FTM_NFC
|
||||
807
feeds/ipq95xx/ftm/src/ftm_nfcnq.c
Executable file
807
feeds/ipq95xx/ftm/src/ftm_nfcnq.c
Executable file
@@ -0,0 +1,807 @@
|
||||
/*=========================================================================
|
||||
NQ NFC FTM C File
|
||||
Description
|
||||
This file contains the definitions of the functions
|
||||
used to communicate with the NQ Chip.
|
||||
|
||||
Copyright (c) 2015-2016 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
|
||||
===========================================================================*/
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
===========================================================================*/
|
||||
|
||||
#include "ftm_nfcnq.h"
|
||||
#include "ftm_nfc.h"
|
||||
#include "ftm_nfcnq_fwdl.h"
|
||||
|
||||
/* Global variables */
|
||||
pthread_t clientThread;
|
||||
PNCI_MESSAGE pNCIMessage;
|
||||
sem_t sRspReady;
|
||||
int fdNfc = 0;
|
||||
uint8_t nciReplyMessage[ 255 ] = { 0 };
|
||||
NQ_CHIP_TYPE whatNQChip = UNKNOWN_NQ_CHIP_TYPE;
|
||||
uint8_t RFdeactivateCmd[ ] = { 0x21, 0x06, 0x01, 0x03};
|
||||
uint8_t EseDataRsp[ ] = { 0x03, 0x00, 0x21, 0x99, 0x50, 0xFE};
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nq_nfc_close
|
||||
|
||||
DESCRIPTION
|
||||
Close the kernel driver for the NQ Chip
|
||||
|
||||
PARAMETERS
|
||||
None
|
||||
|
||||
RETURN VALUE
|
||||
int
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nq_nfc_close( void )
|
||||
{
|
||||
fdNfc = close( fdNfc ); // close the file descriptor
|
||||
|
||||
LOG_MESSAGE( "%s : Exit with fdNfc = %d \n", __func__, fdNfc );
|
||||
|
||||
return fdNfc; // return the result
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nq_nfc_open
|
||||
|
||||
DESCRIPTION
|
||||
Open the kernel driver for the NQ Chip
|
||||
|
||||
PARAMETERS
|
||||
None
|
||||
|
||||
RETURN VALUE
|
||||
int
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nq_nfc_open( void )
|
||||
{
|
||||
fdNfc = open( "/dev/nq-nci", // try to open /dev/nq-nci
|
||||
O_RDWR );
|
||||
|
||||
LOG_MESSAGE( "%s : Exit with fdNfc = %d \n", __func__, fdNfc );
|
||||
|
||||
return fdNfc; // return the result
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_hw_reset
|
||||
|
||||
DESCRIPTION
|
||||
Resets the NQ Chip
|
||||
|
||||
PARAMETERS
|
||||
None
|
||||
|
||||
RETURN VALUE
|
||||
int
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nfc_hw_reset( void )
|
||||
{
|
||||
|
||||
int ret = -1; // return value
|
||||
|
||||
do
|
||||
{
|
||||
if( fdNfc < 0 ) // fdNfc valid?
|
||||
break;
|
||||
|
||||
ret = ioctl( fdNfc, NFC_SET_PWR, POWER_ON ); // turn the chip on
|
||||
if( ret != 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s ioctl( fdNfc, NFC_SET_PWR, POWER_ON ) returned %d", __func__, ret );
|
||||
ret = -2;
|
||||
break;
|
||||
}
|
||||
usleep( 1000 ); // wait
|
||||
|
||||
ret = ioctl( fdNfc, NFC_SET_PWR, POWER_OFF ); // turn the chip off
|
||||
if( ret != 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s ioctl( fdNfc, NFC_SET_PWR, POWER_OFF ) returned %d", __func__, ret );
|
||||
ret = -3;
|
||||
break;
|
||||
}
|
||||
usleep( 1000 ); // wait
|
||||
|
||||
ret = ioctl( fdNfc, NFC_SET_PWR, POWER_ON ); // turn the chip back on
|
||||
if( ret != 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s ioctl( fdNfc, NFC_SET_PWR, POWER_ON ) returned %d", __func__, ret );
|
||||
ret = -4;
|
||||
break;
|
||||
}
|
||||
|
||||
}while( 0 );
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION PrintBytes
|
||||
|
||||
DESCRIPTION
|
||||
Print bytes from an array
|
||||
|
||||
PARAMETERS
|
||||
uint8_t *buf - Byte array to print
|
||||
uint8_t len - Length of the array
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
===========================================================================*/
|
||||
void PrintBytes( uint8_t *buf, uint8_t len)
|
||||
{
|
||||
#ifdef NFC_FTM_DEBUG
|
||||
int idx;
|
||||
|
||||
LOG_INFORMATION( "%s: Length: %d bytes \n", __func__, len ); // print the number of bytes
|
||||
for( idx = 0; idx < len; idx++ ) // print every byte
|
||||
{
|
||||
LOG_INFORMATION( "%02x ", buf[idx] );
|
||||
}
|
||||
LOG_INFORMATION( "\n" );
|
||||
#else
|
||||
UNUSED_PARAMETER( buf );
|
||||
UNUSED_PARAMETER( len );
|
||||
#endif
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_send
|
||||
|
||||
DESCRIPTION
|
||||
Sends a message to the chip
|
||||
|
||||
PARAMETERS
|
||||
uint8_t *buf - buffer to be sent
|
||||
int len - the length of the buffer
|
||||
|
||||
RETURN VALUE
|
||||
int ret - Status
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nfc_send( uint8_t* buf )
|
||||
{
|
||||
int ret = -1; // return value
|
||||
int retries = 15; // number of retries
|
||||
int i;
|
||||
uint16_t nciSendMessageLength;
|
||||
PNCI_MESSAGE pMessageToSend = ( PNCI_MESSAGE ) buf;
|
||||
pfirmware_download_packet_t pFirmwarePacketsToSend =
|
||||
( pfirmware_download_packet_t ) buf;
|
||||
|
||||
|
||||
do
|
||||
{
|
||||
if( fdNfc < 0 ) // fdNfc valid?
|
||||
break;
|
||||
|
||||
if( NULL == buf ) // is the buffer valid?
|
||||
{
|
||||
ret = -2;
|
||||
LOG_ERROR( "%s: buf == NULL Invalid Buffer", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
if( ( pFirmwarePacketsToSend->fFragmentedPacket == FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_NONE ) ||
|
||||
( pFirmwarePacketsToSend->fFragmentedPacket == FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_SET ) )
|
||||
nciSendMessageLength = pFirmwarePacketsToSend->payloadLen +
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN +
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN;
|
||||
else
|
||||
nciSendMessageLength = pMessageToSend->len + offsetof( NCI_MESSAGE, buf );
|
||||
|
||||
PrintBytes( buf, nciSendMessageLength );
|
||||
|
||||
do
|
||||
{
|
||||
retries--; // retries left
|
||||
ret = write( fdNfc,
|
||||
buf,
|
||||
nciSendMessageLength ); // try to write
|
||||
|
||||
if( ret < nciSendMessageLength ) // did you write the length?
|
||||
{
|
||||
LOG_MESSAGE( "%s: %d = write( fdNfc, buf, nciSendMessageLength ), errno = %d, tries left = %d \n", __func__, ret, errno, retries );
|
||||
continue; // try again
|
||||
}
|
||||
else
|
||||
break; // done
|
||||
|
||||
} while( retries > 0 );
|
||||
} while( 0 );
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ProcessCommand
|
||||
|
||||
DESCRIPTION
|
||||
Processes a Command for the NQ Chip
|
||||
|
||||
PARAMETERS
|
||||
uint8_t *nci_data - NCI Data to send
|
||||
|
||||
RETURN VALUE
|
||||
int ret - 0 if successfully received a reply
|
||||
|
||||
===========================================================================*/
|
||||
int ProcessCommand( uint8_t *nci_data )
|
||||
{
|
||||
int ret = -1; // return value
|
||||
struct timespec time_sec;
|
||||
|
||||
do
|
||||
{
|
||||
LOG_MESSAGE( "%s: FTM_NFC_SEND_DATA \n", __func__ );
|
||||
|
||||
ret = ftm_nfc_send( nci_data ); // send the message
|
||||
|
||||
LOG_MESSAGE( "%s: Wait for response \n", __func__ );
|
||||
|
||||
ret = clock_gettime( CLOCK_REALTIME, &time_sec );
|
||||
|
||||
if( ret == -1 )
|
||||
{ // didn't get the time?
|
||||
LOG_ERROR( "%s: clock_gettime for nci_data error \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
time_sec.tv_sec += FTM_NFC_CMD_CMPL_TIMEOUT; // maximum wait
|
||||
ret = sem_timedwait( &sRspReady, // start waiting
|
||||
&time_sec );
|
||||
|
||||
if( ret == -1 ) // wait finished, not signalled?
|
||||
{
|
||||
if(!ese_dwp_test)
|
||||
LOG_ERROR( "%s: nfc ftm command timed out \n", __func__ );
|
||||
break;
|
||||
}
|
||||
} while( 0 );
|
||||
|
||||
return ret;
|
||||
}
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_read
|
||||
|
||||
DESCRIPTION
|
||||
Reads a message from the chip
|
||||
|
||||
PARAMETERS
|
||||
int len - the length of the buffer
|
||||
|
||||
RETURN VALUE
|
||||
int ret - Number of bytes read
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nfc_read( uint8_t* buf, int len )
|
||||
{
|
||||
int ret = -1;
|
||||
|
||||
do
|
||||
{
|
||||
if( fdNfc < 0 ) // fdNfc valid?
|
||||
break;
|
||||
|
||||
ret = read( fdNfc, buf, len ); // try to read
|
||||
|
||||
} while( 0 );
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*==========================================================================
|
||||
FUNCTION
|
||||
CommitLog
|
||||
|
||||
DESCRIPTION
|
||||
This commits the log to Diag
|
||||
|
||||
PARAMETERS
|
||||
NCI_MESSAGE pReadNCIMessage - Pointer to the read NCI Message
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
==========================================================================*/
|
||||
void CommitLog( PNCI_MESSAGE pReadNCIMessage )
|
||||
{
|
||||
pftm_nfc_log_pkt_type pLogBuff;
|
||||
|
||||
do
|
||||
{
|
||||
pLogBuff = ( ftm_nfc_log_pkt_type * ) log_alloc( LOG_NFC_FTM, // allocate a buffer for the log
|
||||
pReadNCIMessage->len + offsetof( NCI_MESSAGE, buf ) + LOG_HEADER_LENGTH );
|
||||
if( NULL == pLogBuff )
|
||||
{
|
||||
LOG_ERROR( "%s: log_alloc returned NULL \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
memcpy( pLogBuff->data, // fill the buffer
|
||||
pReadNCIMessage,
|
||||
pReadNCIMessage->len + offsetof( NCI_MESSAGE, buf ) );
|
||||
|
||||
log_commit( pLogBuff ); // commit the log
|
||||
} while ( 0 );
|
||||
|
||||
}
|
||||
|
||||
/*=============================================================================
|
||||
FUNCTION
|
||||
ProcessReturnedMessage
|
||||
|
||||
DESCRIPTION
|
||||
Routine that processes an NCI Message that was returned and
|
||||
will decide if the message is a notification or a response.
|
||||
|
||||
PARAMETERS
|
||||
PNCI_MESSAGE pReadNCIMessage - Pointer to the read message
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
==============================================================================*/
|
||||
void ProcessReturnedMessage( PNCI_MESSAGE pReadNCIMessage )
|
||||
{
|
||||
|
||||
switch( pReadNCIMessage->gid & NCIMT_NTF ) // check the first byte
|
||||
{
|
||||
case NCIMT_RSP: // reply?
|
||||
sem_post( &sRspReady ); // notify the dispatch function
|
||||
break;
|
||||
|
||||
case NCIMT_NTF: // notification?
|
||||
if (pReadNCIMessage->oid == 0x05)
|
||||
{
|
||||
LOG_INFORMATION("\n << ...TAG DETECTED... >> \n");
|
||||
printTecnologyDetails(pReadNCIMessage->buf[3],pReadNCIMessage->buf[2]);
|
||||
sem_post( &sRfNtf );
|
||||
ProcessCommand( RFdeactivateCmd );
|
||||
}
|
||||
case NCIMT_DATA: // data?
|
||||
if (ese_dwp_test)
|
||||
{
|
||||
if( memcmp( EseDataRsp, nciReplyMessage, sizeof( EseDataRsp ) ) == 0 )
|
||||
{
|
||||
LOG_INFORMATION("\n << ESE detected over DWP >> \n\n");
|
||||
}
|
||||
}
|
||||
if( log_status( LOG_NFC_FTM ) ) // logging enabled?
|
||||
{
|
||||
CommitLog( pReadNCIMessage );
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
LOG_ERROR( "%s: ERROR - SHOULD NOT HAVE REACHED THIS POINT", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION nfc_read_thread
|
||||
|
||||
DESCRIPTION
|
||||
Thread that constantly looks for messages from the chip
|
||||
|
||||
PARAMETERS
|
||||
void
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
===========================================================================*/
|
||||
void *nfc_read_thread( void *arg )
|
||||
{
|
||||
uint8_t readLength = 0;
|
||||
int i;
|
||||
uint8_t readNCIUpToLength = offsetof( NCI_MESSAGE, buf );
|
||||
|
||||
UNUSED_PARAMETER( arg );
|
||||
|
||||
for( ; ; ) // keep reading
|
||||
{
|
||||
readLength = ftm_nfc_read( nciReplyMessage, readNCIUpToLength ); // read the first 3 bytes
|
||||
|
||||
if( readLength == readNCIUpToLength ) // read the message up to NCI Len?
|
||||
{
|
||||
readLength = ftm_nfc_read( pNCIMessage->buf, // go and get the rest
|
||||
pNCIMessage->len );
|
||||
|
||||
if( readLength == pNCIMessage->len ) // successful?
|
||||
{
|
||||
PrintBytes( nciReplyMessage, pNCIMessage->len + readNCIUpToLength );
|
||||
|
||||
ProcessReturnedMessage( pNCIMessage ); // Process the read message
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*==========================================================================
|
||||
FUNCTION PrepareRsp
|
||||
|
||||
DESCRIPTION
|
||||
Routine to prepare a response for diag.
|
||||
|
||||
PARAMETERS
|
||||
ftm_nfc_pkt_type *nfc_ftm_pkt - FTM Packet
|
||||
|
||||
RETURN VALUE
|
||||
void *
|
||||
==========================================================================*/
|
||||
void *PrepareRsp( ftm_nfc_pkt_type *nfc_ftm_pkt )
|
||||
{
|
||||
void *response = NULL;
|
||||
switch( nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id )
|
||||
{
|
||||
case FTM_NFC_NFCC_COMMAND:
|
||||
{
|
||||
ftm_nfc_pkt_type *nfc_nci_rsp = ( ftm_nfc_pkt_type* ) diagpkt_subsys_alloc( DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof( ftm_nfc_pkt_type ) ); // get a Response Buffer for NFCC Command
|
||||
|
||||
if( NULL == nfc_nci_rsp )
|
||||
{
|
||||
LOG_ERROR( "%s: diagpkt_subsys_alloc( DIAG_SUBSYS_FTM, FTM_NFC_CMD_CODE, sizeof( ftm_nfc_pkt_type ) ) returned NULL \n", __func__ );
|
||||
}
|
||||
else
|
||||
{
|
||||
nfc_nci_rsp->ftm_nfc_hdr.nfc_cmd_id = FTM_NFC_NFCC_COMMAND;
|
||||
nfc_nci_rsp->ftm_nfc_hdr.nfc_cmd_len = offsetof( ftm_nfc_cmd_header, nfc_cmd_len ) + offsetof( NCI_MESSAGE, buf ) + pNCIMessage->len ;
|
||||
nfc_nci_rsp->nfc_nci_pkt_len = offsetof( NCI_MESSAGE, buf ) + pNCIMessage->len;
|
||||
|
||||
memcpy( nfc_nci_rsp->nci_data,
|
||||
pNCIMessage,
|
||||
nfc_nci_rsp->nfc_nci_pkt_len );
|
||||
|
||||
response = ( void* ) nfc_nci_rsp;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case FTM_NFC_REQ_CHIP_TYPE:
|
||||
{
|
||||
// change from a NCI packet type to a request chip type packet type
|
||||
ftm_nfc_chip_type_pkt_type *nfc_chip_type_rsp = ( ftm_nfc_chip_type_pkt_type* ) diagpkt_subsys_alloc( DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof( ftm_nfc_chip_type_pkt_type ) ); // get a Response Buffer for Request Chip Type Command
|
||||
if( NULL == nfc_chip_type_rsp )
|
||||
{
|
||||
LOG_ERROR( "%s: diagpkt_subsys_alloc( DIAG_SUBSYS_FTM, FTM_NFC_CMD_CODE, sizeof( ftm_nfc_chip_type_pkt_type ) ) returned NULL \n", __func__ );
|
||||
}
|
||||
else
|
||||
{
|
||||
nfc_chip_type_rsp->nfc_chip_type_cmd_id = FTM_NFC_REQ_CHIP_TYPE;
|
||||
nfc_chip_type_rsp->nfc_chip_type_pkt_len = 1; // only 1 byte for response packet data
|
||||
if( chipType == 1 ) // 1 for QTI, 2 for NQ
|
||||
nfc_chip_type_rsp->nfc_chip_type_pkt_data = FTM_NFC_QTI_CHIP;
|
||||
else
|
||||
nfc_chip_type_rsp->nfc_chip_type_pkt_data = FTM_NFC_NQ_CHIP;
|
||||
|
||||
response = ( void* ) nfc_chip_type_rsp;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case FTM_NFC_FWPIN_CTRL:
|
||||
{
|
||||
// change from a NCI packet type to a firmware download packet type
|
||||
ftm_nfc_fwdl_pkt_type *nfc_fwdl_rsp = ( ftm_nfc_fwdl_pkt_type* ) diagpkt_subsys_alloc( DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof( ftm_nfc_fwdl_pkt_type ) ); // get a Response Buffer for Firmware Download Pin Command
|
||||
if( NULL == nfc_fwdl_rsp )
|
||||
{
|
||||
LOG_ERROR( "%s: diagpkt_subsys_alloc( DIAG_SUBSYS_FTM, FTM_NFC_CMD_CODE, sizeof( ftm_nfc_fwdl_pkt_type ) ) returned NULL \n", __func__ );
|
||||
}
|
||||
else
|
||||
{
|
||||
nfc_fwdl_rsp->nfc_fwdl_cmd_id = FTM_NFC_FWPIN_CTRL;
|
||||
nfc_fwdl_rsp->nfc_fwdl_pkt_len = 1; // only 1 byte for response packet data
|
||||
nfc_fwdl_rsp->nfc_fwdl_pkt_data = FTM_NFC_FWDL_SUCCESS; // 0 for fail, 1 for success
|
||||
|
||||
response = ( void* ) nfc_fwdl_rsp;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
default :
|
||||
|
||||
LOG_ERROR( "%s: ERROR - SHOULD NOT HAVE ENDED UP HERE: default case \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
return response;
|
||||
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_nq_vs_nxp
|
||||
|
||||
DESCRIPTION
|
||||
Check whether the chip is an NQ Chip
|
||||
|
||||
PARAMETERS
|
||||
None
|
||||
|
||||
RETURN VALUE
|
||||
int
|
||||
|
||||
===========================================================================*/
|
||||
int ftm_nfc_nq_vs_nxp( void )
|
||||
{
|
||||
int ret = 0;
|
||||
uint8_t coreResetCmd[ ] = { 0x20, 0x00, 0x01, 0x00 };
|
||||
uint8_t coreResetRsp[ ] = { 0x40, 0x00, 0x03, 0x00, 0x11, 0x00 };
|
||||
uint8_t coreInitCmd[ ] = { 0x20, 0x01, 0x00 };
|
||||
|
||||
do
|
||||
{
|
||||
ret = ProcessCommand( coreResetCmd ); // send a Core Reset CMD
|
||||
|
||||
if( ret == -1 ) // wait finished, not signalled?
|
||||
{
|
||||
LOG_ERROR( "%s: ProcessCommand( coreResetCmd ) error %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
if( memcmp( coreResetRsp, nciReplyMessage, sizeof( coreResetRsp ) ) )
|
||||
{ // not a good reply?
|
||||
coreResetRsp[4] = 0x10;
|
||||
if( memcmp( coreResetRsp, nciReplyMessage, sizeof( coreResetRsp ) ) )
|
||||
{ // check if NCI version is 1.0
|
||||
ret = -1;
|
||||
LOG_ERROR( "%s: bad reply for coreResetRsp", __func__ );
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ret = ProcessCommand( coreInitCmd ); // send the message
|
||||
|
||||
if( ret == -1 ) // wait finished, not signalled?
|
||||
{
|
||||
LOG_ERROR( "%s: ProcessCommand( coreInitCmd ) error %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
switch( nciReplyMessage[ CHIP_ID ] ) // what type of chip is it?
|
||||
{
|
||||
case 0x48:
|
||||
whatNQChip = NQ_210;
|
||||
LOG_INFORMATION( "Connected to NQ210 \n" );
|
||||
break;
|
||||
|
||||
case 0x58:
|
||||
whatNQChip = NQ_220;
|
||||
LOG_INFORMATION( "Connected to NQ220 \n" );
|
||||
break;
|
||||
|
||||
case 0x40:
|
||||
case 0x41:
|
||||
whatNQChip = NQ_310;
|
||||
LOG_INFORMATION( "Connected to NQ310 \n" );
|
||||
break;
|
||||
|
||||
case 0x50:
|
||||
case 0x51:
|
||||
whatNQChip = NQ_330;
|
||||
LOG_INFORMATION( "Connected to NQ330 \n" );
|
||||
break;
|
||||
|
||||
default:
|
||||
whatNQChip = UNKNOWN_NQ_CHIP_TYPE;
|
||||
ret = -1;
|
||||
LOG_INFORMATION( "ERROR Connected to an unknown NQ Chip \n" );
|
||||
break;
|
||||
}
|
||||
}while( 0 );
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_set_fwdl_pin
|
||||
|
||||
DESCRIPTION
|
||||
Sets or resets the firmware download pin high or low
|
||||
|
||||
PARAMETERS
|
||||
ftm_nfc_pkt_type *nfc_ftm_pkt - FTM Packet
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
===========================================================================*/
|
||||
void ftm_nfc_set_fwdl_pin( ftm_nfc_pkt_type *nfc_ftm_pkt )
|
||||
{
|
||||
int ret = 0;
|
||||
// change from a NCI packet type to a firmware download packet type
|
||||
pftm_nfc_fwdl_pkt_type pnfc_fwdl_pkt = ( pftm_nfc_fwdl_pkt_type ) nfc_ftm_pkt;
|
||||
|
||||
switch ( pnfc_fwdl_pkt->nfc_fwdl_pkt_data )
|
||||
{
|
||||
case 0:
|
||||
|
||||
ret = ftm_nfc_hw_reset( ); // Can you reset the hardware?
|
||||
if( ret < 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nfc_hw_reset() failed with ret = %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_MESSAGE( "%s: Firmware download pin set LOW\n", __func__ );
|
||||
break;
|
||||
|
||||
|
||||
case 1:
|
||||
|
||||
ret = ioctl( fdNfc, NFC_SET_PWR, FIRMWARE_MODE );
|
||||
if( ret != 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s ioctl( fdNfc, NFC_SET_PWR, FIRMWARE_MODE ) returned %d", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_MESSAGE( "%s: Firmware download pin set HIGH\n", __func__ );
|
||||
break;
|
||||
|
||||
default :
|
||||
|
||||
LOG_ERROR( "%s: ERROR - SHOULD NOT HAVE ENDED UP HERE: default case \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
ret = ftm_nq_nfc_close( ); // close the handle
|
||||
if( ret != 0 ) // not successful?
|
||||
{
|
||||
LOG_ERROR( "\n\t %s: ftm_nq_nfc_close() failed with ret = %d \n", __func__, ret );
|
||||
}
|
||||
|
||||
ret = ftm_nq_nfc_open( ); // open the kernel driver
|
||||
if( ret < 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "\n\t %s: ftm_nq_nfc_open() failed with ret = %d \n", __func__, ret );
|
||||
}
|
||||
}
|
||||
|
||||
/*=========================================================================
|
||||
FUNCTION ftm_nfc_dispatch_nq
|
||||
|
||||
DESCRIPTION
|
||||
Dispatches QRCT commands and Chip Replies/Notifications/Data
|
||||
|
||||
PARAMETERS
|
||||
ftm_nfc_pkt_type *nfc_ftm_pkt - FTM Packet
|
||||
uint16 pkt_len - FTM Packet Length
|
||||
|
||||
RETURN VALUE
|
||||
void *
|
||||
|
||||
===========================================================================*/
|
||||
void* ftm_nfc_dispatch_nq( ftm_nfc_pkt_type *nfc_ftm_pkt, uint16 pkt_len )
|
||||
{
|
||||
int ret = 0;
|
||||
int len = 0;
|
||||
struct timespec time_sec;
|
||||
char *SkipNQHardwareCheck = NULL;
|
||||
|
||||
void *rsp = NULL;
|
||||
UNUSED_PARAMETER( pkt_len );
|
||||
|
||||
do
|
||||
{
|
||||
if( !fdNfc ) // Already initialized?
|
||||
{
|
||||
ret = ftm_nq_nfc_open( ); // open the kernel driver
|
||||
if( ret < 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "\n\t %s: ftm_nq_nfc_open() failed with ret = %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
ret = ftm_nfc_hw_reset( ); // Can you reset the hardware?
|
||||
if( ret < 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nfc_hw_reset() failed with ret = %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
pNCIMessage = ( PNCI_MESSAGE ) nciReplyMessage;
|
||||
|
||||
ret = pthread_create( &clientThread, // Start the Read Thread
|
||||
NULL,
|
||||
&nfc_read_thread,
|
||||
NULL );
|
||||
if( ret != 0 ) // successful?
|
||||
{
|
||||
LOG_MESSAGE( "%s: pthread_create( nfc_read_thread ) failed with ret = %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
|
||||
SkipNQHardwareCheck = getenv( SKIP_NQ_HARDWARE_CHECK );
|
||||
LOG_MESSAGE( "%s: SkipNQHardwareCheck = %s \n", __func__, SkipNQHardwareCheck );
|
||||
|
||||
if( NULL == SkipNQHardwareCheck ) // no value so check for NQ Chip?
|
||||
{
|
||||
ret = ftm_nfc_nq_vs_nxp( );
|
||||
if( ret < 0 ) // Not an NQ Chip?
|
||||
{
|
||||
LOG_ERROR( "ERROR NOT A KNOWN NQ Chip \n" );
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_INFORMATION( " Skipping NQ Chip Check \n" );
|
||||
whatNQChip = SKIP_CHIP_CHECK;
|
||||
}
|
||||
|
||||
LOG_INFORMATION( "FTM for NFC SUCCESSFULLY STARTED \n" );
|
||||
}
|
||||
|
||||
if( UNKNOWN_NQ_CHIP_TYPE == whatNQChip )
|
||||
{
|
||||
LOG_ERROR( "ERROR This version of the chip is not accepted" );
|
||||
break;
|
||||
}
|
||||
|
||||
if( NULL == nfc_ftm_pkt ) // valid packet?
|
||||
{
|
||||
LOG_ERROR( "%s: Error : nfc_ftm_pkt is NULL \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
if( offsetof( ftm_nfc_pkt_type, ftm_nfc_hdr ) < MIN_CMD_PKT_LEN )
|
||||
{ // packet contains anything?
|
||||
LOG_ERROR( "%s: Error : Invalid FTM Packet \n", __func__ );
|
||||
break;
|
||||
}
|
||||
|
||||
switch( nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id ) // what type of packet is it?
|
||||
{
|
||||
|
||||
case FTM_NFC_NFCC_COMMAND: // NFC Command?
|
||||
case FTM_NFC_SEND_DATA: // NFC Data?
|
||||
|
||||
ret = ProcessCommand( nfc_ftm_pkt->nci_data );
|
||||
if( ret == -1 ) // wait finished, not signalled?
|
||||
{
|
||||
LOG_ERROR( "%s: ProcessCommand( nfc_ftm_pkt->nci_data ) error %d \n", __func__, ret );
|
||||
break;
|
||||
}
|
||||
rsp = PrepareRsp( nfc_ftm_pkt ); // Prepare the response for Diag
|
||||
|
||||
break;
|
||||
|
||||
case FTM_NFC_REQ_CHIP_TYPE:
|
||||
case FTM_NFC_FWPIN_CTRL:
|
||||
|
||||
ftm_nfc_set_fwdl_pin( nfc_ftm_pkt );
|
||||
|
||||
rsp = PrepareRsp( nfc_ftm_pkt ); // Prepare the response for Diag
|
||||
break;
|
||||
|
||||
default :
|
||||
LOG_ERROR( "%s: ERROR - SHOULD NOT HAVE ENDED UP HERE: default case \n", __func__ );
|
||||
break;
|
||||
|
||||
}
|
||||
} while( 0 );
|
||||
|
||||
return rsp;
|
||||
}
|
||||
168
feeds/ipq95xx/ftm/src/ftm_nfcnq.h
Executable file
168
feeds/ipq95xx/ftm/src/ftm_nfcnq.h
Executable file
@@ -0,0 +1,168 @@
|
||||
/*=========================================================================
|
||||
NQ NFC FTM Header File
|
||||
Description
|
||||
This file contains the declarations of the functions
|
||||
used to communicate with the NQ Chip and various definitions.
|
||||
|
||||
Copyright (c) 2015-2017 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
|
||||
===========================================================================*/
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
===========================================================================*/
|
||||
|
||||
#ifndef _FTM_NFCNQ
|
||||
#define _FTM_NFCNQ
|
||||
|
||||
#include "msg.h"
|
||||
#include "diagpkt.h"
|
||||
#include "diagcmd.h"
|
||||
#include "errno.h"
|
||||
#include <linux/ioctl.h>
|
||||
#include <pthread.h>
|
||||
#include <semaphore.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "log.h"
|
||||
|
||||
#define LOG_ERROR( ... ) printf( __VA_ARGS__ )
|
||||
#define LOG_INFORMATION( ... ) printf( __VA_ARGS__ )
|
||||
|
||||
#ifdef NFC_FTM_DEBUG
|
||||
#define LOG_MESSAGE( ... ) printf( __VA_ARGS__ )
|
||||
#else
|
||||
#define LOG_MESSAGE( ... ) do{ } while ( FALSE )
|
||||
#endif
|
||||
|
||||
typedef PACKED struct _ftm_nfc_cmd_header{
|
||||
uint16 nfc_cmd_id;
|
||||
uint16 nfc_cmd_len;
|
||||
} ftm_nfc_cmd_header, *pftm_nfc_cmd_header;
|
||||
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
ftm_nfc_cmd_header ftm_nfc_hdr;
|
||||
uint16 nfc_nci_pkt_len;
|
||||
byte nci_data[258];
|
||||
}ftm_nfc_pkt_type, *pftm_nfc_pkt_type;
|
||||
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
uint16 nfc_fwdl_cmd_id;
|
||||
byte nfc_fwdl_pkt_len;
|
||||
byte nfc_fwdl_pkt_data;
|
||||
}ftm_nfc_fwdl_pkt_type, *pftm_nfc_fwdl_pkt_type;
|
||||
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
uint16 nfc_chip_type_cmd_id;
|
||||
byte nfc_chip_type_pkt_len;
|
||||
byte nfc_chip_type_pkt_data;
|
||||
}ftm_nfc_chip_type_pkt_type, *pftm_nfc_chip_type_pkt_type;
|
||||
|
||||
typedef PACKED struct{
|
||||
log_hdr_type hdr;
|
||||
byte data[1];
|
||||
} ftm_nfc_log_pkt_type, *pftm_nfc_log_pkt_type;
|
||||
|
||||
typedef PACKED struct _NCI_MESSAGE
|
||||
{
|
||||
byte gid; // Group ID
|
||||
byte oid; // Operation ID
|
||||
byte len; // payload length in bytes
|
||||
byte buf[ 252 ]; // Payload Buffer
|
||||
} NCI_MESSAGE, *PNCI_MESSAGE;
|
||||
|
||||
typedef enum
|
||||
{
|
||||
NCIMT_DATA = 0x00, /**< DATA packet. */
|
||||
NCIMT_CMD = 0x20, /**< Control packet - Command. */
|
||||
NCIMT_RSP = 0x40, /**< Control packet - Response. */
|
||||
NCIMT_NTF = 0x60, /**< Control packet - Notification. */
|
||||
|
||||
NCIMT_INVALID_VALUE = 0xFF, /**< Invalid packet type. */
|
||||
|
||||
NCIMT_BITMASK = 0xE0, /**< Most significant three bits. */
|
||||
NCIMT_BITSHIFT = 5
|
||||
|
||||
} NCIMT;
|
||||
|
||||
typedef enum
|
||||
{
|
||||
UNKNOWN_NQ_CHIP_TYPE = 0,
|
||||
SKIP_CHIP_CHECK = 1,
|
||||
NQ_110 = 11,
|
||||
NQ_120 = 12,
|
||||
NQ_210 = 21,
|
||||
NQ_220 = 22,
|
||||
NQ_310 = 31,
|
||||
NQ_330 = 33,
|
||||
MAXIMUM_NQ_CHIP_TYPE
|
||||
} NQ_CHIP_TYPE;
|
||||
|
||||
struct nqx_devinfo
|
||||
{
|
||||
unsigned char chip_type;
|
||||
unsigned char rom_version;
|
||||
unsigned char fw_major;
|
||||
unsigned char fw_minor;
|
||||
};
|
||||
|
||||
union nqx_uinfo
|
||||
{
|
||||
unsigned int i;
|
||||
struct nqx_devinfo info;
|
||||
};
|
||||
|
||||
int ftm_nq_nfc_open( void );
|
||||
int ftm_nq_nfc_close( void );
|
||||
int ftm_nfc_hw_reset( void );
|
||||
int ProcessCommand( uint8_t *nci_data );
|
||||
void *PrepareRsp( ftm_nfc_pkt_type *nfc_ftm_pkt );
|
||||
void *ftm_nfc_dispatch_nq( ftm_nfc_pkt_type *nfc_ftm_pkt, uint16 pkt_len);
|
||||
void *nfc_read_thread( void *arg );
|
||||
extern sem_t sRfNtf;
|
||||
extern int ese_dwp_test;
|
||||
extern void printTecnologyDetails(char technology, char protocol);
|
||||
|
||||
#define FTM_NFC_CMD_CODE 55
|
||||
#define FTM_NFC_NFCC_COMMAND 0x02
|
||||
#define FTM_NFC_SEND_DATA 0x03
|
||||
#define FTM_NFC_REQ_CHIP_TYPE 0x04
|
||||
#define FTM_NFC_FWPIN_CTRL 0x05
|
||||
#define FTM_NFC_CMD_CMPL_TIMEOUT 3
|
||||
|
||||
#define FTM_NFC_QTI_CHIP 0x00
|
||||
#define FTM_NFC_NQ_CHIP 0x01
|
||||
#define FTM_NFC_FWDL_SUCCESS 0x01
|
||||
|
||||
#define MIN_CMD_PKT_LEN 4 // Minimum length for a valid FTM packet, 2 bytes for Diag header, 2 bytes for command ID
|
||||
|
||||
#define LOG_NFC_FTM 0x1802
|
||||
#define LOG_HEADER_LENGTH 12
|
||||
|
||||
#define NFC_SET_PWR _IOW(0xE9, 0x01, unsigned int)
|
||||
#define NFCC_GET_INFO _IOW(0xE9, 0x09, unsigned int)
|
||||
#define POWER_OFF 0
|
||||
#define POWER_ON 1
|
||||
#define FIRMWARE_MODE 2
|
||||
|
||||
#define EXPECTED_CORE_INIT_RSP_LEN 29
|
||||
#define CHIP_ID 24
|
||||
|
||||
#define SKIP_NQ_HARDWARE_CHECK "SkipNQHardwareCheck"
|
||||
#define HARDWARE_TYPE_TIMEOUT 2
|
||||
|
||||
#define UNUSED_PARAMETER( x ) ( void )( x )
|
||||
|
||||
#endif // _FTM_NFCNQ
|
||||
664
feeds/ipq95xx/ftm/src/ftm_nfcnq_fwdl.c
Executable file
664
feeds/ipq95xx/ftm/src/ftm_nfcnq_fwdl.c
Executable file
@@ -0,0 +1,664 @@
|
||||
/*
|
||||
* Copyright (c) 2016-2017 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Not a Contribution.
|
||||
* Apache license notifications and license are retained
|
||||
* for attribution purposes only.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2015 NXP Semiconductors
|
||||
* The original Work has been changed by NXP Semiconductors.
|
||||
*
|
||||
* Copyright (C) 2010 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/*=========================================================================
|
||||
FTM NFC NQ Firmware Download Source File
|
||||
Description
|
||||
This file contains the definitions of the functions
|
||||
used to download firmware onto the NQ Chip.
|
||||
===========================================================================*/
|
||||
|
||||
#include "ftm_nfcnq_fwdl.h"
|
||||
#include "ftm_nfcnq.h"
|
||||
|
||||
unsigned int chip_version = 0x00;
|
||||
|
||||
/* lookup table for CRC-16-CCITT calculation */
|
||||
static uint16_t const crcTable[ 256 ] =
|
||||
{ 0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50a5, 0x60c6, 0x70e7, 0x8108, 0x9129, 0xa14a, 0xb16b, 0xc18c, 0xd1ad,
|
||||
0xe1ce, 0xf1ef, 0x1231, 0x0210, 0x3273, 0x2252, 0x52b5, 0x4294, 0x72f7, 0x62d6, 0x9339, 0x8318, 0xb37b,
|
||||
0xa35a, 0xd3bd, 0xc39c, 0xf3ff, 0xe3de, 0x2462, 0x3443, 0x0420, 0x1401, 0x64e6, 0x74c7, 0x44a4, 0x5485,
|
||||
0xa56a, 0xb54b, 0x8528, 0x9509, 0xe5ee, 0xf5cf, 0xc5ac, 0xd58d, 0x3653, 0x2672, 0x1611, 0x0630, 0x76d7,
|
||||
0x66f6, 0x5695, 0x46b4, 0xb75b, 0xa77a, 0x9719, 0x8738, 0xf7df, 0xe7fe, 0xd79d, 0xc7bc, 0x48c4, 0x58e5,
|
||||
0x6886, 0x78a7, 0x0840, 0x1861, 0x2802, 0x3823, 0xc9cc, 0xd9ed, 0xe98e, 0xf9af, 0x8948, 0x9969, 0xa90a,
|
||||
0xb92b, 0x5af5, 0x4ad4, 0x7ab7, 0x6a96, 0x1a71, 0x0a50, 0x3a33, 0x2a12, 0xdbfd, 0xcbdc, 0xfbbf, 0xeb9e,
|
||||
0x9b79, 0x8b58, 0xbb3b, 0xab1a, 0x6ca6, 0x7c87, 0x4ce4, 0x5cc5, 0x2c22, 0x3c03, 0x0c60, 0x1c41, 0xedae,
|
||||
0xfd8f, 0xcdec, 0xddcd, 0xad2a, 0xbd0b, 0x8d68, 0x9d49, 0x7e97, 0x6eb6, 0x5ed5, 0x4ef4, 0x3e13, 0x2e32,
|
||||
0x1e51, 0x0e70, 0xff9f, 0xefbe, 0xdfdd, 0xcffc, 0xbf1b, 0xaf3a, 0x9f59, 0x8f78, 0x9188, 0x81a9, 0xb1ca,
|
||||
0xa1eb, 0xd10c, 0xc12d, 0xf14e, 0xe16f, 0x1080, 0x00a1, 0x30c2, 0x20e3, 0x5004, 0x4025, 0x7046, 0x6067,
|
||||
0x83b9, 0x9398, 0xa3fb, 0xb3da, 0xc33d, 0xd31c, 0xe37f, 0xf35e, 0x02b1, 0x1290, 0x22f3, 0x32d2, 0x4235,
|
||||
0x5214, 0x6277, 0x7256, 0xb5ea, 0xa5cb, 0x95a8, 0x8589, 0xf56e, 0xe54f, 0xd52c, 0xc50d, 0x34e2, 0x24c3,
|
||||
0x14a0, 0x0481, 0x7466, 0x6447, 0x5424, 0x4405, 0xa7db, 0xb7fa, 0x8799, 0x97b8, 0xe75f, 0xf77e, 0xc71d,
|
||||
0xd73c, 0x26d3, 0x36f2, 0x0691, 0x16b0, 0x6657, 0x7676, 0x4615, 0x5634, 0xd94c, 0xc96d, 0xf90e, 0xe92f,
|
||||
0x99c8, 0x89e9, 0xb98a, 0xa9ab, 0x5844, 0x4865, 0x7806, 0x6827, 0x18c0, 0x08e1, 0x3882, 0x28a3, 0xcb7d,
|
||||
0xdb5c, 0xeb3f, 0xfb1e, 0x8bf9, 0x9bd8, 0xabbb, 0xbb9a, 0x4a75, 0x5a54, 0x6a37, 0x7a16, 0x0af1, 0x1ad0,
|
||||
0x2ab3, 0x3a92, 0xfd2e, 0xed0f, 0xdd6c, 0xcd4d, 0xbdaa, 0xad8b, 0x9de8, 0x8dc9, 0x7c26, 0x6c07, 0x5c64,
|
||||
0x4c45, 0x3ca2, 0x2c83, 0x1ce0, 0x0cc1, 0xef1f, 0xff3e, 0xcf5d, 0xdf7c, 0xaf9b, 0xbfba, 0x8fd9, 0x9ff8,
|
||||
0x6e17, 0x7e36, 0x4e55, 0x5e74, 0x2e93, 0x3eb2, 0x0ed1, 0x1ef0 };
|
||||
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
load_firmware_from_library
|
||||
|
||||
DESCRIPTION
|
||||
gets a pointer to the firmware image and the length of the image
|
||||
|
||||
PARAMETERS
|
||||
const char *pathToLib - path to the firmware image library
|
||||
uint8_t **ppFirmwareImage - pointer to the pointer to the firmware image
|
||||
uint16_t *pFirmwareImageLen - pointer to the firmware image length
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void load_firmware_from_library( const char *pathToLib, uint8_t **ppFirmwareImage,
|
||||
uint16_t *pFirmwareImageLen )
|
||||
{
|
||||
void *pFirmwareLibHandle = NULL;
|
||||
void *pTempFirmwareImage = NULL;
|
||||
void *pTempFirmwareImageLen = NULL;
|
||||
int status = -1;
|
||||
|
||||
do
|
||||
{
|
||||
if( NULL == pathToLib )
|
||||
{
|
||||
if(chip_version == 0x51 || chip_version == 0x50 || chip_version == 0x41 || chip_version == 0x40 )
|
||||
pathToLib = "/system/vendor/firmware/libpn553_fw.so"; // set the path to pn553 firmware library
|
||||
else
|
||||
pathToLib = "/system/vendor/firmware/libpn548ad_fw.so"; // set the default path to pn548ad firmware library
|
||||
}
|
||||
|
||||
if( NULL != pFirmwareLibHandle )
|
||||
{
|
||||
status = dlclose( pFirmwareLibHandle ); // if the firmware library handle is not NULL, release the handle
|
||||
pFirmwareLibHandle = NULL;
|
||||
|
||||
dlerror( ); // clear existing errors
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: dlclose() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pFirmwareLibHandle = dlopen( pathToLib, RTLD_LAZY ); // get a handle to firmware library
|
||||
LOG_MESSAGE( "Opening library handle from %s\n", pathToLib );
|
||||
|
||||
if( NULL == pFirmwareLibHandle )
|
||||
{
|
||||
LOG_ERROR( "%s: dlopen() failed \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
dlerror( ); // clear existing errors
|
||||
|
||||
pTempFirmwareImage = ( void * )dlsym( pFirmwareLibHandle, "gphDnldNfc_DlSeq" ); // get a pointer to the firmware library
|
||||
|
||||
if( dlerror( ) || ( NULL == pTempFirmwareImage ) )
|
||||
{
|
||||
LOG_ERROR( "%s: dlsym() failed, failed to load gphDnldNfc_DlSeq symbol \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
*ppFirmwareImage = *( uint8_t ** )pTempFirmwareImage; // the returned pointer is a pointer to an uint8_t array
|
||||
|
||||
pTempFirmwareImageLen = ( void * ) dlsym( pFirmwareLibHandle, "gphDnldNfc_DlSeqSz" ); // get a pointer to the firmware library length
|
||||
|
||||
if( dlerror( ) || ( NULL == pTempFirmwareImageLen ) )
|
||||
{
|
||||
LOG_ERROR( "%s: dlsym() failed, failed to load gphDnldNfc_DlSeqSz symbol \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
*pFirmwareImageLen = ( uint16_t )( *( ( uint16_t * )pTempFirmwareImageLen ) ); // the returned pointer is a pointer to the length of the image
|
||||
|
||||
} while( FALSE );
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
send_packet_packet_to_chip
|
||||
|
||||
DESCRIPTION
|
||||
sends the constructed packets to the NFC chip by calling ProcessCommand() from ftm_nfcnq.c
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void send_packet_packet_to_chip( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
int status = -1;
|
||||
|
||||
status = ProcessCommand( &pDownloadContext->packetToSend ); // call ProcessCommand() from ftm_nfcnq.c
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: ProcessCommand() failed with status = %d \n", __FUNCTION__, status );
|
||||
}
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
calculate_crc16
|
||||
|
||||
DESCRIPTION
|
||||
calculates CRC-16-CCITT of a given buffer with a given length with seed value of 0xffff(Hex)
|
||||
|
||||
PARAMETERS
|
||||
uint8_t *pBuff - buffer for CRC-16-CCITT calculation
|
||||
uint16_t buffLen - length of buffer for CRC-16-CCITT calculation
|
||||
|
||||
RETURN VALUE
|
||||
uint16_t - calculated CRC-16-CCITT value of buffer
|
||||
|
||||
==========================================================================================================*/
|
||||
static uint16_t calculate_crc16( uint8_t *pBuff, uint16_t buffLen )
|
||||
{
|
||||
uint16_t temp = 0;
|
||||
uint16_t value = 0;
|
||||
uint16_t crc = 0xffff; // seed value
|
||||
uint32_t i = 0;
|
||||
|
||||
if ( ( NULL == pBuff ) || ( 0 == buffLen ) )
|
||||
{
|
||||
LOG_ERROR( "%s: Invalid parameters \n", __FUNCTION__ );
|
||||
}
|
||||
else
|
||||
{
|
||||
for( i = 0; i < buffLen; i++ )
|
||||
{
|
||||
value = 0x00ffU & ( uint16_t )pBuff[ i ];
|
||||
temp = ( crc >> 8U ) ^ value;
|
||||
crc = ( crc << 8U ) ^ crcTable[ temp ];
|
||||
}
|
||||
}
|
||||
|
||||
return crc;
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
insert_crc16
|
||||
|
||||
DESCRIPTION
|
||||
inserts the calculated CRC-16-CCITT value into the end of the buffer
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void insert_crc16( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
uint16_t crcValueToWrite = 0;
|
||||
uint8_t *crcValueInBytes = NULL;
|
||||
|
||||
/* get CRC-16-CCITT value of packet and convert it into 2 bytes */
|
||||
crcValueToWrite = calculate_crc16( &pDownloadContext->packetToSend,
|
||||
pDownloadContext->headerPlusPayloadLen );
|
||||
crcValueInBytes = ( uint8_t * )&crcValueToWrite;
|
||||
|
||||
/* insert crc value into last 2 bytes of the packet */
|
||||
if( pDownloadContext->packetToSend.payloadLen < ( FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN + FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN - 1 ))
|
||||
{
|
||||
pDownloadContext->packetToSend.payloadBuff[ pDownloadContext->packetToSend.payloadLen ] = crcValueInBytes[ 1 ];
|
||||
pDownloadContext->packetToSend.payloadBuff[ pDownloadContext->packetToSend.payloadLen + 1 ] = crcValueInBytes[ 0 ];
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_ERROR( "%s: Packet to send payloadLen more than maximum payloadBuff size \n", __FUNCTION__ );
|
||||
}
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
read_response_from_chip
|
||||
|
||||
DESCRIPTION
|
||||
reader thread that constantly checks for responses from NFC chip, checks the integrity of the
|
||||
response packets by matching the CRC-16-CCITT values and signals the semaphore held by
|
||||
the call to ProcessCommand()
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void read_response_from_chip( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
uint8_t lenRead = 0;
|
||||
uint8_t *pPacketReceived = NULL;
|
||||
uint16_t calculatedCrcValue = 0;
|
||||
uint16_t crcValueFromResponse = 0;
|
||||
|
||||
do
|
||||
{
|
||||
if( fdNfc < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: Invalid handle \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
|
||||
lenRead = read( fdNfc, &pDownloadContext->packetReceived, // get the response packet header
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN );
|
||||
|
||||
if( 0 == lenRead )
|
||||
{
|
||||
LOG_ERROR( "%s: Error reading response packet header \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
pDownloadContext->totalPacketLen = lenRead;
|
||||
}
|
||||
|
||||
lenRead = read( fdNfc, &pDownloadContext->packetReceived.payloadBuff, // get the rest fo the response packet
|
||||
( pDownloadContext->packetReceived.payloadLen +
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN ) );
|
||||
|
||||
if( 0 == lenRead )
|
||||
{
|
||||
LOG_ERROR( "%s: Error reading response packet payload \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
pDownloadContext->totalPacketLen += lenRead; // update the total length of the received packet
|
||||
}
|
||||
|
||||
calculatedCrcValue = calculate_crc16( &pDownloadContext->packetReceived, // calculate the CRC-16-CCITT value of the received packet
|
||||
( pDownloadContext->packetReceived.payloadLen +
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN ) );
|
||||
|
||||
/* convert crc value from the response packet to an uint16_t */
|
||||
if( pDownloadContext->packetReceived.payloadLen < ( FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN + FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN - 1 ))
|
||||
{
|
||||
crcValueFromResponse = pDownloadContext->packetReceived.payloadBuff[ pDownloadContext->packetReceived.payloadLen ];
|
||||
crcValueFromResponse <<= 8;
|
||||
crcValueFromResponse |= pDownloadContext->packetReceived.payloadBuff[ pDownloadContext->packetReceived.payloadLen + 1 ];
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_ERROR( "%s: Packet received payloadLen more than maximum payloadBuff size \n", __FUNCTION__ );
|
||||
}
|
||||
|
||||
if( calculatedCrcValue != crcValueFromResponse ) // compare the CRC-16-CCITT values
|
||||
{
|
||||
LOG_ERROR( "%s: CRC-16-CCITT values do not match, discarding packet \n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
sem_post( &sRspReady ); // signal the semaphore for subsequent packets to be sent
|
||||
}
|
||||
|
||||
} while( FALSE == pDownloadContext->fExitReadThread ); // exit only when the flag is set
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
get_device_firmware_version
|
||||
|
||||
DESCRIPTION
|
||||
sends the get-firmware-version command (0xF1) to the device and outputs the firmware version of
|
||||
the device
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void get_device_firmware_version( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
uint8_t getFirmwareVersionCommand[ ] = { 0x00, 0x04, 0xF1, 0x00, 0x00, 0x00 }; // command to get firmware version on device
|
||||
uint8_t firmwareMajorVersion = 0;
|
||||
uint8_t firmwareMinorVersion = 0;
|
||||
|
||||
pDownloadContext->headerPlusPayloadLen =
|
||||
sizeof( getFirmwareVersionCommand ) / sizeof( getFirmwareVersionCommand[ 0 ] );
|
||||
|
||||
memcpy( &pDownloadContext->packetToSend, &getFirmwareVersionCommand, // construct the command packet
|
||||
( pDownloadContext->headerPlusPayloadLen ) );
|
||||
|
||||
insert_crc16( pDownloadContext ); // insert the CRC-16-CCITT value
|
||||
|
||||
send_packet_packet_to_chip( pDownloadContext ); // send the command packet to NFC chip
|
||||
|
||||
/* continues from here once the reader thread reads the response and flags the semaphore,
|
||||
the last 2 bytes of the get version response payload contains the firmware version currently on the device */
|
||||
firmwareMajorVersion = pDownloadContext->packetReceived.payloadBuff[ pDownloadContext->packetReceived.payloadLen - 1 ];
|
||||
firmwareMinorVersion = pDownloadContext->packetReceived.payloadBuff[ pDownloadContext->packetReceived.payloadLen - 2 ];
|
||||
|
||||
if(chip_version == 0x51 || chip_version == 0x50 || chip_version == 0x41 || chip_version == 0x40 )
|
||||
LOG_INFORMATION( "Firmware version: 11.%02X.%02X\n", firmwareMajorVersion, firmwareMinorVersion );
|
||||
else
|
||||
LOG_INFORMATION( "Firmware version: 10.%02X.%02X\n", firmwareMajorVersion, firmwareMinorVersion );
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
build_first_packet
|
||||
|
||||
DESCRIPTION
|
||||
constructs the first packet to be sent to the NFC chip
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void build_first_packet( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
memset( pDownloadContext->packetToSend.payloadBuff, 0, // initialise the payload buffer to zero
|
||||
FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN );
|
||||
|
||||
memcpy( &pDownloadContext->packetToSend, // copy the first chunk from the firmware library to the packet
|
||||
pDownloadContext->pFirmwareImage,
|
||||
pDownloadContext->headerPlusPayloadLen );
|
||||
|
||||
insert_crc16( pDownloadContext ); // insert the CRC-16-CCITT value
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
build_next_packet
|
||||
|
||||
DESCRIPTION
|
||||
constructs subsequent packets required to be sent to the NFC chip
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void build_next_packet( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
/* for chunks from library that are larger than 256 bytes, the packets have to be fragmented */
|
||||
if( pDownloadContext->bytesLeftToSend > FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN )
|
||||
{
|
||||
pDownloadContext->headerPlusPayloadLen = FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN + // length of header plus the payload for CRC-16-CCITT calculation
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN;
|
||||
|
||||
pDownloadContext->totalPacketLen = FIRMWARE_DOWNLOAD_MAX_PACKET_LEN; // length of the entire packet to be sent
|
||||
|
||||
pDownloadContext->packetToSend.fFragmentedPacket = FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_SET; // set the fragment flag as the first byte
|
||||
|
||||
pDownloadContext->packetToSend.payloadLen = FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN; // insert the payload length in the second byte
|
||||
|
||||
memcpy( ( &pDownloadContext->packetToSend.payloadBuff ), // copy payload from firmware library
|
||||
&pDownloadContext->pFirmwareImage[ pDownloadContext->readIndexFromLib ],
|
||||
FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN );
|
||||
|
||||
pDownloadContext->readIndexFromLib += FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN; // update the buffer index used to read from firmware library
|
||||
|
||||
pDownloadContext->bytesLeftToSend -= FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN; // update the number of bytes left to send from the chunk
|
||||
}
|
||||
|
||||
/* for chunks from library that are smaller than 256 bytes, no fragmentation needed */
|
||||
else
|
||||
{
|
||||
pDownloadContext->headerPlusPayloadLen = pDownloadContext->bytesLeftToSend + // length of header plus the payload for CRC-16-CCITT calculation
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN;
|
||||
|
||||
pDownloadContext->totalPacketLen = pDownloadContext->bytesLeftToSend + // length of the entire packet to be sent
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN +
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN;
|
||||
|
||||
pDownloadContext->packetToSend.fFragmentedPacket = FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_NONE; // set the fragment flag to none as the first byte
|
||||
|
||||
pDownloadContext->packetToSend.payloadLen = pDownloadContext->bytesLeftToSend; // insert the payload length in the second byte
|
||||
|
||||
memcpy( ( &pDownloadContext->packetToSend.payloadBuff ), // copy payload from firmware library
|
||||
&pDownloadContext->pFirmwareImage[ pDownloadContext->readIndexFromLib ],
|
||||
pDownloadContext->bytesLeftToSend );
|
||||
|
||||
pDownloadContext->readIndexFromLib += pDownloadContext->bytesLeftToSend; // update the buffer index used to read from firmware library
|
||||
|
||||
pDownloadContext->bytesLeftToSend = 0; // most likely the last fragment from the chunk
|
||||
}
|
||||
|
||||
insert_crc16( pDownloadContext );
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
process_packets_to_send
|
||||
|
||||
DESCRIPTION
|
||||
determines if the incoming packet is the first one or any subsequent ones and process them
|
||||
accordingly
|
||||
|
||||
PARAMETERS
|
||||
pfirmware_download_context_t pDownloadContext - pointer to structure containing all the
|
||||
information required
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
static void process_packets_to_send( pfirmware_download_context_t pDownloadContext )
|
||||
{
|
||||
uint8_t firstChunkLenFromLib = 0;
|
||||
uint16_t nextChunkLenFromLib = 0;
|
||||
uint16_t buffIndex = pDownloadContext->readIndexFromLib;
|
||||
|
||||
if( TRUE == pDownloadContext->fFirstPacket )
|
||||
{
|
||||
pDownloadContext->fFirstPacket = FALSE; // indicates that the first packet has been processed
|
||||
|
||||
firstChunkLenFromLib = pDownloadContext->pFirmwareImage[ 1 ] + // length of the first chunk read from firmware library
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN;
|
||||
|
||||
pDownloadContext->totalPacketLen = firstChunkLenFromLib + // length of the entire packet to send
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN;
|
||||
|
||||
pDownloadContext->readIndexFromLib += firstChunkLenFromLib; // update the buffer index used to read from firmware library
|
||||
|
||||
pDownloadContext->headerPlusPayloadLen = firstChunkLenFromLib; // length of header plus the payload for CRC-16-CCITT calculation
|
||||
|
||||
build_first_packet( pDownloadContext ); // build the first packet
|
||||
|
||||
send_packet_packet_to_chip( pDownloadContext ); // send the packet to the NFC chip
|
||||
}
|
||||
else if( FALSE == pDownloadContext->fFirstPacket )
|
||||
{
|
||||
nextChunkLenFromLib = pDownloadContext->pFirmwareImage[ buffIndex ]; // length of next chunk read from the firmware library
|
||||
|
||||
/* length of next chunk is stored in 2 bytes in the firmware library */
|
||||
nextChunkLenFromLib <<= 8;
|
||||
nextChunkLenFromLib |= pDownloadContext->pFirmwareImage[ buffIndex + 1 ];
|
||||
|
||||
buffIndex += 2; // add 2 bytes to the buffer index after length of next chunk is read
|
||||
|
||||
pDownloadContext->readIndexFromLib = buffIndex; // update the buffer index used to read from firmware library
|
||||
|
||||
pDownloadContext->bytesLeftToSend = nextChunkLenFromLib; // number of bytes left on the chunk to be sent to the chip
|
||||
|
||||
while( pDownloadContext->bytesLeftToSend > 0 ) // constructs and sends packets as long as there are bytes left in the chunk
|
||||
{
|
||||
build_next_packet( pDownloadContext );
|
||||
send_packet_packet_to_chip( pDownloadContext );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_ERROR( "%s: Should not reach this point \n", __FUNCTION__ );
|
||||
}
|
||||
}
|
||||
|
||||
/*==========================================================================================================
|
||||
FUNCTION
|
||||
ftm_nfc_dispatch_nq_fwdl
|
||||
|
||||
DESCRIPTION
|
||||
called by main() in ftm_main.c to start the firmware download routine
|
||||
|
||||
PARAMETERS
|
||||
none
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
==========================================================================================================*/
|
||||
void ftm_nfc_dispatch_nq_fwdl( void )
|
||||
{
|
||||
int status = 0;
|
||||
|
||||
char *pathToLib = NULL;
|
||||
uint8_t *pFirmwareImage = NULL;
|
||||
uint16_t firmwareImageLen = 0;
|
||||
|
||||
uint8_t *pNextChunkFromLib = NULL;
|
||||
uint16_t nextChunkLenFromLib = 0;
|
||||
uint16_t totalBytesReadFromLib = 0;
|
||||
uint16_t readIndexFromLib = 0;
|
||||
union nqx_uinfo nqx_info;
|
||||
pthread_t readerThread;
|
||||
|
||||
firmware_download_context_t downloadContext = { 0 };
|
||||
pfirmware_download_context_t pDownloadContext = &downloadContext;
|
||||
pDownloadContext->fFirstPacket = TRUE;
|
||||
|
||||
|
||||
do
|
||||
{
|
||||
if( !fdNfc )
|
||||
{
|
||||
status = ftm_nq_nfc_open( ); // get a handle to the kernel driver
|
||||
if( status < 0 )
|
||||
{
|
||||
LOG_ERROR( "\n%s: ftm_nq_nfc_open() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
status = ftm_nfc_hw_reset( ); // reset NFC hardware
|
||||
if( status < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nq_nfc_reset() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
nqx_info.i = ioctl( fdNfc, NFCC_GET_INFO, 0 );
|
||||
if( nqx_info.i < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: nqnfcinfo not enabled, info = %d \n", __FUNCTION__, nqx_info.i );
|
||||
}
|
||||
chip_version = nqx_info.info.chip_type;
|
||||
LOG_INFORMATION( "\n NQ Chip ID : %x\n", chip_version);
|
||||
}
|
||||
|
||||
status = pthread_create( &readerThread, NULL, // create a reader thread
|
||||
&read_response_from_chip, pDownloadContext );
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: pthread_create() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
load_firmware_from_library( pathToLib, &pFirmwareImage, &firmwareImageLen ); // get a pointer to firmware library image and get its length
|
||||
if( ( NULL == pFirmwareImage ) || ( 0 == firmwareImageLen ) )
|
||||
{
|
||||
LOG_ERROR( "%s: Firmware library image extraction failed\n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_MESSAGE( "Firmware major version number: %02X\n", pFirmwareImage[ 5 ] );
|
||||
LOG_MESSAGE( "Firmware minor version number: %02X\n", pFirmwareImage[ 4 ] );
|
||||
LOG_MESSAGE( "Firmware library image length: %d\n", firmwareImageLen );
|
||||
LOG_MESSAGE( "Firmware library image pointer: %X\n", ( uintptr_t )pFirmwareImage );
|
||||
|
||||
pDownloadContext->pFirmwareImage = pFirmwareImage;
|
||||
pDownloadContext->firmwareImageLen = firmwareImageLen;
|
||||
|
||||
status = ioctl( fdNfc, NFC_SET_PWR, FIRMWARE_MODE ); // set NFCC to firmware download mode
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: Failed to set firmware pin high.\n", __FUNCTION__ );
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_INFORMATION( "\nBefore firmware update...\n" );
|
||||
get_device_firmware_version( pDownloadContext ); // get device version before loading firmware
|
||||
|
||||
LOG_INFORMATION( "\nSending firmware packets... Please wait\n" );
|
||||
while( pDownloadContext->readIndexFromLib < pDownloadContext->firmwareImageLen )
|
||||
{
|
||||
process_packets_to_send( pDownloadContext ); // build and send download packets with payload from the firmware library image
|
||||
}
|
||||
|
||||
LOG_INFORMATION( "All packets sent!\n\n" );
|
||||
|
||||
pDownloadContext->fExitReadThread = TRUE; // set flag to indicate that reader thread is safe to exit
|
||||
|
||||
LOG_INFORMATION( "After firmware update...\n" );
|
||||
get_device_firmware_version( pDownloadContext ); // get device version number after loading firmware
|
||||
|
||||
LOG_MESSAGE( "Waiting for reader thread to terminate...\n" );
|
||||
pthread_join( readerThread, NULL ); // wait for reader thread to terminate
|
||||
LOG_MESSAGE( "Reader thread terminated!\n" );
|
||||
|
||||
LOG_MESSAGE( "Resetting NFCC...\n" );
|
||||
|
||||
status = ftm_nfc_hw_reset( ); // reset the NFC hardware which resets the firmware pin as well
|
||||
if( status < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nfc_hw_reset() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
status = ftm_nq_nfc_close( ); // release the handle to the kernel driver
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nq_nfc_close() failed with status = %d \n", __FUNCTION__, status );
|
||||
}
|
||||
|
||||
LOG_INFORMATION( "All done!\n\n" );
|
||||
|
||||
} while( FALSE );
|
||||
|
||||
}
|
||||
111
feeds/ipq95xx/ftm/src/ftm_nfcnq_fwdl.h
Executable file
111
feeds/ipq95xx/ftm/src/ftm_nfcnq_fwdl.h
Executable file
@@ -0,0 +1,111 @@
|
||||
/*
|
||||
* Copyright (c) 2016 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Not a Contribution.
|
||||
* Apache license notifications and license are retained
|
||||
* for attribution purposes only.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2015 NXP Semiconductors
|
||||
* The original Work has been changed by NXP Semiconductors.
|
||||
*
|
||||
* Copyright (C) 2010 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
/*=========================================================================
|
||||
FTM NFC NQ Firmware Download Header File
|
||||
Description
|
||||
This file contains the declarations of the functions and various
|
||||
definitions used to download firmware onto the NQ Chip.
|
||||
===========================================================================*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <dlfcn.h>
|
||||
#include <semaphore.h>
|
||||
#include <pthread.h>
|
||||
|
||||
#define FALSE ( 0 )
|
||||
#define TRUE ( !FALSE )
|
||||
|
||||
#define FIRMWARE_DOWNLOAD_MAX_PACKET_LEN ( 0x100U ) // maximum length for a download packet
|
||||
#define FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN ( 0x02U ) // length of the header
|
||||
#define FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN ( 0x02U ) // length of CRC-16-CCITT value
|
||||
#define FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN FIRMWARE_DOWNLOAD_MAX_PACKET_LEN - \
|
||||
FIRMWARE_DOWNLOAD_PACKET_HEADER_LEN - \
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN
|
||||
|
||||
/* Values for the first byte of each packet, indicates if the packet is fragmented */
|
||||
#define FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_NONE ( 0x00U ) // not fragmented
|
||||
#define FIRMWARE_DOWNLOAD_PACKET_FRAG_FLAG_SET ( 0x04U ) // fragmented packet, next packet is a part of this one
|
||||
|
||||
extern sem_t sRspReady; // semaphore used by reader thread
|
||||
extern int fdNfc; // a handle to the kernel driver
|
||||
|
||||
typedef uint8_t bool_t;
|
||||
|
||||
/* structure of the packet to be sent or received */
|
||||
typedef struct firmware_download_packet
|
||||
{
|
||||
uint8_t fFragmentedPacket; // flag to indicate if the packet is fragmented
|
||||
uint8_t payloadLen; // length of payload
|
||||
uint8_t payloadBuff[ FIRMWARE_DOWNLOAD_PACKET_MAX_PAYLOAD_LEN +
|
||||
FIRMWARE_DOWNLOAD_PACKET_CRC16_LEN ]; // buffer containing the payload and CRC-16-CCITT value
|
||||
} firmware_download_packet_t, *pfirmware_download_packet_t;
|
||||
|
||||
/* structure that contains all the other information about the packets */
|
||||
typedef struct firmware_download_context
|
||||
{
|
||||
const uint8_t *pFirmwareImage; // pointer to the firmware image library
|
||||
uint16_t firmwareImageLen; // length of the firmware image
|
||||
|
||||
uint8_t headerPlusPayloadLen; // header and payload length of a packet for CRC calculation
|
||||
uint16_t readIndexFromLib; // index used to read from the firmware library
|
||||
uint16_t bytesLeftToSend; // number of bytes left to send when the chunk read is fragmented
|
||||
uint16_t totalPacketLen; // total length of packet to be sent or received
|
||||
bool_t fFirstPacket; // flag to indicate if it is the first packet
|
||||
bool_t fExitReadThread; // flag to indicate if reader thread is safe to exit
|
||||
firmware_download_packet_t packetToSend; // contains information about packet to be sent
|
||||
firmware_download_packet_t packetReceived; // contains information about packet from response received
|
||||
} firmware_download_context_t, *pfirmware_download_context_t;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
|
||||
Firmware download packet format
|
||||
|
||||
-----------------------------------------------------------------------------------------------------
|
||||
| Header | Payload | CRC-16-CCITT value |
|
||||
-----------------------------------------------------------------------------------------------------
|
||||
| Fragment flag | Payload length | Command/Response | Data | CRC-16-CCITT value |
|
||||
-----------------------------------------------------------------------------------------------------
|
||||
| 1 byte | 1 byte | 1 byte | n bytes | 2 bytes |
|
||||
-----------------------------------------------------------------------------------------------------
|
||||
|
||||
|
||||
Firmware library image format
|
||||
|
||||
--------------------------------------------------------------------------------- ----------------------------------
|
||||
| 0x00 | First chunk length | First chunk | Next chunk length | Next chunk | ... | Last chunk length | Last chunk |
|
||||
--------------------------------------------------------------------------------- ----------------------------------
|
||||
| 1 byte | 1 byte | n bytes | 2 bytes | n bytes | ... | 2 bytes | n bytes |
|
||||
--------------------------------------------------------------------------------- ----------------------------------
|
||||
|
||||
*/
|
||||
461
feeds/ipq95xx/ftm/src/ftm_nfcnq_test.c
Executable file
461
feeds/ipq95xx/ftm/src/ftm_nfcnq_test.c
Executable file
@@ -0,0 +1,461 @@
|
||||
/*
|
||||
* Copyright (c) 2017 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
#include <libgen.h>
|
||||
#include "ftm_nfcnq.h"
|
||||
#include "ftm_nfcnq_test.h"
|
||||
|
||||
/* Global variables */
|
||||
pthread_t clientThread;
|
||||
PNCI_MESSAGE pNCIMessage;
|
||||
char *progname;
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
eseSpiTest
|
||||
|
||||
DESCRIPTION
|
||||
Send APDU for eSE SPI HLOS test
|
||||
|
||||
PARAMETERS
|
||||
int argc - argument count
|
||||
char **argv - argument vector
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void eseSpiTest(int argc, char **argv )
|
||||
{
|
||||
int ret = 0;
|
||||
int test_mode = 0;
|
||||
unsigned char i = 0;
|
||||
int fp = 0;
|
||||
int choice = 0;
|
||||
unsigned char send_APDU[] = {0x5A,0x00,0x05,0x00,0xA4,0x04,0x00,0x00,0xA5};
|
||||
int size_APDU = 0;
|
||||
unsigned char recv_response[259] = {0};
|
||||
progname = basename(argv[2]);
|
||||
test_mode = getopt(argc, argv, "01");
|
||||
size_APDU = sizeof(send_APDU);
|
||||
|
||||
LOG_INFORMATION("\n### eSE SPI test ###\n");
|
||||
|
||||
if(test_mode == '0')
|
||||
{
|
||||
choice = 0;
|
||||
LOG_INFORMATION("\nInterrupt Mode test\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
choice = 1;
|
||||
LOG_INFORMATION("\nPoll Mode test(default)\n");
|
||||
}
|
||||
|
||||
do
|
||||
{
|
||||
//open module
|
||||
if ((ret = (fp = open("/dev/ese", O_RDWR))) < 0)
|
||||
{
|
||||
LOG_INFORMATION("eSE open error retcode = %d, errno = %d\n", ret, errno);
|
||||
LOG_INFORMATION("\n... eSE SPI Test requires modified boot and TZ image ...");
|
||||
break;
|
||||
}
|
||||
LOG_INFORMATION("eSE open : Ret = %2d\n", ret);
|
||||
|
||||
//enable the logs
|
||||
ioctl(fp, ESE_SET_DBG, 1);
|
||||
//hardware reset
|
||||
ioctl(fp, ESE_SET_PWR, 1);
|
||||
|
||||
ioctl(fp, ESE_SET_MODE, choice);
|
||||
|
||||
//write one APDU
|
||||
ret = write(fp, send_APDU, sizeof(send_APDU));
|
||||
if (ret < 0)
|
||||
{
|
||||
LOG_INFORMATION("ese write error retcode = %d, errno = %d\n", ret, errno);
|
||||
break;
|
||||
}
|
||||
LOG_INFORMATION("ese Write : Ret = %.2X \n", ret);
|
||||
LOG_INFORMATION("APDU sent to eSE: ");
|
||||
for (i=0; i<size_APDU; i++)
|
||||
{
|
||||
LOG_INFORMATION("%.2X ", send_APDU[i]);
|
||||
}
|
||||
sleep(1);
|
||||
|
||||
if ((ret = (read(fp, &recv_response[0], READ_SAMPLE_SIZE)), 0) < 0)
|
||||
{
|
||||
LOG_INFORMATION("\neSE read error retcode = %d, errno = %d", ret, errno);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOG_INFORMATION("\nResponse from eSE: ");
|
||||
for (i=0;i<(recv_response[2]+1);i++)
|
||||
{
|
||||
LOG_INFORMATION("%.2X ", recv_response[i]);
|
||||
}
|
||||
LOG_INFORMATION("\n");
|
||||
}
|
||||
} while(0);
|
||||
|
||||
close(fp);
|
||||
}
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
eseDwpTest
|
||||
|
||||
DESCRIPTION
|
||||
Send NCI commands to NFCC for eSE DWP detection
|
||||
|
||||
PARAMETERS
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void eseDwpTest()
|
||||
{
|
||||
int cmds;
|
||||
cmds = sizeof(NQ330_ESE_DWP) / sizeof(NQ330_ESE_DWP[0]);
|
||||
LOG_INFORMATION( "\n### ese DWP Test ###\n" );
|
||||
if(whatNQChip == NQ_220 || whatNQChip == NQ_330)
|
||||
sendcmds(NQ330_ESE_DWP, cmds);
|
||||
else
|
||||
LOG_INFORMATION( "\nNQ Chipset in use doesn't support eSE\n" );
|
||||
}
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
printTecnologyDetails
|
||||
|
||||
DESCRIPTION
|
||||
Print the technology supported and protocols details
|
||||
|
||||
PARAMETERS
|
||||
char technology - technology supported identifier
|
||||
char protocol - protocol identifier
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void printTecnologyDetails(char technology, char protocol)
|
||||
{
|
||||
switch (protocol)
|
||||
{
|
||||
case NFC_PROTOCOL_ISO_DEP:
|
||||
LOG_INFORMATION( "ISO-DEP Protocol");
|
||||
break;
|
||||
|
||||
case NFC_PROTOCOL_NFC_DEP:
|
||||
LOG_INFORMATION( "NFC-DEP Protocol");
|
||||
break;
|
||||
|
||||
case NFC_PROTOCOL_T1T:
|
||||
LOG_INFORMATION( "T1T Protocol");
|
||||
break;
|
||||
|
||||
case NFC_PROTOCOL_T2T:
|
||||
LOG_INFORMATION( "T2T Protocol");
|
||||
break;
|
||||
|
||||
case NFC_PROTOCOL_T3T:
|
||||
LOG_INFORMATION( "T3T Protocol");
|
||||
break;
|
||||
|
||||
case NFC_PROTOCOL_UNKNOWN:
|
||||
LOG_INFORMATION( "unknown Protocol");
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
switch (technology)
|
||||
{
|
||||
case NFC_NFCA_Poll:
|
||||
LOG_INFORMATION("\nNFC A POLL MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCB_Poll:
|
||||
LOG_INFORMATION("\nNFC B POLL MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCF_Poll:
|
||||
LOG_INFORMATION("\nNFC F POLL MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCA_Listen:
|
||||
LOG_INFORMATION("\nNFC A LISTEN MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCB_Listen:
|
||||
LOG_INFORMATION("\nNFC B LISTEN MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCF_Listen:
|
||||
LOG_INFORMATION("\nNFC F LISTEN MODE TECHNOLOGY\n");
|
||||
break;
|
||||
case NFC_NFCISO15693_Poll:
|
||||
LOG_INFORMATION("\nNFC ISO15693 POLL MODE TECHNOLOGY\n");
|
||||
break;
|
||||
default:
|
||||
LOG_INFORMATION("\nother TECHNOLOGY\n");
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
sendcmds
|
||||
|
||||
DESCRIPTION
|
||||
Send sequence of commands to NFCC
|
||||
|
||||
PARAMETERS
|
||||
uint8_t buffer[] - Command buffer array
|
||||
int no_of_cmds - Number of commands to be sent
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void sendcmds(uint8_t buffer[][MAX_CMD_LEN], int no_of_cmds)
|
||||
{
|
||||
int rows=0,payloadlen=0;
|
||||
int ret = 0;
|
||||
ftm_nfc_pkt_type *nfc_pkt = (ftm_nfc_pkt_type *)malloc(no_of_cmds*255);
|
||||
|
||||
LOG_INFORMATION("\nTotal cmds to be sent = %d\n",no_of_cmds);
|
||||
LOG_INFORMATION("Wait for Commands to be sent... \n\n");
|
||||
|
||||
for(rows = 0; rows < no_of_cmds; rows++)
|
||||
{
|
||||
#ifdef NFC_FTM_DEBUG
|
||||
LOG_INFORMATION ("Number of cmds sent = %d \n",rows+1);
|
||||
#endif
|
||||
payloadlen = 0;
|
||||
payloadlen = 3 + buffer[rows][2];
|
||||
memset(nfc_pkt->nci_data, -1, MAX_CMD_LEN);
|
||||
memcpy(nfc_pkt->nci_data, &buffer[rows], payloadlen);
|
||||
ret = ProcessCommand( nfc_pkt->nci_data );
|
||||
if( ret == -1 ) // wait finished, not signalled?
|
||||
{
|
||||
LOG_ERROR( "Waited for NCI NTF/DATA timeout\n" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
usage
|
||||
|
||||
DESCRIPTION
|
||||
Print usage information for test
|
||||
|
||||
PARAMETERS
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void usage()
|
||||
{
|
||||
LOG_INFORMATION("\nUsage:");
|
||||
LOG_INFORMATION(" %s [-n] [-e] [-d] [h] \n", progname);
|
||||
LOG_INFORMATION(" %s -n ..for NFC test only\n", progname);
|
||||
LOG_INFORMATION(" %s -e ..for eSE SPI test only\n \t-0 ..Interrupt Mode\n \t-1 ..Poll Mode\n", progname);
|
||||
LOG_INFORMATION(" %s -d ..for eSE DWP test only\n", progname);
|
||||
LOG_INFORMATION(" %s -h HELP\n", progname);
|
||||
LOG_INFORMATION(" %s default NFC test only\n", progname);
|
||||
}
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
nfc_ese_pwr
|
||||
|
||||
DESCRIPTION
|
||||
Set ESE power using NFC driver
|
||||
|
||||
PARAMETERS
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void nfc_ese_pwr()
|
||||
{
|
||||
int ret;
|
||||
ret = ioctl( fdNfc, NFC_ESE_SET_PWR, POWER_ON ); // turn the chip on
|
||||
if( ret != 0 )
|
||||
{
|
||||
LOG_INFORMATION("Can't find ESE GPIO in NFC driver: ");
|
||||
LOG_INFORMATION("ret=%d\n",ret);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*==============================================================================
|
||||
FUNCTION
|
||||
ftm_nfc_dispatch_nq_test
|
||||
|
||||
DESCRIPTION
|
||||
called by main() in ftm_main.c to start the nfc test routine
|
||||
|
||||
PARAMETERS
|
||||
int argc - argument count
|
||||
char **argv - argument vector
|
||||
|
||||
RETURN VALUE
|
||||
void
|
||||
|
||||
=============================================================================*/
|
||||
void ftm_nfc_dispatch_nq_test( int argc, char **argv )
|
||||
{
|
||||
int cmds = 0;
|
||||
unsigned int chip_version = 0x00;
|
||||
unsigned int major_version = 0x00;
|
||||
unsigned int minor_version = 0x00;
|
||||
unsigned int rom_version = 0x00;
|
||||
char firmware_version[10];
|
||||
struct timespec time_sec;
|
||||
int type_of_test = 0;
|
||||
int default_test = 0;
|
||||
int status = 0;
|
||||
|
||||
union nqx_uinfo nqx_info;
|
||||
pthread_t readerThread;
|
||||
|
||||
do
|
||||
{
|
||||
if( !fdNfc )
|
||||
{
|
||||
status = ftm_nq_nfc_open( ); // get a handle to the kernel driver
|
||||
if( status < 0 )
|
||||
{
|
||||
LOG_ERROR( "\n%s: ftm_nq_nfc_open() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
status = ftm_nfc_hw_reset( ); // reset NFC hardware
|
||||
if( status < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nq_nfc_reset() failed with status = %d \n", __FUNCTION__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
nqx_info.i = ioctl( fdNfc, NFCC_GET_INFO, 0 );
|
||||
if( nqx_info.i < 0 )
|
||||
{
|
||||
LOG_ERROR( "%s: nqnfcinfo not enabled, info = %d \n", __FUNCTION__, nqx_info.i );
|
||||
}
|
||||
|
||||
chip_version = nqx_info.info.chip_type;
|
||||
rom_version = nqx_info.info.rom_version;
|
||||
major_version = nqx_info.info.fw_major;
|
||||
minor_version = nqx_info.info.fw_minor;
|
||||
|
||||
LOG_INFORMATION( "\n NQ Chip ID : %x\n", chip_version);
|
||||
snprintf(firmware_version, 10, "%02x.%02x.%02x", rom_version, major_version, minor_version);
|
||||
LOG_INFORMATION(" Firmware version : %s\n\n", firmware_version);
|
||||
|
||||
|
||||
if(sem_init(&sRspReady, 0, 0) != 0)
|
||||
{
|
||||
LOG_ERROR("NFC FTM :semaphore_halcmd_complete creation failed \n");
|
||||
break;
|
||||
}
|
||||
if(sem_init(&sRfNtf, 0, 0) != 0)
|
||||
{
|
||||
LOG_ERROR("NFC FTM :semaphore_halcmd_complete creation failed \n");
|
||||
break;
|
||||
}
|
||||
|
||||
pNCIMessage = ( PNCI_MESSAGE ) nciReplyMessage;
|
||||
status = pthread_create( &clientThread, NULL, &nfc_read_thread, NULL ); // Start the Read Thread
|
||||
|
||||
if( status != 0 ) // successful?
|
||||
{
|
||||
LOG_ERROR("nqnfc %s: pthread_create( nfc_read_thread ) failed with ret = %d \n", __func__, status );
|
||||
break;
|
||||
}
|
||||
|
||||
status = ftm_nfc_nq_vs_nxp( );
|
||||
if( status < 0 ) // Not an NQ Chip?
|
||||
{
|
||||
LOG_ERROR("ERROR NOT A KNOWN NQ Chip \n" );
|
||||
}
|
||||
}
|
||||
|
||||
progname = basename(argv[1]);
|
||||
type_of_test = getopt(argc, argv, "nedhf");
|
||||
|
||||
switch (type_of_test) {
|
||||
case 'n':
|
||||
LOG_INFORMATION("NFC test only\n");
|
||||
break;
|
||||
case 'e':
|
||||
LOG_INFORMATION("eSE SPI test only\n");
|
||||
nfc_ese_pwr();
|
||||
ese_spi_test = 1;
|
||||
eseSpiTest(argc, argv);
|
||||
break;
|
||||
case 'd':
|
||||
LOG_INFORMATION("eSE DWP test only\n");
|
||||
ese_dwp_test = 1;
|
||||
eseDwpTest();
|
||||
break;
|
||||
case 'h':
|
||||
usage();
|
||||
break;
|
||||
default:
|
||||
usage();
|
||||
default_test = 1;
|
||||
LOG_INFORMATION("\nDefault NFC test only\n");
|
||||
}
|
||||
|
||||
if(ese_dwp_test || ese_spi_test)
|
||||
break;
|
||||
|
||||
if(type_of_test == 'n' || default_test)
|
||||
{
|
||||
switch(whatNQChip)
|
||||
{
|
||||
case NQ_210:
|
||||
case NQ_220:
|
||||
cmds = sizeof(NQ220_cmds) / sizeof(NQ220_cmds[0]);
|
||||
sendcmds(NQ220_cmds, cmds);
|
||||
break;
|
||||
case NQ_310:
|
||||
case NQ_330:
|
||||
cmds = sizeof(NQ330_cmds) / sizeof(NQ330_cmds[0]);
|
||||
sendcmds(NQ330_cmds, cmds);
|
||||
break;
|
||||
default:
|
||||
LOG_INFORMATION( "Chip not supported, taking NQ330 as default\n ");
|
||||
cmds = sizeof(NQ330_cmds) / sizeof(NQ330_cmds[0]);
|
||||
sendcmds(NQ330_cmds, cmds);
|
||||
break;
|
||||
}
|
||||
|
||||
LOG_INFORMATION("\n<<>> Waiting for TAG detect or 20sec timeout <<>> ...\n");
|
||||
status = clock_gettime( CLOCK_REALTIME, &time_sec );
|
||||
time_sec.tv_sec += NFC_NTF_TIMEOUT;
|
||||
status = sem_timedwait( &sRfNtf, &time_sec ); //start waiting
|
||||
if (status <0) {
|
||||
LOG_INFORMATION("\n No NFC Tag detected, continue ...\n");
|
||||
}
|
||||
}
|
||||
|
||||
status = ftm_nq_nfc_close( ); // release the handle to the kernel driver
|
||||
if( 0 != status )
|
||||
{
|
||||
LOG_ERROR( "%s: ftm_nq_nfc_close() failed with status = %d \n", __FUNCTION__, status );
|
||||
}
|
||||
|
||||
} while( FALSE );
|
||||
|
||||
}
|
||||
202
feeds/ipq95xx/ftm/src/ftm_nfcnq_test.h
Executable file
202
feeds/ipq95xx/ftm/src/ftm_nfcnq_test.h
Executable file
@@ -0,0 +1,202 @@
|
||||
/*
|
||||
* Copyright (c) 2017 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Not a Contribution.
|
||||
* Apache license notifications and license are retained
|
||||
* for attribution purposes only.
|
||||
*
|
||||
* Copyright (C) 2015 The Android Open Source Project
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#define ESE_MAGIC 0xEA
|
||||
#define ESE_SET_PWR _IOW(ESE_MAGIC, 0x01, unsigned int)
|
||||
#define ESE_SET_DBG _IOW(ESE_MAGIC, 0x02, unsigned int)
|
||||
#define ESE_SET_MODE _IOW(ESE_MAGIC, 0x03, unsigned int)
|
||||
#define NFC_ESE_SET_PWR _IOW(0xE9, 0x02, unsigned int)
|
||||
#define NFC_ESE_GET_PWR _IOR(0xE9, 0x03, unsigned int)
|
||||
#define NFC_NTF_TIMEOUT 20
|
||||
|
||||
/* Supported Protocols */
|
||||
#define NFC_PROTOCOL_UNKNOWN 0x00 /* Unknown */
|
||||
#define NFC_PROTOCOL_T1T 0x01 /* Type1Tag - NFC-A */
|
||||
#define NFC_PROTOCOL_T2T 0x02 /* Type2Tag - NFC-A */
|
||||
#define NFC_PROTOCOL_T3T 0x03 /* Type3Tag - NFC-F */
|
||||
#define NFC_PROTOCOL_ISO_DEP 0x04 /* Type 4A,4B - NFC-A or NFC-B */
|
||||
#define NFC_PROTOCOL_NFC_DEP 0x05 /* NFCDEP/LLCP - NFC-A or NFC-F */
|
||||
|
||||
#define MAX_CMD_LEN 255
|
||||
#define READ_SAMPLE_SIZE 258
|
||||
extern int fdNfc; // a handle to the kernel driver
|
||||
extern uint8_t nciReplyMessage[ 255 ];
|
||||
extern NQ_CHIP_TYPE whatNQChip;
|
||||
extern sem_t sRspReady;
|
||||
extern int ftm_nfc_nq_vs_nxp( void );
|
||||
int ese_dwp_test = 0;
|
||||
int ese_spi_test = 0;
|
||||
void sendcmds(uint8_t buffer[][255], int no_of_cmds);
|
||||
void printTecnologyDetails(char technology, char protocol);
|
||||
sem_t sRfNtf;
|
||||
|
||||
struct ese_spi_platform_data
|
||||
{
|
||||
unsigned int use_pwr_req;
|
||||
unsigned int pwr_req;
|
||||
unsigned int ese_intr;
|
||||
};
|
||||
|
||||
/*
|
||||
* Enum definition contains RF technology modes supported.
|
||||
* This information is a part of RF_DISCOVER_NTF or RF_INTF_ACTIVATED_NTF.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
NFC_NFCA_Poll = 0x00, /* Nfc A Technology in Poll Mode */
|
||||
NFC_NFCB_Poll = 0x01, /* Nfc B Technology in Poll Mode */
|
||||
NFC_NFCF_Poll = 0x02, /* Nfc F Technology in Poll Mode */
|
||||
NFC_NFCA_Active_Poll = 0x03, /* Nfc A Technology in Active Poll Mode */
|
||||
NFC_NFCF_Active_Poll = 0x05, /* Nfc F Technology in Active Poll Mode */
|
||||
NFC_NFCISO15693_Poll = 0x06, /* Nfc ISO15693 Technology in Poll Mode */
|
||||
NFC_NxpProp_NFCHID_Poll = 0x70, /* Nfc Hid Technology in Poll Mode */
|
||||
NFC_NxpProp_NFCEPFGEN2_Poll = 0x71, /* Nfc EpcGen2 Technology in Poll Mode */
|
||||
NFC_NxpProp_NFCKOVIO_Poll = 0x72, /* Nfc Kovio Technology in Poll Mode */
|
||||
NFC_NFCA_Listen = 0x80, /* Nfc A Technology in Listen Mode */
|
||||
NFC_NFCB_Listen = 0x81, /* Nfc B Technology in Listen Mode */
|
||||
NFC_NFCF_Listen = 0x82, /* Nfc F Technology in Listen Mode */
|
||||
NFC_NFCA_Active_Listen = 0x83, /* Nfc A Technology in Active Listen Mode */
|
||||
NFC_NFCF_Active_Listen = 0x85, /* Nfc F Technology in Active Listen Mode */
|
||||
NFC_NFCISO15693_Active_Listen = 0x86 /* Nfc ISO15693 Technology in Listen Mode */
|
||||
} NFC_RfTechMode_t;
|
||||
|
||||
uint8_t NQ330_cmds[][255] =
|
||||
{
|
||||
{ 0x20,0x00,0x01,0x00 },
|
||||
{ 0x20,0x01,0x00},
|
||||
{ 0x2F,0x02,0x00 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x0F },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xFC },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xF2 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xD7 },
|
||||
{ 0x20,0x03,0x07,0x03,0xA0,0x02,0xA0,0x03,0xA0,0x04 },
|
||||
{ 0x20,0x02,0x09,0x02,0xA0,0x03,0x01,0x01,0xA0,0x04,0x01,0x06 },
|
||||
{ 0x20,0x02,0x0F,0x01,0xA0,0x0E,0x0B,0x11,0x01,0xC2,0xB2,0x00,0xB2,0x1E,0x1F,0x00,0xD0,0x0C },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0xF2,0x01,0x01 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEC },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xD4 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x14 },
|
||||
{ 0x20,0x02,0x2E,0x0E,0x28,0x01,0x00,0x21,0x01,0x00,0x30,0x01,0x08,0x31,0x01,0x03,0x32,0x01,0x60,0x38,0x01,0x01,0x33,0x04,0x01,0x02,0x03,0x04,0x54,0x01,0x06,0x50,0x01,0x02,0x5B,0x01,0x00,0x80,0x01,0x01,0x81,0x01,0x01,0x82,0x01,0x0E,0x18,0x01,0x01 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0x62,0x01,0x01 },
|
||||
{ 0x20,0x02,0x06,0x01,0xA0,0xF3,0x02,0x10,0x27 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x85 },
|
||||
{ 0x21,0x01,0x07,0x00,0x01,0x01,0x03,0x00,0x01,0x05 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0xF1,0x01,0x00 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x0F },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x00,0x01,0x00 },
|
||||
{ 0x20,0x01,0x00},
|
||||
{ 0x20,0x03,0x02,0x01,0x00 },
|
||||
{ 0x20,0x03,0x02,0x01,0x29 },
|
||||
{ 0x20,0x03,0x02,0x01,0x61 },
|
||||
{ 0x20,0x03,0x02,0x01,0x60 },
|
||||
{ 0x20,0x02,0x0F,0x01,0xA0,0x0E,0x0B,0x11,0x01,0xC2,0xB2,0x00,0xB2,0x1E,0x1F,0x00,0xD0,0x0C },
|
||||
{ 0x21,0x00,0x0D,0x04,0x04,0x03,0x02,0x05,0x03,0x03,0x03,0x02,0x01,0x80,0x01,0x80 },
|
||||
{ 0x20,0x03,0x07,0x03,0xA0,0xEC,0xA0,0xED,0xA0,0xD4 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xF0 },
|
||||
{ 0x22,0x01,0x02,0xC0,0x01 },
|
||||
{ 0x22,0x03,0x02,0xC0,0x00 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x14 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x07 },
|
||||
{ 0x20,0x03,0x02,0x01,0x52 },
|
||||
{ 0x2F,0x15,0x01,0x02 },
|
||||
{ 0x21,0x03,0x07,0x03,0x80,0x01,0x81,0x01,0x82,0x01 },
|
||||
{ 0x21,0x06,0x01,0x00 },
|
||||
{ 0x2F,0x15,0x01,0x00 },
|
||||
{ 0x20,0x02,0x07,0x02,0x32,0x01,0x60,0x38,0x01,0x01 },
|
||||
{ 0x21,0x01,0x1B,0x00,0x05,0x01,0x03,0x00,0x01,0x03,0x01,0x03,0x00,0x41,0x04,0x01,0x03,0x00,0x41,0xA0,0x01,0x03,0x00,0x01,0x05,0x00,0x03,0xC0,0xC3,0x02 },
|
||||
{ 0x20,0x02,0x07,0x02,0x32,0x01,0x60,0x38,0x01,0x01},
|
||||
{ 0x21,0x03,0x19,0x0C,0x00,0x01,0x01,0x01,0x02,0x01,0x03,0x01,0x05,0x01,0x80,0x01,0x81,0x01,0x82,0x01,0x83,0x01,0x85,0x01,0x06,0x01,0x70,0x01}
|
||||
};
|
||||
|
||||
uint8_t NQ330_ESE_DWP[][255] =
|
||||
{
|
||||
{ 0x20,0x00,0x01,0x00 },
|
||||
{ 0x20,0x01,0x00},
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0xF2,0x01,0x01 },
|
||||
{ 0x22,0x00,0x01,0x01 },
|
||||
{ 0x22,0x01,0x2,0x01,0x01 },
|
||||
{ 0x20,0x04,0x06,0x03,0x01,0x01,0x02,0x01,0x01 },
|
||||
{ 0x03,0x00,0x03,0x81,0x02,0x01 },
|
||||
{ 0x03,0x00,0x03,0x81,0x02,0x04 },
|
||||
{ 0x03,0x00,0x03,0x81,0x02,0x07 },
|
||||
{ 0x21,0x01,0x1B,0x00,0x05,0x01,0x03,0x00,0x01,0x03,0x01,0x03,0x00,0x41,0x04,0x01,0x03,0x00,0x41,0xA0,0x01,0x03,0x00,0x01,0x05,0x00,0x03,0xC0,0xC3,0x02 },
|
||||
{ 0x21,0x03,0x19,0x0C,0x00,0x01,0x01,0x01,0x02,0x01,0x03,0x01,0x05,0x01,0x80,0x01,0x81,0x01,0x82,0x01,0x83,0x01,0x85,0x01,0x06,0x01,0x70,0x01},
|
||||
{ 0x03,0x00,0x07,0x99,0x50,0x00,0x70,0x00,0x00,0x01},
|
||||
{ 0x03,0x00,0x09,0x99,0x50,0x80,0xCA,0x00,0xFE,0x02,0xDF,0x21 }
|
||||
};
|
||||
|
||||
uint8_t NQ220_cmds[][255] =
|
||||
{
|
||||
{ 0x20,0x00,0x01,0x00 },
|
||||
{ 0x20,0x01,0x00 },
|
||||
{ 0x2F,0x02,0x00 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x0F },
|
||||
{ 0x20,0x03,0x07,0x03,0xA0,0x02,0xA0,0x03,0xA0,0x04 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0x44,0x01,0x00 },
|
||||
{ 0x20,0x02,0x0B,0x02,0xA0,0x66,0x01,0x00,0xA0,0x0E,0x03,0x02,0x09,0x00 },
|
||||
{ 0x20,0x02,0x26,0x09,0xA0,0xEC,0x01,0x01,0xA0,0xED,0x01,0x03,0xA0,0x5E,0x01,0x01,0xA0,0x12,0x01,0x02,0xA0,0x40,0x01,0x01,0xA0,0xDD,0x01,0x2D,0xA0,0xF2,0x01,0x01,0xA0,0x96,0x01,0x01,0xA0,0x9F,0x02,0x08,0x08 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEC },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x14 },
|
||||
{ 0x20,0x02,0x2E,0x0E,0x28,0x01,0x00,0x21,0x01,0x00,0x30,0x01,0x08,0x31,0x01,0x03,0x32,0x01,0x60,0x38,0x01,0x01,0x33,0x04,0x01,0x02,0x03,0x04,0x54,0x01,0x06,0x50,0x01,0x02,0x5B,0x01,0x00,0x80,0x01,0x01,0x81,0x01,0x01,0x82,0x01,0x0E,0x18,0x01,0x01 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0x62,0x01,0x01 },
|
||||
{ 0x20,0x02,0x06,0x01,0xA0,0xF3,0x02,0x10,0x27 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x85 },
|
||||
{ 0x21,0x01,0x07,0x00,0x01,0x01,0x03,0x00,0x01,0x05 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0xF1,0x01,0x00 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0x91,0x01,0x01 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x0F },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x00,0x01,0x00 },
|
||||
{ 0x20,0x01,0x00 },
|
||||
{ 0x20,0x03,0x02,0x01,0x00 },
|
||||
{ 0x20,0x03,0x02,0x01,0x29 },
|
||||
{ 0x20,0x03,0x02,0x01,0x61 },
|
||||
{ 0x20,0x03,0x02,0x01,0x60 },
|
||||
{ 0x21,0x00,0x0D,0x04,0x04,0x03,0x02,0x05,0x03,0x03,0x03,0x02,0x01,0x80,0x01,0x80 },
|
||||
{ 0x22,0x00,0x01,0x01 },
|
||||
{ 0x20,0x04,0x06,0x03,0x01,0x01,0x02,0x01,0x01 },
|
||||
{ 0x03,0x00,0x05,0x81,0x01,0x03,0x02,0xC0 },
|
||||
{ 0x03,0x00,0x05,0x81,0x01,0x06,0x01,0x00 },
|
||||
{ 0x03,0x00,0x03,0x81,0x02,0x01 },
|
||||
{ 0x03,0x00,0x03,0x81,0x02,0x04 },
|
||||
{ 0x20,0x03,0x05,0x02,0xA0,0xEC,0xA0,0xED },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xF0 },
|
||||
{ 0x20,0x03,0x05,0x02,0xA0,0xEC,0xA0,0xED },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x14 },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0xEB },
|
||||
{ 0x20,0x03,0x03,0x01,0xA0,0x07 },
|
||||
{ 0x20,0x02,0x05,0x01,0xA0,0x07,0x01,0x03 },
|
||||
{ 0x20,0x03,0x02,0x01,0x52 },
|
||||
{ 0x21,0x01,0x16,0x00,0x04,0x01,0x03,0x00,0x01,0x03,0x01,0x03,0x00,0x41,0x04,0x01,0x03,0x00,0x41,0xA0,0x01,0x03,0x00,0x01,0x05 },
|
||||
{ 0x20,0x02,0x0A,0x03,0x32,0x01,0x20,0x38,0x01,0x01,0x50,0x01,0x00 },
|
||||
{ 0x21,0x03,0x07,0x03,0x80,0x01,0x81,0x01,0x82,0x01 },
|
||||
{ 0x21,0x06,0x01,0x00 },
|
||||
{ 0x20,0x02,0x17,0x01,0x61,0x14,0x46,0x66,0x6D,0x01,0x01,0x12,0x02,0x02,0x07,0xFF,0x03,0x02,0x00,0x13,0x04,0x01,0x64,0x07,0x01,0x03 },
|
||||
{ 0x20,0x02,0x0A,0x03,0x32,0x01,0x60,0x38,0x01,0x01,0x50,0x01,0x02 },
|
||||
{ 0x21,0x03,0x19,0x0C,0x00,0x01,0x01,0x01,0x02,0x01,0x03,0x01,0x05,0x01,0x80,0x01,0x81,0x01,0x82,0x01,0x83,0x01,0x85,0x01,0x06,0x01,0x70,0x01 }
|
||||
};
|
||||
724
feeds/ipq95xx/ftm/src/ftm_nfcqti.c
Executable file
724
feeds/ipq95xx/ftm/src/ftm_nfcqti.c
Executable file
@@ -0,0 +1,724 @@
|
||||
/*=========================================================================
|
||||
NFC FTM Source File
|
||||
Description
|
||||
This file contains the routines to communicate with the NFCC in FTM mode.
|
||||
|
||||
Copyright (c) 2015 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
===========================================================================*/
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
===========================================================================*/
|
||||
/*==========================================================================*
|
||||
* INCLUDE FILES *
|
||||
*==========================================================================*/
|
||||
#include "ftm_nfcqti.h"
|
||||
|
||||
#define UNUSED(x) (void)(x)
|
||||
|
||||
/*=========================================================================*
|
||||
* file scope local defnitions *
|
||||
*==========================================================================*/
|
||||
const hw_module_t* hw_module = NULL;
|
||||
nfc_nci_device_t* dev = NULL;
|
||||
uint8 hal_state = NCI_HAL_INIT, nfc_ftmthread = FALSE;
|
||||
uint8 *nfc_cmd_buff = NULL, len = 0;
|
||||
uint16 res_len = 0, async_msg_cnt = 0;
|
||||
uint8 *response_buff = NULL;
|
||||
static uint8 hal_opened = FALSE, wait_rsp = FALSE;
|
||||
static uint8 async_msg_available = FALSE, ftm_data_rsp_pending = FALSE;
|
||||
asyncdata *buff = NULL;
|
||||
asyncdata *start = NULL;
|
||||
/*I2C read/write*/
|
||||
static uint8 i2c_cmd_cnt = 0;
|
||||
uint8 i2c_status=0,i2c_req_write = FALSE, i2c_req_read = FALSE;
|
||||
uint8 i2c_num_of_reg_to_read = 0, i2c_reg_read_data[40]={0}, ii = 0;
|
||||
pthread_mutex_t nfcftm_mutex = PTHREAD_MUTEX_INITIALIZER;
|
||||
/*===================================================================================*
|
||||
* Function Defnitions *
|
||||
*===================================================================================*/
|
||||
/*====================================================================================
|
||||
FUNCTION nfc_ftm_hal_cback
|
||||
DESCRIPTION
|
||||
This is the call back function which will indicate if the nfc hal open is successful
|
||||
or failed.
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
RETURN VALUE
|
||||
none
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
=====================================================================================*/
|
||||
static void nfc_ftm_cback(uint8 event, uint8 status)
|
||||
{
|
||||
switch(event)
|
||||
{
|
||||
case HAL_NFC_OPEN_CPLT_EVT:
|
||||
if(status == HAL_NFC_STATUS_OK)
|
||||
{
|
||||
/* Release semaphore to indicate that hal open is done
|
||||
and change the state to write.*/
|
||||
hal_state = NCI_HAL_WRITE;
|
||||
hal_opened = TRUE;
|
||||
printf("HAL Open Success..state changed to Write \n");
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("HAL Open Failed \n");
|
||||
hal_state = NCI_HAL_ERROR;
|
||||
hal_opened = FALSE;
|
||||
}
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
break;
|
||||
case HAL_NFC_CLOSE_CPLT_EVT:
|
||||
printf("HAL_NFC_CLOSE_CPLT_EVT recieved..\n");
|
||||
break;
|
||||
default:
|
||||
printf ("nfc_ftm_hal_cback unhandled event %x \n", event);
|
||||
break;
|
||||
}
|
||||
}
|
||||
/*==========================================================================================
|
||||
FUNCTION fill_async_data
|
||||
DESCRIPTION
|
||||
This function will store all the incoming async msgs( like ntfs and data from QCA1990)
|
||||
in to a list to be committed further.
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
RETURN VALUE
|
||||
NONE
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
==============================================================================================*/
|
||||
void fill_async_data(uint16 data_len, uint8 *p_data)
|
||||
{
|
||||
uint16 i = 0;
|
||||
asyncdata *next_node = NULL;
|
||||
printf("fill_async_data() function \n");
|
||||
/* Initialize a list which will store all async message untill they are sent*/
|
||||
if(buff == NULL)
|
||||
{
|
||||
/* first node creation*/
|
||||
buff = (asyncdata*)malloc(sizeof(asyncdata));
|
||||
if(buff)
|
||||
{
|
||||
start = buff;
|
||||
buff->response_buff = (uint8*)malloc(data_len);
|
||||
if(buff->response_buff)
|
||||
{
|
||||
memcpy(buff->response_buff, p_data, data_len);
|
||||
buff->async_datalen = data_len;
|
||||
buff->next = NULL;
|
||||
async_msg_cnt = 0;
|
||||
async_msg_cnt++;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("mem allocation failed while storing asysnc msg \n");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("mem allocation failed while trying to make the async list \n");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* this is the case when some data is already present in the list which has not been sent yet*/
|
||||
next_node = (asyncdata*)malloc(sizeof(asyncdata));
|
||||
if(next_node)
|
||||
{
|
||||
next_node->response_buff = (uint8*)malloc(data_len);
|
||||
if(next_node->response_buff)
|
||||
{
|
||||
memcpy(next_node->response_buff, p_data,data_len);
|
||||
next_node->async_datalen = data_len;
|
||||
next_node->next = NULL;
|
||||
async_msg_cnt++;
|
||||
while(buff->next != NULL)
|
||||
{
|
||||
buff = buff->next;
|
||||
}
|
||||
buff->next = next_node;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("mem allocation failed while storing asysnc msg \n");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("mem allocation failed while trying to make the async list \n");
|
||||
}
|
||||
}
|
||||
}
|
||||
/*======================================================================================================
|
||||
FUNCTION nfc_ftm_data_cback
|
||||
DESCRIPTION
|
||||
This is the call back function which will provide back incoming data from the QCA1990
|
||||
to nfc ftm.
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
RETURN VALUE
|
||||
NONE
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
========================================================================================================*/
|
||||
static void nfc_ftm_data_cback(uint16 data_len, uint8 *p_data)
|
||||
{
|
||||
uint8 i = 0;
|
||||
if(hal_opened == FALSE)
|
||||
{
|
||||
/* Reject data call backs untill HAL in initialized */
|
||||
return;
|
||||
}
|
||||
if((data_len == 0x00) || (p_data == NULL))
|
||||
{
|
||||
printf("Error case : wrong data lentgh or buffer revcieved \n");
|
||||
return;
|
||||
}
|
||||
if((i2c_req_write == TRUE) || (i2c_req_read == TRUE))
|
||||
{
|
||||
if(i2c_req_write)
|
||||
{
|
||||
/*check the incoming status*/
|
||||
if(p_data[0] != 0x00) /* 0x00 = Command executed successfully*/
|
||||
{
|
||||
/* some error has occured in I2C write.Send the status code back now to pc app*/
|
||||
i2c_status = p_data[0];
|
||||
printf("Error occured in I2C write .. reporting to application..Error Code = %X \n", i2c_status);
|
||||
hal_state = NCI_HAL_READ;
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
else
|
||||
{
|
||||
/*status is fine. Complete further requests as ftmdaemon is writing one by one*/
|
||||
if(len)
|
||||
{
|
||||
/*send further addr and value pair*/
|
||||
printf("I2C write status correct..sending next..\n");
|
||||
hal_state = NCI_HAL_WRITE;
|
||||
}
|
||||
else
|
||||
{
|
||||
/*All I2C write completed .Send final status to app*/
|
||||
i2c_status = p_data[0];
|
||||
printf(" All I2C write completed i2c_status = %X \n", i2c_status);
|
||||
hal_state = NCI_HAL_READ;
|
||||
}
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/*I2C read rsp arrived . fill it in buffer if correct or report error if wrong*/
|
||||
if(p_data[0] != 0x00)
|
||||
{
|
||||
/* some error has occured in I2C read.Send the status code to app*/
|
||||
i2c_status = p_data[0];
|
||||
printf("Error occured in I2C read .. reporting to application..Error Code = %X \n", i2c_status);
|
||||
hal_state = NCI_HAL_READ;
|
||||
memset(nfc_cmd_buff, 0, len);
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(len)
|
||||
{
|
||||
/*send further addr to read*/
|
||||
i2c_status = p_data[0];
|
||||
i2c_reg_read_data[ii++] = p_data[1];
|
||||
hal_state = NCI_HAL_WRITE;
|
||||
}
|
||||
else
|
||||
{
|
||||
/*All I2C read completed .Send the read data back to pc app*/
|
||||
i2c_status = p_data[0];
|
||||
i2c_reg_read_data[ii++] = p_data[1];
|
||||
hal_state = NCI_HAL_READ;
|
||||
ii = 0;
|
||||
}
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(((p_data[0] & 0xF0) == 0x60 /*ntf packets*/) || ((p_data[0] & 0xF0) == 0x00)/*data packet rsps*/)
|
||||
{
|
||||
async_msg_available = TRUE;
|
||||
pthread_mutex_lock(&nfcftm_mutex);
|
||||
fill_async_data(data_len, p_data);
|
||||
pthread_mutex_unlock(&nfcftm_mutex);
|
||||
if(ftm_data_rsp_pending == TRUE)
|
||||
{
|
||||
printf("Sending data rsp \n");
|
||||
hal_state = NCI_HAL_READ;
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
ftm_data_rsp_pending = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if((wait_rsp == FALSE) || ((p_data[0] == 0x60) && (p_data[1] == 0x00)))
|
||||
{
|
||||
/*This is the case when ntf receieved after rsp is logged to pc app*/
|
||||
printf("Sending async msg to logging subsystem \n");
|
||||
hal_state = NCI_HAL_ASYNC_LOG;
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(response_buff || res_len)
|
||||
{
|
||||
printf("nfc_ftm_data_cback : response_buff = %p, res_len = %d", response_buff, res_len);
|
||||
return;
|
||||
}
|
||||
response_buff = (uint8*)malloc(data_len);
|
||||
if(response_buff)
|
||||
{
|
||||
memcpy(response_buff, p_data, data_len);
|
||||
res_len = data_len;
|
||||
printf("nfc_ftm_data_cback: res_len=%d data_len=%d response_buff= %X %X %X %X %X %X \n", res_len,data_len, \
|
||||
response_buff[0],response_buff[1],response_buff[2],response_buff[3],response_buff[4],response_buff[5]);
|
||||
hal_state = NCI_HAL_READ;
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("Mem allocation failed in nfc_ftm_data_cback \n");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_nfc_hal_open
|
||||
DESCRIPTION
|
||||
This function will open the nfc hal for ftm nfc command processing.
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
RETURN VALUE
|
||||
void
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
===============================================================================*/
|
||||
uint8 ftm_nfc_hal_open(void)
|
||||
{
|
||||
uint8 ret = 0;
|
||||
ret = hw_get_module(NFC_NCI_HARDWARE_MODULE, &hw_module);
|
||||
if(ret == 0)
|
||||
{
|
||||
dev = (nfc_nci_device_t*)malloc(sizeof(nfc_nci_device_t));
|
||||
if(!dev)
|
||||
{
|
||||
printf("NFC FTM : mem allocation failed \n");
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = nfc_nci_open (hw_module, &dev);
|
||||
if(ret != 0)
|
||||
{
|
||||
printf("NFC FTM : nfc_nci_open fail \n");
|
||||
free(dev);
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("NFC FTM : opening NCI HAL \n");
|
||||
dev->common.reserved[0] = FTM_MODE;
|
||||
dev->open (dev, nfc_ftm_cback, nfc_ftm_data_cback);
|
||||
sem_wait(&semaphore_halcmd_complete);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("NFC FTM : hw_get_module() call failed \n");
|
||||
return FALSE;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
/*=================================================================================================
|
||||
FUNCTION ftm_nfc_log_send_msg
|
||||
DESCRIPTION
|
||||
This function will log the asynchronous messages(NTFs and data packets) to the logging subsystem
|
||||
of DIAG.
|
||||
DEPENDENCIES
|
||||
RETURN VALUE
|
||||
TRUE if data logged successfully and FALSE if failed.
|
||||
SIDE EFFECTS
|
||||
None
|
||||
==================================================================================================*/
|
||||
int ftm_nfc_log_send_msg(void)
|
||||
{
|
||||
uint16 i = 0;
|
||||
ftm_nfc_log_pkt_type* ftm_nfc_log_pkt_ptr = NULL;
|
||||
asyncdata* node = NULL;
|
||||
uint8 arr[1]= {'\n'};
|
||||
if(log_status(LOG_NFC_FTM))
|
||||
{
|
||||
buff = start;
|
||||
if(buff != NULL)
|
||||
{
|
||||
do{
|
||||
printf("buff->async_datalen : %d \n", buff->async_datalen);
|
||||
ftm_nfc_log_pkt_ptr = (ftm_nfc_log_pkt_type *)log_alloc(LOG_NFC_FTM, (FTM_NFC_LOG_HEADER_SIZE + (buff->async_datalen)));
|
||||
if(ftm_nfc_log_pkt_ptr)
|
||||
{
|
||||
memcpy((void *)ftm_nfc_log_pkt_ptr->data, (void *)buff->response_buff, buff->async_datalen);
|
||||
printf("Async msg is = ");
|
||||
for(i=0; i<buff->async_datalen; i++)
|
||||
{
|
||||
printf("%X ", ftm_nfc_log_pkt_ptr->data[i]);
|
||||
}
|
||||
printf("%c",arr[0]);
|
||||
node = buff;
|
||||
buff = buff->next;
|
||||
free(node);
|
||||
printf("Commiting the log message(async msg) \n");
|
||||
log_commit(ftm_nfc_log_pkt_ptr);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("\nmem alloc failed in log_alloc \n");
|
||||
return FALSE;
|
||||
}
|
||||
}while(buff != NULL);
|
||||
printf("all msgs committed \n");
|
||||
async_msg_available = FALSE;
|
||||
return TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("No async message left to be logged \n");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("LOG_NFC_FTM code is not enabled in logging subsystem \n");
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION nfc_ftm_readerthread
|
||||
DESCRIPTION
|
||||
Thread Routine to perfom asynchrounous handling of events coming from
|
||||
NFCC. It will perform read and write for all type of commands/data.
|
||||
DEPENDENCIES
|
||||
RETURN VALUE
|
||||
RETURN NIL
|
||||
SIDE EFFECTS
|
||||
None
|
||||
===========================================================================*/
|
||||
void* nfc_ftm_thread(void *ptr)
|
||||
{
|
||||
uint8 i2c_buff[3] = {0};
|
||||
|
||||
UNUSED(ptr);
|
||||
|
||||
while(1)
|
||||
{
|
||||
printf("Waiting for Cmd/Rsp \n");
|
||||
sem_wait (&semaphore_halcmd_complete);
|
||||
switch(hal_state)
|
||||
{
|
||||
case NCI_HAL_INIT:
|
||||
printf("NFC FTM : HAL Open request recieved..\n");
|
||||
if(ftm_nfc_hal_open() == FALSE)
|
||||
{
|
||||
hal_state = NCI_HAL_ERROR;
|
||||
hal_opened = FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
case NCI_HAL_ERROR:
|
||||
/* HAL open failed.Post sem and handle error case*/
|
||||
sem_post(&semaphore_nfcftmcmd_complete);
|
||||
break;
|
||||
case NCI_HAL_WRITE:
|
||||
if(dev != NULL)
|
||||
{
|
||||
printf("NFC FTM : Cmd recieved for nfc ftm..sending.\n");
|
||||
if((!i2c_req_write) && (!i2c_req_read))
|
||||
{
|
||||
/* send data to the NFCC*/
|
||||
if(nfc_cmd_buff[0] == 0x00 /*data req*/)
|
||||
{
|
||||
printf("Data send request arrived \n");
|
||||
ftm_data_rsp_pending = TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("cmd request arrived \n");
|
||||
wait_rsp = TRUE;
|
||||
}
|
||||
dev->write(dev, len, nfc_cmd_buff);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(i2c_req_write)
|
||||
{
|
||||
i2c_buff[0] = 0xFF;
|
||||
i2c_buff[1] = nfc_cmd_buff[i2c_cmd_cnt++]; /* addr*/
|
||||
i2c_buff[2] = nfc_cmd_buff[i2c_cmd_cnt++]; /*value*/
|
||||
len -=2;
|
||||
dev->write(dev, 3, i2c_buff);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* I2c Read req*/
|
||||
i2c_buff[0] = 0xFF;
|
||||
i2c_buff[1] = nfc_cmd_buff[i2c_cmd_cnt++]; /* I2C addr to read*/
|
||||
i2c_reg_read_data[ii++] = i2c_buff[1]; /* store address to send in response.*/
|
||||
len -= 1;
|
||||
dev->write(dev, 2, i2c_buff);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("dev is null \n");
|
||||
}
|
||||
break;
|
||||
case NCI_HAL_READ:
|
||||
/* indicate to ftm that response is avilable now*/
|
||||
sem_post(&semaphore_nfcftmcmd_complete);
|
||||
printf("NFC FTM : State changed to READ i2c_req_read: %d\n",i2c_req_read);
|
||||
break;
|
||||
case NCI_HAL_ASYNC_LOG:
|
||||
/* indicate to ftm that response is avilable now*/
|
||||
printf("NFC FTM : State changed to NCI_HAL_ASYNC_LOG.Logging aysnc message \n");
|
||||
pthread_mutex_lock(&nfcftm_mutex);
|
||||
if(ftm_nfc_log_send_msg())
|
||||
{
|
||||
printf("async msgs commited to the log system..changing HAL state to write \n");
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("async msgs commit failed..changing HAL state to write \n");
|
||||
}
|
||||
hal_state = NCI_HAL_WRITE;
|
||||
pthread_mutex_unlock(&nfcftm_mutex);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
/*===========================================================================
|
||||
FUNCTION ftm_nfc_dispatch
|
||||
DESCRIPTION
|
||||
This is the function which will be called by the NFC FTM layer callback function
|
||||
registered with the DIAG service./
|
||||
DEPENDENCIES
|
||||
RETURN VALUE
|
||||
RETURN rsp pointer(containing the NFCC rsp packets) to the callback function
|
||||
(subsequently for DIAG service)
|
||||
SIDE EFFECTS
|
||||
None
|
||||
===========================================================================*/
|
||||
void* ftm_nfc_dispatch_qti(ftm_nfc_pkt_type *nfc_ftm_pkt, uint16 pkt_len)
|
||||
{
|
||||
ftm_nfc_i2c_write_rsp_pkt_type *i2c_write_rsp = NULL;
|
||||
ftm_nfc_i2c_read_rsp_pkt_type *i2c_read_rsp = NULL;
|
||||
ftm_nfc_pkt_type *rsp = NULL;
|
||||
ftm_nfc_data_rsp_pkt_type *nfc_data_rsp = NULL;
|
||||
struct timespec time_sec;
|
||||
int sem_status;
|
||||
|
||||
UNUSED(pkt_len);
|
||||
|
||||
printf("NFC FTM : nfc ftm mode requested \n");
|
||||
if(nfc_ftm_pkt == NULL)
|
||||
{
|
||||
printf("Error : NULL packet recieved from DIAG \n");
|
||||
goto error_case;
|
||||
}
|
||||
/* Start nfc_ftm_thread which will process all requests as per
|
||||
state machine flow. By Default First state will be NCI_HAL_INIT*/
|
||||
if(!nfc_ftmthread)
|
||||
{
|
||||
if(sem_init(&semaphore_halcmd_complete, 0, 1) != 0)
|
||||
{
|
||||
printf("NFC FTM :semaphore_halcmd_complete creation failed \n");
|
||||
goto error_case;
|
||||
}
|
||||
if(sem_init(&semaphore_nfcftmcmd_complete, 0, 0) != 0)
|
||||
{
|
||||
printf("NFC FTM :semaphore_nfcftmcmd_complete creation failed \n");
|
||||
goto error_case;
|
||||
}
|
||||
printf("NFC FTM : nfc ftm thread is being started \n");
|
||||
pthread_create(&nfc_thread_handle, NULL, nfc_ftm_thread, NULL);
|
||||
nfc_ftmthread = TRUE;
|
||||
}
|
||||
/* parse the diag packet to identify the NFC FTM command which needs to be sent
|
||||
to QCA 1990*/
|
||||
if(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_len > 2)
|
||||
{
|
||||
len = nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_len-2;
|
||||
}
|
||||
else
|
||||
{
|
||||
/*Wrong nfc ftm packet*/
|
||||
goto error_case;
|
||||
}
|
||||
switch(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id)
|
||||
{
|
||||
case FTM_NFC_I2C_SLAVE_WRITE:
|
||||
i2c_req_write = TRUE;
|
||||
break;
|
||||
case FTM_NFC_I2C_SLAVE_READ:
|
||||
i2c_num_of_reg_to_read = len;
|
||||
i2c_req_read = TRUE;
|
||||
break;
|
||||
case FTM_NFC_NFCC_COMMAND:
|
||||
case FTM_NFC_SEND_DATA:
|
||||
break;
|
||||
default :
|
||||
goto error_case;
|
||||
break;
|
||||
}
|
||||
/*copy command to send it further to QCA1990*/
|
||||
nfc_cmd_buff = (uint8 *)malloc(len+1);
|
||||
if(nfc_cmd_buff)
|
||||
{
|
||||
memcpy(nfc_cmd_buff, nfc_ftm_pkt->nci_data, len);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("Mem allocation failed for cmd storage");
|
||||
goto error_case;
|
||||
}
|
||||
/*send the command */
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
printf("\nwaiting for nfc ftm response \n");
|
||||
if (clock_gettime(CLOCK_REALTIME, &time_sec) == -1)
|
||||
{
|
||||
printf("get clock_gettime error");
|
||||
}
|
||||
time_sec.tv_sec += FTM_NFC_CMD_CMPL_TIMEOUT;
|
||||
sem_status = sem_timedwait(&semaphore_nfcftmcmd_complete,&time_sec);
|
||||
if(sem_status == -1)
|
||||
{
|
||||
printf("nfc ftm command timed out\n");
|
||||
goto error_case;
|
||||
}
|
||||
if(!hal_opened)
|
||||
{
|
||||
/*Hal open is failed */
|
||||
free(nfc_cmd_buff);
|
||||
hal_state = NCI_HAL_INIT;
|
||||
goto error_case;
|
||||
}
|
||||
printf("\n\n *****Framing the response to send back to Diag service******** \n\n");
|
||||
/* Frame the response as per the cmd request*/
|
||||
switch(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id)
|
||||
{
|
||||
case FTM_NFC_I2C_SLAVE_WRITE:
|
||||
printf("Framing the response for FTM_NFC_I2C_SLAVE_WRITE cmd \n");
|
||||
i2c_write_rsp = (ftm_nfc_i2c_write_rsp_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof(ftm_nfc_i2c_write_rsp_pkt_type));
|
||||
if(i2c_write_rsp)
|
||||
{
|
||||
i2c_write_rsp->nfc_i2c_slave_status = i2c_status;
|
||||
i2c_status = 0;
|
||||
i2c_cmd_cnt = 0;
|
||||
i2c_req_write = FALSE;
|
||||
}
|
||||
break;
|
||||
case FTM_NFC_I2C_SLAVE_READ:
|
||||
printf("Framing the response for FTM_NFC_I2C_SLAVE_READ cmd \n");
|
||||
i2c_read_rsp = (ftm_nfc_i2c_read_rsp_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof(ftm_nfc_i2c_read_rsp_pkt_type));
|
||||
if(i2c_read_rsp)
|
||||
{
|
||||
i2c_read_rsp->ftm_nfc_hdr.nfc_cmd_id = FTM_NFC_I2C_SLAVE_READ;
|
||||
i2c_read_rsp->ftm_nfc_hdr.nfc_cmd_len = 2+(2*i2c_num_of_reg_to_read);
|
||||
i2c_read_rsp->nfc_i2c_slave_status = i2c_status;
|
||||
if(i2c_status == 0x00)
|
||||
{
|
||||
i2c_read_rsp->nfc_nb_reg_reads = i2c_num_of_reg_to_read;
|
||||
}
|
||||
else
|
||||
{
|
||||
i2c_read_rsp->nfc_nb_reg_reads = 0x00; // error case so return num of read as 0x00.
|
||||
}
|
||||
memcpy(i2c_read_rsp->i2c_reg_read_rsp, i2c_reg_read_data, (i2c_num_of_reg_to_read*2));
|
||||
i2c_cmd_cnt = 0;
|
||||
}
|
||||
break;
|
||||
case FTM_NFC_NFCC_COMMAND:
|
||||
printf("Framing the response for FTM_NFC_NFCC_COMMAND cmd \n");
|
||||
if(response_buff && res_len)
|
||||
{
|
||||
rsp = (ftm_nfc_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof(ftm_nfc_pkt_type));
|
||||
if(rsp)
|
||||
{
|
||||
rsp->ftm_nfc_hdr.nfc_cmd_id = FTM_NFC_NFCC_COMMAND;
|
||||
rsp->ftm_nfc_hdr.nfc_cmd_len = 2+res_len;
|
||||
rsp->nfc_nci_pkt_len = res_len;
|
||||
memcpy(rsp->nci_data, response_buff, res_len);
|
||||
free(response_buff);
|
||||
response_buff = 0;
|
||||
res_len = 0;
|
||||
}
|
||||
}
|
||||
else
|
||||
printf("ftm_nfc_dispatch : response_buff = %p, res_len = %d", response_buff, res_len);
|
||||
break;
|
||||
case FTM_NFC_SEND_DATA:
|
||||
printf("Framing the response for FTM_NFC_SEND_DATA cmd \n");
|
||||
nfc_data_rsp = (ftm_nfc_data_rsp_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_NFC_CMD_CODE,
|
||||
sizeof(ftm_nfc_data_rsp_pkt_type));
|
||||
if(nfc_data_rsp)
|
||||
{
|
||||
nfc_data_rsp->ftm_nfc_hdr.nfc_cmd_id = FTM_NFC_SEND_DATA;
|
||||
nfc_data_rsp->ftm_nfc_hdr.nfc_cmd_len = 0;/*Rsp as per the NFC FTM data rsp req*/
|
||||
}
|
||||
break;
|
||||
default:
|
||||
goto error_case;
|
||||
break;
|
||||
}
|
||||
free(nfc_cmd_buff);
|
||||
hal_state = NCI_HAL_WRITE;
|
||||
if(async_msg_available)
|
||||
{
|
||||
printf(" Some async message available.. committing now.\n");
|
||||
hal_state = NCI_HAL_ASYNC_LOG;
|
||||
sem_post(&semaphore_halcmd_complete);
|
||||
}
|
||||
wait_rsp = FALSE;
|
||||
if(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id == FTM_NFC_I2C_SLAVE_WRITE)
|
||||
{
|
||||
return(void*)i2c_write_rsp;
|
||||
}
|
||||
else if(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id == FTM_NFC_I2C_SLAVE_READ)
|
||||
{
|
||||
i2c_req_read = FALSE;
|
||||
return(void*)i2c_read_rsp;
|
||||
}
|
||||
else if(nfc_ftm_pkt->ftm_nfc_hdr.nfc_cmd_id == FTM_NFC_NFCC_COMMAND)
|
||||
{
|
||||
return(void*)rsp;
|
||||
}
|
||||
else
|
||||
{
|
||||
return(void*)nfc_data_rsp;
|
||||
}
|
||||
error_case:
|
||||
return NULL;
|
||||
}
|
||||
141
feeds/ipq95xx/ftm/src/ftm_nfcqti.h
Executable file
141
feeds/ipq95xx/ftm/src/ftm_nfcqti.h
Executable file
@@ -0,0 +1,141 @@
|
||||
#ifndef FTM_NFCQTI_H_
|
||||
#define FTM_NFCQTI_H_
|
||||
/*==========================================================================
|
||||
|
||||
nfc FTM header File
|
||||
|
||||
Description
|
||||
This file contains the decalarations used by ftm_nfc.c
|
||||
|
||||
Copyright (c) 2015 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
08/06/13 NFC FTM layer
|
||||
===========================================================================*/
|
||||
|
||||
#ifdef CONFIG_FTM_NFC
|
||||
|
||||
#include "stdio.h"
|
||||
#include <pthread.h>
|
||||
#include <semaphore.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/types.h>
|
||||
#include <hardware/nfc.h>
|
||||
#include <hardware/hardware.h>
|
||||
#include <malloc.h>
|
||||
#include <string.h>
|
||||
#include "msg.h"
|
||||
#include "log.h"
|
||||
|
||||
#include "diag_lsm.h"
|
||||
#include "diagpkt.h"
|
||||
#include "diagcmd.h"
|
||||
#include "diag.h"
|
||||
#include "termios.h"
|
||||
|
||||
/*==========================================================================*
|
||||
* Defnitions *
|
||||
*==========================================================================*/
|
||||
#define FTM_MODE 1
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
#define FTM_MODE 1
|
||||
#define FTM_NFC_CMD_CODE 55
|
||||
#define LOG_NFC_FTM 0x1802
|
||||
#define FTM_NFC_LOG_HEADER_SIZE 12
|
||||
|
||||
#define FTM_NFC_I2C_SLAVE_WRITE 0x00
|
||||
#define FTM_NFC_I2C_SLAVE_READ 0x01
|
||||
#define FTM_NFC_NFCC_COMMAND 0x02
|
||||
#define FTM_NFC_SEND_DATA 0x03
|
||||
|
||||
#define FTM_NFC_CMD_CMPL_TIMEOUT 15
|
||||
|
||||
#ifdef ANDROID_M
|
||||
#define NFC_NCI_HARDWARE_MODULE "nfc_nci.qc199x"
|
||||
#else
|
||||
#define NFC_NCI_HARDWARE_MODULE "nfc_nci"
|
||||
#endif
|
||||
|
||||
enum
|
||||
{
|
||||
NCI_HAL_INIT,
|
||||
NCI_HAL_WRITE,
|
||||
NCI_HAL_READ,
|
||||
NCI_HAL_DEINIT,
|
||||
NCI_HAL_ASYNC_LOG,
|
||||
NCI_HAL_ERROR
|
||||
};
|
||||
/*==========================================================================*
|
||||
* Declarations *
|
||||
*==========================================================================*/
|
||||
/* Reader thread handle */
|
||||
pthread_t nfc_thread_handle;
|
||||
sem_t semaphore_halcmd_complete;
|
||||
sem_t semaphore_nfcftmcmd_complete;
|
||||
|
||||
/* structure that contains nfc cmd id and len
|
||||
part of the packet recieved from DIAG*/
|
||||
PACKED struct ftm_nfc_cmd_header_type{
|
||||
uint16 nfc_cmd_id;
|
||||
uint16 nfc_cmd_len;
|
||||
};
|
||||
|
||||
/* nfc FTM packet(for NCI cmd/rsp messages)*/
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
struct ftm_nfc_cmd_header_type ftm_nfc_hdr;
|
||||
uint16 nfc_nci_pkt_len;
|
||||
byte nci_data[258];
|
||||
}ftm_nfc_pkt_type;
|
||||
|
||||
/* nfc FTM packet (for I2C write messgaes)*/
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
uint8 nfc_i2c_slave_status;
|
||||
}ftm_nfc_i2c_write_rsp_pkt_type;
|
||||
|
||||
/* nfc FTM packet (for I2C read messgaes)*/
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
struct ftm_nfc_cmd_header_type ftm_nfc_hdr;
|
||||
uint8 nfc_i2c_slave_status;
|
||||
uint8 nfc_nb_reg_reads;
|
||||
byte i2c_reg_read_rsp[30];
|
||||
}ftm_nfc_i2c_read_rsp_pkt_type;
|
||||
|
||||
|
||||
typedef PACKED struct{
|
||||
diagpkt_subsys_header_type diag_hdr;
|
||||
struct ftm_nfc_cmd_header_type ftm_nfc_hdr;
|
||||
}ftm_nfc_data_rsp_pkt_type;
|
||||
|
||||
typedef PACKED struct{
|
||||
log_hdr_type hdr;
|
||||
byte data[1];
|
||||
}ftm_nfc_log_pkt_type;
|
||||
|
||||
/*Data buffer linked list*/
|
||||
typedef struct asyncdata {
|
||||
uint8 *response_buff;
|
||||
uint8 async_datalen;
|
||||
struct asyncdata *next;
|
||||
}asyncdata;
|
||||
|
||||
typedef void (tHAL_NFC_CBACK) (uint8 event, uint8 status);
|
||||
typedef void (tHAL_NFC_DATA_CBACK) (uint16 data_len, uint8 *p_data);
|
||||
|
||||
void* ftm_nfc_dispatch_qti(ftm_nfc_pkt_type *ftm_nfc_pkt, uint16 pkt_len);
|
||||
|
||||
#endif /* CONFIG_FTM_NFC */
|
||||
#endif /* FTM_NFCQTI_H_ */
|
||||
1212
feeds/ipq95xx/ftm/src/ftm_wlan.c
Executable file
1212
feeds/ipq95xx/ftm/src/ftm_wlan.c
Executable file
File diff suppressed because it is too large
Load Diff
235
feeds/ipq95xx/ftm/src/ftm_wlan.h
Executable file
235
feeds/ipq95xx/ftm/src/ftm_wlan.h
Executable file
@@ -0,0 +1,235 @@
|
||||
/*==========================================================================
|
||||
|
||||
FTM WLAN Header File
|
||||
|
||||
Description
|
||||
The header file includes enums, struct definitions for WLAN FTM packets
|
||||
|
||||
# Copyright (c) 2010-2011, 2014 by Qualcomm Technologies, Inc.
|
||||
# All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
07/11/11 karthikm Created header file to include enums, struct for WLAN FTM
|
||||
for Atheros support
|
||||
========================================================================*/
|
||||
|
||||
#ifndef FTM_WLAN_H_
|
||||
#define FTM_WLAN_H_
|
||||
|
||||
#ifdef CONFIG_FTM_WLAN
|
||||
|
||||
#include "diagpkt.h"
|
||||
#include <sys/types.h>
|
||||
|
||||
#define FTM_WLAN_CMD_CODE 22
|
||||
|
||||
/* TODO: For LE platforms only - need to extend it for BE platform too*/
|
||||
#define cpu32_to_le32(buf, val) \
|
||||
do { \
|
||||
buf[0] = val & 0xff; \
|
||||
buf[1] = (val >> 8) & 0xff; \
|
||||
buf[2] = (val >> 16) & 0xff; \
|
||||
buf[3] = (val >> 24) & 0xff; \
|
||||
} while(0)
|
||||
|
||||
/* TODO: For LE platforms only - need to extend it for BE platform too*/
|
||||
#define le_to_cpu16(buf, uint16_val) \
|
||||
do { \
|
||||
uint16_val = (buf[0] | buf[1] << 8); \
|
||||
} while(0)
|
||||
|
||||
/* TODO: For LE platforms only - need to extend it for BE platform too*/
|
||||
#define le_to_cpu32(buf, uint32_val) \
|
||||
do { \
|
||||
uint32_val = (buf[0] | buf[1] << 8 | buf[2] << 16 | buf[3] << 24); \
|
||||
} while(0)
|
||||
|
||||
extern char g_ifname[];
|
||||
|
||||
/* Various ERROR CODES supported by the FTM WLAN module*/
|
||||
typedef enum {
|
||||
FTM_ERR_CODE_PASS = 0,
|
||||
FTM_ERR_CODE_IOCTL_FAIL,
|
||||
FTM_ERR_CODE_SOCK_FAIL,
|
||||
FTM_ERR_CODE_UNRECOG_FTM
|
||||
}FTM_WLAN_LOAD_ERROR_CODES;
|
||||
|
||||
|
||||
#define CONFIG_HOST_TCMD_SUPPORT 1
|
||||
#define AR6000_IOCTL_SUPPORTED 1
|
||||
|
||||
#define ATH_MAC_LEN 6
|
||||
|
||||
#define FTM_WLAN_SSP_SUCCESS 0
|
||||
#define FTM_WLAN_SSP_FAIL 1
|
||||
|
||||
typedef enum {
|
||||
FTM_WLAN_COMMON_OP,
|
||||
FTM_WLAN_BDF_GET_MAX_TRANSFER_SIZE,
|
||||
FTM_WLAN_BDF_READ,
|
||||
FTM_WLAN_BDF_WRITE,
|
||||
FTM_WLAN_BDF_GET_FNAMEPATH,
|
||||
FTM_WLAN_BDF_SET_FNAMEPATH,
|
||||
#ifdef WIN_AP_AFC
|
||||
FTM_WLAN_SSP_GET_ID = 16,
|
||||
FTM_WLAN_SSP_STR_SSP = 17,
|
||||
FTM_WLAN_SSP_STR_LOC = 18,
|
||||
FTM_WLAN_SSP_STR_CFG = 19
|
||||
#endif /* WIN_AP_AFC */
|
||||
}FTM_WLAN_CMD;
|
||||
|
||||
typedef enum {
|
||||
WLAN_BDF_READ_SUCCESS,
|
||||
WLAN_BDF_READ_FAILED,
|
||||
WLAN_BDF_WRITE_SUCCESS,
|
||||
WLAN_BDF_WRITE_FAILED,
|
||||
WLAN_BDF_INVALID_SIZE = 5,
|
||||
WLAN_BDF_BAD_OFFSET,
|
||||
WLAN_BDF_FILE_OPEN_FAIL,
|
||||
WLAN_BDF_FILE_SEEK_FAIL,
|
||||
WLAN_BDF_FILE_STAT_FAIL,
|
||||
WLAN_BDF_PATH_GET_SUCCESS,
|
||||
WLAN_BDF_PATH_GET_FAILED,
|
||||
WLAN_BDF_PATH_SET_SUCCESS,
|
||||
WLAN_BDF_PATH_SET_FAILED
|
||||
}FTM_WLAN_ERROR_CODES;
|
||||
|
||||
#ifdef WIN_AP_HOST
|
||||
#define PACKED_STRUCT __attribute__((__packed__))
|
||||
#else
|
||||
#define PACKED_STRUCT __attribute__((packed))
|
||||
#endif
|
||||
|
||||
/*FTM WLAN request type*/
|
||||
|
||||
typedef struct
|
||||
{
|
||||
diagpkt_cmd_code_type cmd_code;
|
||||
diagpkt_subsys_id_type subsys_id;
|
||||
diagpkt_subsys_cmd_code_type subsys_cmd_code;
|
||||
uint16 cmd_id; /* command id (required) */
|
||||
uint16 cmd_data_len;
|
||||
uint16 cmd_rsp_pkt_size;
|
||||
union {
|
||||
struct {
|
||||
uint16 rsvd;
|
||||
byte rsvd1;
|
||||
byte rsvd2;
|
||||
byte wlanslotno;
|
||||
byte wlandeviceno;
|
||||
byte data[0];
|
||||
}PACKED_STRUCT common_ops;
|
||||
struct {
|
||||
byte rsvd[6];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT get_max_transfer_size;
|
||||
struct {
|
||||
uint32 offset;
|
||||
byte rsvd[2];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT read_file;
|
||||
struct {
|
||||
uint16 size;
|
||||
uint8 append_flag;
|
||||
byte rsvd[3];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT write_file;
|
||||
struct {
|
||||
byte rsvd[6];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT get_fname;
|
||||
struct {
|
||||
byte rsvd[6];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT set_fname;
|
||||
}cmd;
|
||||
}PACKED_STRUCT ftm_wlan_req_pkt_type;
|
||||
|
||||
/*FTM WLAM response type */
|
||||
typedef struct
|
||||
{
|
||||
struct {
|
||||
diagpkt_subsys_header_type header; /*diag header*/
|
||||
uint16 cmd_id; /* command id (required) */
|
||||
uint16 cmd_data_len;
|
||||
uint16 cmd_rsp_pkt_size;
|
||||
}PACKED_STRUCT common_header;
|
||||
union {
|
||||
struct {
|
||||
uint16 rsvd;
|
||||
uint32 result ;/* error_code */
|
||||
union {
|
||||
struct {
|
||||
byte data[0]; /*rxReport*/
|
||||
}rxReport;
|
||||
struct {
|
||||
byte data[0]; /*ThermValReport*/
|
||||
}thermval_report;
|
||||
}rx_and_therm;
|
||||
}PACKED_STRUCT common_ops;
|
||||
struct {
|
||||
uint16 result; /*error_code*/
|
||||
byte rsvd[4];
|
||||
uint16 max_size;
|
||||
}PACKED_STRUCT get_max_transfer_size;
|
||||
struct {
|
||||
byte result; /*error_code*/
|
||||
uint16 size;
|
||||
byte bytes_remaining[3];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT read_file;
|
||||
struct {
|
||||
byte result;
|
||||
byte rsvd[5];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT write_file;
|
||||
struct {
|
||||
byte result;
|
||||
byte rsvd[5];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT get_fname;
|
||||
struct {
|
||||
byte result;
|
||||
byte rsvd[5];
|
||||
byte data[0];
|
||||
}PACKED_STRUCT set_fname;
|
||||
struct {
|
||||
uint16 win_cmd_specific;
|
||||
uint16 data_len;
|
||||
uint8 rsvd;
|
||||
uint8 wlandeviceno;
|
||||
byte data[0];
|
||||
}PACKED_STRUCT win_resp;
|
||||
struct {
|
||||
uint16 result;
|
||||
uint32 serial;
|
||||
byte data[0];
|
||||
}PACKED_STRUCT ssp;
|
||||
}cmd;
|
||||
}PACKED_STRUCT ftm_wlan_rsp_pkt_type;
|
||||
|
||||
void* ftm_wlan_dispatch(ftm_wlan_req_pkt_type *wlan_ftm_pkt, int pkt_len);
|
||||
|
||||
#ifdef WIN_AP_HOST
|
||||
void setBoardDataCaptureFlag (int flag);
|
||||
void setDeviceId(int id);
|
||||
extern ftm_wlan_rsp_pkt_type *win_bt_mac_flash_write(
|
||||
ftm_wlan_req_pkt_type *wlan_ftm_pkt,
|
||||
int pkt_len);
|
||||
|
||||
extern void win_host_handle_fw_resp (ftm_wlan_rsp_pkt_type *rsp, void *data, uint32_t data_len);
|
||||
extern ftm_wlan_rsp_pkt_type *win_host_handle_bdf_req(
|
||||
ftm_wlan_req_pkt_type *wlan_ftm_pkt, int pkt_len);
|
||||
#endif
|
||||
|
||||
#endif /* CONFIG_FTM_WLAN */
|
||||
#endif /* FTM_WLAN_H_ */
|
||||
196
feeds/ipq95xx/ftm/src/ftm_wlan_win.h
Executable file
196
feeds/ipq95xx/ftm/src/ftm_wlan_win.h
Executable file
@@ -0,0 +1,196 @@
|
||||
/*
|
||||
*Copyright (c) 2017-2019 Qualcomm Technologies, Inc.
|
||||
*
|
||||
*All Rights Reserved.
|
||||
*Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
#ifndef __FTM_WLAN_WIN_H
|
||||
#define __FTM_WLAN_WIN_H
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include <sys/ioctl.h>
|
||||
#include <mtd/mtd-user.h>
|
||||
#include "comdef.h"
|
||||
#include "diagcmd.h"
|
||||
|
||||
#include "ftm_wlan.h"
|
||||
#include "ftm_dbg.h"
|
||||
|
||||
#define MAC_XTAL_LENGTH 7
|
||||
#define MAC_LENGTH_POS 103
|
||||
#define MAC_POS 105
|
||||
#define BT_TLV1_RESP_LEN 84
|
||||
#define BT_RESP_LEN 100
|
||||
#define FLASH_SECTOR_SIZE 0x10000
|
||||
#define BD_LEN_EXPECTED 500
|
||||
#define BD_SIZE_REQ_ID 106
|
||||
#define BD_SIZE_REQ_POS 28
|
||||
#define BD_SIZE_VAL 60
|
||||
|
||||
/* Identifier for first segment of
|
||||
* Board data response
|
||||
*/
|
||||
#define FIRST_SEG 48
|
||||
|
||||
/* Identifier for second segment of
|
||||
* board data response
|
||||
*/
|
||||
#define SECOND_SEG 49
|
||||
#define THIRD_SEG 50
|
||||
#define NO_ERROR 0
|
||||
|
||||
/* header length for first segment of
|
||||
* board data response
|
||||
*/
|
||||
#define FIRST_SEG_TLV_HDR 84
|
||||
#define SECOND_SEG_TLV_HDR 28
|
||||
#define THIRD_SEG_TLV_HDR 28
|
||||
|
||||
#define SEQUENCE_ID_POS 24
|
||||
|
||||
/* Position at which first parameter of
|
||||
* TLV request is located
|
||||
*/
|
||||
#define TLV_PAYLOAD_PARAM_1 80
|
||||
|
||||
/* Position at which second paramter of
|
||||
* TLV request is located
|
||||
*/
|
||||
#define TLV_PAYLOAD_PARAM_2 96
|
||||
|
||||
/* Parameter 1 value if request is for
|
||||
* board data capture
|
||||
*/
|
||||
#define BD_CAPTURE_REQ 101
|
||||
|
||||
/* Parameter 1 value if flash write request */
|
||||
#define FLASH_WRITE_REQ 102
|
||||
|
||||
/* Parameter 1 value for device identify request */
|
||||
#define DEVICE_IDENTIFY 103
|
||||
|
||||
|
||||
/* Parameter 2 value for swift device identify */
|
||||
#define QC9887_DEVICE_ID 0x50
|
||||
#define QC9888_DEVICE_ID 0x3c
|
||||
#define QC99xx_DEVICE_ID 0x46
|
||||
#define QCN9000_DEVICE_ID 0x1104
|
||||
|
||||
#define TLV1_CMD_RESP_SIZE 118
|
||||
#define TLV1_RESP_LEN 102
|
||||
|
||||
/* Offset at which BT_mac is to be stored in flash */
|
||||
#define BT_MAC_OFFSET 0x40
|
||||
|
||||
#define FLASH_BASE_CALDATA_OFFSET_SOC_0 0x1000
|
||||
#define FLASH_BASE_CALDATA_OFFSET_SOC_1 0x33000
|
||||
#define MAX_ART_SLOTS 3
|
||||
#define REQ_SEG_SIZE 4096
|
||||
|
||||
#define CALDATA_SEG_SIZE (150 * 1024)
|
||||
#define FLASH_BASE_CALDATA_OFFSET_PCI_1 (REQ_SEG_SIZE + CALDATA_SEG_SIZE)
|
||||
#define FLASH_BASE_CALDATA_OFFSET_PCI_2 (FLASH_BASE_CALDATA_OFFSET_PCI_1 + CALDATA_SEG_SIZE)
|
||||
|
||||
#define DIAG_HDR_LEN 16
|
||||
|
||||
#define FLASH_PARTITION "/dev/caldata"
|
||||
#define VIRTUAL_FLASH_PARTITION "/tmp/virtual_art.bin"
|
||||
#define WRITE_ART "/lib/compress_vart.sh write_caldata"
|
||||
|
||||
/* (0x33000-0x1000)=0x32000, Max available BDF size */
|
||||
#define MAX_BDF_SIZE 200*1024
|
||||
|
||||
#define QC98XX_BLOCK_SIZE 512
|
||||
|
||||
#define BD_BLOCK_SIZE 256
|
||||
|
||||
/* Position of block size for the data */
|
||||
#define QC98XX_BLOCK_SIZE_VAL 164
|
||||
|
||||
/* Position of block size for the data (radio != qc98XX) */
|
||||
#define LEGACY_BLOCK_SIZE_VAL 100
|
||||
|
||||
#define M_EEEPROM_BLOCK_READ_ID_QC98XX 0xC8
|
||||
|
||||
#define M_EEEPROM_BLOCK_READ_ID_LEGACY 0xE9
|
||||
|
||||
/* Position where block data starts */
|
||||
#define QC98XX_BLOCK_START_POS 200
|
||||
|
||||
#define LEGACY_BLOCK_START_POS 104
|
||||
|
||||
#define BD_READ_CMD_ID_POS 48
|
||||
|
||||
#define BD_READ_RESP_PARAM_POS 88
|
||||
|
||||
#define BD_READ_RESP_PARAM 0x7
|
||||
|
||||
/* Use of this parameter is not known */
|
||||
#define LEGACY_RADIO_PARAM_POS 103
|
||||
|
||||
#define LEGACY_RADIO_PARAM_THRESHOLD 0x30
|
||||
|
||||
/* Valid caldata in each segment from FW */
|
||||
#define CALDATA_SIZE_FIRST_SEG 1480
|
||||
#define CALDATA_SIZE_SECOND_SEG 1536
|
||||
#define CALDATA_SIZE_THIRD_SEG 1080
|
||||
|
||||
|
||||
uint16_t TLV2_Specific_byte;
|
||||
|
||||
unsigned char BDbuffer[MAX_BDF_SIZE];
|
||||
uint32_t BDbuffer_offset;
|
||||
uint32_t resp_counter;
|
||||
uint32_t bd_size;
|
||||
uint8_t start_capture;
|
||||
|
||||
/* Deviceno is the instance id sent from
|
||||
* Qdart for the radio.
|
||||
*/
|
||||
int deviceno;
|
||||
|
||||
/* Device id received in the radio's
|
||||
* radio flash write requests, defaults to 0
|
||||
*/
|
||||
int deviceid = 0;
|
||||
|
||||
/* This is the remainder after whole 4096 size responses are sent */
|
||||
uint32_t remaining_bytes ;
|
||||
uint32_t total_4K_responses;
|
||||
|
||||
unsigned char BTsetmacResponse[] = {
|
||||
0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x38, 0x00, 0x00, 0x00, 0x0F, 0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0xC6, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
|
||||
};
|
||||
|
||||
/* Response sent for BDcapture and Flash write Requests */
|
||||
unsigned char ftm_wlan_tlvRespMsg[] = {
|
||||
0x05, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x4A, 0x00, 0x00, 0x00,
|
||||
0x72, 0xD0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00,
|
||||
0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0xEA, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
|
||||
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||
0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x02, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00,
|
||||
0x07, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x20, 0x2F
|
||||
};
|
||||
|
||||
#endif /* __FTM_WLAN_WIN_H */
|
||||
|
||||
534
feeds/ipq95xx/ftm/src/ftm_write_to_flash.c
Executable file
534
feeds/ipq95xx/ftm/src/ftm_write_to_flash.c
Executable file
@@ -0,0 +1,534 @@
|
||||
/*
|
||||
*Copyright (c) 2017-2019 Qualcomm Technologies, Inc.
|
||||
*
|
||||
*All Rights Reserved.
|
||||
*Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
#include "ftm_dbg.h"
|
||||
#ifdef WIN_AP_HOST
|
||||
#include "ftm_wlan_win.h"
|
||||
#include <string.h>
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION bt_setmac_flash_write
|
||||
|
||||
DESCRIPTION
|
||||
Write MAC and XTAL to flash region
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns status success or failure
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
int bt_setmac_flash_write(uint8_t *mac, unsigned int len)
|
||||
{
|
||||
int fd;
|
||||
int offset;
|
||||
int i;
|
||||
uint8_t *flashdata;
|
||||
|
||||
fd = open(VIRTUAL_FLASH_PARTITION, O_RDWR);
|
||||
|
||||
if (fd < 0) {
|
||||
perror("Could not open flash. Returning without write\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE,"\nNumber of bytes = %d\n",len);
|
||||
|
||||
offset = BT_MAC_OFFSET;
|
||||
lseek(fd, offset, SEEK_SET);
|
||||
if (write(fd, mac, len) < 1) {
|
||||
DPRINTF(FTM_DBG_TRACE,"flash write error. Returning\n");
|
||||
close(fd);
|
||||
return -1;
|
||||
}
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE,
|
||||
"BT mac written successfully to flash @ offset %X size %X\n",
|
||||
offset, len);
|
||||
|
||||
flashdata = (uint8_t *)malloc(len);
|
||||
if (!flashdata){
|
||||
DPRINTF(FTM_DBG_TRACE, "Write verification failed. Unable to allocate memory.\n");
|
||||
close(fd);
|
||||
return -1;
|
||||
}
|
||||
|
||||
lseek(fd, offset, SEEK_SET);
|
||||
if (read(fd, flashdata, len) < 1){
|
||||
DPRINTF(FTM_DBG_TRACE, "Flashdata read failed\n");
|
||||
free(flashdata);
|
||||
return -1;
|
||||
}
|
||||
for(i = 0; i < len; i++){
|
||||
DPRINTF(FTM_DBG_TRACE, "input mac = 0x%x, flashdata = 0x%x\n", mac[i], flashdata[i]);
|
||||
}
|
||||
|
||||
free(flashdata);
|
||||
close(fd);
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION win_bt_mac_flash_write
|
||||
|
||||
DESCRIPTION
|
||||
Call bt_setmac_flash_write function and populate response to Qdart
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns resp to qdart
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
ftm_wlan_rsp_pkt_type *win_bt_mac_flash_write(ftm_wlan_req_pkt_type *wlan_ftm_pkt, int pkt_len)
|
||||
{
|
||||
int i;
|
||||
int status;
|
||||
ftm_wlan_rsp_pkt_type *rsp;
|
||||
unsigned char BtDiagMAC[MAC_XTAL_LENGTH];
|
||||
unsigned int dataLen = 0;
|
||||
uint8_t *input_msg = (uint8_t*)wlan_ftm_pkt;
|
||||
TLV2_Specific_byte = wlan_ftm_pkt->cmd.common_ops.rsvd;
|
||||
|
||||
dataLen = input_msg[MAC_LENGTH_POS];
|
||||
for(i=0; i<dataLen; i++)
|
||||
BtDiagMAC[i]= input_msg[MAC_POS + i];
|
||||
rsp = (ftm_wlan_rsp_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_WLAN_CMD_CODE,
|
||||
(sizeof(rsp->common_header) +
|
||||
sizeof(rsp->cmd.common_ops)+
|
||||
BT_TLV1_RESP_LEN ));
|
||||
if (!rsp)
|
||||
return rsp;
|
||||
|
||||
rsp->common_header.cmd_rsp_pkt_size = BT_RESP_LEN;
|
||||
rsp->common_header.cmd_data_len = 0;
|
||||
rsp->cmd.win_resp.data_len = BT_TLV1_RESP_LEN;
|
||||
rsp->cmd.win_resp.win_cmd_specific = TLV2_Specific_byte;
|
||||
|
||||
status = bt_setmac_flash_write(BtDiagMAC, dataLen);
|
||||
if (status > 0) {
|
||||
memcpy(rsp->cmd.win_resp.data, BTsetmacResponse, BT_TLV1_RESP_LEN);
|
||||
DPRINTF(FTM_DBG_TRACE,"Response sent to Qdart\n");
|
||||
/*print_uchar_array((uint8_t*)(rsp->cmd.win_resp.data), BT_TLV1_RESP_LEN);*/
|
||||
return rsp;
|
||||
}
|
||||
else
|
||||
return rsp;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION win_host_handle_bdf_req
|
||||
|
||||
DESCRIPTION
|
||||
Function to process WIN specific bdf requests.
|
||||
This handles the requests related to device identify,
|
||||
boarddata capture and flash write requests, and sends
|
||||
the response to QDART.
|
||||
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Returns back buffer that is meant for diag callback
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
ftm_wlan_rsp_pkt_type *win_host_handle_bdf_req(ftm_wlan_req_pkt_type *wlan_ftm_pkt, int pkt_len)
|
||||
{
|
||||
uint8_t *input_msg = (uint8_t*)wlan_ftm_pkt;
|
||||
int error = 0;
|
||||
int fd;
|
||||
int file_offset = 0;
|
||||
int art_slot_id;
|
||||
ftm_wlan_rsp_pkt_type *rsp;
|
||||
deviceno = wlan_ftm_pkt->cmd.common_ops.wlandeviceno;
|
||||
art_slot_id = wlan_ftm_pkt->cmd.common_ops.wlanslotno;
|
||||
TLV2_Specific_byte = wlan_ftm_pkt->cmd.common_ops.rsvd;
|
||||
rsp = (ftm_wlan_rsp_pkt_type*)diagpkt_subsys_alloc(DIAG_SUBSYS_FTM,
|
||||
FTM_WLAN_CMD_CODE,
|
||||
(sizeof(rsp->common_header) +
|
||||
sizeof(rsp->cmd.common_ops)+
|
||||
TLV1_RESP_LEN));
|
||||
|
||||
if (rsp == NULL) {
|
||||
DPRINTF(FTM_DBG_ERROR, "Failed to allocate Diag packet: %p\n", rsp);
|
||||
return rsp;
|
||||
}
|
||||
rsp->cmd.win_resp.win_cmd_specific = htole16(TLV2_Specific_byte);
|
||||
rsp->common_header.cmd_rsp_pkt_size = htole16(TLV1_CMD_RESP_SIZE);
|
||||
rsp->common_header.cmd_data_len = 0;
|
||||
rsp->cmd.win_resp.data_len = htole16(TLV1_RESP_LEN);
|
||||
rsp->cmd.win_resp.rsvd = 0;
|
||||
rsp->cmd.win_resp.wlandeviceno = deviceno;
|
||||
|
||||
DPRINTF(FTM_DBG_TRACE, "Received FTM daemon specific TLV\n");
|
||||
|
||||
/* Byte 80 in request signifies type of request, 101 is used for BD capture*/
|
||||
if(input_msg[TLV_PAYLOAD_PARAM_1] == BD_CAPTURE_REQ) {
|
||||
DPRINTF(FTM_DBG_TRACE, "BOARD_DATA_CAPTURE\n");
|
||||
if (input_msg[TLV_PAYLOAD_PARAM_2] == 1) {
|
||||
setBoardDataCaptureFlag(1);
|
||||
} else if (input_msg[TLV_PAYLOAD_PARAM_2] == 0) {
|
||||
setBoardDataCaptureFlag(0);
|
||||
}
|
||||
|
||||
} else if (input_msg[TLV_PAYLOAD_PARAM_1] == FLASH_WRITE_REQ) {
|
||||
fd = open(VIRTUAL_FLASH_PARTITION, O_RDWR);
|
||||
if (fd < 0) {
|
||||
DPRINTF(FTM_DBG_TRACE, "FILE OPEN FAILED\n");
|
||||
error = WLAN_BDF_FILE_OPEN_FAIL;
|
||||
} else {
|
||||
DPRINTF(FTM_DBG_TRACE, "FILE OPEN SUCCESSFULL\n");
|
||||
if (access("/tmp/ftm.conf", F_OK) == 0) {
|
||||
if (art_slot_id == 0) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_0;
|
||||
} else if (art_slot_id == 1) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_0 + (ftm_cfg.slot_size[0] * 1024);
|
||||
} else if (art_slot_id == 2) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_0 +
|
||||
((ftm_cfg.slot_size[0] + ftm_cfg.slot_size[1]) * 1024);
|
||||
} else if (art_slot_id == 3) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_0 +
|
||||
((ftm_cfg.slot_size[0] + ftm_cfg.slot_size[1] +
|
||||
ftm_cfg.slot_size[2]) * 1024);
|
||||
}
|
||||
} else if (!deviceid) {
|
||||
if (art_slot_id > MAX_ART_SLOTS) {
|
||||
close(fd);
|
||||
return rsp;
|
||||
}
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_0 +
|
||||
(art_slot_id * CALDATA_SEG_SIZE);
|
||||
|
||||
} else if (deviceid == QC9887_DEVICE_ID ||
|
||||
deviceid == QC9888_DEVICE_ID) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_1;
|
||||
} else if (deviceid == QC99xx_DEVICE_ID) {
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_SOC_1;
|
||||
} else if (deviceid == QCN9000_DEVICE_ID) {
|
||||
if (art_slot_id == 1)
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_PCI_1;
|
||||
else if (art_slot_id == 2)
|
||||
file_offset = FLASH_BASE_CALDATA_OFFSET_PCI_2;
|
||||
else {
|
||||
close(fd);
|
||||
return rsp;
|
||||
}
|
||||
} else {
|
||||
DPRINTF(FTM_DBG_TRACE, "%s:%d - Invalid Device ID %d\n",
|
||||
__func__, __LINE__, deviceid);
|
||||
close(fd);
|
||||
return rsp;
|
||||
}
|
||||
lseek(fd, file_offset, SEEK_SET);
|
||||
if (write(fd, BDbuffer , BDbuffer_offset) < 1) {
|
||||
DPRINTF(FTM_DBG_TRACE, "%s:%d - Flash write error\n",
|
||||
__func__, __LINE__);
|
||||
error = WLAN_BDF_WRITE_FAILED;
|
||||
close(fd);
|
||||
} else {
|
||||
fsync(fd);
|
||||
close(fd);
|
||||
system(WRITE_ART);
|
||||
|
||||
DPRINTF(FTM_DBG_INFO,
|
||||
"Flash commit success @ offset %0x Size %d\n",
|
||||
file_offset, BDbuffer_offset);
|
||||
}
|
||||
}
|
||||
|
||||
} else if (input_msg[TLV_PAYLOAD_PARAM_1] == DEVICE_IDENTIFY) {
|
||||
DPRINTF(FTM_DBG_TRACE, "Device Identify \n");
|
||||
setDeviceId(input_msg[TLV_PAYLOAD_PARAM_2]);
|
||||
}
|
||||
if (error!=NO_ERROR)
|
||||
/* These commands will not go to firmware */
|
||||
return rsp;
|
||||
else {
|
||||
memcpy(rsp->cmd.win_resp.data, ftm_wlan_tlvRespMsg, TLV1_RESP_LEN);
|
||||
return rsp;
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION setBordDataCaptureFlag
|
||||
|
||||
DESCRIPTION
|
||||
Sets the BDCapture variable
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
NONE
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
|
||||
===========================================================================*/
|
||||
void setBoardDataCaptureFlag (int flag)
|
||||
{
|
||||
DPRINTF(FTM_DBG_TRACE, "Setting BDCapture flag to %d\n", flag);
|
||||
if (flag == 1) {
|
||||
BDbuffer_offset = 0;
|
||||
resp_counter = 0;
|
||||
start_capture = 1;
|
||||
}
|
||||
|
||||
// when board data capture is turned off, set the device id to 0
|
||||
if (flag == 0){
|
||||
start_capture = 0;
|
||||
setDeviceId(0);
|
||||
}
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION setDeviceId
|
||||
|
||||
DESCRIPTION
|
||||
Sets the global variable device id, upon requests
|
||||
according to the parameter 2 of the TLV command
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
NONE
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
============================================================================*/
|
||||
void setDeviceId(int id)
|
||||
{
|
||||
DPRINTF(FTM_DBG_TRACE, "Setting Device id to %d\n", id);
|
||||
deviceid = id;
|
||||
}
|
||||
|
||||
#define BD_SIZE_SIGNATURE_POS 32
|
||||
#define BD_SIZE_SIGNATURE 1147011573
|
||||
|
||||
uint8_t ftm_check_bdf_sizereq_signature(uint8_t *data)
|
||||
{
|
||||
uint8_t ret = 0;
|
||||
uint32_t signature = 0;
|
||||
|
||||
le_to_cpu32(((uint8_t *)data + BD_SIZE_SIGNATURE_POS), signature);
|
||||
if (signature == BD_SIZE_SIGNATURE)
|
||||
ret = 1;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION win_host_handle_fw_resp
|
||||
|
||||
DESCRIPTION
|
||||
WIN specific handler for responses from FW.
|
||||
FW responses for board data are snooped here
|
||||
and stored in a global buffer which is then
|
||||
accessed by the WIN request handler for flash
|
||||
write requests.
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
0 on success
|
||||
1 on failure
|
||||
|
||||
SIDE EFFECTS
|
||||
NONE
|
||||
===========================================================================*/
|
||||
|
||||
void win_host_handle_fw_resp (ftm_wlan_rsp_pkt_type *rsp, void *data, uint32_t data_len)
|
||||
{
|
||||
uint32_t sequence_id;
|
||||
int legacy_dataSize;
|
||||
if (!rsp || !data || !data_len) {
|
||||
DPRINTF(FTM_DBG_ERROR, "rsp/data is NULL\n");
|
||||
rsp = NULL;
|
||||
return;
|
||||
}
|
||||
rsp->cmd.win_resp.win_cmd_specific = htole16(TLV2_Specific_byte);
|
||||
rsp->common_header.cmd_rsp_pkt_size = htole16(data_len + DIAG_HDR_LEN);
|
||||
rsp->cmd.win_resp.data_len = htole16(data_len);
|
||||
rsp->cmd.win_resp.wlandeviceno = deviceno;
|
||||
rsp->cmd.win_resp.rsvd = 0;
|
||||
memcpy(rsp->cmd.win_resp.data, data, data_len);
|
||||
|
||||
/*TODO: Need better identification method for BDF responses*/
|
||||
/* Check if the deviceid is set */
|
||||
|
||||
switch (deviceid) {
|
||||
|
||||
/* DeviceId is 0 for HK and lithium family targets */
|
||||
case 0:
|
||||
{ /* Check if request is for BD_get size. */
|
||||
if (((uint8_t *)data)[BD_SIZE_REQ_POS] == BD_SIZE_REQ_ID &&
|
||||
ftm_check_bdf_sizereq_signature(data)) {
|
||||
bd_size = 0 ;
|
||||
BDbuffer_offset = 0;
|
||||
resp_counter = 0;
|
||||
le_to_cpu32(((uint8_t *)data + BD_SIZE_VAL), bd_size);
|
||||
DPRINTF(FTM_DBG_INFO, "bd_size = %d \n", bd_size);
|
||||
total_4K_responses = bd_size / REQ_SEG_SIZE;
|
||||
remaining_bytes = bd_size % REQ_SEG_SIZE;
|
||||
DPRINTF(FTM_DBG_INFO, "Total_responses= %d \n",
|
||||
total_4K_responses);
|
||||
DPRINTF(FTM_DBG_INFO, "Remaining_bytes = %d \n",
|
||||
remaining_bytes);
|
||||
}
|
||||
|
||||
if (data_len > BD_LEN_EXPECTED && start_capture == 1) {
|
||||
sequence_id = ((uint8_t *)data)[SEQUENCE_ID_POS];
|
||||
DPRINTF(FTM_DBG_INFO, "Sequence_ID= %d\n", sequence_id);
|
||||
|
||||
if (sequence_id == FIRST_SEG)
|
||||
resp_counter ++;
|
||||
DPRINTF(FTM_DBG_INFO, "Response counter == %d\n",
|
||||
resp_counter);
|
||||
DPRINTF(FTM_DBG_INFO, "Buffer offset == %d\n",
|
||||
BDbuffer_offset);
|
||||
|
||||
if (resp_counter < total_4K_responses + 1) {
|
||||
/* Handle 3 segments of BDF resonses
|
||||
* 1st segment - BDF is from offset 84
|
||||
* 2nd segment - BDF is from offset 28
|
||||
* 3rd segment - BDF is from offset 28
|
||||
*/
|
||||
switch (sequence_id) {
|
||||
|
||||
case FIRST_SEG:
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
(void *)((uint8_t*)data + FIRST_SEG_TLV_HDR),
|
||||
data_len - FIRST_SEG_TLV_HDR);
|
||||
BDbuffer_offset += (data_len - FIRST_SEG_TLV_HDR);
|
||||
break;
|
||||
|
||||
case SECOND_SEG:
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
(void *)((uint8_t *)data + SECOND_SEG_TLV_HDR),
|
||||
data_len - SECOND_SEG_TLV_HDR);
|
||||
BDbuffer_offset += (data_len - SECOND_SEG_TLV_HDR);
|
||||
break;
|
||||
|
||||
case THIRD_SEG:
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
(void *)((uint8_t*)data + THIRD_SEG_TLV_HDR),
|
||||
data_len - THIRD_SEG_TLV_HDR);
|
||||
BDbuffer_offset += (data_len - THIRD_SEG_TLV_HDR);
|
||||
break;
|
||||
|
||||
default:
|
||||
/* error */
|
||||
break;
|
||||
|
||||
}
|
||||
/* In case of total bdf data size not being a multiple
|
||||
* of 4k, extra remaining bdf data is handled based on
|
||||
* which segment of 4k it belongs to.
|
||||
*/
|
||||
} else {
|
||||
switch (sequence_id) {
|
||||
case FIRST_SEG:
|
||||
if (remaining_bytes < CALDATA_SIZE_FIRST_SEG) {
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
data + FIRST_SEG_TLV_HDR,
|
||||
remaining_bytes);
|
||||
BDbuffer_offset += remaining_bytes;
|
||||
} else {
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
data + FIRST_SEG_TLV_HDR,
|
||||
data_len - FIRST_SEG_TLV_HDR);
|
||||
BDbuffer_offset += (data_len - FIRST_SEG_TLV_HDR);
|
||||
remaining_bytes -= CALDATA_SIZE_FIRST_SEG;
|
||||
}
|
||||
break;
|
||||
|
||||
case SECOND_SEG:
|
||||
if (remaining_bytes < CALDATA_SIZE_SECOND_SEG) {
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
data + SECOND_SEG_TLV_HDR,
|
||||
remaining_bytes);
|
||||
BDbuffer_offset += remaining_bytes;
|
||||
} else {
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
data + SECOND_SEG_TLV_HDR,
|
||||
data_len - SECOND_SEG_TLV_HDR);
|
||||
BDbuffer_offset += (data_len - SECOND_SEG_TLV_HDR);
|
||||
remaining_bytes -= CALDATA_SIZE_SECOND_SEG;
|
||||
}
|
||||
break;
|
||||
|
||||
case THIRD_SEG:
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
(void *)((uint8_t*)data + THIRD_SEG_TLV_HDR),
|
||||
remaining_bytes);
|
||||
BDbuffer_offset += remaining_bytes;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case QC9887_DEVICE_ID:
|
||||
case QC9888_DEVICE_ID:
|
||||
{
|
||||
if ((((uint8_t *)data)[BD_READ_CMD_ID_POS] == M_EEEPROM_BLOCK_READ_ID_QC98XX) &&
|
||||
(((uint8_t *)data)[BD_READ_RESP_PARAM_POS] == BD_READ_RESP_PARAM)){
|
||||
le_to_cpu32(((uint8_t *)data + QC98XX_BLOCK_SIZE_VAL),
|
||||
legacy_dataSize);
|
||||
DPRINTF(FTM_DBG_TRACE,
|
||||
"Capturing Caldata for QC98xx by FTM :: Size %d\n",
|
||||
legacy_dataSize);
|
||||
DPRINTF(FTM_DBG_TRACE,
|
||||
"BDbuffer Offset : %d \n",
|
||||
(resp_counter * QC98XX_BLOCK_SIZE));
|
||||
memcpy(BDbuffer + BDbuffer_offset, (void *)((uint8_t *)data +
|
||||
QC98XX_BLOCK_START_POS),
|
||||
legacy_dataSize);
|
||||
resp_counter = resp_counter + 1;
|
||||
BDbuffer_offset += legacy_dataSize;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case QC99xx_DEVICE_ID:
|
||||
{
|
||||
if ((((uint8_t *)data)[BD_READ_CMD_ID_POS] == M_EEEPROM_BLOCK_READ_ID_LEGACY) &&
|
||||
(((uint8_t *)data)[BD_READ_RESP_PARAM_POS] == BD_READ_RESP_PARAM) &&
|
||||
((uint8_t *)data)[LEGACY_RADIO_PARAM_POS] < LEGACY_RADIO_PARAM_THRESHOLD) {
|
||||
le_to_cpu16(((uint8_t *)data + LEGACY_BLOCK_SIZE_VAL), legacy_dataSize);
|
||||
DPRINTF(FTM_DBG_TRACE,
|
||||
"Capturing Caldata by FTM :: Size %d\n",
|
||||
legacy_dataSize);
|
||||
DPRINTF(FTM_DBG_TRACE,
|
||||
"BDbuffer Offset : %d \n",
|
||||
(resp_counter * BD_BLOCK_SIZE));
|
||||
memcpy(BDbuffer + BDbuffer_offset,
|
||||
(void *)((uint8_t *)data + LEGACY_BLOCK_START_POS),
|
||||
legacy_dataSize);
|
||||
resp_counter = resp_counter + 1;
|
||||
BDbuffer_offset+=legacy_dataSize;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
159
feeds/ipq95xx/ftm/src/testcmd.h
Executable file
159
feeds/ipq95xx/ftm/src/testcmd.h
Executable file
@@ -0,0 +1,159 @@
|
||||
/*==========================================================================
|
||||
|
||||
TCMD header File
|
||||
|
||||
# Copyright (c) 2011, 2013-2014 by Qualcomm Technologies, Inc.
|
||||
# All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (c) 2006 Atheros Communications Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
*
|
||||
// The software source and binaries included in this development package are
|
||||
// licensed, not sold. You, or your company, received the package under one
|
||||
// or more license agreements. The rights granted to you are specifically
|
||||
// listed in these license agreement(s). All other rights remain with Atheros
|
||||
// Communications, Inc., its subsidiaries, or the respective owner including
|
||||
// those listed on the included copyright notices. Distribution of any
|
||||
// portion of this package must be in strict compliance with the license
|
||||
// agreement(s) terms.
|
||||
// </copyright>
|
||||
//
|
||||
//
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef TESTCMD_H_
|
||||
#define TESTCMD_H_
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef AR6002_REV2
|
||||
#define TCMD_MAX_RATES 12
|
||||
#else
|
||||
#define TCMD_MAX_RATES 28
|
||||
#endif
|
||||
|
||||
#define PREPACK
|
||||
#define POSTPACK __attribute__ ((packed))
|
||||
|
||||
#define ATH_MAC_LEN 6
|
||||
#define TC_CMDS_SIZE_MAX 256
|
||||
|
||||
/* Continuous Rx
|
||||
act: TCMD_CONT_RX_PROMIS - promiscuous mode (accept all incoming frames)
|
||||
TCMD_CONT_RX_FILTER - filter mode (accept only frames with dest
|
||||
address equal specified
|
||||
mac address (set via act =3)
|
||||
TCMD_CONT_RX_REPORT off mode (disable cont rx mode and get the
|
||||
report from the last cont
|
||||
Rx test)
|
||||
|
||||
TCMD_CONT_RX_SETMAC - set MacAddr mode (sets the MAC address for the
|
||||
target. This Overrides
|
||||
the default MAC address.)
|
||||
|
||||
*/
|
||||
typedef enum {
|
||||
TCMD_CONT_RX_PROMIS = 0,
|
||||
TCMD_CONT_RX_FILTER,
|
||||
TCMD_CONT_RX_REPORT,
|
||||
TCMD_CONT_RX_SETMAC,
|
||||
TCMD_CONT_RX_SET_ANT_SWITCH_TABLE,
|
||||
TC_CMD_RESP,
|
||||
TCMD_CONT_RX_GETMAC,
|
||||
} TCMD_CONT_RX_ACT;
|
||||
|
||||
typedef PREPACK struct {
|
||||
uint32_t testCmdId;
|
||||
uint32_t act;
|
||||
uint32_t enANI;
|
||||
PREPACK union {
|
||||
struct PREPACK TCMD_CONT_RX_PARA {
|
||||
uint32_t freq;
|
||||
uint32_t antenna;
|
||||
uint32_t wlanMode;
|
||||
} POSTPACK para;
|
||||
struct PREPACK TCMD_CONT_RX_REPORT {
|
||||
uint32_t totalPkt;
|
||||
int32_t rssiInDBm;
|
||||
uint32_t crcErrPkt;
|
||||
uint32_t secErrPkt;
|
||||
uint16_t rateCnt[TCMD_MAX_RATES];
|
||||
uint16_t rateCntShortGuard[TCMD_MAX_RATES];
|
||||
} POSTPACK report;
|
||||
struct PREPACK TCMD_CONT_RX_MAC {
|
||||
char addr[ATH_MAC_LEN];
|
||||
char btaddr[ATH_MAC_LEN];
|
||||
uint16_t regDmn[2];
|
||||
uint32_t otpWriteFlag;
|
||||
} POSTPACK mac;
|
||||
struct PREPACK TCMD_CONT_RX_ANT_SWITCH_TABLE {
|
||||
uint32_t antswitch1;
|
||||
uint32_t antswitch2;
|
||||
} POSTPACK antswitchtable;
|
||||
} POSTPACK u;
|
||||
} POSTPACK TCMD_CONT_RX;
|
||||
|
||||
typedef enum {
|
||||
TC_CMDS_TS =0,
|
||||
TC_CMDS_CAL,
|
||||
TC_CMDS_TPCCAL = TC_CMDS_CAL,
|
||||
TC_CMDS_TPCCAL_WITH_OTPWRITE,
|
||||
TC_CMDS_OTPDUMP,
|
||||
TC_CMDS_OTPSTREAMWRITE,
|
||||
TC_CMDS_EFUSEDUMP,
|
||||
TC_CMDS_EFUSEWRITE,
|
||||
TC_CMDS_READTHERMAL,
|
||||
} TC_CMDS_ACT;
|
||||
|
||||
typedef PREPACK struct {
|
||||
uint32_t testCmdId;
|
||||
uint32_t act;
|
||||
PREPACK union {
|
||||
uint32_t enANI; // to be identical to CONT_RX struct
|
||||
struct PREPACK {
|
||||
uint16_t length;
|
||||
uint8_t version;
|
||||
uint8_t bufLen;
|
||||
} POSTPACK parm;
|
||||
} POSTPACK u;
|
||||
} POSTPACK TC_CMDS_HDR;
|
||||
|
||||
typedef PREPACK struct {
|
||||
TC_CMDS_HDR hdr;
|
||||
char buf[TC_CMDS_SIZE_MAX];
|
||||
} POSTPACK TC_CMDS;
|
||||
|
||||
typedef enum {
|
||||
TCMD_CONT_TX_ID,
|
||||
TCMD_CONT_RX_ID,
|
||||
TCMD_PM_ID,
|
||||
TC_CMDS_ID,
|
||||
TCMD_SET_REG_ID,
|
||||
TC_CMD_TLV_ID,
|
||||
OP_GENERIC_NART_CMD = 8,
|
||||
|
||||
/*For synergy purpose we added the following tcmd id but these
|
||||
tcmd's will not go to the firmware instead we will write values
|
||||
to the NV area */
|
||||
|
||||
TCMD_NIC_MAC = 100,
|
||||
TCMD_CAL_FILE_INDEX = 101,
|
||||
TCMD_LOAD_DRIVER = 102,
|
||||
TCMD_SET_MAC_ADDR = 198,
|
||||
} TCMD_ID;
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* TESTCMD_H_ */
|
||||
45
feeds/ipq95xx/ftm/src/wds/Android.mk
Executable file
45
feeds/ipq95xx/ftm/src/wds/Android.mk
Executable file
@@ -0,0 +1,45 @@
|
||||
ifeq ($(call is-vendor-board-platform,QCOM),true)
|
||||
ifeq ($(findstring true, $(BOARD_HAVE_QCOM_FM) $(BOARD_HAVE_BLUETOOTH)),true)
|
||||
|
||||
LOCAL_PATH := $(call my-dir)
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
BDROID_DIR:= system/bt
|
||||
ifeq ($(TARGET_SUPPORTS_WEARABLES),true)
|
||||
QTI_DIR := hardware/qcom/bt/msm8909/libbt-vendor
|
||||
else
|
||||
QTI_DIR := hardware/qcom/bt/libbt-vendor
|
||||
endif
|
||||
|
||||
LOCAL_C_INCLUDES := $(TARGET_OUT_HEADERS)/common/inc
|
||||
LOCAL_C_INCLUDES += $(BDROID_DIR)/hci/include
|
||||
LOCAL_C_INCLUDES += $(QTI_DIR)/include
|
||||
ifeq ($(TARGET_SUPPORTS_WEARABLES),true)
|
||||
LOCAL_C_INCLUDES += device/qcom/msm8909w/opensource/bluetooth/tools/hidl_client/inc
|
||||
else
|
||||
LOCAL_C_INCLUDES += vendor/qcom/opensource/bluetooth/tools/hidl_client/inc
|
||||
endif
|
||||
|
||||
LOCAL_CFLAGS := -DANDROID
|
||||
|
||||
ifneq ($(BOARD_ANT_WIRELESS_DEVICE), )
|
||||
LOCAL_CFLAGS += -DCONFIG_ANT
|
||||
endif
|
||||
LOCAL_SRC_FILES := wds_main.c
|
||||
LOCAL_SRC_FILES += wds_hci_pfal_linux.c
|
||||
|
||||
LOCAL_MODULE_PATH := $(TARGET_OUT_VENDOR_EXECUTABLES)
|
||||
LOCAL_MODULE := wdsdaemon
|
||||
ifeq ($(PRODUCT_VENDOR_MOVE_ENABLED),true)
|
||||
LOCAL_PROPRIETARY_MODULE := true
|
||||
endif
|
||||
LOCAL_MODULE_TAGS := optional
|
||||
LOCAL_SHARED_LIBRARIES := libdiag
|
||||
LOCAL_SHARED_LIBRARIES += libcutils \
|
||||
libdl \
|
||||
libbt-hidlclient
|
||||
|
||||
include $(BUILD_EXECUTABLE)
|
||||
endif # filter
|
||||
endif # is-vendor-board-platform
|
||||
170
feeds/ipq95xx/ftm/src/wds/wds_hci_pfal.h
Executable file
170
feeds/ipq95xx/ftm/src/wds/wds_hci_pfal.h
Executable file
@@ -0,0 +1,170 @@
|
||||
/*
|
||||
* Copyright (c) 2016 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Copyright (c) 2012 by Qualcomm Atheros, Inc..
|
||||
* All Rights Reserved.
|
||||
* Qualcomm Atheros Confidential and Proprietary.
|
||||
*/
|
||||
|
||||
#ifndef DEBUG
|
||||
#define DEBUG printf
|
||||
#endif
|
||||
|
||||
#ifndef ERROR
|
||||
#define ERROR printf
|
||||
#endif
|
||||
|
||||
#include "bt_vendor_qcom.h"
|
||||
|
||||
/* error codes */
|
||||
enum {
|
||||
STATUS_SUCCESS,
|
||||
STATUS_ERROR,
|
||||
STATUS_INVALID_LENGTH,
|
||||
STATUS_NO_MEMORY,
|
||||
STATUS_NULL_POINTER,
|
||||
STATUS_CLIENT_ERROR,
|
||||
};
|
||||
|
||||
enum {
|
||||
RX_ERROR = -1,
|
||||
RX_BT_EVT_IND = 1,
|
||||
RX_BT_HDR,
|
||||
RX_BT_DATA,
|
||||
RX_ANT_HDR,
|
||||
RX_ANT_DATA,
|
||||
RX_FM_EVT_IND,
|
||||
RX_FM_HDR,
|
||||
RX_FM_DATA,
|
||||
RX_PKT_IND
|
||||
};
|
||||
|
||||
enum pkt_type {
|
||||
BT_PKT_TYPE = 1,
|
||||
FM_PKT_TYPE,
|
||||
ANT_PKT_TYPE
|
||||
};
|
||||
/* device to communicate between PC and DUT */
|
||||
#define BT_HS_NMEA_DEVICE "/dev/ttyGS0"
|
||||
#define BT_HSLITE_UART_DEVICE "/dev/ttyHSL0"
|
||||
|
||||
/* interface between PC-DUT */
|
||||
typedef struct pc_uart_interafce {
|
||||
unsigned char *intf;
|
||||
int uart_fd;
|
||||
} pc_uart_interface;
|
||||
|
||||
typedef union pc_interface {
|
||||
pc_uart_interface uart;
|
||||
} pc_interface;
|
||||
|
||||
/* device to communicate between DUT and BTSOC */
|
||||
#define APPS_RIVA_FM_CMD_CH "/dev/smd1"
|
||||
#define APPS_RIVA_BT_ACL_CH "/dev/smd2"
|
||||
#define APPS_RIVA_BT_CMD_CH "/dev/smd3"
|
||||
#define APPS_RIVA_ANT_CMD "/dev/smd5"
|
||||
#define APPS_RIVA_ANT_DATA "/dev/smd6"
|
||||
#define BT_HS_UART_DEVICE "/dev/ttyHS0"
|
||||
|
||||
/* SMD interface between DUT-SOC */
|
||||
typedef struct soc_smd_interface {
|
||||
unsigned char *fm_cmd;
|
||||
unsigned char *bt_acl;
|
||||
unsigned char *bt_cmd;
|
||||
unsigned char *ant_cmd;
|
||||
unsigned char *ant_data;
|
||||
int fm_cmd_fd;
|
||||
int bt_acl_fd;
|
||||
int bt_cmd_fd;
|
||||
int ant_cmd_fd;
|
||||
int ant_data_fd;
|
||||
} soc_smd_interface;
|
||||
|
||||
/* UART interface between DUT-SOC */
|
||||
typedef struct soc_uart_interface {
|
||||
unsigned char *intf;
|
||||
int uart_fd;
|
||||
} soc_uart_interface;
|
||||
|
||||
typedef union soc_interface {
|
||||
soc_smd_interface smd;
|
||||
soc_uart_interface uart;
|
||||
} soc_interface;
|
||||
|
||||
/* context for wdsdaemon */
|
||||
typedef struct wdsdaemon {
|
||||
int mode;
|
||||
int soc_type;
|
||||
bool pcinit_mask;
|
||||
pc_interface pc_if;
|
||||
soc_interface soc_if;
|
||||
bool is_server_enabled;
|
||||
int server_socket_fd;
|
||||
pthread_t soc_rthread;
|
||||
} wdsdaemon;
|
||||
|
||||
/* packet types */
|
||||
#define PACKET_TYPE_INVALID (0)
|
||||
#define PACKET_TYPE_BT_CMD (1)
|
||||
#define PACKET_TYPE_FM_CMD (2)
|
||||
#define PACKET_TYPE_BT_ACL (3)
|
||||
#define PACKET_TYPE_ANT_CMD (4)
|
||||
#define PACKET_TYPE_ANT_DATA (5)
|
||||
|
||||
/* operation modes for wdsdaemon */
|
||||
#define MODE_BT_SMD (0)
|
||||
#define MODE_FM_SMD (1)
|
||||
#define MODE_ANT_SMD (2)
|
||||
#define MODE_ALL_SMD (3)
|
||||
#define MODE_BT_UART (4)
|
||||
#define MODE_ANT_UART (5)
|
||||
#define MODE_FM_UART (6)
|
||||
|
||||
/* Bluetooth Header */
|
||||
#define BT_CMD_PKT_HDR_LEN (2)
|
||||
#define BT_EVT_PKT_HDR_LEN (2)
|
||||
#define BT_FM_PKT_UART_HDR_LEN (4)
|
||||
#define BT_ACL_PKT_HDR_LEN (4)
|
||||
#define BT_ACL_PKT_UART_HDR_LEN (5)
|
||||
|
||||
/* FM Header */
|
||||
#define FM_CMD_PKT_HDR_LEN (3) //Opcode(2byte) + Param len(1 byte)
|
||||
#define FM_EVT_PKT_HDR_LEN (2) //Opcode(1 byte) + Param len(1 byte)
|
||||
|
||||
/* ANT Header */
|
||||
#define ANT_CMD_PKT_HDR_LEN (1)
|
||||
#define ANT_DATA_PKT_HDR_LEN (1)
|
||||
#define ANT_CMD_DATA_PKT_UART_HDR_LEN (2)
|
||||
|
||||
#define BT_EVT_PKT_HDR_LEN_UART (BT_CMD_PKT_HDR_LEN+1)
|
||||
#define BT_ACL_PKT_HDR_LEN_UART (BT_ACL_PKT_HDR_LEN+1)
|
||||
|
||||
/* ANT data packet type */
|
||||
#define ANT_DATA_TYPE_BROADCAST (0x4E)
|
||||
#define ANT_DATA_TYPE_ACKNOWLEDGED (0x4F)
|
||||
#define ANT_DATA_TYPE_BURST (0x50)
|
||||
#define ANT_DATA_TYPE_ADV_BURST (0x72)
|
||||
|
||||
/*Packet Identifiers */
|
||||
#define BT_CMD_PKT_ID 0x01
|
||||
#define FM_CMD_PKT_ID 0x11
|
||||
#define BT_EVT_PKT_ID 0x04
|
||||
#define FM_EVT_PKT_ID 0x14
|
||||
#define ANT_CMD_PKT_ID 0x0C
|
||||
#define ANT_EVT_PKT_ID 0x0C
|
||||
#define ANT_DATA_PKT_ID 0x0E
|
||||
#define BT_ACL_DATA_PKT_ID 0x02
|
||||
|
||||
#define SMD_BUF_SIZE (9000)
|
||||
#define UART_BUF_SIZE (9000)
|
||||
|
||||
#define PC_TO_SOC (1)
|
||||
#define SOC_TO_PC (2)
|
||||
|
||||
int get_acl_pkt_length(unsigned char, unsigned char);
|
||||
unsigned short get_pkt_data_len(unsigned char type, unsigned char *buf);
|
||||
int init_pc_interface(wdsdaemon *wds);
|
||||
int init_soc_interface(wdsdaemon *wds);
|
||||
int establish_server_socket(wdsdaemon *wds);
|
||||
720
feeds/ipq95xx/ftm/src/wds/wds_hci_pfal_linux.c
Executable file
720
feeds/ipq95xx/ftm/src/wds/wds_hci_pfal_linux.c
Executable file
@@ -0,0 +1,720 @@
|
||||
/*
|
||||
* Copyright (c) 2016 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Copyright (c) 2012 by Qualcomm Atheros, Inc..
|
||||
* All Rights Reserved.
|
||||
* Qualcomm Atheros Confidential and Proprietary.
|
||||
*/
|
||||
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/socket.h>
|
||||
#include <cutils/sockets.h>
|
||||
#include <sys/un.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/select.h>
|
||||
#include <termios.h>
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
#include "wds_hci_pfal.h"
|
||||
#include <math.h>
|
||||
#include <dlfcn.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include "hidl_client.h"
|
||||
|
||||
#ifdef ANDROID
|
||||
#include "bt_vendor_lib.h"
|
||||
#else
|
||||
#ifdef BT_SOC_TYPE_ROME
|
||||
#include "bt_vendor_lib.h"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define SOCKET_NAME "wdssock"
|
||||
|
||||
typedef unsigned char uint8;
|
||||
extern int process_packet_type(wdsdaemon *wds, unsigned char pkt_id,
|
||||
int *dst_fd, int *len, int dir);
|
||||
|
||||
#ifdef ANDROID
|
||||
extern int soc_type;
|
||||
#endif
|
||||
|
||||
static int find_max(int *arr, int len)
|
||||
{
|
||||
int max = arr[0];
|
||||
int i;
|
||||
|
||||
for (i = 1; i < len; i++) {
|
||||
if (arr[i] > max)
|
||||
max = arr[i];
|
||||
}
|
||||
|
||||
return max;
|
||||
}
|
||||
|
||||
unsigned short get_pkt_data_len(unsigned char type,
|
||||
unsigned char *buf)
|
||||
{
|
||||
unsigned short len = 0;
|
||||
switch (type) {
|
||||
case BT_EVT_PKT_ID:
|
||||
/* Event packet: 1 byte length */
|
||||
len = buf[BT_EVT_PKT_HDR_LEN_UART - 1];
|
||||
break;
|
||||
case BT_ACL_DATA_PKT_ID:
|
||||
/* ACL packet: 2 byte length */
|
||||
len =
|
||||
(((unsigned short) buf[BT_ACL_PKT_HDR_LEN_UART - 1] << 8) &
|
||||
0xFF00) | (((unsigned short) buf[BT_ACL_PKT_HDR_LEN_UART - 2])
|
||||
& 0x00FF);
|
||||
break;
|
||||
case BT_CMD_PKT_ID:
|
||||
len = buf[BT_EVT_PKT_HDR_LEN_UART];
|
||||
break;
|
||||
case FM_CMD_PKT_ID:
|
||||
/* FM Cmd packet param len: 1 byte length */
|
||||
len = buf[FM_CMD_PKT_HDR_LEN];
|
||||
break;
|
||||
case FM_EVT_PKT_ID:
|
||||
/* FM Evt packet param len: 1 byte length */
|
||||
len = buf[FM_EVT_PKT_HDR_LEN];
|
||||
break;
|
||||
}
|
||||
return len;
|
||||
}
|
||||
|
||||
static int process_soc_data_to_pc(wdsdaemon *wds, unsigned char *buf_in,
|
||||
int src_fd)
|
||||
{
|
||||
int retval = STATUS_SUCCESS;
|
||||
ssize_t n_bytes = 0, n_total = 0;
|
||||
int len = 1, dst_fd = 0, i;
|
||||
int state = RX_PKT_IND, offset = 0;
|
||||
unsigned char pkt_ind_to_read = 1;
|
||||
|
||||
|
||||
/* In case of Pronto, we have different channels for CMD and ACL,
|
||||
* so we don't get packet indicator from SoC.
|
||||
* Below condition will skip reading packet indicator byte in
|
||||
* case of Pronto.
|
||||
*/
|
||||
if (wds->mode != MODE_BT_UART && wds->mode != MODE_ANT_UART &&
|
||||
wds->mode != MODE_FM_UART) {
|
||||
pkt_ind_to_read = 0;
|
||||
offset++;
|
||||
}
|
||||
|
||||
do {
|
||||
while (len) {
|
||||
if (pkt_ind_to_read == 0)
|
||||
goto dont_read_pkt_ind;
|
||||
|
||||
if ((n_bytes = read(src_fd,
|
||||
(unsigned char *)(&buf_in[offset + n_total]),
|
||||
len)) > 0) {
|
||||
n_total += n_bytes;
|
||||
len -= n_bytes;
|
||||
if (len)
|
||||
continue;
|
||||
dont_read_pkt_ind:
|
||||
switch(state) {
|
||||
case RX_PKT_IND:
|
||||
pkt_ind_to_read = 1;
|
||||
state = process_packet_type(wds, buf_in[0], &dst_fd, &len,
|
||||
SOC_TO_PC);
|
||||
break;
|
||||
case RX_BT_HDR:
|
||||
len = get_pkt_data_len(buf_in[0], buf_in);
|
||||
state = RX_BT_DATA;
|
||||
break;
|
||||
case RX_BT_DATA:
|
||||
len = 0;
|
||||
break;
|
||||
case RX_ANT_HDR:
|
||||
pkt_ind_to_read = 1;
|
||||
len = buf_in[n_total];
|
||||
state = RX_ANT_DATA;
|
||||
break;
|
||||
case RX_ANT_DATA:
|
||||
if (buf_in[2] ==
|
||||
ANT_DATA_TYPE_BROADCAST ||
|
||||
buf_in[2] ==
|
||||
ANT_DATA_TYPE_ACKNOWLEDGED ||
|
||||
buf_in[2] == ANT_DATA_TYPE_BURST ||
|
||||
buf_in[2] == ANT_DATA_TYPE_ADV_BURST)
|
||||
buf_in[0] = ANT_DATA_PKT_ID;
|
||||
else
|
||||
buf_in[0] = ANT_EVT_PKT_ID;
|
||||
|
||||
retval = STATUS_SUCCESS;
|
||||
break;
|
||||
case RX_FM_HDR:
|
||||
len = get_pkt_data_len(buf_in[0], buf_in);
|
||||
state = RX_FM_DATA;
|
||||
break;
|
||||
case RX_FM_DATA:
|
||||
len = 0;
|
||||
break;
|
||||
default:
|
||||
retval = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
ERROR("%s Failed To read from SoC fd = %d\n",__func__, src_fd);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (retval)
|
||||
break;
|
||||
n_total += offset;
|
||||
len = 0;
|
||||
|
||||
DEBUG("evt:\t");
|
||||
for (i = 0; i < n_total; i++)
|
||||
DEBUG("0x%x\t", buf_in[i]);
|
||||
DEBUG("\n");
|
||||
while (n_total) {
|
||||
if((n_bytes = write(dst_fd, buf_in + len, n_total)) >= 0) {
|
||||
len += n_bytes;
|
||||
n_total -= n_bytes;
|
||||
}
|
||||
else {
|
||||
if (wds->is_server_enabled) {
|
||||
retval = STATUS_CLIENT_ERROR;
|
||||
ERROR("%s: unable to write to client socket, fd = %d err = %s\n", __func__, dst_fd, strerror(errno));
|
||||
}
|
||||
else {
|
||||
retval = STATUS_ERROR;
|
||||
ERROR("%s: unable to write to pc_if fd = %d err = %s\n", __func__, dst_fd, strerror(errno));
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
} while (0);
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
static void *process_soc_data(void *arg)
|
||||
{
|
||||
int retval = STATUS_ERROR;
|
||||
fd_set readfds, saved_readfds;
|
||||
wdsdaemon *wds = (wdsdaemon *) arg;
|
||||
int max, src_fd = 0, dst_fd = 0;
|
||||
size_t sz = 0;
|
||||
unsigned char *buf_in = NULL;
|
||||
int arr[5], num = 0;
|
||||
|
||||
FD_ZERO(&readfds);
|
||||
FD_ZERO(&saved_readfds);
|
||||
|
||||
if (wds->mode == MODE_BT_UART || wds->mode == MODE_ANT_UART ||
|
||||
wds->mode == MODE_FM_UART) {
|
||||
FD_SET(wds->soc_if.uart.uart_fd, &saved_readfds);
|
||||
max = wds->soc_if.uart.uart_fd;
|
||||
sz = UART_BUF_SIZE * sizeof(unsigned char);
|
||||
} else {
|
||||
if (wds->mode == MODE_BT_SMD || wds->mode == MODE_ALL_SMD) {
|
||||
FD_SET((arr[num] = wds->soc_if.smd.bt_acl_fd), &saved_readfds);num++;
|
||||
FD_SET((arr[num] = wds->soc_if.smd.bt_cmd_fd), &saved_readfds);num++;
|
||||
}
|
||||
if (wds->mode == MODE_ANT_SMD || wds->mode == MODE_ALL_SMD) {
|
||||
FD_SET((arr[num] = wds->soc_if.smd.ant_cmd_fd), &saved_readfds);num++;
|
||||
FD_SET((arr[num] = wds->soc_if.smd.ant_data_fd), &saved_readfds);num++;
|
||||
}
|
||||
|
||||
if (wds->mode == MODE_FM_SMD || wds->mode == MODE_ALL_SMD)
|
||||
FD_SET((arr[num] = wds->soc_if.smd.fm_cmd_fd), &saved_readfds);num++;
|
||||
|
||||
max = find_max(arr, num);
|
||||
|
||||
sz = SMD_BUF_SIZE * sizeof(unsigned char);
|
||||
}
|
||||
|
||||
buf_in = (unsigned char *) calloc(sz, 1);
|
||||
if (!buf_in) {
|
||||
ERROR("Insufficient Memory");
|
||||
retval = STATUS_NO_MEMORY;
|
||||
goto failed;
|
||||
}
|
||||
|
||||
do {
|
||||
readfds = saved_readfds;
|
||||
retval = select(max + 1, &readfds, NULL, NULL, NULL);
|
||||
if (retval == -1) {
|
||||
ERROR("select failed, Error: %s (%d)\n", strerror(errno),
|
||||
errno);
|
||||
break;
|
||||
}
|
||||
|
||||
switch (wds->mode) {
|
||||
case MODE_BT_UART:
|
||||
case MODE_FM_UART:
|
||||
case MODE_ANT_UART:
|
||||
src_fd = wds->soc_if.uart.uart_fd;
|
||||
if (FD_ISSET(src_fd,&readfds))
|
||||
retval = process_soc_data_to_pc(wds, buf_in, src_fd);
|
||||
break;
|
||||
case MODE_ALL_SMD:
|
||||
case MODE_BT_SMD:
|
||||
src_fd = wds->soc_if.smd.bt_cmd_fd;
|
||||
if (FD_ISSET(src_fd ,&readfds)) {
|
||||
buf_in[0] = BT_EVT_PKT_ID;
|
||||
retval = process_soc_data_to_pc(wds, buf_in,src_fd);
|
||||
}
|
||||
src_fd = wds->soc_if.smd.bt_acl_fd;
|
||||
if (FD_ISSET(src_fd ,&readfds)) {
|
||||
buf_in[0] = BT_ACL_DATA_PKT_ID;
|
||||
retval = process_soc_data_to_pc(wds, buf_in, src_fd);
|
||||
}
|
||||
if (wds->mode == MODE_BT_SMD)
|
||||
break;
|
||||
case MODE_FM_SMD:
|
||||
src_fd = wds->soc_if.smd.fm_cmd_fd;
|
||||
if (FD_ISSET(src_fd ,&readfds)) {
|
||||
buf_in[0] = FM_EVT_PKT_ID;
|
||||
retval = process_soc_data_to_pc(wds, buf_in, src_fd);
|
||||
}
|
||||
if (wds->mode == MODE_FM_SMD)
|
||||
break;
|
||||
break;
|
||||
case MODE_ANT_SMD:
|
||||
src_fd = wds->soc_if.smd.ant_cmd_fd;
|
||||
if (FD_ISSET(src_fd, &readfds)) {
|
||||
buf_in[0] = ANT_EVT_PKT_ID;
|
||||
retval = process_soc_data_to_pc(wds, buf_in, src_fd);
|
||||
}
|
||||
src_fd = wds->soc_if.smd.ant_data_fd;
|
||||
if (FD_ISSET(src_fd ,&readfds)) {
|
||||
buf_in[0] = ANT_DATA_PKT_ID;
|
||||
retval = process_soc_data_to_pc(wds, buf_in, src_fd);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (STATUS_SUCCESS != retval) {
|
||||
if (retval == STATUS_CLIENT_ERROR) {
|
||||
ERROR("Write to client failed\n");
|
||||
continue;
|
||||
}
|
||||
ERROR("Failed to process SOC data\n");
|
||||
break;
|
||||
}
|
||||
} while(1);
|
||||
|
||||
failed:
|
||||
ERROR("\nReader thread exited\n");
|
||||
if (buf_in) {
|
||||
free(buf_in);
|
||||
buf_in = NULL;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int set_port_raw_mode(int fd)
|
||||
{
|
||||
struct termios term;
|
||||
int ret = STATUS_SUCCESS;
|
||||
|
||||
if (tcgetattr(fd, &term) < 0) {
|
||||
ERROR("Failed to get attributes");
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
cfmakeraw(&term);
|
||||
if (tcsetattr(fd, TCSANOW, &term) < 0) {
|
||||
ERROR("Failed to set attributes");
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
if (tcflush(fd, TCIFLUSH) < 0) {
|
||||
ERROR("Failed to flush port");
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
return STATUS_ERROR;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION port_init_libbt
|
||||
|
||||
DESCRIPTION
|
||||
Initilize port and open the file through libbt-vendor
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
RETURN fd handle
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
#ifndef BT_BLUEZ
|
||||
static int port_init_libbt(uint8 option)
|
||||
{
|
||||
int fd_array[CH_MAX];
|
||||
bt_vendor_callbacks_t cb;
|
||||
uint8_t init_bd_addr[6] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 };
|
||||
bt_vendor_interface_t * p_btf = NULL;
|
||||
bt_vendor_opcode_t opCmd1, opCmd2;
|
||||
int iState;
|
||||
|
||||
void* vendor_handle = dlopen("libbt-vendor.so", RTLD_NOW);
|
||||
if(!vendor_handle){
|
||||
ERROR("Error open libbt-vendor \n");
|
||||
return -1;
|
||||
}
|
||||
p_btf = (bt_vendor_interface_t *)dlsym(vendor_handle,
|
||||
"BLUETOOTH_VENDOR_LIB_INTERFACE");
|
||||
if(!p_btf){
|
||||
ERROR("Failed obtain the address of libbt-vendor \n");
|
||||
return -1;
|
||||
}
|
||||
if (p_btf->init(&cb, &init_bd_addr[0]) < 0){
|
||||
ERROR("bt vendor init failed \n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
switch (option) {
|
||||
case MODE_BT_UART:
|
||||
opCmd1 = BT_VND_OP_POWER_CTRL;
|
||||
opCmd2 = BT_VND_OP_USERIAL_OPEN;
|
||||
break;
|
||||
case MODE_FM_UART:
|
||||
opCmd1 = FM_VND_OP_POWER_CTRL;
|
||||
opCmd2 = BT_VND_OP_FM_USERIAL_OPEN;
|
||||
break;
|
||||
case MODE_ANT_UART:
|
||||
opCmd1 = BT_VND_OP_POWER_CTRL;
|
||||
opCmd2 = BT_VND_OP_USERIAL_OPEN;
|
||||
break;
|
||||
default:
|
||||
printf("Invalid option\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
iState = BT_VND_PWR_ON;
|
||||
|
||||
if (p_btf->op(opCmd1, &iState) < 0){
|
||||
ERROR("Power on failed \n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (p_btf->op(opCmd2, (void*)fd_array) < 0){
|
||||
ERROR("op(VND_OP_USERIAL_OPEN) failed \n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return fd_array[0];
|
||||
}
|
||||
#endif
|
||||
|
||||
static int change_baud(int fd, speed_t baud)
|
||||
{
|
||||
struct termios term;
|
||||
int ret = STATUS_SUCCESS; /* assume success */
|
||||
|
||||
do {
|
||||
if (tcgetattr(fd, &term) < 0) {
|
||||
ERROR("Failed to get attributes");
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
cfsetospeed(&term, baud);
|
||||
/* don't change speed until last write done */
|
||||
if (tcsetattr(fd, TCSADRAIN, &term) < 0) {
|
||||
ERROR("Failed to set attribute");
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
} while(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int init_soc_interface(wdsdaemon *wds)
|
||||
{
|
||||
int ret = STATUS_ERROR;
|
||||
int fd = 0;
|
||||
struct termios term;
|
||||
|
||||
if (!wds) {
|
||||
ret = STATUS_NULL_POINTER;
|
||||
ERROR("Invalid input argument\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
switch (wds->mode) {
|
||||
case MODE_FM_UART:
|
||||
if(hidl_client_initialize(MODE_FM,&fd) == false)
|
||||
{
|
||||
ERROR("HIDL client initialization failed");
|
||||
exit(1);
|
||||
}
|
||||
wds->soc_if.uart.uart_fd = fd;
|
||||
ret = STATUS_SUCCESS;
|
||||
break;
|
||||
case MODE_BT_UART:
|
||||
#ifdef BT_BLUEZ
|
||||
fd = open(wds->soc_if.uart.intf,
|
||||
O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
break;
|
||||
}
|
||||
if (tcflush(fd, TCIOFLUSH) < 0) {
|
||||
ERROR("Failed to flush port: %s\n",
|
||||
wds->soc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
close(fd);
|
||||
break;
|
||||
}
|
||||
if (tcgetattr(fd, &term) < 0) {
|
||||
ERROR("Failed to get attributes for port: %s\n",
|
||||
wds->soc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
close(fd);
|
||||
break;
|
||||
}
|
||||
cfmakeraw(&term);
|
||||
/* enable flow control */
|
||||
term.c_cflag |= (CRTSCTS | CLOCAL);
|
||||
if (tcsetattr(fd, TCSANOW, &term) < 0) {
|
||||
ERROR("Failed to set attributes for port: %s\n",
|
||||
wds->soc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
close(fd);
|
||||
break;
|
||||
}
|
||||
if (STATUS_SUCCESS != change_baud(fd, B3000000)) { //TODO:set baud rate
|
||||
ERROR("Failed to change baud rate\n");
|
||||
close(fd);
|
||||
break;
|
||||
}
|
||||
#else
|
||||
if(hidl_client_initialize(MODE_BT,&fd) == false)
|
||||
{
|
||||
ERROR("HIDL client initialization failed");
|
||||
exit(1);
|
||||
}
|
||||
#endif
|
||||
/* everything okay */
|
||||
wds->soc_if.uart.uart_fd = fd;
|
||||
ret = STATUS_SUCCESS;
|
||||
break;
|
||||
case MODE_ANT_UART:
|
||||
#ifndef BT_BLUEZ
|
||||
if(hidl_client_initialize(MODE_ANT,&fd) == true){
|
||||
wds->soc_if.uart.uart_fd = fd;
|
||||
}
|
||||
else {
|
||||
ERROR("HIDL client initialization failed, opening port with port_init_libbt\n");
|
||||
wds->soc_if.uart.uart_fd = port_init_libbt(wds->mode);
|
||||
}
|
||||
ret = STATUS_SUCCESS;
|
||||
#endif
|
||||
break;
|
||||
case MODE_ALL_SMD:
|
||||
case MODE_ANT_SMD:
|
||||
/* ANT commdnas */
|
||||
fd = open(wds->soc_if.smd.ant_cmd,
|
||||
O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.smd.ant_cmd);
|
||||
ERROR("Error: %s (%d)\n", strerror(errno),
|
||||
errno);
|
||||
break;
|
||||
}
|
||||
set_port_raw_mode(fd);
|
||||
wds->soc_if.smd.ant_cmd_fd = fd;
|
||||
/* ANT data */
|
||||
fd = open(wds->soc_if.smd.ant_data,
|
||||
O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.smd.ant_data);
|
||||
ERROR("Error: %s (%d)", strerror(errno),
|
||||
errno);
|
||||
break;
|
||||
}
|
||||
set_port_raw_mode(fd);
|
||||
wds->soc_if.smd.ant_data_fd = fd;
|
||||
if (wds->mode == MODE_ANT_SMD) {
|
||||
ret = STATUS_SUCCESS;
|
||||
break;
|
||||
}
|
||||
/* fallthrough intentional for MODE_ALL_SMD */
|
||||
case MODE_BT_SMD:
|
||||
/* BT commdnas */
|
||||
fd = open(wds->soc_if.smd.bt_cmd,
|
||||
O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.smd.bt_cmd_fd);
|
||||
ERROR("Error: %s (%d)\n",
|
||||
strerror(errno), errno);
|
||||
break;
|
||||
}
|
||||
set_port_raw_mode(fd);
|
||||
wds->soc_if.smd.bt_cmd_fd = fd;
|
||||
/* BT ACL */
|
||||
fd = open(wds->soc_if.smd.bt_acl,
|
||||
O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.smd.bt_acl);
|
||||
ERROR("Error: %s (%d)\n",
|
||||
strerror(errno), errno);
|
||||
break;
|
||||
}
|
||||
set_port_raw_mode(fd);
|
||||
wds->soc_if.smd.bt_acl_fd = fd;
|
||||
if (wds->mode == MODE_BT_SMD) {
|
||||
ret = STATUS_SUCCESS;
|
||||
break;
|
||||
}
|
||||
/* fallthrough intentional for MODE_ALL_SMD */
|
||||
case MODE_FM_SMD:
|
||||
/* FM commdnas */
|
||||
fd = open(wds->soc_if.smd.fm_cmd, O_RDWR | O_NONBLOCK | O_NOCTTY);
|
||||
if (-1 == fd) {
|
||||
ERROR("Failed to open port: %s\n",
|
||||
wds->soc_if.smd.fm_cmd_fd);
|
||||
ERROR("Error: %s (%d)\n",
|
||||
strerror(errno), errno);
|
||||
break;
|
||||
}
|
||||
set_port_raw_mode(fd);
|
||||
wds->soc_if.smd.fm_cmd_fd = fd;
|
||||
ret = STATUS_SUCCESS;
|
||||
break;
|
||||
}
|
||||
|
||||
if (ret == STATUS_SUCCESS)
|
||||
if (pthread_create(&wds->soc_rthread, NULL, process_soc_data,
|
||||
wds) != 0) {
|
||||
ERROR("%s:Unable to create pthread err = %s\n", __func__,
|
||||
strerror(errno));
|
||||
close(fd);
|
||||
ret = STATUS_ERROR;
|
||||
}
|
||||
|
||||
failed:
|
||||
return ret;
|
||||
}
|
||||
|
||||
int init_pc_interface(wdsdaemon *wds)
|
||||
{
|
||||
int fd = 0;
|
||||
int ret = STATUS_ERROR;
|
||||
struct termios term;
|
||||
|
||||
if (!wds) {
|
||||
ret = STATUS_NULL_POINTER;
|
||||
ERROR("Invalid input argument");
|
||||
return ret;
|
||||
}
|
||||
|
||||
do {
|
||||
fd = open(wds->pc_if.uart.intf, O_RDWR);
|
||||
if (-1 == fd) {
|
||||
ERROR("Unable to open port: %s", wds->pc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
/* set terminal properties */
|
||||
if (tcgetattr(fd, &term) < 0) {
|
||||
ERROR("Failed to get attributes of port: %s",
|
||||
wds->pc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
close(fd);
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
cfmakeraw(&term);
|
||||
term.c_lflag = term.c_lflag & ((tcflag_t)(~ECHO));
|
||||
/* TODO: Make baud rate command line argument */
|
||||
cfsetospeed(&term, B115200);
|
||||
cfsetispeed(&term, B115200);
|
||||
if (tcsetattr(fd, TCSANOW, &term) < 0) {
|
||||
ERROR("Failed to set attributes of port: %s",
|
||||
wds->pc_if.uart.intf);
|
||||
ERROR("Error: %s (%d)", strerror(errno), errno);
|
||||
close(fd);
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
tcflush(fd, TCIOFLUSH);
|
||||
|
||||
/* everything okay, set success */
|
||||
wds->pc_if.uart.uart_fd = fd;
|
||||
ret = STATUS_SUCCESS;
|
||||
} while(0);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
int establish_server_socket(wdsdaemon *wds)
|
||||
{
|
||||
int fd = -1;
|
||||
struct sockaddr_un client_address;
|
||||
socklen_t clen;
|
||||
int sock_id, ret = STATUS_ERROR;
|
||||
DEBUG("%s(%s) Entry \n", __func__, SOCKET_NAME);
|
||||
|
||||
if (!wds) {
|
||||
ret = STATUS_NULL_POINTER;
|
||||
ERROR("Invalid input argument\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
sock_id = socket(AF_LOCAL, SOCK_STREAM, 0);
|
||||
if (sock_id < 0) {
|
||||
ERROR("%s: server Socket creation failure\n", __func__);
|
||||
return ret;
|
||||
}
|
||||
|
||||
DEBUG("convert name to android abstract name:%s %d\n", SOCKET_NAME, sock_id);
|
||||
if (socket_local_server_bind(sock_id,
|
||||
SOCKET_NAME, ANDROID_SOCKET_NAMESPACE_ABSTRACT) >= 0) {
|
||||
if (listen(sock_id, 5) == 0) {
|
||||
DEBUG("listen to local socket:%s, fd:%d\n", SOCKET_NAME, sock_id);
|
||||
} else {
|
||||
ERROR("listen to local socket:failed\n");
|
||||
close(sock_id);
|
||||
return ret;
|
||||
}
|
||||
} else {
|
||||
close(sock_id);
|
||||
ERROR("%s: server bind failed for socket : %s\n", __func__, SOCKET_NAME);
|
||||
return ret;
|
||||
}
|
||||
|
||||
clen = sizeof(client_address);
|
||||
DEBUG("%s: before accept_server_socket\n", SOCKET_NAME);
|
||||
fd = accept(sock_id, (struct sockaddr *)&client_address, &clen);
|
||||
if (fd > 0) {
|
||||
DEBUG("%s accepted fd:%d for server fd:%d\n", SOCKET_NAME, fd, sock_id);
|
||||
close(sock_id);
|
||||
wds->server_socket_fd = fd;
|
||||
return STATUS_SUCCESS;
|
||||
} else {
|
||||
ERROR("Accept failed fd:%d sock d:%d error %s\n", fd, sock_id, strerror(errno));
|
||||
close(sock_id);
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
568
feeds/ipq95xx/ftm/src/wds/wds_main.c
Executable file
568
feeds/ipq95xx/ftm/src/wds/wds_main.c
Executable file
@@ -0,0 +1,568 @@
|
||||
/*
|
||||
* Copyright (c) 2016 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* Copyright (c) 2012 by Qualcomm Atheros, Inc..
|
||||
* All Rights Reserved.
|
||||
* Qualcomm Atheros Confidential and Proprietary.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Description:
|
||||
* Added wdsdaemon to enable testing of Host Controller Interface (HCI)
|
||||
* communication with stack layers bypassed.
|
||||
* 1. Acts as a communication bridge between PC to DUT over UART (/dev/ttyHSL0)
|
||||
* and also UART transport between DUT and BTSOC (/dev/ttyHS0).
|
||||
* 2. Used to test exchange of BT-FM HCI commands, events and ACL data packets
|
||||
* between host and controller.
|
||||
**/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <pthread.h>
|
||||
#include <stdbool.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/socket.h>
|
||||
#include <cutils/sockets.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/time.h>
|
||||
#include <stdlib.h>
|
||||
#include <sys/time.h>
|
||||
#include <getopt.h>
|
||||
#include <strings.h>
|
||||
#include <termios.h>
|
||||
#include <math.h>
|
||||
#include <string.h>
|
||||
#include <signal.h>
|
||||
#include "wds_hci_pfal.h"
|
||||
#include "hidl_client.h"
|
||||
|
||||
#ifdef ANDROID
|
||||
#include <cutils/properties.h>
|
||||
#endif
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION get_pkt_type
|
||||
|
||||
DESCRIPTION
|
||||
Routine to get the packet type from the data bytes received
|
||||
|
||||
DEPENDENCIES
|
||||
NIL
|
||||
|
||||
RETURN VALUE
|
||||
Packet type for the data bytes received
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
static int get_packet_type(unsigned char id)
|
||||
{
|
||||
int type;
|
||||
|
||||
switch (id) {
|
||||
case BT_CMD_PKT_ID:
|
||||
type = PACKET_TYPE_BT_CMD;
|
||||
break;
|
||||
case FM_CMD_PKT_ID:
|
||||
type = PACKET_TYPE_FM_CMD;
|
||||
break;
|
||||
case BT_ACL_DATA_PKT_ID:
|
||||
type = PACKET_TYPE_BT_ACL;
|
||||
break;
|
||||
case ANT_CMD_PKT_ID:
|
||||
type = PACKET_TYPE_ANT_CMD;
|
||||
break;
|
||||
case ANT_DATA_PKT_ID:
|
||||
type = PACKET_TYPE_ANT_DATA;
|
||||
break;
|
||||
default:
|
||||
type = PACKET_TYPE_INVALID;
|
||||
}
|
||||
|
||||
return type;
|
||||
}
|
||||
|
||||
#ifdef ANDROID
|
||||
|
||||
int soc_type;
|
||||
|
||||
/** Get Bluetooth SoC type from system setting */
|
||||
static int get_bt_soc_type()
|
||||
{
|
||||
int ret = 0;
|
||||
char bt_soc_type[PROPERTY_VALUE_MAX];
|
||||
|
||||
DEBUG("bt-hci: get_bt_soc_type\n");
|
||||
|
||||
ret = property_get("qcom.bluetooth.soc", bt_soc_type, NULL);
|
||||
if (ret != 0) {
|
||||
DEBUG("qcom.bluetooth.soc set to %s\n", bt_soc_type);
|
||||
if (!strncasecmp(bt_soc_type, "rome", sizeof("rome"))) {
|
||||
return BT_SOC_ROME;
|
||||
}
|
||||
else if (!strncasecmp(bt_soc_type, "cherokee", sizeof("cherokee"))) {
|
||||
return BT_SOC_CHEROKEE;
|
||||
}
|
||||
else if (!strncasecmp(bt_soc_type, "ath3k", sizeof("ath3k"))) {
|
||||
return BT_SOC_AR3K;
|
||||
}
|
||||
else if (!strncasecmp(bt_soc_type, "napier", sizeof("napier"))) {
|
||||
return BT_SOC_NAPIER;
|
||||
}
|
||||
else {
|
||||
DEBUG("qcom.bluetooth.soc not set, so using default.\n");
|
||||
return BT_SOC_DEFAULT;
|
||||
}
|
||||
}
|
||||
else {
|
||||
DEBUG("%s: Failed to get soc type\n", __FUNCTION__);
|
||||
ret = BT_SOC_DEFAULT;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int parse_options(wdsdaemon *wds, int argc, char *argv[])
|
||||
{
|
||||
int ret = STATUS_SUCCESS;
|
||||
int opt;
|
||||
|
||||
if (argc > 2) {
|
||||
ERROR("Invalid number of arguments\n");
|
||||
ret = STATUS_INVALID_LENGTH;
|
||||
ERROR("Usage %s [-abfunht]", argv[0]);
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (argc == 1) {
|
||||
wds->mode = MODE_ALL_SMD;
|
||||
return ret;
|
||||
}
|
||||
|
||||
while ((opt = getopt(argc, argv, "abfunhstm")) != -1) {
|
||||
switch (opt) {
|
||||
case 'a':
|
||||
DEBUG("Opening ANT SMD channels\n");
|
||||
wds->mode = MODE_ANT_SMD;
|
||||
break;
|
||||
case 'b':
|
||||
DEBUG("Opening BT SMD channels\n");
|
||||
wds->mode = MODE_BT_SMD;
|
||||
break;
|
||||
case 'f':
|
||||
DEBUG("Opening FM SMD channels\n");
|
||||
wds->mode = MODE_FM_SMD;
|
||||
break;
|
||||
case 't':
|
||||
ERROR("Setting mask for pc initialization\n");
|
||||
wds->pcinit_mask = true;
|
||||
break;
|
||||
case 's':
|
||||
ERROR("Opening WDS server socket\n");
|
||||
wds->is_server_enabled = true;
|
||||
wds->pcinit_mask = true;
|
||||
break;
|
||||
#ifdef ANDROID
|
||||
if (soc_type == BT_SOC_ROME || soc_type == BT_SOC_CHEROKEE) {
|
||||
case 'u':
|
||||
DEBUG("Opening UART BT Channel\n");
|
||||
wds->mode = MODE_BT_UART;
|
||||
break;
|
||||
}
|
||||
if (soc_type == BT_SOC_CHEROKEE) {
|
||||
case 'm':
|
||||
DEBUG("Opening UART FM Channel\n");
|
||||
wds->mode = MODE_FM_UART;
|
||||
break;
|
||||
}
|
||||
#else
|
||||
#ifdef BT_SOC_TYPE_ROME
|
||||
case 'u':
|
||||
DEBUG("Opening UART BT Channel\n");
|
||||
wds->mode = MODE_BT_UART;
|
||||
break;
|
||||
#endif
|
||||
#endif
|
||||
#ifdef CONFIG_ANT
|
||||
case 'n':
|
||||
ERROR("Opening ANT UART channels\n");
|
||||
wds->mode = MODE_ANT_UART;
|
||||
break;
|
||||
#endif
|
||||
case 'h':
|
||||
DEBUG("By Default, it will open all SMD channels\n");
|
||||
DEBUG("Use -a for opening only ANT Channels\n");
|
||||
DEBUG("Use -b for opening only BT Channels\n");
|
||||
DEBUG("Use -f for opening only FM Channels\n");
|
||||
|
||||
#ifdef ANDROID
|
||||
if (soc_type == BT_SOC_ROME || soc_type == BT_SOC_CHEROKEE) {
|
||||
DEBUG("Use -u for opening only UART Channel for BT (ROME)\n");
|
||||
}
|
||||
if (soc_type == BT_SOC_CHEROKEE) {
|
||||
DEBUG("Use -m for opening only UART Channel for FM\n");
|
||||
}
|
||||
#else
|
||||
#ifdef BT_SOC_TYPE_ROME
|
||||
DEBUG("Use -u for opening only UART Channel for BT (ROME)\n");
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_ANT
|
||||
DEBUG("Use -n for opening ANT UART channels only\n");
|
||||
#endif
|
||||
DEBUG("Use -t for masking pc initialization\n");
|
||||
DEBUG("Use -s for setting communication via server socket\n");
|
||||
DEBUG("Use -h to print help\n");
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
default:
|
||||
DEBUG("Usage %s [-abfunhmst]\n", argv[0]);
|
||||
ret = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void wdsdaemon_init(wdsdaemon *wds)
|
||||
{
|
||||
/* PC-DUT interface */
|
||||
#ifdef BT_BLUEZ
|
||||
wds->pc_if.uart.intf = (unsigned char *)BT_HSLITE_UART_DEVICE;
|
||||
#else
|
||||
wds->pc_if.uart.intf = (unsigned char *)BT_HS_NMEA_DEVICE;
|
||||
#endif
|
||||
|
||||
/* DUT-BTSOC interface */
|
||||
switch (wds->mode) {
|
||||
case MODE_ALL_SMD:
|
||||
wds->soc_if.smd.fm_cmd = (unsigned char *)APPS_RIVA_FM_CMD_CH;
|
||||
wds->soc_if.smd.bt_acl = (unsigned char*)APPS_RIVA_BT_ACL_CH;
|
||||
wds->soc_if.smd.bt_cmd = (unsigned char *)APPS_RIVA_BT_CMD_CH;
|
||||
wds->soc_if.smd.ant_cmd = (unsigned char *)APPS_RIVA_ANT_CMD;
|
||||
wds->soc_if.smd.ant_data = (unsigned char *)APPS_RIVA_ANT_DATA;
|
||||
break;
|
||||
case MODE_ANT_SMD:
|
||||
wds->soc_if.smd.ant_cmd = (unsigned char *)APPS_RIVA_ANT_CMD;
|
||||
wds->soc_if.smd.ant_data = (unsigned char *)APPS_RIVA_ANT_DATA;
|
||||
break;
|
||||
case MODE_BT_SMD:
|
||||
wds->soc_if.smd.bt_acl = (unsigned char *)APPS_RIVA_BT_ACL_CH;
|
||||
wds->soc_if.smd.bt_cmd = (unsigned char *)APPS_RIVA_BT_CMD_CH;
|
||||
break;
|
||||
case MODE_FM_SMD:
|
||||
wds->soc_if.smd.fm_cmd = (unsigned char *)APPS_RIVA_FM_CMD_CH;
|
||||
break;
|
||||
case MODE_BT_UART:
|
||||
case MODE_ANT_UART:
|
||||
wds->soc_if.uart.intf = (unsigned char *)BT_HS_UART_DEVICE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
int process_packet_type(wdsdaemon *wds, unsigned char pkt_id,
|
||||
int *dst_fd, int *len, int dir)
|
||||
{
|
||||
int state;
|
||||
|
||||
switch(pkt_id) {
|
||||
case BT_CMD_PKT_ID:
|
||||
*len = BT_EVT_PKT_HDR_LEN_UART;
|
||||
case BT_EVT_PKT_ID:
|
||||
case BT_ACL_DATA_PKT_ID:
|
||||
state = RX_BT_HDR;
|
||||
if (wds->mode == MODE_BT_UART)
|
||||
*dst_fd = wds->soc_if.uart.uart_fd;
|
||||
else
|
||||
if (pkt_id == BT_CMD_PKT_ID)
|
||||
*dst_fd = wds->soc_if.smd.bt_cmd_fd;
|
||||
else
|
||||
*dst_fd = wds->soc_if.smd.bt_acl_fd;
|
||||
if (pkt_id == BT_ACL_DATA_PKT_ID)
|
||||
*len = BT_ACL_PKT_HDR_LEN;
|
||||
else if (pkt_id == BT_EVT_PKT_ID)
|
||||
*len = BT_EVT_PKT_HDR_LEN;
|
||||
break;
|
||||
case FM_CMD_PKT_ID:
|
||||
if (wds-> mode == MODE_FM_UART)
|
||||
*dst_fd = wds->soc_if.uart.uart_fd;
|
||||
else
|
||||
*dst_fd = wds->soc_if.smd.fm_cmd_fd;
|
||||
case FM_EVT_PKT_ID:
|
||||
state = RX_FM_HDR;
|
||||
if (pkt_id == FM_CMD_PKT_ID)
|
||||
*len = FM_CMD_PKT_HDR_LEN;
|
||||
else if (pkt_id == FM_EVT_PKT_ID)
|
||||
*len = FM_EVT_PKT_HDR_LEN;
|
||||
break;
|
||||
case ANT_CMD_PKT_ID:
|
||||
case ANT_DATA_PKT_ID:
|
||||
state = RX_ANT_HDR;
|
||||
if (wds->mode == MODE_ANT_UART)
|
||||
*dst_fd = wds->soc_if.uart.uart_fd;
|
||||
else
|
||||
if (pkt_id == ANT_CMD_PKT_ID)
|
||||
*dst_fd = wds->soc_if.smd.ant_cmd_fd;
|
||||
else
|
||||
*dst_fd = wds->soc_if.smd.ant_data_fd;
|
||||
break;
|
||||
default:
|
||||
state = RX_ERROR;
|
||||
break;
|
||||
}
|
||||
|
||||
if (dir == SOC_TO_PC) {
|
||||
if (wds->is_server_enabled)
|
||||
*dst_fd = wds->server_socket_fd;
|
||||
else
|
||||
*dst_fd = wds->pc_if.uart.uart_fd;
|
||||
}
|
||||
|
||||
return state;
|
||||
}
|
||||
|
||||
static int process_pc_data_to_soc(wdsdaemon *wds, unsigned char *buf, int src_fd)
|
||||
{
|
||||
int retval = STATUS_SUCCESS;
|
||||
int len = 1, n_bytes = 0, n_total = 0;
|
||||
int pkt_id = 0, dst_fd = 0;
|
||||
int state = RX_PKT_IND, i;
|
||||
|
||||
do {
|
||||
if ((n_bytes = read(src_fd, (unsigned char *)&buf[n_total], len)) > 0) {
|
||||
n_total += n_bytes;
|
||||
len -= n_bytes;
|
||||
if (len)
|
||||
continue;
|
||||
|
||||
switch(state) {
|
||||
case RX_PKT_IND:
|
||||
pkt_id = buf[0];
|
||||
state = process_packet_type(wds, pkt_id, &dst_fd, &len,
|
||||
PC_TO_SOC);
|
||||
break;
|
||||
case RX_BT_HDR:
|
||||
len = get_pkt_data_len(pkt_id, buf);
|
||||
state = RX_BT_DATA;
|
||||
break;
|
||||
case RX_ANT_HDR:
|
||||
len = buf[0];
|
||||
state = RX_ANT_DATA;
|
||||
break;
|
||||
case RX_FM_HDR:
|
||||
len = get_pkt_data_len(pkt_id, buf);
|
||||
state = RX_FM_DATA;
|
||||
break;
|
||||
case RX_BT_DATA:
|
||||
case RX_ANT_DATA:
|
||||
case RX_FM_DATA:
|
||||
len = 0;
|
||||
break;
|
||||
default:
|
||||
retval = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
ERROR("%s: error while reading from fd = %d err = %s\n",
|
||||
__func__, src_fd, strerror(errno));
|
||||
if (n_bytes < 0)
|
||||
ERROR("%s:read returns err: %d\n", __func__,n_bytes);
|
||||
if (n_bytes == 0)
|
||||
ERROR("%s: This indicates the close of other end\n", __func__);
|
||||
retval = STATUS_ERROR;
|
||||
break;
|
||||
}
|
||||
} while (len);
|
||||
|
||||
if(retval)
|
||||
goto fail;
|
||||
|
||||
/* In case of Pronto, for BT, we have different channels for CMD and ACL,
|
||||
* so we don't send packet indicator to SoC.
|
||||
* Below condition will skip the packet indicator byte to Soc in\
|
||||
* case of Pronto.
|
||||
*/
|
||||
if (wds->mode != MODE_BT_UART && wds->mode != MODE_ANT_UART &&
|
||||
wds->mode != MODE_FM_UART) {
|
||||
n_total -= 1;
|
||||
len = 1;
|
||||
}
|
||||
while(n_total) {
|
||||
if((n_bytes = write(dst_fd, buf + len, n_total)) > 0) {
|
||||
len += n_bytes;
|
||||
n_total -= n_bytes;
|
||||
} else
|
||||
ERROR("%s :Error while writeto fd = %d err = %s\n",
|
||||
__func__, dst_fd, strerror(errno));
|
||||
break;
|
||||
}
|
||||
|
||||
DEBUG("cmd:\t");
|
||||
for (i = 0; i < len; i++)
|
||||
DEBUG("0x%x\t", buf[i]);
|
||||
DEBUG("\n");
|
||||
|
||||
if (n_total)
|
||||
retval = STATUS_ERROR;
|
||||
|
||||
fail:
|
||||
return retval;
|
||||
}
|
||||
|
||||
static void thread_exit_handler(int signo){
|
||||
DEBUG("%s: %d",__func__,signo);
|
||||
}
|
||||
|
||||
int server_create(wdsdaemon *wds,int *src_fd) {
|
||||
int retval = establish_server_socket(wds);
|
||||
if (STATUS_SUCCESS == retval)
|
||||
*src_fd = wds->server_socket_fd;
|
||||
else
|
||||
ERROR("Failed to init server socket\n");
|
||||
|
||||
return retval;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
int retval = STATUS_ERROR, src_fd = 0;
|
||||
fd_set readfds;
|
||||
wdsdaemon wds;
|
||||
unsigned char *buf = NULL;
|
||||
size_t size = UART_BUF_SIZE;
|
||||
struct sigaction action;
|
||||
sigset_t sigmask, emptymask;
|
||||
|
||||
sigemptyset(&sigmask);
|
||||
sigaddset(&sigmask, SIGINT);
|
||||
sigaddset(&sigmask, SIGPIPE);
|
||||
if (sigprocmask(SIG_BLOCK, &sigmask, NULL) == -1) {
|
||||
ERROR("failed to sigprocmask");
|
||||
}
|
||||
memset(&action, 0, sizeof(struct sigaction));
|
||||
sigemptyset(&action.sa_mask);
|
||||
action.sa_flags = 0;
|
||||
action.sa_handler = thread_exit_handler;
|
||||
|
||||
sigemptyset(&emptymask);
|
||||
|
||||
if (sigaction(SIGINT, &action, NULL) < 0) {
|
||||
ERROR("%s:sigaction failed\n", __func__);
|
||||
}
|
||||
|
||||
memset(&wds, 0, sizeof(wdsdaemon));
|
||||
|
||||
#ifdef ANDROID
|
||||
soc_type = get_bt_soc_type();
|
||||
#endif
|
||||
|
||||
/* parse options */
|
||||
retval = parse_options(&wds, argc, argv);
|
||||
if (STATUS_SUCCESS != retval) {
|
||||
goto fail;
|
||||
}
|
||||
|
||||
wdsdaemon_init(&wds);
|
||||
|
||||
if(!(wds.pcinit_mask))
|
||||
{
|
||||
retval = init_pc_interface(&wds);
|
||||
if (STATUS_SUCCESS != retval) {
|
||||
ERROR("Failed to init DUT-PC interface\n");
|
||||
goto fail;
|
||||
}
|
||||
src_fd = wds.pc_if.uart.uart_fd;
|
||||
}
|
||||
|
||||
retval = init_soc_interface(&wds);
|
||||
if (STATUS_SUCCESS != retval) {
|
||||
ERROR("Failed to init DUT-BTSOC interface\n");
|
||||
goto fail;
|
||||
}
|
||||
#ifdef BT_BLUEZ
|
||||
fflush(stdout);
|
||||
fflush(stderr);
|
||||
#endif
|
||||
|
||||
buf = (unsigned char *)calloc(size, 1);
|
||||
if (!buf) {
|
||||
ERROR("%s:Unable to allocate memory\n", __func__);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if( wds.is_server_enabled && ( server_create(&wds, &src_fd)!= STATUS_SUCCESS ))
|
||||
goto fail;
|
||||
|
||||
do {
|
||||
FD_ZERO(&readfds);
|
||||
FD_SET(src_fd, &readfds);
|
||||
|
||||
DEBUG("Waiting for data:\n");
|
||||
if ((retval = select(src_fd + 1, &readfds, NULL, NULL, NULL)) == -1) {
|
||||
ERROR("%s:select failed\n", __func__);
|
||||
if (wds.is_server_enabled)
|
||||
{
|
||||
ERROR("%s:closing the server socket and reopening\n", __func__);
|
||||
close(src_fd);
|
||||
if(server_create(&wds, &src_fd)== STATUS_SUCCESS)
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (FD_ISSET(src_fd, &readfds)) {
|
||||
retval = process_pc_data_to_soc(&wds, buf, src_fd);
|
||||
} else
|
||||
ERROR("%s:src_fd port not set\n",__func__);
|
||||
if (retval != STATUS_SUCCESS) {
|
||||
ERROR("%s: Error while processing Data to SoC err = %d\n", __func__, retval);
|
||||
if (wds.is_server_enabled)
|
||||
{
|
||||
ERROR("%s:closing the server socket and reopening\n", __func__);
|
||||
close(src_fd);
|
||||
if(server_create(&wds, &src_fd)== STATUS_SUCCESS)
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}while(1);
|
||||
|
||||
fail:
|
||||
if (buf)
|
||||
free(buf);
|
||||
shutdown(src_fd, SHUT_RDWR);
|
||||
switch (wds.mode) {
|
||||
case MODE_BT_UART:
|
||||
case MODE_FM_UART:
|
||||
case MODE_ANT_UART:
|
||||
shutdown(wds.soc_if.uart.uart_fd, SHUT_RDWR);
|
||||
break;
|
||||
case MODE_ALL_SMD:
|
||||
case MODE_BT_SMD:
|
||||
shutdown(wds.soc_if.smd.bt_cmd_fd, SHUT_RDWR);
|
||||
shutdown(wds.soc_if.smd.bt_acl_fd, SHUT_RDWR);
|
||||
if(wds.mode == MODE_BT_SMD)
|
||||
break;
|
||||
case MODE_FM_SMD:
|
||||
shutdown(wds.soc_if.smd.fm_cmd_fd, SHUT_RDWR);
|
||||
if (wds.mode == MODE_FM_SMD)
|
||||
break;
|
||||
case MODE_ANT_SMD:
|
||||
shutdown(wds.soc_if.smd.ant_cmd_fd, SHUT_RDWR);
|
||||
shutdown(wds.soc_if.smd.ant_data_fd, SHUT_RDWR);
|
||||
break;
|
||||
}
|
||||
pthread_join(wds.soc_rthread, NULL);
|
||||
|
||||
hidl_client_close();
|
||||
return retval;
|
||||
}
|
||||
@@ -59,3 +59,21 @@ define KernelPackage/usb-phy-ipq807x/description
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,usb-phy-ipq807x))
|
||||
|
||||
define KernelPackage/diag-char
|
||||
TITLE:=CHAR DIAG
|
||||
KCONFIG:= CONFIG_DIAG_MHI=y@ge5.4 \
|
||||
CONFIG_DIAG_OVER_PCIE=n@ge5.4 \
|
||||
CONFIG_DIAGFWD_BRIDGE_CODE=y \
|
||||
CONFIG_DIAG_CHAR=m
|
||||
DEPENDS:=+kmod-lib-crc-ccitt
|
||||
FILES:=$(LINUX_DIR)/drivers/char/diag/diagchar.ko
|
||||
endef
|
||||
|
||||
define KernelPackage/diag-char/description
|
||||
CHAR DIAG
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,diag-char))
|
||||
|
||||
|
||||
|
||||
54
feeds/ipq95xx/ipq53xx/patches/301-diag_char.patch
Normal file
54
feeds/ipq95xx/ipq53xx/patches/301-diag_char.patch
Normal file
@@ -0,0 +1,54 @@
|
||||
Index: linux-5.4.164-qsdk-26349818b464f8c7b52d59ce73579d9f3dd6bd5d/drivers/char/diag/diagchar_core.c
|
||||
===================================================================
|
||||
--- linux-5.4.164-qsdk-26349818b464f8c7b52d59ce73579d9f3dd6bd5d.orig/drivers/char/diag/diagchar_core.c
|
||||
+++ linux-5.4.164-qsdk-26349818b464f8c7b52d59ce73579d9f3dd6bd5d/drivers/char/diag/diagchar_core.c
|
||||
@@ -763,11 +763,6 @@ static void diag_cmd_invalidate_polling(
|
||||
driver->polling_reg_flag = 0;
|
||||
list_for_each_safe(start, temp, &driver->cmd_reg_list) {
|
||||
item = list_entry(start, struct diag_cmd_reg_t, link);
|
||||
- if (&item->entry == NULL) {
|
||||
- pr_err("diag: In %s, unable to search command\n",
|
||||
- __func__);
|
||||
- return;
|
||||
- }
|
||||
polling = diag_cmd_chk_polling(&item->entry);
|
||||
if (polling == DIAG_CMD_POLLING) {
|
||||
driver->polling_reg_flag = 1;
|
||||
@@ -829,11 +824,6 @@ struct diag_cmd_reg_entry_t *diag_cmd_se
|
||||
|
||||
list_for_each_safe(start, temp, &driver->cmd_reg_list) {
|
||||
item = list_entry(start, struct diag_cmd_reg_t, link);
|
||||
- if (&item->entry == NULL) {
|
||||
- pr_err("diag: In %s, unable to search command\n",
|
||||
- __func__);
|
||||
- return NULL;
|
||||
- }
|
||||
temp_entry = &item->entry;
|
||||
if (temp_entry->cmd_code == entry->cmd_code &&
|
||||
temp_entry->subsys_id == entry->subsys_id &&
|
||||
@@ -907,12 +897,6 @@ void diag_cmd_remove_reg_by_pid(int pid)
|
||||
mutex_lock(&driver->cmd_reg_mutex);
|
||||
list_for_each_safe(start, temp, &driver->cmd_reg_list) {
|
||||
item = list_entry(start, struct diag_cmd_reg_t, link);
|
||||
- if (&item->entry == NULL) {
|
||||
- pr_err("diag: In %s, unable to search command\n",
|
||||
- __func__);
|
||||
- mutex_unlock(&driver->cmd_reg_mutex);
|
||||
- return;
|
||||
- }
|
||||
if (item->pid == pid) {
|
||||
list_del(&item->link);
|
||||
kfree(item);
|
||||
@@ -931,12 +915,6 @@ void diag_cmd_remove_reg_by_proc(int pro
|
||||
mutex_lock(&driver->cmd_reg_mutex);
|
||||
list_for_each_safe(start, temp, &driver->cmd_reg_list) {
|
||||
item = list_entry(start, struct diag_cmd_reg_t, link);
|
||||
- if (&item->entry == NULL) {
|
||||
- pr_err("diag: In %s, unable to search command\n",
|
||||
- __func__);
|
||||
- mutex_unlock(&driver->cmd_reg_mutex);
|
||||
- return;
|
||||
- }
|
||||
if (item->proc == proc) {
|
||||
list_del(&item->link);
|
||||
kfree(item);
|
||||
56
feeds/ipq95xx/libtcmd/Makefile
Executable file
56
feeds/ipq95xx/libtcmd/Makefile
Executable file
@@ -0,0 +1,56 @@
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG:=libtcmd
|
||||
PKG_NAME:=$(PKG)
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_VERSION:=12.3
|
||||
|
||||
#PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/$(PKG_NAME)
|
||||
SECTION:=QCA
|
||||
CATEGORY:=QTI software
|
||||
URL:=http://www.qca.qualcomm.com
|
||||
MAINTAINER:=Qualcomm Atheros
|
||||
TITLE:= QCA libtcmd utils
|
||||
DEPENDS:= @TARGET_ipq_ipq807x||TARGET_ipq_ipq807x_64||TARGET_ipq_ipq60xx||TARGET_ipq_ipq60xx_64||TARGET_ipq_ipq50xx||TARGET_ipq_ipq50xx_64||TARGET_ipq807x||TARGET_ipq50xx||TARGET_ipq60xx||TARGET_ipq95xx||TARGET_ipq53xx +libpthread +libnl
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/description/Default
|
||||
LIBTCMD Package Support for QCA WIFI 11 drivers
|
||||
endef
|
||||
|
||||
|
||||
TARGET_CFLAGS += -I$(STAGING_DIR)/usr/include \
|
||||
-I$(STAGING_DIR)/usr/include/libnl3 \
|
||||
-I$(STAGING_DIR)/include \
|
||||
-fPIC -DWLAN_API_NL80211 -DLIBNL_2 -DWIN_AP_HOST
|
||||
|
||||
TARGET_LDFLAGS += -lnl-3 -lnl-genl-3 -shared
|
||||
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-mac80211),)
|
||||
TARGET_CFLAGS+=-DWIN_AP_HOST_OPEN=1
|
||||
endif
|
||||
|
||||
define Build/Compile
|
||||
$(MAKE) -C $(PKG_BUILD_DIR) \
|
||||
CC="$(TARGET_CC)" \
|
||||
CFLAGS="$(TARGET_CFLAGS)" \
|
||||
LDFLAGS="$(TARGET_LDFLAGS)"
|
||||
endef
|
||||
|
||||
define Build/InstallDev
|
||||
$(INSTALL_DIR) $(1)/usr/include/ $(1)/usr/lib/
|
||||
$(CP) $(PKG_BUILD_DIR)/*.h $(1)/usr/include/
|
||||
$(CP) $(PKG_BUILD_DIR)/libtcmd.so $(1)/usr/lib/
|
||||
endef
|
||||
|
||||
define Package/$(PKG_NAME)/install
|
||||
$(INSTALL_DIR) $(1)/usr/lib
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/libtcmd.so $(1)/usr/lib/
|
||||
endef
|
||||
|
||||
$(eval $(call BuildPackage,libtcmd))
|
||||
27
feeds/ipq95xx/libtcmd/patches/100-compile.patch
Normal file
27
feeds/ipq95xx/libtcmd/patches/100-compile.patch
Normal file
@@ -0,0 +1,27 @@
|
||||
Index: libtcmd-11.5/libtcmd.h
|
||||
===================================================================
|
||||
--- libtcmd-11.5.orig/libtcmd.h
|
||||
+++ libtcmd-11.5/libtcmd.h
|
||||
@@ -71,7 +71,9 @@ struct tcmd_cfg {
|
||||
struct sigevent sev;
|
||||
timer_t timer;
|
||||
bool timeout;
|
||||
-} tcmd_cfg;
|
||||
+};
|
||||
+
|
||||
+extern struct tcmd_cfg tcmd_cfg;
|
||||
|
||||
/* WLAN API */
|
||||
#ifdef WLAN_API_NL80211
|
||||
Index: libtcmd-11.5/nl80211.c
|
||||
===================================================================
|
||||
--- libtcmd-11.5.orig/nl80211.c
|
||||
+++ libtcmd-11.5/nl80211.c
|
||||
@@ -23,6 +23,7 @@
|
||||
#endif
|
||||
|
||||
int cb_ret;
|
||||
+struct tcmd_cfg tcmd_cfg;
|
||||
|
||||
#ifdef LIBNL_2
|
||||
static inline struct nl_sock *nl_handle_alloc(void)
|
||||
54
feeds/ipq95xx/libtcmd/src/Android.mk
Executable file
54
feeds/ipq95xx/libtcmd/src/Android.mk
Executable file
@@ -0,0 +1,54 @@
|
||||
LOCAL_PATH:=$(call my-dir)
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
LOCAL_MODULE := libtcmd_headers
|
||||
LOCAL_CFLAGS := -Werror
|
||||
LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)
|
||||
LOCAL_PROPRIETARY_MODULE := true
|
||||
include $(BUILD_HEADER_LIBRARY)
|
||||
|
||||
# Build libtcmd =========================
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
LOCAL_CLANG := true
|
||||
LOCAL_MODULE := libtcmd
|
||||
LOCAL_SRC_FILES:= \
|
||||
nl80211.c \
|
||||
libtcmd.c \
|
||||
os.c
|
||||
|
||||
ifeq ($(PRODUCT_VENDOR_MOVE_ENABLED), true)
|
||||
LOCAL_PROPRIETARY_MODULE := true
|
||||
endif
|
||||
|
||||
ifeq ($(BOARD_HAS_ATH_WLAN_AR6004),true)
|
||||
LOCAL_CFLAGS+= -DCONFIG_AR6002_REV6
|
||||
endif
|
||||
|
||||
ifneq ($(wildcard external/libnl-headers),)
|
||||
LOCAL_C_INCLUDES += external/libnl-headers
|
||||
else
|
||||
LOCAL_C_INCLUDES += external/libnl/include external/libnl/include/linux-private
|
||||
endif
|
||||
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include
|
||||
LOCAL_ADDITIONAL_DEPENDENCIES := $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr
|
||||
|
||||
LOCAL_CFLAGS += \
|
||||
-DWLAN_API_NL80211 \
|
||||
-DANDROID \
|
||||
-DLIBNL_2 \
|
||||
-DSYSCONFDIR="\"/etc/libnl\""\
|
||||
-Werror
|
||||
|
||||
ifneq ($(wildcard system/core/libnl_2),)
|
||||
# ICS ships with libnl 2.0
|
||||
LOCAL_SHARED_LIBRARIES := libnl_2
|
||||
else
|
||||
LOCAL_SHARED_LIBRARIES := libnl
|
||||
endif
|
||||
|
||||
LOCAL_MODULE_OWNER := qcom
|
||||
LOCAL_SANITIZE := signed-integer-overflow unsigned-integer-overflow
|
||||
|
||||
include $(BUILD_STATIC_LIBRARY)
|
||||
24
feeds/ipq95xx/libtcmd/src/Makefile
Executable file
24
feeds/ipq95xx/libtcmd/src/Makefile
Executable file
@@ -0,0 +1,24 @@
|
||||
#CC := $(ATH_CROSS_COMPILE_TYPE)gcc
|
||||
CC ?= gcc
|
||||
|
||||
CFLAGS += -DWLAN_API_NL80211 -DLIBNL_2
|
||||
LDFLAGS += -shared
|
||||
|
||||
TARGET_LIB = libtcmd.so
|
||||
SRCS = os.c nl80211.c libtcmd.c
|
||||
OBJS = $(SRCS:.c=.o)
|
||||
|
||||
.PHONY=: all
|
||||
|
||||
all: ${TARGET_LIB}
|
||||
|
||||
$(TARGET_LIB): $(OBJS)
|
||||
$(CC) ${LDFLAGS} -o $@ $^
|
||||
|
||||
$(SRCS:.c=.d):%.d:%.c
|
||||
$(CC) $(CFLAGS) -MM $< >$@
|
||||
|
||||
.PHONY: clean
|
||||
|
||||
clean:
|
||||
rm -f ${TARGET_LIB} ${OBJS}
|
||||
23
feeds/ipq95xx/libtcmd/src/Makefile.am
Executable file
23
feeds/ipq95xx/libtcmd/src/Makefile.am
Executable file
@@ -0,0 +1,23 @@
|
||||
AM_CFLAGS = -Wall \
|
||||
-g -O0 \
|
||||
-DLIBNL_2 \
|
||||
-DWLAN_API_NL80211 \
|
||||
$(LIBNL_CFLAGS)
|
||||
|
||||
if USE_GLIB
|
||||
AM_CFLAGS += -DUSE_GLIB $(GLIB_CFLAGS)
|
||||
endif
|
||||
|
||||
if MDM_SET
|
||||
AM_CFLAGS += -DMDM
|
||||
endif
|
||||
|
||||
c_sources = os.c \
|
||||
nl80211.c \
|
||||
libtcmd.c
|
||||
|
||||
AM_CFLAGS += -DWLAN_API_NL80211
|
||||
lib_LIBRARIES = libtcmd.a
|
||||
libtcmd_a_SOURCES = $(c_sources)
|
||||
libtcmd_a_LDFLAGS = -static
|
||||
pkginclude_HEADERS = libtcmd.h
|
||||
132
feeds/ipq95xx/libtcmd/src/libtcmd.c
Executable file
132
feeds/ipq95xx/libtcmd/src/libtcmd.c
Executable file
@@ -0,0 +1,132 @@
|
||||
/*
|
||||
* Copyright (c) 2019 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
/*
|
||||
* 2011-2012, 2016 Qualcomm Atheros Inc. All Rights Reserved.
|
||||
* Qualcomm Atheros Proprietary and Confidential.
|
||||
*/
|
||||
|
||||
#include "string.h"
|
||||
#include "libtcmd.h"
|
||||
#include "os.h"
|
||||
|
||||
#ifdef USE_GLIB
|
||||
#include <glib.h>
|
||||
#define strlcat g_strlcat
|
||||
#define strlcpy g_strlcpy
|
||||
#endif
|
||||
|
||||
int tcmd_tx(void *buf, int len, bool resp)
|
||||
{
|
||||
int err = 0;
|
||||
|
||||
/* XXX: just call nl80211 directly for now */
|
||||
#ifdef WLAN_API_NL80211
|
||||
err = nl80211_tcmd_tx(&tcmd_cfg, buf, len);
|
||||
if (err)
|
||||
goto err_out;
|
||||
#endif
|
||||
if (resp)
|
||||
#ifdef WLAN_API_NL80211
|
||||
err = nl80211_tcmd_rx(&tcmd_cfg);
|
||||
#endif
|
||||
|
||||
return err;
|
||||
err_out:
|
||||
A_DBG("tcmd_tx failed: %s\n", strerror(-err));
|
||||
return err;
|
||||
}
|
||||
|
||||
static void tcmd_expire(union sigval sig)
|
||||
{
|
||||
/* tcmd expired, do something */
|
||||
A_DBG("timer expired %d\n",sig.sival_int);
|
||||
tcmd_cfg.timeout = true;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_AR6002_REV6
|
||||
int tcmd_tx_init(char *iface, void (*rx_cb)(void *buf, int len))
|
||||
{
|
||||
int err;
|
||||
|
||||
strlcpy(tcmd_cfg.iface, iface, sizeof(tcmd_cfg.iface));
|
||||
tcmd_cfg.rx_cb = rx_cb;
|
||||
|
||||
tcmd_cfg.sev.sigev_notify = SIGEV_THREAD;
|
||||
tcmd_cfg.sev.sigev_notify_function = tcmd_expire;
|
||||
timer_create(CLOCK_REALTIME, &tcmd_cfg.sev, &tcmd_cfg.timer);
|
||||
|
||||
#ifdef WLAN_API_NL80211
|
||||
err = nl80211_init(&tcmd_cfg);
|
||||
if (err) {
|
||||
A_DBG("couldn't init nl80211!: %s\n", strerror(-err));
|
||||
return err;
|
||||
}
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#else
|
||||
/* get driver ep from tcmd ep */
|
||||
static int tcmd_set_ep(uint32_t *driv_ep, enum tcmd_ep ep)
|
||||
{
|
||||
#ifdef WLAN_API_NL80211
|
||||
return nl80211_set_ep(driv_ep, ep);
|
||||
#endif
|
||||
}
|
||||
|
||||
void tcmd_response_cb(void *buf, int len)
|
||||
{
|
||||
tcmd_cfg.timeout = true;
|
||||
tcmd_reset_timer(&tcmd_cfg);
|
||||
tcmd_cfg.docommand_rx_cb(buf, len);
|
||||
}
|
||||
|
||||
int tcmd_init(char *iface, void (*rx_cb)(void *buf, int len), ...)
|
||||
{
|
||||
int err;
|
||||
enum tcmd_ep ep;
|
||||
va_list ap;
|
||||
va_start(ap, rx_cb);
|
||||
ep = va_arg(ap, enum tcmd_ep);
|
||||
va_end(ap);
|
||||
|
||||
strlcpy(tcmd_cfg.iface, iface, sizeof(tcmd_cfg.iface));
|
||||
tcmd_cfg.docommand_rx_cb = rx_cb;
|
||||
tcmd_cfg.rx_cb = tcmd_response_cb;
|
||||
err = tcmd_set_ep(&tcmd_cfg.ep, ep);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
tcmd_cfg.sev.sigev_notify = SIGEV_THREAD;
|
||||
tcmd_cfg.sev.sigev_notify_function = tcmd_expire;
|
||||
timer_create(CLOCK_REALTIME, &tcmd_cfg.sev, &tcmd_cfg.timer);
|
||||
|
||||
#ifdef WLAN_API_NL80211
|
||||
err = nl80211_init(&tcmd_cfg);
|
||||
if (err) {
|
||||
A_DBG("couldn't init nl80211!: %s\n", strerror(-err));
|
||||
return err;
|
||||
}
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
int tcmd_tx_start( void )
|
||||
{
|
||||
return nl80211_tcmd_start(&tcmd_cfg);
|
||||
}
|
||||
|
||||
int tcmd_tx_stop( void )
|
||||
{
|
||||
return nl80211_tcmd_stop(&tcmd_cfg);
|
||||
}
|
||||
int tcmd_tx_init(char *iface, void (*rx_cb)(void *buf, int len))
|
||||
{
|
||||
return tcmd_init(iface, rx_cb, TCMD_EP_TCMD);
|
||||
}
|
||||
#endif
|
||||
95
feeds/ipq95xx/libtcmd/src/libtcmd.h
Executable file
95
feeds/ipq95xx/libtcmd/src/libtcmd.h
Executable file
@@ -0,0 +1,95 @@
|
||||
/*
|
||||
* Copyright (c) 2011-2012, 2020 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* 2011-2012 Qualcomm Atheros Inc. All Rights Reserved.
|
||||
* Qualcomm Atheros Proprietary and Confidential.
|
||||
*/
|
||||
|
||||
#ifndef _LIBTCMD_H_
|
||||
#define _LIBTCMD_H_
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <getopt.h>
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
#include <net/if.h>
|
||||
#include <signal.h>
|
||||
#include <time.h>
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
#include <stdarg.h>
|
||||
#endif
|
||||
|
||||
#define A_ERR(ret, args...) { \
|
||||
printf(args); \
|
||||
exit(ret); \
|
||||
}
|
||||
#define A_DBG printf
|
||||
|
||||
#ifdef WIN_AP_HOST
|
||||
/* In 6GHz the channel list is larger,
|
||||
* it can potentially take 60s or more so
|
||||
* increasing timeout.
|
||||
*/
|
||||
#define TCMD_TIMEOUT 70 /* s */
|
||||
#else
|
||||
#define TCMD_TIMEOUT 16 /* s */
|
||||
#endif
|
||||
|
||||
#define UNUSED(x) (void)(x)
|
||||
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
enum tcmd_ep {
|
||||
TCMD_EP_TCMD,
|
||||
TCMD_EP_WMI,
|
||||
};
|
||||
#endif
|
||||
|
||||
struct tcmd_cfg {
|
||||
char iface[100];
|
||||
void (*rx_cb)(void *buf, int len);
|
||||
void (*docommand_rx_cb)(void *buf, int len);
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
uint32_t ep;
|
||||
#endif
|
||||
#ifdef WLAN_API_NL80211
|
||||
/* XXX: eventually default to libnl-2.0 API */
|
||||
#ifdef LIBNL_2
|
||||
#define nl_handle nl_sock
|
||||
#endif
|
||||
struct nl_handle *nl_handle;
|
||||
int nl_id;
|
||||
#endif
|
||||
struct sigevent sev;
|
||||
timer_t timer;
|
||||
bool timeout;
|
||||
} tcmd_cfg;
|
||||
|
||||
/* WLAN API */
|
||||
#ifdef WLAN_API_NL80211
|
||||
#include "nl80211_drv.h"
|
||||
#endif
|
||||
|
||||
/* send tcmd in buffer buf of length len. resp == true if a response by the FW
|
||||
* is required. Returns: 0 on success, -ETIMEOUT on timeout
|
||||
*/
|
||||
int tcmd_tx(void *buf, int len, bool resp);
|
||||
|
||||
/* Initialize tcmd transport layer on given iface. Call given rx_cb on tcmd
|
||||
* response */
|
||||
int tcmd_tx_init(char *iface, void (*rx_cb)(void *buf, int len));
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
/* same as above, but takes optional testmode endpoint (e.g. WMI vs. TCMD) */
|
||||
int tcmd_init(char *iface, void (*rx_cb)(void *buf, int len), ...);
|
||||
#endif
|
||||
int tcmd_tx_start( void );
|
||||
int tcmd_tx_stop( void );
|
||||
#endif /* _LIBTCMD_H_ */
|
||||
563
feeds/ipq95xx/libtcmd/src/nl80211.c
Executable file
563
feeds/ipq95xx/libtcmd/src/nl80211.c
Executable file
@@ -0,0 +1,563 @@
|
||||
/*
|
||||
* Copyright (c) 2011-2012, 2016-2018, 2021 Qualcomm Technologies Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* 2011-2012, 2016 Qualcomm Atheros Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* $ATH_LICENSE_HOSTSDK0_C$
|
||||
*
|
||||
* nl80211 code from iw and hwsim tool by Johannes Berg
|
||||
* http://git.sipsolutions.net/?p=iw.git;a=summary
|
||||
* http://git.sipsolutions.net/?p=hwsim.git;a=summary
|
||||
*/
|
||||
|
||||
#include "libtcmd.h"
|
||||
#include "os.h"
|
||||
#ifdef WIN_AP_HOST
|
||||
#include <netlink/handlers.h>
|
||||
#include <linux/genetlink.h>
|
||||
#include <linux/nl80211.h>
|
||||
#include <linux/errno.h>
|
||||
#endif
|
||||
|
||||
int cb_ret;
|
||||
|
||||
#ifdef LIBNL_2
|
||||
static inline struct nl_sock *nl_handle_alloc(void)
|
||||
{
|
||||
return nl_socket_alloc();
|
||||
}
|
||||
|
||||
static inline void nl_handle_destroy(struct nl_handle *h)
|
||||
{
|
||||
nl_socket_free(h);
|
||||
}
|
||||
|
||||
#define nl_disable_sequence_check nl_socket_disable_seq_check
|
||||
#endif
|
||||
|
||||
/* copied from ath6kl */
|
||||
enum ar6k_testmode_attr {
|
||||
__AR6K_TM_ATTR_INVALID = 0,
|
||||
AR6K_TM_ATTR_CMD = 1,
|
||||
AR6K_TM_ATTR_DATA = 2,
|
||||
AR6K_TM_ATTR_STREAM_ID = 3,
|
||||
|
||||
/* keep last */
|
||||
__AR6K_TM_ATTR_AFTER_LAST,
|
||||
AR6K_TM_ATTR_MAX = __AR6K_TM_ATTR_AFTER_LAST - 1
|
||||
};
|
||||
|
||||
#ifdef WIN_AP_HOST_OPEN
|
||||
enum ar6k_testmode_cmd {
|
||||
AR6K_TM_CMD_VERSION = 0,
|
||||
AR6K_TM_CMD_START = 1,
|
||||
AR6K_TM_CMD_STOP = 2,
|
||||
AR6K_TM_CMD_WMI_CMD = 3,
|
||||
AR6K_TM_CMD_TCMD = 4,
|
||||
};
|
||||
#else
|
||||
enum ar6k_testmode_cmd {
|
||||
AR6K_TM_CMD_TCMD = 0,
|
||||
AR6K_TM_CMD_START = 1,
|
||||
AR6K_TM_CMD_STOP = 2,
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
AR6K_TM_CMD_WMI_CMD = 0xF000,
|
||||
#endif
|
||||
};
|
||||
#endif
|
||||
|
||||
static int error_handler(struct sockaddr_nl *nla, struct nlmsgerr *err,
|
||||
void *arg)
|
||||
{
|
||||
int *ret = arg;
|
||||
*ret = err->error;
|
||||
|
||||
UNUSED(nla);
|
||||
return NL_STOP;
|
||||
}
|
||||
|
||||
static int finish_handler(struct nl_msg *msg, void *arg)
|
||||
{
|
||||
int *ret = arg;
|
||||
*ret = 0;
|
||||
|
||||
UNUSED(msg);
|
||||
return NL_SKIP;
|
||||
}
|
||||
|
||||
static int ack_handler(struct nl_msg *msg, void *arg)
|
||||
{
|
||||
int *ret = arg;
|
||||
*ret = 0;
|
||||
|
||||
UNUSED(msg);
|
||||
return NL_STOP;
|
||||
}
|
||||
|
||||
#ifdef ANDROID
|
||||
#ifndef in_addr_t
|
||||
typedef uint32_t in_addr_t;
|
||||
#endif
|
||||
#include "netlink-private/genl.h"
|
||||
/* android's libnl_2 does not include this, define it here */
|
||||
static int android_genl_ctrl_resolve(struct nl_handle *handle,
|
||||
const char *name)
|
||||
{
|
||||
/*
|
||||
* Android ICS has very minimal genl_ctrl_resolve() implementation, so
|
||||
* need to work around that.
|
||||
*/
|
||||
struct nl_cache *cache = NULL;
|
||||
struct genl_family *nl80211 = NULL;
|
||||
int id = -1;
|
||||
|
||||
if (genl_ctrl_alloc_cache(handle, &cache) < 0) {
|
||||
A_DBG("nl80211: Failed to allocate generic "
|
||||
"netlink cache");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
nl80211 = genl_ctrl_search_by_name(cache, name);
|
||||
if (nl80211 == NULL)
|
||||
goto fail;
|
||||
|
||||
id = genl_family_get_id(nl80211);
|
||||
|
||||
fail:
|
||||
if (nl80211)
|
||||
genl_family_put(nl80211);
|
||||
if (cache)
|
||||
nl_cache_free(cache);
|
||||
|
||||
return id;
|
||||
}
|
||||
#define genl_ctrl_resolve android_genl_ctrl_resolve
|
||||
|
||||
#define nl_socket_get_cb nl_sk_get_cb
|
||||
struct nl_cb *nl_socket_get_cb(const struct nl_sock *sk)
|
||||
{
|
||||
return nl_cb_get(sk->s_cb);
|
||||
}
|
||||
|
||||
#define nl_socket_enable_msg_peek nl_sk_enable_msg_peek
|
||||
void nl_socket_enable_msg_peek(struct nl_sock *sk)
|
||||
{
|
||||
sk->s_flags |= NL_MSG_PEEK;
|
||||
}
|
||||
|
||||
#define nl_socket_set_nonblocking nl_sk_set_nb
|
||||
int nl_socket_set_nonblocking(const struct nl_sock *sk)
|
||||
{
|
||||
fcntl(sk->s_fd, F_SETFL, O_NONBLOCK);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int seq_ok(struct nl_msg *msg, void *arg)
|
||||
{
|
||||
UNUSED(msg);
|
||||
UNUSED(arg);
|
||||
|
||||
return NL_OK;
|
||||
}
|
||||
|
||||
#define nl_socket_disable_seq_check disable_seq_check
|
||||
static inline void disable_seq_check(struct nl_handle *handle)
|
||||
{
|
||||
nl_cb_set(nl_socket_get_cb(handle), NL_CB_SEQ_CHECK,
|
||||
NL_CB_CUSTOM, seq_ok, NULL);
|
||||
}
|
||||
#endif
|
||||
|
||||
struct handler_args {
|
||||
const char *group;
|
||||
int id;
|
||||
};
|
||||
|
||||
static int family_handler(struct nl_msg *msg, void *arg)
|
||||
{
|
||||
struct handler_args *grp = arg;
|
||||
struct nlattr *tb[CTRL_ATTR_MAX + 1];
|
||||
struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
|
||||
struct nlattr *mcgrp;
|
||||
int rem_mcgrp;
|
||||
|
||||
nla_parse(tb, CTRL_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
|
||||
genlmsg_attrlen(gnlh, 0), NULL);
|
||||
|
||||
if (!tb[CTRL_ATTR_MCAST_GROUPS])
|
||||
return NL_SKIP;
|
||||
|
||||
nla_for_each_nested(mcgrp, tb[CTRL_ATTR_MCAST_GROUPS], rem_mcgrp) {
|
||||
struct nlattr *tb_mcgrp[CTRL_ATTR_MCAST_GRP_MAX + 1];
|
||||
|
||||
nla_parse(tb_mcgrp, CTRL_ATTR_MCAST_GRP_MAX,
|
||||
nla_data(mcgrp), nla_len(mcgrp), NULL);
|
||||
|
||||
if (!tb_mcgrp[CTRL_ATTR_MCAST_GRP_NAME] ||
|
||||
!tb_mcgrp[CTRL_ATTR_MCAST_GRP_ID])
|
||||
continue;
|
||||
else
|
||||
grp->id = nla_get_u32(tb_mcgrp[CTRL_ATTR_MCAST_GRP_ID]);
|
||||
if (strncmp(nla_data(tb_mcgrp[CTRL_ATTR_MCAST_GRP_NAME]),
|
||||
grp->group,
|
||||
nla_len(tb_mcgrp[CTRL_ATTR_MCAST_GRP_NAME])))
|
||||
continue;
|
||||
grp->id = nla_get_u32(tb_mcgrp[CTRL_ATTR_MCAST_GRP_ID]);
|
||||
break;
|
||||
}
|
||||
|
||||
return NL_SKIP;
|
||||
}
|
||||
|
||||
int nl_get_multicast_id(struct nl_handle *sock, const char *family,
|
||||
const char *group)
|
||||
{
|
||||
struct nl_msg *msg;
|
||||
struct nl_cb *cb;
|
||||
int ret, ctrlid;
|
||||
struct handler_args grp = {
|
||||
.group = group,
|
||||
.id = -ENOENT,
|
||||
};
|
||||
|
||||
msg = nlmsg_alloc();
|
||||
if (!msg)
|
||||
return -ENOMEM;
|
||||
|
||||
cb = nl_cb_alloc(NL_CB_DEFAULT);
|
||||
if (!cb) {
|
||||
ret = -ENOMEM;
|
||||
goto out_fail_cb;
|
||||
}
|
||||
|
||||
ctrlid = genl_ctrl_resolve(sock, "nlctrl");
|
||||
|
||||
#ifdef ANDROID
|
||||
genlmsg_put(msg, NL_AUTO_PID, NL_AUTO_SEQ, GENL_ID_CTRL, 0, 0,
|
||||
CTRL_CMD_GETFAMILY, 1);
|
||||
#else
|
||||
genlmsg_put(msg, 0, 0, ctrlid, 0, 0, CTRL_CMD_GETFAMILY, 0);
|
||||
#endif
|
||||
|
||||
ret = -ENOBUFS;
|
||||
NLA_PUT_STRING(msg, CTRL_ATTR_FAMILY_NAME, family);
|
||||
|
||||
ret = nl_send_auto_complete(sock, msg);
|
||||
if (ret < 0)
|
||||
goto out;
|
||||
|
||||
ret = 1;
|
||||
|
||||
nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &ret);
|
||||
nl_cb_set(cb, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, &ret);
|
||||
nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, &ret);
|
||||
nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM, family_handler, &grp);
|
||||
|
||||
while (ret > 0)
|
||||
nl_recvmsgs(sock, cb);
|
||||
|
||||
if (ret == 0)
|
||||
ret = grp.id;
|
||||
nla_put_failure:
|
||||
out:
|
||||
nl_cb_put(cb);
|
||||
out_fail_cb:
|
||||
nlmsg_free(msg);
|
||||
return ret;
|
||||
}
|
||||
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
int nl80211_set_ep(uint32_t *driv_ep, enum tcmd_ep ep)
|
||||
{
|
||||
switch (ep) {
|
||||
case TCMD_EP_TCMD:
|
||||
*driv_ep = AR6K_TM_CMD_TCMD;
|
||||
break;
|
||||
case TCMD_EP_WMI:
|
||||
*driv_ep = AR6K_TM_CMD_WMI_CMD;
|
||||
break;
|
||||
default:
|
||||
fprintf(stderr, "nl80211: unknown ep!");
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* tcmd rx_cb wrapper to "unpack" the nl80211 msg and call the "real" cb */
|
||||
int nl80211_rx_cb(struct nl_msg *msg, void *arg)
|
||||
{
|
||||
struct nlattr *tb[NL80211_ATTR_MAX + 1];
|
||||
struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
|
||||
struct nlattr *td[AR6K_TM_ATTR_MAX + 1];
|
||||
void *buf;
|
||||
int len;
|
||||
|
||||
UNUSED(arg);
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("nl80211: cb wrapper called\n");
|
||||
#endif
|
||||
nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
|
||||
genlmsg_attrlen(gnlh, 0), NULL);
|
||||
|
||||
if (!tb[NL80211_ATTR_TESTDATA] || !tb[NL80211_ATTR_WIPHY]) {
|
||||
printf("no data!\n");
|
||||
return NL_SKIP;
|
||||
}
|
||||
|
||||
nla_parse(td, AR6K_TM_ATTR_MAX, nla_data(tb[NL80211_ATTR_TESTDATA]),
|
||||
nla_len(tb[NL80211_ATTR_TESTDATA]), NULL);
|
||||
|
||||
if (!td[AR6K_TM_ATTR_DATA]) {
|
||||
#ifndef WIN_AP_HOST_OPEN
|
||||
printf("no data in reply\n");
|
||||
#endif
|
||||
return NL_SKIP;
|
||||
}
|
||||
|
||||
buf = nla_data(td[AR6K_TM_ATTR_DATA]);
|
||||
len = nla_len(td[AR6K_TM_ATTR_DATA]);
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("nl80211: resp received, calling custom cb\n");
|
||||
#endif
|
||||
tcmd_cfg.rx_cb(buf, len);
|
||||
/* trip waiting thread */
|
||||
tcmd_cfg.timeout = true;
|
||||
|
||||
return NL_SKIP;
|
||||
}
|
||||
|
||||
int nl80211_init(struct tcmd_cfg *cfg)
|
||||
{
|
||||
struct nl_cb *cb;
|
||||
int err;
|
||||
#ifdef WIN_AP_HOST_OPEN
|
||||
int opt;
|
||||
#endif
|
||||
|
||||
if(cfg->nl_handle)
|
||||
nl_handle_destroy(cfg->nl_handle);
|
||||
|
||||
cfg->nl_handle = nl_handle_alloc();
|
||||
if (!cfg->nl_handle) {
|
||||
A_DBG("Failed to allocate netlink socket.\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
if (genl_connect(cfg->nl_handle)) {
|
||||
A_DBG("Failed to connect to generic netlink.\n");
|
||||
err = -ENOLINK;
|
||||
goto out_handle_destroy;
|
||||
}
|
||||
|
||||
cfg->nl_id = genl_ctrl_resolve(cfg->nl_handle, "nl80211");
|
||||
if (cfg->nl_id < 0) {
|
||||
A_DBG("nl80211 not found.\n");
|
||||
err = -ENOENT;
|
||||
goto out_handle_destroy;
|
||||
}
|
||||
|
||||
/* replace this with genl_ctrl_resolve_grp() once we move to libnl3 */
|
||||
err = nl_get_multicast_id(cfg->nl_handle, "nl80211", "testmode");
|
||||
if (err >= 0) {
|
||||
err = nl_socket_add_membership(cfg->nl_handle, err);
|
||||
if (err) {
|
||||
A_DBG("failed to join testmode group!\n");
|
||||
goto out_handle_destroy;
|
||||
}
|
||||
} else
|
||||
goto out_handle_destroy;
|
||||
/*
|
||||
* Enable peek mode so drivers can send large amounts
|
||||
* of data in blobs without problems.
|
||||
*/
|
||||
nl_socket_enable_msg_peek(cfg->nl_handle);
|
||||
|
||||
/*
|
||||
* disable sequence checking to handle events.
|
||||
*/
|
||||
nl_disable_sequence_check(cfg->nl_handle);
|
||||
|
||||
cb = nl_socket_get_cb(cfg->nl_handle);
|
||||
#ifdef ANDROID
|
||||
/* libnl_2 does not provide default handlers */
|
||||
nl_cb_err(cb, NL_CB_CUSTOM, error_handler, &cb_ret);
|
||||
nl_cb_set(cb, NL_CB_ACK, NL_CB_CUSTOM, ack_handler, &cb_ret);
|
||||
nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, &cb_ret);
|
||||
#endif
|
||||
nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM, nl80211_rx_cb, NULL);
|
||||
|
||||
/* so we can handle timeouts properly */
|
||||
nl_socket_set_nonblocking(cfg->nl_handle);
|
||||
|
||||
#ifdef WIN_AP_HOST_OPEN
|
||||
/* nobuf errors are useful for identifying lost packets and doing a
|
||||
* resync. Such handling is not performed by libtcmd since we
|
||||
* do a synchronous recv after performing a tx. Since
|
||||
* we are listening in multicast socket and we recv/process the
|
||||
* data only when do a tx, there are chances we receive overrun
|
||||
* or ENOBUF errors which affects our data recv and better to
|
||||
* avoid them
|
||||
*/
|
||||
opt = 1;
|
||||
setsockopt(nl_socket_get_fd(cfg->nl_handle), SOL_NETLINK,
|
||||
NETLINK_NO_ENOBUFS, &opt, sizeof(opt));
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
|
||||
out_handle_destroy:
|
||||
nl_handle_destroy(cfg->nl_handle);
|
||||
return err;
|
||||
}
|
||||
|
||||
int nl80211_tcmd_connect(struct tcmd_cfg *cfg, enum ar6k_testmode_cmd cmd )
|
||||
{
|
||||
struct nl_msg *msg;
|
||||
struct nlattr *nest;
|
||||
int devidx, err = 0;
|
||||
|
||||
/* CHANGE HERE: you may need to allocate larger messages! */
|
||||
msg = nlmsg_alloc();
|
||||
if (!msg) {
|
||||
A_DBG("failed to allocate netlink message\n");
|
||||
return 2;
|
||||
}
|
||||
|
||||
genlmsg_put(msg, 0, 0, cfg->nl_id, 0,
|
||||
0, NL80211_CMD_TESTMODE, 0);
|
||||
|
||||
devidx = if_nametoindex(cfg->iface);
|
||||
if (devidx) {
|
||||
NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, devidx);
|
||||
} else {
|
||||
A_DBG("Device not found\n");
|
||||
err = -ENOENT;
|
||||
goto out_free_msg;
|
||||
}
|
||||
|
||||
nest = nla_nest_start(msg, NL80211_ATTR_TESTDATA);
|
||||
if (!nest) {
|
||||
A_DBG("failed to nest\n");
|
||||
err = -1;
|
||||
goto out_free_msg;
|
||||
}
|
||||
|
||||
NLA_PUT_U32(msg, AR6K_TM_ATTR_CMD, cmd);
|
||||
|
||||
nla_nest_end(msg, nest);
|
||||
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("nl80211: sending message\n");
|
||||
#endif
|
||||
nl_send_auto_complete(cfg->nl_handle, msg);
|
||||
|
||||
out_free_msg:
|
||||
nlmsg_free(msg);
|
||||
return err;
|
||||
|
||||
nla_put_failure:
|
||||
nlmsg_free(msg);
|
||||
A_DBG("building message failed\n");
|
||||
return 2;
|
||||
}
|
||||
|
||||
int nl80211_tcmd_start(struct tcmd_cfg *cfg)
|
||||
{
|
||||
return nl80211_tcmd_connect(cfg, AR6K_TM_CMD_START);
|
||||
}
|
||||
|
||||
int nl80211_tcmd_stop(struct tcmd_cfg *cfg)
|
||||
{
|
||||
return nl80211_tcmd_connect(cfg,AR6K_TM_CMD_STOP);
|
||||
}
|
||||
|
||||
int nl80211_tcmd_tx(struct tcmd_cfg *cfg, void *buf, int len)
|
||||
{
|
||||
struct nl_msg *msg;
|
||||
struct nlattr *nest;
|
||||
int devidx, err = 0;
|
||||
|
||||
/* CHANGE HERE: you may need to allocate larger messages! */
|
||||
msg = nlmsg_alloc();
|
||||
if (!msg) {
|
||||
A_DBG("failed to allocate netlink message\n");
|
||||
return 2;
|
||||
}
|
||||
|
||||
genlmsg_put(msg, 0, 0, cfg->nl_id, 0,
|
||||
0, NL80211_CMD_TESTMODE, 0);
|
||||
|
||||
devidx = if_nametoindex(cfg->iface);
|
||||
if (devidx) {
|
||||
NLA_PUT_U32(msg, NL80211_ATTR_IFINDEX, devidx);
|
||||
} else {
|
||||
A_DBG("Device not found\n");
|
||||
err = -ENOENT;
|
||||
goto out_free_msg;
|
||||
}
|
||||
|
||||
nest = nla_nest_start(msg, NL80211_ATTR_TESTDATA);
|
||||
if (!nest) {
|
||||
A_DBG("failed to nest\n");
|
||||
err = -1;
|
||||
goto out_free_msg;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_AR6002_REV6
|
||||
NLA_PUT_U32(msg, AR6K_TM_ATTR_CMD, AR6K_TM_CMD_TCMD);
|
||||
#else
|
||||
NLA_PUT_U32(msg, AR6K_TM_ATTR_CMD, cfg->ep);
|
||||
#endif
|
||||
NLA_PUT(msg, AR6K_TM_ATTR_DATA, len, buf);
|
||||
|
||||
nla_nest_end(msg, nest);
|
||||
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("nl80211: sending message\n");
|
||||
#endif
|
||||
nl_send_auto_complete(cfg->nl_handle, msg);
|
||||
|
||||
out_free_msg:
|
||||
nlmsg_free(msg);
|
||||
return err;
|
||||
|
||||
nla_put_failure:
|
||||
nlmsg_free(msg);
|
||||
A_DBG("building message failed\n");
|
||||
return 2;
|
||||
}
|
||||
|
||||
int nl80211_tcmd_rx(struct tcmd_cfg *cfg)
|
||||
{
|
||||
struct nl_cb *cb;
|
||||
int err = 0;
|
||||
|
||||
cb = nl_socket_get_cb(cfg->nl_handle);
|
||||
if (!cb) {
|
||||
fprintf(stderr, "failed to allocate netlink callbacks\n");
|
||||
err = 2;
|
||||
goto out;
|
||||
}
|
||||
|
||||
err = tcmd_set_timer(cfg);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("nl80211: waiting for response\n");
|
||||
#endif
|
||||
while (!cfg->timeout)
|
||||
nl_recvmsgs(cfg->nl_handle, cb);
|
||||
|
||||
if (!cfg->timeout)
|
||||
return tcmd_reset_timer(cfg);
|
||||
else
|
||||
return 0;
|
||||
|
||||
out:
|
||||
return err;
|
||||
}
|
||||
34
feeds/ipq95xx/libtcmd/src/nl80211_drv.h
Executable file
34
feeds/ipq95xx/libtcmd/src/nl80211_drv.h
Executable file
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* Copyright (c) 2011-2012 Qualcomm Atheros Inc. All Rights Reserved.
|
||||
* Qualcomm Atheros Proprietary and Confidential.
|
||||
*/
|
||||
|
||||
#ifndef _NL80211_DRV_H_
|
||||
#define _NL80211_DRV_H_
|
||||
|
||||
#include <netlink/socket.h>
|
||||
|
||||
#if !defined(WIN_AP_HOST) && !defined(MDM)
|
||||
#ifndef sockaddr_storage
|
||||
#define sockaddr_storage __kernel_sockaddr_storage
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#include <netlink/genl/genl.h>
|
||||
#include <netlink/genl/family.h>
|
||||
#include <netlink/genl/ctrl.h>
|
||||
#include <netlink/msg.h>
|
||||
#include <netlink/attr.h>
|
||||
#include <linux/nl80211.h>
|
||||
#include <netinet/in.h>
|
||||
#include "libtcmd.h"
|
||||
|
||||
int nl80211_init(struct tcmd_cfg *cfg);
|
||||
int nl80211_tcmd_tx(struct tcmd_cfg *cfg, void *buf, int len);
|
||||
int nl80211_tcmd_rx(struct tcmd_cfg *cfg);
|
||||
int nl80211_tcmd_start(struct tcmd_cfg *cfg);
|
||||
int nl80211_tcmd_stop(struct tcmd_cfg *cfg);
|
||||
#ifndef CONFIG_AR6002_REV6
|
||||
int nl80211_set_ep(uint32_t *driv_ep, enum tcmd_ep ep);
|
||||
#endif
|
||||
#endif /* _NL80211_DRV_H_ */
|
||||
57
feeds/ipq95xx/libtcmd/src/os.c
Executable file
57
feeds/ipq95xx/libtcmd/src/os.c
Executable file
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
* Copyright (c) 2011-2012, 2018 Qualcomm Technologies, Inc.
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*
|
||||
* 2011-2012 Qualcomm Atheros Inc. All Rights Reserved.
|
||||
* Qualcomm Atheros Proprietary and Confidential.
|
||||
*/
|
||||
|
||||
#include <strings.h>
|
||||
#include "libtcmd.h"
|
||||
#include "os.h"
|
||||
|
||||
#ifdef WIN_AP_HOST
|
||||
#include <linux/errno.h>
|
||||
#endif
|
||||
|
||||
int tcmd_set_timer(struct tcmd_cfg *cfg)
|
||||
{
|
||||
struct itimerspec exp_time;
|
||||
int err;
|
||||
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("setting timer\n");
|
||||
#endif
|
||||
|
||||
bzero(&exp_time, sizeof(exp_time));
|
||||
exp_time.it_value.tv_sec = TCMD_TIMEOUT;
|
||||
err = timer_settime(cfg->timer, 0, &exp_time, NULL);
|
||||
cfg->timeout = false;
|
||||
if (err < 0)
|
||||
return -errno;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int tcmd_reset_timer(struct tcmd_cfg *cfg)
|
||||
{
|
||||
struct itimerspec curr_time;
|
||||
int err;
|
||||
|
||||
err = timer_gettime(cfg->timer, &curr_time);
|
||||
if (err < 0)
|
||||
return -errno;
|
||||
|
||||
if (!curr_time.it_value.tv_sec && !curr_time.it_value.tv_nsec)
|
||||
return -ETIMEDOUT;
|
||||
|
||||
#ifndef WIN_AP_HOST
|
||||
A_DBG("resetting timer\n");
|
||||
#endif
|
||||
|
||||
bzero(&curr_time, sizeof(curr_time));
|
||||
err = timer_settime(cfg->timer, 0, &curr_time, NULL);
|
||||
if (err < 0)
|
||||
return -errno;
|
||||
return 0;
|
||||
}
|
||||
10
feeds/ipq95xx/libtcmd/src/os.h
Executable file
10
feeds/ipq95xx/libtcmd/src/os.h
Executable file
@@ -0,0 +1,10 @@
|
||||
/*
|
||||
* Copyright (c) 2011-2012 Qualcomm Atheros Inc. All Rights Reserved.
|
||||
* Qualcomm Atheros Proprietary and Confidential.
|
||||
*/
|
||||
|
||||
/* private, os-specific things go here */
|
||||
int tcmd_set_timer(struct tcmd_cfg *cfg);
|
||||
/* reset timer and return 0 if still running, return -ETIMEDOUT if the tcmd
|
||||
* timer timed out */
|
||||
int tcmd_reset_timer(struct tcmd_cfg *cfg);
|
||||
72
feeds/ipq95xx/qca-diag/Makefile
Executable file
72
feeds/ipq95xx/qca-diag/Makefile
Executable file
@@ -0,0 +1,72 @@
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=qca-diag
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_VERSION:=12.3
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define Package/qca-diag
|
||||
SECTION:=QCA
|
||||
CATEGORY:=QTI software
|
||||
TITLE:=QCA Linux diag software
|
||||
DEPENDS:=@TARGET_ipq50xx||TARGET_ipq_ipq807x||TARGET_ipq_ipq807x_64||TARGET_ipq_ipq60xx||TARGET_ipq_ipq60xx_64||TARGET_ipq_ipq50xx||TARGET_ipq_ipq50xx_64||TARGET_ipq807x||TARGET_ipq60xx||TARGET_ipq95xx||TARGET_ipq53xx +libpthread
|
||||
endef
|
||||
|
||||
define Package/qca-diag/Description
|
||||
This package contains a Linux qca diag application such as on device logging
|
||||
and socket logging for QCA chipset.
|
||||
This package enables diag messages to log over sockets and also expose
|
||||
interface for other modules to route the diag message to kernel diag
|
||||
stack.
|
||||
endef
|
||||
|
||||
EXTRA_CFLAGS+= -Wno-error=address-of-packed-member
|
||||
|
||||
QCASSDK_CONFIG_OPTS+= TOOL_PATH=$(TOOLCHAIN_DIR)/bin/ \
|
||||
SYS_PATH=$(LINUX_DIR) \
|
||||
TOOLPREFIX=$(TARGET_CROSS) \
|
||||
KVER=$(LINUX_VERSION) \
|
||||
ARCH=$(LINUX_KARCH)
|
||||
|
||||
|
||||
define Build/InstallDev
|
||||
$(INSTALL_DIR) $(STAGING_DIR)/usr/include/qca-diag $(STAGING_DIR)/usr/lib/
|
||||
$(CP) $(PKG_BUILD_DIR)/include/* $(STAGING_DIR)/usr/include/qca-diag/
|
||||
$(CP) $(PKG_BUILD_DIR)/lib/libdiag.so $(STAGING_DIR)/usr/lib/
|
||||
endef
|
||||
|
||||
|
||||
define Package/qca-diag/install
|
||||
$(INSTALL_DIR) $(1)/usr/sbin
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_DIR) $(1)/usr/lib
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/bin/diag_socket_app $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/bin/diag_stress_app $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/bin/registerReboot $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/bin/qld_server $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/bin/diag_mdlog $(1)/usr/sbin/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/lib/libdiag.so $(1)/usr/lib/
|
||||
$(INSTALL_BIN) $(PKG_BUILD_DIR)/qdss_setup.sh $(1)/usr/bin/
|
||||
endef
|
||||
|
||||
|
||||
$(eval $(call BuildPackage,qca-diag))
|
||||
|
||||
define KernelPackage/coresight-stream-sock
|
||||
TITLE:=Add Coresight network stream module
|
||||
KCONFIG:=CONFIG_CORESIGHT_STREAM
|
||||
DEPENDS:=\
|
||||
+kmod-udptunnel4 \
|
||||
+IPV6:kmod-udptunnel6
|
||||
FILES:=$(LINUX_DIR)/drivers/hwtracing/coresight/coresight-stream.ko
|
||||
endef
|
||||
|
||||
define KernelPackage/coresight-stream-sock/description
|
||||
Add Coresight network stream module
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,coresight-stream-sock))
|
||||
1
feeds/ipq95xx/qca-diag/src/Android.mk
Executable file
1
feeds/ipq95xx/qca-diag/src/Android.mk
Executable file
@@ -0,0 +1 @@
|
||||
include $(call all-subdir-makefiles)
|
||||
44
feeds/ipq95xx/qca-diag/src/Makefile
Executable file
44
feeds/ipq95xx/qca-diag/src/Makefile
Executable file
@@ -0,0 +1,44 @@
|
||||
INCLUDE_DIR += include -I src
|
||||
LIB := -lpthread -shared
|
||||
LDFLAGS += -Llib/ -ldiag -lpthread -pie
|
||||
FLAGS = -fPIC -g -DUSE_MUSL
|
||||
EXTRA_CFLAGS = $(TARGET_CFLAGS) $(TARGET_LDFLAGS) $(TARGET_CPPFLAGS) -fstack-protector-all -znow -zrelro -Werror -Wno-error=address-of-packed-member -Wl,--allow-multiple-definition -Wno-error=attributes
|
||||
sample_cliobj := dci_client/diag_dci_sample.c
|
||||
klogobj := klog/diag_klog.c
|
||||
mdobj := mdlog/diag_mdlog.c
|
||||
socketobj := socket_log/diag_socket_log.c
|
||||
uartobj := uart_log/diag_uart_log.c
|
||||
testdiag := test/test_diag.c
|
||||
|
||||
libdiag := src/diag_lsm.c src/diag_lsm_dci.c src/ts_linux.c src/diag_lsm_event.c \
|
||||
src/diag_lsm_log.c src/diag_lsm_msg.c src/diag_lsm_pkt.c \
|
||||
src/diagsvc_malloc.c src/msg_arrays_i.c src/diag_qshrink4_db_parser.c
|
||||
|
||||
all:
|
||||
$(CC) -o libdiag.so $(libdiag) $(TARGET_LDFLAGS) $(FLAGS) $(EXTRA_CFLAGS) -I $(INCLUDE_DIR) $(LIB)
|
||||
mkdir -p lib
|
||||
mv libdiag.so lib/
|
||||
|
||||
$(CC) -o diag_socket_app $(socketobj) $(LDFLAGS) $(EXTRA_CFLAGS) -fpie -I $(INCLUDE_DIR)
|
||||
mkdir -p bin
|
||||
mv diag_socket_app bin/
|
||||
|
||||
$(CC) -o registerReboot registerReboot.c $(LDFLAGS) $(EXTRA_CFLAGS) -fpie -I $(INCLUDE_DIR)
|
||||
mkdir -p bin
|
||||
mv registerReboot bin/
|
||||
|
||||
$(CC) -o qld_server qld_server.c $(LDFLAGS) $(EXTRA_CFLAGS) -fpie -I $(INCLUDE_DIR)
|
||||
mkdir -p bin
|
||||
mv qld_server bin/
|
||||
|
||||
$(CC) -o diag_stress_app $(testdiag) $(LDFLAGS) $(EXTRA_CFLAGS) -fpie -I $(INCLUDE_DIR)
|
||||
mv diag_stress_app bin/
|
||||
|
||||
$(CC) -o diag_mdlog $(mdobj) $(LDFLAGS) $(EXTRA_CFLAGS) -fpie -I $(INCLUDE_DIR)
|
||||
mkdir -p bin
|
||||
mv diag_mdlog bin/
|
||||
|
||||
clean:
|
||||
rm -rf lib/
|
||||
rm -rf bin/
|
||||
rm -rf *.o
|
||||
11
feeds/ipq95xx/qca-diag/src/Makefile.am
Executable file
11
feeds/ipq95xx/qca-diag/src/Makefile.am
Executable file
@@ -0,0 +1,11 @@
|
||||
# Makefile.am - Automake script for diag
|
||||
#
|
||||
ACLOCAL_AMFLAGS = -I m4
|
||||
|
||||
SUBDIRS = src test klog mdlog PktRspTest uart_log dci_sample callback_sample socket_log
|
||||
dist_doc_DATA =
|
||||
docdir = doc
|
||||
|
||||
pkgconfigdir = $(libdir)/pkgconfig
|
||||
pkgconfig_DATA = diag.pc
|
||||
EXTRA_DIST = $(pkgconfig_DATA)
|
||||
28
feeds/ipq95xx/qca-diag/src/PktRspTest/Android.mk
Executable file
28
feeds/ipq95xx/qca-diag/src/PktRspTest/Android.mk
Executable file
@@ -0,0 +1,28 @@
|
||||
################################################################################
|
||||
# @file pkgs/diag/Android.mk
|
||||
# @brief Makefile for building the string library on Android.
|
||||
################################################################################
|
||||
|
||||
LOCAL_PATH:= $(call my-dir)
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
libdiag_includes:= \
|
||||
$(LOCAL_PATH)/../include \
|
||||
$(LOCAL_PATH)/../src \
|
||||
|
||||
LOCAL_C_INCLUDES:= $(libdiag_includes)
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/common/inc
|
||||
|
||||
LOCAL_SRC_FILES:= \
|
||||
PktRspTest.c \
|
||||
|
||||
commonSharedLibraries :=libdiag \
|
||||
|
||||
LOCAL_MODULE:= PktRspTest
|
||||
LOCAL_MODULE_TAGS := optional debug
|
||||
LOCAL_SHARED_LIBRARIES := $(commonSharedLibraries)
|
||||
|
||||
LOCAL_MODULE_OWNER := qcom
|
||||
include $(BUILD_EXECUTABLE)
|
||||
|
||||
23
feeds/ipq95xx/qca-diag/src/PktRspTest/Makefile.am
Executable file
23
feeds/ipq95xx/qca-diag/src/PktRspTest/Makefile.am
Executable file
@@ -0,0 +1,23 @@
|
||||
|
||||
AM_CFLAGS = -Wall \
|
||||
-Wundef \
|
||||
-Wstrict-prototypes \
|
||||
-Wno-trigraphs \
|
||||
-Werror
|
||||
|
||||
AM_CPPFLAGS = -D__packed__= \
|
||||
-DIMAGE_APPS_PROC \
|
||||
-DFEATURE_Q_SINGLE_LINK \
|
||||
-DFEATURE_Q_NO_SELF_QPTR \
|
||||
-DFEATURE_LINUX \
|
||||
-DFEATURE_NATIVELINUX \
|
||||
-DFEATURE_DSM_DUP_ITEMS \
|
||||
-DFEATURE_LE_DIAG \
|
||||
-I../src \
|
||||
-I../include
|
||||
|
||||
bin_PROGRAMS = PktRspTest
|
||||
|
||||
PktRspTest_SOURCES = PktRspTest.c
|
||||
PktRspTest_LDFLAGS = -lpthread
|
||||
PktRspTest_LDADD = ../src/libdiag.la
|
||||
214
feeds/ipq95xx/qca-diag/src/PktRspTest/PktRspTest.c
Executable file
214
feeds/ipq95xx/qca-diag/src/PktRspTest/PktRspTest.c
Executable file
@@ -0,0 +1,214 @@
|
||||
/*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*
|
||||
|
||||
Sample Packet Response Test Application on Diag Interface
|
||||
|
||||
GENERAL DESCRIPTION
|
||||
Contains main implementation of PktRsp Test app. on Apps processor using
|
||||
Diagnostic Services.
|
||||
|
||||
EXTERNALIZED FUNCTIONS
|
||||
None
|
||||
|
||||
INITIALIZATION AND SEQUENCING REQUIREMENTS
|
||||
|
||||
Copyright (c) 2007-2011, 2016 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Qualcomm Technologies Confidential and Proprietary
|
||||
|
||||
*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
EDIT HISTORY FOR MODULE
|
||||
|
||||
This section contains comments describing changes made to the module.
|
||||
Notice that changes are listed in reverse chronological order.
|
||||
|
||||
$Header:
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
3/11/2009 Shalabh Jain and Hiren Bhinde Created
|
||||
4/2/2009 Shalabh Jain and Yash Kharia Adding ftmTest app to the mainline
|
||||
===========================================================================*/
|
||||
|
||||
#include "msg.h"
|
||||
#include "diag_lsm.h"
|
||||
#include "stdio.h"
|
||||
#include "diagpkt.h"
|
||||
#include "string.h"
|
||||
#include <unistd.h>
|
||||
|
||||
/* Subsystem command codes for the test app */
|
||||
#define DIAG_TEST_APP_MT_NO_SUBSYS 143
|
||||
#define DIAG_SUBSYS_TEST_CLIENT_MT 11
|
||||
#define DIAG_TEST_APP_F_75 0x0000
|
||||
#define DIAG_TEST_APP_F_75_test 0x0003
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Local Function declarations */
|
||||
/*===========================================================================*/
|
||||
|
||||
void *dummy_func_no_subsys(void *req_pkt,
|
||||
uint16 pkt_len);
|
||||
|
||||
void *dummy_func_75(void *req_pkt,
|
||||
uint16 pkt_len);
|
||||
|
||||
void sample_parse_request(void *req_pkt, uint16 pkt_len, void *rsp);
|
||||
|
||||
/*===========================================================================*/
|
||||
/* User tables for this client(ftmtest app) */
|
||||
/*===========================================================================*/
|
||||
static const diagpkt_user_table_entry_type test_tbl_1[] =
|
||||
{ /* subsys cmd low, subsys cmd code high, call back function */
|
||||
{DIAG_TEST_APP_MT_NO_SUBSYS, DIAG_TEST_APP_MT_NO_SUBSYS,
|
||||
dummy_func_no_subsys},
|
||||
};
|
||||
|
||||
static const diagpkt_user_table_entry_type test_tbl_2[] =
|
||||
{ /* susbsys_cmd_code lo = 0 , susbsys_cmd_code hi = 0, call back function */
|
||||
{DIAG_TEST_APP_F_75, DIAG_TEST_APP_F_75, dummy_func_75},
|
||||
/* susbsys_cmd_code lo = 3 , susbsys_cmd_code hi = 3, call back function */
|
||||
{DIAG_TEST_APP_F_75_test, DIAG_TEST_APP_F_75_test, dummy_func_75},
|
||||
};
|
||||
|
||||
/*===========================================================================*/
|
||||
/* Main Function. This initializes Diag_LSM, calls the tested APIs and exits. */
|
||||
/*===========================================================================*/
|
||||
int main(void)
|
||||
{
|
||||
boolean bInit_Success = FALSE;
|
||||
|
||||
printf("\n\t\t=====================");
|
||||
printf("\n\t\tStarting FTM Test App");
|
||||
printf("\n\t\t=====================");
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("\n Calling LSM init \n");
|
||||
#endif
|
||||
/* Calling LSM init */
|
||||
bInit_Success = Diag_LSM_Init(NULL);
|
||||
|
||||
if (!bInit_Success) {
|
||||
printf("FTM Test App: Diag_LSM_Init() failed.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("FTM Test App: Diag_LSM_Init succeeded. \n");
|
||||
#endif
|
||||
/* Registering diag packet with no subsystem id.
|
||||
* This is so that an empty request to the app. gets a response back
|
||||
* and we can ensure that the diag is working as well as the app. is
|
||||
* responding subsys id = 255, table = test_tb1_1 ....
|
||||
* To execute on QXDM :: "send_data 143 0 0 0 0 0"
|
||||
*/
|
||||
DIAGPKT_DISPATCH_TABLE_REGISTER(DIAGPKT_NO_SUBSYS_ID, test_tbl_1);
|
||||
|
||||
/* Registering diag packet with no subsystem id. This is so
|
||||
* that an empty request to the app. gets a response back
|
||||
* and we can ensure that the diag is working as well as the app. is
|
||||
* responding subsys id = 11, table = test_tbl_2,
|
||||
* To execute on QXDM :: "send_data 75 11 0 0 0 0 0 0"
|
||||
OR
|
||||
* To execute on QXDM :: "send_data 75 11 3 0 0 0 0 0"
|
||||
*/
|
||||
DIAGPKT_DISPATCH_TABLE_REGISTER(DIAG_SUBSYS_TEST_CLIENT_MT,
|
||||
test_tbl_2);
|
||||
|
||||
/* Adding Sleep of 5 sec so that mask is updated */
|
||||
sleep(5);
|
||||
do {
|
||||
MSG_1(MSG_SSID_DIAG, MSG_LVL_HIGH,
|
||||
"Hello world from FTM Test App.%d", 270938);
|
||||
sleep(1);
|
||||
} while (1);
|
||||
|
||||
/* Now find the DeInit function and call it.
|
||||
* Clean up before exiting
|
||||
*/
|
||||
Diag_LSM_DeInit();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/*===========================================================================*/
|
||||
/* dummy registered functions */
|
||||
/*===========================================================================*/
|
||||
|
||||
void *dummy_func_no_subsys(void *req_pkt, uint16 pkt_len)
|
||||
{
|
||||
void *rsp = NULL;
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("\n ##### FTM Test App: : Inside dummy_func_no_subsys #####\n");
|
||||
#endif
|
||||
/* Allocate the same length as the request. */
|
||||
rsp = diagpkt_alloc(DIAG_TEST_APP_MT_NO_SUBSYS, pkt_len);
|
||||
|
||||
if (rsp != NULL) {
|
||||
memcpy((void *) rsp, (void *) req_pkt, pkt_len);
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("FTM Test APP: diagpkt_alloc succeeded");
|
||||
#endif
|
||||
} else {
|
||||
printf("FTM Test APP: diagpkt_subsys_alloc failed");
|
||||
}
|
||||
|
||||
return rsp;
|
||||
}
|
||||
|
||||
|
||||
void *dummy_func_75(void *req_pkt, uint16 pkt_len)
|
||||
{
|
||||
void *rsp = NULL;
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("\n FTM Test App: Inside dummy_func_75 \n");
|
||||
#endif
|
||||
/* Allocate the same length as the request. */
|
||||
rsp = diagpkt_subsys_alloc(DIAG_TEST_APP_MT_NO_SUBSYS,
|
||||
DIAG_TEST_APP_F_75, 20);
|
||||
/* The request sent in from QXDM is parsed here. The response to each kind of
|
||||
request can be customized. To demonstrate this, we look for codes 1, 2, 3, 4 in
|
||||
the request (in the same order). For example, send_data 75 11 3 0 1 2 3 4 0 0 0.
|
||||
Here a specific response string will be sent back. Any other request is simply
|
||||
echoed back.This is demonstrated in sample_parse_request function
|
||||
*/
|
||||
if (rsp != NULL) {
|
||||
sample_parse_request(req_pkt, pkt_len, rsp);
|
||||
#ifdef DIAG_DEBUG
|
||||
printf("FTM Test App: diagpkt_subsys_alloc succeeded \n");
|
||||
#endif
|
||||
} else
|
||||
printf("FTM Test APP: diagpkt_subsys_alloc failed");
|
||||
|
||||
|
||||
return rsp;
|
||||
}
|
||||
|
||||
/*===========================================================================*/
|
||||
/* dummy parse request function*/
|
||||
/*===========================================================================*/
|
||||
|
||||
void sample_parse_request(void *req_pkt, uint16 pkt_len, void *rsp)
|
||||
{
|
||||
unsigned char *temp = (unsigned char *)req_pkt + 4;
|
||||
int code1, code2, code3, code4;
|
||||
char *rsp_string = "FTM response";
|
||||
|
||||
code1 = (int)(*(char *)temp);
|
||||
temp++;
|
||||
code2 = (int)(*(char *)temp);
|
||||
temp++;
|
||||
code3 = (int)(*(char *)temp);
|
||||
temp++;
|
||||
code4 = (int)(*(char *)temp);
|
||||
|
||||
if (code1 == 1 && code2 == 2 && code3 == 3 && code4 == 4) {
|
||||
memcpy((void *) rsp, (void *) req_pkt, 4);
|
||||
memcpy((void *) ((unsigned char *)rsp+4), (void *) rsp_string,
|
||||
strlen(rsp_string));
|
||||
} else
|
||||
memcpy((void *) (rsp), (void *) req_pkt, pkt_len);
|
||||
|
||||
}
|
||||
10
feeds/ipq95xx/qca-diag/src/autogen.sh
Executable file
10
feeds/ipq95xx/qca-diag/src/autogen.sh
Executable file
@@ -0,0 +1,10 @@
|
||||
#!/bin/sh
|
||||
|
||||
# autogen.sh -- Autotools bootstrapping
|
||||
|
||||
libtoolize --copy --force
|
||||
aclocal &&\
|
||||
autoheader &&\
|
||||
autoconf &&\
|
||||
automake --add-missing --copy
|
||||
|
||||
29
feeds/ipq95xx/qca-diag/src/callback_sample/Android.mk
Executable file
29
feeds/ipq95xx/qca-diag/src/callback_sample/Android.mk
Executable file
@@ -0,0 +1,29 @@
|
||||
################################################################################
|
||||
# @file pkgs/stringl/Android.mk
|
||||
# @brief Makefile for building the string library on Android.
|
||||
################################################################################
|
||||
|
||||
LOCAL_PATH:= $(call my-dir)
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
libdiag_includes:= \
|
||||
$(LOCAL_PATH)/../include \
|
||||
$(LOCAL_PATH)/../src
|
||||
|
||||
LOCAL_C_INCLUDES := $(libdiag_includes)
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/common/inc
|
||||
|
||||
LOCAL_SRC_FILES:= \
|
||||
diag_callback_sample.c
|
||||
|
||||
commonSharedLibraries :=libdiag
|
||||
|
||||
LOCAL_MODULE := diag_callback_sample
|
||||
LOCAL_MODULE_TAGS := optional
|
||||
LOCAL_SHARED_LIBRARIES := $(commonSharedLibraries)
|
||||
LOCAL_SHARED_LIBRARIES += liblog
|
||||
|
||||
LOCAL_MODULE_OWNER := qcom
|
||||
include $(BUILD_EXECUTABLE)
|
||||
|
||||
27
feeds/ipq95xx/qca-diag/src/callback_sample/Makefile.am
Executable file
27
feeds/ipq95xx/qca-diag/src/callback_sample/Makefile.am
Executable file
@@ -0,0 +1,27 @@
|
||||
|
||||
AM_CFLAGS = -Wall \
|
||||
-Wundef \
|
||||
-Wstrict-prototypes \
|
||||
-Wno-trigraphs
|
||||
|
||||
AM_CPPFLAGS = -D__packed__= \
|
||||
-DIMAGE_APPS_PROC \
|
||||
-DFEATURE_Q_SINGLE_LINK \
|
||||
-DFEATURE_Q_NO_SELF_QPTR \
|
||||
-DFEATURE_LINUX \
|
||||
-DFEATURE_NATIVELINUX \
|
||||
-DFEATURE_DSM_DUP_ITEMS \
|
||||
-DFEATURE_LE_DIAG \
|
||||
-I../src \
|
||||
-I../include
|
||||
|
||||
bin_PROGRAMS = diag_callback_sample
|
||||
|
||||
diag_callback_sample_SOURCES = diag_callback_sample.c
|
||||
diag_callback_sample_LDADD = ../src/libdiag.la
|
||||
if USE_GLIB
|
||||
diag_callback_sample_CFLAGS = -DUSE_GLIB @GLIB_CFLAGS@
|
||||
diag_callback_sample_LDFLAGS = -lpthread @GLIB_LIBS@
|
||||
else
|
||||
diag_callback_sample_LDFLAGS = -lpthread -lcutils
|
||||
endif
|
||||
184
feeds/ipq95xx/qca-diag/src/callback_sample/diag_callback_sample.c
Executable file
184
feeds/ipq95xx/qca-diag/src/callback_sample/diag_callback_sample.c
Executable file
@@ -0,0 +1,184 @@
|
||||
/*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*
|
||||
|
||||
Sample Application for Diag Callback Interface
|
||||
|
||||
GENERAL DESCRIPTION
|
||||
Contains sample implementation of Diagnostic Callback APIs.
|
||||
|
||||
EXTERNALIZED FUNCTIONS
|
||||
None
|
||||
|
||||
INITIALIZATION AND SEQUENCING REQUIREMENTS
|
||||
|
||||
Copyright (c) 2012-2014 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Qualcomm Technologies Confidential and Proprietary
|
||||
|
||||
*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include "string.h"
|
||||
#include "malloc.h"
|
||||
#include <unistd.h>
|
||||
#include <fcntl.h>
|
||||
#include <getopt.h>
|
||||
#include <unistd.h>
|
||||
#include "errno.h"
|
||||
#include "msg.h"
|
||||
#include "diag_lsm.h"
|
||||
#include "stdio.h"
|
||||
#include "diagpkt.h"
|
||||
#include "diag_lsmi.h"
|
||||
#include "diag_shared_i.h"
|
||||
|
||||
#define REQ_LOOPBACK_LEN 7
|
||||
#define REQ_STRESSTEST_LEN 24
|
||||
|
||||
/* Callback for the receiving Diag data */
|
||||
int process_diag_data(unsigned char *ptr, int len, void *context_data)
|
||||
{
|
||||
int i;
|
||||
if (!ptr) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (context_data) {
|
||||
if (*(int *)context_data == MSM) {
|
||||
DIAG_LOGE("diag_callback_sample: Received data of len %d from MSM", len);
|
||||
} else if (*(int *)context_data == MDM) {
|
||||
DIAG_LOGE("diag_callback_sample: Received data of len %d from MDM", len);
|
||||
} else {
|
||||
DIAG_LOGE("diag_callback_sample: Received data of len %d from unknown proc %d", len, *(int *)context_data);
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < len; i++) {
|
||||
if (i % 8 == 0) {
|
||||
DIAG_LOGE("\n ");
|
||||
}
|
||||
DIAG_LOGE("%02x ", ptr[i]);
|
||||
}
|
||||
DIAG_LOGE("\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Helper function to check if MDM is supported */
|
||||
static uint8 is_mdm_supported()
|
||||
{
|
||||
uint16 remote_mask = 0;
|
||||
uint8 err = 0;
|
||||
err = diag_has_remote_device(&remote_mask);
|
||||
if (err != 1) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to check for MDM support, err: %d\n", errno);
|
||||
return 0;
|
||||
}
|
||||
return (remote_mask & MDM);
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
int err = 0;
|
||||
int data_primary = MSM;
|
||||
int data_remote = MDM;
|
||||
uint8 mdm_support = 0;
|
||||
boolean status = FALSE;
|
||||
unsigned char req_modem_loopback[REQ_LOOPBACK_LEN] =
|
||||
{ 75, 18, 41, 0, 1, 2, 3 };
|
||||
unsigned char req_modem_msg_stress_test[REQ_STRESSTEST_LEN] =
|
||||
{ 75, 18, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
|
||||
unsigned char req_adsp_log_stress_test[REQ_STRESSTEST_LEN] =
|
||||
{ 75, 18, 7, 0, 1, 0, 0, 0, 16, 1, 1, 0, 0, 1, 0, 0, 5, 0, 0, 0, 10, 0, 0, 0 };
|
||||
|
||||
status = Diag_LSM_Init(NULL);
|
||||
if (!status) {
|
||||
DIAG_LOGE("diag_callback_sample: Diag LSM Init failed, exiting... err: %d\n", errno);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
/* Register the callback function for receiving data from MSM */
|
||||
diag_register_callback(process_diag_data, &data_primary);
|
||||
|
||||
/* Check if MDM is supported, If yes, register for MDM callback too */
|
||||
mdm_support = is_mdm_supported();
|
||||
if (mdm_support)
|
||||
diag_register_remote_callback(process_diag_data, MDM, &data_remote);
|
||||
|
||||
/* Switch to Callback mode to receive Diag data in this application */
|
||||
diag_switch_logging(CALLBACK_MODE, NULL);
|
||||
|
||||
/*
|
||||
* You can now send requests to the processors. The response, and any
|
||||
* log, event or F3s will be sent via the callback function.
|
||||
*/
|
||||
DIAG_LOGE("diag_callback_sample: Sending Modem loopback request to MSM\n");
|
||||
err = diag_callback_send_data(MSM, req_modem_loopback, REQ_LOOPBACK_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send Modem loopback request to MSM\n");
|
||||
} else {
|
||||
sleep(2);
|
||||
}
|
||||
|
||||
DIAG_LOGE("diag_callback_sample: Sending Modem Message Stress Test to MSM\n");
|
||||
err = diag_callback_send_data(MSM, req_modem_msg_stress_test, REQ_STRESSTEST_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send Modem Message Stress Test to MSM\n");
|
||||
} else {
|
||||
sleep(30);
|
||||
}
|
||||
|
||||
DIAG_LOGE("diag_callback_sample: Sending ADSP Log Stress Test to MSM\n");
|
||||
err = diag_callback_send_data(MSM, req_adsp_log_stress_test, REQ_STRESSTEST_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send ADSP Log Stress Test to MSM\n");
|
||||
} else {
|
||||
sleep(30);
|
||||
}
|
||||
|
||||
if (!mdm_support)
|
||||
goto finish;
|
||||
|
||||
DIAG_LOGE("diag_callback_sample: Sending Modem loopback request to MDM\n");
|
||||
/* If MDM is supported, send the requests to MDM ASIC as well */
|
||||
err = diag_callback_send_data(MDM, req_modem_loopback, REQ_LOOPBACK_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send Modem loopback request to MDM\n");
|
||||
} else {
|
||||
sleep(2);
|
||||
}
|
||||
|
||||
DIAG_LOGE("diag_callback_sample: Sending Modem Message Stress Test to MDM\n");
|
||||
err = diag_callback_send_data(MDM, req_modem_msg_stress_test, REQ_STRESSTEST_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send Modem Message Stress Test to MDM\n");
|
||||
} else {
|
||||
sleep(30);
|
||||
}
|
||||
|
||||
DIAG_LOGE("diag_callback_sample: Sending ADSP Log Stress Test to MDM\n");
|
||||
err = diag_callback_send_data(MDM, req_adsp_log_stress_test, REQ_STRESSTEST_LEN);
|
||||
if (err) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to send ADSP Log Stress Test to MDM\n");
|
||||
} else {
|
||||
sleep(30);
|
||||
}
|
||||
|
||||
finish:
|
||||
/*
|
||||
* When you are done using the Callback Mode, it is highly recommended
|
||||
* that you switch back to USB Mode.
|
||||
*/
|
||||
diag_switch_logging(USB_MODE, NULL);
|
||||
|
||||
/* Release the handle to Diag*/
|
||||
status = Diag_LSM_DeInit();
|
||||
if (!status) {
|
||||
DIAG_LOGE("diag_callback_sample: Unable to close handle to diag driver, err: %d\n", errno);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
110
feeds/ipq95xx/qca-diag/src/configure.ac
Executable file
110
feeds/ipq95xx/qca-diag/src/configure.ac
Executable file
@@ -0,0 +1,110 @@
|
||||
# -*- Autoconf -*-
|
||||
|
||||
# configure.ac -- Autoconf script for diag
|
||||
#
|
||||
|
||||
# Process this file with autoconf to produce a configure script.
|
||||
|
||||
AC_PREREQ(2.61)
|
||||
AC_INIT([diag],
|
||||
1.0.0)
|
||||
AM_INIT_AUTOMAKE([foreign])
|
||||
AM_MAINTAINER_MODE
|
||||
AC_CONFIG_SRCDIR([src/diag_lsm.c])
|
||||
AC_CONFIG_HEADER([config.h])
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
|
||||
DIAG_LIBRARY_NAME=diag
|
||||
|
||||
#release versioning
|
||||
DIAG_MAJOR_VERSION=1
|
||||
DIAG_MINOR_VERSION=0
|
||||
DIAG_MICRO_VERSION=0
|
||||
|
||||
DIAG_LIBRARY_VERSION=1:0:0
|
||||
AC_SUBST(DIAG_LIBRARY_VERSION)
|
||||
|
||||
PACKAGE=$DIAG_LIBRARY_NAME
|
||||
AC_SUBST(DIAG_LIBRARY_NAME)
|
||||
|
||||
DIAG_VERSION=$DIAG_MAJOR_VERSION.$DIAG_MINOR_VERSION.$DIAG_MICRO_VERSION
|
||||
DIAG_RELEASE=$DIAG_MAJOR_VERSION.$DIAG_MINOR_VERSION
|
||||
AC_SUBST(DIAG_RELEASE)
|
||||
AC_SUBST(DIAG_VERSION)
|
||||
|
||||
VERSION=$DIAG_VERSION
|
||||
|
||||
LT_INIT
|
||||
AM_PROG_LIBTOOL
|
||||
# Checks for programs.
|
||||
AC_PROG_CC
|
||||
AM_PROG_CC_C_O
|
||||
AC_PROG_LIBTOOL
|
||||
AC_PROG_AWK
|
||||
AC_PROG_CPP
|
||||
AC_PROG_INSTALL
|
||||
AC_PROG_LN_S
|
||||
AC_PROG_MAKE_SET
|
||||
PKG_PROG_PKG_CONFIG
|
||||
|
||||
AC_ARG_WITH([kernel],
|
||||
AC_HELP_STRING([--with-kernel=@<:@dir@:>@],
|
||||
[Specify the location of the Linux kernel headers]),
|
||||
[kerneldir=$withval],
|
||||
with_kernel=no)
|
||||
|
||||
if test "x$with_kernel" != "xno"; then
|
||||
CFLAGS="${CFLAGS} -I${kerneldir}/include -I${kerneldir}/arch/arm/include"
|
||||
fi
|
||||
|
||||
AC_ARG_WITH([glib],
|
||||
AC_HELP_STRING([--with-glib],
|
||||
[enable glib, building HLOS systems which use glib]))
|
||||
|
||||
if (test "x${with_glib}" = "xyes"); then
|
||||
AC_DEFINE(ENABLE_USEGLIB, 1, [Define if HLOS systems uses glib])
|
||||
PKG_CHECK_MODULES(GTHREAD, gthread-2.0 >= 2.16, dummy=yes,
|
||||
AC_MSG_ERROR(GThread >= 2.16 is required))
|
||||
PKG_CHECK_MODULES(GLIB, glib-2.0 >= 2.16, dummy=yes,
|
||||
AC_MSG_ERROR(GLib >= 2.16 is required))
|
||||
GLIB_CFLAGS="$GLIB_CFLAGS $GTHREAD_CFLAGS"
|
||||
GLIB_LIBS="$GLIB_LIBS $GTHREAD_LIBS"
|
||||
|
||||
AC_SUBST(GLIB_CFLAGS)
|
||||
AC_SUBST(GLIB_LIBS)
|
||||
fi
|
||||
|
||||
AC_ARG_WITH([common_includes],
|
||||
AC_HELP_STRING([--with-common-includes=@<:@dir@:>@],
|
||||
[Specify the location of the common headers]),
|
||||
[common_incdir=$withval],
|
||||
with_common_includes=no)
|
||||
|
||||
if test "x$with_common_includes" != "xno"; then
|
||||
CFLAGS="${CFLAGS} -I${common_incdir}"
|
||||
fi
|
||||
|
||||
AM_CONDITIONAL(USE_GLIB, test "x${with_glib}" = "xyes")
|
||||
|
||||
# Checks for libraries.
|
||||
PKG_CHECK_MODULES([TGENOFF], [time-genoff])
|
||||
AC_SUBST([TGENOFF_CFLAGS])
|
||||
AC_SUBST([TGENOFF_LIBS])
|
||||
|
||||
AC_SUBST([CFLAGS])
|
||||
AC_SUBST([CC])
|
||||
AC_CONFIG_FILES([ \
|
||||
Makefile \
|
||||
src/Makefile \
|
||||
test/Makefile \
|
||||
klog/Makefile \
|
||||
mdlog/Makefile \
|
||||
uart_log/Makefile \
|
||||
PktRspTest/Makefile \
|
||||
dci_sample/Makefile \
|
||||
callback_sample/Makefile \
|
||||
socket_log/Makefile \
|
||||
diag.pc
|
||||
])
|
||||
AC_OUTPUT
|
||||
|
||||
29
feeds/ipq95xx/qca-diag/src/dci_sample/Android.mk
Executable file
29
feeds/ipq95xx/qca-diag/src/dci_sample/Android.mk
Executable file
@@ -0,0 +1,29 @@
|
||||
################################################################################
|
||||
# @file pkgs/stringl/Android.mk
|
||||
# @brief Makefile for building the string library on Android.
|
||||
################################################################################
|
||||
|
||||
LOCAL_PATH:= $(call my-dir)
|
||||
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
libdiag_includes:= \
|
||||
$(LOCAL_PATH)/../include \
|
||||
$(LOCAL_PATH)/../src
|
||||
|
||||
LOCAL_C_INCLUDES := $(libdiag_includes)
|
||||
LOCAL_C_INCLUDES += $(TARGET_OUT_HEADERS)/common/inc
|
||||
|
||||
LOCAL_SRC_FILES:= \
|
||||
diag_dci_sample.c
|
||||
|
||||
commonSharedLibraries :=libdiag
|
||||
|
||||
LOCAL_MODULE := diag_dci_sample
|
||||
LOCAL_MODULE_TAGS := optional
|
||||
LOCAL_SHARED_LIBRARIES := $(commonSharedLibraries)
|
||||
LOCAL_SHARED_LIBRARIES += liblog
|
||||
|
||||
LOCAL_MODULE_OWNER := qcom
|
||||
include $(BUILD_EXECUTABLE)
|
||||
|
||||
28
feeds/ipq95xx/qca-diag/src/dci_sample/Makefile.am
Executable file
28
feeds/ipq95xx/qca-diag/src/dci_sample/Makefile.am
Executable file
@@ -0,0 +1,28 @@
|
||||
|
||||
AM_CFLAGS = -Wall \
|
||||
-Wundef \
|
||||
-Wstrict-prototypes \
|
||||
-Wno-trigraphs
|
||||
|
||||
AM_CPPFLAGS = -D__packed__= \
|
||||
-DIMAGE_APPS_PROC \
|
||||
-DFEATURE_Q_SINGLE_LINK \
|
||||
-DFEATURE_Q_NO_SELF_QPTR \
|
||||
-DFEATURE_LINUX \
|
||||
-DFEATURE_NATIVELINUX \
|
||||
-DFEATURE_DSM_DUP_ITEMS \
|
||||
-DFEATURE_LE_DIAG \
|
||||
-I../src \
|
||||
-I../include \
|
||||
-I$(WORKSPACE)/common/inc
|
||||
|
||||
bin_PROGRAMS = diag_dci_sample
|
||||
|
||||
diag_dci_sample_SOURCES = diag_dci_sample.c
|
||||
diag_dci_sample_LDADD = ../src/libdiag.la
|
||||
if USE_GLIB
|
||||
diag_dci_sample_CFLAGS = -DUSE_GLIB @GLIB_CFLAGS@
|
||||
diag_dci_sample_LDFLAGS = -lpthread @GLIB_LIBS@
|
||||
else
|
||||
diag_dci_sample_LDFLAGS = -lpthread -lcutils
|
||||
endif
|
||||
590
feeds/ipq95xx/qca-diag/src/dci_sample/diag_dci_sample.c
Executable file
590
feeds/ipq95xx/qca-diag/src/dci_sample/diag_dci_sample.c
Executable file
@@ -0,0 +1,590 @@
|
||||
|
||||
/*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*
|
||||
|
||||
Sample Application for Diag Consumer Interface
|
||||
|
||||
GENERAL DESCRIPTION
|
||||
This is a sample application to demonstrate using Diag Consumer Interface APIs.
|
||||
|
||||
EXTERNALIZED FUNCTIONS
|
||||
None
|
||||
|
||||
INITIALIZATION AND SEQUENCING REQUIREMENTS
|
||||
|
||||
|
||||
Copyright (c) 2013-2016 Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
Author: Ravi Aravamudhan
|
||||
Source: Jamila Murabbi
|
||||
*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*/
|
||||
|
||||
/*===========================================================================*/
|
||||
|
||||
#include "event.h"
|
||||
#include "msg.h"
|
||||
#include "log.h"
|
||||
#include "diag_lsm.h"
|
||||
#include "diag_lsmi.h"
|
||||
#include "diag_lsm_dci.h"
|
||||
#include "diag_shared_i.h"
|
||||
#include "stdio.h"
|
||||
#include "string.h"
|
||||
#include "malloc.h"
|
||||
#include "diagpkt.h"
|
||||
#include "../src/diagdiag.h" /* For macros used in this sample. */
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#include <pthread.h>
|
||||
#include <sys/klog.h>
|
||||
#include <sys/stat.h>
|
||||
#include <stdlib.h>
|
||||
#include <getopt.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#define TOTAL_LOG_CODES 1
|
||||
#define TOTAL_LOG_CODES_APPS 3
|
||||
#define TOTAL_EVENT_CODES 4
|
||||
#define DIAG_SAMPLE_SIGNAL SIGRTMIN + 15
|
||||
|
||||
#define DIAG_CMD_CODE_IDX 0
|
||||
#define DIAG_SUBSYS_ID_IDX 1
|
||||
#define DIAG_STRESS_TEST_OP_IDX 8
|
||||
|
||||
/* Structure for Log packet parsing*/
|
||||
struct log_code_name_type {
|
||||
int log_code;
|
||||
char *name;
|
||||
};
|
||||
|
||||
struct event_code_name_type {
|
||||
event_id_enum_type event_code;
|
||||
char *name;
|
||||
};
|
||||
|
||||
/* Channel proc set to MSM by default */
|
||||
static int channel = MSM;
|
||||
|
||||
/* Set a sample log codes */
|
||||
struct log_code_name_type log_codes[TOTAL_LOG_CODES] = {
|
||||
{ LOG_DIAG_STRESS_TEST_C, "Diag Log Stress Test" }
|
||||
};
|
||||
|
||||
struct log_code_name_type log_codes_apps[TOTAL_LOG_CODES_APPS] = {
|
||||
{ LOG_WMS_SET_ROUTES_C, "WMS Set Routes" },
|
||||
{ LOG_DATA_PROTOCOL_LOGGING_C, "DPL Log Messages" },
|
||||
{ LOG_WMS_READ_C, "WMS Read" }
|
||||
};
|
||||
|
||||
struct event_code_name_type event_codes[TOTAL_EVENT_CODES] = {
|
||||
{ EVENT_DIAG_STRESS_TEST_NO_PAYLOAD, "Diag Event Stress Test" },
|
||||
{ EVENT_DIAG_STRESS_TEST_WITH_PAYLOAD, "Diag Event w/ Payload Stress Test"},
|
||||
{ EVENT_DIAG_STRESS_TEST_COMPLETED, "Diag Event Stress Test Complete"},
|
||||
{ EVENT_DIAG_DROP_DEBUG, "Diag Event Drop Debug"}
|
||||
};
|
||||
|
||||
/* Set flag to print the bytes */
|
||||
static inline void print_bytes(unsigned char *buf, int len, int flag)
|
||||
{
|
||||
int i = 0;
|
||||
if (!flag)
|
||||
return;
|
||||
if (!buf || len <= 0)
|
||||
return;
|
||||
for (i = 0; i < len; i++) {
|
||||
if(i % 8 == 0)
|
||||
printf("\n");
|
||||
printf(" %02x ", buf[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
static void usage(char *progname)
|
||||
{
|
||||
printf("\n Usage for %s:\n", progname);
|
||||
printf("\n-c --channel name:\t Designate the channel name for all operations 0 - MSM and 1 - MDM\n");
|
||||
exit(0);
|
||||
}
|
||||
|
||||
static void parse_args(int argc, char **argv)
|
||||
{
|
||||
int command, proc_id;
|
||||
int file_num = 0;
|
||||
struct option longopts[] =
|
||||
{
|
||||
{ "channelname", 1, NULL, 'c'},
|
||||
{ "help", 0, NULL, 'h'},
|
||||
};
|
||||
|
||||
while ((command = getopt_long(argc, argv, "c:h", longopts, NULL))
|
||||
!= -1) {
|
||||
switch (command) {
|
||||
case 'c':
|
||||
proc_id = atol(optarg);
|
||||
if (proc_id >= MSM && proc_id <= MDM)
|
||||
channel = proc_id;
|
||||
break;
|
||||
case 'h':
|
||||
default:
|
||||
usage(argv[0]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Signal handler that handles the change in DCI channel */
|
||||
void notify_handler(int signal, siginfo_t *info, void *unused)
|
||||
{
|
||||
(void)unused;
|
||||
|
||||
if (info) {
|
||||
int err;
|
||||
diag_dci_peripherals list = 0;
|
||||
|
||||
DIAG_LOGE("diag: In %s, signal %d received from kernel, data is: %x\n",
|
||||
__func__, signal, info->si_int);
|
||||
|
||||
if (info->si_int & DIAG_STATUS_OPEN) {
|
||||
if (info->si_int & DIAG_CON_MPSS) {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_OPEN on DIAG_CON_MPSS\n");
|
||||
} else if (info->si_int & DIAG_CON_LPASS) {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_OPEN on DIAG_CON_LPASS\n");
|
||||
} else {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_OPEN on unknown peripheral\n");
|
||||
}
|
||||
} else if (info->si_int & DIAG_STATUS_CLOSED) {
|
||||
if (info->si_int & DIAG_CON_MPSS) {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_CLOSED on DIAG_CON_MPSS\n");
|
||||
} else if (info->si_int & DIAG_CON_LPASS) {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_CLOSED on DIAG_CON_LPASS\n");
|
||||
} else {
|
||||
DIAG_LOGE("diag: DIAG_STATUS_CLOSED on unknown peripheral\n");
|
||||
}
|
||||
}
|
||||
err = diag_get_dci_support_list_proc(MSM, &list);
|
||||
if (err != DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE("diag: could not get support list, err: %d\n", err);
|
||||
}
|
||||
/* This will print out all peripherals supporting DCI */
|
||||
if (list & DIAG_CON_MPSS)
|
||||
DIAG_LOGE("diag: Modem supports DCI\n");
|
||||
if (list & DIAG_CON_LPASS)
|
||||
DIAG_LOGE("diag: LPASS supports DCI\n");
|
||||
if (list & DIAG_CON_WCNSS)
|
||||
DIAG_LOGE("diag: RIVA supports DCI\n");
|
||||
if (list & DIAG_CON_APSS)
|
||||
DIAG_LOGE("diag: APSS supports DCI\n");
|
||||
if (!list)
|
||||
DIAG_LOGE("diag: No current dci support\n");
|
||||
} else {
|
||||
DIAG_LOGE("diag: In %s, signal %d received from kernel, but no info value, info: 0x%p\n",
|
||||
__func__, signal, info);
|
||||
}
|
||||
}
|
||||
|
||||
/* Singal Handler that will be fired when we receive DCI data */
|
||||
void dci_data_handler(int signal)
|
||||
{
|
||||
(void)signal;
|
||||
|
||||
/* Do something here when you receive DCI data. */
|
||||
|
||||
/* This is usually for holding wakelocks when the
|
||||
clients are running in Diag Non Real Time mode
|
||||
or when they know the Apps processor is in deep
|
||||
sleep but they still need to process DCI data.
|
||||
|
||||
Please Note: Wakelocks must be released
|
||||
after processing the data in the respective
|
||||
response/log/event handler. Failure to do so
|
||||
will affect the power consumption of the Apps
|
||||
processor. */
|
||||
}
|
||||
|
||||
void process_dci_log_stream(unsigned char *ptr, int len)
|
||||
{
|
||||
int i, found = 0;
|
||||
for (i = 0; i < TOTAL_LOG_CODES; i++) {
|
||||
if (*(uint16 *)(ptr + 2) == log_codes[i].log_code) {
|
||||
DIAG_LOGE(" Received a Log of type %s, length = %d\n", log_codes[i].name, len);
|
||||
found = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
for (i = 0; i < TOTAL_LOG_CODES_APPS && !found; i++) {
|
||||
if (*(uint16 *)(ptr + 2) == log_codes_apps[i].log_code) {
|
||||
DIAG_LOGE(" Received a Log of type %s, length = %d\n", log_codes_apps[i].name, len);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (*(uint8 *)ptr == 0x98) {
|
||||
DIAG_LOGE(" Received an EXT API LOG PKT %d bytes\n", len);
|
||||
print_bytes(ptr, len, FALSE);
|
||||
}
|
||||
|
||||
print_bytes(ptr, len, FALSE);
|
||||
}
|
||||
|
||||
void process_dci_event_stream(unsigned char *ptr, int len)
|
||||
{
|
||||
if (*(uint8 *)ptr == 0x98) {
|
||||
DIAG_LOGE(" Received an EXT API EVENT PKT %d bytes\n", len);
|
||||
print_bytes(ptr, len, FALSE);
|
||||
return;
|
||||
}
|
||||
DIAG_LOGE(" Received an event of size %d bytes\n", len);
|
||||
print_bytes(ptr, len, FALSE);
|
||||
}
|
||||
|
||||
void process_response(unsigned char *ptr, int len, void *data_ptr)
|
||||
{
|
||||
int i = 0;
|
||||
uint8 operation = 0;
|
||||
(void)data_ptr;
|
||||
|
||||
if (!ptr || len < 0)
|
||||
return;
|
||||
|
||||
DIAG_LOGE(" Received Response of size %d bytes.\n", len);
|
||||
print_bytes(ptr, len, TRUE);
|
||||
|
||||
/* Parsing Logic for the response - Based on the request in this sample */
|
||||
if (len <= DIAG_STRESS_TEST_OP_IDX)
|
||||
return;
|
||||
|
||||
operation = ptr[DIAG_STRESS_TEST_OP_IDX];
|
||||
if (ptr[DIAG_CMD_CODE_IDX] == DIAG_SUBSYS_CMD_F &&
|
||||
ptr[DIAG_SUBSYS_ID_IDX] == DIAG_SUBSYS_DIAG_SERV) {
|
||||
DIAG_LOGE(" Command Code: Diag\n");
|
||||
DIAG_LOGE(" Subsystem ID: Diag\n");
|
||||
if (operation <= DIAGDIAG_STRESS_TEST_ERR_FATAL) {
|
||||
DIAG_LOGE(" Test for: F3s\n");
|
||||
} else if (operation == DIAGDIAG_STRESS_TEST_LOG) {
|
||||
DIAG_LOGE(" Test for: Logs\n");
|
||||
} else if (operation == DIAGDIAG_STRESS_TEST_EVENT_NO_PAYLOAD) {
|
||||
DIAG_LOGE(" Test for: Events without payload\n");
|
||||
} else if (operation == DIAGDIAG_STRESS_TEST_EVENT_WITH_PAYLOAD) {
|
||||
DIAG_LOGE(" Test for: Events with payload\n");
|
||||
}
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
/* Main Function. This demonstrates using the DCI APIs defined in diag_lsm_dci.h*/
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
int err, client_id;
|
||||
int signal_type = SIGCONT;
|
||||
boolean bInit_success = FALSE;
|
||||
diag_dci_peripherals list = DIAG_CON_MPSS | DIAG_CON_APSS | DIAG_CON_LPASS;
|
||||
struct diag_dci_health_stats *dci_health_stats; /* To collect DCI Health Statistics */
|
||||
unsigned char *dci_rsp_pkt = NULL;
|
||||
(void)argc;
|
||||
(void)argv;
|
||||
|
||||
/* Signal handling to handle SSR */
|
||||
struct sigaction notify_action;
|
||||
sigemptyset(¬ify_action.sa_mask);
|
||||
notify_action.sa_sigaction = notify_handler;
|
||||
/* Use SA_SIGINFO to denote we are expecting data with the signal */
|
||||
notify_action.sa_flags = SA_SIGINFO;
|
||||
sigaction(signal_type, ¬ify_action, NULL);
|
||||
|
||||
/* Signal handling for DCI Data */
|
||||
struct sigaction dci_data_action;
|
||||
sigemptyset(&dci_data_action.sa_mask);
|
||||
dci_data_action.sa_handler = dci_data_handler;
|
||||
dci_data_action.sa_flags = 0;
|
||||
sigaction(DIAG_SAMPLE_SIGNAL, &dci_data_action, NULL);
|
||||
|
||||
parse_args(argc, argv);
|
||||
/* Registering with Diag which gives the client a handle to the Diag driver */
|
||||
bInit_success = Diag_LSM_Init(NULL);
|
||||
if (!bInit_success) {
|
||||
DIAG_LOGE(" Couldn't register with Diag LSM, errno: %d\n", errno);
|
||||
return -1;
|
||||
}
|
||||
|
||||
dci_rsp_pkt = (unsigned char *)malloc(DIAG_MAX_RX_PKT_SIZ);
|
||||
if (!dci_rsp_pkt) {
|
||||
DIAG_LOGE(" Unable to allocate memory for DCI rsp pkt, errno: %d", errno);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Registering with DCI - This assigns a client ID */
|
||||
/* Channel 0 - MSM, 1 - MDM */
|
||||
err = diag_register_dci_client(&client_id, &list, channel, &signal_type);
|
||||
if (err != DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE(" Could not register with DCI, err: %d, errno: %d\n", err, errno);
|
||||
free(dci_rsp_pkt);
|
||||
return -1;
|
||||
} else
|
||||
DIAG_LOGE(" Successfully registered with DCI, client ID = %d\n", client_id);
|
||||
|
||||
err = diag_register_dci_signal_data(client_id, DIAG_SAMPLE_SIGNAL);
|
||||
if (err != DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE(" Could not register signal for DCI Data, err: %d, errno: %d\n", err, errno);
|
||||
free(dci_rsp_pkt);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Getting supported Peripherals list*/
|
||||
DIAG_LOGE(" DCI Status on Processors:\n");
|
||||
err = diag_get_dci_support_list_proc(channel, &list);
|
||||
if (err != DIAG_DCI_NO_ERROR) {
|
||||
printf(" Could not get support list, err: %d, errno: %d\n", err, errno);
|
||||
free(dci_rsp_pkt);
|
||||
return -1;
|
||||
}
|
||||
DIAG_LOGE(" MPSS:\t ");
|
||||
DIAG_LOGE((list & DIAG_CON_MPSS) ? "UP\n" : "DOWN\n");
|
||||
DIAG_LOGE(" LPASS:\t ");
|
||||
DIAG_LOGE((list & DIAG_CON_LPASS) ? "UP\n" : "DOWN\n");
|
||||
DIAG_LOGE(" WCNSS:\t ");
|
||||
DIAG_LOGE((list & DIAG_CON_WCNSS) ? "UP\n" : "DOWN\n");
|
||||
DIAG_LOGE(" APSS:\t ");
|
||||
DIAG_LOGE((list & DIAG_CON_APSS) ? "UP\n" : "DOWN\n");
|
||||
|
||||
|
||||
/* Initializing Log and Event streaming by registering
|
||||
listeners - This is required to receive Logs and Events */
|
||||
DIAG_LOGE(" Opening Data Stream, registering listeners\n");
|
||||
err = diag_register_dci_stream_proc(client_id, process_dci_log_stream, process_dci_event_stream);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Unable to register DCI stream, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
printf("\n");
|
||||
|
||||
DIAG_LOGE(" Sending Asynchronous Command \n");
|
||||
/* Diag Log stress test command - one Log packet comes out every second */
|
||||
unsigned char buf[24] = {75, 18, 0, 0, 1, 0, 0, 0, 16, 1, 1, 0, 0, 1, 0, 0, 232, 3, 0, 0, 1, 0, 0, 0};
|
||||
err = diag_send_dci_async_req(client_id, buf, 24, dci_rsp_pkt, DIAG_MAX_RX_PKT_SIZ, &process_response, NULL);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SEND_REQUEST_ASYNC to peripheral %d\n", err);
|
||||
|
||||
sleep(1);
|
||||
printf("\n");
|
||||
|
||||
/* Setting Log masks ----------------------------
|
||||
0x115F - Diag Stress Test Log
|
||||
-------------------------------------------*/
|
||||
DIAG_LOGE(" Setting Log masks\n");
|
||||
DIAG_LOGE(" [0x115F] Diag Stress Test Log\n");
|
||||
uint16 log_codes_array[TOTAL_LOG_CODES] = { LOG_DIAG_STRESS_TEST_C };
|
||||
err = diag_log_stream_config(client_id, ENABLE, log_codes_array, TOTAL_LOG_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SET_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Putting the thread to sleep for 30 seconds. The client must sleep for the time it
|
||||
wants to receive logs/events/command responses */
|
||||
sleep(30);
|
||||
printf("\n");
|
||||
|
||||
/* Display Health Statistics */
|
||||
DIAG_LOGE(" Modem Health Statistics on the Apps processor:\n");
|
||||
dci_health_stats = malloc(sizeof(struct diag_dci_health_stats));
|
||||
if (!dci_health_stats) {
|
||||
DIAG_LOGE(" Unable to allocate memory for DCI health stats, errno: %d", errno);
|
||||
free(dci_rsp_pkt);
|
||||
return -1;
|
||||
}
|
||||
|
||||
err = diag_get_health_stats_proc(client_id, dci_health_stats, DIAG_MODEM_PROC);
|
||||
if (err == DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE(" Log Drop Count for Modem:\t%d\n", dci_health_stats->dropped_logs);
|
||||
DIAG_LOGE(" Log Total Count for Modem:\t%d\n", dci_health_stats->received_logs);
|
||||
DIAG_LOGE(" Event Drop Count for Modem:\t%d\n", dci_health_stats->dropped_events);
|
||||
DIAG_LOGE(" Event Total Count for Modem:\t%d\n", dci_health_stats->received_events);
|
||||
} else
|
||||
DIAG_LOGE(" Error in collecting statistics, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
sleep(1);
|
||||
printf("\n");
|
||||
|
||||
/* Clearing these log masks ------------------------
|
||||
0x115F - Diag Stress Test Log
|
||||
---------------------------------------------------- */
|
||||
DIAG_LOGE(" Clearing log masks\n");
|
||||
DIAG_LOGE(" [0x115F] Diag Stress Test Log\n");
|
||||
err = diag_log_stream_config(client_id, DISABLE, log_codes_array, TOTAL_LOG_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending CLEAR_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
sleep(5);
|
||||
printf("\n");
|
||||
|
||||
/* Setting Log masks ----------------------------
|
||||
0x117B - WMS Set Routes
|
||||
0x11EB - DPL Log Messages
|
||||
0x1160 - WMS Read
|
||||
-------------------------------------------*/
|
||||
DIAG_LOGE(" *** To generate the following logs on APSS, please run the test_diag app\n");
|
||||
DIAG_LOGE(" Setting Log masks\n");
|
||||
DIAG_LOGE(" [0x117B] WMS Set Routes\n");
|
||||
DIAG_LOGE(" [0x11EB] DPL Log Messages\n");
|
||||
DIAG_LOGE(" [0x1160] WMS Read\n");
|
||||
|
||||
uint16 log_codes_array_apps[TOTAL_LOG_CODES_APPS] = { LOG_WMS_SET_ROUTES_C,
|
||||
LOG_DATA_PROTOCOL_LOGGING_C,
|
||||
LOG_WMS_READ_C };
|
||||
err = diag_log_stream_config(client_id, ENABLE, log_codes_array_apps, TOTAL_LOG_CODES_APPS);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SET_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Putting the thread to sleep for 30 seconds. The client must sleep for the time it
|
||||
wants to receive logs/events/command responses */
|
||||
sleep(30);
|
||||
printf("\n");
|
||||
|
||||
/* Display Health Statistics */
|
||||
DIAG_LOGE(" Health statistics for the Application processor Data:\n");
|
||||
err = diag_get_health_stats_proc(client_id, dci_health_stats, DIAG_APPS_PROC);
|
||||
if (err == DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE(" Log Drop Count for APSS:\t%d\n", dci_health_stats->dropped_logs);
|
||||
DIAG_LOGE(" Log Total Count for APSS:\t%d\n", dci_health_stats->received_logs);
|
||||
DIAG_LOGE(" Event Drop Count for APSS:\t%d\n", dci_health_stats->dropped_events);
|
||||
DIAG_LOGE(" Event Total Count for APSS:\t%d\n", dci_health_stats->received_events);
|
||||
} else
|
||||
DIAG_LOGE(" Error in collecting statistics, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
sleep(1);
|
||||
|
||||
printf("\n");
|
||||
|
||||
/* Clearing these log masks ------------------------
|
||||
0x117B - WMS Set Routes
|
||||
0x11EB - DPL Log Messages
|
||||
0x1160 - WMS Read
|
||||
---------------------------------------------------- */
|
||||
DIAG_LOGE(" Clearing log masks\n");
|
||||
DIAG_LOGE(" [0x117B] WMS Set Routes\n");
|
||||
DIAG_LOGE(" [0x11EB] DPL Log Messages\n");
|
||||
DIAG_LOGE(" [0x1160] WMS Read\n");
|
||||
err = diag_log_stream_config(client_id, DISABLE, log_codes_array_apps, TOTAL_LOG_CODES_APPS);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending CLEAR_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
sleep(5);
|
||||
printf("\n");
|
||||
|
||||
DIAG_LOGE(" ##### STARTING Ext API Log Packets unit test #####\n");
|
||||
DIAG_LOGE(" Registering for Version 1 of DCI (EXT Header Support)");
|
||||
err = diag_dci_set_version(client_id, 1);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error registering version to DCI %d\n", err);
|
||||
|
||||
|
||||
DIAG_LOGE(" Sending Asynchronous Command for Ext API Log Packets\n");
|
||||
/* Diag Log stress test command - one Log packet comes out every second */
|
||||
unsigned char log_ext[24] = {75, 18, 0, 0, 1, 0, 0, 0, 57, 1, 1, 0, 0, 1, 0, 0, 232, 3, 0, 0, 1, 0, 0, 0};
|
||||
err = diag_send_dci_async_req(client_id, log_ext, 24, dci_rsp_pkt, DIAG_MAX_RX_PKT_SIZ, &process_response, NULL);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SEND_REQUEST_ASYNC to peripheral %d\n", err);
|
||||
|
||||
/* Diag Events w/ payload test command - one Log packet comes out every second */
|
||||
DIAG_LOGE(" Sending Asynchronous Command for Ext API Event Packets\n");
|
||||
unsigned char event_ext[24] = {75, 18, 0, 0, 1, 0, 0, 0, 70, 1, 1, 0, 0, 1, 0, 0, 232, 3, 0, 0, 1, 0, 0, 0};
|
||||
err = diag_send_dci_async_req(client_id, event_ext, 24, dci_rsp_pkt, DIAG_MAX_RX_PKT_SIZ, &process_response, NULL);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SEND_REQUEST_ASYNC to peripheral %d\n", err);
|
||||
|
||||
sleep(1);
|
||||
printf("\n");
|
||||
|
||||
/* Setting Log masks ----------------------------
|
||||
0x115F - Diag Stress Test Log
|
||||
-------------------------------------------*/
|
||||
DIAG_LOGE(" Setting Log masks\n");
|
||||
DIAG_LOGE(" [0x115F] Diag Stress Test Log\n");
|
||||
err = diag_log_stream_config(client_id, ENABLE, log_codes_array, TOTAL_LOG_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SET_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Setting Log masks ----------------------------
|
||||
0x115F - Diag Stress Test Event
|
||||
-------------------------------------------*/
|
||||
DIAG_LOGE(" Setting Event masks\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_NO_PAYLOAD\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_WITH_PAYLOAD\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_COMPLETED\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_DROP_DEBUG\n");
|
||||
|
||||
int event_codes_array[TOTAL_EVENT_CODES] = {
|
||||
EVENT_DIAG_STRESS_TEST_NO_PAYLOAD,
|
||||
EVENT_DIAG_STRESS_TEST_WITH_PAYLOAD,
|
||||
EVENT_DIAG_STRESS_TEST_COMPLETED,
|
||||
EVENT_DIAG_DROP_DEBUG
|
||||
};
|
||||
|
||||
err = diag_event_stream_config(client_id, ENABLE, event_codes_array, TOTAL_EVENT_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending SET_EVENT_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Putting the thread to sleep for 30 seconds. The client must sleep for the time it
|
||||
wants to receive logs/events/command responses */
|
||||
sleep(30);
|
||||
printf("\n");
|
||||
|
||||
/* Test Ext Header stripping for dci clients that do not support version 1 of DCI */
|
||||
DIAG_LOGE(" Un-Registering for Version 1 of DCI (EXT Header Support)");
|
||||
err = diag_dci_set_version(client_id, 0);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error registering version to DCI %d\n", err);
|
||||
|
||||
sleep(30);
|
||||
printf("\n");
|
||||
|
||||
/* Display Health Statistics */
|
||||
DIAG_LOGE(" Modem Health Statistics on the Apps processor:\n");
|
||||
dci_health_stats = malloc(sizeof(struct diag_dci_health_stats));
|
||||
if (!dci_health_stats) {
|
||||
DIAG_LOGE(" Unable to allocate memory for DCI health stats, errno: %d", errno);
|
||||
free(dci_rsp_pkt);
|
||||
return -1;
|
||||
}
|
||||
|
||||
err = diag_get_health_stats_proc(client_id, dci_health_stats, DIAG_MODEM_PROC);
|
||||
if (err == DIAG_DCI_NO_ERROR) {
|
||||
DIAG_LOGE(" Log Drop Count for Modem:\t%d\n", dci_health_stats->dropped_logs);
|
||||
DIAG_LOGE(" Log Total Count for Modem:\t%d\n", dci_health_stats->received_logs);
|
||||
DIAG_LOGE(" Event Drop Count for Modem:\t%d\n", dci_health_stats->dropped_events);
|
||||
DIAG_LOGE(" Event Total Count for Modem:\t%d\n", dci_health_stats->received_events);
|
||||
} else
|
||||
DIAG_LOGE(" Error in collecting statistics, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
sleep(1);
|
||||
printf("\n");
|
||||
|
||||
/* Clearing these log masks ------------------------
|
||||
0x115F - Diag Stress Test Log
|
||||
---------------------------------------------------- */
|
||||
DIAG_LOGE(" Clearing log masks\n");
|
||||
DIAG_LOGE(" [0x115F] Diag Stress Test Log\n");
|
||||
err = diag_log_stream_config(client_id, DISABLE, log_codes_array, TOTAL_LOG_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending CLEAR_LOG_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Clearing Event masks ----------------------------
|
||||
0x115F - Diag Stress Test Event
|
||||
-------------------------------------------*/
|
||||
DIAG_LOGE(" Clearing event masks\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_NO_PAYLOAD\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_WITH_PAYLOAD\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_STRESS_TEST_COMPLETED\n");
|
||||
DIAG_LOGE(" EVENT_DIAG_DROP_DEBUG\n");
|
||||
err = diag_event_stream_config(client_id, DISABLE, event_codes_array, TOTAL_EVENT_CODES);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error sending CLEAR_EVENT_MASK to peripheral, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
/* Releasing DCI connection */
|
||||
DIAG_LOGE(" Releasing DCI connection \n");
|
||||
err = diag_release_dci_client(&client_id);
|
||||
if (err != DIAG_DCI_NO_ERROR)
|
||||
DIAG_LOGE(" Error releasing DCI connection, err: %d, errno: %d\n", err, errno);
|
||||
|
||||
Diag_LSM_DeInit();
|
||||
printf("\n");
|
||||
free(dci_health_stats);
|
||||
free(dci_rsp_pkt);
|
||||
return 0;
|
||||
}
|
||||
10
feeds/ipq95xx/qca-diag/src/diag.pc.in
Executable file
10
feeds/ipq95xx/qca-diag/src/diag.pc.in
Executable file
@@ -0,0 +1,10 @@
|
||||
prefix=@prefix@
|
||||
exec_prefix=@exec_prefix@
|
||||
libdir=@libdir@
|
||||
includedir=@includedir@
|
||||
|
||||
Name: diag
|
||||
Description: Common functions for DIAG project test assets
|
||||
Version: @VERSION@
|
||||
Libs: -L${libdir} -ldiag
|
||||
Cflags: -I${includedir}/diag
|
||||
54
feeds/ipq95xx/qca-diag/src/include/comdef.h
Executable file
54
feeds/ipq95xx/qca-diag/src/include/comdef.h
Executable file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (c) 2017-2018 Qualcomm Technologies, Inc.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
* Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
*/
|
||||
|
||||
#ifndef __COMDEF_H
|
||||
#define __COMDEF_H
|
||||
|
||||
#define PACK(x) x __attribute__((__packed__))
|
||||
|
||||
#define TRUE 1
|
||||
#define FALSE 0
|
||||
#define QSDK_BUILD 1
|
||||
#define FEATURE_LE_DIAG 1
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/*
|
||||
* type defs
|
||||
*/
|
||||
|
||||
typedef uint8_t boolean; /* Boolean value type. */
|
||||
typedef uint32_t uint32; /* Unsigned 32 bit value */
|
||||
typedef uint16_t uint16; /* Unsigned 16 bit value */
|
||||
typedef uint8_t uint8; /* Unsigned 8 bit value */
|
||||
typedef int32_t int32; /* Signed 32 bit value */
|
||||
typedef int16_t int16; /* Signed 16 bit value */
|
||||
typedef int8_t int8; /* Signed 8 bit value */
|
||||
typedef uint64_t uint64;
|
||||
typedef uint8_t byte;
|
||||
typedef uint32_t dword;
|
||||
typedef uint16_t word;
|
||||
|
||||
#if __SIZEOF_POINTER__ == 4
|
||||
# define FPOS( type, field ) \
|
||||
/*lint -e545 */ ( (dword) &(( type *) 0)-> field) /*lint +e545 */
|
||||
#else
|
||||
# define FPOS( type, field ) \
|
||||
/*lint -e545 */ ((uint64) &(( type *) 0)-> field) /*lint +e545 */
|
||||
#endif
|
||||
|
||||
#define FSIZ( type, field ) sizeof( ((type *) 0)->field )
|
||||
|
||||
#ifndef MAX
|
||||
#define MAX( x, y ) ( ((x) > (y)) ? (x) : (y) )
|
||||
#endif
|
||||
|
||||
#ifndef MIN
|
||||
#define MIN( x, y ) ( ((x) < (y)) ? (x) : (y) )
|
||||
#endif
|
||||
|
||||
#endif /* END _COMDEF_H */
|
||||
232
feeds/ipq95xx/qca-diag/src/include/diag.h
Executable file
232
feeds/ipq95xx/qca-diag/src/include/diag.h
Executable file
@@ -0,0 +1,232 @@
|
||||
#ifndef DIAG_H
|
||||
#define DIAG_H
|
||||
/*==========================================================================
|
||||
|
||||
Diagnostic Task Header File
|
||||
|
||||
Description
|
||||
Global Data declarations of the diag_task.
|
||||
|
||||
# Copyright (c) 2007-2011, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.===========================================================================*/
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
$Header: //depot/asic/msmshared/services/diag/DIAG_7K/diag.h#5 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
12/22/06 as Moved proc ID macros to diag.h
|
||||
12/05/06 as Added signal for Diag drain timer
|
||||
11/21/06 as Moved DIAG internal features from diagi.h to diag.h
|
||||
03/30/05 sl Added support for SPC_UNLOCK_TTL to unlock/lock the sp_state
|
||||
10/17/03 ph For Rel A builds, redirect to new MC subsystem command.
|
||||
09/23/03 gr Function prototypes related to changes that enable more
|
||||
efficient detection of the condition where diag is out of
|
||||
heap space.
|
||||
08/20/01 jal Changes to support more Diag packets. Support for powerup
|
||||
online/offline state, service programming lock state.
|
||||
04/06/01 lad Cosmetic changes.
|
||||
02/23/01 lad Rearchitected the diagnostics subsystem to be a service
|
||||
rather than a module. All coupling to targets has been
|
||||
moved to target-specific implementations. This file now
|
||||
contains an API. No other information or coupling remains
|
||||
except for featurized legacy code that impacts existing
|
||||
targets.
|
||||
Old history comments have been removed since most of them
|
||||
are no longer applicable.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
** Definitions and Declarations
|
||||
** ------------------------------------------------------------------------- */
|
||||
/* Diagnostics version (protocol revision).
|
||||
*/
|
||||
/* DIAG_DIAGVER
|
||||
Diagnostics version, used to ensure compatibility of the DM and the DMSS.
|
||||
1 Original
|
||||
2 Changes to status packet and verno packet. Removed verstr packet
|
||||
3 for release to factory. Sends RF mode in status packet
|
||||
4 Adds release directory to verno packet and dipswitch packets
|
||||
5 Many changes in DM.
|
||||
6 Added Vocoder PCM and PKT loopback, and Analog IS-55 tests
|
||||
7 New FER data in tagraph packet
|
||||
8 Streaming protocol enhancements and event reporting.
|
||||
*/
|
||||
#ifdef FEATURE_DIAG_NON_STREAMING
|
||||
#define DIAG_DIAGVER 7
|
||||
#else
|
||||
#define DIAG_DIAGVER 8
|
||||
#endif
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
** Diag Internal features
|
||||
** ------------------------------------------------------------------------- */
|
||||
/* Group all standalone features */
|
||||
#if (defined(FEATURE_STANDALONE) || defined(FEATURE_STANDALONE_APPS) || \
|
||||
defined(FEATURE_STANDALONE_MODEM))
|
||||
#define DIAG_STANDALONE
|
||||
#endif
|
||||
|
||||
/* Multi processor Diag */
|
||||
#if defined(FEATURE_MULTIPROCESSOR) && !(defined(DIAG_STANDALONE))
|
||||
#define DIAG_MP
|
||||
#endif
|
||||
|
||||
#define DIAG_MODEM_PROC 0
|
||||
#define DIAG_APP_PROC 1
|
||||
#define DIAG_DUAL_PROC 2
|
||||
|
||||
#if defined (DIAG_MP)
|
||||
#if defined (FEATURE_DIAG_MP_MASTER_MODEM)
|
||||
/* Master DIAG is on Modem Processor */
|
||||
#if defined (IMAGE_MODEM_PROC)
|
||||
#define DIAG_MP_MASTER IMAGE_MODEM_PROC
|
||||
#undef DIAG_MP_SLAVE
|
||||
#endif
|
||||
#if defined (IMAGE_APPS_PROC)
|
||||
#define DIAG_MP_SLAVE IMAGE_APPS_PROC
|
||||
#undef DIAG_MP_MASTER
|
||||
#endif
|
||||
#define DIAGPKT_REQ_FWD_PROC DIAG_APP_PROC
|
||||
#elif defined (FEATURE_DIAG_MP_MASTER_APPS)
|
||||
/* Master DIAG is on Apps Processor */
|
||||
#if defined (IMAGE_APPS_PROC)
|
||||
#define DIAG_MP_MASTER IMAGE_APPS_PROC
|
||||
#undef DIAG_MP_SLAVE
|
||||
/* Mobile View code */
|
||||
#define DIAG_MV_CMD_RPC
|
||||
#endif
|
||||
#if defined (IMAGE_MODEM_PROC)
|
||||
#define DIAG_MP_SLAVE IMAGE_MODEM_PROC
|
||||
#undef DIAG_MP_MASTER
|
||||
#endif
|
||||
#define DIAGPKT_REQ_FWD_PROC DIAG_MODEM_PROC
|
||||
#elif defined (FEATURE_DIAG_MP_MODEM_ONLY)
|
||||
/* Should be same as single processor DIAG_SINGLE_PROC */
|
||||
#else
|
||||
#error "Select where master diag should be"
|
||||
#endif
|
||||
#else
|
||||
/* Should be same as single processor DIAG_SINGLE_PROC*/
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/* Runtime Device Map port selection for diag */
|
||||
#if defined (FEATURE_RUNTIME_DEVMAP)
|
||||
#if defined (DIAG_MP)
|
||||
#if defined (DIAG_MP_MASTER)|| defined(FEATURE_DIAG_MP_MODEM_ONLY)
|
||||
#define DIAG_RUNTIME_DEVMAP
|
||||
#endif
|
||||
#else
|
||||
#define DIAG_RUNTIME_DEVMAP
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined DIAG_MP
|
||||
#if defined (DIAG_MP_MASTER)
|
||||
#define DIAG_REQ_FWD /* Fowards requests to the slave proc */
|
||||
#define DIAG_NO_DSM_CHAINING
|
||||
#define DIAG_FRAMING
|
||||
#define DIAG_SIO_USB
|
||||
#elif defined (DIAG_MP_SLAVE)
|
||||
#define DIAG_RSP_SEND /* sends response */
|
||||
#endif
|
||||
|
||||
#if defined (FEATURE_DIAG_MP_MODEM_ONLY)
|
||||
#define DIAG_NO_DSM_CHAINING
|
||||
#define DIAG_FRAMING
|
||||
#define DIAG_RSP_SEND /* sends response */
|
||||
#undef DIAG_REQ_FWD
|
||||
#endif
|
||||
|
||||
#else /*DIAG_MP */
|
||||
/* Single processor or standalone builds */
|
||||
#define DIAG_NO_DSM_CHAINING
|
||||
#define DIAG_FRAMING
|
||||
#define DIAG_RSP_SEND /* sends response */
|
||||
#endif /*DIAG_MP*/
|
||||
|
||||
|
||||
/* Error cases */
|
||||
#if defined (DIAG_MP) && !defined(FEATURE_SMD)
|
||||
#error "Error: FEATURE_SND is required for DIAG_MP"
|
||||
#endif
|
||||
#if defined (FEATURE_DIAG_MP_MODEM_ONLY) && \
|
||||
!(defined (DIAG_MP) || defined (IMAGE_MODEM_PROC))
|
||||
#error "Error: Invalid configuration for DIAG MP"
|
||||
#endif
|
||||
|
||||
#if defined (DIAG_MP_MASTER)
|
||||
#if defined (DIAG_RSP_SEND)
|
||||
#error "Error DIAG_RSP_SEND defined on Master"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined (DIAG_MP_SLAVE)
|
||||
#if defined (DIAG_REQ_FWD)
|
||||
#error "Error: DIAG_REQ_FWD defined on Slave"
|
||||
#endif
|
||||
#if defined (DIAG_NO_DSM_CHAINING)
|
||||
#error "Error: DIAG_NO_DSM_CHAINING defined on Slave"
|
||||
#endif
|
||||
#if defined (DIAG_FRAMING)
|
||||
#error "Error: DIAG_FRAMING defined on Slave"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
#define DIAG_FTM_SWITCH_VAL 2
|
||||
/* This structure is sent to an event listener when an event is processed.
|
||||
The implementation relies on the format of this structure. It is
|
||||
dangerous to change this format of this structure. */
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int event_id; /* event ID */
|
||||
//qword ts; /* 8-byte CDMA time stamp. */
|
||||
uint32 ts_lo; /* Time stamp */
|
||||
uint32 ts_hi;
|
||||
|
||||
uint8 length; /* length of the payload */
|
||||
/* Payload of size 'length': */
|
||||
uint8 payload[255]; /* payload, if length > 0 */
|
||||
|
||||
}
|
||||
diag_event_type;
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION TYPE DIAG_CMD_RSP
|
||||
|
||||
DESCRIPTION
|
||||
This function type is provided by the caller when sending a request packet
|
||||
using diag_cmd_req(). After the request is processed, this function is
|
||||
called (if specified) with a pointer to the response packet and the handle
|
||||
returned from the corresponding diag_cmd_req() call.
|
||||
|
||||
Memory is owned by the DIAG task and is freed when this function returns.
|
||||
|
||||
'param' is the unmodified value from the corresponding diag_cmd_req() call.
|
||||
|
||||
RETURN VALUE
|
||||
None.
|
||||
|
||||
===========================================================================*/
|
||||
typedef void (*diag_cmd_rsp) (const byte *rsp, unsigned int length,
|
||||
void *param);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* DIAG_H */
|
||||
567
feeds/ipq95xx/qca-diag/src/include/diag_lsm.h
Executable file
567
feeds/ipq95xx/qca-diag/src/include/diag_lsm.h
Executable file
@@ -0,0 +1,567 @@
|
||||
#ifndef DIAG_LSM_H
|
||||
#define DIAG_LSM_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Diag Mapping Layer DLL declarations
|
||||
|
||||
DESCRIPTION
|
||||
Function declarations for Diag Service Mapping Layer
|
||||
|
||||
|
||||
Copyright (c)2007-2012, 2014-2016 Qualcomm Technologies, Inc.
|
||||
All Rights Reserved.
|
||||
Confidential and Proprietary - Qualcomm Technologies, Inc.
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
EDIT HISTORY FOR MODULE
|
||||
|
||||
This section contains comments describing changes made to the module.
|
||||
Notice that changes are listed in reverse chronological order.
|
||||
|
||||
$Header:
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
02/04/08 mad Added declarations for Diag_LSM_Init and DeInit functions
|
||||
to enable diag clients to call these directly.
|
||||
Moved IDiagPkt handle declaration to an internal header
|
||||
file, Diag_LSMi.h
|
||||
11/29/07 mad Created File
|
||||
===========================================================================*/
|
||||
|
||||
#define MSG_MASKS_TYPE 0x00000001
|
||||
#define LOG_MASKS_TYPE 0x00000002
|
||||
#define EVENT_MASKS_TYPE 0x00000004
|
||||
#define PKT_TYPE 0x00000008
|
||||
#define DEINIT_TYPE 0x00000010
|
||||
#define USER_SPACE_DATA_TYPE 0x00000020
|
||||
#define DCI_DATA_TYPE 0x00000040
|
||||
#define USER_SPACE_RAW_DATA_TYPE 0x00000080
|
||||
#define DCI_LOG_MASKS_TYPE 0x00000100
|
||||
#define DCI_EVENT_MASKS_TYPE 0x00000200
|
||||
#define DCI_PKT_TYPE 0x00000400
|
||||
#define HDLC_SUPPORT_TYPE 0x00001000
|
||||
|
||||
#define USB_MODE 1
|
||||
#define MEMORY_DEVICE_MODE 2
|
||||
#define NO_LOGGING_MODE 3
|
||||
#define UART_MODE 4
|
||||
#define SOCKET_MODE 5
|
||||
#define CALLBACK_MODE 6
|
||||
|
||||
#define MAX_NUM_FILES_ON_DEVICE 2000 /* If user wants to stop logging on SD after reaching a max file limit */
|
||||
#define CONTROL_CHAR 0x7E
|
||||
#define FILE_NAME_LEN 500
|
||||
#define NUM_PROC 10
|
||||
/* Token to identify MDM log */
|
||||
#define MDM_TOKEN -1
|
||||
#define MDM2_TOKEN -2
|
||||
#define MDM3_TOKEN -3
|
||||
/* Token to identify QSC log */
|
||||
#define QSC_TOKEN -5
|
||||
#define MSM 0
|
||||
#define MDM 1
|
||||
#define QSC 2
|
||||
|
||||
#define MODE_NONREALTIME 0
|
||||
#define MODE_REALTIME 1
|
||||
#define MODE_UNKNOWN 2
|
||||
|
||||
#define DIAG_PROC_DCI 1
|
||||
#define DIAG_PROC_MEMORY_DEVICE 2
|
||||
|
||||
/* List of processors */
|
||||
#define DIAG_ALL_PROC -1
|
||||
#define DIAG_MODEM_PROC 0
|
||||
#define DIAG_LPASS_PROC 1
|
||||
#define DIAG_WCNSS_PROC 2
|
||||
#define DIAG_SENSORS_PROC 3
|
||||
#define NUM_PERIPHERALS 4
|
||||
#define DIAG_APPS_PROC (NUM_PERIPHERALS)
|
||||
|
||||
#define DIAG_CON_APSS (0x0001) /* Bit mask for APSS */
|
||||
#define DIAG_CON_MPSS (0x0002) /* Bit mask for MPSS */
|
||||
#define DIAG_CON_LPASS (0x0004) /* Bit mask for LPASS */
|
||||
#define DIAG_CON_WCNSS (0x0008) /* Bit mask for WCNSS */
|
||||
#define DIAG_CON_SENSORS (0x0010) /* Bit mask for Sensors */
|
||||
#define DIAG_CON_WDSP (0x0020)
|
||||
#define DIAG_CON_CDSP (0x0040)
|
||||
#define DIAG_CON_NPU (0x0080)
|
||||
#define DIAG_CON_NONE (0x0000) /* Bit mask for No SS*/
|
||||
#define DIAG_CON_ALL (DIAG_CON_APSS | DIAG_CON_MPSS \
|
||||
| DIAG_CON_LPASS | DIAG_CON_WCNSS \
|
||||
| DIAG_CON_SENSORS | DIAG_CON_WDSP \
|
||||
| DIAG_CON_CDSP | DIAG_CON_NPU)
|
||||
|
||||
#define DIAG_MSM_MASK (0x0001) /* Bit mask for APSS */
|
||||
#define DIAG_MDM_MASK (0x0002) /* Bit mask for MPSS */
|
||||
#define DIAG_MDM2_MASK (0x0004) /* Bit mask for LPASS */
|
||||
#define DIAG_MDM3_MASK (0x0008)
|
||||
|
||||
#define DIAG_STREAMING_MODE 0
|
||||
#define DIAG_THRESHOLD_BUFFERING_MODE 1
|
||||
#define DIAG_CIRCULAR_BUFFERING_MODE 2
|
||||
|
||||
#define DIAG_MD_NONE 0
|
||||
#define DIAG_MD_PERIPHERAL 1
|
||||
|
||||
/*
|
||||
* The status bit masks when received in a signal handler are to be
|
||||
* used in conjunction with the peripheral list bit mask to determine the
|
||||
* status for a peripheral. For instance, 0x00010002 would denote an open
|
||||
* status on the MPSS
|
||||
*/
|
||||
#define DIAG_STATUS_OPEN (0x00010000) /* Bit mask for DCI channel open status */
|
||||
#define DIAG_STATUS_CLOSED (0x00020000) /* Bit mask for DCI channel closed status */
|
||||
|
||||
#define GUID_LEN 16
|
||||
|
||||
#if defined (ANDROID) || defined (USE_ANDROID_LOGGING)
|
||||
#define LOG_TAG "Diag_Lib"
|
||||
#define DIAG_LOGE(...) { \
|
||||
ALOGE(__VA_ARGS__); \
|
||||
if (!diag_disable_console) \
|
||||
printf(__VA_ARGS__); \
|
||||
}
|
||||
#define DIAG_LOGD(...) { \
|
||||
ALOGE(__VA_ARGS__); \
|
||||
if (!diag_disable_console) \
|
||||
printf(__VA_ARGS__); \
|
||||
}
|
||||
#include <log/log.h>
|
||||
#include "common_log.h"
|
||||
#else
|
||||
#define DIAG_LOGE(...) printf (__VA_ARGS__)
|
||||
#define DIAG_LOGD(...) printf (__VA_ARGS__)
|
||||
#endif
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#define GUID_LIST_XML_TAG_SIZE 13
|
||||
#define GUID_LIST_END_XML_TAG_SIZE 20
|
||||
|
||||
#ifdef USE_GLIB
|
||||
#define strlcpy g_strlcpy
|
||||
#define strlcat g_strlcat
|
||||
#endif
|
||||
|
||||
extern int logging_mode;
|
||||
extern char mask_file[FILE_NAME_LEN];
|
||||
extern char mask_file_mdm[FILE_NAME_LEN];
|
||||
extern char output_dir[NUM_PROC][FILE_NAME_LEN];
|
||||
extern int diag_disable_console;
|
||||
extern char dir_name[FILE_NAME_LEN];
|
||||
extern char proc_name[NUM_PROC][6];
|
||||
extern pthread_cond_t qsr4_read_db_cond;
|
||||
extern uint8 hdlc_disabled;
|
||||
extern char qsr4_xml_file_name[FILE_NAME_LEN];
|
||||
extern int fd_qsr4_xml[NUM_PROC];
|
||||
|
||||
typedef enum {
|
||||
DB_PARSER_STATE_OFF,
|
||||
DB_PARSER_STATE_ON,
|
||||
DB_PARSER_STATE_LIST,
|
||||
DB_PARSER_STATE_OPEN,
|
||||
DB_PARSER_STATE_READ,
|
||||
DB_PARSER_STATE_CLOSE,
|
||||
} qsr4_db_file_parser_state;
|
||||
|
||||
/* enum to handle packet processing status */
|
||||
enum pkt_status{
|
||||
PKT_PROCESS_ONGOING,
|
||||
PKT_PROCESS_DONE
|
||||
};
|
||||
|
||||
/*
|
||||
* Structure to keep track of diag callback interface clients. Please note that
|
||||
* there can be only client communicating with an ASIC at a given time.
|
||||
*
|
||||
* @inited: flag to indicate if the table entry is initialized
|
||||
* @cb_func_ptr: callback function pointer
|
||||
* @context_data: user specified data
|
||||
*
|
||||
*/
|
||||
struct diag_callback_tbl_t {
|
||||
int inited;
|
||||
int (*cb_func_ptr)(unsigned char *, int len, void *context_data);
|
||||
void *context_data;
|
||||
};
|
||||
|
||||
struct diag_uart_tbl_t {
|
||||
int proc_type;
|
||||
int pid;
|
||||
int (*cb_func_ptr)(unsigned char *, int len, void *context_data);
|
||||
void *context_data;
|
||||
};
|
||||
|
||||
struct diag_con_all_param_t {
|
||||
uint32 diag_con_all;
|
||||
uint32 num_peripherals;
|
||||
uint32 upd_map_supported;
|
||||
};
|
||||
|
||||
struct diag_query_pid_t {
|
||||
uint32 peripheral_mask;
|
||||
uint32 pd_mask;
|
||||
int pid;
|
||||
uint32 device_mask;
|
||||
};
|
||||
|
||||
struct diag_logging_mode_param_t {
|
||||
uint32 req_mode;
|
||||
uint32 peripheral_mask;
|
||||
uint32 pd_mask;
|
||||
uint8 mode_param;
|
||||
uint8 diag_id;
|
||||
uint8 pd_val;
|
||||
uint8 reserved;
|
||||
int peripheral;
|
||||
uint32 device_mask;
|
||||
};
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION Diag_LSM_Init
|
||||
|
||||
DESCRIPTION
|
||||
Initializes the Diag Legacy Mapping Layer. This should be called
|
||||
only once per process.
|
||||
|
||||
DEPENDENCIES
|
||||
Successful initialization requires Diag CS component files to be present
|
||||
and accessible in the file system.
|
||||
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean Diag_LSM_Init (byte* pIEnv);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION diag_switch_logging_proc
|
||||
|
||||
DESCRIPTION
|
||||
This swtiches the logging mode from default USB to memory device logging
|
||||
|
||||
DEPENDENCIES
|
||||
valid data type to be passed in:
|
||||
|
||||
RETURN VALUE
|
||||
0 - Success; failure otherwise
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_switch_logging_proc(struct diag_logging_mode_param_t *params);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION diag_switch_logging
|
||||
|
||||
DESCRIPTION
|
||||
This swtiches the logging mode from default USB to memory device logging
|
||||
|
||||
DEPENDENCIES
|
||||
valid data type to be passed in:
|
||||
In case of ODL second argument is to specifying directory location.
|
||||
In case of UART mode second argument is specify PROC type.
|
||||
|
||||
RETURN VALUE
|
||||
None
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void diag_switch_logging(int requested_mode, char *dir_location);
|
||||
/*===========================================================================
|
||||
FUNCTION diag_read_mask_file
|
||||
|
||||
DESCRIPTION
|
||||
This reads the mask file
|
||||
|
||||
DEPENDENCIES
|
||||
valid data type to be passed in
|
||||
|
||||
RETURN VALUE
|
||||
None
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
int diag_read_mask_file(void);
|
||||
/*===========================================================================
|
||||
FUNCTION diag_register_callback
|
||||
|
||||
DESCRIPTION
|
||||
This allows diag client to register a callback function with LSM library.
|
||||
If the library receives data from kernel space, it will invoke this call
|
||||
back function, thus passing the data to the client through this function.
|
||||
|
||||
DEPENDENCIES
|
||||
valid data type to be passed in
|
||||
|
||||
RETURN VALUE
|
||||
None
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void diag_register_callback(int (*client_cb_func_ptr)(unsigned char *ptr,
|
||||
int len, void *context_data), void *context_data);
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION diag_register_remote_callback
|
||||
|
||||
DESCRIPTION
|
||||
This allows diag client to register a callback function with LSM library.
|
||||
If the library receives data from kernel space originating from the remote
|
||||
processor, it will invoke this call back function, thus passing the data
|
||||
to the client through this function.
|
||||
|
||||
DEPENDENCIES
|
||||
valid data type to be passed in
|
||||
|
||||
RETURN VALUE
|
||||
None
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
void diag_register_remote_callback(int (*client_rmt_cb_func_ptr)(unsigned char *ptr,
|
||||
int len, void *context_data), int proc,
|
||||
void *context_data);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_send_data
|
||||
|
||||
DESCRIPTION
|
||||
Inject data into diag kernel driver
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE.
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_send_data(unsigned char *, int);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_callback_send_data
|
||||
|
||||
DESCRIPTION
|
||||
Inject data into diag kernel driver for a specific processor in
|
||||
callback mode
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE.
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_callback_send_data(int proc, unsigned char * buf, int len);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_callback_send_data_hdlc
|
||||
|
||||
DESCRIPTION
|
||||
Inject hdlc data into diag kernel driver for a specific processor in
|
||||
callback mode
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE.
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_callback_send_data_hdlc(int proc, unsigned char * buf, int len);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_vote_md_real_time
|
||||
|
||||
DESCRIPTION
|
||||
Votes the on device logging process for real/non-real time
|
||||
mode
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
0 = success, -1 = failure
|
||||
|
||||
SIDE EFFECTS
|
||||
Puts the entire diag in the mode specified if the process wins
|
||||
the vote
|
||||
|
||||
===========================================================================*/
|
||||
int diag_vote_md_real_time(int real_time);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_vote_md_real_time_proc
|
||||
|
||||
DESCRIPTION
|
||||
Votes the on device logging process for real/non-real time
|
||||
mode, in a particular processor.
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
0 = success, -1 = failure
|
||||
|
||||
SIDE EFFECTS
|
||||
Puts the entire diag in the mode specified if the process wins
|
||||
the vote
|
||||
|
||||
===========================================================================*/
|
||||
int diag_vote_md_real_time_proc(int proc, int real_time);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_get_real_time_status
|
||||
|
||||
DESCRIPTION
|
||||
Gets the mode (real time or non real time) in which Diag is in
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
0 = success, -1 = failure
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_get_real_time_status(int *real_time);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_get_real_time_status_proc
|
||||
|
||||
DESCRIPTION
|
||||
Gets the mode (real time or non real time) in which Diag is
|
||||
in, in a particular processor
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
0 = success, -1 = failure
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
int diag_get_real_time_status_proc(int proc, int *real_time);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION Diag_LSM_DeInit
|
||||
|
||||
DESCRIPTION
|
||||
De-Initialize the Diag service.
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
FALSE = failure, else TRUE.
|
||||
Currently all the internal boolean return functions called by
|
||||
this function just returns TRUE w/o doing anything.
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
boolean Diag_LSM_DeInit(void);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_configure_peripheral_buffering_tx_mode
|
||||
|
||||
DESCRIPTION
|
||||
Configure the peripheral Diag's TX mode to Streaming, Circular, or
|
||||
Threshold buffering mode and set high and low watermark threshold limits.
|
||||
Streaming Mode is a default TX mode for peripheral Diag.
|
||||
Switching to Threshold or Circular buffering mode puts the peripheral
|
||||
Diag to Non-Real Time mode (NRT).
|
||||
Switching to streaming mode will put the peripheral to Real Time (RT) mode.
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
1 = success, else failure
|
||||
|
||||
SIDE EFFECTS
|
||||
Clients cannot vote for real/non-real time when the Tx mode is set
|
||||
to Circular, or Threshold buffering mode.
|
||||
|
||||
===========================================================================*/
|
||||
int diag_configure_peripheral_buffering_tx_mode(uint8 peripheral, uint8 tx_mode,
|
||||
uint8 low_wm_val, uint8 high_wm_val);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION diag_peripheral_buffering_drain_immediate
|
||||
|
||||
DESCRIPTION
|
||||
|
||||
Request the peripheral to drain its Tx buffering pool immediately.
|
||||
If peripheral Diag receives this request in
|
||||
Streaming mode - No action is taken since Diag is already streaming.
|
||||
Threshold or Circular buffering modes - Diag will drain its Tx buffering
|
||||
pool until the low watermark threshold is reached, and then resume
|
||||
buffering in the tx mode it was set
|
||||
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
1 = success, else failure
|
||||
|
||||
SIDE EFFECTS
|
||||
None
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
int diag_peripheral_buffering_drain_immediate(uint8 peripheral);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* DIAG_LSM_H */
|
||||
|
||||
212
feeds/ipq95xx/qca-diag/src/include/diag_lsm_dci.h
Executable file
212
feeds/ipq95xx/qca-diag/src/include/diag_lsm_dci.h
Executable file
@@ -0,0 +1,212 @@
|
||||
#ifndef DIAG_LSM_DCI_H
|
||||
#define DIAG_LSM_DCI_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
/*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*
|
||||
# Copyright (c) 2012-2013, 2015-2016 by Qualcomm Technologies, Inc.
|
||||
# All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
|
||||
Diag Consumer Interface (DCI)
|
||||
|
||||
GENERAL DESCRIPTION
|
||||
|
||||
Headers specific to DCI.
|
||||
|
||||
*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
EDIT HISTORY FOR MODULE
|
||||
|
||||
$Header:
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
10/09/12 RA Added Interface for DCI I/O
|
||||
03/20/12 SJ Created
|
||||
===========================================================================*/
|
||||
|
||||
/*strlcpy is from OpenBSD and not supported by Meego.
|
||||
GNU has an equivalent g_strlcpy implementation into glib.
|
||||
Featurized with compile time USE_GLIB flag for Meego builds.*/
|
||||
#ifdef USE_GLIB
|
||||
#define strlcpy g_strlcpy
|
||||
#define strlcat g_strlcat
|
||||
#include <pthread.h>
|
||||
#include <signal.h>
|
||||
#endif
|
||||
|
||||
/* This is a bit mask used for peripheral list. */
|
||||
typedef uint16 diag_dci_peripherals;
|
||||
|
||||
#define ENABLE 1
|
||||
#define DISABLE 0
|
||||
#define IN_BUF_SIZE 16384
|
||||
|
||||
#define DIAG_INVALID_SIGNAL 0
|
||||
|
||||
#define DIAG_PROC_MSM 0
|
||||
#define DIAG_PROC_MDM 1
|
||||
|
||||
/* This is used for health stats */
|
||||
struct diag_dci_health_stats {
|
||||
int dropped_logs;
|
||||
int dropped_events;
|
||||
int received_logs;
|
||||
int received_events;
|
||||
int reset_status;
|
||||
};
|
||||
|
||||
/* List of possible error codes returned during DCI transaction */
|
||||
enum {
|
||||
DIAG_DCI_NO_ERROR = 1001, /* No error */
|
||||
DIAG_DCI_NO_REG, /* Could not register */
|
||||
DIAG_DCI_NO_MEM, /* Failed memory allocation */
|
||||
DIAG_DCI_NOT_SUPPORTED, /* This particular client is not supported */
|
||||
DIAG_DCI_HUGE_PACKET, /* Request/Response Packet too huge */
|
||||
DIAG_DCI_SEND_DATA_FAIL, /* writing to kernel or remote peripheral fails */
|
||||
DIAG_DCI_ERR_DEREG, /* Error while de-registering */
|
||||
DIAG_DCI_PARAM_FAIL, /* Incorrect Parameter */
|
||||
DIAG_DCI_DUP_CLIENT /* Client already exists for this proc */
|
||||
} diag_dci_error_type;
|
||||
|
||||
/* ---------------------------------------------------------------------------
|
||||
External functions
|
||||
--------------------------------------------------------------------------- */
|
||||
|
||||
/* Initialization function required for DCI functions. Input parameters are:
|
||||
a) pointer to an int which holds client id
|
||||
b) pointer to a bit mask which holds peripheral information,
|
||||
c) an integer to specify which processor to talk to (Local or Remote in the case of Fusion Devices),
|
||||
d) void* for future needs (not implemented as of now) */
|
||||
int diag_register_dci_client(int *, diag_dci_peripherals *, int, void *);
|
||||
|
||||
/* This API provides information about the peripherals that supports
|
||||
DCI in the local processor. Input parameters are:
|
||||
a) pointer to a diag_dci_peripherals variable to store the bit mask
|
||||
|
||||
DEPRECATED - Use diag_get_dci_support_list_proc instead. */
|
||||
int diag_get_dci_support_list(diag_dci_peripherals *);
|
||||
|
||||
/* This API provides information about the peripherals that support
|
||||
DCI in a given processor. Input Parameters are:
|
||||
a) processor id
|
||||
b) pointer to a diag_dci_peripherals variable to store the bit mask */
|
||||
int diag_get_dci_support_list_proc(int proc, diag_dci_peripherals *list);
|
||||
|
||||
/* Version handshaking function. This will get the dci version of diag lsm */
|
||||
int diag_dci_get_version(void);
|
||||
|
||||
/* Version handshaking function. This will register the version the client is using */
|
||||
int diag_dci_set_version(int proc, int version);
|
||||
|
||||
/* Main command to send the DCI request. Input parameters are:
|
||||
a) client ID generate earlier
|
||||
b) request buffer
|
||||
c) request buffer length
|
||||
d) response buffer
|
||||
e) response buffer length
|
||||
f) call back function pointer
|
||||
g) data pointer */
|
||||
int diag_send_dci_async_req(int client_id, unsigned char buf[], int bytes, unsigned char *rsp_ptr, int rsp_len,
|
||||
void (*func_ptr)(unsigned char *ptr, int len, void *data_ptr), void *data_ptr);
|
||||
|
||||
/* Closes DCI connection for this client. The client needs to pass a pointer
|
||||
to the client id generated earlier */
|
||||
int diag_release_dci_client(int *);
|
||||
|
||||
/* Used to set up log streaming to the client. This will send an array of log codes, which are desired
|
||||
by client. Input parameters are:
|
||||
1. Client ID
|
||||
2. Boolean value telling to set or disable logs specified later
|
||||
3. Array of log codes
|
||||
4. Number of log codes specified in argument 3
|
||||
*/
|
||||
int diag_log_stream_config(int client_id, int set_mask, uint16 log_codes_array[], int num_codes);
|
||||
|
||||
/* Initialization function required for DCI streaming. Input parameters are:
|
||||
call back function pointers.
|
||||
|
||||
DEPRECATED - Use diag_register_dci_stream_proc instead */
|
||||
int diag_register_dci_stream(void (*func_ptr_logs)(unsigned char *ptr, int len),
|
||||
void (*func_ptr_events)(unsigned char *ptr, int len));
|
||||
|
||||
int diag_register_dci_stream_proc(int client_id,
|
||||
void(*func_ptr_logs)(unsigned char *ptr, int len),
|
||||
void(*func_ptr_events)(unsigned char *ptr, int len));
|
||||
|
||||
/* Used to set up event streaming to the client. This will send an array of event ids, which are desired
|
||||
by client. Input parameters are:
|
||||
1. Client ID
|
||||
2. Boolean value telling to set or disable event specified later
|
||||
3. Array of event id
|
||||
4. Number of event ids specified in argument 3
|
||||
*/
|
||||
int diag_event_stream_config(int client_id, int set_mask, int event_id_array[], int num_codes);
|
||||
|
||||
/* Used to query DCI statistics on all processors for logs & events.
|
||||
|
||||
DEPRECATED - Use diag_get_health_stats_proc instead */
|
||||
int diag_get_health_stats(struct diag_dci_health_stats *dci_health);
|
||||
|
||||
/* Used to query DCI statistics on a specific processor for logs & events */
|
||||
int diag_get_health_stats_proc(int client_id, struct diag_dci_health_stats *dci_health, int proc);
|
||||
|
||||
/* Queries a given Log Code to check if it is enabled or not. Input parameters are:
|
||||
1. Client ID
|
||||
2. Log Code that needs to be checked
|
||||
3. Pointer to boolean to store the result */
|
||||
int diag_get_log_status(int client_id, uint16 log_code, boolean *value);
|
||||
|
||||
/* Queries a given Event ID to check if it is enabled or not. Input parameters are:
|
||||
1. Client ID
|
||||
2. Event ID that needs to be checked
|
||||
3. Pointer to boolean to store the result */
|
||||
int diag_get_event_status(int client_id, uint16 event_id, boolean *value);
|
||||
|
||||
/* Disables all the Log Codes for a given client. The Input parameters are:
|
||||
1. Client ID */
|
||||
int diag_disable_all_logs(int client_id);
|
||||
|
||||
/* Disables all the Event ID for a given client. The Input parameters are:
|
||||
1. Client ID */
|
||||
int diag_disable_all_events(int client_id);
|
||||
|
||||
/* Votes for real time or non real time mode. The Input paramters are:
|
||||
1. Client ID
|
||||
2. The desired mode - MODE_REALTIME or MODE_NONREALTIME */
|
||||
int diag_dci_vote_real_time(int client_id, int real_time);
|
||||
|
||||
/* Gets the current mode (Real time or Non Real Time ) Diag is in.
|
||||
The Input parameters are:
|
||||
1. A pointer to an integer that will hold the result */
|
||||
int diag_dci_get_real_time_status(int *real_time);
|
||||
|
||||
/* Gets the current mode (Real time or Non Real Time ) Diag is
|
||||
in, in the requested processor. The Input parameters are:
|
||||
1. processor the client is interested in
|
||||
2. A pointer to an integer that will hold the result*/
|
||||
int diag_dci_get_real_time_status_proc(int proc, int *real_time);
|
||||
|
||||
/* Registers a signal to be fired on receiving DCI data from
|
||||
the peripherals. The input parameters are:
|
||||
1. Client ID
|
||||
2. Signal Type */
|
||||
int diag_register_dci_signal_data(int client_id, int signal_type);
|
||||
|
||||
/* Disables the signal that fires on receiving DCI data from
|
||||
the peripherals. The input parameters are:
|
||||
1. Client ID
|
||||
2. Signal Type */
|
||||
int diag_deregister_dci_signal_data(int client_id);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* DIAG_LSM_DCI_H */
|
||||
|
||||
679
feeds/ipq95xx/qca-diag/src/include/diagcmd.h
Executable file
679
feeds/ipq95xx/qca-diag/src/include/diagcmd.h
Executable file
@@ -0,0 +1,679 @@
|
||||
#ifndef DIAGCMD_H
|
||||
#define DIAGCMD_H
|
||||
/*!
|
||||
@ingroup packet_service
|
||||
@file diagcmd.h
|
||||
|
||||
@brief
|
||||
|
||||
Diagnostic Services Packet Processing Command Code Defintions
|
||||
|
||||
|
||||
@details
|
||||
This file contains packet id definitions and enumeration constants for subsystem identifiers (diagpkt_subsys_cmd_enum_type)
|
||||
for the serial interface to the dmss. All packets must have unique identifiers (command codes). Once published, an identifier cannot
|
||||
be changed. Subsystem identifiers (SSIDs) allow each technology area to define, grow, and maintain a list of unique packet identifiers
|
||||
without coordinating with each other. It is required that all clients of the diagnostic dispatching service use the subsystem commands.
|
||||
Subsystem Identifiers 250 to 254 are reserved for OEMs use only .Please refer to the documentation of 80-V1294-1 for the packet request/response
|
||||
defintions of each packet id .
|
||||
|
||||
@note
|
||||
DO NOT MODIFY THIS FILE WITHOUT PRIOR APPROVAL
|
||||
Diag commands, by design, are a tightly controlled set of values.
|
||||
Developers may not create command IDs at will.
|
||||
Request new commands using the following process:
|
||||
|
||||
1. Send email to asw.diag.request requesting command ID assignments.
|
||||
2. Identify the command needed by name.
|
||||
3. Provide a brief description for the command.
|
||||
|
||||
*/
|
||||
|
||||
/*
|
||||
Copyright (c) 1993-2015 by Qualcomm Technologies, Incorporated. All Rights Reserved.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
$Header: //source/qcom/qct/core/api/services/diag/main/latest/diagcmd.h#48 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
08/04/14 xy Added DIAG_SUBSYS_AOSTLM_TEST
|
||||
06/18/14 xy Added DIAG_SUBSYS_STORAGE and DIAG_SUBSYS_WCI2
|
||||
11/13/13 xy Added DIAG_QSR4_EXT_MSG_TERSE_F
|
||||
10/09/13 xy Added DIAG_SUBSYS_IMS_QVP_RTP
|
||||
09/25/13 xy Added DIAG_SUBSYS_LWIP
|
||||
08/26/13 sr Added DIAG_SUBSYS_CNSS_POWER
|
||||
06/26/13 sr Added DIAG_SUBSYS_SYSTEM_OPERATIONS
|
||||
05/31/13 sr Removed the peek and poke cmds
|
||||
05/08/13 sr Added DIAG_SUBSYS_DS_IPA
|
||||
03/22/13 sr Added DIAG_SUBSYS_LIMITSMGR
|
||||
10/23/12 sr Added DIAG_SUBSYS_FTM_ANT
|
||||
09/19/12 rh Added DIAG_SUBSYS_TTLITE
|
||||
09/17/12 rh Added DIAG_SUBSYS_GNSS_SOC
|
||||
08/13/12 rh Added DIAG_SUBSYS_CXM
|
||||
06/22/12 rh Added subsystem ID for QDSS
|
||||
06/06/12 rh Added subsystem ID DIAG_SUBSYS_MPOWER
|
||||
01/16/12 tbg Added Secure Service Module error response
|
||||
01/03/12 is Add subsystem ID for TDSCDMA
|
||||
10/21/11 rh CMAPI subsystem id added
|
||||
10/18/11 hm New DCI commands added
|
||||
07/01/11 hm Allocated subsystem command codes for Flash
|
||||
04/06/11 hm Added subsystem id for 3GPP NAS team
|
||||
02/25/11 hm Added subsystem id for USCRIPT tool
|
||||
01/18/11 hm Added subsystem id for Q5 CORE
|
||||
09/22/10 vg Added subsystem id for STRIDE
|
||||
07/15/10 sg Added subsystem id for QNP
|
||||
05/21/10 sg Doxygenated the file
|
||||
05/16/10 as Added cmd_codes 101,102,105&106 for backward comparibility
|
||||
04/21/10 sg Added new SSID for Ulog Services
|
||||
04/20/10 is Remove support for DIAG_GET_PROPERTY_F, DIAG_PUT_PROPERTY_F,
|
||||
DIAG_GET_PERM_PROPERTY_F, and DIAG_PUT_PERM_PROPERTY_F.
|
||||
06/10/02 lcl/jwh FEATURE_HWTC changes.
|
||||
05/23/02 sfh Added DIAG_PROTOCOL_LOOPBACK_F (123) command.
|
||||
06/27/01 lad Assigned equipment ID 0 to be for OEMs to use.
|
||||
05/21/01 sfh Added DIAG_TRACE_EVENT_REPORT_F for trace event support.
|
||||
04/17/01 lad Moved subsystem dispatch IDs from diagpkt.h.
|
||||
04/06/01 lad Changed the name of cmd code 111 from DUAG_TUNNEL_F to
|
||||
DIAG_ROUTE_F.
|
||||
02/23/01 lad Cosmetic changes.
|
||||
09/06/00 bgc Added support for FEATURE_FACTORY_TESTMODE with
|
||||
DIAG_FTM_CMD_F (set to 59, which is also DIAG_TMOB_F).
|
||||
08/31/00 lad Added command code for tunneling capability.
|
||||
06/23/00 lad Removed obsolete command codes and marked them "reserved".
|
||||
06/19/00 lad Added DIAG_PARM_RETRIEVE_F
|
||||
05/31/00 jal Added GPS statistics, session control, and grid support.
|
||||
05/15/00 lad Added streaming config support (nice).
|
||||
02/28/00 lad Added codes for event reporting service.
|
||||
02/02/00 lad Added commands used with FEATURE_DIAG_QCT_EXT.
|
||||
09/17/99 lcc Merged in RPC support from PLT archive.
|
||||
08/17/99 tac Merged in EFS changes from branch.
|
||||
07/19/99 sk Replacing reset_sup_fer with walsh code.
|
||||
07/19/99 sk Added walsh code display command.
|
||||
03/30/99 lad Added support for FEATURE_IS95B_MDR and FEATURE_SPECIAL_MDR.
|
||||
11/04/98 lad Added 1998/1999 copyright information.
|
||||
10/29/98 jmk Merged Module command changes into the mainline.
|
||||
(Replaced MOD_GET_STATUS with MOD_EXTENDED_PKT cmd code 75)
|
||||
10/27/98 jmk Added cmd IDs for CSS command, and SMS message read/write.
|
||||
09/11/98 grl Added feature query command
|
||||
10/06/97 jjn Added new commands for the Module Phase 1 interface. These
|
||||
include Module Status Mask, AKEY and audio control packets.
|
||||
04/23/97 jjn Added new packet pair to allow System Unit to access
|
||||
service option and caller ID information
|
||||
03/25/97 jjn Added new command (and packets) that allow writing to NV
|
||||
without going offline (for the Module only)
|
||||
02/28/97 jjn Enabled RSSI packets for the Module, added a packet for
|
||||
module status and sound reporting, and added a pcket for
|
||||
retrieving SMS messages
|
||||
06/25/96 jmk Added cmd id for preferred roaming list read.
|
||||
06/24/96 jmk Added cmd id for preferred roaming list write.
|
||||
04/09/96 jmk Added cmd ids for sending security code, and return code
|
||||
if phone is not unlocked for operations that require it.
|
||||
03/06/96 jmk Added command id for serial mode change (to AT cmd mode)
|
||||
and command id for get rssi (for antenna aiming/WLL only)
|
||||
08/16/95 jmk Added command id for parm_get2 (includes MUX2 parms)
|
||||
08/10/95 jmk Added command id for Phone State, Pilot Sets and SPC reqs
|
||||
01/28/95 ptw Added command id to obtain System Time from the mobile.
|
||||
12/07/94 jmk Added command id for portable sleep on/off request.
|
||||
11/07/94 jmk Added command to request that seq_nums be used in pkts.
|
||||
09/26/94 jmk Put DIAG_ORIG_F and DIAG_END_F back in.
|
||||
07/23/93 twp Added DIAG_TMOB_F
|
||||
01/14/93 twp First release
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/*--------------------------------------------------------------------------
|
||||
|
||||
Command Codes between the Diagnostic Monitor and the mobile. Packets
|
||||
travelling in each direction are defined here, while the packet templates
|
||||
for requests and responses are distinct. Note that the same packet id
|
||||
value can be used for both a request and a response. These values
|
||||
are used to index a dispatch table in diag.c, so
|
||||
|
||||
DON'T CHANGE THE NUMBERS ( REPLACE UNUSED IDS WITH FILLERS ). NEW IDs
|
||||
MUST BE ASSIGNED AT THE END.
|
||||
|
||||
----------------------------------------------------------------------------*/
|
||||
|
||||
/*!
|
||||
@cond DOXYGEN_BLOAT
|
||||
*/
|
||||
/* Version Number Request/Response */
|
||||
#define DIAG_VERNO_F 0
|
||||
|
||||
/* Mobile Station ESN Request/Response */
|
||||
#define DIAG_ESN_F 1
|
||||
|
||||
/* 2-11 Obsolete */
|
||||
|
||||
|
||||
/* DMSS status Request/Response */
|
||||
#define DIAG_STATUS_F 12
|
||||
|
||||
/* 13-14 Reserved */
|
||||
|
||||
/* Set logging mask Request/Response */
|
||||
#define DIAG_LOGMASK_F 15
|
||||
|
||||
/* Log packet Request/Response */
|
||||
#define DIAG_LOG_F 16
|
||||
|
||||
/* Peek at NV memory Request/Response */
|
||||
#define DIAG_NV_PEEK_F 17
|
||||
|
||||
/* Poke at NV memory Request/Response */
|
||||
#define DIAG_NV_POKE_F 18
|
||||
|
||||
/* Invalid Command Response */
|
||||
#define DIAG_BAD_CMD_F 19
|
||||
|
||||
/* Invalid parmaeter Response */
|
||||
#define DIAG_BAD_PARM_F 20
|
||||
|
||||
/* Invalid packet length Response */
|
||||
#define DIAG_BAD_LEN_F 21
|
||||
|
||||
/* 22-23 Reserved */
|
||||
|
||||
/* Packet not allowed in this mode
|
||||
( online vs offline ) */
|
||||
#define DIAG_BAD_MODE_F 24
|
||||
|
||||
/* info for TA power and voice graphs */
|
||||
#define DIAG_TAGRAPH_F 25
|
||||
|
||||
/* Markov statistics */
|
||||
#define DIAG_MARKOV_F 26
|
||||
|
||||
/* Reset of Markov statistics */
|
||||
#define DIAG_MARKOV_RESET_F 27
|
||||
|
||||
/* Return diag version for comparison to
|
||||
detect incompatabilities */
|
||||
#define DIAG_DIAG_VER_F 28
|
||||
|
||||
/* Return a timestamp */
|
||||
#define DIAG_TS_F 29
|
||||
|
||||
/* Set TA parameters */
|
||||
#define DIAG_TA_PARM_F 30
|
||||
|
||||
/* Request for msg report */
|
||||
#define DIAG_MSG_F 31
|
||||
|
||||
/* Handset Emulation -- keypress */
|
||||
#define DIAG_HS_KEY_F 32
|
||||
|
||||
/* Handset Emulation -- lock or unlock */
|
||||
#define DIAG_HS_LOCK_F 33
|
||||
|
||||
/* Handset Emulation -- display request */
|
||||
#define DIAG_HS_SCREEN_F 34
|
||||
|
||||
/* 35 Reserved */
|
||||
|
||||
/* Parameter Download */
|
||||
#define DIAG_PARM_SET_F 36
|
||||
|
||||
/* 37 Reserved */
|
||||
|
||||
/* Read NV item */
|
||||
#define DIAG_NV_READ_F 38
|
||||
/* Write NV item */
|
||||
#define DIAG_NV_WRITE_F 39
|
||||
/* 40 Reserved */
|
||||
|
||||
/* Mode change request */
|
||||
#define DIAG_CONTROL_F 41
|
||||
|
||||
/* Error record retreival */
|
||||
#define DIAG_ERR_READ_F 42
|
||||
|
||||
/* Error record clear */
|
||||
#define DIAG_ERR_CLEAR_F 43
|
||||
|
||||
/* Symbol error rate counter reset */
|
||||
#define DIAG_SER_RESET_F 44
|
||||
|
||||
/* Symbol error rate counter report */
|
||||
#define DIAG_SER_REPORT_F 45
|
||||
|
||||
/* Run a specified test */
|
||||
#define DIAG_TEST_F 46
|
||||
|
||||
/* Retreive the current dip switch setting */
|
||||
#define DIAG_GET_DIPSW_F 47
|
||||
|
||||
/* Write new dip switch setting */
|
||||
#define DIAG_SET_DIPSW_F 48
|
||||
|
||||
/* Start/Stop Vocoder PCM loopback */
|
||||
#define DIAG_VOC_PCM_LB_F 49
|
||||
|
||||
/* Start/Stop Vocoder PKT loopback */
|
||||
#define DIAG_VOC_PKT_LB_F 50
|
||||
|
||||
/* 51-52 Reserved */
|
||||
|
||||
/* Originate a call */
|
||||
#define DIAG_ORIG_F 53
|
||||
/* End a call */
|
||||
#define DIAG_END_F 54
|
||||
/* 55-57 Reserved */
|
||||
|
||||
/* Switch to downloader */
|
||||
#define DIAG_DLOAD_F 58
|
||||
/* Test Mode Commands and FTM commands */
|
||||
#define DIAG_TMOB_F 59
|
||||
/* Test Mode Commands and FTM commands */
|
||||
#define DIAG_FTM_CMD_F 59
|
||||
/* 60-62 Reserved */
|
||||
|
||||
/* Featurization Removal requested by CMI
|
||||
#ifdef FEATURE_HWTC
|
||||
*/
|
||||
|
||||
#define DIAG_TEST_STATE_F 61
|
||||
/*
|
||||
#endif
|
||||
*/
|
||||
|
||||
/* Return the current state of the phone */
|
||||
#define DIAG_STATE_F 63
|
||||
|
||||
/* Return all current sets of pilots */
|
||||
#define DIAG_PILOT_SETS_F 64
|
||||
|
||||
/* Send the Service Prog. Code to allow SP */
|
||||
#define DIAG_SPC_F 65
|
||||
|
||||
/* Invalid nv_read/write because SP is locked */
|
||||
#define DIAG_BAD_SPC_MODE_F 66
|
||||
|
||||
/* get parms obsoletes PARM_GET */
|
||||
#define DIAG_PARM_GET2_F 67
|
||||
|
||||
/* Serial mode change Request/Response */
|
||||
#define DIAG_SERIAL_CHG_F 68
|
||||
|
||||
/* 69 Reserved */
|
||||
|
||||
/* Send password to unlock secure operations
|
||||
the phone to be in a security state that
|
||||
is wasn't - like unlocked. */
|
||||
#define DIAG_PASSWORD_F 70
|
||||
|
||||
/* An operation was attempted which required */
|
||||
#define DIAG_BAD_SEC_MODE_F 71
|
||||
|
||||
/* Write Preferred Roaming list to the phone. */
|
||||
#define DIAG_PR_LIST_WR_F 72
|
||||
|
||||
/* Read Preferred Roaming list from the phone.*/
|
||||
#define DIAG_PR_LIST_RD_F 73
|
||||
|
||||
/* 74 Reserved */
|
||||
|
||||
/* Subssytem dispatcher (extended diag cmd) */
|
||||
#define DIAG_SUBSYS_CMD_F 75
|
||||
|
||||
/* 76-80 Reserved */
|
||||
|
||||
/* Asks the phone what it supports */
|
||||
#define DIAG_FEATURE_QUERY_F 81
|
||||
|
||||
/* 82 Reserved */
|
||||
|
||||
/* Read SMS message out of NV */
|
||||
#define DIAG_SMS_READ_F 83
|
||||
|
||||
/* Write SMS message into NV */
|
||||
#define DIAG_SMS_WRITE_F 84
|
||||
|
||||
/* info for Frame Error Rate
|
||||
on multiple channels */
|
||||
#define DIAG_SUP_FER_F 85
|
||||
|
||||
/* Supplemental channel walsh codes */
|
||||
#define DIAG_SUP_WALSH_CODES_F 86
|
||||
|
||||
/* Sets the maximum # supplemental
|
||||
channels */
|
||||
#define DIAG_SET_MAX_SUP_CH_F 87
|
||||
|
||||
/* get parms including SUPP and MUX2:
|
||||
obsoletes PARM_GET and PARM_GET_2 */
|
||||
#define DIAG_PARM_GET_IS95B_F 88
|
||||
|
||||
/* Performs an Embedded File System
|
||||
(EFS) operation. */
|
||||
#define DIAG_FS_OP_F 89
|
||||
|
||||
/* AKEY Verification. */
|
||||
#define DIAG_AKEY_VERIFY_F 90
|
||||
|
||||
/* Handset emulation - Bitmap screen */
|
||||
#define DIAG_BMP_HS_SCREEN_F 91
|
||||
|
||||
/* Configure communications */
|
||||
#define DIAG_CONFIG_COMM_F 92
|
||||
|
||||
/* Extended logmask for > 32 bits. */
|
||||
#define DIAG_EXT_LOGMASK_F 93
|
||||
|
||||
/* 94-95 reserved */
|
||||
|
||||
/* Static Event reporting. */
|
||||
#define DIAG_EVENT_REPORT_F 96
|
||||
|
||||
/* Load balancing and more! */
|
||||
#define DIAG_STREAMING_CONFIG_F 97
|
||||
|
||||
/* Parameter retrieval */
|
||||
#define DIAG_PARM_RETRIEVE_F 98
|
||||
|
||||
/* A state/status snapshot of the DMSS. */
|
||||
#define DIAG_STATUS_SNAPSHOT_F 99
|
||||
|
||||
/* 100 obsolete */
|
||||
|
||||
/* Get_property requests */
|
||||
#define DIAG_GET_PROPERTY_F 101
|
||||
|
||||
/* Put_property requests */
|
||||
#define DIAG_PUT_PROPERTY_F 102
|
||||
|
||||
/* Get_guid requests */
|
||||
#define DIAG_GET_GUID_F 103
|
||||
|
||||
/* Invocation of user callbacks */
|
||||
#define DIAG_USER_CMD_F 104
|
||||
|
||||
/* Get permanent properties */
|
||||
#define DIAG_GET_PERM_PROPERTY_F 105
|
||||
|
||||
/* Put permanent properties */
|
||||
#define DIAG_PUT_PERM_PROPERTY_F 106
|
||||
|
||||
/* Permanent user callbacks */
|
||||
#define DIAG_PERM_USER_CMD_F 107
|
||||
|
||||
/* GPS Session Control */
|
||||
#define DIAG_GPS_SESS_CTRL_F 108
|
||||
|
||||
/* GPS search grid */
|
||||
#define DIAG_GPS_GRID_F 109
|
||||
|
||||
/* GPS Statistics */
|
||||
#define DIAG_GPS_STATISTICS_F 110
|
||||
|
||||
/* Packet routing for multiple instances of diag */
|
||||
#define DIAG_ROUTE_F 111
|
||||
|
||||
/* IS2000 status */
|
||||
#define DIAG_IS2000_STATUS_F 112
|
||||
|
||||
/* RLP statistics reset */
|
||||
#define DIAG_RLP_STAT_RESET_F 113
|
||||
|
||||
/* (S)TDSO statistics reset */
|
||||
#define DIAG_TDSO_STAT_RESET_F 114
|
||||
|
||||
/* Logging configuration packet */
|
||||
#define DIAG_LOG_CONFIG_F 115
|
||||
|
||||
/* Static Trace Event reporting */
|
||||
#define DIAG_TRACE_EVENT_REPORT_F 116
|
||||
|
||||
/* SBI Read */
|
||||
#define DIAG_SBI_READ_F 117
|
||||
|
||||
/* SBI Write */
|
||||
#define DIAG_SBI_WRITE_F 118
|
||||
|
||||
/* SSD Verify */
|
||||
#define DIAG_SSD_VERIFY_F 119
|
||||
|
||||
/* Log on Request */
|
||||
#define DIAG_LOG_ON_DEMAND_F 120
|
||||
|
||||
/* Request for extended msg report */
|
||||
#define DIAG_EXT_MSG_F 121
|
||||
|
||||
/* ONCRPC diag packet */
|
||||
#define DIAG_ONCRPC_F 122
|
||||
|
||||
/* Diagnostics protocol loopback. */
|
||||
#define DIAG_PROTOCOL_LOOPBACK_F 123
|
||||
|
||||
/* Extended build ID text */
|
||||
#define DIAG_EXT_BUILD_ID_F 124
|
||||
|
||||
/* Request for extended msg report */
|
||||
#define DIAG_EXT_MSG_CONFIG_F 125
|
||||
|
||||
/* Extended messages in terse format */
|
||||
#define DIAG_EXT_MSG_TERSE_F 126
|
||||
|
||||
/* Translate terse format message identifier */
|
||||
#define DIAG_EXT_MSG_TERSE_XLATE_F 127
|
||||
|
||||
/* Subssytem dispatcher Version 2 (delayed response capable) */
|
||||
#define DIAG_SUBSYS_CMD_VER_2_F 128
|
||||
|
||||
/* Get the event mask */
|
||||
#define DIAG_EVENT_MASK_GET_F 129
|
||||
|
||||
/* Set the event mask */
|
||||
#define DIAG_EVENT_MASK_SET_F 130
|
||||
|
||||
/* RESERVED CODES: 131-139 */
|
||||
|
||||
/* Command Code for Changing Port Settings */
|
||||
#define DIAG_CHANGE_PORT_SETTINGS 140
|
||||
|
||||
/* Country network information for assisted dialing */
|
||||
#define DIAG_CNTRY_INFO_F 141
|
||||
|
||||
/* Send a Supplementary Service Request */
|
||||
#define DIAG_SUPS_REQ_F 142
|
||||
|
||||
/* Originate SMS request for MMS */
|
||||
#define DIAG_MMS_ORIG_SMS_REQUEST_F 143
|
||||
|
||||
/* Change measurement mode*/
|
||||
#define DIAG_MEAS_MODE_F 144
|
||||
|
||||
/* Request measurements for HDR channels */
|
||||
#define DIAG_MEAS_REQ_F 145
|
||||
|
||||
/* Send Optimized F3 messages */
|
||||
#define DIAG_QSR_EXT_MSG_TERSE_F 146
|
||||
|
||||
/* Packet ID for command/responses sent over DCI */
|
||||
#define DIAG_DCI_CMD_REQ 147
|
||||
|
||||
/* Packet ID for delayed responses sent over DCI */
|
||||
#define DIAG_DCI_DELAYED_RSP 148
|
||||
|
||||
/* Error response code on DCI (only APSS side) */
|
||||
#define DIAG_BAD_TRANS_F 149
|
||||
|
||||
/* Error response code for cmomands disallowed by SSM */
|
||||
#define DIAG_SSM_DISALLOWED_CMD_F 150
|
||||
|
||||
/* Log on extended Request */
|
||||
#define DIAG_LOG_ON_DEMAND_EXT_F 151
|
||||
|
||||
/* Packet ID for extended event/log/F3 pkt */
|
||||
#define DIAG_CMD_EXT_F 152
|
||||
|
||||
/*Qshrink4 command code for Qshrink 4 packet*/
|
||||
#define DIAG_QSR4_EXT_MSG_TERSE_F 153
|
||||
|
||||
/*DCI command code for dci control packet*/
|
||||
#define DIAG_DCI_CONTROL_PACKET 154
|
||||
|
||||
/*Compressed diag data which is sent out by the DMSS to the host.*/
|
||||
#define DIAG_COMPRESSED_PKT 155
|
||||
|
||||
|
||||
/* Number of packets defined. */
|
||||
#define DIAG_MAX_F 155
|
||||
|
||||
|
||||
|
||||
typedef enum {
|
||||
DIAG_SUBSYS_OEM = 0, /* Reserved for OEM use */
|
||||
DIAG_SUBSYS_ZREX = 1, /* ZREX */
|
||||
DIAG_SUBSYS_SD = 2, /* System Determination */
|
||||
DIAG_SUBSYS_BT = 3, /* Bluetooth */
|
||||
DIAG_SUBSYS_WCDMA = 4, /* WCDMA */
|
||||
DIAG_SUBSYS_HDR = 5, /* 1xEvDO */
|
||||
DIAG_SUBSYS_DIABLO = 6, /* DIABLO */
|
||||
DIAG_SUBSYS_TREX = 7, /* TREX - Off-target testing environments */
|
||||
DIAG_SUBSYS_GSM = 8, /* GSM */
|
||||
DIAG_SUBSYS_UMTS = 9, /* UMTS */
|
||||
DIAG_SUBSYS_HWTC = 10, /* HWTC */
|
||||
DIAG_SUBSYS_FTM = 11, /* Factory Test Mode */
|
||||
DIAG_SUBSYS_REX = 12, /* Rex */
|
||||
DIAG_SUBSYS_OS = DIAG_SUBSYS_REX,
|
||||
DIAG_SUBSYS_GPS = 13, /* Global Positioning System */
|
||||
DIAG_SUBSYS_WMS = 14, /* Wireless Messaging Service (WMS, SMS) */
|
||||
DIAG_SUBSYS_CM = 15, /* Call Manager */
|
||||
DIAG_SUBSYS_HS = 16, /* Handset */
|
||||
DIAG_SUBSYS_AUDIO_SETTINGS = 17, /* Audio Settings */
|
||||
DIAG_SUBSYS_DIAG_SERV = 18, /* DIAG Services */
|
||||
DIAG_SUBSYS_FS = 19, /* File System - EFS2 */
|
||||
DIAG_SUBSYS_PORT_MAP_SETTINGS = 20, /* Port Map Settings */
|
||||
DIAG_SUBSYS_MEDIAPLAYER = 21, /* QCT Mediaplayer */
|
||||
DIAG_SUBSYS_QCAMERA = 22, /* QCT QCamera */
|
||||
DIAG_SUBSYS_MOBIMON = 23, /* QCT MobiMon */
|
||||
DIAG_SUBSYS_GUNIMON = 24, /* QCT GuniMon */
|
||||
DIAG_SUBSYS_LSM = 25, /* Location Services Manager */
|
||||
DIAG_SUBSYS_QCAMCORDER = 26, /* QCT QCamcorder */
|
||||
DIAG_SUBSYS_MUX1X = 27, /* Multiplexer */
|
||||
DIAG_SUBSYS_DATA1X = 28, /* Data */
|
||||
DIAG_SUBSYS_SRCH1X = 29, /* Searcher */
|
||||
DIAG_SUBSYS_CALLP1X = 30, /* Call Processor */
|
||||
DIAG_SUBSYS_APPS = 31, /* Applications */
|
||||
DIAG_SUBSYS_SETTINGS = 32, /* Settings */
|
||||
DIAG_SUBSYS_GSDI = 33, /* Generic SIM Driver Interface */
|
||||
DIAG_SUBSYS_UIMDIAG = DIAG_SUBSYS_GSDI,
|
||||
DIAG_SUBSYS_TMC = 34, /* Task Main Controller */
|
||||
DIAG_SUBSYS_USB = 35, /* Universal Serial Bus */
|
||||
DIAG_SUBSYS_PM = 36, /* Power Management */
|
||||
DIAG_SUBSYS_DEBUG = 37,
|
||||
DIAG_SUBSYS_QTV = 38,
|
||||
DIAG_SUBSYS_CLKRGM = 39, /* Clock Regime */
|
||||
DIAG_SUBSYS_DEVICES = 40,
|
||||
DIAG_SUBSYS_WLAN = 41, /* 802.11 Technology */
|
||||
DIAG_SUBSYS_PS_DATA_LOGGING = 42, /* Data Path Logging */
|
||||
DIAG_SUBSYS_PS = DIAG_SUBSYS_PS_DATA_LOGGING,
|
||||
DIAG_SUBSYS_MFLO = 43, /* MediaFLO */
|
||||
DIAG_SUBSYS_DTV = 44, /* Digital TV */
|
||||
DIAG_SUBSYS_RRC = 45, /* WCDMA Radio Resource Control state */
|
||||
DIAG_SUBSYS_PROF = 46, /* Miscellaneous Profiling Related */
|
||||
DIAG_SUBSYS_TCXOMGR = 47,
|
||||
DIAG_SUBSYS_NV = 48, /* Non Volatile Memory */
|
||||
DIAG_SUBSYS_AUTOCONFIG = 49,
|
||||
DIAG_SUBSYS_PARAMS = 50, /* Parameters required for debugging subsystems */
|
||||
DIAG_SUBSYS_MDDI = 51, /* Mobile Display Digital Interface */
|
||||
DIAG_SUBSYS_DS_ATCOP = 52,
|
||||
DIAG_SUBSYS_L4LINUX = 53, /* L4/Linux */
|
||||
DIAG_SUBSYS_MVS = 54, /* Multimode Voice Services */
|
||||
DIAG_SUBSYS_CNV = 55, /* Compact NV */
|
||||
DIAG_SUBSYS_APIONE_PROGRAM = 56, /* apiOne */
|
||||
DIAG_SUBSYS_HIT = 57, /* Hardware Integration Test */
|
||||
DIAG_SUBSYS_DRM = 58, /* Digital Rights Management */
|
||||
DIAG_SUBSYS_DM = 59, /* Device Management */
|
||||
DIAG_SUBSYS_FC = 60, /* Flow Controller */
|
||||
DIAG_SUBSYS_MEMORY = 61, /* Malloc Manager */
|
||||
DIAG_SUBSYS_FS_ALTERNATE = 62, /* Alternate File System */
|
||||
DIAG_SUBSYS_REGRESSION = 63, /* Regression Test Commands */
|
||||
DIAG_SUBSYS_SENSORS = 64, /* The sensors subsystem */
|
||||
DIAG_SUBSYS_FLUTE = 65, /* FLUTE */
|
||||
DIAG_SUBSYS_ANALOG = 66, /* Analog die subsystem */
|
||||
DIAG_SUBSYS_APIONE_PROGRAM_MODEM = 67, /* apiOne Program On Modem Processor */
|
||||
DIAG_SUBSYS_LTE = 68, /* LTE */
|
||||
DIAG_SUBSYS_BREW = 69, /* BREW */
|
||||
DIAG_SUBSYS_PWRDB = 70, /* Power Debug Tool */
|
||||
DIAG_SUBSYS_CHORD = 71, /* Chaos Coordinator */
|
||||
DIAG_SUBSYS_SEC = 72, /* Security */
|
||||
DIAG_SUBSYS_TIME = 73, /* Time Services */
|
||||
DIAG_SUBSYS_Q6_CORE = 74, /* Q6 core services */
|
||||
DIAG_SUBSYS_COREBSP = 75, /* CoreBSP */
|
||||
/* Command code allocation:
|
||||
[0 - 2047] - HWENGINES
|
||||
[2048 - 2147] - MPROC
|
||||
[2148 - 2247] - BUSES
|
||||
[2248 - 2347] - USB
|
||||
[2348 - 2447] - FLASH
|
||||
[2448 - 3447] - UART
|
||||
[3448 - 3547] - PRODUCTS
|
||||
[3547 - 65535] - Reserved
|
||||
*/
|
||||
|
||||
DIAG_SUBSYS_MFLO2 = 76, /* Media Flow */
|
||||
/* Command code allocation:
|
||||
[0 - 1023] - APPs
|
||||
[1024 - 65535] - Reserved
|
||||
*/
|
||||
DIAG_SUBSYS_ULOG = 77, /* ULog Services */
|
||||
DIAG_SUBSYS_APR = 78, /* Asynchronous Packet Router (Yu, Andy)*/
|
||||
DIAG_SUBSYS_QNP = 79 , /*QNP (Ravinder Are , Arun Harnoor)*/
|
||||
DIAG_SUBSYS_STRIDE = 80 , /* Ivailo Petrov */
|
||||
DIAG_SUBSYS_OEMDPP = 81 , /* to read/write calibration to DPP partition */
|
||||
DIAG_SUBSYS_Q5_CORE = 82 , /* Requested by ADSP team */
|
||||
DIAG_SUBSYS_USCRIPT = 83 , /* core/power team USCRIPT tool */
|
||||
DIAG_SUBSYS_NAS = 84 , /* Requested by 3GPP NAS team */
|
||||
DIAG_SUBSYS_CMAPI = 85 , /* Requested by CMAPI */
|
||||
DIAG_SUBSYS_SSM = 86,
|
||||
DIAG_SUBSYS_TDSCDMA = 87, /* Requested by TDSCDMA team */
|
||||
DIAG_SUBSYS_SSM_TEST = 88,
|
||||
DIAG_SUBSYS_MPOWER = 89, /* Requested by MPOWER team */
|
||||
DIAG_SUBSYS_QDSS = 90, /* For QDSS STM commands */
|
||||
DIAG_SUBSYS_CXM = 91,
|
||||
DIAG_SUBSYS_GNSS_SOC = 92, /* Secondary GNSS system */
|
||||
DIAG_SUBSYS_TTLITE = 93,
|
||||
DIAG_SUBSYS_FTM_ANT = 94,
|
||||
DIAG_SUBSYS_MLOG = 95,
|
||||
DIAG_SUBSYS_LIMITSMGR = 96,
|
||||
DIAG_SUBSYS_EFSMONITOR = 97,
|
||||
DIAG_SUBSYS_DISPLAY_CALIBRATION = 98,
|
||||
DIAG_SUBSYS_VERSION_REPORT = 99,
|
||||
DIAG_SUBSYS_DS_IPA = 100,
|
||||
DIAG_SUBSYS_SYSTEM_OPERATIONS = 101,
|
||||
DIAG_SUBSYS_CNSS_POWER = 102,
|
||||
DIAG_SUBSYS_LWIP = 103,
|
||||
DIAG_SUBSYS_IMS_QVP_RTP = 104,
|
||||
DIAG_SUBSYS_STORAGE = 105,
|
||||
DIAG_SUBSYS_WCI2 = 106,
|
||||
DIAG_SUBSYS_AOSTLM_TEST = 107,
|
||||
DIAG_SUBSYS_CFCM = 108,
|
||||
DIAG_SUBSYS_CORE_SERVICES = 109,
|
||||
DIAG_SUBSYS_CVD = 110,
|
||||
DIAG_SUBSYS_MCFG = 111,
|
||||
DIAG_SUBSYS_MODEM_STRESSFW = 112,
|
||||
DIAG_SUBSYS_LAST,
|
||||
|
||||
/* Subsystem IDs reserved for OEM use */
|
||||
DIAG_SUBSYS_RESERVED_OEM_0 = 250,
|
||||
DIAG_SUBSYS_RESERVED_OEM_1 = 251,
|
||||
DIAG_SUBSYS_RESERVED_OEM_2 = 252,
|
||||
DIAG_SUBSYS_RESERVED_OEM_3 = 253,
|
||||
DIAG_SUBSYS_RESERVED_OEM_4 = 254,
|
||||
DIAG_SUBSYS_LEGACY = 255
|
||||
} diagpkt_subsys_cmd_enum_type;
|
||||
/*!
|
||||
@endcond
|
||||
*/
|
||||
#endif /* DIAGCMD_H */
|
||||
|
||||
|
||||
|
||||
96
feeds/ipq95xx/qca-diag/src/include/diagi.h
Executable file
96
feeds/ipq95xx/qca-diag/src/include/diagi.h
Executable file
@@ -0,0 +1,96 @@
|
||||
#ifndef DIAGI_H
|
||||
#define DIAGI_H
|
||||
/*==========================================================================
|
||||
|
||||
Diagnostic Subsystem Internal Header File
|
||||
|
||||
Description
|
||||
Shared declarations and prototypes internal to the Diagnostic subsystem.
|
||||
|
||||
# Copyright (c) 2007-2011, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
$Header: //depot/asic/msmshared/services/diag/DIAG_7K/diagi.h#1 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
10/01/08 sj Changes for CBSP2.0
|
||||
11/21/06 as Moved DIAG internal features from diagi.h to diag.h
|
||||
08/28/06 as Added win mobile featurization support.
|
||||
03/28/06 pc Changed DIAG_TX_APP_SIG from 0x00800000 to 0x00080000.
|
||||
10/19/05 as Modified diag_searchlist_type to make it 4-byte aligned.
|
||||
07/05/05 sl Added support for SPC_TIMEOUT to double the timeout value
|
||||
on consecutive incorrect SPCs.
|
||||
06/16/05 as New signal for DM to communicate completion.
|
||||
05/17/05 as Added new signal for Application processor data.
|
||||
10/24/01 jal New signal for SIO to indicate the UART is flushed.
|
||||
New signal for SIO to indicate port closure is complete.
|
||||
08/20/01 jal Supported more Diag packets. Added NV cache typedef,
|
||||
prototypes for diag_set_sp_state(), downloader status.
|
||||
06/27/01 lad Various non-functional changes to facilitate update of
|
||||
log services.
|
||||
04/06/01 lad Added definitions of DIAG_TASK_xxx sigs to decouple from
|
||||
task.h.
|
||||
ASYNC con<F2st definitions moved to diagcomm.h?
|
||||
Externalized msg_nice[] and log_nice[] for streaming config
|
||||
support.
|
||||
Moved prototype of diag_kick_watchdog() to diagtarget.h.
|
||||
Added prototype of diagpkt_process_request() (moved from
|
||||
diagpkt.h).
|
||||
Updated prototype for diag_do_escaping().
|
||||
Removed prototype for diag_do_unescaping().
|
||||
Removed references to diagpkt_refresh_cache().
|
||||
02/23/01 lad Rearchitected the diagnostics subsystem to be a service
|
||||
rather than a module. All coupling to targets has been
|
||||
moved to target-specific implementations. The only coupling
|
||||
that remains are common services and REX.
|
||||
Old history comments have been removed since most of them
|
||||
are no longer applicable.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
#include "diag.h"
|
||||
#include "diagpkt.h"
|
||||
#include "log.h"
|
||||
#include <string.h>
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
** Diag Task Signal Definitions
|
||||
** ------------------------------------------------------------------------- */
|
||||
// Added this for CBSP2.0
|
||||
typedef enum { /* begin feature_query_enum_type */
|
||||
FEATURE_QUERY_ENUM_LENGTH /* used to determine mask size */
|
||||
} feature_query_enum_type;
|
||||
|
||||
|
||||
/* The shortest length of the mask to cover all entries in the enum */
|
||||
#define FEATURE_MASK_LENGTH \
|
||||
((FEATURE_QUERY_ENUM_LENGTH / 8)+1)
|
||||
|
||||
|
||||
/* This specifies the last equipment ID for use in logging services. This is a
|
||||
* 4-bit value, so it cannot exceed 15. */
|
||||
#define LOG_EQUIP_ID_LAST LOG_EQUIP_ID_LAST_DEFAULT
|
||||
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
** Externalized data members
|
||||
** ------------------------------------------------------------------------- */
|
||||
|
||||
|
||||
|
||||
/* The following is used by the packet service to store rsp packets. */
|
||||
typedef struct {
|
||||
unsigned int pattern; /* Pattern to check validity of committed pointers. */
|
||||
unsigned int size; /* Size of usable buffer (diagpkt_q_type->pkt) */
|
||||
unsigned int length; /* Size of packet */
|
||||
byte pkt[DIAG_MAX_RX_PKT_SIZ]; /* Sized by 'length' field. */
|
||||
} diagpkt_rsp_type;
|
||||
|
||||
#endif /* DIAGI_H */
|
||||
203
feeds/ipq95xx/qca-diag/src/include/diaglogi.h
Executable file
203
feeds/ipq95xx/qca-diag/src/include/diaglogi.h
Executable file
@@ -0,0 +1,203 @@
|
||||
#ifndef DIAGLOGI_H
|
||||
#define DIAGLOGI_H
|
||||
/*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*
|
||||
|
||||
Logging Services internal header file
|
||||
|
||||
General Description
|
||||
Internal declarations to support data logging.
|
||||
|
||||
Initializing and Sequencing Requirements
|
||||
'log_init()' must be called once during initialization prior to use.
|
||||
|
||||
# Copyright (c) 2007-2011, 2014 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
*====*====*====*====*====*====*====*====*====*====*====*====*====*====*====*/
|
||||
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
10/01/08 sj Changes for CBSP2.0
|
||||
01/10/08 mad Added copyright and file description.
|
||||
12/5/07 as Created
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
|
||||
#include "log_codes.h"
|
||||
#include "./../include/log.h"
|
||||
// COMMENTED OUT FOR LINUX
|
||||
//#include "diagi.h"
|
||||
/* -------------------------------------------------------------------------
|
||||
* Definitions and Declarations
|
||||
* ------------------------------------------------------------------------- */
|
||||
typedef PACK(struct)
|
||||
{
|
||||
uint16 len; /* Specifies the length, in bytes of
|
||||
the entry, including this header. */
|
||||
|
||||
uint16 code; /* Specifies the log code for the
|
||||
entry as enumerated above.
|
||||
Note: This is specified as word
|
||||
to guarantee size. */
|
||||
// removed AMSS specific code
|
||||
//qword ts; // The system timestamp for the log entry. The upper 48 bits
|
||||
// represent elapsed time since 6 Jan 1980 00:00:00
|
||||
// in 1.25 ms units. The low order 16 bits represent elapsed
|
||||
// time since the last 1.25 ms tick in 1/32 chip units
|
||||
// (this 16 bit counter wraps at the value 49152).
|
||||
uint32 ts_lo; /* Time stamp */
|
||||
uint32 ts_hi;
|
||||
|
||||
} log_header_type;
|
||||
|
||||
#ifndef EQUIP_ID_MAX
|
||||
#define EQUIP_ID_MAX 16
|
||||
#endif
|
||||
|
||||
typedef enum
|
||||
{
|
||||
LOG_INIT_STATE = 0,
|
||||
LOG_NORMAL_STATE,
|
||||
LOG_FLUSH_STATE, /* Pending flush operation. */
|
||||
LOG_PANIC_STATE /* Panic mode flush in progress */
|
||||
|
||||
} log_state_enum_type;
|
||||
|
||||
//static log_state_enum_type log_state = LOG_INIT_STATE;
|
||||
static void *log_commit_last = NULL; /* Many writers, 1 reader (DIAG) */
|
||||
//static void *log_flush_last = NULL; /* 1 writer, 1 reader (both DIAG) */
|
||||
|
||||
|
||||
#define LOG_DIAGPKT_OFFSET FPOS(diag_log_rsp_type, log)
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
* Definitions for last log code per equipment ID.
|
||||
* If it is undefined, it is defined to 0. digatune.h need only to
|
||||
* contain values for included equipment IDs.
|
||||
* ------------------------------------------------------------------------- */
|
||||
#if !defined (LOG_EQUIP_ID_0_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_0_LAST_CODE LOG_EQUIP_ID_0_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_1_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_1_LAST_CODE LOG_EQUIP_ID_1_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_2_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_2_LAST_CODE LOG_EQUIP_ID_2_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_3_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_3_LAST_CODE LOG_EQUIP_ID_3_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_4_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_4_LAST_CODE LOG_EQUIP_ID_4_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_5_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_5_LAST_CODE LOG_EQUIP_ID_5_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_6_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_6_LAST_CODE LOG_EQUIP_ID_6_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_7_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_7_LAST_CODE LOG_EQUIP_ID_7_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_8_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_8_LAST_CODE LOG_EQUIP_ID_8_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_9_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_9_LAST_CODE LOG_EQUIP_ID_9_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_10_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_10_LAST_CODE LOG_EQUIP_ID_10_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_11_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_11_LAST_CODE LOG_EQUIP_ID_11_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_12_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_12_LAST_CODE LOG_EQUIP_ID_12_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_13_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_13_LAST_CODE LOG_EQUIP_ID_13_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_14_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_14_LAST_CODE LOG_EQUIP_ID_14_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
#if !defined (LOG_EQUIP_ID_15_LAST_CODE)
|
||||
#define LOG_EQUIP_ID_15_LAST_CODE LOG_EQUIP_ID_15_LAST_CODE_DEFAULT
|
||||
#endif
|
||||
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
* Logging mask implementation details.
|
||||
*
|
||||
* The logging mask stores a bit for every code within the range specified
|
||||
* in log_codes.h. Each equipment ID has a mask that is represented
|
||||
* as an array of bytes. All of this are listed in an array of bytes
|
||||
* of size 'LOG_MASK_SIZE'. An offset into this array is used to determine
|
||||
* the start of the mask associated with a particular equipment ID.
|
||||
*
|
||||
* The range is inclusive, meaning the beginning (0) and end value
|
||||
* ('LOG_EQUIP_ID_xxx_LAST_ITEM') are included in the range. Therefore, all
|
||||
* equipment IDs have at least 1 byte (range 0-0).
|
||||
*
|
||||
* 'log_mask' is the mask of bits used to represent the configuration of all
|
||||
* log codes. '1' denotes the code being enabled, '0' denotes disabled.
|
||||
*
|
||||
* 'log_last_item_tbl' is an array of offsets into log_mask indexed by
|
||||
* equipment ID.
|
||||
*
|
||||
* 'LOG_MASK_ARRAY_INDEX()' determine the index into the mask for a given
|
||||
* equipment ID.
|
||||
*
|
||||
* 'LOG_MASK_BIT_MASK()' gives the bit of the code within its byte in the
|
||||
* mask.
|
||||
*
|
||||
* 'LOG_GET_EQUIP_ID()' retuns the equipment ID of a given log code.
|
||||
*
|
||||
* 'LOG_GET_ITEM_NUM()' returns the item number of a given log code.
|
||||
*
|
||||
* 'log_mask_enabled()' returns non-zero if a code is enabled.
|
||||
*
|
||||
* 'log_set_equip_id()' sets the equipment ID in a log code.
|
||||
*
|
||||
* ------------------------------------------------------------------------- */
|
||||
|
||||
#define LOG_MASK_ARRAY_INDEX(xx_item) ((xx_item) >> 3)
|
||||
|
||||
#define LOG_MASK_BIT_MASK(xx_item) (0x01 << ((xx_item) & 7))
|
||||
|
||||
#define LOG_GET_EQUIP_ID(xx_code) ((((log_code_type) (xx_code)) >> 12) & 0x000F)
|
||||
|
||||
#define LOG_GET_ITEM_NUM(xx_code) (((log_code_type) (xx_code)) & 0x0FFF)
|
||||
|
||||
/* This computes the number of bytes in the log mask array. */
|
||||
#define MAX_EQUIP_ID 16
|
||||
#define MAX_ITEMS_PER_EQUIP_ID 512
|
||||
#define LOG_MASK_ITEM_SIZE (sizeof(uint8) + sizeof(unsigned int) + MAX_ITEMS_PER_EQUIP_ID)
|
||||
#define LOG_MASK_SIZE (MAX_EQUIP_ID * LOG_MASK_ITEM_SIZE)
|
||||
#define DCI_LOG_EQUIP_MAX_SIZE (MAX_ITEMS_PER_EQUIP_ID + 2)
|
||||
#define DCI_LOG_MASK_SIZE (MAX_EQUIP_ID*DCI_LOG_EQUIP_MAX_SIZE)
|
||||
|
||||
typedef PACK(struct) {
|
||||
uint8 equip_id;
|
||||
unsigned int num_items;
|
||||
byte mask[MAX_ITEMS_PER_EQUIP_ID];
|
||||
} diag_log_mask_t;
|
||||
|
||||
#endif /* DIAGLOGI_H */
|
||||
759
feeds/ipq95xx/qca-diag/src/include/diagpkt.h
Executable file
759
feeds/ipq95xx/qca-diag/src/include/diagpkt.h
Executable file
@@ -0,0 +1,759 @@
|
||||
#ifndef DIAGPKT_H
|
||||
#define DIAGPKT_H
|
||||
|
||||
/*==========================================================================
|
||||
|
||||
Diagnostic System Packet Interface
|
||||
|
||||
Description: Interface definitions use the diag packet processing service.
|
||||
|
||||
!!! NOTE: Diagnostic packets are sent over an external interface.
|
||||
Structure definitions must be portable to other C compilers. The easiest
|
||||
way to do this is to byte-align the packet definitions. The ARM compiler
|
||||
uses the PACKED keyword to denote byte alignment. Most other compilers
|
||||
use #pragma pack(1) to enable structure packing. The structure is not
|
||||
required to be byte-aligned, but it is required to be portable to other
|
||||
compilers.
|
||||
|
||||
!!! WARNING: Each command code is part of the externalized diagnostic command
|
||||
interface. Internally within QCT, these numbers *MUST* be assigned by a
|
||||
member of QCT's tools development team. 3rd party developers may use the
|
||||
reserved subsystem IDs to define and grow the diagnostic packet needs.
|
||||
|
||||
# Copyright (c) 2007-2011, 2016 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
===========================================================================*/
|
||||
|
||||
/* <EJECT> */
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
$Header: //depot/asic/msmshared/services/diag/Diag_1.5/Diag_LSM/diagpkt.h#2 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
04/10/08 pc Introduced support for masking events.
|
||||
12/22/06 as Moved proc ID macros to diag.h
|
||||
10/31/05 as Fixed lint errors.
|
||||
12/23/04 ec Added function diagpkt_free() declaration
|
||||
03/15/04 as Implemented functions to access fields in delayed response
|
||||
header
|
||||
12/16/03 as Added new macro to support delayed response.
|
||||
08/30/02 lad Revised file for multimode diagnostics version.
|
||||
05/21/01 lad Made diagpkt headers in DIAGPKT macros opaque.
|
||||
Added FEATURE_DIAG_PACKET_COUPLING to facililitate migration
|
||||
to this API.
|
||||
04/17/01 lad Removed inclusion of diagtune.h.
|
||||
Moved subsystem dispatch IDs to diagcmd.h.
|
||||
04/06/01 lad Introduced typedefs for command codes, etc.
|
||||
Updated DIAGPKT_SUBSYS_REQ_DEFINE macros.
|
||||
Added diagpkt_subsys_alloc().
|
||||
Removed diagpkt_process_request() since it is not part of the
|
||||
externalized interface.
|
||||
02/23/01 lad Rearchitected the diagnostics subsystem to be a service
|
||||
rather than a module. All coupling to targets has been
|
||||
moved to target-specific implementations. This file now
|
||||
contains an API for packet processing services.
|
||||
No other information or coupling remains except for
|
||||
featurized legacy code that impacts existing targets.
|
||||
Old history comments have been removed since most of them
|
||||
are no longer applicable.
|
||||
Packet definitions are no longer included in this file.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
#include "diag.h"
|
||||
/* Max size packet that the DIAG kernel driver allows.
|
||||
These are additionally defined in diagchar_core.c & diagchar.h */
|
||||
#define DIAG_MAX_TX_PKT_SIZ (16*1024)
|
||||
#define DIAG_MAX_RX_PKT_SIZ (16*1024)
|
||||
/* -------------------------------------------------------------------------
|
||||
Type and Packet Definition Macros
|
||||
------------------------------------------------------------------------- */
|
||||
typedef uint8 diagpkt_cmd_code_type;
|
||||
typedef uint8 diagpkt_subsys_id_type;
|
||||
typedef uint16 diagpkt_subsys_cmd_code_type;
|
||||
typedef uint32 diagpkt_subsys_status_type;
|
||||
typedef uint16 diagpkt_subsys_delayed_rsp_id_type;
|
||||
typedef uint16 diagpkt_subsys_rsp_cnt;
|
||||
|
||||
typedef PACK(struct)
|
||||
{
|
||||
byte opaque_header;
|
||||
}
|
||||
diagpkt_header_type;
|
||||
|
||||
typedef PACK(struct)
|
||||
{
|
||||
byte opaque_header[4];
|
||||
}
|
||||
diagpkt_subsys_header_type;
|
||||
|
||||
typedef PACK(struct)
|
||||
{
|
||||
byte opaque_header[12];
|
||||
}
|
||||
diagpkt_subsys_header_v2_type;
|
||||
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
Function Definitions
|
||||
------------------------------------------------------------------------- */
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
/* Packet Handler Types */
|
||||
|
||||
/* An array of this type is created by the client and registered with this
|
||||
service. It must be declared 'const' (preferrably 'static const').
|
||||
The function is called when an inbound packet matches subsystem ID and
|
||||
is within the command code range specified in the table. */
|
||||
typedef struct
|
||||
{
|
||||
word cmd_code_lo;
|
||||
word cmd_code_hi;
|
||||
void *(*func_ptr) (void *req_pkt_ptr, uint16 pkt_len);
|
||||
}
|
||||
diagpkt_user_table_entry_type;
|
||||
|
||||
/* Note: the following 2 items are used internally via the macro below. */
|
||||
|
||||
/* User table type */
|
||||
typedef struct
|
||||
{ uint16 delay_flag; /* 0 means no delay and 1 means with delay */
|
||||
uint16 cmd_code;
|
||||
word subsysid;
|
||||
word count;
|
||||
uint16 proc_id;
|
||||
const diagpkt_user_table_entry_type *user_table;
|
||||
} diagpkt_user_table_type;
|
||||
|
||||
|
||||
|
||||
#define DIAGPKT_NO_SUBSYS_ID 0xFF
|
||||
|
||||
void diagpkt_tbl_reg (const diagpkt_user_table_type * tbl_ptr);
|
||||
|
||||
|
||||
|
||||
/* Use this macro to register your dispatch table with the diagnostics
|
||||
packet dispatching service. */
|
||||
|
||||
/* This macro is used to manually register the client table with the
|
||||
packet dispatch service. This solution is intended to be temporary
|
||||
pending support for C++ on targets. This macro requires the client
|
||||
to explicitly register the table. */
|
||||
|
||||
/* USAGE: For registering diag packet tables on dual processor target, use
|
||||
the following functions:
|
||||
For diag packets which are specific to APP's processor use:
|
||||
DIAGPKT_DISPATCH_TABLE_REGISTER_PROC (DIAG_APP_PROC, DIAG_SUBSYS_XXXX,
|
||||
XXXX_subsys_tbl_app);
|
||||
For diag packets which are common to both processor's use:
|
||||
DIAGPKT_DISPATCH_TABLE_REGISTER_PROC (DIAG_DUAL_PROC, DIAGPKT_SUBSYS_XXXX,
|
||||
XXXX_common_tbl);
|
||||
*/
|
||||
#if defined (IMAGE_APPS_PROC)
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER(xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, 0xFF, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 1, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2(xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 1, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2_DELAY(xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
1, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 1, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
#else
|
||||
/* Single processor or modem proc*/
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER(xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, 0xFF, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 0, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2(xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 0, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2_DELAY(xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
1, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), 0, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
#endif
|
||||
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_PROC(xx_proc_id, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, 0xFF, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), xx_proc_id, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2_PROC(xx_proc_id, xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), xx_proc_id, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
#define DIAGPKT_DISPATCH_TABLE_REGISTER_V2_DELAY_PROC(xx_proc_id, xx_cmdcode, xx_subsysid, xx_entry) \
|
||||
do { \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
1, xx_cmdcode, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), xx_proc_id, xx_entry \
|
||||
}; \
|
||||
/*lint -save -e717 */ \
|
||||
diagpkt_tbl_reg (&xx_entry##_table); \
|
||||
} while (0)
|
||||
/*lint -restore */
|
||||
|
||||
#ifdef __cplusplus
|
||||
/* C++ class used for autoregister */
|
||||
class DiagDispatch
|
||||
{
|
||||
public:
|
||||
DiagDispatch (const diagpkt_user_table_type *tbl_ptr)
|
||||
{
|
||||
diagpkt_tbl_reg(tbl_ptr);
|
||||
}
|
||||
};
|
||||
|
||||
/* If C++ is supported in the build, this macro, defined in the
|
||||
preprocessor, instantiates a class with a 'static const' constructor.
|
||||
This class is therefore instantiated at boot, calling the constructor
|
||||
prior to the system 'main()'. This eliminates the need to acquire
|
||||
scope to register, it is done automatically. */
|
||||
|
||||
#define DIAGPKT_DISPATCH_AUTOREGISTER(xx_subsysid, xx_entry) \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
0, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), xx_entry \
|
||||
}; \
|
||||
DiagDispatch xx_entry##_instance(&xx_entry##_table)
|
||||
|
||||
/* This macro is used if the diag packet has delayed response */
|
||||
|
||||
#define DIAGPKT_DISPATCH_AUTOREGISTER_DELAY(xx_subsysid, xx_entry) \
|
||||
static const diagpkt_user_table_type xx_entry##_table = { \
|
||||
1, xx_subsysid, sizeof (xx_entry) / sizeof (xx_entry[0]), xx_entry \
|
||||
}; \
|
||||
DiagDispatch xx_entry##_instance(&xx_entry##_table)
|
||||
|
||||
#endif
|
||||
|
||||
/* ------------------------------------------------------------------------
|
||||
Functions
|
||||
------------------------------------------------------------------------ */
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_ALLOC
|
||||
|
||||
DESCRIPTION
|
||||
This function allocates the specified amount of space in the diag output
|
||||
buffer. If space is unavailable, access to the allocation buffer will be
|
||||
blocked using a semaphore until space is available.
|
||||
|
||||
DEPENDENCIES
|
||||
This may only be called by the diag task for responses to explicit request
|
||||
packets! This function is *not* re-entrant. If the OS ever supports
|
||||
semaphores other than INTLOCK, this function can be made re-entrant.
|
||||
|
||||
diagpkt_commit() must be called to commit the response packet to be sent.
|
||||
Not calling diagpkt_commit() will result in a memory leak.
|
||||
|
||||
============================================================================*/
|
||||
void *diagpkt_alloc (diagpkt_cmd_code_type code, unsigned int length);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_ALLOC
|
||||
|
||||
DESCRIPTION
|
||||
This call is the same as calling diagpkt_alloc(), but is used for
|
||||
allocating responses for subsystem commands. It fills in the subsystem
|
||||
header info for you.
|
||||
|
||||
DEPENDENCIES
|
||||
This may only be called by the diag task for responses to explicit request
|
||||
packets! This function is *not* re-entrant. If the OS ever supports
|
||||
semaphores other than INTLOCK, this function can be made re-entrant.
|
||||
|
||||
diagpkt_commit() must be called to commit the response packet to be sent.
|
||||
Not calling diagpkt_commit() will result in a memory leak.
|
||||
|
||||
============================================================================*/
|
||||
void *diagpkt_subsys_alloc (diagpkt_subsys_id_type id,
|
||||
diagpkt_subsys_cmd_code_type code, unsigned int length);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
FUNCTION DIAGPKT_SUBSYS_ALLOC_V2
|
||||
|
||||
DESCRIPTION
|
||||
This function allocates the specified amount of space in the diag output
|
||||
buffer. If space is unavailable, access to the allocation buffer will be
|
||||
blocked using a semaphore until space is available.
|
||||
|
||||
DEPENDENCIES
|
||||
This may only be called by the diag task for responses to explicit request
|
||||
packets! This function is *not* re-entrant. If the OS ever supports
|
||||
semaphores other than INTLOCK, this function can be made re-entrant.
|
||||
|
||||
diagpkt_commit() must be called to commit the response packet to be sent.
|
||||
Not calling diagpkt_commit() will result in a memory leak.
|
||||
===========================================================================*/
|
||||
void *diagpkt_subsys_alloc_v2 (diagpkt_subsys_id_type id,
|
||||
diagpkt_subsys_cmd_code_type code, unsigned int length);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_ALLOC_V2_DELAY
|
||||
|
||||
DESCRIPTION
|
||||
This function allocates the specified amount of space in the diag output
|
||||
buffer. This function is used to send a delayed response.This response has
|
||||
same priority as F3 messages and logs.
|
||||
|
||||
DEPENDENCIES
|
||||
diagpkt_delay_commit() must be called to commit the response packet to be
|
||||
sent. Not calling diagpkt_delay_commit() will result in a memory leak.
|
||||
|
||||
Note:User is required to provide delayed response id as an argument.
|
||||
This helps tools to match the delayed response with the original
|
||||
request response pair.
|
||||
|
||||
===========================================================================*/
|
||||
void *diagpkt_subsys_alloc_v2_delay (
|
||||
diagpkt_subsys_id_type id,
|
||||
diagpkt_subsys_cmd_code_type code,
|
||||
diagpkt_subsys_delayed_rsp_id_type delayed_rsp_id,
|
||||
unsigned int length);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SHORTEN
|
||||
|
||||
DESCRIPTION
|
||||
This function reduces the length field of a previously allcated buffer.
|
||||
|
||||
'ptr' must point to the same address that was returned by a prior call to
|
||||
diagpkt_alloc() or diagpkt_subsys_alloc().
|
||||
|
||||
Allocating too much and using this to shorten the packet is ideal for
|
||||
situations in which the length of the packet is not known prior to
|
||||
allocation. Using this scheme does, however, consume resources that would
|
||||
otherwise be used to buffer outbound diagnostics data. Please use this
|
||||
capability sparingly.
|
||||
|
||||
============================================================================*/
|
||||
void diagpkt_shorten (void *ptr, unsigned int length);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_MASK_TBL_CS_INIT
|
||||
|
||||
DESCRIPTION
|
||||
This function initializes the mask_tbl_cs mutex variable.
|
||||
===========================================================================*/
|
||||
void diagpkt_mask_tbl_cs_init(void);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_MASTER_TBL_CS_INIT
|
||||
|
||||
DESCRIPTION
|
||||
This function initializes the master_tbl_cs mutex variable.
|
||||
===========================================================================*/
|
||||
void diagpkt_master_tbl_cs_init(void);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_COMMIT_DCM
|
||||
|
||||
DESCRIPTION
|
||||
This function commits previously allocated space in the diagnostics output
|
||||
buffer.
|
||||
|
||||
'ptr' must be the same pointer that was returned from diagpkt_alloc() or
|
||||
diagpkt_subsys_alloc().
|
||||
|
||||
This function signals the DIAG task and may cause a context switch.
|
||||
|
||||
The packet handler type returns the response pointer. The dispatcher
|
||||
calls diagpkt_commit() internally. This only needs to be called
|
||||
explicitly if the packet needs to be committed before the packet handler
|
||||
returns. In this case, the packet handler should return NULL.
|
||||
|
||||
============================================================================*/
|
||||
void diagpkt_commit_dcm (byte *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_COMMIT
|
||||
|
||||
DESCRIPTION
|
||||
This function commits previously allocated space in the diagnostics output
|
||||
buffer.
|
||||
|
||||
'ptr' must be the same pointer that was returned from diagpkt_alloc() or
|
||||
diagpkt_subsys_alloc().
|
||||
|
||||
This function signals the DIAG task and may cause a context switch.
|
||||
|
||||
The packet handler type returns the response pointer. The dispatcher
|
||||
calls diagpkt_commit() internally. This only needs to be called
|
||||
explicitly if the packet needs to be committed before the packet handler
|
||||
returns. In this case, the packet handler should return NULL.
|
||||
|
||||
============================================================================*/
|
||||
void diagpkt_commit (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_DELAY_COMMIT
|
||||
|
||||
DESCRIPTION
|
||||
This function is a wrapper to diagbuf_commit
|
||||
|
||||
===========================================================================*/
|
||||
void diagpkt_delay_commit (void *pkt);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_GET_CMD_CODE
|
||||
|
||||
DESCRIPTION
|
||||
This function returns the command code in the specified diagnostics packet.
|
||||
|
||||
===========================================================================*/
|
||||
diagpkt_cmd_code_type diagpkt_get_cmd_code (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SET_CMD_CODE
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the command code in the specified diagnostics packet.
|
||||
|
||||
===========================================================================*/
|
||||
void diagpkt_set_cmd_code (void *ptr, diagpkt_cmd_code_type cmd_code);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_GET_ID
|
||||
|
||||
DESCRIPTION
|
||||
This function returns the subsystem ID in the specified diagnostics packet.
|
||||
|
||||
If the packet is not a DIAG_SUBSYS_CMD_F or DIAG_SUBSYS_CMD_VER_2_F packet,
|
||||
0xFFFF is returned.
|
||||
|
||||
===========================================================================*/
|
||||
diagpkt_subsys_id_type diagpkt_subsys_get_id (void *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_GET_CMD_CODE
|
||||
|
||||
DESCRIPTION
|
||||
This function returns the subsystem command code in the specified
|
||||
diagnostics packet.
|
||||
|
||||
If the packet is not a DIAG_SUBSYS_CMD_F or DIAG_SUBSYS_CMD_VER_2_F packet,
|
||||
0xFFFF is returned.
|
||||
|
||||
===========================================================================*/
|
||||
diagpkt_subsys_cmd_code_type diagpkt_subsys_get_cmd_code (void *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_GET_STATUS
|
||||
|
||||
DESCRIPTION
|
||||
This function gets the status field in the DIAG_SUBSYS_CMD_VER_2_F packet
|
||||
|
||||
This function's first argument (ptr) should always be DIAG_SUBSYS_CMD_VER_2_F
|
||||
packet.
|
||||
|
||||
===========================================================================*/
|
||||
diagpkt_subsys_status_type diagpkt_subsys_get_status (void *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_SET_STATUS
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the status field in the DIAG_SUBSYS_CMD_VER_2_F packet.
|
||||
|
||||
This function's first argument (ptr) should always be DIAG_SUBSYS_CMD_VER_2_F
|
||||
packet.
|
||||
|
||||
===========================================================================*/
|
||||
void diagpkt_subsys_set_status (void *ptr,
|
||||
diagpkt_subsys_status_type status);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_GET_DELAYED_RSP_ID
|
||||
|
||||
DESCRIPTION
|
||||
This function gets the delayed response ID field in the
|
||||
DIAG_SUBSYS_CMD_VER_2_F packet.
|
||||
|
||||
This function's first argument (ptr) should always be DIAG_SUBSYS_CMD_VER_2_F
|
||||
packet.
|
||||
|
||||
===========================================================================*/
|
||||
diagpkt_subsys_delayed_rsp_id_type diagpkt_subsys_get_delayed_rsp_id
|
||||
(void *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_RESET_DELAYED_RSP_ID
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the delayed response ID to zero in the
|
||||
DIAG_SUBSYS_CMD_VER_2_F packet.
|
||||
|
||||
This function's first argument (ptr) should always be DIAG_SUBSYS_CMD_VER_2_F
|
||||
packet.
|
||||
|
||||
===========================================================================*/
|
||||
void diagpkt_subsys_reset_delayed_rsp_id (void *ptr);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_SUBSYS_SET_RSP_CNT
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the response count in the DIAG_SUBSYS_CMD_VER_2_F packet.
|
||||
|
||||
This function's first argument (ptr) should always be DIAG_SUBSYS_CMD_VER_2_F
|
||||
packet.
|
||||
|
||||
===========================================================================*/
|
||||
void diagpkt_subsys_set_rsp_cnt (void *ptr,
|
||||
diagpkt_subsys_rsp_cnt rsp_cnt);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_ERR_RSP
|
||||
|
||||
DESCRIPTION
|
||||
This function builds an error packet.
|
||||
Usage: rsp_ptr = diagpkt_err_rsp ( error_code, req_pkt );
|
||||
|
||||
===========================================================================*/
|
||||
void *diagpkt_err_rsp (diagpkt_cmd_code_type code,
|
||||
void *req_ptr, uint16 req_len);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_ASYNC_BLOCK
|
||||
|
||||
DESCRIPTION
|
||||
This procedure blocks while we wait for the DIAG_ASYNC_BLOCK_SIG to be set
|
||||
to allow for asynchronous delays in packet handling.
|
||||
|
||||
============================================================================*/
|
||||
void diagpkt_async_block (void);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION DIAGPKT_ASYNC_RELEASE
|
||||
|
||||
DESCRIPTION
|
||||
This procedure sets the DIAG_ASYNC_BLOCK_SIG to end the asynchronous delay
|
||||
started with DIAGPKT_ASYNC_BLOCK
|
||||
|
||||
============================================================================*/
|
||||
void diagpkt_async_release (void);
|
||||
|
||||
|
||||
|
||||
|
||||
/*-------------------------------------------------------------
|
||||
Diagnostics Packet Type Defintion Macros
|
||||
|
||||
These macros were defined to provide and enforce naming
|
||||
conventions for declaring packets. However, these macros
|
||||
make editor tags useless and add consufion. The use of
|
||||
these macros has been deprecated, but is included here for
|
||||
compatibility with existing usage. The naming convention
|
||||
enforced by these macros is not required for use of this
|
||||
service.
|
||||
|
||||
!!! It is not recommended to continue use of these macros.
|
||||
|
||||
The naming convention enforced by these macros is outlined
|
||||
below:
|
||||
|
||||
Command codes use the naming convention: DIAG_xxx_F
|
||||
|
||||
Requests types:
|
||||
DIAG_xxx_F_req_type
|
||||
|
||||
Response types:
|
||||
DIAG_xxx_F_rsp_type
|
||||
|
||||
-------------------------------------------------------------*/
|
||||
#ifndef FEATURE_DIAG_EXPOSED_HEADER
|
||||
#define DIAGPKT_REQ_DEFINE( xx_cmd_code ) \
|
||||
typedef struct xx_cmd_code##_req_tag \
|
||||
xx_cmd_code##_req_type; \
|
||||
PACK(struct) xx_cmd_code##_req_tag { \
|
||||
diagpkt_header_type xx_header;
|
||||
#else
|
||||
#define DIAGPKT_REQ_DEFINE( xx_cmd_code ) \
|
||||
typedef struct xx_cmd_code##_req_tag \
|
||||
xx_cmd_code##_req_type; \
|
||||
PACK(struct) xx_cmd_code##_req_tag { \
|
||||
diagpkt_cmd_code_type command_code;
|
||||
#endif
|
||||
|
||||
#define DIAGPKT_REQ_END };
|
||||
|
||||
/* If the response is the same structure as the request... */
|
||||
#define DIAGPKT_DEFINE_RSP_AS_REQ( xx_cmd_code ) \
|
||||
typedef xx_cmd_code##_req_type xx_cmd_code##_rsp_type;
|
||||
|
||||
#ifndef FEATURE_DIAG_EXPOSED_HEADER
|
||||
#define DIAGPKT_RSP_DEFINE( xx_cmd_code ) \
|
||||
typedef struct xx_cmd_code##_rsp_tag \
|
||||
xx_cmd_code##_rsp_type; \
|
||||
PACK(struct) xx_cmd_code##_rsp_tag { \
|
||||
diagpkt_header_type xx_header;
|
||||
#else
|
||||
#define DIAGPKT_RSP_DEFINE( xx_cmd_code ) \
|
||||
typedef struct xx_cmd_code##_rsp_tag \
|
||||
xx_cmd_code##_rsp_type; \
|
||||
PACK(struct) xx_cmd_code##_rsp_tag { \
|
||||
diagpkt_cmd_code_type command_code;
|
||||
#endif
|
||||
|
||||
#define DIAGPKT_RSP_END };
|
||||
|
||||
/*-------------------------------------------------------------
|
||||
Diagnostics Subsystem Packet Type Definition Macros
|
||||
|
||||
These macros were defined to provide and enforce naming
|
||||
conventions for declaring packets.
|
||||
|
||||
!!! It is not recommended to continue use of these macros.
|
||||
|
||||
The naming convention enforced by these macros is outlined
|
||||
below:
|
||||
|
||||
Diag has a subsystem command that dispatches diag commands to
|
||||
various subsystems. All subsystem packet types use the same
|
||||
naming convention throughout the DMSS. The subsystem command
|
||||
uses a 16 bit command code per subsystem. This results in
|
||||
user data starting on a 32 bit boundary.
|
||||
|
||||
The naming convention is as follows:
|
||||
|
||||
Command codes use the naming convnetion: DIAG_SUBSYS_xxx_F
|
||||
|
||||
Requests types:
|
||||
DIAG_SUBSYS_xxx_yyy_req_type
|
||||
|
||||
Response types:
|
||||
DIAG_SUBSYS_xxx_yyy_rsp_type
|
||||
|
||||
-------------------------------------------------------------*/
|
||||
#define DIAGPKT_SUBSYS_REQ_DEFINE( xx_subsys, xx_subsys_cmd_code ) \
|
||||
typedef struct DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_req_tag \
|
||||
DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_req_type; \
|
||||
PACK(struct) DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_req_tag { \
|
||||
diagpkt_subsys_header_type xx_header;
|
||||
|
||||
#define DIAGPKT_SUBSYS_REQ_END };
|
||||
|
||||
#define DIAGPKT_SUBSYS_RSP_DEFINE( xx_subsys, xx_subsys_cmd_code ) \
|
||||
typedef struct DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_rsp_tag \
|
||||
DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_rsp_type; \
|
||||
PACK(struct) DIAG_SUBSYS_##xx_subsys##_##xx_subsys_cmd_code##_rsp_tag { \
|
||||
diagpkt_subsys_header_type xx_header;
|
||||
|
||||
#define DIAGPKT_SUBSYS_RSP_END };
|
||||
|
||||
|
||||
#ifdef FEATURE_DIAG_PACKET_COUPLING
|
||||
|
||||
/* As a temporary measure, this is added since mclog.h expects packet
|
||||
definitions to be defined in diagpkt.h Once mclog.h is updated, this can
|
||||
be removed. */
|
||||
#include "diagcmd.h" /* mclog.c needs to include this */
|
||||
#include "cdma2kdiag.h"
|
||||
#include "parmdiag.h"
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* DIAGPKT_H */
|
||||
95
feeds/ipq95xx/qca-diag/src/include/event.h
Executable file
95
feeds/ipq95xx/qca-diag/src/include/event.h
Executable file
@@ -0,0 +1,95 @@
|
||||
#ifndef EVENT_H
|
||||
#define EVENT_H
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Event Reporting Services
|
||||
|
||||
General Description
|
||||
All declarations and definitions necessary to support the static
|
||||
system event reporting service.
|
||||
|
||||
# Copyright (c) 2007-2011 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
Edit History
|
||||
|
||||
$Header: //depot/asic/msmshared/services/diag/Diag_1.5/Diag_LSM/event.h#1 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
01/02/08 mad Added extern "C" modifiers for function declarations
|
||||
05/14/04 eav Added FEATURE_SAVE_DEBUG_TRACE. Added the function
|
||||
event_save_circ_buffer_to_efs, which is called from err.c
|
||||
04/17/01 lad Moved constants to diagtune.h.
|
||||
Moved event definitions to event_defs.h.
|
||||
02/23/01 lad Updated API for core diagnostics service.
|
||||
11/17/00 jal Bit fields in event_id_type came out in inverted order
|
||||
from what we wanted. Fixed.
|
||||
11/13/00 lcc Added event and type definitions for some events.
|
||||
11/10/00 lad Made obsolete event_report_data() a macro to NULL.
|
||||
11/09/00 jal Took the old event IDs out (again!)
|
||||
11/07/00 jal Renamed event_extra_data_type to event_payload_type
|
||||
10/17/00 jal Changes for new event accumulation mechanism
|
||||
05/15/00 lad Changed truncated timsteamp from uint32 to uint16.
|
||||
04/11/00 lad Increased # of customer reserved event IDs to 0x100.
|
||||
12/16/99 lad Added support for event reporting service.
|
||||
01/21/99 lad Created file.
|
||||
|
||||
===========================================================================*/
|
||||
|
||||
/* Since the IDs and type definitions are part of the API, include it here */
|
||||
#include "event_defs.h"
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
Function Defintions
|
||||
------------------------------------------------------------------------- */
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION EVENT_REPORT
|
||||
|
||||
DESCRIPTION
|
||||
Report an event.
|
||||
|
||||
DEPENDENCIES
|
||||
Event services must be initialized.
|
||||
|
||||
RETURN VALUE
|
||||
None.
|
||||
|
||||
SIDE EFFECTS
|
||||
None.
|
||||
|
||||
===========================================================================*/
|
||||
void event_report (event_id_enum_type event_id);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION EVENT_REPORT_PAYLOAD
|
||||
|
||||
DESCRIPTION
|
||||
Report an event with payload data.
|
||||
|
||||
DEPENDENCIES
|
||||
Event services must be initialized.
|
||||
|
||||
RETURN VALUE
|
||||
None.
|
||||
|
||||
SIDE EFFECTS
|
||||
None.
|
||||
|
||||
===========================================================================*/
|
||||
void event_report_payload (event_id_enum_type event_id, uint8 length, void *data);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* for extern "C" modifier */
|
||||
#endif /* EVENT_H */
|
||||
2764
feeds/ipq95xx/qca-diag/src/include/event_defs.h
Executable file
2764
feeds/ipq95xx/qca-diag/src/include/event_defs.h
Executable file
File diff suppressed because it is too large
Load Diff
442
feeds/ipq95xx/qca-diag/src/include/log.h
Executable file
442
feeds/ipq95xx/qca-diag/src/include/log.h
Executable file
@@ -0,0 +1,442 @@
|
||||
#ifndef LOG_H
|
||||
#define LOG_H
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Logging Service Header File
|
||||
|
||||
General Description
|
||||
This file contains the API for the logging service.
|
||||
|
||||
The logging service allows clients to send information in the form of a
|
||||
log record to the external device that is collecting logs (i.e., QXDM).
|
||||
|
||||
!!! Important usage note:
|
||||
The logging service uses a memory management system for logging outbound
|
||||
information. Due to limited resources, this memory management system is a
|
||||
FIFO queueing system with no garbage collection. Queue insertion occurs at
|
||||
the time a logging buffer is allocated, not when it is commmited. When you
|
||||
allocate a buffer, that buffer blocks the emptying of the FIFO until that
|
||||
log record is commmited. Therefore, if you hold onto a buffer for a long
|
||||
time, no other log records can be sent until you commit (or free) your
|
||||
buffer. If you need to accumulate data for a log record, you must
|
||||
accumulate it in your own memory space, not the memory allocated by the
|
||||
logging service. When ready to send, call log_submit().
|
||||
|
||||
General usage:
|
||||
ptr = log_alloc(code, length);
|
||||
|
||||
if (ptr) {
|
||||
//Fill in log record here
|
||||
|
||||
log_commit(ptr);
|
||||
}
|
||||
|
||||
|
||||
# Copyright (c) 2007-2011, 2014, 2016 by Qualcomm Technologies, Inc. All Rights Reserved.
|
||||
# Qualcomm Technologies Proprietary and Confidential.
|
||||
===========================================================================*/
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
Edit History
|
||||
|
||||
$Header: //depot/asic/msmshared/services/diag/Diag_1.5/Diag_LSM/log.h#1 $
|
||||
|
||||
when who what, where, why
|
||||
-------- --- ----------------------------------------------------------
|
||||
10/01/08 SJ Changes for CBSP2.0
|
||||
01/16/08 JV Modified comments and descriptions as per Diag 1.5A (WM)
|
||||
09/18/02 lad Created file from old version. Content has been removed
|
||||
from this file, leaving only the logging service API.
|
||||
===========================================================================*/
|
||||
|
||||
#include "log_codes.h"
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
Definitions and Declarations
|
||||
------------------------------------------------------------------------- */
|
||||
|
||||
/* Log code type. Currently this is 16 bits. */
|
||||
typedef uint16 log_code_type;
|
||||
|
||||
/* Log Record Header Type:
|
||||
Currently, all log records structure definitions must begin with
|
||||
log_hdr_type. This place holder is needed for the internal
|
||||
implementation of the logging service to function properly.
|
||||
|
||||
!!! Notice: Do not reference this header directly. In planned future
|
||||
versions of this service, this type will be typedef void, and the header
|
||||
will be transparant to the user of this service. Any direct reference
|
||||
to this type will not compile when this enhancement is implemented. */
|
||||
|
||||
#if !defined(FEATURE_LOG_EXPOSED_HEADER)
|
||||
|
||||
typedef PACK(struct
|
||||
{
|
||||
unsigned char header[12]; /* A log header is 12 bytes long */
|
||||
}) log_hdr_type;
|
||||
|
||||
#else
|
||||
|
||||
/* Some clients, for legacy reasons, reference the log header. Until those
|
||||
references are cleaned up, the logging service must expose the header
|
||||
to avoid compilation failure. */
|
||||
|
||||
typedef PACK(struct
|
||||
{
|
||||
word len; /* Specifies the length, in bytes of the
|
||||
entry, including this header. */
|
||||
|
||||
word code; /* Specifies the log code for the entry as
|
||||
enumerated above. Note: This is
|
||||
specified as word to guarantee size. */
|
||||
// removed AMSS specific code
|
||||
//qword ts; The system timestamp for the log entry. The
|
||||
/*upper 48 bits represent elapsed time since
|
||||
6 Jan 1980 00:00:00 in 1.25 ms units. The
|
||||
low order 16 bits represent elapsed time
|
||||
since the last 1.25 ms tick in 1/32 chip
|
||||
units (this 16 bit counter wraps at the
|
||||
value 49152). */
|
||||
uint32 ts_lo; /* Time stamp */
|
||||
uint32 ts_hi;
|
||||
})
|
||||
log_hdr_type;
|
||||
|
||||
#endif /* !FEATURE_LOG_EXPOSED_HEADER */
|
||||
|
||||
/* Indicates which type of time stamp to use when setting a time stamp. */
|
||||
typedef enum
|
||||
{
|
||||
LOG_TIME_IND_CDMA_E,
|
||||
LOG_TIME_IND_MSP_E,
|
||||
LOG_TIME_IND_WCDMA_E
|
||||
}
|
||||
log_time_indicator_type;
|
||||
|
||||
|
||||
/* -------------------------------------------------------------------------
|
||||
Function Declarations
|
||||
------------------------------------------------------------------------- */
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_ALLOC
|
||||
|
||||
DESCRIPTION
|
||||
This function allocates a buffer of size 'length' for logging data. The
|
||||
specified length is the length of the entire log, including the log
|
||||
header. This operation is inteneded only for logs that do not require
|
||||
data accumulation.
|
||||
|
||||
!!! The header is filled in automatically by this routine.
|
||||
|
||||
DEPENDENCIES:
|
||||
CS needs to be initialized.
|
||||
log_commit() or log_free() must be called ASAP after this call.
|
||||
|
||||
RETURN VALUE
|
||||
A pointer to the allocated buffer is returned on success.
|
||||
Expect a NULL when gnDiagSvcMalloc_Initialized is not initialized
|
||||
or if heap is full.
|
||||
|
||||
SIDE EFFECTS
|
||||
Since this allocation is made from a shared resource pool, log_commit()
|
||||
or log_free() must be called as soon as possible and in a timely fashion.
|
||||
|
||||
If you need to log accumulated data, store the accumulated data in your
|
||||
own memory space and use log_submit() to log the data.
|
||||
===========================================================================*/
|
||||
void *log_alloc (log_code_type code, unsigned int length);
|
||||
#define log_alloc_ex(a, b) log_alloc (a, b)
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_SHORTEN
|
||||
|
||||
DESCRIPTION
|
||||
This function shortens the length of a previously allocated logging buffer in
|
||||
legacy code. This is used when the size of the record is not known at allocation
|
||||
time.Now that diagbuf is not used in the LSM layer and we just use memory from
|
||||
a pre-allocated pool, calling log_shorten, does not free the excess memory, it just
|
||||
updates the length field.
|
||||
|
||||
DEPENDENCIES
|
||||
This must be called prior to log_commit().
|
||||
|
||||
RETURN VALUE
|
||||
None.
|
||||
|
||||
===========================================================================*/
|
||||
void log_shorten (void *log_ptr, unsigned int length);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_COMMIT
|
||||
|
||||
DESCRIPTION
|
||||
This function commits a log buffer allocated by log_alloc(). Calling this
|
||||
function tells the logging service that the user is finished with the
|
||||
allocated buffer.
|
||||
|
||||
DEPENDENCIES
|
||||
'ptr' must point to the address that was returned by a prior call to
|
||||
log_alloc().
|
||||
|
||||
RETURN VALUE
|
||||
None.
|
||||
|
||||
SIDE EFFECTS
|
||||
Since this allocation is made from a shared resource pool, this must be
|
||||
called as soon as possible after a log_alloc call. This operation is not
|
||||
intended for logs that take considerable amounts of time ( > 0.01 sec ).
|
||||
|
||||
===========================================================================*/
|
||||
void log_commit (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_FREE
|
||||
|
||||
DESCRIPTION
|
||||
This function frees the buffer in pre-allocated memory.
|
||||
|
||||
DEPENDENCIES
|
||||
'ptr' must point to a log entry that was allocated by log_alloc().
|
||||
|
||||
===========================================================================*/
|
||||
void log_free (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_SUBMIT
|
||||
|
||||
DESCRIPTION
|
||||
This function is called to log an accumlated log entry. If logging is
|
||||
enabled for the entry by the external device, then the entry is copied
|
||||
into the diag allocation manager and commited immediately.
|
||||
|
||||
This function essentially does the folliwng:
|
||||
log = log_alloc ();
|
||||
memcpy (log, ptr, log->len);
|
||||
log_commit (log);
|
||||
|
||||
|
||||
|
||||
RETURN VALUE
|
||||
Boolean indicating success.
|
||||
|
||||
===========================================================================*/
|
||||
boolean log_submit (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_SET_LENGTH
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the length field in the given log record.
|
||||
|
||||
!!! Use with caution. It is possible to corrupt a log record using this
|
||||
command. It is intended for use only with accumulated log records, not
|
||||
buffers returned by log_alloc().
|
||||
|
||||
===========================================================================*/
|
||||
void log_set_length (void *ptr, unsigned int length);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_SET_CODE
|
||||
|
||||
DESCRIPTION
|
||||
This function sets the logging code in the given log record.
|
||||
|
||||
===========================================================================*/
|
||||
void log_set_code (void *ptr, log_code_type code);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_SET_TIMESTAMP
|
||||
|
||||
DESCRIPTION
|
||||
This function captures the system time and stores it in the given log record.
|
||||
|
||||
===========================================================================*/
|
||||
void log_set_timestamp (
|
||||
#ifdef FEATURE_ZREX_TIME
|
||||
void *ptr, log_time_indicator_type time_type
|
||||
#else
|
||||
void *ptr
|
||||
#endif
|
||||
);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_GET_LENGTH
|
||||
|
||||
DESCRIPTION
|
||||
This function returns the length field in the given log record.
|
||||
|
||||
|
||||
RETURN VALUE
|
||||
An unsigned int, the length
|
||||
|
||||
===========================================================================*/
|
||||
unsigned int log_get_length (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_GET_CODE
|
||||
|
||||
DESCRIPTION
|
||||
This function returns the log code field in the given log record.
|
||||
|
||||
|
||||
|
||||
RETURN VALUE
|
||||
log_code_type, the code
|
||||
===========================================================================*/
|
||||
log_code_type log_get_code (void *ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_STATUS
|
||||
|
||||
DESCRIPTION
|
||||
This function returns whether a particular code is enabled for logging.
|
||||
|
||||
===========================================================================*/
|
||||
boolean log_status (log_code_type code);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_PROCESS_LSM_MASK_REQ
|
||||
DESCRIPTION
|
||||
Handles requests from LSM to transfer the event mask.
|
||||
============================================================================*/
|
||||
|
||||
//int log_process_LSM_mask_req (unsigned char* mask, int maskLen, int * maskLenReq);
|
||||
/* Not required here, not an external API */
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
|
||||
NOTE: No function pointer support in diag1.5A. These 2 functions are just stubs
|
||||
|
||||
FUNCTION TYPE LOG_ON_DEMAND
|
||||
|
||||
DESCRIPTION
|
||||
This function, provided via reference by the caller, indicates a trigger
|
||||
for the specified log code issued from the external device. This routine
|
||||
must return status, which is send to the external device.
|
||||
|
||||
DEPENDENCIES
|
||||
None.
|
||||
|
||||
RETURN VALUE
|
||||
'log_on_demand_status_enum_type'
|
||||
|
||||
SIDE EFFECTS
|
||||
None.
|
||||
|
||||
===========================================================================*/
|
||||
typedef enum
|
||||
{
|
||||
LOG_ON_DEMAND_SENT_S = 0,
|
||||
LOG_ON_DEMAND_ACKNOWLEDGE_S,
|
||||
LOG_ON_DEMAND_DROPPED_S,
|
||||
LOG_ON_DEMAND_NOT_SUPPORTED_S,
|
||||
LOG_ON_DEMAND_FAILED_ATTEMPT_S
|
||||
}
|
||||
log_on_demand_status_enum_type;
|
||||
|
||||
typedef log_on_demand_status_enum_type (*log_on_demand) (log_code_type
|
||||
log_code);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_ON_DEMAND_REGISTER
|
||||
|
||||
DESCRIPTION
|
||||
This function registers a function pointer to be associated with a
|
||||
log code for logging on demand. If the external device sends a request
|
||||
to trigger this log code, the function will be called. The logging
|
||||
must be performed by the client of this service. It will not be
|
||||
performed by the logging service itself.
|
||||
|
||||
===========================================================================*/
|
||||
boolean log_on_demand_register (log_code_type log_code,
|
||||
log_on_demand log_on_demand_ptr);
|
||||
|
||||
/*===========================================================================
|
||||
|
||||
FUNCTION LOG_ON_DEMAND_UNREGISTER
|
||||
|
||||
DESCRIPTION
|
||||
This function unregisters the log function
|
||||
|
||||
===========================================================================*/
|
||||
boolean log_on_demand_unregister (log_code_type log_code);
|
||||
|
||||
|
||||
/*===========================================================================
|
||||
MACRO LOG_RECORD_DEFINE
|
||||
MACRO LOG_RECORD_END
|
||||
|
||||
DESCRIPTION
|
||||
These macros were defined to provide and enforce naming
|
||||
conventions for declaring packets. However, these macros
|
||||
make editor tags useless and add consufion. The use of
|
||||
these macros has been deprecated, but is included here for
|
||||
compatibility with existing usage. The naming convention
|
||||
enforced by these macros is not required for use of this
|
||||
service.
|
||||
|
||||
!!! It is not recommended to continue use of these macros.
|
||||
|
||||
All that is required for defining a log structure is to place
|
||||
a member of 'log_hdr_type' at the top of the structure. Do not
|
||||
access this member directly as this type is slated to be type-cast
|
||||
to 'void' when extending the logging service beyond 16-bit log codes.
|
||||
|
||||
The naming convention enforced by these macros is outlined
|
||||
below:
|
||||
|
||||
Log codes use the naming convention LOG_xxx_F.
|
||||
|
||||
This macro expands the name of the defined structure to be:
|
||||
LOG_xxx_C_type
|
||||
|
||||
===========================================================================*/
|
||||
#ifdef FEATURE_LOG_EXPOSED_HEADER
|
||||
#define LOG_RECORD_DEFINE( xx_code ) \
|
||||
typedef struct xx_code##_tag xx_code##_type; \
|
||||
PACK(struct) xx_code##_tag { \
|
||||
log_hdr_type hdr;
|
||||
#else
|
||||
#define LOG_RECORD_DEFINE( xx_code ) \
|
||||
typedef struct xx_code##_tag xx_code##_type; \
|
||||
PACK(struct) xx_code##_tag { \
|
||||
log_hdr_type xx_hdr;
|
||||
#endif
|
||||
|
||||
#define LOG_RECORD_END };
|
||||
|
||||
#if defined(FEATURE_DIAG_PACKET_COUPLING)
|
||||
|
||||
/* In legacy versions, log.h contains log packet definitions. Those
|
||||
definitions have been moved to a separate file to isolate coupling. */
|
||||
#include "log_dmss.h"
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif /* LOG_H */
|
||||
2990
feeds/ipq95xx/qca-diag/src/include/log_codes.h
Executable file
2990
feeds/ipq95xx/qca-diag/src/include/log_codes.h
Executable file
File diff suppressed because it is too large
Load Diff
1097
feeds/ipq95xx/qca-diag/src/include/msg.h
Executable file
1097
feeds/ipq95xx/qca-diag/src/include/msg.h
Executable file
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user