1// SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause)
2/* Copyright 2013-2016 Freescale Semiconductor Inc.
3 * Copyright 2016 NXP
4 * Copyright 2020 NXP
5 */
6#include <linux/kernel.h>
7#include <linux/errno.h>
8#include <linux/fsl/mc.h>
9#include "dpni.h"
10#include "dpni-cmd.h"
11
12/**
13 * dpni_prepare_key_cfg() - function prepare extract parameters
14 * @cfg: defining a full Key Generation profile (rule)
15 * @key_cfg_buf: Zeroed 256 bytes of memory before mapping it to DMA
16 *
17 * This function has to be called before the following functions:
18 *	- dpni_set_rx_tc_dist()
19 *	- dpni_set_qos_table()
20 *
21 * Return:	'0' on Success; Error code otherwise.
22 */
23int dpni_prepare_key_cfg(const struct dpkg_profile_cfg *cfg, u8 *key_cfg_buf)
24{
25	int i, j;
26	struct dpni_ext_set_rx_tc_dist *dpni_ext;
27	struct dpni_dist_extract *extr;
28
29	if (cfg->num_extracts > DPKG_MAX_NUM_OF_EXTRACTS)
30		return -EINVAL;
31
32	dpni_ext = (struct dpni_ext_set_rx_tc_dist *)key_cfg_buf;
33	dpni_ext->num_extracts = cfg->num_extracts;
34
35	for (i = 0; i < cfg->num_extracts; i++) {
36		extr = &dpni_ext->extracts[i];
37
38		switch (cfg->extracts[i].type) {
39		case DPKG_EXTRACT_FROM_HDR:
40			extr->prot = cfg->extracts[i].extract.from_hdr.prot;
41			dpni_set_field(extr->efh_type, EFH_TYPE,
42				       cfg->extracts[i].extract.from_hdr.type);
43			extr->size = cfg->extracts[i].extract.from_hdr.size;
44			extr->offset = cfg->extracts[i].extract.from_hdr.offset;
45			extr->field = cpu_to_le32(
46				cfg->extracts[i].extract.from_hdr.field);
47			extr->hdr_index =
48				cfg->extracts[i].extract.from_hdr.hdr_index;
49			break;
50		case DPKG_EXTRACT_FROM_DATA:
51			extr->size = cfg->extracts[i].extract.from_data.size;
52			extr->offset =
53				cfg->extracts[i].extract.from_data.offset;
54			break;
55		case DPKG_EXTRACT_FROM_PARSE:
56			extr->size = cfg->extracts[i].extract.from_parse.size;
57			extr->offset =
58				cfg->extracts[i].extract.from_parse.offset;
59			break;
60		default:
61			return -EINVAL;
62		}
63
64		extr->num_of_byte_masks = cfg->extracts[i].num_of_byte_masks;
65		dpni_set_field(extr->extract_type, EXTRACT_TYPE,
66			       cfg->extracts[i].type);
67
68		for (j = 0; j < DPKG_NUM_OF_MASKS; j++) {
69			extr->masks[j].mask = cfg->extracts[i].masks[j].mask;
70			extr->masks[j].offset =
71				cfg->extracts[i].masks[j].offset;
72		}
73	}
74
75	return 0;
76}
77
78/**
79 * dpni_open() - Open a control session for the specified object
80 * @mc_io:	Pointer to MC portal's I/O object
81 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
82 * @dpni_id:	DPNI unique ID
83 * @token:	Returned token; use in subsequent API calls
84 *
85 * This function can be used to open a control session for an
86 * already created object; an object may have been declared in
87 * the DPL or by calling the dpni_create() function.
88 * This function returns a unique authentication token,
89 * associated with the specific object ID and the specific MC
90 * portal; this token must be used in all subsequent commands for
91 * this specific object.
92 *
93 * Return:	'0' on Success; Error code otherwise.
94 */
95int dpni_open(struct fsl_mc_io *mc_io,
96	      u32 cmd_flags,
97	      int dpni_id,
98	      u16 *token)
99{
100	struct fsl_mc_command cmd = { 0 };
101	struct dpni_cmd_open *cmd_params;
102
103	int err;
104
105	/* prepare command */
106	cmd.header = mc_encode_cmd_header(DPNI_CMDID_OPEN,
107					  cmd_flags,
108					  0);
109	cmd_params = (struct dpni_cmd_open *)cmd.params;
110	cmd_params->dpni_id = cpu_to_le32(dpni_id);
111
112	/* send command to mc*/
113	err = mc_send_command(mc_io, &cmd);
114	if (err)
115		return err;
116
117	/* retrieve response parameters */
118	*token = mc_cmd_hdr_read_token(&cmd);
119
120	return 0;
121}
122
123/**
124 * dpni_close() - Close the control session of the object
125 * @mc_io:	Pointer to MC portal's I/O object
126 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
127 * @token:	Token of DPNI object
128 *
129 * After this function is called, no further operations are
130 * allowed on the object without opening a new control session.
131 *
132 * Return:	'0' on Success; Error code otherwise.
133 */
134int dpni_close(struct fsl_mc_io *mc_io,
135	       u32 cmd_flags,
136	       u16 token)
137{
138	struct fsl_mc_command cmd = { 0 };
139
140	/* prepare command */
141	cmd.header = mc_encode_cmd_header(DPNI_CMDID_CLOSE,
142					  cmd_flags,
143					  token);
144
145	/* send command to mc*/
146	return mc_send_command(mc_io, &cmd);
147}
148
149/**
150 * dpni_set_pools() - Set buffer pools configuration
151 * @mc_io:	Pointer to MC portal's I/O object
152 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
153 * @token:	Token of DPNI object
154 * @cfg:	Buffer pools configuration
155 *
156 * mandatory for DPNI operation
157 * warning:Allowed only when DPNI is disabled
158 *
159 * Return:	'0' on Success; Error code otherwise.
160 */
161int dpni_set_pools(struct fsl_mc_io *mc_io,
162		   u32 cmd_flags,
163		   u16 token,
164		   const struct dpni_pools_cfg *cfg)
165{
166	struct fsl_mc_command cmd = { 0 };
167	struct dpni_cmd_set_pools *cmd_params;
168	int i;
169
170	/* prepare command */
171	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_POOLS,
172					  cmd_flags,
173					  token);
174	cmd_params = (struct dpni_cmd_set_pools *)cmd.params;
175	cmd_params->num_dpbp = cfg->num_dpbp;
176	cmd_params->pool_options = cfg->pool_options;
177	for (i = 0; i < DPNI_MAX_DPBP; i++) {
178		cmd_params->pool[i].dpbp_id =
179			cpu_to_le16(cfg->pools[i].dpbp_id);
180		cmd_params->pool[i].priority_mask =
181			cfg->pools[i].priority_mask;
182		cmd_params->buffer_size[i] =
183			cpu_to_le16(cfg->pools[i].buffer_size);
184		cmd_params->backup_pool_mask |=
185			DPNI_BACKUP_POOL(cfg->pools[i].backup_pool, i);
186	}
187
188	/* send command to mc*/
189	return mc_send_command(mc_io, &cmd);
190}
191
192/**
193 * dpni_enable() - Enable the DPNI, allow sending and receiving frames.
194 * @mc_io:	Pointer to MC portal's I/O object
195 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
196 * @token:		Token of DPNI object
197 *
198 * Return:	'0' on Success; Error code otherwise.
199 */
200int dpni_enable(struct fsl_mc_io *mc_io,
201		u32 cmd_flags,
202		u16 token)
203{
204	struct fsl_mc_command cmd = { 0 };
205
206	/* prepare command */
207	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ENABLE,
208					  cmd_flags,
209					  token);
210
211	/* send command to mc*/
212	return mc_send_command(mc_io, &cmd);
213}
214
215/**
216 * dpni_disable() - Disable the DPNI, stop sending and receiving frames.
217 * @mc_io:	Pointer to MC portal's I/O object
218 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
219 * @token:	Token of DPNI object
220 *
221 * Return:	'0' on Success; Error code otherwise.
222 */
223int dpni_disable(struct fsl_mc_io *mc_io,
224		 u32 cmd_flags,
225		 u16 token)
226{
227	struct fsl_mc_command cmd = { 0 };
228
229	/* prepare command */
230	cmd.header = mc_encode_cmd_header(DPNI_CMDID_DISABLE,
231					  cmd_flags,
232					  token);
233
234	/* send command to mc*/
235	return mc_send_command(mc_io, &cmd);
236}
237
238/**
239 * dpni_is_enabled() - Check if the DPNI is enabled.
240 * @mc_io:	Pointer to MC portal's I/O object
241 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
242 * @token:	Token of DPNI object
243 * @en:		Returns '1' if object is enabled; '0' otherwise
244 *
245 * Return:	'0' on Success; Error code otherwise.
246 */
247int dpni_is_enabled(struct fsl_mc_io *mc_io,
248		    u32 cmd_flags,
249		    u16 token,
250		    int *en)
251{
252	struct fsl_mc_command cmd = { 0 };
253	struct dpni_rsp_is_enabled *rsp_params;
254	int err;
255
256	/* prepare command */
257	cmd.header = mc_encode_cmd_header(DPNI_CMDID_IS_ENABLED,
258					  cmd_flags,
259					  token);
260
261	/* send command to mc*/
262	err = mc_send_command(mc_io, &cmd);
263	if (err)
264		return err;
265
266	/* retrieve response parameters */
267	rsp_params = (struct dpni_rsp_is_enabled *)cmd.params;
268	*en = dpni_get_field(rsp_params->enabled, ENABLE);
269
270	return 0;
271}
272
273/**
274 * dpni_reset() - Reset the DPNI, returns the object to initial state.
275 * @mc_io:	Pointer to MC portal's I/O object
276 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
277 * @token:	Token of DPNI object
278 *
279 * Return:	'0' on Success; Error code otherwise.
280 */
281int dpni_reset(struct fsl_mc_io *mc_io,
282	       u32 cmd_flags,
283	       u16 token)
284{
285	struct fsl_mc_command cmd = { 0 };
286
287	/* prepare command */
288	cmd.header = mc_encode_cmd_header(DPNI_CMDID_RESET,
289					  cmd_flags,
290					  token);
291
292	/* send command to mc*/
293	return mc_send_command(mc_io, &cmd);
294}
295
296/**
297 * dpni_set_irq_enable() - Set overall interrupt state.
298 * @mc_io:	Pointer to MC portal's I/O object
299 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
300 * @token:	Token of DPNI object
301 * @irq_index:	The interrupt index to configure
302 * @en:		Interrupt state: - enable = 1, disable = 0
303 *
304 * Allows GPP software to control when interrupts are generated.
305 * Each interrupt can have up to 32 causes.  The enable/disable control's the
306 * overall interrupt state. if the interrupt is disabled no causes will cause
307 * an interrupt.
308 *
309 * Return:	'0' on Success; Error code otherwise.
310 */
311int dpni_set_irq_enable(struct fsl_mc_io *mc_io,
312			u32 cmd_flags,
313			u16 token,
314			u8 irq_index,
315			u8 en)
316{
317	struct fsl_mc_command cmd = { 0 };
318	struct dpni_cmd_set_irq_enable *cmd_params;
319
320	/* prepare command */
321	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_IRQ_ENABLE,
322					  cmd_flags,
323					  token);
324	cmd_params = (struct dpni_cmd_set_irq_enable *)cmd.params;
325	dpni_set_field(cmd_params->enable, ENABLE, en);
326	cmd_params->irq_index = irq_index;
327
328	/* send command to mc*/
329	return mc_send_command(mc_io, &cmd);
330}
331
332/**
333 * dpni_get_irq_enable() - Get overall interrupt state
334 * @mc_io:	Pointer to MC portal's I/O object
335 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
336 * @token:	Token of DPNI object
337 * @irq_index:	The interrupt index to configure
338 * @en:		Returned interrupt state - enable = 1, disable = 0
339 *
340 * Return:	'0' on Success; Error code otherwise.
341 */
342int dpni_get_irq_enable(struct fsl_mc_io *mc_io,
343			u32 cmd_flags,
344			u16 token,
345			u8 irq_index,
346			u8 *en)
347{
348	struct fsl_mc_command cmd = { 0 };
349	struct dpni_cmd_get_irq_enable *cmd_params;
350	struct dpni_rsp_get_irq_enable *rsp_params;
351
352	int err;
353
354	/* prepare command */
355	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_IRQ_ENABLE,
356					  cmd_flags,
357					  token);
358	cmd_params = (struct dpni_cmd_get_irq_enable *)cmd.params;
359	cmd_params->irq_index = irq_index;
360
361	/* send command to mc*/
362	err = mc_send_command(mc_io, &cmd);
363	if (err)
364		return err;
365
366	/* retrieve response parameters */
367	rsp_params = (struct dpni_rsp_get_irq_enable *)cmd.params;
368	*en = dpni_get_field(rsp_params->enabled, ENABLE);
369
370	return 0;
371}
372
373/**
374 * dpni_set_irq_mask() - Set interrupt mask.
375 * @mc_io:	Pointer to MC portal's I/O object
376 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
377 * @token:	Token of DPNI object
378 * @irq_index:	The interrupt index to configure
379 * @mask:	event mask to trigger interrupt;
380 *			each bit:
381 *				0 = ignore event
382 *				1 = consider event for asserting IRQ
383 *
384 * Every interrupt can have up to 32 causes and the interrupt model supports
385 * masking/unmasking each cause independently
386 *
387 * Return:	'0' on Success; Error code otherwise.
388 */
389int dpni_set_irq_mask(struct fsl_mc_io *mc_io,
390		      u32 cmd_flags,
391		      u16 token,
392		      u8 irq_index,
393		      u32 mask)
394{
395	struct fsl_mc_command cmd = { 0 };
396	struct dpni_cmd_set_irq_mask *cmd_params;
397
398	/* prepare command */
399	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_IRQ_MASK,
400					  cmd_flags,
401					  token);
402	cmd_params = (struct dpni_cmd_set_irq_mask *)cmd.params;
403	cmd_params->mask = cpu_to_le32(mask);
404	cmd_params->irq_index = irq_index;
405
406	/* send command to mc*/
407	return mc_send_command(mc_io, &cmd);
408}
409
410/**
411 * dpni_get_irq_mask() - Get interrupt mask.
412 * @mc_io:	Pointer to MC portal's I/O object
413 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
414 * @token:	Token of DPNI object
415 * @irq_index:	The interrupt index to configure
416 * @mask:	Returned event mask to trigger interrupt
417 *
418 * Every interrupt can have up to 32 causes and the interrupt model supports
419 * masking/unmasking each cause independently
420 *
421 * Return:	'0' on Success; Error code otherwise.
422 */
423int dpni_get_irq_mask(struct fsl_mc_io *mc_io,
424		      u32 cmd_flags,
425		      u16 token,
426		      u8 irq_index,
427		      u32 *mask)
428{
429	struct fsl_mc_command cmd = { 0 };
430	struct dpni_cmd_get_irq_mask *cmd_params;
431	struct dpni_rsp_get_irq_mask *rsp_params;
432	int err;
433
434	/* prepare command */
435	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_IRQ_MASK,
436					  cmd_flags,
437					  token);
438	cmd_params = (struct dpni_cmd_get_irq_mask *)cmd.params;
439	cmd_params->irq_index = irq_index;
440
441	/* send command to mc*/
442	err = mc_send_command(mc_io, &cmd);
443	if (err)
444		return err;
445
446	/* retrieve response parameters */
447	rsp_params = (struct dpni_rsp_get_irq_mask *)cmd.params;
448	*mask = le32_to_cpu(rsp_params->mask);
449
450	return 0;
451}
452
453/**
454 * dpni_get_irq_status() - Get the current status of any pending interrupts.
455 * @mc_io:	Pointer to MC portal's I/O object
456 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
457 * @token:	Token of DPNI object
458 * @irq_index:	The interrupt index to configure
459 * @status:	Returned interrupts status - one bit per cause:
460 *			0 = no interrupt pending
461 *			1 = interrupt pending
462 *
463 * Return:	'0' on Success; Error code otherwise.
464 */
465int dpni_get_irq_status(struct fsl_mc_io *mc_io,
466			u32 cmd_flags,
467			u16 token,
468			u8 irq_index,
469			u32 *status)
470{
471	struct fsl_mc_command cmd = { 0 };
472	struct dpni_cmd_get_irq_status *cmd_params;
473	struct dpni_rsp_get_irq_status *rsp_params;
474	int err;
475
476	/* prepare command */
477	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_IRQ_STATUS,
478					  cmd_flags,
479					  token);
480	cmd_params = (struct dpni_cmd_get_irq_status *)cmd.params;
481	cmd_params->status = cpu_to_le32(*status);
482	cmd_params->irq_index = irq_index;
483
484	/* send command to mc*/
485	err = mc_send_command(mc_io, &cmd);
486	if (err)
487		return err;
488
489	/* retrieve response parameters */
490	rsp_params = (struct dpni_rsp_get_irq_status *)cmd.params;
491	*status = le32_to_cpu(rsp_params->status);
492
493	return 0;
494}
495
496/**
497 * dpni_clear_irq_status() - Clear a pending interrupt's status
498 * @mc_io:	Pointer to MC portal's I/O object
499 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
500 * @token:	Token of DPNI object
501 * @irq_index:	The interrupt index to configure
502 * @status:	bits to clear (W1C) - one bit per cause:
503 *			0 = don't change
504 *			1 = clear status bit
505 *
506 * Return:	'0' on Success; Error code otherwise.
507 */
508int dpni_clear_irq_status(struct fsl_mc_io *mc_io,
509			  u32 cmd_flags,
510			  u16 token,
511			  u8 irq_index,
512			  u32 status)
513{
514	struct fsl_mc_command cmd = { 0 };
515	struct dpni_cmd_clear_irq_status *cmd_params;
516
517	/* prepare command */
518	cmd.header = mc_encode_cmd_header(DPNI_CMDID_CLEAR_IRQ_STATUS,
519					  cmd_flags,
520					  token);
521	cmd_params = (struct dpni_cmd_clear_irq_status *)cmd.params;
522	cmd_params->irq_index = irq_index;
523	cmd_params->status = cpu_to_le32(status);
524
525	/* send command to mc*/
526	return mc_send_command(mc_io, &cmd);
527}
528
529/**
530 * dpni_get_attributes() - Retrieve DPNI attributes.
531 * @mc_io:	Pointer to MC portal's I/O object
532 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
533 * @token:	Token of DPNI object
534 * @attr:	Object's attributes
535 *
536 * Return:	'0' on Success; Error code otherwise.
537 */
538int dpni_get_attributes(struct fsl_mc_io *mc_io,
539			u32 cmd_flags,
540			u16 token,
541			struct dpni_attr *attr)
542{
543	struct fsl_mc_command cmd = { 0 };
544	struct dpni_rsp_get_attr *rsp_params;
545
546	int err;
547
548	/* prepare command */
549	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_ATTR,
550					  cmd_flags,
551					  token);
552
553	/* send command to mc*/
554	err = mc_send_command(mc_io, &cmd);
555	if (err)
556		return err;
557
558	/* retrieve response parameters */
559	rsp_params = (struct dpni_rsp_get_attr *)cmd.params;
560	attr->options = le32_to_cpu(rsp_params->options);
561	attr->num_queues = rsp_params->num_queues;
562	attr->num_tcs = rsp_params->num_tcs;
563	attr->mac_filter_entries = rsp_params->mac_filter_entries;
564	attr->vlan_filter_entries = rsp_params->vlan_filter_entries;
565	attr->qos_entries = rsp_params->qos_entries;
566	attr->fs_entries = le16_to_cpu(rsp_params->fs_entries);
567	attr->qos_key_size = rsp_params->qos_key_size;
568	attr->fs_key_size = rsp_params->fs_key_size;
569	attr->wriop_version = le16_to_cpu(rsp_params->wriop_version);
570
571	return 0;
572}
573
574/**
575 * dpni_set_errors_behavior() - Set errors behavior
576 * @mc_io:	Pointer to MC portal's I/O object
577 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
578 * @token:	Token of DPNI object
579 * @cfg:	Errors configuration
580 *
581 * this function may be called numerous times with different
582 * error masks
583 *
584 * Return:	'0' on Success; Error code otherwise.
585 */
586int dpni_set_errors_behavior(struct fsl_mc_io *mc_io,
587			     u32 cmd_flags,
588			     u16 token,
589			     struct dpni_error_cfg *cfg)
590{
591	struct fsl_mc_command cmd = { 0 };
592	struct dpni_cmd_set_errors_behavior *cmd_params;
593
594	/* prepare command */
595	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_ERRORS_BEHAVIOR,
596					  cmd_flags,
597					  token);
598	cmd_params = (struct dpni_cmd_set_errors_behavior *)cmd.params;
599	cmd_params->errors = cpu_to_le32(cfg->errors);
600	dpni_set_field(cmd_params->flags, ERROR_ACTION, cfg->error_action);
601	dpni_set_field(cmd_params->flags, FRAME_ANN, cfg->set_frame_annotation);
602
603	/* send command to mc*/
604	return mc_send_command(mc_io, &cmd);
605}
606
607/**
608 * dpni_get_buffer_layout() - Retrieve buffer layout attributes.
609 * @mc_io:	Pointer to MC portal's I/O object
610 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
611 * @token:	Token of DPNI object
612 * @qtype:	Type of queue to retrieve configuration for
613 * @layout:	Returns buffer layout attributes
614 *
615 * Return:	'0' on Success; Error code otherwise.
616 */
617int dpni_get_buffer_layout(struct fsl_mc_io *mc_io,
618			   u32 cmd_flags,
619			   u16 token,
620			   enum dpni_queue_type qtype,
621			   struct dpni_buffer_layout *layout)
622{
623	struct fsl_mc_command cmd = { 0 };
624	struct dpni_cmd_get_buffer_layout *cmd_params;
625	struct dpni_rsp_get_buffer_layout *rsp_params;
626	int err;
627
628	/* prepare command */
629	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_BUFFER_LAYOUT,
630					  cmd_flags,
631					  token);
632	cmd_params = (struct dpni_cmd_get_buffer_layout *)cmd.params;
633	cmd_params->qtype = qtype;
634
635	/* send command to mc*/
636	err = mc_send_command(mc_io, &cmd);
637	if (err)
638		return err;
639
640	/* retrieve response parameters */
641	rsp_params = (struct dpni_rsp_get_buffer_layout *)cmd.params;
642	layout->pass_timestamp = dpni_get_field(rsp_params->flags, PASS_TS);
643	layout->pass_parser_result = dpni_get_field(rsp_params->flags, PASS_PR);
644	layout->pass_frame_status = dpni_get_field(rsp_params->flags, PASS_FS);
645	layout->private_data_size = le16_to_cpu(rsp_params->private_data_size);
646	layout->data_align = le16_to_cpu(rsp_params->data_align);
647	layout->data_head_room = le16_to_cpu(rsp_params->head_room);
648	layout->data_tail_room = le16_to_cpu(rsp_params->tail_room);
649
650	return 0;
651}
652
653/**
654 * dpni_set_buffer_layout() - Set buffer layout configuration.
655 * @mc_io:	Pointer to MC portal's I/O object
656 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
657 * @token:	Token of DPNI object
658 * @qtype:	Type of queue this configuration applies to
659 * @layout:	Buffer layout configuration
660 *
661 * Return:	'0' on Success; Error code otherwise.
662 *
663 * @warning	Allowed only when DPNI is disabled
664 */
665int dpni_set_buffer_layout(struct fsl_mc_io *mc_io,
666			   u32 cmd_flags,
667			   u16 token,
668			   enum dpni_queue_type qtype,
669			   const struct dpni_buffer_layout *layout)
670{
671	struct fsl_mc_command cmd = { 0 };
672	struct dpni_cmd_set_buffer_layout *cmd_params;
673
674	/* prepare command */
675	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_BUFFER_LAYOUT,
676					  cmd_flags,
677					  token);
678	cmd_params = (struct dpni_cmd_set_buffer_layout *)cmd.params;
679	cmd_params->qtype = qtype;
680	cmd_params->options = cpu_to_le16(layout->options);
681	dpni_set_field(cmd_params->flags, PASS_TS, layout->pass_timestamp);
682	dpni_set_field(cmd_params->flags, PASS_PR, layout->pass_parser_result);
683	dpni_set_field(cmd_params->flags, PASS_FS, layout->pass_frame_status);
684	cmd_params->private_data_size = cpu_to_le16(layout->private_data_size);
685	cmd_params->data_align = cpu_to_le16(layout->data_align);
686	cmd_params->head_room = cpu_to_le16(layout->data_head_room);
687	cmd_params->tail_room = cpu_to_le16(layout->data_tail_room);
688
689	/* send command to mc*/
690	return mc_send_command(mc_io, &cmd);
691}
692
693/**
694 * dpni_set_offload() - Set DPNI offload configuration.
695 * @mc_io:	Pointer to MC portal's I/O object
696 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
697 * @token:	Token of DPNI object
698 * @type:	Type of DPNI offload
699 * @config:	Offload configuration.
700 *		For checksum offloads, non-zero value enables the offload
701 *
702 * Return:     '0' on Success; Error code otherwise.
703 *
704 * @warning    Allowed only when DPNI is disabled
705 */
706
707int dpni_set_offload(struct fsl_mc_io *mc_io,
708		     u32 cmd_flags,
709		     u16 token,
710		     enum dpni_offload type,
711		     u32 config)
712{
713	struct fsl_mc_command cmd = { 0 };
714	struct dpni_cmd_set_offload *cmd_params;
715
716	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_OFFLOAD,
717					  cmd_flags,
718					  token);
719	cmd_params = (struct dpni_cmd_set_offload *)cmd.params;
720	cmd_params->dpni_offload = type;
721	cmd_params->config = cpu_to_le32(config);
722
723	return mc_send_command(mc_io, &cmd);
724}
725
726int dpni_get_offload(struct fsl_mc_io *mc_io,
727		     u32 cmd_flags,
728		     u16 token,
729		     enum dpni_offload type,
730		     u32 *config)
731{
732	struct fsl_mc_command cmd = { 0 };
733	struct dpni_cmd_get_offload *cmd_params;
734	struct dpni_rsp_get_offload *rsp_params;
735	int err;
736
737	/* prepare command */
738	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_OFFLOAD,
739					  cmd_flags,
740					  token);
741	cmd_params = (struct dpni_cmd_get_offload *)cmd.params;
742	cmd_params->dpni_offload = type;
743
744	/* send command to mc*/
745	err = mc_send_command(mc_io, &cmd);
746	if (err)
747		return err;
748
749	/* retrieve response parameters */
750	rsp_params = (struct dpni_rsp_get_offload *)cmd.params;
751	*config = le32_to_cpu(rsp_params->config);
752
753	return 0;
754}
755
756/**
757 * dpni_get_qdid() - Get the Queuing Destination ID (QDID) that should be used
758 *			for enqueue operations
759 * @mc_io:	Pointer to MC portal's I/O object
760 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
761 * @token:	Token of DPNI object
762 * @qtype:	Type of queue to receive QDID for
763 * @qdid:	Returned virtual QDID value that should be used as an argument
764 *			in all enqueue operations
765 *
766 * Return:	'0' on Success; Error code otherwise.
767 */
768int dpni_get_qdid(struct fsl_mc_io *mc_io,
769		  u32 cmd_flags,
770		  u16 token,
771		  enum dpni_queue_type qtype,
772		  u16 *qdid)
773{
774	struct fsl_mc_command cmd = { 0 };
775	struct dpni_cmd_get_qdid *cmd_params;
776	struct dpni_rsp_get_qdid *rsp_params;
777	int err;
778
779	/* prepare command */
780	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_QDID,
781					  cmd_flags,
782					  token);
783	cmd_params = (struct dpni_cmd_get_qdid *)cmd.params;
784	cmd_params->qtype = qtype;
785
786	/* send command to mc*/
787	err = mc_send_command(mc_io, &cmd);
788	if (err)
789		return err;
790
791	/* retrieve response parameters */
792	rsp_params = (struct dpni_rsp_get_qdid *)cmd.params;
793	*qdid = le16_to_cpu(rsp_params->qdid);
794
795	return 0;
796}
797
798/**
799 * dpni_get_tx_data_offset() - Get the Tx data offset (from start of buffer)
800 * @mc_io:	Pointer to MC portal's I/O object
801 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
802 * @token:	Token of DPNI object
803 * @data_offset: Tx data offset (from start of buffer)
804 *
805 * Return:	'0' on Success; Error code otherwise.
806 */
807int dpni_get_tx_data_offset(struct fsl_mc_io *mc_io,
808			    u32 cmd_flags,
809			    u16 token,
810			    u16 *data_offset)
811{
812	struct fsl_mc_command cmd = { 0 };
813	struct dpni_rsp_get_tx_data_offset *rsp_params;
814	int err;
815
816	/* prepare command */
817	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_TX_DATA_OFFSET,
818					  cmd_flags,
819					  token);
820
821	/* send command to mc*/
822	err = mc_send_command(mc_io, &cmd);
823	if (err)
824		return err;
825
826	/* retrieve response parameters */
827	rsp_params = (struct dpni_rsp_get_tx_data_offset *)cmd.params;
828	*data_offset = le16_to_cpu(rsp_params->data_offset);
829
830	return 0;
831}
832
833/**
834 * dpni_set_link_cfg() - set the link configuration.
835 * @mc_io:	Pointer to MC portal's I/O object
836 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
837 * @token:	Token of DPNI object
838 * @cfg:	Link configuration
839 *
840 * Return:	'0' on Success; Error code otherwise.
841 */
842int dpni_set_link_cfg(struct fsl_mc_io *mc_io,
843		      u32 cmd_flags,
844		      u16 token,
845		      const struct dpni_link_cfg *cfg)
846{
847	struct fsl_mc_command cmd = { 0 };
848	struct dpni_cmd_link_cfg *cmd_params;
849
850	/* prepare command */
851	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_LINK_CFG,
852					  cmd_flags,
853					  token);
854	cmd_params = (struct dpni_cmd_link_cfg *)cmd.params;
855	cmd_params->rate = cpu_to_le32(cfg->rate);
856	cmd_params->options = cpu_to_le64(cfg->options);
857
858	/* send command to mc*/
859	return mc_send_command(mc_io, &cmd);
860}
861
862/**
863 * dpni_get_link_cfg() - return the link configuration
864 * @mc_io:	Pointer to MC portal's I/O object
865 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
866 * @token:	Token of DPNI object
867 * @cfg:	Link configuration from dpni object
868 *
869 * Return:	'0' on Success; Error code otherwise.
870 */
871int dpni_get_link_cfg(struct fsl_mc_io *mc_io,
872		      u32 cmd_flags,
873		      u16 token,
874		      struct dpni_link_cfg *cfg)
875{
876	struct fsl_mc_command cmd = { 0 };
877	struct dpni_cmd_link_cfg *rsp_params;
878	int err;
879
880	/* prepare command */
881	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_LINK_CFG,
882					  cmd_flags,
883					  token);
884
885	/* send command to mc*/
886	err = mc_send_command(mc_io, &cmd);
887	if (err)
888		return err;
889
890	/* retrieve response parameters */
891	rsp_params = (struct dpni_cmd_link_cfg *)cmd.params;
892	cfg->rate = le32_to_cpu(rsp_params->rate);
893	cfg->options = le64_to_cpu(rsp_params->options);
894
895	return err;
896}
897
898/**
899 * dpni_get_link_state() - Return the link state (either up or down)
900 * @mc_io:	Pointer to MC portal's I/O object
901 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
902 * @token:	Token of DPNI object
903 * @state:	Returned link state;
904 *
905 * Return:	'0' on Success; Error code otherwise.
906 */
907int dpni_get_link_state(struct fsl_mc_io *mc_io,
908			u32 cmd_flags,
909			u16 token,
910			struct dpni_link_state *state)
911{
912	struct fsl_mc_command cmd = { 0 };
913	struct dpni_rsp_get_link_state *rsp_params;
914	int err;
915
916	/* prepare command */
917	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_LINK_STATE,
918					  cmd_flags,
919					  token);
920
921	/* send command to mc*/
922	err = mc_send_command(mc_io, &cmd);
923	if (err)
924		return err;
925
926	/* retrieve response parameters */
927	rsp_params = (struct dpni_rsp_get_link_state *)cmd.params;
928	state->up = dpni_get_field(rsp_params->flags, LINK_STATE);
929	state->rate = le32_to_cpu(rsp_params->rate);
930	state->options = le64_to_cpu(rsp_params->options);
931
932	return 0;
933}
934
935/**
936 * dpni_set_max_frame_length() - Set the maximum received frame length.
937 * @mc_io:	Pointer to MC portal's I/O object
938 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
939 * @token:	Token of DPNI object
940 * @max_frame_length:	Maximum received frame length (in
941 *				bytes); frame is discarded if its
942 *				length exceeds this value
943 *
944 * Return:	'0' on Success; Error code otherwise.
945 */
946int dpni_set_max_frame_length(struct fsl_mc_io *mc_io,
947			      u32 cmd_flags,
948			      u16 token,
949			      u16 max_frame_length)
950{
951	struct fsl_mc_command cmd = { 0 };
952	struct dpni_cmd_set_max_frame_length *cmd_params;
953
954	/* prepare command */
955	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_MAX_FRAME_LENGTH,
956					  cmd_flags,
957					  token);
958	cmd_params = (struct dpni_cmd_set_max_frame_length *)cmd.params;
959	cmd_params->max_frame_length = cpu_to_le16(max_frame_length);
960
961	/* send command to mc*/
962	return mc_send_command(mc_io, &cmd);
963}
964
965/**
966 * dpni_get_max_frame_length() - Get the maximum received frame length.
967 * @mc_io:	Pointer to MC portal's I/O object
968 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
969 * @token:	Token of DPNI object
970 * @max_frame_length:	Maximum received frame length (in
971 *				bytes); frame is discarded if its
972 *				length exceeds this value
973 *
974 * Return:	'0' on Success; Error code otherwise.
975 */
976int dpni_get_max_frame_length(struct fsl_mc_io *mc_io,
977			      u32 cmd_flags,
978			      u16 token,
979			      u16 *max_frame_length)
980{
981	struct fsl_mc_command cmd = { 0 };
982	struct dpni_rsp_get_max_frame_length *rsp_params;
983	int err;
984
985	/* prepare command */
986	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_MAX_FRAME_LENGTH,
987					  cmd_flags,
988					  token);
989
990	/* send command to mc*/
991	err = mc_send_command(mc_io, &cmd);
992	if (err)
993		return err;
994
995	/* retrieve response parameters */
996	rsp_params = (struct dpni_rsp_get_max_frame_length *)cmd.params;
997	*max_frame_length = le16_to_cpu(rsp_params->max_frame_length);
998
999	return 0;
1000}
1001
1002/**
1003 * dpni_set_multicast_promisc() - Enable/disable multicast promiscuous mode
1004 * @mc_io:	Pointer to MC portal's I/O object
1005 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1006 * @token:	Token of DPNI object
1007 * @en:		Set to '1' to enable; '0' to disable
1008 *
1009 * Return:	'0' on Success; Error code otherwise.
1010 */
1011int dpni_set_multicast_promisc(struct fsl_mc_io *mc_io,
1012			       u32 cmd_flags,
1013			       u16 token,
1014			       int en)
1015{
1016	struct fsl_mc_command cmd = { 0 };
1017	struct dpni_cmd_set_multicast_promisc *cmd_params;
1018
1019	/* prepare command */
1020	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_MCAST_PROMISC,
1021					  cmd_flags,
1022					  token);
1023	cmd_params = (struct dpni_cmd_set_multicast_promisc *)cmd.params;
1024	dpni_set_field(cmd_params->enable, ENABLE, en);
1025
1026	/* send command to mc*/
1027	return mc_send_command(mc_io, &cmd);
1028}
1029
1030/**
1031 * dpni_get_multicast_promisc() - Get multicast promiscuous mode
1032 * @mc_io:	Pointer to MC portal's I/O object
1033 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1034 * @token:	Token of DPNI object
1035 * @en:		Returns '1' if enabled; '0' otherwise
1036 *
1037 * Return:	'0' on Success; Error code otherwise.
1038 */
1039int dpni_get_multicast_promisc(struct fsl_mc_io *mc_io,
1040			       u32 cmd_flags,
1041			       u16 token,
1042			       int *en)
1043{
1044	struct fsl_mc_command cmd = { 0 };
1045	struct dpni_rsp_get_multicast_promisc *rsp_params;
1046	int err;
1047
1048	/* prepare command */
1049	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_MCAST_PROMISC,
1050					  cmd_flags,
1051					  token);
1052
1053	/* send command to mc*/
1054	err = mc_send_command(mc_io, &cmd);
1055	if (err)
1056		return err;
1057
1058	/* retrieve response parameters */
1059	rsp_params = (struct dpni_rsp_get_multicast_promisc *)cmd.params;
1060	*en = dpni_get_field(rsp_params->enabled, ENABLE);
1061
1062	return 0;
1063}
1064
1065/**
1066 * dpni_set_unicast_promisc() - Enable/disable unicast promiscuous mode
1067 * @mc_io:	Pointer to MC portal's I/O object
1068 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1069 * @token:	Token of DPNI object
1070 * @en:		Set to '1' to enable; '0' to disable
1071 *
1072 * Return:	'0' on Success; Error code otherwise.
1073 */
1074int dpni_set_unicast_promisc(struct fsl_mc_io *mc_io,
1075			     u32 cmd_flags,
1076			     u16 token,
1077			     int en)
1078{
1079	struct fsl_mc_command cmd = { 0 };
1080	struct dpni_cmd_set_unicast_promisc *cmd_params;
1081
1082	/* prepare command */
1083	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_UNICAST_PROMISC,
1084					  cmd_flags,
1085					  token);
1086	cmd_params = (struct dpni_cmd_set_unicast_promisc *)cmd.params;
1087	dpni_set_field(cmd_params->enable, ENABLE, en);
1088
1089	/* send command to mc*/
1090	return mc_send_command(mc_io, &cmd);
1091}
1092
1093/**
1094 * dpni_get_unicast_promisc() - Get unicast promiscuous mode
1095 * @mc_io:	Pointer to MC portal's I/O object
1096 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1097 * @token:	Token of DPNI object
1098 * @en:		Returns '1' if enabled; '0' otherwise
1099 *
1100 * Return:	'0' on Success; Error code otherwise.
1101 */
1102int dpni_get_unicast_promisc(struct fsl_mc_io *mc_io,
1103			     u32 cmd_flags,
1104			     u16 token,
1105			     int *en)
1106{
1107	struct fsl_mc_command cmd = { 0 };
1108	struct dpni_rsp_get_unicast_promisc *rsp_params;
1109	int err;
1110
1111	/* prepare command */
1112	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_UNICAST_PROMISC,
1113					  cmd_flags,
1114					  token);
1115
1116	/* send command to mc*/
1117	err = mc_send_command(mc_io, &cmd);
1118	if (err)
1119		return err;
1120
1121	/* retrieve response parameters */
1122	rsp_params = (struct dpni_rsp_get_unicast_promisc *)cmd.params;
1123	*en = dpni_get_field(rsp_params->enabled, ENABLE);
1124
1125	return 0;
1126}
1127
1128/**
1129 * dpni_set_primary_mac_addr() - Set the primary MAC address
1130 * @mc_io:	Pointer to MC portal's I/O object
1131 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1132 * @token:	Token of DPNI object
1133 * @mac_addr:	MAC address to set as primary address
1134 *
1135 * Return:	'0' on Success; Error code otherwise.
1136 */
1137int dpni_set_primary_mac_addr(struct fsl_mc_io *mc_io,
1138			      u32 cmd_flags,
1139			      u16 token,
1140			      const u8 mac_addr[6])
1141{
1142	struct fsl_mc_command cmd = { 0 };
1143	struct dpni_cmd_set_primary_mac_addr *cmd_params;
1144	int i;
1145
1146	/* prepare command */
1147	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_PRIM_MAC,
1148					  cmd_flags,
1149					  token);
1150	cmd_params = (struct dpni_cmd_set_primary_mac_addr *)cmd.params;
1151	for (i = 0; i < 6; i++)
1152		cmd_params->mac_addr[i] = mac_addr[5 - i];
1153
1154	/* send command to mc*/
1155	return mc_send_command(mc_io, &cmd);
1156}
1157
1158/**
1159 * dpni_get_primary_mac_addr() - Get the primary MAC address
1160 * @mc_io:	Pointer to MC portal's I/O object
1161 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1162 * @token:	Token of DPNI object
1163 * @mac_addr:	Returned MAC address
1164 *
1165 * Return:	'0' on Success; Error code otherwise.
1166 */
1167int dpni_get_primary_mac_addr(struct fsl_mc_io *mc_io,
1168			      u32 cmd_flags,
1169			      u16 token,
1170			      u8 mac_addr[6])
1171{
1172	struct fsl_mc_command cmd = { 0 };
1173	struct dpni_rsp_get_primary_mac_addr *rsp_params;
1174	int i, err;
1175
1176	/* prepare command */
1177	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_PRIM_MAC,
1178					  cmd_flags,
1179					  token);
1180
1181	/* send command to mc*/
1182	err = mc_send_command(mc_io, &cmd);
1183	if (err)
1184		return err;
1185
1186	/* retrieve response parameters */
1187	rsp_params = (struct dpni_rsp_get_primary_mac_addr *)cmd.params;
1188	for (i = 0; i < 6; i++)
1189		mac_addr[5 - i] = rsp_params->mac_addr[i];
1190
1191	return 0;
1192}
1193
1194/**
1195 * dpni_get_port_mac_addr() - Retrieve MAC address associated to the physical
1196 *			port the DPNI is attached to
1197 * @mc_io:	Pointer to MC portal's I/O object
1198 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1199 * @token:	Token of DPNI object
1200 * @mac_addr:	MAC address of the physical port, if any, otherwise 0
1201 *
1202 * The primary MAC address is not cleared by this operation.
1203 *
1204 * Return:	'0' on Success; Error code otherwise.
1205 */
1206int dpni_get_port_mac_addr(struct fsl_mc_io *mc_io,
1207			   u32 cmd_flags,
1208			   u16 token,
1209			   u8 mac_addr[6])
1210{
1211	struct fsl_mc_command cmd = { 0 };
1212	struct dpni_rsp_get_port_mac_addr *rsp_params;
1213	int i, err;
1214
1215	/* prepare command */
1216	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_PORT_MAC_ADDR,
1217					  cmd_flags,
1218					  token);
1219
1220	/* send command to mc*/
1221	err = mc_send_command(mc_io, &cmd);
1222	if (err)
1223		return err;
1224
1225	/* retrieve response parameters */
1226	rsp_params = (struct dpni_rsp_get_port_mac_addr *)cmd.params;
1227	for (i = 0; i < 6; i++)
1228		mac_addr[5 - i] = rsp_params->mac_addr[i];
1229
1230	return 0;
1231}
1232
1233/**
1234 * dpni_enable_vlan_filter() - Enable/disable VLAN filtering mode
1235 * @mc_io:	Pointer to MC portal's I/O object
1236 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1237 * @token:	Token of DPNI object
1238 * @en:		Set to '1' to enable; '0' to disable
1239 *
1240 * Return:	'0' on Success; Error code otherwise.
1241 */
1242int dpni_enable_vlan_filter(struct fsl_mc_io *mc_io,
1243			    u32 cmd_flags,
1244			    u16 token,
1245			    u32 en)
1246{
1247	struct dpni_cmd_enable_vlan_filter *cmd_params;
1248	struct fsl_mc_command cmd = { 0 };
1249
1250	/* prepare command */
1251	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ENABLE_VLAN_FILTER,
1252					  cmd_flags,
1253					  token);
1254	cmd_params = (struct dpni_cmd_enable_vlan_filter *)cmd.params;
1255	dpni_set_field(cmd_params->en, ENABLE, en);
1256
1257	/* send command to mc*/
1258	return mc_send_command(mc_io, &cmd);
1259}
1260
1261/**
1262 * dpni_add_vlan_id() - Add VLAN ID filter
1263 * @mc_io:	Pointer to MC portal's I/O object
1264 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1265 * @token:	Token of DPNI object
1266 * @vlan_id:	VLAN ID to add
1267 * @flags:   0 - tc_id and flow_id will be ignored.
1268 * Pkt with this vlan_id will be passed to the next
1269 * classification stages
1270 * DPNI_VLAN_SET_QUEUE_ACTION
1271 * Pkt with this vlan_id will be forward directly to
1272 * queue defined by the tc_id and flow_id
1273 *
1274 * @tc_id: Traffic class selection (0-7)
1275 * @flow_id: Selects the specific queue out of the set allocated for the
1276 *           same as tc_id. Value must be in range 0 to NUM_QUEUES - 1
1277 *
1278 * Return:	'0' on Success; Error code otherwise.
1279 */
1280int dpni_add_vlan_id(struct fsl_mc_io *mc_io, u32 cmd_flags, u16 token,
1281		     u16 vlan_id, u8 flags, u8 tc_id, u8 flow_id)
1282{
1283	struct dpni_cmd_vlan_id *cmd_params;
1284	struct fsl_mc_command cmd = { 0 };
1285
1286	/* prepare command */
1287	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ADD_VLAN_ID,
1288					  cmd_flags,
1289					  token);
1290	cmd_params = (struct dpni_cmd_vlan_id *)cmd.params;
1291	cmd_params->flags = flags;
1292	cmd_params->tc_id = tc_id;
1293	cmd_params->flow_id =  flow_id;
1294	cmd_params->vlan_id = cpu_to_le16(vlan_id);
1295
1296	/* send command to mc*/
1297	return mc_send_command(mc_io, &cmd);
1298}
1299
1300/**
1301 * dpni_remove_vlan_id() - Remove VLAN ID filter
1302 * @mc_io:	Pointer to MC portal's I/O object
1303 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1304 * @token:	Token of DPNI object
1305 * @vlan_id:	VLAN ID to remove
1306 *
1307 * Return:	'0' on Success; Error code otherwise.
1308 */
1309int dpni_remove_vlan_id(struct fsl_mc_io *mc_io, u32 cmd_flags, u16 token,
1310			u16 vlan_id)
1311{
1312	struct dpni_cmd_vlan_id *cmd_params;
1313	struct fsl_mc_command cmd = { 0 };
1314
1315	/* prepare command */
1316	cmd.header = mc_encode_cmd_header(DPNI_CMDID_REMOVE_VLAN_ID,
1317					  cmd_flags,
1318					  token);
1319	cmd_params = (struct dpni_cmd_vlan_id *)cmd.params;
1320	cmd_params->vlan_id = cpu_to_le16(vlan_id);
1321
1322	/* send command to mc*/
1323	return mc_send_command(mc_io, &cmd);
1324}
1325
1326/**
1327 * dpni_add_mac_addr() - Add MAC address filter
1328 * @mc_io:	Pointer to MC portal's I/O object
1329 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1330 * @token:	Token of DPNI object
1331 * @mac_addr:	MAC address to add
1332 *
1333 * Return:	'0' on Success; Error code otherwise.
1334 */
1335int dpni_add_mac_addr(struct fsl_mc_io *mc_io,
1336		      u32 cmd_flags,
1337		      u16 token,
1338		      const u8 mac_addr[6])
1339{
1340	struct fsl_mc_command cmd = { 0 };
1341	struct dpni_cmd_add_mac_addr *cmd_params;
1342	int i;
1343
1344	/* prepare command */
1345	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ADD_MAC_ADDR,
1346					  cmd_flags,
1347					  token);
1348	cmd_params = (struct dpni_cmd_add_mac_addr *)cmd.params;
1349	for (i = 0; i < 6; i++)
1350		cmd_params->mac_addr[i] = mac_addr[5 - i];
1351
1352	/* send command to mc*/
1353	return mc_send_command(mc_io, &cmd);
1354}
1355
1356/**
1357 * dpni_remove_mac_addr() - Remove MAC address filter
1358 * @mc_io:	Pointer to MC portal's I/O object
1359 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1360 * @token:	Token of DPNI object
1361 * @mac_addr:	MAC address to remove
1362 *
1363 * Return:	'0' on Success; Error code otherwise.
1364 */
1365int dpni_remove_mac_addr(struct fsl_mc_io *mc_io,
1366			 u32 cmd_flags,
1367			 u16 token,
1368			 const u8 mac_addr[6])
1369{
1370	struct fsl_mc_command cmd = { 0 };
1371	struct dpni_cmd_remove_mac_addr *cmd_params;
1372	int i;
1373
1374	/* prepare command */
1375	cmd.header = mc_encode_cmd_header(DPNI_CMDID_REMOVE_MAC_ADDR,
1376					  cmd_flags,
1377					  token);
1378	cmd_params = (struct dpni_cmd_remove_mac_addr *)cmd.params;
1379	for (i = 0; i < 6; i++)
1380		cmd_params->mac_addr[i] = mac_addr[5 - i];
1381
1382	/* send command to mc*/
1383	return mc_send_command(mc_io, &cmd);
1384}
1385
1386/**
1387 * dpni_clear_mac_filters() - Clear all unicast and/or multicast MAC filters
1388 * @mc_io:	Pointer to MC portal's I/O object
1389 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1390 * @token:	Token of DPNI object
1391 * @unicast:	Set to '1' to clear unicast addresses
1392 * @multicast:	Set to '1' to clear multicast addresses
1393 *
1394 * The primary MAC address is not cleared by this operation.
1395 *
1396 * Return:	'0' on Success; Error code otherwise.
1397 */
1398int dpni_clear_mac_filters(struct fsl_mc_io *mc_io,
1399			   u32 cmd_flags,
1400			   u16 token,
1401			   int unicast,
1402			   int multicast)
1403{
1404	struct fsl_mc_command cmd = { 0 };
1405	struct dpni_cmd_clear_mac_filters *cmd_params;
1406
1407	/* prepare command */
1408	cmd.header = mc_encode_cmd_header(DPNI_CMDID_CLR_MAC_FILTERS,
1409					  cmd_flags,
1410					  token);
1411	cmd_params = (struct dpni_cmd_clear_mac_filters *)cmd.params;
1412	dpni_set_field(cmd_params->flags, UNICAST_FILTERS, unicast);
1413	dpni_set_field(cmd_params->flags, MULTICAST_FILTERS, multicast);
1414
1415	/* send command to mc*/
1416	return mc_send_command(mc_io, &cmd);
1417}
1418
1419/**
1420 * dpni_set_rx_tc_dist() - Set Rx traffic class distribution configuration
1421 * @mc_io:	Pointer to MC portal's I/O object
1422 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1423 * @token:	Token of DPNI object
1424 * @tc_id:	Traffic class selection (0-7)
1425 * @cfg:	Traffic class distribution configuration
1426 *
1427 * warning: if 'dist_mode != DPNI_DIST_MODE_NONE', call dpni_prepare_key_cfg()
1428 *			first to prepare the key_cfg_iova parameter
1429 *
1430 * Return:	'0' on Success; error code otherwise.
1431 */
1432int dpni_set_rx_tc_dist(struct fsl_mc_io *mc_io,
1433			u32 cmd_flags,
1434			u16 token,
1435			u8 tc_id,
1436			const struct dpni_rx_tc_dist_cfg *cfg)
1437{
1438	struct fsl_mc_command cmd = { 0 };
1439	struct dpni_cmd_set_rx_tc_dist *cmd_params;
1440
1441	/* prepare command */
1442	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_RX_TC_DIST,
1443					  cmd_flags,
1444					  token);
1445	cmd_params = (struct dpni_cmd_set_rx_tc_dist *)cmd.params;
1446	cmd_params->dist_size = cpu_to_le16(cfg->dist_size);
1447	cmd_params->tc_id = tc_id;
1448	dpni_set_field(cmd_params->flags, DIST_MODE, cfg->dist_mode);
1449	dpni_set_field(cmd_params->flags, MISS_ACTION, cfg->fs_cfg.miss_action);
1450	cmd_params->default_flow_id = cpu_to_le16(cfg->fs_cfg.default_flow_id);
1451	cmd_params->key_cfg_iova = cpu_to_le64(cfg->key_cfg_iova);
1452
1453	/* send command to mc*/
1454	return mc_send_command(mc_io, &cmd);
1455}
1456
1457/**
1458 * dpni_set_congestion_notification() - Set traffic class congestion
1459 *					notification configuration
1460 * @mc_io:	Pointer to MC portal's I/O object
1461 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1462 * @token:	Token of DPNI object
1463 * @qtype:	Type of queue - Rx, Tx and Tx confirm types are supported
1464 * @tc_id:	Traffic class selection (0-7)
1465 * @cfg:	Congestion notification configuration
1466 *
1467 * Return:	'0' on Success; error code otherwise.
1468 */
1469int dpni_set_congestion_notification(
1470			struct fsl_mc_io *mc_io,
1471			u32 cmd_flags,
1472			u16 token,
1473			enum dpni_queue_type qtype,
1474			u8 tc_id,
1475			const struct dpni_congestion_notification_cfg *cfg)
1476{
1477	struct dpni_cmd_set_congestion_notification *cmd_params;
1478	struct fsl_mc_command cmd = { 0 };
1479
1480	/* prepare command */
1481	cmd.header =
1482		mc_encode_cmd_header(DPNI_CMDID_SET_CONGESTION_NOTIFICATION,
1483				     cmd_flags,
1484				     token);
1485	cmd_params = (struct dpni_cmd_set_congestion_notification *)cmd.params;
1486	cmd_params->qtype = qtype;
1487	cmd_params->tc = tc_id;
1488	cmd_params->dest_id = cpu_to_le32(cfg->dest_cfg.dest_id);
1489	cmd_params->notification_mode = cpu_to_le16(cfg->notification_mode);
1490	cmd_params->dest_priority = cfg->dest_cfg.priority;
1491	dpni_set_field(cmd_params->type_units, DEST_TYPE,
1492		       cfg->dest_cfg.dest_type);
1493	dpni_set_field(cmd_params->type_units, CONG_UNITS, cfg->units);
1494	cmd_params->message_iova = cpu_to_le64(cfg->message_iova);
1495	cmd_params->message_ctx = cpu_to_le64(cfg->message_ctx);
1496	cmd_params->threshold_entry = cpu_to_le32(cfg->threshold_entry);
1497	cmd_params->threshold_exit = cpu_to_le32(cfg->threshold_exit);
1498
1499	/* send command to mc*/
1500	return mc_send_command(mc_io, &cmd);
1501}
1502
1503/**
1504 * dpni_set_queue() - Set queue parameters
1505 * @mc_io:	Pointer to MC portal's I/O object
1506 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1507 * @token:	Token of DPNI object
1508 * @qtype:	Type of queue - all queue types are supported, although
1509 *		the command is ignored for Tx
1510 * @tc:		Traffic class, in range 0 to NUM_TCS - 1
1511 * @index:	Selects the specific queue out of the set allocated for the
1512 *		same TC. Value must be in range 0 to NUM_QUEUES - 1
1513 * @options:	A combination of DPNI_QUEUE_OPT_ values that control what
1514 *		configuration options are set on the queue
1515 * @queue:	Queue structure
1516 *
1517 * Return:	'0' on Success; Error code otherwise.
1518 */
1519int dpni_set_queue(struct fsl_mc_io *mc_io,
1520		   u32 cmd_flags,
1521		   u16 token,
1522		   enum dpni_queue_type qtype,
1523		   u8 tc,
1524		   u8 index,
1525		   u8 options,
1526		   const struct dpni_queue *queue)
1527{
1528	struct fsl_mc_command cmd = { 0 };
1529	struct dpni_cmd_set_queue *cmd_params;
1530
1531	/* prepare command */
1532	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_QUEUE,
1533					  cmd_flags,
1534					  token);
1535	cmd_params = (struct dpni_cmd_set_queue *)cmd.params;
1536	cmd_params->qtype = qtype;
1537	cmd_params->tc = tc;
1538	cmd_params->index = index;
1539	cmd_params->options = options;
1540	cmd_params->dest_id = cpu_to_le32(queue->destination.id);
1541	cmd_params->dest_prio = queue->destination.priority;
1542	dpni_set_field(cmd_params->flags, DEST_TYPE, queue->destination.type);
1543	dpni_set_field(cmd_params->flags, STASH_CTRL, queue->flc.stash_control);
1544	dpni_set_field(cmd_params->flags, HOLD_ACTIVE,
1545		       queue->destination.hold_active);
1546	cmd_params->flc = cpu_to_le64(queue->flc.value);
1547	cmd_params->user_context = cpu_to_le64(queue->user_context);
1548
1549	/* send command to mc */
1550	return mc_send_command(mc_io, &cmd);
1551}
1552
1553/**
1554 * dpni_get_queue() - Get queue parameters
1555 * @mc_io:	Pointer to MC portal's I/O object
1556 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1557 * @token:	Token of DPNI object
1558 * @qtype:	Type of queue - all queue types are supported
1559 * @tc:		Traffic class, in range 0 to NUM_TCS - 1
1560 * @index:	Selects the specific queue out of the set allocated for the
1561 *		same TC. Value must be in range 0 to NUM_QUEUES - 1
1562 * @queue:	Queue configuration structure
1563 * @qid:	Queue identification
1564 *
1565 * Return:	'0' on Success; Error code otherwise.
1566 */
1567int dpni_get_queue(struct fsl_mc_io *mc_io,
1568		   u32 cmd_flags,
1569		   u16 token,
1570		   enum dpni_queue_type qtype,
1571		   u8 tc,
1572		   u8 index,
1573		   struct dpni_queue *queue,
1574		   struct dpni_queue_id *qid)
1575{
1576	struct fsl_mc_command cmd = { 0 };
1577	struct dpni_cmd_get_queue *cmd_params;
1578	struct dpni_rsp_get_queue *rsp_params;
1579	int err;
1580
1581	/* prepare command */
1582	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_QUEUE,
1583					  cmd_flags,
1584					  token);
1585	cmd_params = (struct dpni_cmd_get_queue *)cmd.params;
1586	cmd_params->qtype = qtype;
1587	cmd_params->tc = tc;
1588	cmd_params->index = index;
1589
1590	/* send command to mc */
1591	err = mc_send_command(mc_io, &cmd);
1592	if (err)
1593		return err;
1594
1595	/* retrieve response parameters */
1596	rsp_params = (struct dpni_rsp_get_queue *)cmd.params;
1597	queue->destination.id = le32_to_cpu(rsp_params->dest_id);
1598	queue->destination.priority = rsp_params->dest_prio;
1599	queue->destination.type = dpni_get_field(rsp_params->flags,
1600						 DEST_TYPE);
1601	queue->flc.stash_control = dpni_get_field(rsp_params->flags,
1602						  STASH_CTRL);
1603	queue->destination.hold_active = dpni_get_field(rsp_params->flags,
1604							HOLD_ACTIVE);
1605	queue->flc.value = le64_to_cpu(rsp_params->flc);
1606	queue->user_context = le64_to_cpu(rsp_params->user_context);
1607	qid->fqid = le32_to_cpu(rsp_params->fqid);
1608	qid->qdbin = le16_to_cpu(rsp_params->qdbin);
1609
1610	return 0;
1611}
1612
1613/**
1614 * dpni_get_statistics() - Get DPNI statistics
1615 * @mc_io:	Pointer to MC portal's I/O object
1616 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1617 * @token:	Token of DPNI object
1618 * @page:	Selects the statistics page to retrieve, see
1619 *		DPNI_GET_STATISTICS output. Pages are numbered 0 to 6.
1620 * @stat:	Structure containing the statistics
1621 *
1622 * Return:	'0' on Success; Error code otherwise.
1623 */
1624int dpni_get_statistics(struct fsl_mc_io *mc_io,
1625			u32 cmd_flags,
1626			u16 token,
1627			u8 page,
1628			union dpni_statistics *stat)
1629{
1630	struct fsl_mc_command cmd = { 0 };
1631	struct dpni_cmd_get_statistics *cmd_params;
1632	struct dpni_rsp_get_statistics *rsp_params;
1633	int i, err;
1634
1635	/* prepare command */
1636	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_STATISTICS,
1637					  cmd_flags,
1638					  token);
1639	cmd_params = (struct dpni_cmd_get_statistics *)cmd.params;
1640	cmd_params->page_number = page;
1641
1642	/* send command to mc */
1643	err = mc_send_command(mc_io, &cmd);
1644	if (err)
1645		return err;
1646
1647	/* retrieve response parameters */
1648	rsp_params = (struct dpni_rsp_get_statistics *)cmd.params;
1649	for (i = 0; i < DPNI_STATISTICS_CNT; i++)
1650		stat->raw.counter[i] = le64_to_cpu(rsp_params->counter[i]);
1651
1652	return 0;
1653}
1654
1655/**
1656 * dpni_set_taildrop() - Set taildrop per queue or TC
1657 * @mc_io:	Pointer to MC portal's I/O object
1658 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1659 * @token:	Token of DPNI object
1660 * @cg_point:	Congestion point
1661 * @qtype:	Queue type on which the taildrop is configured.
1662 *		Only Rx queues are supported for now
1663 * @tc:		Traffic class to apply this taildrop to
1664 * @index:	Index of the queue if the DPNI supports multiple queues for
1665 *		traffic distribution. Ignored if CONGESTION_POINT is not 0.
1666 * @taildrop:	Taildrop structure
1667 *
1668 * Return:	'0' on Success; Error code otherwise.
1669 */
1670int dpni_set_taildrop(struct fsl_mc_io *mc_io,
1671		      u32 cmd_flags,
1672		      u16 token,
1673		      enum dpni_congestion_point cg_point,
1674		      enum dpni_queue_type qtype,
1675		      u8 tc,
1676		      u8 index,
1677		      struct dpni_taildrop *taildrop)
1678{
1679	struct fsl_mc_command cmd = { 0 };
1680	struct dpni_cmd_set_taildrop *cmd_params;
1681
1682	/* prepare command */
1683	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_TAILDROP,
1684					  cmd_flags,
1685					  token);
1686	cmd_params = (struct dpni_cmd_set_taildrop *)cmd.params;
1687	cmd_params->congestion_point = cg_point;
1688	cmd_params->qtype = qtype;
1689	cmd_params->tc = tc;
1690	cmd_params->index = index;
1691	dpni_set_field(cmd_params->enable, ENABLE, taildrop->enable);
1692	cmd_params->units = taildrop->units;
1693	cmd_params->threshold = cpu_to_le32(taildrop->threshold);
1694
1695	/* send command to mc */
1696	return mc_send_command(mc_io, &cmd);
1697}
1698
1699/**
1700 * dpni_get_taildrop() - Get taildrop information
1701 * @mc_io:	Pointer to MC portal's I/O object
1702 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1703 * @token:	Token of DPNI object
1704 * @cg_point:	Congestion point
1705 * @qtype:	Queue type on which the taildrop is configured.
1706 *		Only Rx queues are supported for now
1707 * @tc:		Traffic class to apply this taildrop to
1708 * @index:	Index of the queue if the DPNI supports multiple queues for
1709 *		traffic distribution. Ignored if CONGESTION_POINT is not 0.
1710 * @taildrop:	Taildrop structure
1711 *
1712 * Return:	'0' on Success; Error code otherwise.
1713 */
1714int dpni_get_taildrop(struct fsl_mc_io *mc_io,
1715		      u32 cmd_flags,
1716		      u16 token,
1717		      enum dpni_congestion_point cg_point,
1718		      enum dpni_queue_type qtype,
1719		      u8 tc,
1720		      u8 index,
1721		      struct dpni_taildrop *taildrop)
1722{
1723	struct fsl_mc_command cmd = { 0 };
1724	struct dpni_cmd_get_taildrop *cmd_params;
1725	struct dpni_rsp_get_taildrop *rsp_params;
1726	int err;
1727
1728	/* prepare command */
1729	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_TAILDROP,
1730					  cmd_flags,
1731					  token);
1732	cmd_params = (struct dpni_cmd_get_taildrop *)cmd.params;
1733	cmd_params->congestion_point = cg_point;
1734	cmd_params->qtype = qtype;
1735	cmd_params->tc = tc;
1736	cmd_params->index = index;
1737
1738	/* send command to mc */
1739	err = mc_send_command(mc_io, &cmd);
1740	if (err)
1741		return err;
1742
1743	/* retrieve response parameters */
1744	rsp_params = (struct dpni_rsp_get_taildrop *)cmd.params;
1745	taildrop->enable = dpni_get_field(rsp_params->enable, ENABLE);
1746	taildrop->units = rsp_params->units;
1747	taildrop->threshold = le32_to_cpu(rsp_params->threshold);
1748
1749	return 0;
1750}
1751
1752/**
1753 * dpni_get_api_version() - Get Data Path Network Interface API version
1754 * @mc_io:	Pointer to MC portal's I/O object
1755 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1756 * @major_ver:	Major version of data path network interface API
1757 * @minor_ver:	Minor version of data path network interface API
1758 *
1759 * Return:	'0' on Success; Error code otherwise.
1760 */
1761int dpni_get_api_version(struct fsl_mc_io *mc_io,
1762			 u32 cmd_flags,
1763			 u16 *major_ver,
1764			 u16 *minor_ver)
1765{
1766	struct dpni_rsp_get_api_version *rsp_params;
1767	struct fsl_mc_command cmd = { 0 };
1768	int err;
1769
1770	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_API_VERSION,
1771					  cmd_flags, 0);
1772
1773	err = mc_send_command(mc_io, &cmd);
1774	if (err)
1775		return err;
1776
1777	rsp_params = (struct dpni_rsp_get_api_version *)cmd.params;
1778	*major_ver = le16_to_cpu(rsp_params->major);
1779	*minor_ver = le16_to_cpu(rsp_params->minor);
1780
1781	return 0;
1782}
1783
1784/**
1785 * dpni_set_rx_fs_dist() - Set Rx flow steering distribution
1786 * @mc_io:	Pointer to MC portal's I/O object
1787 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1788 * @token:	Token of DPNI object
1789 * @cfg: Distribution configuration
1790 *
1791 * If the FS is already enabled with a previous call the classification
1792 * key will be changed but all the table rules are kept. If the
1793 * existing rules do not match the key the results will not be
1794 * predictable. It is the user responsibility to keep key integrity.
1795 * If cfg.enable is set to 1 the command will create a flow steering table
1796 * and will classify packets according to this table. The packets that
1797 * miss all the table rules will be classified according to settings
1798 * made in dpni_set_rx_hash_dist()
1799 * If cfg.enable is set to 0 the command will clear flow steering table.
1800 * The packets will be classified according to settings made in
1801 * dpni_set_rx_hash_dist()
1802 *
1803 * Return:	'0' on Success; Error code otherwise.
1804 */
1805int dpni_set_rx_fs_dist(struct fsl_mc_io *mc_io,
1806			u32 cmd_flags,
1807			u16 token,
1808			const struct dpni_rx_dist_cfg *cfg)
1809{
1810	struct dpni_cmd_set_rx_fs_dist *cmd_params;
1811	struct fsl_mc_command cmd = { 0 };
1812
1813	/* prepare command */
1814	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_RX_FS_DIST,
1815					  cmd_flags,
1816					  token);
1817	cmd_params = (struct dpni_cmd_set_rx_fs_dist *)cmd.params;
1818	cmd_params->dist_size = cpu_to_le16(cfg->dist_size);
1819	dpni_set_field(cmd_params->enable, RX_FS_DIST_ENABLE, cfg->enable);
1820	cmd_params->tc = cfg->tc;
1821	cmd_params->miss_flow_id = cpu_to_le16(cfg->fs_miss_flow_id);
1822	cmd_params->key_cfg_iova = cpu_to_le64(cfg->key_cfg_iova);
1823
1824	/* send command to mc*/
1825	return mc_send_command(mc_io, &cmd);
1826}
1827
1828/**
1829 * dpni_set_rx_hash_dist() - Set Rx hash distribution
1830 * @mc_io:	Pointer to MC portal's I/O object
1831 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1832 * @token:	Token of DPNI object
1833 * @cfg: Distribution configuration
1834 * If cfg.enable is set to 1 the packets will be classified using a hash
1835 * function based on the key received in cfg.key_cfg_iova parameter.
1836 * If cfg.enable is set to 0 the packets will be sent to the default queue
1837 *
1838 * Return:	'0' on Success; Error code otherwise.
1839 */
1840int dpni_set_rx_hash_dist(struct fsl_mc_io *mc_io,
1841			  u32 cmd_flags,
1842			  u16 token,
1843			  const struct dpni_rx_dist_cfg *cfg)
1844{
1845	struct dpni_cmd_set_rx_hash_dist *cmd_params;
1846	struct fsl_mc_command cmd = { 0 };
1847
1848	/* prepare command */
1849	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_RX_HASH_DIST,
1850					  cmd_flags,
1851					  token);
1852	cmd_params = (struct dpni_cmd_set_rx_hash_dist *)cmd.params;
1853	cmd_params->dist_size = cpu_to_le16(cfg->dist_size);
1854	dpni_set_field(cmd_params->enable, RX_HASH_DIST_ENABLE, cfg->enable);
1855	cmd_params->tc = cfg->tc;
1856	cmd_params->key_cfg_iova = cpu_to_le64(cfg->key_cfg_iova);
1857
1858	/* send command to mc*/
1859	return mc_send_command(mc_io, &cmd);
1860}
1861
1862/**
1863 * dpni_add_fs_entry() - Add Flow Steering entry for a specific traffic class
1864 *			(to select a flow ID)
1865 * @mc_io:	Pointer to MC portal's I/O object
1866 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1867 * @token:	Token of DPNI object
1868 * @tc_id:	Traffic class selection (0-7)
1869 * @index:	Location in the FS table where to insert the entry.
1870 *		Only relevant if MASKING is enabled for FS
1871 *		classification on this DPNI, it is ignored for exact match.
1872 * @cfg:	Flow steering rule to add
1873 * @action:	Action to be taken as result of a classification hit
1874 *
1875 * Return:	'0' on Success; Error code otherwise.
1876 */
1877int dpni_add_fs_entry(struct fsl_mc_io *mc_io,
1878		      u32 cmd_flags,
1879		      u16 token,
1880		      u8 tc_id,
1881		      u16 index,
1882		      const struct dpni_rule_cfg *cfg,
1883		      const struct dpni_fs_action_cfg *action)
1884{
1885	struct dpni_cmd_add_fs_entry *cmd_params;
1886	struct fsl_mc_command cmd = { 0 };
1887
1888	/* prepare command */
1889	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ADD_FS_ENT,
1890					  cmd_flags,
1891					  token);
1892	cmd_params = (struct dpni_cmd_add_fs_entry *)cmd.params;
1893	cmd_params->tc_id = tc_id;
1894	cmd_params->key_size = cfg->key_size;
1895	cmd_params->index = cpu_to_le16(index);
1896	cmd_params->key_iova = cpu_to_le64(cfg->key_iova);
1897	cmd_params->mask_iova = cpu_to_le64(cfg->mask_iova);
1898	cmd_params->options = cpu_to_le16(action->options);
1899	cmd_params->flow_id = cpu_to_le16(action->flow_id);
1900	cmd_params->flc = cpu_to_le64(action->flc);
1901
1902	/* send command to mc*/
1903	return mc_send_command(mc_io, &cmd);
1904}
1905
1906/**
1907 * dpni_remove_fs_entry() - Remove Flow Steering entry from a specific
1908 *			    traffic class
1909 * @mc_io:	Pointer to MC portal's I/O object
1910 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1911 * @token:	Token of DPNI object
1912 * @tc_id:	Traffic class selection (0-7)
1913 * @cfg:	Flow steering rule to remove
1914 *
1915 * Return:	'0' on Success; Error code otherwise.
1916 */
1917int dpni_remove_fs_entry(struct fsl_mc_io *mc_io,
1918			 u32 cmd_flags,
1919			 u16 token,
1920			 u8 tc_id,
1921			 const struct dpni_rule_cfg *cfg)
1922{
1923	struct dpni_cmd_remove_fs_entry *cmd_params;
1924	struct fsl_mc_command cmd = { 0 };
1925
1926	/* prepare command */
1927	cmd.header = mc_encode_cmd_header(DPNI_CMDID_REMOVE_FS_ENT,
1928					  cmd_flags,
1929					  token);
1930	cmd_params = (struct dpni_cmd_remove_fs_entry *)cmd.params;
1931	cmd_params->tc_id = tc_id;
1932	cmd_params->key_size = cfg->key_size;
1933	cmd_params->key_iova = cpu_to_le64(cfg->key_iova);
1934	cmd_params->mask_iova = cpu_to_le64(cfg->mask_iova);
1935
1936	/* send command to mc*/
1937	return mc_send_command(mc_io, &cmd);
1938}
1939
1940/**
1941 * dpni_set_qos_table() - Set QoS mapping table
1942 * @mc_io:	Pointer to MC portal's I/O object
1943 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1944 * @token:	Token of DPNI object
1945 * @cfg:	QoS table configuration
1946 *
1947 * This function and all QoS-related functions require that
1948 *'max_tcs > 1' was set at DPNI creation.
1949 *
1950 * warning: Before calling this function, call dpkg_prepare_key_cfg() to
1951 *			prepare the key_cfg_iova parameter
1952 *
1953 * Return:	'0' on Success; Error code otherwise.
1954 */
1955int dpni_set_qos_table(struct fsl_mc_io *mc_io,
1956		       u32 cmd_flags,
1957		       u16 token,
1958		       const struct dpni_qos_tbl_cfg *cfg)
1959{
1960	struct dpni_cmd_set_qos_table *cmd_params;
1961	struct fsl_mc_command cmd = { 0 };
1962
1963	/* prepare command */
1964	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_QOS_TBL,
1965					  cmd_flags,
1966					  token);
1967	cmd_params = (struct dpni_cmd_set_qos_table *)cmd.params;
1968	cmd_params->default_tc = cfg->default_tc;
1969	cmd_params->key_cfg_iova = cpu_to_le64(cfg->key_cfg_iova);
1970	dpni_set_field(cmd_params->discard_on_miss, DISCARD_ON_MISS,
1971		       cfg->discard_on_miss);
1972
1973	/* send command to mc*/
1974	return mc_send_command(mc_io, &cmd);
1975}
1976
1977/**
1978 * dpni_add_qos_entry() - Add QoS mapping entry (to select a traffic class)
1979 * @mc_io:	Pointer to MC portal's I/O object
1980 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
1981 * @token:	Token of DPNI object
1982 * @cfg:	QoS rule to add
1983 * @tc_id:	Traffic class selection (0-7)
1984 * @index:	Location in the QoS table where to insert the entry.
1985 *		Only relevant if MASKING is enabled for QoS classification on
1986 *		this DPNI, it is ignored for exact match.
1987 *
1988 * Return:	'0' on Success; Error code otherwise.
1989 */
1990int dpni_add_qos_entry(struct fsl_mc_io *mc_io,
1991		       u32 cmd_flags,
1992		       u16 token,
1993		       const struct dpni_rule_cfg *cfg,
1994		       u8 tc_id,
1995		       u16 index)
1996{
1997	struct dpni_cmd_add_qos_entry *cmd_params;
1998	struct fsl_mc_command cmd = { 0 };
1999
2000	/* prepare command */
2001	cmd.header = mc_encode_cmd_header(DPNI_CMDID_ADD_QOS_ENT,
2002					  cmd_flags,
2003					  token);
2004	cmd_params = (struct dpni_cmd_add_qos_entry *)cmd.params;
2005	cmd_params->tc_id = tc_id;
2006	cmd_params->key_size = cfg->key_size;
2007	cmd_params->index = cpu_to_le16(index);
2008	cmd_params->key_iova = cpu_to_le64(cfg->key_iova);
2009	cmd_params->mask_iova = cpu_to_le64(cfg->mask_iova);
2010
2011	/* send command to mc*/
2012	return mc_send_command(mc_io, &cmd);
2013}
2014
2015/**
2016 * dpni_remove_qos_entry() - Remove QoS mapping entry
2017 * @mc_io:	Pointer to MC portal's I/O object
2018 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
2019 * @token:	Token of DPNI object
2020 * @cfg:	QoS rule to remove
2021 *
2022 * Return:	'0' on Success; Error code otherwise.
2023 */
2024int dpni_remove_qos_entry(struct fsl_mc_io *mc_io,
2025			  u32 cmd_flags,
2026			  u16 token,
2027			  const struct dpni_rule_cfg *cfg)
2028{
2029	struct dpni_cmd_remove_qos_entry *cmd_params;
2030	struct fsl_mc_command cmd = { 0 };
2031
2032	/* prepare command */
2033	cmd.header = mc_encode_cmd_header(DPNI_CMDID_REMOVE_QOS_ENT,
2034					  cmd_flags,
2035					  token);
2036	cmd_params = (struct dpni_cmd_remove_qos_entry *)cmd.params;
2037	cmd_params->key_size = cfg->key_size;
2038	cmd_params->key_iova = cpu_to_le64(cfg->key_iova);
2039	cmd_params->mask_iova = cpu_to_le64(cfg->mask_iova);
2040
2041	/* send command to mc*/
2042	return mc_send_command(mc_io, &cmd);
2043}
2044
2045/**
2046 * dpni_clear_qos_table() - Clear all QoS mapping entries
2047 * @mc_io:	Pointer to MC portal's I/O object
2048 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
2049 * @token:	Token of DPNI object
2050 *
2051 * Following this function call, all frames are directed to
2052 * the default traffic class (0)
2053 *
2054 * Return:	'0' on Success; Error code otherwise.
2055 */
2056int dpni_clear_qos_table(struct fsl_mc_io *mc_io,
2057			 u32 cmd_flags,
2058			 u16 token)
2059{
2060	struct fsl_mc_command cmd = { 0 };
2061
2062	/* prepare command */
2063	cmd.header = mc_encode_cmd_header(DPNI_CMDID_CLR_QOS_TBL,
2064					  cmd_flags,
2065					  token);
2066
2067	/* send command to mc*/
2068	return mc_send_command(mc_io, &cmd);
2069}
2070
2071/**
2072 * dpni_set_tx_shaping() - Set the transmit shaping
2073 * @mc_io:		Pointer to MC portal's I/O object
2074 * @cmd_flags:		Command flags; one or more of 'MC_CMD_FLAG_'
2075 * @token:		Token of DPNI object
2076 * @tx_cr_shaper:	TX committed rate shaping configuration
2077 * @tx_er_shaper:	TX excess rate shaping configuration
2078 * @coupled:		Committed and excess rate shapers are coupled
2079 *
2080 * Return:	'0' on Success; Error code otherwise.
2081 */
2082int dpni_set_tx_shaping(struct fsl_mc_io *mc_io,
2083			u32 cmd_flags,
2084			u16 token,
2085			const struct dpni_tx_shaping_cfg *tx_cr_shaper,
2086			const struct dpni_tx_shaping_cfg *tx_er_shaper,
2087			int coupled)
2088{
2089	struct dpni_cmd_set_tx_shaping *cmd_params;
2090	struct fsl_mc_command cmd = { 0 };
2091
2092	/* prepare command */
2093	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_TX_SHAPING,
2094					  cmd_flags,
2095					  token);
2096	cmd_params = (struct dpni_cmd_set_tx_shaping *)cmd.params;
2097	cmd_params->tx_cr_max_burst_size = cpu_to_le16(tx_cr_shaper->max_burst_size);
2098	cmd_params->tx_er_max_burst_size = cpu_to_le16(tx_er_shaper->max_burst_size);
2099	cmd_params->tx_cr_rate_limit = cpu_to_le32(tx_cr_shaper->rate_limit);
2100	cmd_params->tx_er_rate_limit = cpu_to_le32(tx_er_shaper->rate_limit);
2101	dpni_set_field(cmd_params->coupled, COUPLED, coupled);
2102
2103	/* send command to mc*/
2104	return mc_send_command(mc_io, &cmd);
2105}
2106
2107/**
2108 * dpni_get_single_step_cfg() - return current configuration for
2109 *                              single step PTP
2110 * @mc_io:	Pointer to MC portal's I/O object
2111 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
2112 * @token:	Token of DPNI object
2113 * @ptp_cfg:	ptp single step configuration
2114 *
2115 * Return:	'0' on Success; Error code otherwise.
2116 *
2117 */
2118int dpni_get_single_step_cfg(struct fsl_mc_io *mc_io,
2119			     u32 cmd_flags,
2120			     u16 token,
2121			     struct dpni_single_step_cfg *ptp_cfg)
2122{
2123	struct dpni_rsp_single_step_cfg *rsp_params;
2124	struct fsl_mc_command cmd = { 0 };
2125	int err;
2126
2127	/* prepare command */
2128	cmd.header = mc_encode_cmd_header(DPNI_CMDID_GET_SINGLE_STEP_CFG,
2129					  cmd_flags, token);
2130	/* send command to mc*/
2131	err =  mc_send_command(mc_io, &cmd);
2132	if (err)
2133		return err;
2134
2135	/* read command response */
2136	rsp_params = (struct dpni_rsp_single_step_cfg *)cmd.params;
2137	ptp_cfg->offset = le16_to_cpu(rsp_params->offset);
2138	ptp_cfg->en = dpni_get_field(le16_to_cpu(rsp_params->flags),
2139				     PTP_ENABLE) ? 1 : 0;
2140	ptp_cfg->ch_update = dpni_get_field(le16_to_cpu(rsp_params->flags),
2141					    PTP_CH_UPDATE) ? 1 : 0;
2142	ptp_cfg->peer_delay = le32_to_cpu(rsp_params->peer_delay);
2143	ptp_cfg->ptp_onestep_reg_base =
2144				  le32_to_cpu(rsp_params->ptp_onestep_reg_base);
2145
2146	return err;
2147}
2148
2149/**
2150 * dpni_set_single_step_cfg() - enable/disable and configure single step PTP
2151 * @mc_io:	Pointer to MC portal's I/O object
2152 * @cmd_flags:	Command flags; one or more of 'MC_CMD_FLAG_'
2153 * @token:	Token of DPNI object
2154 * @ptp_cfg:	ptp single step configuration
2155 *
2156 * Return:	'0' on Success; Error code otherwise.
2157 *
2158 * The function has effect only when dpni object is connected to a dpmac
2159 * object. If the dpni is not connected to a dpmac the configuration will
2160 * be stored inside and applied when connection is made.
2161 */
2162int dpni_set_single_step_cfg(struct fsl_mc_io *mc_io,
2163			     u32 cmd_flags,
2164			     u16 token,
2165			     struct dpni_single_step_cfg *ptp_cfg)
2166{
2167	struct dpni_cmd_single_step_cfg *cmd_params;
2168	struct fsl_mc_command cmd = { 0 };
2169	u16 flags;
2170
2171	/* prepare command */
2172	cmd.header = mc_encode_cmd_header(DPNI_CMDID_SET_SINGLE_STEP_CFG,
2173					  cmd_flags, token);
2174	cmd_params = (struct dpni_cmd_single_step_cfg *)cmd.params;
2175	cmd_params->offset = cpu_to_le16(ptp_cfg->offset);
2176	cmd_params->peer_delay = cpu_to_le32(ptp_cfg->peer_delay);
2177
2178	flags = le16_to_cpu(cmd_params->flags);
2179	dpni_set_field(flags, PTP_ENABLE, !!ptp_cfg->en);
2180	dpni_set_field(flags, PTP_CH_UPDATE, !!ptp_cfg->ch_update);
2181	cmd_params->flags = cpu_to_le16(flags);
2182
2183	/* send command to mc*/
2184	return mc_send_command(mc_io, &cmd);
2185}
2186