xref: /linux/drivers/net/ethernet/intel/ice/ice_dpll.c (revision 359bcf15ec1d6738ede721db628594ecf05fd998)
1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright (C) 2022, Intel Corporation. */
3 
4 #include "ice.h"
5 #include "ice_lib.h"
6 #include "ice_trace.h"
7 #include <linux/dpll.h>
8 
9 #define ICE_CGU_STATE_ACQ_ERR_THRESHOLD		50
10 #define ICE_DPLL_PIN_IDX_INVALID		0xff
11 #define ICE_DPLL_RCLK_NUM_PER_PF		1
12 #define ICE_DPLL_PIN_ESYNC_PULSE_HIGH_PERCENT	25
13 #define ICE_DPLL_PIN_GEN_RCLK_FREQ		1953125
14 #define ICE_DPLL_PIN_PRIO_OUTPUT		0xff
15 #define ICE_DPLL_INPUT_REF_NUM			10
16 #define ICE_DPLL_PHASE_OFFSET_PERIOD		2
17 #define ICE_DPLL_SW_PIN_INPUT_BASE_SFP		4
18 #define ICE_DPLL_SW_PIN_INPUT_BASE_QSFP		6
19 #define ICE_DPLL_SW_PIN_OUTPUT_BASE		0
20 
21 #define ICE_DPLL_PIN_SW_INPUT_ABS(in_idx) \
22 	(ICE_DPLL_SW_PIN_INPUT_BASE_SFP + (in_idx))
23 
24 #define ICE_DPLL_PIN_SW_1_INPUT_ABS_IDX \
25 	(ICE_DPLL_PIN_SW_INPUT_ABS(ICE_DPLL_PIN_SW_1_IDX))
26 
27 #define ICE_DPLL_PIN_SW_2_INPUT_ABS_IDX \
28 	(ICE_DPLL_PIN_SW_INPUT_ABS(ICE_DPLL_PIN_SW_2_IDX))
29 
30 #define ICE_DPLL_PIN_SW_OUTPUT_ABS(out_idx) \
31 	(ICE_DPLL_SW_PIN_OUTPUT_BASE + (out_idx))
32 
33 #define ICE_DPLL_PIN_SW_1_OUTPUT_ABS_IDX \
34 	(ICE_DPLL_PIN_SW_OUTPUT_ABS(ICE_DPLL_PIN_SW_1_IDX))
35 
36 #define ICE_DPLL_PIN_SW_2_OUTPUT_ABS_IDX \
37 	(ICE_DPLL_PIN_SW_OUTPUT_ABS(ICE_DPLL_PIN_SW_2_IDX))
38 
39 /**
40  * enum ice_dpll_pin_type - enumerate ice pin types:
41  * @ICE_DPLL_PIN_INVALID: invalid pin type
42  * @ICE_DPLL_PIN_TYPE_INPUT: input pin
43  * @ICE_DPLL_PIN_TYPE_OUTPUT: output pin
44  * @ICE_DPLL_PIN_TYPE_RCLK_INPUT: recovery clock input pin
45  * @ICE_DPLL_PIN_TYPE_SOFTWARE: software controlled SMA/U.FL pins
46  */
47 enum ice_dpll_pin_type {
48 	ICE_DPLL_PIN_INVALID,
49 	ICE_DPLL_PIN_TYPE_INPUT,
50 	ICE_DPLL_PIN_TYPE_OUTPUT,
51 	ICE_DPLL_PIN_TYPE_RCLK_INPUT,
52 	ICE_DPLL_PIN_TYPE_SOFTWARE,
53 };
54 
55 static const char * const pin_type_name[] = {
56 	[ICE_DPLL_PIN_TYPE_INPUT] = "input",
57 	[ICE_DPLL_PIN_TYPE_OUTPUT] = "output",
58 	[ICE_DPLL_PIN_TYPE_RCLK_INPUT] = "rclk-input",
59 	[ICE_DPLL_PIN_TYPE_SOFTWARE] = "software",
60 };
61 
62 static const char * const ice_dpll_sw_pin_sma[] = { "SMA1", "SMA2" };
63 static const char * const ice_dpll_sw_pin_ufl[] = { "U.FL1", "U.FL2" };
64 
65 static const struct dpll_pin_frequency ice_esync_range[] = {
66 	DPLL_PIN_FREQUENCY_RANGE(0, DPLL_PIN_FREQUENCY_1_HZ),
67 };
68 
69 /**
70  * ice_dpll_is_sw_pin - check if given pin shall be controlled by SW
71  * @pf: private board structure
72  * @index: index of a pin as understood by FW
73  * @input: true for input, false for output
74  *
75  * Check if the pin shall be controlled by SW - instead of providing raw access
76  * for pin control. For E810 NIC with dpll there is additional MUX-related logic
77  * between SMA/U.FL pins/connectors and dpll device, best to give user access
78  * with series of wrapper functions as from user perspective they convey single
79  * functionality rather then separated pins.
80  *
81  * Return:
82  * * true - pin controlled by SW
83  * * false - pin not controlled by SW
84  */
85 static bool ice_dpll_is_sw_pin(struct ice_pf *pf, u8 index, bool input)
86 {
87 	if (input && pf->hw.device_id == ICE_DEV_ID_E810C_QSFP)
88 		index -= ICE_DPLL_SW_PIN_INPUT_BASE_QSFP -
89 			 ICE_DPLL_SW_PIN_INPUT_BASE_SFP;
90 
91 	if ((input && (index == ICE_DPLL_PIN_SW_1_INPUT_ABS_IDX ||
92 		       index == ICE_DPLL_PIN_SW_2_INPUT_ABS_IDX)) ||
93 	    (!input && (index == ICE_DPLL_PIN_SW_1_OUTPUT_ABS_IDX ||
94 			index == ICE_DPLL_PIN_SW_2_OUTPUT_ABS_IDX)))
95 		return true;
96 	return false;
97 }
98 
99 /**
100  * ice_dpll_is_reset - check if reset is in progress
101  * @pf: private board structure
102  * @extack: error reporting
103  *
104  * If reset is in progress, fill extack with error.
105  *
106  * Return:
107  * * false - no reset in progress
108  * * true - reset in progress
109  */
110 static bool ice_dpll_is_reset(struct ice_pf *pf, struct netlink_ext_ack *extack)
111 {
112 	if (ice_is_reset_in_progress(pf->state)) {
113 		NL_SET_ERR_MSG(extack, "PF reset in progress");
114 		return true;
115 	}
116 	return false;
117 }
118 
119 /**
120  * ice_dpll_pin_freq_set - set pin's frequency
121  * @pf: private board structure
122  * @pin: pointer to a pin
123  * @pin_type: type of pin being configured
124  * @freq: frequency to be set
125  * @extack: error reporting
126  *
127  * Set requested frequency on a pin.
128  *
129  * Context: Called under pf->dplls.lock
130  * Return:
131  * * 0 - success
132  * * negative - error on AQ or wrong pin type given
133  */
134 static int
135 ice_dpll_pin_freq_set(struct ice_pf *pf, struct ice_dpll_pin *pin,
136 		      enum ice_dpll_pin_type pin_type, const u32 freq,
137 		      struct netlink_ext_ack *extack)
138 {
139 	u8 flags;
140 	int ret;
141 
142 	switch (pin_type) {
143 	case ICE_DPLL_PIN_TYPE_INPUT:
144 		flags = ICE_AQC_SET_CGU_IN_CFG_FLG1_UPDATE_FREQ;
145 		ret = ice_aq_set_input_pin_cfg(&pf->hw, pin->idx, flags,
146 					       pin->flags[0], freq, 0);
147 		break;
148 	case ICE_DPLL_PIN_TYPE_OUTPUT:
149 		flags = ICE_AQC_SET_CGU_OUT_CFG_UPDATE_FREQ;
150 		ret = ice_aq_set_output_pin_cfg(&pf->hw, pin->idx, flags,
151 						0, freq, 0);
152 		break;
153 	default:
154 		return -EINVAL;
155 	}
156 	if (ret) {
157 		NL_SET_ERR_MSG_FMT(extack,
158 				   "err:%d %s failed to set pin freq:%u on pin:%u",
159 				   ret,
160 				   ice_aq_str(pf->hw.adminq.sq_last_status),
161 				   freq, pin->idx);
162 		return ret;
163 	}
164 	pin->freq = freq;
165 
166 	return 0;
167 }
168 
169 /**
170  * ice_dpll_frequency_set - wrapper for pin callback for set frequency
171  * @pin: pointer to a pin
172  * @pin_priv: private data pointer passed on pin registration
173  * @dpll: pointer to dpll
174  * @dpll_priv: private data pointer passed on dpll registration
175  * @frequency: frequency to be set
176  * @extack: error reporting
177  * @pin_type: type of pin being configured
178  *
179  * Wraps internal set frequency command on a pin.
180  *
181  * Context: Acquires pf->dplls.lock
182  * Return:
183  * * 0 - success
184  * * negative - error pin not found or couldn't set in hw
185  */
186 static int
187 ice_dpll_frequency_set(const struct dpll_pin *pin, void *pin_priv,
188 		       const struct dpll_device *dpll, void *dpll_priv,
189 		       const u32 frequency,
190 		       struct netlink_ext_ack *extack,
191 		       enum ice_dpll_pin_type pin_type)
192 {
193 	struct ice_dpll_pin *p = pin_priv;
194 	struct ice_dpll *d = dpll_priv;
195 	struct ice_pf *pf = d->pf;
196 	int ret;
197 
198 	if (ice_dpll_is_reset(pf, extack))
199 		return -EBUSY;
200 
201 	mutex_lock(&pf->dplls.lock);
202 	ret = ice_dpll_pin_freq_set(pf, p, pin_type, frequency, extack);
203 	mutex_unlock(&pf->dplls.lock);
204 
205 	return ret;
206 }
207 
208 /**
209  * ice_dpll_input_frequency_set - input pin callback for set frequency
210  * @pin: pointer to a pin
211  * @pin_priv: private data pointer passed on pin registration
212  * @dpll: pointer to dpll
213  * @dpll_priv: private data pointer passed on dpll registration
214  * @frequency: frequency to be set
215  * @extack: error reporting
216  *
217  * Wraps internal set frequency command on a pin.
218  *
219  * Context: Calls a function which acquires pf->dplls.lock
220  * Return:
221  * * 0 - success
222  * * negative - error pin not found or couldn't set in hw
223  */
224 static int
225 ice_dpll_input_frequency_set(const struct dpll_pin *pin, void *pin_priv,
226 			     const struct dpll_device *dpll, void *dpll_priv,
227 			     u64 frequency, struct netlink_ext_ack *extack)
228 {
229 	return ice_dpll_frequency_set(pin, pin_priv, dpll, dpll_priv, frequency,
230 				      extack, ICE_DPLL_PIN_TYPE_INPUT);
231 }
232 
233 /**
234  * ice_dpll_output_frequency_set - output pin callback for set frequency
235  * @pin: pointer to a pin
236  * @pin_priv: private data pointer passed on pin registration
237  * @dpll: pointer to dpll
238  * @dpll_priv: private data pointer passed on dpll registration
239  * @frequency: frequency to be set
240  * @extack: error reporting
241  *
242  * Wraps internal set frequency command on a pin.
243  *
244  * Context: Calls a function which acquires pf->dplls.lock
245  * Return:
246  * * 0 - success
247  * * negative - error pin not found or couldn't set in hw
248  */
249 static int
250 ice_dpll_output_frequency_set(const struct dpll_pin *pin, void *pin_priv,
251 			      const struct dpll_device *dpll, void *dpll_priv,
252 			      u64 frequency, struct netlink_ext_ack *extack)
253 {
254 	return ice_dpll_frequency_set(pin, pin_priv, dpll, dpll_priv, frequency,
255 				      extack, ICE_DPLL_PIN_TYPE_OUTPUT);
256 }
257 
258 /**
259  * ice_dpll_frequency_get - wrapper for pin callback for get frequency
260  * @pin: pointer to a pin
261  * @pin_priv: private data pointer passed on pin registration
262  * @dpll: pointer to dpll
263  * @dpll_priv: private data pointer passed on dpll registration
264  * @frequency: on success holds pin's frequency
265  * @extack: error reporting
266  * @pin_type: type of pin being configured
267  *
268  * Wraps internal get frequency command of a pin.
269  *
270  * Context: Acquires pf->dplls.lock
271  * Return:
272  * * 0 - success
273  * * negative - error pin not found or couldn't get from hw
274  */
275 static int
276 ice_dpll_frequency_get(const struct dpll_pin *pin, void *pin_priv,
277 		       const struct dpll_device *dpll, void *dpll_priv,
278 		       u64 *frequency, struct netlink_ext_ack *extack,
279 		       enum ice_dpll_pin_type pin_type)
280 {
281 	struct ice_dpll_pin *p = pin_priv;
282 	struct ice_dpll *d = dpll_priv;
283 	struct ice_pf *pf = d->pf;
284 
285 	mutex_lock(&pf->dplls.lock);
286 	*frequency = p->freq;
287 	mutex_unlock(&pf->dplls.lock);
288 
289 	return 0;
290 }
291 
292 /**
293  * ice_dpll_input_frequency_get - input pin callback for get frequency
294  * @pin: pointer to a pin
295  * @pin_priv: private data pointer passed on pin registration
296  * @dpll: pointer to dpll
297  * @dpll_priv: private data pointer passed on dpll registration
298  * @frequency: on success holds pin's frequency
299  * @extack: error reporting
300  *
301  * Wraps internal get frequency command of a input pin.
302  *
303  * Context: Calls a function which acquires pf->dplls.lock
304  * Return:
305  * * 0 - success
306  * * negative - error pin not found or couldn't get from hw
307  */
308 static int
309 ice_dpll_input_frequency_get(const struct dpll_pin *pin, void *pin_priv,
310 			     const struct dpll_device *dpll, void *dpll_priv,
311 			     u64 *frequency, struct netlink_ext_ack *extack)
312 {
313 	return ice_dpll_frequency_get(pin, pin_priv, dpll, dpll_priv, frequency,
314 				      extack, ICE_DPLL_PIN_TYPE_INPUT);
315 }
316 
317 /**
318  * ice_dpll_output_frequency_get - output pin callback for get frequency
319  * @pin: pointer to a pin
320  * @pin_priv: private data pointer passed on pin registration
321  * @dpll: pointer to dpll
322  * @dpll_priv: private data pointer passed on dpll registration
323  * @frequency: on success holds pin's frequency
324  * @extack: error reporting
325  *
326  * Wraps internal get frequency command of a pin.
327  *
328  * Context: Calls a function which acquires pf->dplls.lock
329  * Return:
330  * * 0 - success
331  * * negative - error pin not found or couldn't get from hw
332  */
333 static int
334 ice_dpll_output_frequency_get(const struct dpll_pin *pin, void *pin_priv,
335 			      const struct dpll_device *dpll, void *dpll_priv,
336 			      u64 *frequency, struct netlink_ext_ack *extack)
337 {
338 	return ice_dpll_frequency_get(pin, pin_priv, dpll, dpll_priv, frequency,
339 				      extack, ICE_DPLL_PIN_TYPE_OUTPUT);
340 }
341 
342 /**
343  * ice_dpll_sw_pin_frequency_set - callback to set frequency of SW pin
344  * @pin: pointer to a pin
345  * @pin_priv: private data pointer passed on pin registration
346  * @dpll: pointer to dpll
347  * @dpll_priv: private data pointer passed on dpll registration
348  * @frequency: on success holds pin's frequency
349  * @extack: error reporting
350  *
351  * Calls set frequency command for corresponding and active input/output pin.
352  *
353  * Context: Calls a function which acquires and releases pf->dplls.lock
354  * Return:
355  * * 0 - success
356  * * negative - error pin not active or couldn't get from hw
357  */
358 static int
359 ice_dpll_sw_pin_frequency_set(const struct dpll_pin *pin, void *pin_priv,
360 			      const struct dpll_device *dpll, void *dpll_priv,
361 			      u64 frequency, struct netlink_ext_ack *extack)
362 {
363 	struct ice_dpll_pin *sma = pin_priv;
364 	int ret;
365 
366 	if (!sma->active) {
367 		NL_SET_ERR_MSG(extack, "pin is not active");
368 		return -EINVAL;
369 	}
370 	if (sma->direction == DPLL_PIN_DIRECTION_INPUT)
371 		ret = ice_dpll_input_frequency_set(NULL, sma->input, dpll,
372 						   dpll_priv, frequency,
373 						   extack);
374 	else
375 		ret = ice_dpll_output_frequency_set(NULL, sma->output, dpll,
376 						    dpll_priv, frequency,
377 						    extack);
378 
379 	return ret;
380 }
381 
382 /**
383  * ice_dpll_sw_pin_frequency_get - callback for get frequency of SW pin
384  * @pin: pointer to a pin
385  * @pin_priv: private data pointer passed on pin registration
386  * @dpll: pointer to dpll
387  * @dpll_priv: private data pointer passed on dpll registration
388  * @frequency: on success holds pin's frequency
389  * @extack: error reporting
390  *
391  * Calls get frequency command for corresponding active input/output.
392  *
393  * Context: Calls a function which acquires and releases pf->dplls.lock
394  * Return:
395  * * 0 - success
396  * * negative - error pin not active or couldn't get from hw
397  */
398 static int
399 ice_dpll_sw_pin_frequency_get(const struct dpll_pin *pin, void *pin_priv,
400 			      const struct dpll_device *dpll, void *dpll_priv,
401 			      u64 *frequency, struct netlink_ext_ack *extack)
402 {
403 	struct ice_dpll_pin *sma = pin_priv;
404 	int ret;
405 
406 	if (!sma->active) {
407 		*frequency = 0;
408 		return 0;
409 	}
410 	if (sma->direction == DPLL_PIN_DIRECTION_INPUT) {
411 		ret = ice_dpll_input_frequency_get(NULL, sma->input, dpll,
412 						   dpll_priv, frequency,
413 						   extack);
414 	} else {
415 		ret = ice_dpll_output_frequency_get(NULL, sma->output, dpll,
416 						    dpll_priv, frequency,
417 						    extack);
418 	}
419 
420 	return ret;
421 }
422 
423 /**
424  * ice_dpll_pin_enable - enable a pin on dplls
425  * @hw: board private hw structure
426  * @pin: pointer to a pin
427  * @dpll_idx: dpll index to connect to output pin
428  * @pin_type: type of pin being enabled
429  * @extack: error reporting
430  *
431  * Enable a pin on both dplls. Store current state in pin->flags.
432  *
433  * Context: Called under pf->dplls.lock
434  * Return:
435  * * 0 - OK
436  * * negative - error
437  */
438 static int
439 ice_dpll_pin_enable(struct ice_hw *hw, struct ice_dpll_pin *pin,
440 		    u8 dpll_idx, enum ice_dpll_pin_type pin_type,
441 		    struct netlink_ext_ack *extack)
442 {
443 	u8 flags = 0;
444 	int ret;
445 
446 	switch (pin_type) {
447 	case ICE_DPLL_PIN_TYPE_INPUT:
448 		if (pin->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN)
449 			flags |= ICE_AQC_SET_CGU_IN_CFG_FLG2_ESYNC_EN;
450 		flags |= ICE_AQC_SET_CGU_IN_CFG_FLG2_INPUT_EN;
451 		ret = ice_aq_set_input_pin_cfg(hw, pin->idx, 0, flags, 0, 0);
452 		break;
453 	case ICE_DPLL_PIN_TYPE_OUTPUT:
454 		flags = ICE_AQC_SET_CGU_OUT_CFG_UPDATE_SRC_SEL;
455 		if (pin->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN)
456 			flags |= ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN;
457 		flags |= ICE_AQC_SET_CGU_OUT_CFG_OUT_EN;
458 		ret = ice_aq_set_output_pin_cfg(hw, pin->idx, flags, dpll_idx,
459 						0, 0);
460 		break;
461 	default:
462 		return -EINVAL;
463 	}
464 	if (ret)
465 		NL_SET_ERR_MSG_FMT(extack,
466 				   "err:%d %s failed to enable %s pin:%u",
467 				   ret, ice_aq_str(hw->adminq.sq_last_status),
468 				   pin_type_name[pin_type], pin->idx);
469 
470 	return ret;
471 }
472 
473 /**
474  * ice_dpll_pin_disable - disable a pin on dplls
475  * @hw: board private hw structure
476  * @pin: pointer to a pin
477  * @pin_type: type of pin being disabled
478  * @extack: error reporting
479  *
480  * Disable a pin on both dplls. Store current state in pin->flags.
481  *
482  * Context: Called under pf->dplls.lock
483  * Return:
484  * * 0 - OK
485  * * negative - error
486  */
487 static int
488 ice_dpll_pin_disable(struct ice_hw *hw, struct ice_dpll_pin *pin,
489 		     enum ice_dpll_pin_type pin_type,
490 		     struct netlink_ext_ack *extack)
491 {
492 	u8 flags = 0;
493 	int ret;
494 
495 	switch (pin_type) {
496 	case ICE_DPLL_PIN_TYPE_INPUT:
497 		if (pin->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN)
498 			flags |= ICE_AQC_SET_CGU_IN_CFG_FLG2_ESYNC_EN;
499 		ret = ice_aq_set_input_pin_cfg(hw, pin->idx, 0, flags, 0, 0);
500 		break;
501 	case ICE_DPLL_PIN_TYPE_OUTPUT:
502 		if (pin->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN)
503 			flags |= ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN;
504 		ret = ice_aq_set_output_pin_cfg(hw, pin->idx, flags, 0, 0, 0);
505 		break;
506 	default:
507 		return -EINVAL;
508 	}
509 	if (ret)
510 		NL_SET_ERR_MSG_FMT(extack,
511 				   "err:%d %s failed to disable %s pin:%u",
512 				   ret, ice_aq_str(hw->adminq.sq_last_status),
513 				   pin_type_name[pin_type], pin->idx);
514 
515 	return ret;
516 }
517 
518 /**
519  * ice_dpll_sw_pins_update - update status of all SW pins
520  * @pf: private board struct
521  *
522  * Determine and update pin struct fields (direction/active) of their current
523  * values for all the SW controlled pins.
524  *
525  * Context: Call with pf->dplls.lock held
526  * Return:
527  * * 0 - OK
528  * * negative - error
529  */
530 static int
531 ice_dpll_sw_pins_update(struct ice_pf *pf)
532 {
533 	struct ice_dplls *d = &pf->dplls;
534 	struct ice_dpll_pin *p;
535 	u8 data = 0;
536 	int ret;
537 
538 	ret = ice_read_sma_ctrl(&pf->hw, &data);
539 	if (ret)
540 		return ret;
541 	/* no change since last check */
542 	if (d->sma_data == data)
543 		return 0;
544 
545 	/*
546 	 * SMA1/U.FL1 vs SMA2/U.FL2 are using different bit scheme to decide
547 	 * on their direction and if are active
548 	 */
549 	p = &d->sma[ICE_DPLL_PIN_SW_1_IDX];
550 	p->active = true;
551 	p->direction = DPLL_PIN_DIRECTION_INPUT;
552 	if (data & ICE_SMA1_DIR_EN) {
553 		p->direction = DPLL_PIN_DIRECTION_OUTPUT;
554 		if (data & ICE_SMA1_TX_EN)
555 			p->active = false;
556 	}
557 
558 	p = &d->sma[ICE_DPLL_PIN_SW_2_IDX];
559 	p->active = true;
560 	p->direction = DPLL_PIN_DIRECTION_INPUT;
561 	if ((data & ICE_SMA2_INACTIVE_MASK) == ICE_SMA2_INACTIVE_MASK)
562 		p->active = false;
563 	else if (data & ICE_SMA2_DIR_EN)
564 		p->direction = DPLL_PIN_DIRECTION_OUTPUT;
565 
566 	p = &d->ufl[ICE_DPLL_PIN_SW_1_IDX];
567 	if (!(data & (ICE_SMA1_DIR_EN | ICE_SMA1_TX_EN)))
568 		p->active = true;
569 	else
570 		p->active = false;
571 
572 	p = &d->ufl[ICE_DPLL_PIN_SW_2_IDX];
573 	p->active = (data & ICE_SMA2_DIR_EN) && !(data & ICE_SMA2_UFL2_RX_DIS);
574 	d->sma_data = data;
575 
576 	return 0;
577 }
578 
579 /**
580  * ice_dpll_pin_state_update - update pin's state
581  * @pf: private board struct
582  * @pin: structure with pin attributes to be updated
583  * @pin_type: type of pin being updated
584  * @extack: error reporting
585  *
586  * Determine pin current state and frequency, then update struct
587  * holding the pin info. For input pin states are separated for each
588  * dpll, for rclk pins states are separated for each parent.
589  *
590  * Context: Called under pf->dplls.lock
591  * Return:
592  * * 0 - OK
593  * * negative - error
594  */
595 static int
596 ice_dpll_pin_state_update(struct ice_pf *pf, struct ice_dpll_pin *pin,
597 			  enum ice_dpll_pin_type pin_type,
598 			  struct netlink_ext_ack *extack)
599 {
600 	u8 parent, port_num = ICE_AQC_SET_PHY_REC_CLK_OUT_CURR_PORT;
601 	int ret;
602 
603 	switch (pin_type) {
604 	case ICE_DPLL_PIN_TYPE_INPUT:
605 		ret = ice_aq_get_input_pin_cfg(&pf->hw, pin->idx, &pin->status,
606 					       NULL, NULL, &pin->flags[0],
607 					       &pin->freq, &pin->phase_adjust);
608 		if (ret)
609 			goto err;
610 		if (ICE_AQC_GET_CGU_IN_CFG_FLG2_INPUT_EN & pin->flags[0]) {
611 			if (pin->pin) {
612 				pin->state[pf->dplls.eec.dpll_idx] =
613 					pin->pin == pf->dplls.eec.active_input ?
614 					DPLL_PIN_STATE_CONNECTED :
615 					DPLL_PIN_STATE_SELECTABLE;
616 				pin->state[pf->dplls.pps.dpll_idx] =
617 					pin->pin == pf->dplls.pps.active_input ?
618 					DPLL_PIN_STATE_CONNECTED :
619 					DPLL_PIN_STATE_SELECTABLE;
620 			} else {
621 				pin->state[pf->dplls.eec.dpll_idx] =
622 					DPLL_PIN_STATE_SELECTABLE;
623 				pin->state[pf->dplls.pps.dpll_idx] =
624 					DPLL_PIN_STATE_SELECTABLE;
625 			}
626 		} else {
627 			pin->state[pf->dplls.eec.dpll_idx] =
628 				DPLL_PIN_STATE_DISCONNECTED;
629 			pin->state[pf->dplls.pps.dpll_idx] =
630 				DPLL_PIN_STATE_DISCONNECTED;
631 		}
632 		break;
633 	case ICE_DPLL_PIN_TYPE_OUTPUT:
634 		ret = ice_aq_get_output_pin_cfg(&pf->hw, pin->idx,
635 						&pin->flags[0], &parent,
636 						&pin->freq, NULL);
637 		if (ret)
638 			goto err;
639 
640 		parent &= ICE_AQC_GET_CGU_OUT_CFG_DPLL_SRC_SEL;
641 		if (ICE_AQC_GET_CGU_OUT_CFG_OUT_EN & pin->flags[0]) {
642 			pin->state[pf->dplls.eec.dpll_idx] =
643 				parent == pf->dplls.eec.dpll_idx ?
644 				DPLL_PIN_STATE_CONNECTED :
645 				DPLL_PIN_STATE_DISCONNECTED;
646 			pin->state[pf->dplls.pps.dpll_idx] =
647 				parent == pf->dplls.pps.dpll_idx ?
648 				DPLL_PIN_STATE_CONNECTED :
649 				DPLL_PIN_STATE_DISCONNECTED;
650 		} else {
651 			pin->state[pf->dplls.eec.dpll_idx] =
652 				DPLL_PIN_STATE_DISCONNECTED;
653 			pin->state[pf->dplls.pps.dpll_idx] =
654 				DPLL_PIN_STATE_DISCONNECTED;
655 		}
656 		break;
657 	case ICE_DPLL_PIN_TYPE_RCLK_INPUT:
658 		for (parent = 0; parent < pf->dplls.rclk.num_parents;
659 		     parent++) {
660 			u8 p = parent;
661 
662 			ret = ice_aq_get_phy_rec_clk_out(&pf->hw, &p,
663 							 &port_num,
664 							 &pin->flags[parent],
665 							 NULL);
666 			if (ret)
667 				goto err;
668 			if (ICE_AQC_GET_PHY_REC_CLK_OUT_OUT_EN &
669 			    pin->flags[parent])
670 				pin->state[parent] = DPLL_PIN_STATE_CONNECTED;
671 			else
672 				pin->state[parent] =
673 					DPLL_PIN_STATE_DISCONNECTED;
674 		}
675 		break;
676 	case ICE_DPLL_PIN_TYPE_SOFTWARE:
677 		ret = ice_dpll_sw_pins_update(pf);
678 		if (ret)
679 			goto err;
680 		break;
681 	default:
682 		return -EINVAL;
683 	}
684 
685 	return 0;
686 err:
687 	if (extack)
688 		NL_SET_ERR_MSG_FMT(extack,
689 				   "err:%d %s failed to update %s pin:%u",
690 				   ret,
691 				   ice_aq_str(pf->hw.adminq.sq_last_status),
692 				   pin_type_name[pin_type], pin->idx);
693 	else
694 		dev_err_ratelimited(ice_pf_to_dev(pf),
695 				    "err:%d %s failed to update %s pin:%u\n",
696 				    ret,
697 				    ice_aq_str(pf->hw.adminq.sq_last_status),
698 				    pin_type_name[pin_type], pin->idx);
699 	return ret;
700 }
701 
702 /**
703  * ice_dpll_hw_input_prio_set - set input priority value in hardware
704  * @pf: board private structure
705  * @dpll: ice dpll pointer
706  * @pin: ice pin pointer
707  * @prio: priority value being set on a dpll
708  * @extack: error reporting
709  *
710  * Internal wrapper for setting the priority in the hardware.
711  *
712  * Context: Called under pf->dplls.lock
713  * Return:
714  * * 0 - success
715  * * negative - failure
716  */
717 static int
718 ice_dpll_hw_input_prio_set(struct ice_pf *pf, struct ice_dpll *dpll,
719 			   struct ice_dpll_pin *pin, const u32 prio,
720 			   struct netlink_ext_ack *extack)
721 {
722 	int ret;
723 
724 	ret = ice_aq_set_cgu_ref_prio(&pf->hw, dpll->dpll_idx, pin->idx,
725 				      (u8)prio);
726 	if (ret)
727 		NL_SET_ERR_MSG_FMT(extack,
728 				   "err:%d %s failed to set pin prio:%u on pin:%u",
729 				   ret,
730 				   ice_aq_str(pf->hw.adminq.sq_last_status),
731 				   prio, pin->idx);
732 	else
733 		dpll->input_prio[pin->idx] = prio;
734 
735 	return ret;
736 }
737 
738 /**
739  * ice_dpll_lock_status_get - get dpll lock status callback
740  * @dpll: registered dpll pointer
741  * @dpll_priv: private data pointer passed on dpll registration
742  * @status: on success holds dpll's lock status
743  * @status_error: status error value
744  * @extack: error reporting
745  *
746  * Dpll subsystem callback, provides dpll's lock status.
747  *
748  * Context: Acquires pf->dplls.lock
749  * Return:
750  * * 0 - success
751  * * negative - failure
752  */
753 static int
754 ice_dpll_lock_status_get(const struct dpll_device *dpll, void *dpll_priv,
755 			 enum dpll_lock_status *status,
756 			 enum dpll_lock_status_error *status_error,
757 			 struct netlink_ext_ack *extack)
758 {
759 	struct ice_dpll *d = dpll_priv;
760 	struct ice_pf *pf = d->pf;
761 
762 	mutex_lock(&pf->dplls.lock);
763 	*status = d->dpll_state;
764 	mutex_unlock(&pf->dplls.lock);
765 
766 	return 0;
767 }
768 
769 /**
770  * ice_dpll_mode_get - get dpll's working mode
771  * @dpll: registered dpll pointer
772  * @dpll_priv: private data pointer passed on dpll registration
773  * @mode: on success holds current working mode of dpll
774  * @extack: error reporting
775  *
776  * Dpll subsystem callback. Provides working mode of dpll.
777  *
778  * Context: Acquires pf->dplls.lock
779  * Return:
780  * * 0 - success
781  * * negative - failure
782  */
783 static int ice_dpll_mode_get(const struct dpll_device *dpll, void *dpll_priv,
784 			     enum dpll_mode *mode,
785 			     struct netlink_ext_ack *extack)
786 {
787 	struct ice_dpll *d = dpll_priv;
788 	struct ice_pf *pf = d->pf;
789 
790 	mutex_lock(&pf->dplls.lock);
791 	*mode = d->mode;
792 	mutex_unlock(&pf->dplls.lock);
793 
794 	return 0;
795 }
796 
797 /**
798  * ice_dpll_phase_offset_monitor_set - set phase offset monitor state
799  * @dpll: registered dpll pointer
800  * @dpll_priv: private data pointer passed on dpll registration
801  * @state: feature state to be set
802  * @extack: error reporting
803  *
804  * Dpll subsystem callback. Enable/disable phase offset monitor feature of dpll.
805  *
806  * Context: Acquires and releases pf->dplls.lock
807  * Return: 0 - success
808  */
809 static int ice_dpll_phase_offset_monitor_set(const struct dpll_device *dpll,
810 					     void *dpll_priv,
811 					     enum dpll_feature_state state,
812 					     struct netlink_ext_ack *extack)
813 {
814 	struct ice_dpll *d = dpll_priv;
815 	struct ice_pf *pf = d->pf;
816 
817 	mutex_lock(&pf->dplls.lock);
818 	if (state == DPLL_FEATURE_STATE_ENABLE)
819 		d->phase_offset_monitor_period = ICE_DPLL_PHASE_OFFSET_PERIOD;
820 	else
821 		d->phase_offset_monitor_period = 0;
822 	mutex_unlock(&pf->dplls.lock);
823 
824 	return 0;
825 }
826 
827 /**
828  * ice_dpll_phase_offset_monitor_get - get phase offset monitor state
829  * @dpll: registered dpll pointer
830  * @dpll_priv: private data pointer passed on dpll registration
831  * @state: on success holds current state of phase offset monitor
832  * @extack: error reporting
833  *
834  * Dpll subsystem callback. Provides current state of phase offset monitor
835  * features on dpll device.
836  *
837  * Context: Acquires and releases pf->dplls.lock
838  * Return: 0 - success
839  */
840 static int ice_dpll_phase_offset_monitor_get(const struct dpll_device *dpll,
841 					     void *dpll_priv,
842 					     enum dpll_feature_state *state,
843 					     struct netlink_ext_ack *extack)
844 {
845 	struct ice_dpll *d = dpll_priv;
846 	struct ice_pf *pf = d->pf;
847 
848 	mutex_lock(&pf->dplls.lock);
849 	if (d->phase_offset_monitor_period)
850 		*state = DPLL_FEATURE_STATE_ENABLE;
851 	else
852 		*state = DPLL_FEATURE_STATE_DISABLE;
853 	mutex_unlock(&pf->dplls.lock);
854 
855 	return 0;
856 }
857 
858 /**
859  * ice_dpll_pin_state_set - set pin's state on dpll
860  * @pin: pointer to a pin
861  * @pin_priv: private data pointer passed on pin registration
862  * @dpll: registered dpll pointer
863  * @dpll_priv: private data pointer passed on dpll registration
864  * @enable: if pin shalll be enabled
865  * @extack: error reporting
866  * @pin_type: type of a pin
867  *
868  * Set pin state on a pin.
869  *
870  * Context: Acquires pf->dplls.lock
871  * Return:
872  * * 0 - OK or no change required
873  * * negative - error
874  */
875 static int
876 ice_dpll_pin_state_set(const struct dpll_pin *pin, void *pin_priv,
877 		       const struct dpll_device *dpll, void *dpll_priv,
878 		       bool enable, struct netlink_ext_ack *extack,
879 		       enum ice_dpll_pin_type pin_type)
880 {
881 	struct ice_dpll_pin *p = pin_priv;
882 	struct ice_dpll *d = dpll_priv;
883 	struct ice_pf *pf = d->pf;
884 	int ret;
885 
886 	if (ice_dpll_is_reset(pf, extack))
887 		return -EBUSY;
888 
889 	mutex_lock(&pf->dplls.lock);
890 	if (enable)
891 		ret = ice_dpll_pin_enable(&pf->hw, p, d->dpll_idx, pin_type,
892 					  extack);
893 	else
894 		ret = ice_dpll_pin_disable(&pf->hw, p, pin_type, extack);
895 	if (!ret)
896 		ret = ice_dpll_pin_state_update(pf, p, pin_type, extack);
897 	mutex_unlock(&pf->dplls.lock);
898 
899 	return ret;
900 }
901 
902 /**
903  * ice_dpll_output_state_set - enable/disable output pin on dpll device
904  * @pin: pointer to a pin
905  * @pin_priv: private data pointer passed on pin registration
906  * @dpll: dpll being configured
907  * @dpll_priv: private data pointer passed on dpll registration
908  * @state: state of pin to be set
909  * @extack: error reporting
910  *
911  * Dpll subsystem callback. Set given state on output type pin.
912  *
913  * Context: Calls a function which acquires pf->dplls.lock
914  * Return:
915  * * 0 - successfully enabled mode
916  * * negative - failed to enable mode
917  */
918 static int
919 ice_dpll_output_state_set(const struct dpll_pin *pin, void *pin_priv,
920 			  const struct dpll_device *dpll, void *dpll_priv,
921 			  enum dpll_pin_state state,
922 			  struct netlink_ext_ack *extack)
923 {
924 	bool enable = state == DPLL_PIN_STATE_CONNECTED;
925 	struct ice_dpll_pin *p = pin_priv;
926 	struct ice_dpll *d = dpll_priv;
927 
928 	if (state == DPLL_PIN_STATE_SELECTABLE)
929 		return -EINVAL;
930 	if (!enable && p->state[d->dpll_idx] == DPLL_PIN_STATE_DISCONNECTED)
931 		return 0;
932 
933 	return ice_dpll_pin_state_set(pin, pin_priv, dpll, dpll_priv, enable,
934 				      extack, ICE_DPLL_PIN_TYPE_OUTPUT);
935 }
936 
937 /**
938  * ice_dpll_input_state_set - enable/disable input pin on dpll levice
939  * @pin: pointer to a pin
940  * @pin_priv: private data pointer passed on pin registration
941  * @dpll: dpll being configured
942  * @dpll_priv: private data pointer passed on dpll registration
943  * @state: state of pin to be set
944  * @extack: error reporting
945  *
946  * Dpll subsystem callback. Enables given mode on input type pin.
947  *
948  * Context: Calls a function which acquires pf->dplls.lock
949  * Return:
950  * * 0 - successfully enabled mode
951  * * negative - failed to enable mode
952  */
953 static int
954 ice_dpll_input_state_set(const struct dpll_pin *pin, void *pin_priv,
955 			 const struct dpll_device *dpll, void *dpll_priv,
956 			 enum dpll_pin_state state,
957 			 struct netlink_ext_ack *extack)
958 {
959 	bool enable = state == DPLL_PIN_STATE_SELECTABLE;
960 
961 	return ice_dpll_pin_state_set(pin, pin_priv, dpll, dpll_priv, enable,
962 				      extack, ICE_DPLL_PIN_TYPE_INPUT);
963 }
964 
965 /**
966  * ice_dpll_pin_state_get - set pin's state on dpll
967  * @pin: pointer to a pin
968  * @pin_priv: private data pointer passed on pin registration
969  * @dpll: registered dpll pointer
970  * @dpll_priv: private data pointer passed on dpll registration
971  * @state: on success holds state of the pin
972  * @extack: error reporting
973  * @pin_type: type of questioned pin
974  *
975  * Determine pin state set it on a pin.
976  *
977  * Context: Acquires pf->dplls.lock
978  * Return:
979  * * 0 - success
980  * * negative - failed to get state
981  */
982 static int
983 ice_dpll_pin_state_get(const struct dpll_pin *pin, void *pin_priv,
984 		       const struct dpll_device *dpll, void *dpll_priv,
985 		       enum dpll_pin_state *state,
986 		       struct netlink_ext_ack *extack,
987 		       enum ice_dpll_pin_type pin_type)
988 {
989 	struct ice_dpll_pin *p = pin_priv;
990 	struct ice_dpll *d = dpll_priv;
991 	struct ice_pf *pf = d->pf;
992 	int ret;
993 
994 	if (ice_dpll_is_reset(pf, extack))
995 		return -EBUSY;
996 
997 	mutex_lock(&pf->dplls.lock);
998 	ret = ice_dpll_pin_state_update(pf, p, pin_type, extack);
999 	if (ret)
1000 		goto unlock;
1001 	if (pin_type == ICE_DPLL_PIN_TYPE_INPUT ||
1002 	    pin_type == ICE_DPLL_PIN_TYPE_OUTPUT)
1003 		*state = p->state[d->dpll_idx];
1004 	ret = 0;
1005 unlock:
1006 	mutex_unlock(&pf->dplls.lock);
1007 
1008 	return ret;
1009 }
1010 
1011 /**
1012  * ice_dpll_output_state_get - get output pin state on dpll device
1013  * @pin: pointer to a pin
1014  * @pin_priv: private data pointer passed on pin registration
1015  * @dpll: registered dpll pointer
1016  * @dpll_priv: private data pointer passed on dpll registration
1017  * @state: on success holds state of the pin
1018  * @extack: error reporting
1019  *
1020  * Dpll subsystem callback. Check state of a pin.
1021  *
1022  * Context: Calls a function which acquires pf->dplls.lock
1023  * Return:
1024  * * 0 - success
1025  * * negative - failed to get state
1026  */
1027 static int
1028 ice_dpll_output_state_get(const struct dpll_pin *pin, void *pin_priv,
1029 			  const struct dpll_device *dpll, void *dpll_priv,
1030 			  enum dpll_pin_state *state,
1031 			  struct netlink_ext_ack *extack)
1032 {
1033 	return ice_dpll_pin_state_get(pin, pin_priv, dpll, dpll_priv, state,
1034 				      extack, ICE_DPLL_PIN_TYPE_OUTPUT);
1035 }
1036 
1037 /**
1038  * ice_dpll_input_state_get - get input pin state on dpll device
1039  * @pin: pointer to a pin
1040  * @pin_priv: private data pointer passed on pin registration
1041  * @dpll: registered dpll pointer
1042  * @dpll_priv: private data pointer passed on dpll registration
1043  * @state: on success holds state of the pin
1044  * @extack: error reporting
1045  *
1046  * Dpll subsystem callback. Check state of a input pin.
1047  *
1048  * Context: Calls a function which acquires pf->dplls.lock
1049  * Return:
1050  * * 0 - success
1051  * * negative - failed to get state
1052  */
1053 static int
1054 ice_dpll_input_state_get(const struct dpll_pin *pin, void *pin_priv,
1055 			 const struct dpll_device *dpll, void *dpll_priv,
1056 			 enum dpll_pin_state *state,
1057 			 struct netlink_ext_ack *extack)
1058 {
1059 	return ice_dpll_pin_state_get(pin, pin_priv, dpll, dpll_priv, state,
1060 				      extack, ICE_DPLL_PIN_TYPE_INPUT);
1061 }
1062 
1063 /**
1064  * ice_dpll_sma_direction_set - set direction of SMA pin
1065  * @p: pointer to a pin
1066  * @direction: requested direction of the pin
1067  * @extack: error reporting
1068  *
1069  * Wrapper for dpll subsystem callback. Set direction of a SMA pin.
1070  *
1071  * Context: Call with pf->dplls.lock held
1072  * Return:
1073  * * 0 - success
1074  * * negative - failed to get state
1075  */
1076 static int ice_dpll_sma_direction_set(struct ice_dpll_pin *p,
1077 				      enum dpll_pin_direction direction,
1078 				      struct netlink_ext_ack *extack)
1079 {
1080 	u8 data;
1081 	int ret;
1082 
1083 	if (p->direction == direction && p->active)
1084 		return 0;
1085 	ret = ice_read_sma_ctrl(&p->pf->hw, &data);
1086 	if (ret)
1087 		return ret;
1088 
1089 	switch (p->idx) {
1090 	case ICE_DPLL_PIN_SW_1_IDX:
1091 		data &= ~ICE_SMA1_MASK;
1092 		if (direction == DPLL_PIN_DIRECTION_OUTPUT)
1093 			data |= ICE_SMA1_DIR_EN;
1094 		break;
1095 	case ICE_DPLL_PIN_SW_2_IDX:
1096 		if (direction == DPLL_PIN_DIRECTION_INPUT) {
1097 			data &= ~ICE_SMA2_DIR_EN;
1098 		} else {
1099 			data &= ~ICE_SMA2_TX_EN;
1100 			data |= ICE_SMA2_DIR_EN;
1101 		}
1102 		break;
1103 	default:
1104 		return -EINVAL;
1105 	}
1106 	ret = ice_write_sma_ctrl(&p->pf->hw, data);
1107 	if (!ret)
1108 		ret = ice_dpll_pin_state_update(p->pf, p,
1109 						ICE_DPLL_PIN_TYPE_SOFTWARE,
1110 						extack);
1111 
1112 	return ret;
1113 }
1114 
1115 /**
1116  * ice_dpll_ufl_pin_state_set - set U.FL pin state on dpll device
1117  * @pin: pointer to a pin
1118  * @pin_priv: private data pointer passed on pin registration
1119  * @dpll: registered dpll pointer
1120  * @dpll_priv: private data pointer passed on dpll registration
1121  * @state: requested state of the pin
1122  * @extack: error reporting
1123  *
1124  * Dpll subsystem callback. Set the state of a pin.
1125  *
1126  * Context: Acquires and releases pf->dplls.lock
1127  * Return:
1128  * * 0 - success
1129  * * negative - error
1130  */
1131 static int
1132 ice_dpll_ufl_pin_state_set(const struct dpll_pin *pin, void *pin_priv,
1133 			   const struct dpll_device *dpll, void *dpll_priv,
1134 			   enum dpll_pin_state state,
1135 			   struct netlink_ext_ack *extack)
1136 {
1137 	struct ice_dpll_pin *p = pin_priv, *target;
1138 	struct ice_dpll *d = dpll_priv;
1139 	enum ice_dpll_pin_type type;
1140 	struct ice_pf *pf = p->pf;
1141 	struct ice_hw *hw;
1142 	bool enable;
1143 	u8 data;
1144 	int ret;
1145 
1146 	if (ice_dpll_is_reset(pf, extack))
1147 		return -EBUSY;
1148 
1149 	mutex_lock(&pf->dplls.lock);
1150 	hw = &pf->hw;
1151 	ret = ice_read_sma_ctrl(hw, &data);
1152 	if (ret)
1153 		goto unlock;
1154 
1155 	ret = -EINVAL;
1156 	switch (p->idx) {
1157 	case ICE_DPLL_PIN_SW_1_IDX:
1158 		if (state == DPLL_PIN_STATE_CONNECTED) {
1159 			data &= ~ICE_SMA1_MASK;
1160 			enable = true;
1161 		} else if (state == DPLL_PIN_STATE_DISCONNECTED) {
1162 			data |= ICE_SMA1_TX_EN;
1163 			enable = false;
1164 		} else {
1165 			goto unlock;
1166 		}
1167 		target = p->output;
1168 		type = ICE_DPLL_PIN_TYPE_OUTPUT;
1169 		break;
1170 	case ICE_DPLL_PIN_SW_2_IDX:
1171 		if (state == DPLL_PIN_STATE_SELECTABLE) {
1172 			data |= ICE_SMA2_DIR_EN;
1173 			data &= ~ICE_SMA2_UFL2_RX_DIS;
1174 			enable = true;
1175 		} else if (state == DPLL_PIN_STATE_DISCONNECTED) {
1176 			data |= ICE_SMA2_UFL2_RX_DIS;
1177 			enable = false;
1178 		} else {
1179 			goto unlock;
1180 		}
1181 		target = p->input;
1182 		type = ICE_DPLL_PIN_TYPE_INPUT;
1183 		break;
1184 	default:
1185 		goto unlock;
1186 	}
1187 
1188 	ret = ice_write_sma_ctrl(hw, data);
1189 	if (ret)
1190 		goto unlock;
1191 	ret = ice_dpll_pin_state_update(pf, p, ICE_DPLL_PIN_TYPE_SOFTWARE,
1192 					extack);
1193 	if (ret)
1194 		goto unlock;
1195 
1196 	if (enable)
1197 		ret = ice_dpll_pin_enable(hw, target, d->dpll_idx, type, extack);
1198 	else
1199 		ret = ice_dpll_pin_disable(hw, target, type, extack);
1200 	if (!ret)
1201 		ret = ice_dpll_pin_state_update(pf, target, type, extack);
1202 
1203 unlock:
1204 	mutex_unlock(&pf->dplls.lock);
1205 
1206 	return ret;
1207 }
1208 
1209 /**
1210  * ice_dpll_sw_pin_state_get - get SW pin state
1211  * @pin: pointer to a pin
1212  * @pin_priv: private data pointer passed on pin registration
1213  * @dpll: registered dpll pointer
1214  * @dpll_priv: private data pointer passed on dpll registration
1215  * @state: on success holds state of the pin
1216  * @extack: error reporting
1217  *
1218  * Dpll subsystem callback. Check state of a SW pin.
1219  *
1220  * Context: Acquires and releases pf->dplls.lock
1221  * Return:
1222  * * 0 - success
1223  * * negative - error
1224  */
1225 static int
1226 ice_dpll_sw_pin_state_get(const struct dpll_pin *pin, void *pin_priv,
1227 			  const struct dpll_device *dpll, void *dpll_priv,
1228 			  enum dpll_pin_state *state,
1229 			  struct netlink_ext_ack *extack)
1230 {
1231 	struct ice_dpll_pin *p = pin_priv;
1232 	struct ice_dpll *d = dpll_priv;
1233 	struct ice_pf *pf = p->pf;
1234 	int ret = 0;
1235 
1236 	if (ice_dpll_is_reset(pf, extack))
1237 		return -EBUSY;
1238 	mutex_lock(&pf->dplls.lock);
1239 	if (!p->active) {
1240 		*state = DPLL_PIN_STATE_DISCONNECTED;
1241 		goto unlock;
1242 	}
1243 
1244 	if (p->direction == DPLL_PIN_DIRECTION_INPUT) {
1245 		ret = ice_dpll_pin_state_update(pf, p->input,
1246 						ICE_DPLL_PIN_TYPE_INPUT,
1247 						extack);
1248 		if (ret)
1249 			goto unlock;
1250 		*state = p->input->state[d->dpll_idx];
1251 	} else {
1252 		ret = ice_dpll_pin_state_update(pf, p->output,
1253 						ICE_DPLL_PIN_TYPE_OUTPUT,
1254 						extack);
1255 		if (ret)
1256 			goto unlock;
1257 		*state = p->output->state[d->dpll_idx];
1258 	}
1259 unlock:
1260 	mutex_unlock(&pf->dplls.lock);
1261 
1262 	return ret;
1263 }
1264 
1265 /**
1266  * ice_dpll_sma_pin_state_set - set SMA pin state on dpll device
1267  * @pin: pointer to a pin
1268  * @pin_priv: private data pointer passed on pin registration
1269  * @dpll: registered dpll pointer
1270  * @dpll_priv: private data pointer passed on dpll registration
1271  * @state: requested state of the pin
1272  * @extack: error reporting
1273  *
1274  * Dpll subsystem callback. Set state of a pin.
1275  *
1276  * Context: Acquires and releases pf->dplls.lock
1277  * Return:
1278  * * 0 - success
1279  * * negative - failed to get state
1280  */
1281 static int
1282 ice_dpll_sma_pin_state_set(const struct dpll_pin *pin, void *pin_priv,
1283 			   const struct dpll_device *dpll, void *dpll_priv,
1284 			   enum dpll_pin_state state,
1285 			   struct netlink_ext_ack *extack)
1286 {
1287 	struct ice_dpll_pin *sma = pin_priv, *target;
1288 	struct ice_dpll *d = dpll_priv;
1289 	struct ice_pf *pf = sma->pf;
1290 	enum ice_dpll_pin_type type;
1291 	bool enable;
1292 	int ret;
1293 
1294 	if (ice_dpll_is_reset(pf, extack))
1295 		return -EBUSY;
1296 
1297 	mutex_lock(&pf->dplls.lock);
1298 	if (!sma->active) {
1299 		ret = ice_dpll_sma_direction_set(sma, sma->direction, extack);
1300 		if (ret)
1301 			goto unlock;
1302 	}
1303 	if (sma->direction == DPLL_PIN_DIRECTION_INPUT) {
1304 		enable = state == DPLL_PIN_STATE_SELECTABLE;
1305 		target = sma->input;
1306 		type = ICE_DPLL_PIN_TYPE_INPUT;
1307 	} else {
1308 		enable = state == DPLL_PIN_STATE_CONNECTED;
1309 		target = sma->output;
1310 		type = ICE_DPLL_PIN_TYPE_OUTPUT;
1311 	}
1312 
1313 	if (enable)
1314 		ret = ice_dpll_pin_enable(&pf->hw, target, d->dpll_idx, type,
1315 					  extack);
1316 	else
1317 		ret = ice_dpll_pin_disable(&pf->hw, target, type, extack);
1318 	if (!ret)
1319 		ret = ice_dpll_pin_state_update(pf, target, type, extack);
1320 
1321 unlock:
1322 	mutex_unlock(&pf->dplls.lock);
1323 
1324 	return ret;
1325 }
1326 
1327 /**
1328  * ice_dpll_input_prio_get - get dpll's input prio
1329  * @pin: pointer to a pin
1330  * @pin_priv: private data pointer passed on pin registration
1331  * @dpll: registered dpll pointer
1332  * @dpll_priv: private data pointer passed on dpll registration
1333  * @prio: on success - returns input priority on dpll
1334  * @extack: error reporting
1335  *
1336  * Dpll subsystem callback. Handler for getting priority of a input pin.
1337  *
1338  * Context: Acquires pf->dplls.lock
1339  * Return:
1340  * * 0 - success
1341  * * negative - failure
1342  */
1343 static int
1344 ice_dpll_input_prio_get(const struct dpll_pin *pin, void *pin_priv,
1345 			const struct dpll_device *dpll, void *dpll_priv,
1346 			u32 *prio, struct netlink_ext_ack *extack)
1347 {
1348 	struct ice_dpll_pin *p = pin_priv;
1349 	struct ice_dpll *d = dpll_priv;
1350 	struct ice_pf *pf = d->pf;
1351 
1352 	mutex_lock(&pf->dplls.lock);
1353 	*prio = d->input_prio[p->idx];
1354 	mutex_unlock(&pf->dplls.lock);
1355 
1356 	return 0;
1357 }
1358 
1359 /**
1360  * ice_dpll_input_prio_set - set dpll input prio
1361  * @pin: pointer to a pin
1362  * @pin_priv: private data pointer passed on pin registration
1363  * @dpll: registered dpll pointer
1364  * @dpll_priv: private data pointer passed on dpll registration
1365  * @prio: input priority to be set on dpll
1366  * @extack: error reporting
1367  *
1368  * Dpll subsystem callback. Handler for setting priority of a input pin.
1369  *
1370  * Context: Acquires pf->dplls.lock
1371  * Return:
1372  * * 0 - success
1373  * * negative - failure
1374  */
1375 static int
1376 ice_dpll_input_prio_set(const struct dpll_pin *pin, void *pin_priv,
1377 			const struct dpll_device *dpll, void *dpll_priv,
1378 			u32 prio, struct netlink_ext_ack *extack)
1379 {
1380 	struct ice_dpll_pin *p = pin_priv;
1381 	struct ice_dpll *d = dpll_priv;
1382 	struct ice_pf *pf = d->pf;
1383 	int ret;
1384 
1385 	if (ice_dpll_is_reset(pf, extack))
1386 		return -EBUSY;
1387 
1388 	mutex_lock(&pf->dplls.lock);
1389 	ret = ice_dpll_hw_input_prio_set(pf, d, p, prio, extack);
1390 	mutex_unlock(&pf->dplls.lock);
1391 
1392 	return ret;
1393 }
1394 
1395 static int
1396 ice_dpll_sw_input_prio_get(const struct dpll_pin *pin, void *pin_priv,
1397 			   const struct dpll_device *dpll, void *dpll_priv,
1398 			   u32 *prio, struct netlink_ext_ack *extack)
1399 {
1400 	struct ice_dpll_pin *p = pin_priv;
1401 	struct ice_dpll *d = dpll_priv;
1402 	struct ice_pf *pf = d->pf;
1403 
1404 	mutex_lock(&pf->dplls.lock);
1405 	if (p->input && p->direction == DPLL_PIN_DIRECTION_INPUT)
1406 		*prio = d->input_prio[p->input->idx];
1407 	else
1408 		*prio = ICE_DPLL_PIN_PRIO_OUTPUT;
1409 	mutex_unlock(&pf->dplls.lock);
1410 
1411 	return 0;
1412 }
1413 
1414 static int
1415 ice_dpll_sw_input_prio_set(const struct dpll_pin *pin, void *pin_priv,
1416 			   const struct dpll_device *dpll, void *dpll_priv,
1417 			   u32 prio, struct netlink_ext_ack *extack)
1418 {
1419 	struct ice_dpll_pin *p = pin_priv;
1420 	struct ice_dpll *d = dpll_priv;
1421 	struct ice_pf *pf = d->pf;
1422 	int ret;
1423 
1424 	if (!p->input || p->direction != DPLL_PIN_DIRECTION_INPUT)
1425 		return -EINVAL;
1426 	if (ice_dpll_is_reset(pf, extack))
1427 		return -EBUSY;
1428 
1429 	mutex_lock(&pf->dplls.lock);
1430 	ret = ice_dpll_hw_input_prio_set(pf, d, p->input, prio, extack);
1431 	mutex_unlock(&pf->dplls.lock);
1432 
1433 	return ret;
1434 }
1435 
1436 /**
1437  * ice_dpll_input_direction - callback for get input pin direction
1438  * @pin: pointer to a pin
1439  * @pin_priv: private data pointer passed on pin registration
1440  * @dpll: registered dpll pointer
1441  * @dpll_priv: private data pointer passed on dpll registration
1442  * @direction: holds input pin direction
1443  * @extack: error reporting
1444  *
1445  * Dpll subsystem callback. Handler for getting direction of a input pin.
1446  *
1447  * Return:
1448  * * 0 - success
1449  */
1450 static int
1451 ice_dpll_input_direction(const struct dpll_pin *pin, void *pin_priv,
1452 			 const struct dpll_device *dpll, void *dpll_priv,
1453 			 enum dpll_pin_direction *direction,
1454 			 struct netlink_ext_ack *extack)
1455 {
1456 	*direction = DPLL_PIN_DIRECTION_INPUT;
1457 
1458 	return 0;
1459 }
1460 
1461 /**
1462  * ice_dpll_output_direction - callback for get output pin direction
1463  * @pin: pointer to a pin
1464  * @pin_priv: private data pointer passed on pin registration
1465  * @dpll: registered dpll pointer
1466  * @dpll_priv: private data pointer passed on dpll registration
1467  * @direction: holds output pin direction
1468  * @extack: error reporting
1469  *
1470  * Dpll subsystem callback. Handler for getting direction of an output pin.
1471  *
1472  * Return:
1473  * * 0 - success
1474  */
1475 static int
1476 ice_dpll_output_direction(const struct dpll_pin *pin, void *pin_priv,
1477 			  const struct dpll_device *dpll, void *dpll_priv,
1478 			  enum dpll_pin_direction *direction,
1479 			  struct netlink_ext_ack *extack)
1480 {
1481 	*direction = DPLL_PIN_DIRECTION_OUTPUT;
1482 
1483 	return 0;
1484 }
1485 
1486 /**
1487  * ice_dpll_pin_sma_direction_set - callback for set SMA pin direction
1488  * @pin: pointer to a pin
1489  * @pin_priv: private data pointer passed on pin registration
1490  * @dpll: registered dpll pointer
1491  * @dpll_priv: private data pointer passed on dpll registration
1492  * @direction: requested pin direction
1493  * @extack: error reporting
1494  *
1495  * Dpll subsystem callback. Handler for setting direction of a SMA pin.
1496  *
1497  * Context: Acquires and releases pf->dplls.lock
1498  * Return:
1499  * * 0 - success
1500  * * negative - error
1501  */
1502 static int
1503 ice_dpll_pin_sma_direction_set(const struct dpll_pin *pin, void *pin_priv,
1504 			       const struct dpll_device *dpll, void *dpll_priv,
1505 			       enum dpll_pin_direction direction,
1506 			       struct netlink_ext_ack *extack)
1507 {
1508 	struct ice_dpll_pin *p = pin_priv;
1509 	struct ice_pf *pf = p->pf;
1510 	int ret;
1511 
1512 	if (ice_dpll_is_reset(pf, extack))
1513 		return -EBUSY;
1514 
1515 	mutex_lock(&pf->dplls.lock);
1516 	ret = ice_dpll_sma_direction_set(p, direction, extack);
1517 	mutex_unlock(&pf->dplls.lock);
1518 
1519 	return ret;
1520 }
1521 
1522 /**
1523  * ice_dpll_pin_sw_direction_get - callback for get SW pin direction
1524  * @pin: pointer to a pin
1525  * @pin_priv: private data pointer passed on pin registration
1526  * @dpll: registered dpll pointer
1527  * @dpll_priv: private data pointer passed on dpll registration
1528  * @direction: on success holds pin direction
1529  * @extack: error reporting
1530  *
1531  * Dpll subsystem callback. Handler for getting direction of a SMA pin.
1532  *
1533  * Context: Acquires and releases pf->dplls.lock
1534  * Return:
1535  * * 0 - success
1536  * * negative - error
1537  */
1538 static int
1539 ice_dpll_pin_sw_direction_get(const struct dpll_pin *pin, void *pin_priv,
1540 			      const struct dpll_device *dpll, void *dpll_priv,
1541 			      enum dpll_pin_direction *direction,
1542 			      struct netlink_ext_ack *extack)
1543 {
1544 	struct ice_dpll_pin *p = pin_priv;
1545 	struct ice_pf *pf = p->pf;
1546 
1547 	if (ice_dpll_is_reset(pf, extack))
1548 		return -EBUSY;
1549 	mutex_lock(&pf->dplls.lock);
1550 	*direction = p->direction;
1551 	mutex_unlock(&pf->dplls.lock);
1552 
1553 	return 0;
1554 }
1555 
1556 /**
1557  * ice_dpll_pin_phase_adjust_get - callback for get pin phase adjust value
1558  * @pin: pointer to a pin
1559  * @pin_priv: private data pointer passed on pin registration
1560  * @dpll: registered dpll pointer
1561  * @dpll_priv: private data pointer passed on dpll registration
1562  * @phase_adjust: on success holds pin phase_adjust value
1563  * @extack: error reporting
1564  *
1565  * Dpll subsystem callback. Handler for getting phase adjust value of a pin.
1566  *
1567  * Context: Acquires pf->dplls.lock
1568  * Return:
1569  * * 0 - success
1570  * * negative - error
1571  */
1572 static int
1573 ice_dpll_pin_phase_adjust_get(const struct dpll_pin *pin, void *pin_priv,
1574 			      const struct dpll_device *dpll, void *dpll_priv,
1575 			      s32 *phase_adjust,
1576 			      struct netlink_ext_ack *extack)
1577 {
1578 	struct ice_dpll_pin *p = pin_priv;
1579 	struct ice_pf *pf = p->pf;
1580 
1581 	mutex_lock(&pf->dplls.lock);
1582 	*phase_adjust = p->phase_adjust;
1583 	mutex_unlock(&pf->dplls.lock);
1584 
1585 	return 0;
1586 }
1587 
1588 /**
1589  * ice_dpll_pin_phase_adjust_set - helper for setting a pin phase adjust value
1590  * @pin: pointer to a pin
1591  * @pin_priv: private data pointer passed on pin registration
1592  * @dpll: registered dpll pointer
1593  * @dpll_priv: private data pointer passed on dpll registration
1594  * @phase_adjust: phase_adjust to be set
1595  * @extack: error reporting
1596  * @type: type of a pin
1597  *
1598  * Helper for dpll subsystem callback. Handler for setting phase adjust value
1599  * of a pin.
1600  *
1601  * Context: Acquires pf->dplls.lock
1602  * Return:
1603  * * 0 - success
1604  * * negative - error
1605  */
1606 static int
1607 ice_dpll_pin_phase_adjust_set(const struct dpll_pin *pin, void *pin_priv,
1608 			      const struct dpll_device *dpll, void *dpll_priv,
1609 			      s32 phase_adjust,
1610 			      struct netlink_ext_ack *extack,
1611 			      enum ice_dpll_pin_type type)
1612 {
1613 	struct ice_dpll_pin *p = pin_priv;
1614 	struct ice_dpll *d = dpll_priv;
1615 	struct ice_pf *pf = d->pf;
1616 	u8 flag, flags_en = 0;
1617 	int ret;
1618 
1619 	if (ice_dpll_is_reset(pf, extack))
1620 		return -EBUSY;
1621 
1622 	mutex_lock(&pf->dplls.lock);
1623 	switch (type) {
1624 	case ICE_DPLL_PIN_TYPE_INPUT:
1625 		flag = ICE_AQC_SET_CGU_IN_CFG_FLG1_UPDATE_DELAY;
1626 		if (p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN)
1627 			flags_en |= ICE_AQC_SET_CGU_IN_CFG_FLG2_ESYNC_EN;
1628 		if (p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_INPUT_EN)
1629 			flags_en |= ICE_AQC_SET_CGU_IN_CFG_FLG2_INPUT_EN;
1630 		ret = ice_aq_set_input_pin_cfg(&pf->hw, p->idx, flag, flags_en,
1631 					       0, phase_adjust);
1632 		break;
1633 	case ICE_DPLL_PIN_TYPE_OUTPUT:
1634 		flag = ICE_AQC_SET_CGU_OUT_CFG_UPDATE_PHASE;
1635 		if (p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_OUT_EN)
1636 			flag |= ICE_AQC_SET_CGU_OUT_CFG_OUT_EN;
1637 		if (p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN)
1638 			flag |= ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN;
1639 		ret = ice_aq_set_output_pin_cfg(&pf->hw, p->idx, flag, 0, 0,
1640 						phase_adjust);
1641 		break;
1642 	default:
1643 		ret = -EINVAL;
1644 	}
1645 	if (!ret)
1646 		p->phase_adjust = phase_adjust;
1647 	mutex_unlock(&pf->dplls.lock);
1648 	if (ret)
1649 		NL_SET_ERR_MSG_FMT(extack,
1650 				   "err:%d %s failed to set pin phase_adjust:%d for pin:%u on dpll:%u",
1651 				   ret,
1652 				   ice_aq_str(pf->hw.adminq.sq_last_status),
1653 				   phase_adjust, p->idx, d->dpll_idx);
1654 
1655 	return ret;
1656 }
1657 
1658 /**
1659  * ice_dpll_input_phase_adjust_set - callback for set input pin phase adjust
1660  * @pin: pointer to a pin
1661  * @pin_priv: private data pointer passed on pin registration
1662  * @dpll: registered dpll pointer
1663  * @dpll_priv: private data pointer passed on dpll registration
1664  * @phase_adjust: phase_adjust to be set
1665  * @extack: error reporting
1666  *
1667  * Dpll subsystem callback. Wraps a handler for setting phase adjust on input
1668  * pin.
1669  *
1670  * Context: Calls a function which acquires and releases pf->dplls.lock
1671  * Return:
1672  * * 0 - success
1673  * * negative - error
1674  */
1675 static int
1676 ice_dpll_input_phase_adjust_set(const struct dpll_pin *pin, void *pin_priv,
1677 				const struct dpll_device *dpll, void *dpll_priv,
1678 				s32 phase_adjust,
1679 				struct netlink_ext_ack *extack)
1680 {
1681 	return ice_dpll_pin_phase_adjust_set(pin, pin_priv, dpll, dpll_priv,
1682 					     phase_adjust, extack,
1683 					     ICE_DPLL_PIN_TYPE_INPUT);
1684 }
1685 
1686 /**
1687  * ice_dpll_output_phase_adjust_set - callback for set output pin phase adjust
1688  * @pin: pointer to a pin
1689  * @pin_priv: private data pointer passed on pin registration
1690  * @dpll: registered dpll pointer
1691  * @dpll_priv: private data pointer passed on dpll registration
1692  * @phase_adjust: phase_adjust to be set
1693  * @extack: error reporting
1694  *
1695  * Dpll subsystem callback. Wraps a handler for setting phase adjust on output
1696  * pin.
1697  *
1698  * Context: Calls a function which acquires pf->dplls.lock
1699  * Return:
1700  * * 0 - success
1701  * * negative - error
1702  */
1703 static int
1704 ice_dpll_output_phase_adjust_set(const struct dpll_pin *pin, void *pin_priv,
1705 				 const struct dpll_device *dpll, void *dpll_priv,
1706 				 s32 phase_adjust,
1707 				 struct netlink_ext_ack *extack)
1708 {
1709 	return ice_dpll_pin_phase_adjust_set(pin, pin_priv, dpll, dpll_priv,
1710 					     phase_adjust, extack,
1711 					     ICE_DPLL_PIN_TYPE_OUTPUT);
1712 }
1713 
1714 /**
1715  * ice_dpll_sw_phase_adjust_get - callback for get SW pin phase adjust
1716  * @pin: pointer to a pin
1717  * @pin_priv: private data pointer passed on pin registration
1718  * @dpll: registered dpll pointer
1719  * @dpll_priv: private data pointer passed on dpll registration
1720  * @phase_adjust: on success holds phase adjust value
1721  * @extack: error reporting
1722  *
1723  * Dpll subsystem callback. Wraps a handler for getting phase adjust on sw
1724  * pin.
1725  *
1726  * Context: Calls a function which acquires and releases pf->dplls.lock
1727  * Return:
1728  * * 0 - success
1729  * * negative - error
1730  */
1731 static int
1732 ice_dpll_sw_phase_adjust_get(const struct dpll_pin *pin, void *pin_priv,
1733 			     const struct dpll_device *dpll, void *dpll_priv,
1734 			     s32 *phase_adjust,
1735 			     struct netlink_ext_ack *extack)
1736 {
1737 	struct ice_dpll_pin *p = pin_priv;
1738 
1739 	if (p->direction == DPLL_PIN_DIRECTION_INPUT)
1740 		return ice_dpll_pin_phase_adjust_get(p->input->pin, p->input,
1741 						     dpll, dpll_priv,
1742 						     phase_adjust, extack);
1743 	else
1744 		return ice_dpll_pin_phase_adjust_get(p->output->pin, p->output,
1745 						     dpll, dpll_priv,
1746 						     phase_adjust, extack);
1747 }
1748 
1749 /**
1750  * ice_dpll_sw_phase_adjust_set - callback for set SW pin phase adjust value
1751  * @pin: pointer to a pin
1752  * @pin_priv: private data pointer passed on pin registration
1753  * @dpll: registered dpll pointer
1754  * @dpll_priv: private data pointer passed on dpll registration
1755  * @phase_adjust: phase_adjust to be set
1756  * @extack: error reporting
1757  *
1758  * Dpll subsystem callback. Wraps a handler for setting phase adjust on output
1759  * pin.
1760  *
1761  * Context: Calls a function which acquires and releases pf->dplls.lock
1762  * Return:
1763  * * 0 - success
1764  * * negative - error
1765  */
1766 static int
1767 ice_dpll_sw_phase_adjust_set(const struct dpll_pin *pin, void *pin_priv,
1768 			     const struct dpll_device *dpll, void *dpll_priv,
1769 			     s32 phase_adjust,
1770 			     struct netlink_ext_ack *extack)
1771 {
1772 	struct ice_dpll_pin *p = pin_priv;
1773 
1774 	if (!p->active) {
1775 		NL_SET_ERR_MSG(extack, "pin is not active");
1776 		return -EINVAL;
1777 	}
1778 	if (p->direction == DPLL_PIN_DIRECTION_INPUT)
1779 		return ice_dpll_pin_phase_adjust_set(p->input->pin, p->input,
1780 						     dpll, dpll_priv,
1781 						     phase_adjust, extack,
1782 						     ICE_DPLL_PIN_TYPE_INPUT);
1783 	else
1784 		return ice_dpll_pin_phase_adjust_set(p->output->pin, p->output,
1785 						     dpll, dpll_priv,
1786 						     phase_adjust, extack,
1787 						     ICE_DPLL_PIN_TYPE_OUTPUT);
1788 }
1789 
1790 #define ICE_DPLL_PHASE_OFFSET_DIVIDER	100
1791 #define ICE_DPLL_PHASE_OFFSET_FACTOR		\
1792 	(DPLL_PHASE_OFFSET_DIVIDER / ICE_DPLL_PHASE_OFFSET_DIVIDER)
1793 /**
1794  * ice_dpll_phase_offset_get - callback for get dpll phase shift value
1795  * @pin: pointer to a pin
1796  * @pin_priv: private data pointer passed on pin registration
1797  * @dpll: registered dpll pointer
1798  * @dpll_priv: private data pointer passed on dpll registration
1799  * @phase_offset: on success holds pin phase_offset value
1800  * @extack: error reporting
1801  *
1802  * Dpll subsystem callback. Handler for getting phase shift value between
1803  * dpll's input and output.
1804  *
1805  * Context: Acquires pf->dplls.lock
1806  * Return:
1807  * * 0 - success
1808  * * negative - error
1809  */
1810 static int
1811 ice_dpll_phase_offset_get(const struct dpll_pin *pin, void *pin_priv,
1812 			  const struct dpll_device *dpll, void *dpll_priv,
1813 			  s64 *phase_offset, struct netlink_ext_ack *extack)
1814 {
1815 	struct ice_dpll_pin *p = pin_priv;
1816 	struct ice_dpll *d = dpll_priv;
1817 	struct ice_pf *pf = d->pf;
1818 
1819 	mutex_lock(&pf->dplls.lock);
1820 	if (d->active_input == pin || (p->input &&
1821 				       d->active_input == p->input->pin))
1822 		*phase_offset = d->phase_offset * ICE_DPLL_PHASE_OFFSET_FACTOR;
1823 	else if (d->phase_offset_monitor_period)
1824 		*phase_offset = p->phase_offset * ICE_DPLL_PHASE_OFFSET_FACTOR;
1825 	else
1826 		*phase_offset = 0;
1827 	mutex_unlock(&pf->dplls.lock);
1828 
1829 	return 0;
1830 }
1831 
1832 /**
1833  * ice_dpll_output_esync_set - callback for setting embedded sync
1834  * @pin: pointer to a pin
1835  * @pin_priv: private data pointer passed on pin registration
1836  * @dpll: registered dpll pointer
1837  * @dpll_priv: private data pointer passed on dpll registration
1838  * @freq: requested embedded sync frequency
1839  * @extack: error reporting
1840  *
1841  * Dpll subsystem callback. Handler for setting embedded sync frequency value
1842  * on output pin.
1843  *
1844  * Context: Acquires pf->dplls.lock
1845  * Return:
1846  * * 0 - success
1847  * * negative - error
1848  */
1849 static int
1850 ice_dpll_output_esync_set(const struct dpll_pin *pin, void *pin_priv,
1851 			  const struct dpll_device *dpll, void *dpll_priv,
1852 			  u64 freq, struct netlink_ext_ack *extack)
1853 {
1854 	struct ice_dpll_pin *p = pin_priv;
1855 	struct ice_dpll *d = dpll_priv;
1856 	struct ice_pf *pf = d->pf;
1857 	u8 flags = 0;
1858 	int ret;
1859 
1860 	if (ice_dpll_is_reset(pf, extack))
1861 		return -EBUSY;
1862 	mutex_lock(&pf->dplls.lock);
1863 	if (p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_OUT_EN)
1864 		flags = ICE_AQC_SET_CGU_OUT_CFG_OUT_EN;
1865 	if (freq == DPLL_PIN_FREQUENCY_1_HZ) {
1866 		if (p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN) {
1867 			ret = 0;
1868 		} else {
1869 			flags |= ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN;
1870 			ret = ice_aq_set_output_pin_cfg(&pf->hw, p->idx, flags,
1871 							0, 0, 0);
1872 		}
1873 	} else {
1874 		if (!(p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN)) {
1875 			ret = 0;
1876 		} else {
1877 			flags &= ~ICE_AQC_SET_CGU_OUT_CFG_ESYNC_EN;
1878 			ret = ice_aq_set_output_pin_cfg(&pf->hw, p->idx, flags,
1879 							0, 0, 0);
1880 		}
1881 	}
1882 	mutex_unlock(&pf->dplls.lock);
1883 
1884 	return ret;
1885 }
1886 
1887 /**
1888  * ice_dpll_output_esync_get - callback for getting embedded sync config
1889  * @pin: pointer to a pin
1890  * @pin_priv: private data pointer passed on pin registration
1891  * @dpll: registered dpll pointer
1892  * @dpll_priv: private data pointer passed on dpll registration
1893  * @esync: on success holds embedded sync pin properties
1894  * @extack: error reporting
1895  *
1896  * Dpll subsystem callback. Handler for getting embedded sync frequency value
1897  * and capabilities on output pin.
1898  *
1899  * Context: Acquires pf->dplls.lock
1900  * Return:
1901  * * 0 - success
1902  * * negative - error
1903  */
1904 static int
1905 ice_dpll_output_esync_get(const struct dpll_pin *pin, void *pin_priv,
1906 			  const struct dpll_device *dpll, void *dpll_priv,
1907 			  struct dpll_pin_esync *esync,
1908 			  struct netlink_ext_ack *extack)
1909 {
1910 	struct ice_dpll_pin *p = pin_priv;
1911 	struct ice_dpll *d = dpll_priv;
1912 	struct ice_pf *pf = d->pf;
1913 
1914 	if (ice_dpll_is_reset(pf, extack))
1915 		return -EBUSY;
1916 	mutex_lock(&pf->dplls.lock);
1917 	if (!(p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_ABILITY) ||
1918 	    p->freq != DPLL_PIN_FREQUENCY_10_MHZ) {
1919 		mutex_unlock(&pf->dplls.lock);
1920 		return -EOPNOTSUPP;
1921 	}
1922 	esync->range = ice_esync_range;
1923 	esync->range_num = ARRAY_SIZE(ice_esync_range);
1924 	if (p->flags[0] & ICE_AQC_GET_CGU_OUT_CFG_ESYNC_EN) {
1925 		esync->freq = DPLL_PIN_FREQUENCY_1_HZ;
1926 		esync->pulse = ICE_DPLL_PIN_ESYNC_PULSE_HIGH_PERCENT;
1927 	} else {
1928 		esync->freq = 0;
1929 		esync->pulse = 0;
1930 	}
1931 	mutex_unlock(&pf->dplls.lock);
1932 
1933 	return 0;
1934 }
1935 
1936 /**
1937  * ice_dpll_input_esync_set - callback for setting embedded sync
1938  * @pin: pointer to a pin
1939  * @pin_priv: private data pointer passed on pin registration
1940  * @dpll: registered dpll pointer
1941  * @dpll_priv: private data pointer passed on dpll registration
1942  * @freq: requested embedded sync frequency
1943  * @extack: error reporting
1944  *
1945  * Dpll subsystem callback. Handler for setting embedded sync frequency value
1946  * on input pin.
1947  *
1948  * Context: Acquires pf->dplls.lock
1949  * Return:
1950  * * 0 - success
1951  * * negative - error
1952  */
1953 static int
1954 ice_dpll_input_esync_set(const struct dpll_pin *pin, void *pin_priv,
1955 			 const struct dpll_device *dpll, void *dpll_priv,
1956 			 u64 freq, struct netlink_ext_ack *extack)
1957 {
1958 	struct ice_dpll_pin *p = pin_priv;
1959 	struct ice_dpll *d = dpll_priv;
1960 	struct ice_pf *pf = d->pf;
1961 	u8 flags_en = 0;
1962 	int ret;
1963 
1964 	if (ice_dpll_is_reset(pf, extack))
1965 		return -EBUSY;
1966 	mutex_lock(&pf->dplls.lock);
1967 	if (p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_INPUT_EN)
1968 		flags_en = ICE_AQC_SET_CGU_IN_CFG_FLG2_INPUT_EN;
1969 	if (freq == DPLL_PIN_FREQUENCY_1_HZ) {
1970 		if (p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN) {
1971 			ret = 0;
1972 		} else {
1973 			flags_en |= ICE_AQC_SET_CGU_IN_CFG_FLG2_ESYNC_EN;
1974 			ret = ice_aq_set_input_pin_cfg(&pf->hw, p->idx, 0,
1975 						       flags_en, 0, 0);
1976 		}
1977 	} else {
1978 		if (!(p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN)) {
1979 			ret = 0;
1980 		} else {
1981 			flags_en &= ~ICE_AQC_SET_CGU_IN_CFG_FLG2_ESYNC_EN;
1982 			ret = ice_aq_set_input_pin_cfg(&pf->hw, p->idx, 0,
1983 						       flags_en, 0, 0);
1984 		}
1985 	}
1986 	mutex_unlock(&pf->dplls.lock);
1987 
1988 	return ret;
1989 }
1990 
1991 /**
1992  * ice_dpll_input_esync_get - callback for getting embedded sync config
1993  * @pin: pointer to a pin
1994  * @pin_priv: private data pointer passed on pin registration
1995  * @dpll: registered dpll pointer
1996  * @dpll_priv: private data pointer passed on dpll registration
1997  * @esync: on success holds embedded sync pin properties
1998  * @extack: error reporting
1999  *
2000  * Dpll subsystem callback. Handler for getting embedded sync frequency value
2001  * and capabilities on input pin.
2002  *
2003  * Context: Acquires pf->dplls.lock
2004  * Return:
2005  * * 0 - success
2006  * * negative - error
2007  */
2008 static int
2009 ice_dpll_input_esync_get(const struct dpll_pin *pin, void *pin_priv,
2010 			 const struct dpll_device *dpll, void *dpll_priv,
2011 			 struct dpll_pin_esync *esync,
2012 			 struct netlink_ext_ack *extack)
2013 {
2014 	struct ice_dpll_pin *p = pin_priv;
2015 	struct ice_dpll *d = dpll_priv;
2016 	struct ice_pf *pf = d->pf;
2017 
2018 	if (ice_dpll_is_reset(pf, extack))
2019 		return -EBUSY;
2020 	mutex_lock(&pf->dplls.lock);
2021 	if (!(p->status & ICE_AQC_GET_CGU_IN_CFG_STATUS_ESYNC_CAP) ||
2022 	    p->freq != DPLL_PIN_FREQUENCY_10_MHZ) {
2023 		mutex_unlock(&pf->dplls.lock);
2024 		return -EOPNOTSUPP;
2025 	}
2026 	esync->range = ice_esync_range;
2027 	esync->range_num = ARRAY_SIZE(ice_esync_range);
2028 	if (p->flags[0] & ICE_AQC_GET_CGU_IN_CFG_FLG2_ESYNC_EN) {
2029 		esync->freq = DPLL_PIN_FREQUENCY_1_HZ;
2030 		esync->pulse = ICE_DPLL_PIN_ESYNC_PULSE_HIGH_PERCENT;
2031 	} else {
2032 		esync->freq = 0;
2033 		esync->pulse = 0;
2034 	}
2035 	mutex_unlock(&pf->dplls.lock);
2036 
2037 	return 0;
2038 }
2039 
2040 /**
2041  * ice_dpll_sw_esync_set - callback for setting embedded sync on SW pin
2042  * @pin: pointer to a pin
2043  * @pin_priv: private data pointer passed on pin registration
2044  * @dpll: registered dpll pointer
2045  * @dpll_priv: private data pointer passed on dpll registration
2046  * @freq: requested embedded sync frequency
2047  * @extack: error reporting
2048  *
2049  * Dpll subsystem callback. Handler for setting embedded sync frequency value
2050  * on SW pin.
2051  *
2052  * Context: Calls a function which acquires and releases pf->dplls.lock
2053  * Return:
2054  * * 0 - success
2055  * * negative - error
2056  */
2057 static int
2058 ice_dpll_sw_esync_set(const struct dpll_pin *pin, void *pin_priv,
2059 		      const struct dpll_device *dpll, void *dpll_priv,
2060 		      u64 freq, struct netlink_ext_ack *extack)
2061 {
2062 	struct ice_dpll_pin *p = pin_priv;
2063 
2064 	if (!p->active) {
2065 		NL_SET_ERR_MSG(extack, "pin is not active");
2066 		return -EINVAL;
2067 	}
2068 	if (p->direction == DPLL_PIN_DIRECTION_INPUT)
2069 		return ice_dpll_input_esync_set(p->input->pin, p->input, dpll,
2070 						dpll_priv, freq, extack);
2071 	else
2072 		return ice_dpll_output_esync_set(p->output->pin, p->output,
2073 						 dpll, dpll_priv, freq, extack);
2074 }
2075 
2076 /**
2077  * ice_dpll_sw_esync_get - callback for getting embedded sync on SW pin
2078  * @pin: pointer to a pin
2079  * @pin_priv: private data pointer passed on pin registration
2080  * @dpll: registered dpll pointer
2081  * @dpll_priv: private data pointer passed on dpll registration
2082  * @esync: on success holds embedded sync frequency and properties
2083  * @extack: error reporting
2084  *
2085  * Dpll subsystem callback. Handler for getting embedded sync frequency value
2086  * of SW pin.
2087  *
2088  * Context: Calls a function which acquires and releases pf->dplls.lock
2089  * Return:
2090  * * 0 - success
2091  * * negative - error
2092  */
2093 static int
2094 ice_dpll_sw_esync_get(const struct dpll_pin *pin, void *pin_priv,
2095 		      const struct dpll_device *dpll, void *dpll_priv,
2096 		      struct dpll_pin_esync *esync,
2097 		      struct netlink_ext_ack *extack)
2098 {
2099 	struct ice_dpll_pin *p = pin_priv;
2100 
2101 	if (p->direction == DPLL_PIN_DIRECTION_INPUT)
2102 		return ice_dpll_input_esync_get(p->input->pin, p->input, dpll,
2103 						dpll_priv, esync, extack);
2104 	else
2105 		return ice_dpll_output_esync_get(p->output->pin, p->output,
2106 						 dpll, dpll_priv, esync,
2107 						 extack);
2108 }
2109 
2110 /**
2111  * ice_dpll_rclk_state_on_pin_set - set a state on rclk pin
2112  * @pin: pointer to a pin
2113  * @pin_priv: private data pointer passed on pin registration
2114  * @parent_pin: pin parent pointer
2115  * @parent_pin_priv: parent private data pointer passed on pin registration
2116  * @state: state to be set on pin
2117  * @extack: error reporting
2118  *
2119  * Dpll subsystem callback, set a state of a rclk pin on a parent pin
2120  *
2121  * Context: Acquires pf->dplls.lock
2122  * Return:
2123  * * 0 - success
2124  * * negative - failure
2125  */
2126 static int
2127 ice_dpll_rclk_state_on_pin_set(const struct dpll_pin *pin, void *pin_priv,
2128 			       const struct dpll_pin *parent_pin,
2129 			       void *parent_pin_priv,
2130 			       enum dpll_pin_state state,
2131 			       struct netlink_ext_ack *extack)
2132 {
2133 	struct ice_dpll_pin *p = pin_priv, *parent = parent_pin_priv;
2134 	bool enable = state == DPLL_PIN_STATE_CONNECTED;
2135 	struct ice_pf *pf = p->pf;
2136 	int ret = -EINVAL;
2137 	u32 hw_idx;
2138 
2139 	if (ice_dpll_is_reset(pf, extack))
2140 		return -EBUSY;
2141 
2142 	mutex_lock(&pf->dplls.lock);
2143 	hw_idx = parent->idx - pf->dplls.base_rclk_idx;
2144 	if (hw_idx >= pf->dplls.num_inputs)
2145 		goto unlock;
2146 
2147 	if ((enable && p->state[hw_idx] == DPLL_PIN_STATE_CONNECTED) ||
2148 	    (!enable && p->state[hw_idx] == DPLL_PIN_STATE_DISCONNECTED)) {
2149 		NL_SET_ERR_MSG_FMT(extack,
2150 				   "pin:%u state:%u on parent:%u already set",
2151 				   p->idx, state, parent->idx);
2152 		goto unlock;
2153 	}
2154 	ret = ice_aq_set_phy_rec_clk_out(&pf->hw, hw_idx, enable,
2155 					 &p->freq);
2156 	if (ret)
2157 		NL_SET_ERR_MSG_FMT(extack,
2158 				   "err:%d %s failed to set pin state:%u for pin:%u on parent:%u",
2159 				   ret,
2160 				   ice_aq_str(pf->hw.adminq.sq_last_status),
2161 				   state, p->idx, parent->idx);
2162 unlock:
2163 	mutex_unlock(&pf->dplls.lock);
2164 
2165 	return ret;
2166 }
2167 
2168 /**
2169  * ice_dpll_rclk_state_on_pin_get - get a state of rclk pin
2170  * @pin: pointer to a pin
2171  * @pin_priv: private data pointer passed on pin registration
2172  * @parent_pin: pin parent pointer
2173  * @parent_pin_priv: pin parent priv data pointer passed on pin registration
2174  * @state: on success holds pin state on parent pin
2175  * @extack: error reporting
2176  *
2177  * dpll subsystem callback, get a state of a recovered clock pin.
2178  *
2179  * Context: Acquires pf->dplls.lock
2180  * Return:
2181  * * 0 - success
2182  * * negative - failure
2183  */
2184 static int
2185 ice_dpll_rclk_state_on_pin_get(const struct dpll_pin *pin, void *pin_priv,
2186 			       const struct dpll_pin *parent_pin,
2187 			       void *parent_pin_priv,
2188 			       enum dpll_pin_state *state,
2189 			       struct netlink_ext_ack *extack)
2190 {
2191 	struct ice_dpll_pin *p = pin_priv, *parent = parent_pin_priv;
2192 	struct ice_pf *pf = p->pf;
2193 	int ret = -EINVAL;
2194 	u32 hw_idx;
2195 
2196 	if (ice_dpll_is_reset(pf, extack))
2197 		return -EBUSY;
2198 
2199 	mutex_lock(&pf->dplls.lock);
2200 	hw_idx = parent->idx - pf->dplls.base_rclk_idx;
2201 	if (hw_idx >= pf->dplls.num_inputs)
2202 		goto unlock;
2203 
2204 	ret = ice_dpll_pin_state_update(pf, p, ICE_DPLL_PIN_TYPE_RCLK_INPUT,
2205 					extack);
2206 	if (ret)
2207 		goto unlock;
2208 
2209 	*state = p->state[hw_idx];
2210 	ret = 0;
2211 unlock:
2212 	mutex_unlock(&pf->dplls.lock);
2213 
2214 	return ret;
2215 }
2216 
2217 static const struct dpll_pin_ops ice_dpll_rclk_ops = {
2218 	.state_on_pin_set = ice_dpll_rclk_state_on_pin_set,
2219 	.state_on_pin_get = ice_dpll_rclk_state_on_pin_get,
2220 	.direction_get = ice_dpll_input_direction,
2221 };
2222 
2223 static const struct dpll_pin_ops ice_dpll_pin_sma_ops = {
2224 	.state_on_dpll_set = ice_dpll_sma_pin_state_set,
2225 	.state_on_dpll_get = ice_dpll_sw_pin_state_get,
2226 	.direction_get = ice_dpll_pin_sw_direction_get,
2227 	.direction_set = ice_dpll_pin_sma_direction_set,
2228 	.prio_get = ice_dpll_sw_input_prio_get,
2229 	.prio_set = ice_dpll_sw_input_prio_set,
2230 	.frequency_get = ice_dpll_sw_pin_frequency_get,
2231 	.frequency_set = ice_dpll_sw_pin_frequency_set,
2232 	.phase_adjust_get = ice_dpll_sw_phase_adjust_get,
2233 	.phase_adjust_set = ice_dpll_sw_phase_adjust_set,
2234 	.phase_offset_get = ice_dpll_phase_offset_get,
2235 	.esync_set = ice_dpll_sw_esync_set,
2236 	.esync_get = ice_dpll_sw_esync_get,
2237 };
2238 
2239 static const struct dpll_pin_ops ice_dpll_pin_ufl_ops = {
2240 	.state_on_dpll_set = ice_dpll_ufl_pin_state_set,
2241 	.state_on_dpll_get = ice_dpll_sw_pin_state_get,
2242 	.direction_get = ice_dpll_pin_sw_direction_get,
2243 	.frequency_get = ice_dpll_sw_pin_frequency_get,
2244 	.frequency_set = ice_dpll_sw_pin_frequency_set,
2245 	.esync_set = ice_dpll_sw_esync_set,
2246 	.esync_get = ice_dpll_sw_esync_get,
2247 	.phase_adjust_get = ice_dpll_sw_phase_adjust_get,
2248 	.phase_adjust_set = ice_dpll_sw_phase_adjust_set,
2249 	.phase_offset_get = ice_dpll_phase_offset_get,
2250 };
2251 
2252 static const struct dpll_pin_ops ice_dpll_input_ops = {
2253 	.frequency_get = ice_dpll_input_frequency_get,
2254 	.frequency_set = ice_dpll_input_frequency_set,
2255 	.state_on_dpll_get = ice_dpll_input_state_get,
2256 	.state_on_dpll_set = ice_dpll_input_state_set,
2257 	.prio_get = ice_dpll_input_prio_get,
2258 	.prio_set = ice_dpll_input_prio_set,
2259 	.direction_get = ice_dpll_input_direction,
2260 	.phase_adjust_get = ice_dpll_pin_phase_adjust_get,
2261 	.phase_adjust_set = ice_dpll_input_phase_adjust_set,
2262 	.phase_offset_get = ice_dpll_phase_offset_get,
2263 	.esync_set = ice_dpll_input_esync_set,
2264 	.esync_get = ice_dpll_input_esync_get,
2265 };
2266 
2267 static const struct dpll_pin_ops ice_dpll_output_ops = {
2268 	.frequency_get = ice_dpll_output_frequency_get,
2269 	.frequency_set = ice_dpll_output_frequency_set,
2270 	.state_on_dpll_get = ice_dpll_output_state_get,
2271 	.state_on_dpll_set = ice_dpll_output_state_set,
2272 	.direction_get = ice_dpll_output_direction,
2273 	.phase_adjust_get = ice_dpll_pin_phase_adjust_get,
2274 	.phase_adjust_set = ice_dpll_output_phase_adjust_set,
2275 	.esync_set = ice_dpll_output_esync_set,
2276 	.esync_get = ice_dpll_output_esync_get,
2277 };
2278 
2279 static const struct dpll_device_ops ice_dpll_ops = {
2280 	.lock_status_get = ice_dpll_lock_status_get,
2281 	.mode_get = ice_dpll_mode_get,
2282 };
2283 
2284 static const struct dpll_device_ops ice_dpll_pom_ops = {
2285 	.lock_status_get = ice_dpll_lock_status_get,
2286 	.mode_get = ice_dpll_mode_get,
2287 	.phase_offset_monitor_set = ice_dpll_phase_offset_monitor_set,
2288 	.phase_offset_monitor_get = ice_dpll_phase_offset_monitor_get,
2289 };
2290 
2291 /**
2292  * ice_generate_clock_id - generates unique clock_id for registering dpll.
2293  * @pf: board private structure
2294  *
2295  * Generates unique (per board) clock_id for allocation and search of dpll
2296  * devices in Linux dpll subsystem.
2297  *
2298  * Return: generated clock id for the board
2299  */
2300 static u64 ice_generate_clock_id(struct ice_pf *pf)
2301 {
2302 	return pci_get_dsn(pf->pdev);
2303 }
2304 
2305 /**
2306  * ice_dpll_notify_changes - notify dpll subsystem about changes
2307  * @d: pointer do dpll
2308  *
2309  * Once change detected appropriate event is submitted to the dpll subsystem.
2310  */
2311 static void ice_dpll_notify_changes(struct ice_dpll *d)
2312 {
2313 	bool pin_notified = false;
2314 
2315 	if (d->prev_dpll_state != d->dpll_state) {
2316 		d->prev_dpll_state = d->dpll_state;
2317 		dpll_device_change_ntf(d->dpll);
2318 	}
2319 	if (d->prev_input != d->active_input) {
2320 		if (d->prev_input)
2321 			dpll_pin_change_ntf(d->prev_input);
2322 		d->prev_input = d->active_input;
2323 		if (d->active_input) {
2324 			dpll_pin_change_ntf(d->active_input);
2325 			pin_notified = true;
2326 		}
2327 	}
2328 	if (d->prev_phase_offset != d->phase_offset) {
2329 		d->prev_phase_offset = d->phase_offset;
2330 		if (!pin_notified && d->active_input)
2331 			dpll_pin_change_ntf(d->active_input);
2332 	}
2333 }
2334 
2335 /**
2336  * ice_dpll_is_pps_phase_monitor - check if dpll capable of phase offset monitor
2337  * @pf: pf private structure
2338  *
2339  * Check if firmware is capable of supporting admin command to provide
2340  * phase offset monitoring on all the input pins on PPS dpll.
2341  *
2342  * Returns:
2343  * * true - PPS dpll phase offset monitoring is supported
2344  * * false - PPS dpll phase offset monitoring is not supported
2345  */
2346 static bool ice_dpll_is_pps_phase_monitor(struct ice_pf *pf)
2347 {
2348 	struct ice_cgu_input_measure meas[ICE_DPLL_INPUT_REF_NUM];
2349 	int ret = ice_aq_get_cgu_input_pin_measure(&pf->hw, DPLL_TYPE_PPS, meas,
2350 						   ARRAY_SIZE(meas));
2351 
2352 	if (ret && pf->hw.adminq.sq_last_status == ICE_AQ_RC_ESRCH)
2353 		return false;
2354 
2355 	return true;
2356 }
2357 
2358 /**
2359  * ice_dpll_pins_notify_mask - notify dpll subsystem about bulk pin changes
2360  * @pins: array of ice_dpll_pin pointers registered within dpll subsystem
2361  * @pin_num: number of pins
2362  * @phase_offset_ntf_mask: bitmask of pin indexes to notify
2363  *
2364  * Iterate over array of pins and call dpll subsystem pin notify if
2365  * corresponding pin index within bitmask is set.
2366  *
2367  * Context: Must be called while pf->dplls.lock is released.
2368  */
2369 static void ice_dpll_pins_notify_mask(struct ice_dpll_pin *pins,
2370 				      u8 pin_num,
2371 				      u32 phase_offset_ntf_mask)
2372 {
2373 	int i = 0;
2374 
2375 	for (i = 0; i < pin_num; i++)
2376 		if (phase_offset_ntf_mask & (1 << i))
2377 			dpll_pin_change_ntf(pins[i].pin);
2378 }
2379 
2380 /**
2381  * ice_dpll_pps_update_phase_offsets - update phase offset measurements
2382  * @pf: pf private structure
2383  * @phase_offset_pins_updated: returns mask of updated input pin indexes
2384  *
2385  * Read phase offset measurements for PPS dpll device and store values in
2386  * input pins array. On success phase_offset_pins_updated - fills bitmask of
2387  * updated input pin indexes, pins shall be notified.
2388  *
2389  * Context: Shall be called with pf->dplls.lock being locked.
2390  * Returns:
2391  * * 0 - success or no data available
2392  * * negative - AQ failure
2393  */
2394 static int ice_dpll_pps_update_phase_offsets(struct ice_pf *pf,
2395 					     u32 *phase_offset_pins_updated)
2396 {
2397 	struct ice_cgu_input_measure meas[ICE_DPLL_INPUT_REF_NUM];
2398 	struct ice_dpll_pin *p;
2399 	s64 phase_offset, tmp;
2400 	int i, j, ret;
2401 
2402 	*phase_offset_pins_updated = 0;
2403 	ret = ice_aq_get_cgu_input_pin_measure(&pf->hw, DPLL_TYPE_PPS, meas,
2404 					       ARRAY_SIZE(meas));
2405 	if (ret && pf->hw.adminq.sq_last_status == ICE_AQ_RC_EAGAIN) {
2406 		return 0;
2407 	} else if (ret) {
2408 		dev_err(ice_pf_to_dev(pf),
2409 			"failed to get input pin measurements dpll=%d, ret=%d %s\n",
2410 			DPLL_TYPE_PPS, ret,
2411 			ice_aq_str(pf->hw.adminq.sq_last_status));
2412 		return ret;
2413 	}
2414 	for (i = 0; i < pf->dplls.num_inputs; i++) {
2415 		p = &pf->dplls.inputs[i];
2416 		phase_offset = 0;
2417 		for (j = 0; j < ICE_CGU_INPUT_PHASE_OFFSET_BYTES; j++) {
2418 			tmp = meas[i].phase_offset[j];
2419 #ifdef __LITTLE_ENDIAN
2420 			phase_offset += tmp << 8 * j;
2421 #else
2422 			phase_offset += tmp << 8 *
2423 				(ICE_CGU_INPUT_PHASE_OFFSET_BYTES - 1 - j);
2424 #endif
2425 		}
2426 		phase_offset = sign_extend64(phase_offset, 47);
2427 		if (p->phase_offset != phase_offset) {
2428 			dev_dbg(ice_pf_to_dev(pf),
2429 				"phase offset changed for pin:%d old:%llx, new:%llx\n",
2430 				p->idx, p->phase_offset, phase_offset);
2431 			p->phase_offset = phase_offset;
2432 			*phase_offset_pins_updated |= (1 << i);
2433 		}
2434 	}
2435 
2436 	return 0;
2437 }
2438 
2439 /**
2440  * ice_dpll_update_state - update dpll state
2441  * @pf: pf private structure
2442  * @d: pointer to queried dpll device
2443  * @init: if function called on initialization of ice dpll
2444  *
2445  * Poll current state of dpll from hw and update ice_dpll struct.
2446  *
2447  * Context: Called by kworker under pf->dplls.lock
2448  * Return:
2449  * * 0 - success
2450  * * negative - AQ failure
2451  */
2452 static int
2453 ice_dpll_update_state(struct ice_pf *pf, struct ice_dpll *d, bool init)
2454 {
2455 	struct ice_dpll_pin *p = NULL;
2456 	int ret;
2457 
2458 	ret = ice_get_cgu_state(&pf->hw, d->dpll_idx, d->prev_dpll_state,
2459 				&d->input_idx, &d->ref_state, &d->eec_mode,
2460 				&d->phase_offset, &d->dpll_state);
2461 
2462 	dev_dbg(ice_pf_to_dev(pf),
2463 		"update dpll=%d, prev_src_idx:%u, src_idx:%u, state:%d, prev:%d mode:%d\n",
2464 		d->dpll_idx, d->prev_input_idx, d->input_idx,
2465 		d->dpll_state, d->prev_dpll_state, d->mode);
2466 	if (ret) {
2467 		dev_err(ice_pf_to_dev(pf),
2468 			"update dpll=%d state failed, ret=%d %s\n",
2469 			d->dpll_idx, ret,
2470 			ice_aq_str(pf->hw.adminq.sq_last_status));
2471 		return ret;
2472 	}
2473 	if (init) {
2474 		if (d->dpll_state == DPLL_LOCK_STATUS_LOCKED ||
2475 		    d->dpll_state == DPLL_LOCK_STATUS_LOCKED_HO_ACQ)
2476 			d->active_input = pf->dplls.inputs[d->input_idx].pin;
2477 		p = &pf->dplls.inputs[d->input_idx];
2478 		return ice_dpll_pin_state_update(pf, p,
2479 						 ICE_DPLL_PIN_TYPE_INPUT, NULL);
2480 	}
2481 	if (d->dpll_state == DPLL_LOCK_STATUS_HOLDOVER ||
2482 	    d->dpll_state == DPLL_LOCK_STATUS_UNLOCKED) {
2483 		d->active_input = NULL;
2484 		if (d->input_idx != ICE_DPLL_PIN_IDX_INVALID)
2485 			p = &pf->dplls.inputs[d->input_idx];
2486 		d->prev_input_idx = ICE_DPLL_PIN_IDX_INVALID;
2487 		d->input_idx = ICE_DPLL_PIN_IDX_INVALID;
2488 		if (!p)
2489 			return 0;
2490 		ret = ice_dpll_pin_state_update(pf, p,
2491 						ICE_DPLL_PIN_TYPE_INPUT, NULL);
2492 	} else if (d->input_idx != d->prev_input_idx) {
2493 		if (d->prev_input_idx != ICE_DPLL_PIN_IDX_INVALID) {
2494 			p = &pf->dplls.inputs[d->prev_input_idx];
2495 			ice_dpll_pin_state_update(pf, p,
2496 						  ICE_DPLL_PIN_TYPE_INPUT,
2497 						  NULL);
2498 		}
2499 		if (d->input_idx != ICE_DPLL_PIN_IDX_INVALID) {
2500 			p = &pf->dplls.inputs[d->input_idx];
2501 			d->active_input = p->pin;
2502 			ice_dpll_pin_state_update(pf, p,
2503 						  ICE_DPLL_PIN_TYPE_INPUT,
2504 						  NULL);
2505 		}
2506 		d->prev_input_idx = d->input_idx;
2507 	}
2508 
2509 	return ret;
2510 }
2511 
2512 /**
2513  * ice_dpll_periodic_work - DPLLs periodic worker
2514  * @work: pointer to kthread_work structure
2515  *
2516  * DPLLs periodic worker is responsible for polling state of dpll.
2517  * Context: Holds pf->dplls.lock
2518  */
2519 static void ice_dpll_periodic_work(struct kthread_work *work)
2520 {
2521 	struct ice_dplls *d = container_of(work, struct ice_dplls, work.work);
2522 	struct ice_pf *pf = container_of(d, struct ice_pf, dplls);
2523 	struct ice_dpll *de = &pf->dplls.eec;
2524 	struct ice_dpll *dp = &pf->dplls.pps;
2525 	u32 phase_offset_ntf = 0;
2526 	int ret = 0;
2527 
2528 	if (ice_is_reset_in_progress(pf->state))
2529 		goto resched;
2530 	mutex_lock(&pf->dplls.lock);
2531 	d->periodic_counter++;
2532 	ret = ice_dpll_update_state(pf, de, false);
2533 	if (!ret)
2534 		ret = ice_dpll_update_state(pf, dp, false);
2535 	if (!ret && dp->phase_offset_monitor_period &&
2536 	    d->periodic_counter % dp->phase_offset_monitor_period == 0)
2537 		ret = ice_dpll_pps_update_phase_offsets(pf, &phase_offset_ntf);
2538 	if (ret) {
2539 		d->cgu_state_acq_err_num++;
2540 		/* stop rescheduling this worker */
2541 		if (d->cgu_state_acq_err_num >
2542 		    ICE_CGU_STATE_ACQ_ERR_THRESHOLD) {
2543 			dev_err(ice_pf_to_dev(pf),
2544 				"EEC/PPS DPLLs periodic work disabled\n");
2545 			mutex_unlock(&pf->dplls.lock);
2546 			return;
2547 		}
2548 	}
2549 	mutex_unlock(&pf->dplls.lock);
2550 	ice_dpll_notify_changes(de);
2551 	ice_dpll_notify_changes(dp);
2552 	if (phase_offset_ntf)
2553 		ice_dpll_pins_notify_mask(d->inputs, d->num_inputs,
2554 					  phase_offset_ntf);
2555 
2556 resched:
2557 	/* Run twice a second or reschedule if update failed */
2558 	kthread_queue_delayed_work(d->kworker, &d->work,
2559 				   ret ? msecs_to_jiffies(10) :
2560 				   msecs_to_jiffies(500));
2561 }
2562 
2563 /**
2564  * ice_dpll_release_pins - release pins resources from dpll subsystem
2565  * @pins: pointer to pins array
2566  * @count: number of pins
2567  *
2568  * Release resources of given pins array in the dpll subsystem.
2569  */
2570 static void ice_dpll_release_pins(struct ice_dpll_pin *pins, int count)
2571 {
2572 	int i;
2573 
2574 	for (i = 0; i < count; i++)
2575 		dpll_pin_put(pins[i].pin);
2576 }
2577 
2578 /**
2579  * ice_dpll_get_pins - get pins from dpll subsystem
2580  * @pf: board private structure
2581  * @pins: pointer to pins array
2582  * @start_idx: get starts from this pin idx value
2583  * @count: number of pins
2584  * @clock_id: clock_id of dpll device
2585  *
2586  * Get pins - allocate - in dpll subsystem, store them in pin field of given
2587  * pins array.
2588  *
2589  * Return:
2590  * * 0 - success
2591  * * negative - allocation failure reason
2592  */
2593 static int
2594 ice_dpll_get_pins(struct ice_pf *pf, struct ice_dpll_pin *pins,
2595 		  int start_idx, int count, u64 clock_id)
2596 {
2597 	int i, ret;
2598 
2599 	for (i = 0; i < count; i++) {
2600 		pins[i].pin = dpll_pin_get(clock_id, i + start_idx, THIS_MODULE,
2601 					   &pins[i].prop);
2602 		if (IS_ERR(pins[i].pin)) {
2603 			ret = PTR_ERR(pins[i].pin);
2604 			goto release_pins;
2605 		}
2606 	}
2607 
2608 	return 0;
2609 
2610 release_pins:
2611 	while (--i >= 0)
2612 		dpll_pin_put(pins[i].pin);
2613 	return ret;
2614 }
2615 
2616 /**
2617  * ice_dpll_unregister_pins - unregister pins from a dpll
2618  * @dpll: dpll device pointer
2619  * @pins: pointer to pins array
2620  * @ops: callback ops registered with the pins
2621  * @count: number of pins
2622  *
2623  * Unregister pins of a given array of pins from given dpll device registered in
2624  * dpll subsystem.
2625  */
2626 static void
2627 ice_dpll_unregister_pins(struct dpll_device *dpll, struct ice_dpll_pin *pins,
2628 			 const struct dpll_pin_ops *ops, int count)
2629 {
2630 	int i;
2631 
2632 	for (i = 0; i < count; i++)
2633 		if (!pins[i].hidden)
2634 			dpll_pin_unregister(dpll, pins[i].pin, ops, &pins[i]);
2635 }
2636 
2637 /**
2638  * ice_dpll_register_pins - register pins with a dpll
2639  * @dpll: dpll pointer to register pins with
2640  * @pins: pointer to pins array
2641  * @ops: callback ops registered with the pins
2642  * @count: number of pins
2643  *
2644  * Register pins of a given array with given dpll in dpll subsystem.
2645  *
2646  * Return:
2647  * * 0 - success
2648  * * negative - registration failure reason
2649  */
2650 static int
2651 ice_dpll_register_pins(struct dpll_device *dpll, struct ice_dpll_pin *pins,
2652 		       const struct dpll_pin_ops *ops, int count)
2653 {
2654 	int ret, i;
2655 
2656 	for (i = 0; i < count; i++) {
2657 		if (!pins[i].hidden) {
2658 			ret = dpll_pin_register(dpll, pins[i].pin, ops, &pins[i]);
2659 			if (ret)
2660 				goto unregister_pins;
2661 		}
2662 	}
2663 
2664 	return 0;
2665 
2666 unregister_pins:
2667 	while (--i >= 0)
2668 		if (!pins[i].hidden)
2669 			dpll_pin_unregister(dpll, pins[i].pin, ops, &pins[i]);
2670 	return ret;
2671 }
2672 
2673 /**
2674  * ice_dpll_deinit_direct_pins - deinitialize direct pins
2675  * @cgu: if cgu is present and controlled by this NIC
2676  * @pins: pointer to pins array
2677  * @count: number of pins
2678  * @ops: callback ops registered with the pins
2679  * @first: dpll device pointer
2680  * @second: dpll device pointer
2681  *
2682  * If cgu is owned unregister pins from given dplls.
2683  * Release pins resources to the dpll subsystem.
2684  */
2685 static void
2686 ice_dpll_deinit_direct_pins(bool cgu, struct ice_dpll_pin *pins, int count,
2687 			    const struct dpll_pin_ops *ops,
2688 			    struct dpll_device *first,
2689 			    struct dpll_device *second)
2690 {
2691 	if (cgu) {
2692 		ice_dpll_unregister_pins(first, pins, ops, count);
2693 		ice_dpll_unregister_pins(second, pins, ops, count);
2694 	}
2695 	ice_dpll_release_pins(pins, count);
2696 }
2697 
2698 /**
2699  * ice_dpll_init_direct_pins - initialize direct pins
2700  * @pf: board private structure
2701  * @cgu: if cgu is present and controlled by this NIC
2702  * @pins: pointer to pins array
2703  * @start_idx: on which index shall allocation start in dpll subsystem
2704  * @count: number of pins
2705  * @ops: callback ops registered with the pins
2706  * @first: dpll device pointer
2707  * @second: dpll device pointer
2708  *
2709  * Allocate directly connected pins of a given array in dpll subsystem.
2710  * If cgu is owned register allocated pins with given dplls.
2711  *
2712  * Return:
2713  * * 0 - success
2714  * * negative - registration failure reason
2715  */
2716 static int
2717 ice_dpll_init_direct_pins(struct ice_pf *pf, bool cgu,
2718 			  struct ice_dpll_pin *pins, int start_idx, int count,
2719 			  const struct dpll_pin_ops *ops,
2720 			  struct dpll_device *first, struct dpll_device *second)
2721 {
2722 	int ret;
2723 
2724 	ret = ice_dpll_get_pins(pf, pins, start_idx, count, pf->dplls.clock_id);
2725 	if (ret)
2726 		return ret;
2727 	if (cgu) {
2728 		ret = ice_dpll_register_pins(first, pins, ops, count);
2729 		if (ret)
2730 			goto release_pins;
2731 		ret = ice_dpll_register_pins(second, pins, ops, count);
2732 		if (ret)
2733 			goto unregister_first;
2734 	}
2735 
2736 	return 0;
2737 
2738 unregister_first:
2739 	ice_dpll_unregister_pins(first, pins, ops, count);
2740 release_pins:
2741 	ice_dpll_release_pins(pins, count);
2742 	return ret;
2743 }
2744 
2745 /**
2746  * ice_dpll_deinit_rclk_pin - release rclk pin resources
2747  * @pf: board private structure
2748  *
2749  * Deregister rclk pin from parent pins and release resources in dpll subsystem.
2750  */
2751 static void ice_dpll_deinit_rclk_pin(struct ice_pf *pf)
2752 {
2753 	struct ice_dpll_pin *rclk = &pf->dplls.rclk;
2754 	struct ice_vsi *vsi = ice_get_main_vsi(pf);
2755 	struct dpll_pin *parent;
2756 	int i;
2757 
2758 	for (i = 0; i < rclk->num_parents; i++) {
2759 		parent = pf->dplls.inputs[rclk->parent_idx[i]].pin;
2760 		if (!parent)
2761 			continue;
2762 		dpll_pin_on_pin_unregister(parent, rclk->pin,
2763 					   &ice_dpll_rclk_ops, rclk);
2764 	}
2765 	if (WARN_ON_ONCE(!vsi || !vsi->netdev))
2766 		return;
2767 	dpll_netdev_pin_clear(vsi->netdev);
2768 	dpll_pin_put(rclk->pin);
2769 }
2770 
2771 /**
2772  * ice_dpll_init_rclk_pins - initialize recovered clock pin
2773  * @pf: board private structure
2774  * @pin: pin to register
2775  * @start_idx: on which index shall allocation start in dpll subsystem
2776  * @ops: callback ops registered with the pins
2777  *
2778  * Allocate resource for recovered clock pin in dpll subsystem. Register the
2779  * pin with the parents it has in the info. Register pin with the pf's main vsi
2780  * netdev.
2781  *
2782  * Return:
2783  * * 0 - success
2784  * * negative - registration failure reason
2785  */
2786 static int
2787 ice_dpll_init_rclk_pins(struct ice_pf *pf, struct ice_dpll_pin *pin,
2788 			int start_idx, const struct dpll_pin_ops *ops)
2789 {
2790 	struct ice_vsi *vsi = ice_get_main_vsi(pf);
2791 	struct dpll_pin *parent;
2792 	int ret, i;
2793 
2794 	if (WARN_ON((!vsi || !vsi->netdev)))
2795 		return -EINVAL;
2796 	ret = ice_dpll_get_pins(pf, pin, start_idx, ICE_DPLL_RCLK_NUM_PER_PF,
2797 				pf->dplls.clock_id);
2798 	if (ret)
2799 		return ret;
2800 	for (i = 0; i < pf->dplls.rclk.num_parents; i++) {
2801 		parent = pf->dplls.inputs[pf->dplls.rclk.parent_idx[i]].pin;
2802 		if (!parent) {
2803 			ret = -ENODEV;
2804 			goto unregister_pins;
2805 		}
2806 		ret = dpll_pin_on_pin_register(parent, pf->dplls.rclk.pin,
2807 					       ops, &pf->dplls.rclk);
2808 		if (ret)
2809 			goto unregister_pins;
2810 	}
2811 	dpll_netdev_pin_set(vsi->netdev, pf->dplls.rclk.pin);
2812 
2813 	return 0;
2814 
2815 unregister_pins:
2816 	while (i) {
2817 		parent = pf->dplls.inputs[pf->dplls.rclk.parent_idx[--i]].pin;
2818 		dpll_pin_on_pin_unregister(parent, pf->dplls.rclk.pin,
2819 					   &ice_dpll_rclk_ops, &pf->dplls.rclk);
2820 	}
2821 	ice_dpll_release_pins(pin, ICE_DPLL_RCLK_NUM_PER_PF);
2822 	return ret;
2823 }
2824 
2825 /**
2826  * ice_dpll_deinit_pins - deinitialize direct pins
2827  * @pf: board private structure
2828  * @cgu: if cgu is controlled by this pf
2829  *
2830  * If cgu is owned unregister directly connected pins from the dplls.
2831  * Release resources of directly connected pins from the dpll subsystem.
2832  */
2833 static void ice_dpll_deinit_pins(struct ice_pf *pf, bool cgu)
2834 {
2835 	struct ice_dpll_pin *outputs = pf->dplls.outputs;
2836 	struct ice_dpll_pin *inputs = pf->dplls.inputs;
2837 	int num_outputs = pf->dplls.num_outputs;
2838 	int num_inputs = pf->dplls.num_inputs;
2839 	struct ice_dplls *d = &pf->dplls;
2840 	struct ice_dpll *de = &d->eec;
2841 	struct ice_dpll *dp = &d->pps;
2842 
2843 	ice_dpll_deinit_rclk_pin(pf);
2844 	if (cgu) {
2845 		ice_dpll_unregister_pins(dp->dpll, inputs, &ice_dpll_input_ops,
2846 					 num_inputs);
2847 		ice_dpll_unregister_pins(de->dpll, inputs, &ice_dpll_input_ops,
2848 					 num_inputs);
2849 	}
2850 	ice_dpll_release_pins(inputs, num_inputs);
2851 	if (cgu) {
2852 		ice_dpll_unregister_pins(dp->dpll, outputs,
2853 					 &ice_dpll_output_ops, num_outputs);
2854 		ice_dpll_unregister_pins(de->dpll, outputs,
2855 					 &ice_dpll_output_ops, num_outputs);
2856 		ice_dpll_release_pins(outputs, num_outputs);
2857 		if (!pf->dplls.generic) {
2858 			ice_dpll_deinit_direct_pins(cgu, pf->dplls.ufl,
2859 						    ICE_DPLL_PIN_SW_NUM,
2860 						    &ice_dpll_pin_ufl_ops,
2861 						    pf->dplls.pps.dpll,
2862 						    pf->dplls.eec.dpll);
2863 			ice_dpll_deinit_direct_pins(cgu, pf->dplls.sma,
2864 						    ICE_DPLL_PIN_SW_NUM,
2865 						    &ice_dpll_pin_sma_ops,
2866 						    pf->dplls.pps.dpll,
2867 						    pf->dplls.eec.dpll);
2868 		}
2869 	}
2870 }
2871 
2872 /**
2873  * ice_dpll_init_pins - init pins and register pins with a dplls
2874  * @pf: board private structure
2875  * @cgu: if cgu is present and controlled by this NIC
2876  *
2877  * Initialize directly connected pf's pins within pf's dplls in a Linux dpll
2878  * subsystem.
2879  *
2880  * Return:
2881  * * 0 - success
2882  * * negative - initialization failure reason
2883  */
2884 static int ice_dpll_init_pins(struct ice_pf *pf, bool cgu)
2885 {
2886 	int ret, count;
2887 
2888 	ret = ice_dpll_init_direct_pins(pf, cgu, pf->dplls.inputs, 0,
2889 					pf->dplls.num_inputs,
2890 					&ice_dpll_input_ops,
2891 					pf->dplls.eec.dpll, pf->dplls.pps.dpll);
2892 	if (ret)
2893 		return ret;
2894 	count = pf->dplls.num_inputs;
2895 	if (cgu) {
2896 		ret = ice_dpll_init_direct_pins(pf, cgu, pf->dplls.outputs,
2897 						count,
2898 						pf->dplls.num_outputs,
2899 						&ice_dpll_output_ops,
2900 						pf->dplls.eec.dpll,
2901 						pf->dplls.pps.dpll);
2902 		if (ret)
2903 			goto deinit_inputs;
2904 		count += pf->dplls.num_outputs;
2905 		if (!pf->dplls.generic) {
2906 			ret = ice_dpll_init_direct_pins(pf, cgu, pf->dplls.sma,
2907 							count,
2908 							ICE_DPLL_PIN_SW_NUM,
2909 							&ice_dpll_pin_sma_ops,
2910 							pf->dplls.eec.dpll,
2911 							pf->dplls.pps.dpll);
2912 			if (ret)
2913 				goto deinit_outputs;
2914 			count += ICE_DPLL_PIN_SW_NUM;
2915 			ret = ice_dpll_init_direct_pins(pf, cgu, pf->dplls.ufl,
2916 							count,
2917 							ICE_DPLL_PIN_SW_NUM,
2918 							&ice_dpll_pin_ufl_ops,
2919 							pf->dplls.eec.dpll,
2920 							pf->dplls.pps.dpll);
2921 			if (ret)
2922 				goto deinit_sma;
2923 			count += ICE_DPLL_PIN_SW_NUM;
2924 		}
2925 	} else {
2926 		count += pf->dplls.num_outputs + 2 * ICE_DPLL_PIN_SW_NUM;
2927 	}
2928 	ret = ice_dpll_init_rclk_pins(pf, &pf->dplls.rclk, count + pf->hw.pf_id,
2929 				      &ice_dpll_rclk_ops);
2930 	if (ret)
2931 		goto deinit_ufl;
2932 
2933 	return 0;
2934 deinit_ufl:
2935 	ice_dpll_deinit_direct_pins(cgu, pf->dplls.ufl,
2936 				    ICE_DPLL_PIN_SW_NUM,
2937 				    &ice_dpll_pin_ufl_ops,
2938 				    pf->dplls.pps.dpll, pf->dplls.eec.dpll);
2939 deinit_sma:
2940 	ice_dpll_deinit_direct_pins(cgu, pf->dplls.sma,
2941 				    ICE_DPLL_PIN_SW_NUM,
2942 				    &ice_dpll_pin_sma_ops,
2943 				    pf->dplls.pps.dpll, pf->dplls.eec.dpll);
2944 deinit_outputs:
2945 	ice_dpll_deinit_direct_pins(cgu, pf->dplls.outputs,
2946 				    pf->dplls.num_outputs,
2947 				    &ice_dpll_output_ops, pf->dplls.pps.dpll,
2948 				    pf->dplls.eec.dpll);
2949 deinit_inputs:
2950 	ice_dpll_deinit_direct_pins(cgu, pf->dplls.inputs, pf->dplls.num_inputs,
2951 				    &ice_dpll_input_ops, pf->dplls.pps.dpll,
2952 				    pf->dplls.eec.dpll);
2953 	return ret;
2954 }
2955 
2956 /**
2957  * ice_dpll_deinit_dpll - deinitialize dpll device
2958  * @pf: board private structure
2959  * @d: pointer to ice_dpll
2960  * @cgu: if cgu is present and controlled by this NIC
2961  *
2962  * If cgu is owned unregister the dpll from dpll subsystem.
2963  * Release resources of dpll device from dpll subsystem.
2964  */
2965 static void
2966 ice_dpll_deinit_dpll(struct ice_pf *pf, struct ice_dpll *d, bool cgu)
2967 {
2968 	if (cgu)
2969 		dpll_device_unregister(d->dpll, d->ops, d);
2970 	dpll_device_put(d->dpll);
2971 }
2972 
2973 /**
2974  * ice_dpll_init_dpll - initialize dpll device in dpll subsystem
2975  * @pf: board private structure
2976  * @d: dpll to be initialized
2977  * @cgu: if cgu is present and controlled by this NIC
2978  * @type: type of dpll being initialized
2979  *
2980  * Allocate dpll instance for this board in dpll subsystem, if cgu is controlled
2981  * by this NIC, register dpll with the callback ops.
2982  *
2983  * Return:
2984  * * 0 - success
2985  * * negative - initialization failure reason
2986  */
2987 static int
2988 ice_dpll_init_dpll(struct ice_pf *pf, struct ice_dpll *d, bool cgu,
2989 		   enum dpll_type type)
2990 {
2991 	u64 clock_id = pf->dplls.clock_id;
2992 	int ret;
2993 
2994 	d->dpll = dpll_device_get(clock_id, d->dpll_idx, THIS_MODULE);
2995 	if (IS_ERR(d->dpll)) {
2996 		ret = PTR_ERR(d->dpll);
2997 		dev_err(ice_pf_to_dev(pf),
2998 			"dpll_device_get failed (%p) err=%d\n", d, ret);
2999 		return ret;
3000 	}
3001 	d->pf = pf;
3002 	if (cgu) {
3003 		const struct dpll_device_ops *ops = &ice_dpll_ops;
3004 
3005 		if (type == DPLL_TYPE_PPS && ice_dpll_is_pps_phase_monitor(pf))
3006 			ops =  &ice_dpll_pom_ops;
3007 		ice_dpll_update_state(pf, d, true);
3008 		ret = dpll_device_register(d->dpll, type, ops, d);
3009 		if (ret) {
3010 			dpll_device_put(d->dpll);
3011 			return ret;
3012 		}
3013 		d->ops = ops;
3014 	}
3015 
3016 	return 0;
3017 }
3018 
3019 /**
3020  * ice_dpll_deinit_worker - deinitialize dpll kworker
3021  * @pf: board private structure
3022  *
3023  * Stop dpll's kworker, release it's resources.
3024  */
3025 static void ice_dpll_deinit_worker(struct ice_pf *pf)
3026 {
3027 	struct ice_dplls *d = &pf->dplls;
3028 
3029 	kthread_cancel_delayed_work_sync(&d->work);
3030 	kthread_destroy_worker(d->kworker);
3031 }
3032 
3033 /**
3034  * ice_dpll_init_worker - Initialize DPLLs periodic worker
3035  * @pf: board private structure
3036  *
3037  * Create and start DPLLs periodic worker.
3038  *
3039  * Context: Shall be called after pf->dplls.lock is initialized.
3040  * Return:
3041  * * 0 - success
3042  * * negative - create worker failure
3043  */
3044 static int ice_dpll_init_worker(struct ice_pf *pf)
3045 {
3046 	struct ice_dplls *d = &pf->dplls;
3047 	struct kthread_worker *kworker;
3048 
3049 	kthread_init_delayed_work(&d->work, ice_dpll_periodic_work);
3050 	kworker = kthread_run_worker(0, "ice-dplls-%s",
3051 					dev_name(ice_pf_to_dev(pf)));
3052 	if (IS_ERR(kworker))
3053 		return PTR_ERR(kworker);
3054 	d->kworker = kworker;
3055 	d->cgu_state_acq_err_num = 0;
3056 	kthread_queue_delayed_work(d->kworker, &d->work, 0);
3057 
3058 	return 0;
3059 }
3060 
3061 /**
3062  * ice_dpll_phase_range_set - initialize phase adjust range helper
3063  * @range: pointer to phase adjust range struct to be initialized
3064  * @phase_adj: a value to be used as min(-)/max(+) boundary
3065  */
3066 static void ice_dpll_phase_range_set(struct dpll_pin_phase_adjust_range *range,
3067 				     u32 phase_adj)
3068 {
3069 	range->min = -phase_adj;
3070 	range->max = phase_adj;
3071 }
3072 
3073 /**
3074  * ice_dpll_init_info_pins_generic - initializes generic pins info
3075  * @pf: board private structure
3076  * @input: if input pins initialized
3077  *
3078  * Init information for generic pins, cache them in PF's pins structures.
3079  *
3080  * Return:
3081  * * 0 - success
3082  * * negative - init failure reason
3083  */
3084 static int ice_dpll_init_info_pins_generic(struct ice_pf *pf, bool input)
3085 {
3086 	struct ice_dpll *de = &pf->dplls.eec, *dp = &pf->dplls.pps;
3087 	static const char labels[][sizeof("99")] = {
3088 		"0", "1", "2", "3", "4", "5", "6", "7", "8",
3089 		"9", "10", "11", "12", "13", "14", "15" };
3090 	u32 cap = DPLL_PIN_CAPABILITIES_STATE_CAN_CHANGE;
3091 	enum ice_dpll_pin_type pin_type;
3092 	int i, pin_num, ret = -EINVAL;
3093 	struct ice_dpll_pin *pins;
3094 	u32 phase_adj_max;
3095 
3096 	if (input) {
3097 		pin_num = pf->dplls.num_inputs;
3098 		pins = pf->dplls.inputs;
3099 		phase_adj_max = pf->dplls.input_phase_adj_max;
3100 		pin_type = ICE_DPLL_PIN_TYPE_INPUT;
3101 		cap |= DPLL_PIN_CAPABILITIES_PRIORITY_CAN_CHANGE;
3102 	} else {
3103 		pin_num = pf->dplls.num_outputs;
3104 		pins = pf->dplls.outputs;
3105 		phase_adj_max = pf->dplls.output_phase_adj_max;
3106 		pin_type = ICE_DPLL_PIN_TYPE_OUTPUT;
3107 	}
3108 	if (pin_num > ARRAY_SIZE(labels))
3109 		return ret;
3110 
3111 	for (i = 0; i < pin_num; i++) {
3112 		pins[i].idx = i;
3113 		pins[i].prop.board_label = labels[i];
3114 		ice_dpll_phase_range_set(&pins[i].prop.phase_range,
3115 					 phase_adj_max);
3116 		pins[i].prop.capabilities = cap;
3117 		pins[i].pf = pf;
3118 		ret = ice_dpll_pin_state_update(pf, &pins[i], pin_type, NULL);
3119 		if (ret)
3120 			break;
3121 		if (input && pins[i].freq == ICE_DPLL_PIN_GEN_RCLK_FREQ)
3122 			pins[i].prop.type = DPLL_PIN_TYPE_MUX;
3123 		else
3124 			pins[i].prop.type = DPLL_PIN_TYPE_EXT;
3125 		if (!input)
3126 			continue;
3127 		ret = ice_aq_get_cgu_ref_prio(&pf->hw, de->dpll_idx, i,
3128 					      &de->input_prio[i]);
3129 		if (ret)
3130 			break;
3131 		ret = ice_aq_get_cgu_ref_prio(&pf->hw, dp->dpll_idx, i,
3132 					      &dp->input_prio[i]);
3133 		if (ret)
3134 			break;
3135 	}
3136 
3137 	return ret;
3138 }
3139 
3140 /**
3141  * ice_dpll_init_info_direct_pins - initializes direct pins info
3142  * @pf: board private structure
3143  * @pin_type: type of pins being initialized
3144  *
3145  * Init information for directly connected pins, cache them in pf's pins
3146  * structures.
3147  *
3148  * Return:
3149  * * 0 - success
3150  * * negative - init failure reason
3151  */
3152 static int
3153 ice_dpll_init_info_direct_pins(struct ice_pf *pf,
3154 			       enum ice_dpll_pin_type pin_type)
3155 {
3156 	struct ice_dpll *de = &pf->dplls.eec, *dp = &pf->dplls.pps;
3157 	int num_pins, i, ret = -EINVAL;
3158 	struct ice_hw *hw = &pf->hw;
3159 	struct ice_dpll_pin *pins;
3160 	unsigned long caps;
3161 	u32 phase_adj_max;
3162 	u8 freq_supp_num;
3163 	bool input;
3164 
3165 	switch (pin_type) {
3166 	case ICE_DPLL_PIN_TYPE_INPUT:
3167 		pins = pf->dplls.inputs;
3168 		num_pins = pf->dplls.num_inputs;
3169 		phase_adj_max = pf->dplls.input_phase_adj_max;
3170 		input = true;
3171 		break;
3172 	case ICE_DPLL_PIN_TYPE_OUTPUT:
3173 		pins = pf->dplls.outputs;
3174 		num_pins = pf->dplls.num_outputs;
3175 		phase_adj_max = pf->dplls.output_phase_adj_max;
3176 		input = false;
3177 		break;
3178 	default:
3179 		return -EINVAL;
3180 	}
3181 	if (num_pins != ice_cgu_get_num_pins(hw, input)) {
3182 		pf->dplls.generic = true;
3183 		return ice_dpll_init_info_pins_generic(pf, input);
3184 	}
3185 
3186 	for (i = 0; i < num_pins; i++) {
3187 		caps = 0;
3188 		pins[i].idx = i;
3189 		pins[i].prop.board_label = ice_cgu_get_pin_name(hw, i, input);
3190 		pins[i].prop.type = ice_cgu_get_pin_type(hw, i, input);
3191 		if (input) {
3192 			ret = ice_aq_get_cgu_ref_prio(hw, de->dpll_idx, i,
3193 						      &de->input_prio[i]);
3194 			if (ret)
3195 				return ret;
3196 			ret = ice_aq_get_cgu_ref_prio(hw, dp->dpll_idx, i,
3197 						      &dp->input_prio[i]);
3198 			if (ret)
3199 				return ret;
3200 			caps |= (DPLL_PIN_CAPABILITIES_PRIORITY_CAN_CHANGE |
3201 				 DPLL_PIN_CAPABILITIES_STATE_CAN_CHANGE);
3202 			if (ice_dpll_is_sw_pin(pf, i, true))
3203 				pins[i].hidden = true;
3204 		} else {
3205 			ret = ice_cgu_get_output_pin_state_caps(hw, i, &caps);
3206 			if (ret)
3207 				return ret;
3208 			if (ice_dpll_is_sw_pin(pf, i, false))
3209 				pins[i].hidden = true;
3210 		}
3211 		ice_dpll_phase_range_set(&pins[i].prop.phase_range,
3212 					 phase_adj_max);
3213 		pins[i].prop.capabilities = caps;
3214 		ret = ice_dpll_pin_state_update(pf, &pins[i], pin_type, NULL);
3215 		if (ret)
3216 			return ret;
3217 		pins[i].prop.freq_supported =
3218 			ice_cgu_get_pin_freq_supp(hw, i, input, &freq_supp_num);
3219 		pins[i].prop.freq_supported_num = freq_supp_num;
3220 		pins[i].pf = pf;
3221 	}
3222 
3223 	return ret;
3224 }
3225 
3226 /**
3227  * ice_dpll_init_info_rclk_pin - initializes rclk pin information
3228  * @pf: board private structure
3229  *
3230  * Init information for rclk pin, cache them in pf->dplls.rclk.
3231  *
3232  * Return:
3233  * * 0 - success
3234  * * negative - init failure reason
3235  */
3236 static int ice_dpll_init_info_rclk_pin(struct ice_pf *pf)
3237 {
3238 	struct ice_dpll_pin *pin = &pf->dplls.rclk;
3239 
3240 	pin->prop.type = DPLL_PIN_TYPE_SYNCE_ETH_PORT;
3241 	pin->prop.capabilities |= DPLL_PIN_CAPABILITIES_STATE_CAN_CHANGE;
3242 	pin->pf = pf;
3243 
3244 	return ice_dpll_pin_state_update(pf, pin,
3245 					 ICE_DPLL_PIN_TYPE_RCLK_INPUT, NULL);
3246 }
3247 
3248 /**
3249  * ice_dpll_init_info_sw_pins - initializes software controlled pin information
3250  * @pf: board private structure
3251  *
3252  * Init information for software controlled pins, cache them in
3253  * pf->dplls.sma and pf->dplls.ufl.
3254  *
3255  * Return:
3256  * * 0 - success
3257  * * negative - init failure reason
3258  */
3259 static int ice_dpll_init_info_sw_pins(struct ice_pf *pf)
3260 {
3261 	u8 freq_supp_num, pin_abs_idx, input_idx_offset = 0;
3262 	struct ice_dplls *d = &pf->dplls;
3263 	struct ice_dpll_pin *pin;
3264 	u32 phase_adj_max, caps;
3265 	int i, ret;
3266 
3267 	if (pf->hw.device_id == ICE_DEV_ID_E810C_QSFP)
3268 		input_idx_offset = ICE_E810_RCLK_PINS_NUM;
3269 	phase_adj_max = max(d->input_phase_adj_max, d->output_phase_adj_max);
3270 	caps = DPLL_PIN_CAPABILITIES_STATE_CAN_CHANGE;
3271 	for (i = 0; i < ICE_DPLL_PIN_SW_NUM; i++) {
3272 		pin = &d->sma[i];
3273 		pin->idx = i;
3274 		pin->prop.type = DPLL_PIN_TYPE_EXT;
3275 		pin_abs_idx = ICE_DPLL_PIN_SW_INPUT_ABS(i) + input_idx_offset;
3276 		pin->prop.freq_supported =
3277 			ice_cgu_get_pin_freq_supp(&pf->hw, pin_abs_idx,
3278 						  true, &freq_supp_num);
3279 		pin->prop.freq_supported_num = freq_supp_num;
3280 		pin->prop.capabilities =
3281 			(DPLL_PIN_CAPABILITIES_DIRECTION_CAN_CHANGE |
3282 			 DPLL_PIN_CAPABILITIES_PRIORITY_CAN_CHANGE |
3283 			 caps);
3284 		pin->pf = pf;
3285 		pin->prop.board_label = ice_dpll_sw_pin_sma[i];
3286 		pin->input = &d->inputs[pin_abs_idx];
3287 		pin->output = &d->outputs[ICE_DPLL_PIN_SW_OUTPUT_ABS(i)];
3288 		ice_dpll_phase_range_set(&pin->prop.phase_range, phase_adj_max);
3289 	}
3290 	for (i = 0; i < ICE_DPLL_PIN_SW_NUM; i++) {
3291 		pin = &d->ufl[i];
3292 		pin->idx = i;
3293 		pin->prop.type = DPLL_PIN_TYPE_EXT;
3294 		pin->prop.capabilities = caps;
3295 		pin->pf = pf;
3296 		pin->prop.board_label = ice_dpll_sw_pin_ufl[i];
3297 		if (i == ICE_DPLL_PIN_SW_1_IDX) {
3298 			pin->direction = DPLL_PIN_DIRECTION_OUTPUT;
3299 			pin_abs_idx = ICE_DPLL_PIN_SW_OUTPUT_ABS(i);
3300 			pin->prop.freq_supported =
3301 				ice_cgu_get_pin_freq_supp(&pf->hw, pin_abs_idx,
3302 							  false,
3303 							  &freq_supp_num);
3304 			pin->prop.freq_supported_num = freq_supp_num;
3305 			pin->input = NULL;
3306 			pin->output = &d->outputs[pin_abs_idx];
3307 		} else if (i == ICE_DPLL_PIN_SW_2_IDX) {
3308 			pin->direction = DPLL_PIN_DIRECTION_INPUT;
3309 			pin_abs_idx = ICE_DPLL_PIN_SW_INPUT_ABS(i) +
3310 				      input_idx_offset;
3311 			pin->output = NULL;
3312 			pin->input = &d->inputs[pin_abs_idx];
3313 			pin->prop.freq_supported =
3314 				ice_cgu_get_pin_freq_supp(&pf->hw, pin_abs_idx,
3315 							  true, &freq_supp_num);
3316 			pin->prop.freq_supported_num = freq_supp_num;
3317 			pin->prop.capabilities =
3318 				(DPLL_PIN_CAPABILITIES_PRIORITY_CAN_CHANGE |
3319 				 caps);
3320 		}
3321 		ice_dpll_phase_range_set(&pin->prop.phase_range, phase_adj_max);
3322 	}
3323 	ret = ice_dpll_pin_state_update(pf, pin, ICE_DPLL_PIN_TYPE_SOFTWARE,
3324 					NULL);
3325 	if (ret)
3326 		return ret;
3327 
3328 	return 0;
3329 }
3330 
3331 /**
3332  * ice_dpll_init_pins_info - init pins info wrapper
3333  * @pf: board private structure
3334  * @pin_type: type of pins being initialized
3335  *
3336  * Wraps functions for pin initialization.
3337  *
3338  * Return:
3339  * * 0 - success
3340  * * negative - init failure reason
3341  */
3342 static int
3343 ice_dpll_init_pins_info(struct ice_pf *pf, enum ice_dpll_pin_type pin_type)
3344 {
3345 	switch (pin_type) {
3346 	case ICE_DPLL_PIN_TYPE_INPUT:
3347 	case ICE_DPLL_PIN_TYPE_OUTPUT:
3348 		return ice_dpll_init_info_direct_pins(pf, pin_type);
3349 	case ICE_DPLL_PIN_TYPE_RCLK_INPUT:
3350 		return ice_dpll_init_info_rclk_pin(pf);
3351 	case ICE_DPLL_PIN_TYPE_SOFTWARE:
3352 		return ice_dpll_init_info_sw_pins(pf);
3353 	default:
3354 		return -EINVAL;
3355 	}
3356 }
3357 
3358 /**
3359  * ice_dpll_deinit_info - release memory allocated for pins info
3360  * @pf: board private structure
3361  *
3362  * Release memory allocated for pins by ice_dpll_init_info function.
3363  */
3364 static void ice_dpll_deinit_info(struct ice_pf *pf)
3365 {
3366 	kfree(pf->dplls.inputs);
3367 	kfree(pf->dplls.outputs);
3368 	kfree(pf->dplls.eec.input_prio);
3369 	kfree(pf->dplls.pps.input_prio);
3370 }
3371 
3372 /**
3373  * ice_dpll_init_info - prepare pf's dpll information structure
3374  * @pf: board private structure
3375  * @cgu: if cgu is present and controlled by this NIC
3376  *
3377  * Acquire (from HW) and set basic dpll information (on pf->dplls struct).
3378  *
3379  * Return:
3380  * * 0 - success
3381  * * negative - init failure reason
3382  */
3383 static int ice_dpll_init_info(struct ice_pf *pf, bool cgu)
3384 {
3385 	struct ice_aqc_get_cgu_abilities abilities;
3386 	struct ice_dpll *de = &pf->dplls.eec;
3387 	struct ice_dpll *dp = &pf->dplls.pps;
3388 	struct ice_dplls *d = &pf->dplls;
3389 	struct ice_hw *hw = &pf->hw;
3390 	int ret, alloc_size, i;
3391 
3392 	d->clock_id = ice_generate_clock_id(pf);
3393 	ret = ice_aq_get_cgu_abilities(hw, &abilities);
3394 	if (ret) {
3395 		dev_err(ice_pf_to_dev(pf),
3396 			"err:%d %s failed to read cgu abilities\n",
3397 			ret, ice_aq_str(hw->adminq.sq_last_status));
3398 		return ret;
3399 	}
3400 
3401 	de->dpll_idx = abilities.eec_dpll_idx;
3402 	dp->dpll_idx = abilities.pps_dpll_idx;
3403 	d->num_inputs = abilities.num_inputs;
3404 	d->num_outputs = abilities.num_outputs;
3405 	d->input_phase_adj_max = le32_to_cpu(abilities.max_in_phase_adj) &
3406 		ICE_AQC_GET_CGU_MAX_PHASE_ADJ;
3407 	d->output_phase_adj_max = le32_to_cpu(abilities.max_out_phase_adj) &
3408 		ICE_AQC_GET_CGU_MAX_PHASE_ADJ;
3409 
3410 	alloc_size = sizeof(*d->inputs) * d->num_inputs;
3411 	d->inputs = kzalloc(alloc_size, GFP_KERNEL);
3412 	if (!d->inputs)
3413 		return -ENOMEM;
3414 
3415 	alloc_size = sizeof(*de->input_prio) * d->num_inputs;
3416 	de->input_prio = kzalloc(alloc_size, GFP_KERNEL);
3417 	if (!de->input_prio)
3418 		return -ENOMEM;
3419 
3420 	dp->input_prio = kzalloc(alloc_size, GFP_KERNEL);
3421 	if (!dp->input_prio)
3422 		return -ENOMEM;
3423 
3424 	ret = ice_dpll_init_pins_info(pf, ICE_DPLL_PIN_TYPE_INPUT);
3425 	if (ret)
3426 		goto deinit_info;
3427 
3428 	if (cgu) {
3429 		alloc_size = sizeof(*d->outputs) * d->num_outputs;
3430 		d->outputs = kzalloc(alloc_size, GFP_KERNEL);
3431 		if (!d->outputs) {
3432 			ret = -ENOMEM;
3433 			goto deinit_info;
3434 		}
3435 
3436 		ret = ice_dpll_init_pins_info(pf, ICE_DPLL_PIN_TYPE_OUTPUT);
3437 		if (ret)
3438 			goto deinit_info;
3439 		ret = ice_dpll_init_pins_info(pf, ICE_DPLL_PIN_TYPE_SOFTWARE);
3440 		if (ret)
3441 			goto deinit_info;
3442 	}
3443 
3444 	ret = ice_get_cgu_rclk_pin_info(&pf->hw, &d->base_rclk_idx,
3445 					&pf->dplls.rclk.num_parents);
3446 	if (ret)
3447 		return ret;
3448 	for (i = 0; i < pf->dplls.rclk.num_parents; i++)
3449 		pf->dplls.rclk.parent_idx[i] = d->base_rclk_idx + i;
3450 	ret = ice_dpll_init_pins_info(pf, ICE_DPLL_PIN_TYPE_RCLK_INPUT);
3451 	if (ret)
3452 		return ret;
3453 	de->mode = DPLL_MODE_AUTOMATIC;
3454 	dp->mode = DPLL_MODE_AUTOMATIC;
3455 
3456 	dev_dbg(ice_pf_to_dev(pf),
3457 		"%s - success, inputs:%u, outputs:%u rclk-parents:%u\n",
3458 		__func__, d->num_inputs, d->num_outputs, d->rclk.num_parents);
3459 
3460 	return 0;
3461 
3462 deinit_info:
3463 	dev_err(ice_pf_to_dev(pf),
3464 		"%s - fail: d->inputs:%p, de->input_prio:%p, dp->input_prio:%p, d->outputs:%p\n",
3465 		__func__, d->inputs, de->input_prio,
3466 		dp->input_prio, d->outputs);
3467 	ice_dpll_deinit_info(pf);
3468 	return ret;
3469 }
3470 
3471 /**
3472  * ice_dpll_deinit - Disable the driver/HW support for dpll subsystem
3473  * the dpll device.
3474  * @pf: board private structure
3475  *
3476  * Handles the cleanup work required after dpll initialization, freeing
3477  * resources and unregistering the dpll, pin and all resources used for
3478  * handling them.
3479  *
3480  * Context: Destroys pf->dplls.lock mutex. Call only if ICE_FLAG_DPLL was set.
3481  */
3482 void ice_dpll_deinit(struct ice_pf *pf)
3483 {
3484 	bool cgu = ice_is_feature_supported(pf, ICE_F_CGU);
3485 
3486 	clear_bit(ICE_FLAG_DPLL, pf->flags);
3487 	if (cgu)
3488 		ice_dpll_deinit_worker(pf);
3489 
3490 	ice_dpll_deinit_pins(pf, cgu);
3491 	ice_dpll_deinit_dpll(pf, &pf->dplls.pps, cgu);
3492 	ice_dpll_deinit_dpll(pf, &pf->dplls.eec, cgu);
3493 	ice_dpll_deinit_info(pf);
3494 	mutex_destroy(&pf->dplls.lock);
3495 }
3496 
3497 /**
3498  * ice_dpll_init - initialize support for dpll subsystem
3499  * @pf: board private structure
3500  *
3501  * Set up the device dplls, register them and pins connected within Linux dpll
3502  * subsystem. Allow userspace to obtain state of DPLL and handling of DPLL
3503  * configuration requests.
3504  *
3505  * Context: Initializes pf->dplls.lock mutex.
3506  */
3507 void ice_dpll_init(struct ice_pf *pf)
3508 {
3509 	bool cgu = ice_is_feature_supported(pf, ICE_F_CGU);
3510 	struct ice_dplls *d = &pf->dplls;
3511 	int err = 0;
3512 
3513 	mutex_init(&d->lock);
3514 	err = ice_dpll_init_info(pf, cgu);
3515 	if (err)
3516 		goto err_exit;
3517 	err = ice_dpll_init_dpll(pf, &pf->dplls.eec, cgu, DPLL_TYPE_EEC);
3518 	if (err)
3519 		goto deinit_info;
3520 	err = ice_dpll_init_dpll(pf, &pf->dplls.pps, cgu, DPLL_TYPE_PPS);
3521 	if (err)
3522 		goto deinit_eec;
3523 	err = ice_dpll_init_pins(pf, cgu);
3524 	if (err)
3525 		goto deinit_pps;
3526 	if (cgu) {
3527 		err = ice_dpll_init_worker(pf);
3528 		if (err)
3529 			goto deinit_pins;
3530 	}
3531 	set_bit(ICE_FLAG_DPLL, pf->flags);
3532 
3533 	return;
3534 
3535 deinit_pins:
3536 	ice_dpll_deinit_pins(pf, cgu);
3537 deinit_pps:
3538 	ice_dpll_deinit_dpll(pf, &pf->dplls.pps, cgu);
3539 deinit_eec:
3540 	ice_dpll_deinit_dpll(pf, &pf->dplls.eec, cgu);
3541 deinit_info:
3542 	ice_dpll_deinit_info(pf);
3543 err_exit:
3544 	mutex_destroy(&d->lock);
3545 	dev_warn(ice_pf_to_dev(pf), "DPLLs init failure err:%d\n", err);
3546 }
3547