1/* SPDX-License-Identifier: GPL-2.0-only */
2/* Copyright (C) 2023 Intel Corporation */
3
4#ifndef _IDPF_CONTROLQ_API_H_
5#define _IDPF_CONTROLQ_API_H_
6
7#include "idpf_mem.h"
8
9struct idpf_hw;
10
11/* Used for queue init, response and events */
12enum idpf_ctlq_type {
13	IDPF_CTLQ_TYPE_MAILBOX_TX	= 0,
14	IDPF_CTLQ_TYPE_MAILBOX_RX	= 1,
15	IDPF_CTLQ_TYPE_CONFIG_TX	= 2,
16	IDPF_CTLQ_TYPE_CONFIG_RX	= 3,
17	IDPF_CTLQ_TYPE_EVENT_RX		= 4,
18	IDPF_CTLQ_TYPE_RDMA_TX		= 5,
19	IDPF_CTLQ_TYPE_RDMA_RX		= 6,
20	IDPF_CTLQ_TYPE_RDMA_COMPL	= 7
21};
22
23/* Generic Control Queue Structures */
24struct idpf_ctlq_reg {
25	/* used for queue tracking */
26	u32 head;
27	u32 tail;
28	/* Below applies only to default mb (if present) */
29	u32 len;
30	u32 bah;
31	u32 bal;
32	u32 len_mask;
33	u32 len_ena_mask;
34	u32 head_mask;
35};
36
37/* Generic queue msg structure */
38struct idpf_ctlq_msg {
39	u8 vmvf_type; /* represents the source of the message on recv */
40#define IDPF_VMVF_TYPE_VF 0
41#define IDPF_VMVF_TYPE_VM 1
42#define IDPF_VMVF_TYPE_PF 2
43	u8 host_id;
44	/* 3b field used only when sending a message to CP - to be used in
45	 * combination with target func_id to route the message
46	 */
47#define IDPF_HOST_ID_MASK 0x7
48
49	u16 opcode;
50	u16 data_len;	/* data_len = 0 when no payload is attached */
51	union {
52		u16 func_id;	/* when sending a message */
53		u16 status;	/* when receiving a message */
54	};
55	union {
56		struct {
57			u32 chnl_opcode;
58			u32 chnl_retval;
59		} mbx;
60	} cookie;
61	union {
62#define IDPF_DIRECT_CTX_SIZE	16
63#define IDPF_INDIRECT_CTX_SIZE	8
64		/* 16 bytes of context can be provided or 8 bytes of context
65		 * plus the address of a DMA buffer
66		 */
67		u8 direct[IDPF_DIRECT_CTX_SIZE];
68		struct {
69			u8 context[IDPF_INDIRECT_CTX_SIZE];
70			struct idpf_dma_mem *payload;
71		} indirect;
72		struct {
73			u32 rsvd;
74			u16 data;
75			u16 flags;
76		} sw_cookie;
77	} ctx;
78};
79
80/* Generic queue info structures */
81/* MB, CONFIG and EVENT q do not have extended info */
82struct idpf_ctlq_create_info {
83	enum idpf_ctlq_type type;
84	int id; /* absolute queue offset passed as input
85		 * -1 for default mailbox if present
86		 */
87	u16 len; /* Queue length passed as input */
88	u16 buf_size; /* buffer size passed as input */
89	u64 base_address; /* output, HPA of the Queue start  */
90	struct idpf_ctlq_reg reg; /* registers accessed by ctlqs */
91
92	int ext_info_size;
93	void *ext_info; /* Specific to q type */
94};
95
96/* Control Queue information */
97struct idpf_ctlq_info {
98	struct list_head cq_list;
99
100	enum idpf_ctlq_type cq_type;
101	int q_id;
102	struct mutex cq_lock;		/* control queue lock */
103	/* used for interrupt processing */
104	u16 next_to_use;
105	u16 next_to_clean;
106	u16 next_to_post;		/* starting descriptor to post buffers
107					 * to after recev
108					 */
109
110	struct idpf_dma_mem desc_ring;	/* descriptor ring memory
111					 * idpf_dma_mem is defined in OSdep.h
112					 */
113	union {
114		struct idpf_dma_mem **rx_buff;
115		struct idpf_ctlq_msg **tx_msg;
116	} bi;
117
118	u16 buf_size;			/* queue buffer size */
119	u16 ring_size;			/* Number of descriptors */
120	struct idpf_ctlq_reg reg;	/* registers accessed by ctlqs */
121};
122
123/**
124 * enum idpf_mbx_opc - PF/VF mailbox commands
125 * @idpf_mbq_opc_send_msg_to_cp: used by PF or VF to send a message to its CP
126 */
127enum idpf_mbx_opc {
128	idpf_mbq_opc_send_msg_to_cp		= 0x0801,
129};
130
131/* API supported for control queue management */
132/* Will init all required q including default mb.  "q_info" is an array of
133 * create_info structs equal to the number of control queues to be created.
134 */
135int idpf_ctlq_init(struct idpf_hw *hw, u8 num_q,
136		   struct idpf_ctlq_create_info *q_info);
137
138/* Allocate and initialize a single control queue, which will be added to the
139 * control queue list; returns a handle to the created control queue
140 */
141int idpf_ctlq_add(struct idpf_hw *hw,
142		  struct idpf_ctlq_create_info *qinfo,
143		  struct idpf_ctlq_info **cq);
144
145/* Deinitialize and deallocate a single control queue */
146void idpf_ctlq_remove(struct idpf_hw *hw,
147		      struct idpf_ctlq_info *cq);
148
149/* Sends messages to HW and will also free the buffer*/
150int idpf_ctlq_send(struct idpf_hw *hw,
151		   struct idpf_ctlq_info *cq,
152		   u16 num_q_msg,
153		   struct idpf_ctlq_msg q_msg[]);
154
155/* Receives messages and called by interrupt handler/polling
156 * initiated by app/process. Also caller is supposed to free the buffers
157 */
158int idpf_ctlq_recv(struct idpf_ctlq_info *cq, u16 *num_q_msg,
159		   struct idpf_ctlq_msg *q_msg);
160
161/* Reclaims send descriptors on HW write back */
162int idpf_ctlq_clean_sq(struct idpf_ctlq_info *cq, u16 *clean_count,
163		       struct idpf_ctlq_msg *msg_status[]);
164
165/* Indicate RX buffers are done being processed */
166int idpf_ctlq_post_rx_buffs(struct idpf_hw *hw,
167			    struct idpf_ctlq_info *cq,
168			    u16 *buff_count,
169			    struct idpf_dma_mem **buffs);
170
171/* Will destroy all q including the default mb */
172void idpf_ctlq_deinit(struct idpf_hw *hw);
173
174#endif /* _IDPF_CONTROLQ_API_H_ */
175