1 /* SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause) */
2 /*
3  * Copyright 2014-2016 Freescale Semiconductor Inc.
4  * Copyright 2016 NXP
5  *
6  */
7 #ifndef __FSL_DPAA2_FD_H
8 #define __FSL_DPAA2_FD_H
9 
10 #include <linux/kernel.h>
11 
12 /**
13  * DOC: DPAA2 FD - Frame Descriptor APIs for DPAA2
14  *
15  * Frame Descriptors (FDs) are used to describe frame data in the DPAA2.
16  * Frames can be enqueued and dequeued to Frame Queues (FQs) which are consumed
17  * by the various DPAA accelerators (WRIOP, SEC, PME, DCE)
18  *
19  * There are three types of frames: single, scatter gather, and frame lists.
20  *
21  * The set of APIs in this file must be used to create, manipulate and
22  * query Frame Descriptors.
23  */
24 
25 /**
26  * struct dpaa2_fd - Struct describing FDs
27  * @words:         for easier/faster copying the whole FD structure
28  * @addr:          address in the FD
29  * @len:           length in the FD
30  * @bpid:          buffer pool ID
31  * @format_offset: format, offset, and short-length fields
32  * @frc:           frame context
33  * @ctrl:          control bits...including dd, sc, va, err, etc
34  * @flc:           flow context address
35  *
36  * This structure represents the basic Frame Descriptor used in the system.
37  */
38 struct dpaa2_fd {
39 	union {
40 		u32 words[8];
41 		struct dpaa2_fd_simple {
42 			__le64 addr;
43 			__le32 len;
44 			__le16 bpid;
45 			__le16 format_offset;
46 			__le32 frc;
47 			__le32 ctrl;
48 			__le64 flc;
49 		} simple;
50 	};
51 };
52 
53 #define FD_SHORT_LEN_FLAG_MASK	0x1
54 #define FD_SHORT_LEN_FLAG_SHIFT	14
55 #define FD_SHORT_LEN_MASK	0x3FFFF
56 #define FD_OFFSET_MASK		0x0FFF
57 #define FD_FORMAT_MASK		0x3
58 #define FD_FORMAT_SHIFT		12
59 #define FD_BPID_MASK		0x3FFF
60 #define SG_SHORT_LEN_FLAG_MASK	0x1
61 #define SG_SHORT_LEN_FLAG_SHIFT	14
62 #define SG_SHORT_LEN_MASK	0x1FFFF
63 #define SG_OFFSET_MASK		0x0FFF
64 #define SG_FORMAT_MASK		0x3
65 #define SG_FORMAT_SHIFT		12
66 #define SG_BPID_MASK		0x3FFF
67 #define SG_FINAL_FLAG_MASK	0x1
68 #define SG_FINAL_FLAG_SHIFT	15
69 
70 /* Error bits in FD CTRL */
71 #define FD_CTRL_ERR_MASK	0x000000FF
72 #define FD_CTRL_UFD		0x00000004
73 #define FD_CTRL_SBE		0x00000008
74 #define FD_CTRL_FLC		0x00000010
75 #define FD_CTRL_FSE		0x00000020
76 #define FD_CTRL_FAERR		0x00000040
77 
78 /* Annotation bits in FD CTRL */
79 #define FD_CTRL_PTA		0x00800000
80 #define FD_CTRL_PTV1		0x00400000
81 
82 enum dpaa2_fd_format {
83 	dpaa2_fd_single = 0,
84 	dpaa2_fd_list,
85 	dpaa2_fd_sg
86 };
87 
88 /**
89  * dpaa2_fd_get_addr() - get the addr field of frame descriptor
90  * @fd: the given frame descriptor
91  *
92  * Return the address in the frame descriptor.
93  */
dpaa2_fd_get_addr(const struct dpaa2_fd * fd)94 static inline dma_addr_t dpaa2_fd_get_addr(const struct dpaa2_fd *fd)
95 {
96 	return (dma_addr_t)le64_to_cpu(fd->simple.addr);
97 }
98 
99 /**
100  * dpaa2_fd_set_addr() - Set the addr field of frame descriptor
101  * @fd: the given frame descriptor
102  * @addr: the address needs to be set in frame descriptor
103  */
dpaa2_fd_set_addr(struct dpaa2_fd * fd,dma_addr_t addr)104 static inline void dpaa2_fd_set_addr(struct dpaa2_fd *fd, dma_addr_t addr)
105 {
106 	fd->simple.addr = cpu_to_le64(addr);
107 }
108 
109 /**
110  * dpaa2_fd_get_frc() - Get the frame context in the frame descriptor
111  * @fd: the given frame descriptor
112  *
113  * Return the frame context field in the frame descriptor.
114  */
dpaa2_fd_get_frc(const struct dpaa2_fd * fd)115 static inline u32 dpaa2_fd_get_frc(const struct dpaa2_fd *fd)
116 {
117 	return le32_to_cpu(fd->simple.frc);
118 }
119 
120 /**
121  * dpaa2_fd_set_frc() - Set the frame context in the frame descriptor
122  * @fd: the given frame descriptor
123  * @frc: the frame context needs to be set in frame descriptor
124  */
dpaa2_fd_set_frc(struct dpaa2_fd * fd,u32 frc)125 static inline void dpaa2_fd_set_frc(struct dpaa2_fd *fd, u32 frc)
126 {
127 	fd->simple.frc = cpu_to_le32(frc);
128 }
129 
130 /**
131  * dpaa2_fd_get_ctrl() - Get the control bits in the frame descriptor
132  * @fd: the given frame descriptor
133  *
134  * Return the control bits field in the frame descriptor.
135  */
dpaa2_fd_get_ctrl(const struct dpaa2_fd * fd)136 static inline u32 dpaa2_fd_get_ctrl(const struct dpaa2_fd *fd)
137 {
138 	return le32_to_cpu(fd->simple.ctrl);
139 }
140 
141 /**
142  * dpaa2_fd_set_ctrl() - Set the control bits in the frame descriptor
143  * @fd: the given frame descriptor
144  * @ctrl: the control bits to be set in the frame descriptor
145  */
dpaa2_fd_set_ctrl(struct dpaa2_fd * fd,u32 ctrl)146 static inline void dpaa2_fd_set_ctrl(struct dpaa2_fd *fd, u32 ctrl)
147 {
148 	fd->simple.ctrl = cpu_to_le32(ctrl);
149 }
150 
151 /**
152  * dpaa2_fd_get_flc() - Get the flow context in the frame descriptor
153  * @fd: the given frame descriptor
154  *
155  * Return the flow context in the frame descriptor.
156  */
dpaa2_fd_get_flc(const struct dpaa2_fd * fd)157 static inline dma_addr_t dpaa2_fd_get_flc(const struct dpaa2_fd *fd)
158 {
159 	return (dma_addr_t)le64_to_cpu(fd->simple.flc);
160 }
161 
162 /**
163  * dpaa2_fd_set_flc() - Set the flow context field of frame descriptor
164  * @fd: the given frame descriptor
165  * @flc_addr: the flow context needs to be set in frame descriptor
166  */
dpaa2_fd_set_flc(struct dpaa2_fd * fd,dma_addr_t flc_addr)167 static inline void dpaa2_fd_set_flc(struct dpaa2_fd *fd,  dma_addr_t flc_addr)
168 {
169 	fd->simple.flc = cpu_to_le64(flc_addr);
170 }
171 
dpaa2_fd_short_len(const struct dpaa2_fd * fd)172 static inline bool dpaa2_fd_short_len(const struct dpaa2_fd *fd)
173 {
174 	return !!((le16_to_cpu(fd->simple.format_offset) >>
175 		  FD_SHORT_LEN_FLAG_SHIFT) & FD_SHORT_LEN_FLAG_MASK);
176 }
177 
178 /**
179  * dpaa2_fd_get_len() - Get the length in the frame descriptor
180  * @fd: the given frame descriptor
181  *
182  * Return the length field in the frame descriptor.
183  */
dpaa2_fd_get_len(const struct dpaa2_fd * fd)184 static inline u32 dpaa2_fd_get_len(const struct dpaa2_fd *fd)
185 {
186 	if (dpaa2_fd_short_len(fd))
187 		return le32_to_cpu(fd->simple.len) & FD_SHORT_LEN_MASK;
188 
189 	return le32_to_cpu(fd->simple.len);
190 }
191 
192 /**
193  * dpaa2_fd_set_len() - Set the length field of frame descriptor
194  * @fd: the given frame descriptor
195  * @len: the length needs to be set in frame descriptor
196  */
dpaa2_fd_set_len(struct dpaa2_fd * fd,u32 len)197 static inline void dpaa2_fd_set_len(struct dpaa2_fd *fd, u32 len)
198 {
199 	fd->simple.len = cpu_to_le32(len);
200 }
201 
202 /**
203  * dpaa2_fd_get_offset() - Get the offset field in the frame descriptor
204  * @fd: the given frame descriptor
205  *
206  * Return the offset.
207  */
dpaa2_fd_get_offset(const struct dpaa2_fd * fd)208 static inline uint16_t dpaa2_fd_get_offset(const struct dpaa2_fd *fd)
209 {
210 	return le16_to_cpu(fd->simple.format_offset) & FD_OFFSET_MASK;
211 }
212 
213 /**
214  * dpaa2_fd_set_offset() - Set the offset field of frame descriptor
215  * @fd: the given frame descriptor
216  * @offset: the offset needs to be set in frame descriptor
217  */
dpaa2_fd_set_offset(struct dpaa2_fd * fd,uint16_t offset)218 static inline void dpaa2_fd_set_offset(struct dpaa2_fd *fd, uint16_t offset)
219 {
220 	fd->simple.format_offset &= cpu_to_le16(~FD_OFFSET_MASK);
221 	fd->simple.format_offset |= cpu_to_le16(offset);
222 }
223 
224 /**
225  * dpaa2_fd_get_format() - Get the format field in the frame descriptor
226  * @fd: the given frame descriptor
227  *
228  * Return the format.
229  */
dpaa2_fd_get_format(const struct dpaa2_fd * fd)230 static inline enum dpaa2_fd_format dpaa2_fd_get_format(
231 						const struct dpaa2_fd *fd)
232 {
233 	return (enum dpaa2_fd_format)((le16_to_cpu(fd->simple.format_offset)
234 				      >> FD_FORMAT_SHIFT) & FD_FORMAT_MASK);
235 }
236 
237 /**
238  * dpaa2_fd_set_format() - Set the format field of frame descriptor
239  * @fd: the given frame descriptor
240  * @format: the format needs to be set in frame descriptor
241  */
dpaa2_fd_set_format(struct dpaa2_fd * fd,enum dpaa2_fd_format format)242 static inline void dpaa2_fd_set_format(struct dpaa2_fd *fd,
243 				       enum dpaa2_fd_format format)
244 {
245 	fd->simple.format_offset &=
246 		cpu_to_le16(~(FD_FORMAT_MASK << FD_FORMAT_SHIFT));
247 	fd->simple.format_offset |= cpu_to_le16(format << FD_FORMAT_SHIFT);
248 }
249 
250 /**
251  * dpaa2_fd_get_bpid() - Get the bpid field in the frame descriptor
252  * @fd: the given frame descriptor
253  *
254  * Return the buffer pool id.
255  */
dpaa2_fd_get_bpid(const struct dpaa2_fd * fd)256 static inline uint16_t dpaa2_fd_get_bpid(const struct dpaa2_fd *fd)
257 {
258 	return le16_to_cpu(fd->simple.bpid) & FD_BPID_MASK;
259 }
260 
261 /**
262  * dpaa2_fd_set_bpid() - Set the bpid field of frame descriptor
263  * @fd: the given frame descriptor
264  * @bpid: buffer pool id to be set
265  */
dpaa2_fd_set_bpid(struct dpaa2_fd * fd,uint16_t bpid)266 static inline void dpaa2_fd_set_bpid(struct dpaa2_fd *fd, uint16_t bpid)
267 {
268 	fd->simple.bpid &= cpu_to_le16(~(FD_BPID_MASK));
269 	fd->simple.bpid |= cpu_to_le16(bpid);
270 }
271 
272 /**
273  * struct dpaa2_sg_entry - the scatter-gathering structure
274  * @addr: address of the sg entry
275  * @len: length in this sg entry
276  * @bpid: buffer pool id
277  * @format_offset: format and offset fields
278  */
279 struct dpaa2_sg_entry {
280 	__le64 addr;
281 	__le32 len;
282 	__le16 bpid;
283 	__le16 format_offset;
284 };
285 
286 enum dpaa2_sg_format {
287 	dpaa2_sg_single = 0,
288 	dpaa2_sg_frame_data,
289 	dpaa2_sg_sgt_ext
290 };
291 
292 /* Accessors for SG entry fields */
293 
294 /**
295  * dpaa2_sg_get_addr() - Get the address from SG entry
296  * @sg: the given scatter-gathering object
297  *
298  * Return the address.
299  */
dpaa2_sg_get_addr(const struct dpaa2_sg_entry * sg)300 static inline dma_addr_t dpaa2_sg_get_addr(const struct dpaa2_sg_entry *sg)
301 {
302 	return (dma_addr_t)le64_to_cpu(sg->addr);
303 }
304 
305 /**
306  * dpaa2_sg_set_addr() - Set the address in SG entry
307  * @sg: the given scatter-gathering object
308  * @addr: the address to be set
309  */
dpaa2_sg_set_addr(struct dpaa2_sg_entry * sg,dma_addr_t addr)310 static inline void dpaa2_sg_set_addr(struct dpaa2_sg_entry *sg, dma_addr_t addr)
311 {
312 	sg->addr = cpu_to_le64(addr);
313 }
314 
dpaa2_sg_short_len(const struct dpaa2_sg_entry * sg)315 static inline bool dpaa2_sg_short_len(const struct dpaa2_sg_entry *sg)
316 {
317 	return !!((le16_to_cpu(sg->format_offset) >> SG_SHORT_LEN_FLAG_SHIFT)
318 		& SG_SHORT_LEN_FLAG_MASK);
319 }
320 
321 /**
322  * dpaa2_sg_get_len() - Get the length in SG entry
323  * @sg: the given scatter-gathering object
324  *
325  * Return the length.
326  */
dpaa2_sg_get_len(const struct dpaa2_sg_entry * sg)327 static inline u32 dpaa2_sg_get_len(const struct dpaa2_sg_entry *sg)
328 {
329 	if (dpaa2_sg_short_len(sg))
330 		return le32_to_cpu(sg->len) & SG_SHORT_LEN_MASK;
331 
332 	return le32_to_cpu(sg->len);
333 }
334 
335 /**
336  * dpaa2_sg_set_len() - Set the length in SG entry
337  * @sg: the given scatter-gathering object
338  * @len: the length to be set
339  */
dpaa2_sg_set_len(struct dpaa2_sg_entry * sg,u32 len)340 static inline void dpaa2_sg_set_len(struct dpaa2_sg_entry *sg, u32 len)
341 {
342 	sg->len = cpu_to_le32(len);
343 }
344 
345 /**
346  * dpaa2_sg_get_offset() - Get the offset in SG entry
347  * @sg: the given scatter-gathering object
348  *
349  * Return the offset.
350  */
dpaa2_sg_get_offset(const struct dpaa2_sg_entry * sg)351 static inline u16 dpaa2_sg_get_offset(const struct dpaa2_sg_entry *sg)
352 {
353 	return le16_to_cpu(sg->format_offset) & SG_OFFSET_MASK;
354 }
355 
356 /**
357  * dpaa2_sg_set_offset() - Set the offset in SG entry
358  * @sg: the given scatter-gathering object
359  * @offset: the offset to be set
360  */
dpaa2_sg_set_offset(struct dpaa2_sg_entry * sg,u16 offset)361 static inline void dpaa2_sg_set_offset(struct dpaa2_sg_entry *sg,
362 				       u16 offset)
363 {
364 	sg->format_offset &= cpu_to_le16(~SG_OFFSET_MASK);
365 	sg->format_offset |= cpu_to_le16(offset);
366 }
367 
368 /**
369  * dpaa2_sg_get_format() - Get the SG format in SG entry
370  * @sg: the given scatter-gathering object
371  *
372  * Return the format.
373  */
374 static inline enum dpaa2_sg_format
dpaa2_sg_get_format(const struct dpaa2_sg_entry * sg)375 	dpaa2_sg_get_format(const struct dpaa2_sg_entry *sg)
376 {
377 	return (enum dpaa2_sg_format)((le16_to_cpu(sg->format_offset)
378 				       >> SG_FORMAT_SHIFT) & SG_FORMAT_MASK);
379 }
380 
381 /**
382  * dpaa2_sg_set_format() - Set the SG format in SG entry
383  * @sg: the given scatter-gathering object
384  * @format: the format to be set
385  */
dpaa2_sg_set_format(struct dpaa2_sg_entry * sg,enum dpaa2_sg_format format)386 static inline void dpaa2_sg_set_format(struct dpaa2_sg_entry *sg,
387 				       enum dpaa2_sg_format format)
388 {
389 	sg->format_offset &= cpu_to_le16(~(SG_FORMAT_MASK << SG_FORMAT_SHIFT));
390 	sg->format_offset |= cpu_to_le16(format << SG_FORMAT_SHIFT);
391 }
392 
393 /**
394  * dpaa2_sg_get_bpid() - Get the buffer pool id in SG entry
395  * @sg: the given scatter-gathering object
396  *
397  * Return the bpid.
398  */
dpaa2_sg_get_bpid(const struct dpaa2_sg_entry * sg)399 static inline u16 dpaa2_sg_get_bpid(const struct dpaa2_sg_entry *sg)
400 {
401 	return le16_to_cpu(sg->bpid) & SG_BPID_MASK;
402 }
403 
404 /**
405  * dpaa2_sg_set_bpid() - Set the buffer pool id in SG entry
406  * @sg: the given scatter-gathering object
407  * @bpid: the bpid to be set
408  */
dpaa2_sg_set_bpid(struct dpaa2_sg_entry * sg,u16 bpid)409 static inline void dpaa2_sg_set_bpid(struct dpaa2_sg_entry *sg, u16 bpid)
410 {
411 	sg->bpid &= cpu_to_le16(~(SG_BPID_MASK));
412 	sg->bpid |= cpu_to_le16(bpid);
413 }
414 
415 /**
416  * dpaa2_sg_is_final() - Check final bit in SG entry
417  * @sg: the given scatter-gathering object
418  *
419  * Return bool.
420  */
dpaa2_sg_is_final(const struct dpaa2_sg_entry * sg)421 static inline bool dpaa2_sg_is_final(const struct dpaa2_sg_entry *sg)
422 {
423 	return !!(le16_to_cpu(sg->format_offset) >> SG_FINAL_FLAG_SHIFT);
424 }
425 
426 /**
427  * dpaa2_sg_set_final() - Set the final bit in SG entry
428  * @sg: the given scatter-gathering object
429  * @final: the final boolean to be set
430  */
dpaa2_sg_set_final(struct dpaa2_sg_entry * sg,bool final)431 static inline void dpaa2_sg_set_final(struct dpaa2_sg_entry *sg, bool final)
432 {
433 	sg->format_offset &= cpu_to_le16((~(SG_FINAL_FLAG_MASK
434 					 << SG_FINAL_FLAG_SHIFT)) & 0xFFFF);
435 	sg->format_offset |= cpu_to_le16(final << SG_FINAL_FLAG_SHIFT);
436 }
437 
438 #endif /* __FSL_DPAA2_FD_H */
439