136 lines
3.9 KiB
C
136 lines
3.9 KiB
C
|
/* SPDX-License-Identifier: GPL-2.0-only
|
||
|
*
|
||
|
* Copyright (c) 2021, MediaTek Inc.
|
||
|
* Copyright (c) 2021-2022, Intel Corporation.
|
||
|
*
|
||
|
* Authors:
|
||
|
* Haijun Liu <haijun.liu@mediatek.com>
|
||
|
* Moises Veleta <moises.veleta@intel.com>
|
||
|
* Ricardo Martinez <ricardo.martinez@linux.intel.com>
|
||
|
*
|
||
|
* Contributors:
|
||
|
* Amir Hanania <amir.hanania@intel.com>
|
||
|
* Andy Shevchenko <andriy.shevchenko@linux.intel.com>
|
||
|
* Chandrashekar Devegowda <chandrashekar.devegowda@intel.com>
|
||
|
* Eliot Lee <eliot.lee@intel.com>
|
||
|
*/
|
||
|
|
||
|
#ifndef __T7XX_PORT_H__
|
||
|
#define __T7XX_PORT_H__
|
||
|
|
||
|
#include <linux/bits.h>
|
||
|
#include <linux/device.h>
|
||
|
#include <linux/mutex.h>
|
||
|
#include <linux/sched.h>
|
||
|
#include <linux/skbuff.h>
|
||
|
#include <linux/spinlock.h>
|
||
|
#include <linux/types.h>
|
||
|
#include <linux/wait.h>
|
||
|
#include <linux/wwan.h>
|
||
|
|
||
|
#include "t7xx_hif_cldma.h"
|
||
|
#include "t7xx_pci.h"
|
||
|
|
||
|
#define PORT_CH_ID_MASK GENMASK(7, 0)
|
||
|
|
||
|
/* Channel ID and Message ID definitions.
|
||
|
* The channel number consists of peer_id(15:12) , channel_id(11:0)
|
||
|
* peer_id:
|
||
|
* 0:reserved, 1: to sAP, 2: to MD
|
||
|
*/
|
||
|
enum port_ch {
|
||
|
/* to MD */
|
||
|
PORT_CH_CONTROL_RX = 0x2000,
|
||
|
PORT_CH_CONTROL_TX = 0x2001,
|
||
|
PORT_CH_UART1_RX = 0x2006, /* META */
|
||
|
PORT_CH_UART1_TX = 0x2008,
|
||
|
PORT_CH_UART2_RX = 0x200a, /* AT */
|
||
|
PORT_CH_UART2_TX = 0x200c,
|
||
|
PORT_CH_MD_LOG_RX = 0x202a, /* MD logging */
|
||
|
PORT_CH_MD_LOG_TX = 0x202b,
|
||
|
PORT_CH_LB_IT_RX = 0x203e, /* Loop back test */
|
||
|
PORT_CH_LB_IT_TX = 0x203f,
|
||
|
PORT_CH_STATUS_RX = 0x2043, /* Status events */
|
||
|
PORT_CH_MIPC_RX = 0x20ce, /* MIPC */
|
||
|
PORT_CH_MIPC_TX = 0x20cf,
|
||
|
PORT_CH_MBIM_RX = 0x20d0,
|
||
|
PORT_CH_MBIM_TX = 0x20d1,
|
||
|
PORT_CH_DSS0_RX = 0x20d2,
|
||
|
PORT_CH_DSS0_TX = 0x20d3,
|
||
|
PORT_CH_DSS1_RX = 0x20d4,
|
||
|
PORT_CH_DSS1_TX = 0x20d5,
|
||
|
PORT_CH_DSS2_RX = 0x20d6,
|
||
|
PORT_CH_DSS2_TX = 0x20d7,
|
||
|
PORT_CH_DSS3_RX = 0x20d8,
|
||
|
PORT_CH_DSS3_TX = 0x20d9,
|
||
|
PORT_CH_DSS4_RX = 0x20da,
|
||
|
PORT_CH_DSS4_TX = 0x20db,
|
||
|
PORT_CH_DSS5_RX = 0x20dc,
|
||
|
PORT_CH_DSS5_TX = 0x20dd,
|
||
|
PORT_CH_DSS6_RX = 0x20de,
|
||
|
PORT_CH_DSS6_TX = 0x20df,
|
||
|
PORT_CH_DSS7_RX = 0x20e0,
|
||
|
PORT_CH_DSS7_TX = 0x20e1,
|
||
|
};
|
||
|
|
||
|
struct t7xx_port;
|
||
|
struct port_ops {
|
||
|
int (*init)(struct t7xx_port *port);
|
||
|
int (*recv_skb)(struct t7xx_port *port, struct sk_buff *skb);
|
||
|
void (*md_state_notify)(struct t7xx_port *port, unsigned int md_state);
|
||
|
void (*uninit)(struct t7xx_port *port);
|
||
|
int (*enable_chl)(struct t7xx_port *port);
|
||
|
int (*disable_chl)(struct t7xx_port *port);
|
||
|
};
|
||
|
|
||
|
struct t7xx_port_conf {
|
||
|
enum port_ch tx_ch;
|
||
|
enum port_ch rx_ch;
|
||
|
unsigned char txq_index;
|
||
|
unsigned char rxq_index;
|
||
|
unsigned char txq_exp_index;
|
||
|
unsigned char rxq_exp_index;
|
||
|
enum cldma_id path_id;
|
||
|
struct port_ops *ops;
|
||
|
char *name;
|
||
|
enum wwan_port_type port_type;
|
||
|
};
|
||
|
|
||
|
struct t7xx_port {
|
||
|
/* Members not initialized in definition */
|
||
|
const struct t7xx_port_conf *port_conf;
|
||
|
struct wwan_port *wwan_port;
|
||
|
struct t7xx_pci_dev *t7xx_dev;
|
||
|
struct device *dev;
|
||
|
u16 seq_nums[2]; /* TX/RX sequence numbers */
|
||
|
atomic_t usage_cnt;
|
||
|
struct list_head entry;
|
||
|
struct list_head queue_entry;
|
||
|
/* TX and RX flows are asymmetric since ports are multiplexed on
|
||
|
* queues.
|
||
|
*
|
||
|
* TX: data blocks are sent directly to a queue. Each port
|
||
|
* does not maintain a TX list; instead, they only provide
|
||
|
* a wait_queue_head for blocking writes.
|
||
|
*
|
||
|
* RX: Each port uses a RX list to hold packets,
|
||
|
* allowing the modem to dispatch RX packet as quickly as possible.
|
||
|
*/
|
||
|
struct sk_buff_head rx_skb_list;
|
||
|
spinlock_t port_update_lock; /* Protects port configuration */
|
||
|
wait_queue_head_t rx_wq;
|
||
|
int rx_length_th;
|
||
|
bool chan_enable;
|
||
|
struct task_struct *thread;
|
||
|
};
|
||
|
|
||
|
struct sk_buff *t7xx_port_alloc_skb(int payload);
|
||
|
struct sk_buff *t7xx_ctrl_alloc_skb(int payload);
|
||
|
int t7xx_port_enqueue_skb(struct t7xx_port *port, struct sk_buff *skb);
|
||
|
int t7xx_port_send_skb(struct t7xx_port *port, struct sk_buff *skb, unsigned int pkt_header,
|
||
|
unsigned int ex_msg);
|
||
|
int t7xx_port_send_ctl_skb(struct t7xx_port *port, struct sk_buff *skb, unsigned int msg,
|
||
|
unsigned int ex_msg);
|
||
|
|
||
|
#endif /* __T7XX_PORT_H__ */
|