rmnet_ctl: Support IPA EP

Support QMAP commands from dedicated IPA EP.

Change-Id: Ic5e489d2b33223b2af2fb471d20611bc5a0d7d58
Acked-by: Weiyi Chen <weiyic@qti.qualcomm.com>
Signed-off-by: Subash Abhinov Kasiviswanathan <subashab@codeaurora.org>
这个提交包含在:
Subash Abhinov Kasiviswanathan
2020-03-02 12:10:49 -08:00
父节点 5fd6051c6c
当前提交 5a88e58652
修改 10 个文件,包含 211 行新增18 行删除

查看文件

@@ -26,6 +26,10 @@ struct rmnet_ctl_endpoint {
void *ipc_log;
};
#if defined(CONFIG_IPA_DEBUG) || defined(CONFIG_MHI_DEBUG)
#define CONFIG_RMNET_CTL_DEBUG 1
#endif
#ifdef CONFIG_RMNET_CTL_DEBUG
static u8 ipc_log_lvl = RMNET_CTL_LOG_DEBUG;
#else
@@ -35,13 +39,13 @@ static u8 ipc_log_lvl = RMNET_CTL_LOG_ERR;
static DEFINE_SPINLOCK(client_lock);
static struct rmnet_ctl_endpoint ctl_ep;
void rmnet_ctl_endpoint_setdev(const struct rmnet_ctl_dev *dev)
void rmnet_ctl_set_dbgfs(bool enable)
{
rcu_assign_pointer(ctl_ep.dev, dev);
if (enable) {
if (IS_ERR_OR_NULL(ctl_ep.dbgfs_dir))
ctl_ep.dbgfs_dir = debugfs_create_dir(
RMNET_CTL_LOG_NAME, NULL);
if (dev) {
ctl_ep.dbgfs_dir = debugfs_create_dir(
RMNET_CTL_LOG_NAME, NULL);
if (!IS_ERR_OR_NULL(ctl_ep.dbgfs_dir))
ctl_ep.dbgfs_loglvl = debugfs_create_u8(
RMNET_CTL_LOG_LVL, 0644, ctl_ep.dbgfs_dir,
@@ -52,9 +56,18 @@ void rmnet_ctl_endpoint_setdev(const struct rmnet_ctl_dev *dev)
RMNET_CTL_LOG_PAGE, RMNET_CTL_LOG_NAME, 0);
} else {
debugfs_remove_recursive(ctl_ep.dbgfs_dir);
ipc_log_context_destroy(ctl_ep.ipc_log);
ctl_ep.dbgfs_dir = NULL;
ctl_ep.dbgfs_loglvl = NULL;
ctl_ep.ipc_log = NULL;
}
}
void rmnet_ctl_endpoint_setdev(const struct rmnet_ctl_dev *dev)
{
rcu_assign_pointer(ctl_ep.dev, dev);
}
void rmnet_ctl_endpoint_post(const void *data, size_t len)
{
struct rmnet_ctl_client *client;
@@ -63,22 +76,38 @@ void rmnet_ctl_endpoint_post(const void *data, size_t len)
if (unlikely(!data || !len))
return;
rmnet_ctl_log_info("RX", data, len);
if (len == 0xFFFFFFFF) {
skb = (struct sk_buff *)data;
rmnet_ctl_log_info("RX", skb->data, skb->len);
rcu_read_lock();
rcu_read_lock();
client = rcu_dereference(ctl_ep.client);
if (client && client->hooks.ctl_dl_client_hook) {
skb = alloc_skb(len, GFP_ATOMIC);
if (skb) {
skb_put_data(skb, data, len);
client = rcu_dereference(ctl_ep.client);
if (client && client->hooks.ctl_dl_client_hook) {
skb->protocol = htons(ETH_P_MAP);
client->hooks.ctl_dl_client_hook(skb);
} else {
kfree(skb);
}
}
rcu_read_unlock();
rcu_read_unlock();
} else {
rmnet_ctl_log_info("RX", data, len);
rcu_read_lock();
client = rcu_dereference(ctl_ep.client);
if (client && client->hooks.ctl_dl_client_hook) {
skb = alloc_skb(len, GFP_ATOMIC);
if (skb) {
skb_put_data(skb, data, len);
skb->protocol = htons(ETH_P_MAP);
client->hooks.ctl_dl_client_hook(skb);
}
}
rcu_read_unlock();
}
}
void *rmnet_ctl_register_client(struct rmnet_ctl_client_hooks *hook)