xref: /openbmc/linux/drivers/soc/fsl/qe/ucc.c (revision 2d96b44f)
1 /*
2  * arch/powerpc/sysdev/qe_lib/ucc.c
3  *
4  * QE UCC API Set - UCC specific routines implementations.
5  *
6  * Copyright (C) 2006 Freescale Semiconductor, Inc. All rights reserved.
7  *
8  * Authors: 	Shlomi Gridish <gridish@freescale.com>
9  * 		Li Yang <leoli@freescale.com>
10  *
11  * This program is free software; you can redistribute  it and/or modify it
12  * under  the terms of  the GNU General  Public License as published by the
13  * Free Software Foundation;  either version 2 of the  License, or (at your
14  * option) any later version.
15  */
16 #include <linux/kernel.h>
17 #include <linux/errno.h>
18 #include <linux/stddef.h>
19 #include <linux/spinlock.h>
20 #include <linux/export.h>
21 
22 #include <asm/irq.h>
23 #include <asm/io.h>
24 #include <soc/fsl/qe/immap_qe.h>
25 #include <soc/fsl/qe/qe.h>
26 #include <soc/fsl/qe/ucc.h>
27 
28 #define UCC_TDM_NUM 8
29 #define RX_SYNC_SHIFT_BASE 30
30 #define TX_SYNC_SHIFT_BASE 14
31 #define RX_CLK_SHIFT_BASE 28
32 #define TX_CLK_SHIFT_BASE 12
33 
34 int ucc_set_qe_mux_mii_mng(unsigned int ucc_num)
35 {
36 	unsigned long flags;
37 
38 	if (ucc_num > UCC_MAX_NUM - 1)
39 		return -EINVAL;
40 
41 	spin_lock_irqsave(&cmxgcr_lock, flags);
42 	clrsetbits_be32(&qe_immr->qmx.cmxgcr, QE_CMXGCR_MII_ENET_MNG,
43 		ucc_num << QE_CMXGCR_MII_ENET_MNG_SHIFT);
44 	spin_unlock_irqrestore(&cmxgcr_lock, flags);
45 
46 	return 0;
47 }
48 EXPORT_SYMBOL(ucc_set_qe_mux_mii_mng);
49 
50 /* Configure the UCC to either Slow or Fast.
51  *
52  * A given UCC can be figured to support either "slow" devices (e.g. UART)
53  * or "fast" devices (e.g. Ethernet).
54  *
55  * 'ucc_num' is the UCC number, from 0 - 7.
56  *
57  * This function also sets the UCC_GUEMR_SET_RESERVED3 bit because that bit
58  * must always be set to 1.
59  */
60 int ucc_set_type(unsigned int ucc_num, enum ucc_speed_type speed)
61 {
62 	u8 __iomem *guemr;
63 
64 	/* The GUEMR register is at the same location for both slow and fast
65 	   devices, so we just use uccX.slow.guemr. */
66 	switch (ucc_num) {
67 	case 0: guemr = &qe_immr->ucc1.slow.guemr;
68 		break;
69 	case 1: guemr = &qe_immr->ucc2.slow.guemr;
70 		break;
71 	case 2: guemr = &qe_immr->ucc3.slow.guemr;
72 		break;
73 	case 3: guemr = &qe_immr->ucc4.slow.guemr;
74 		break;
75 	case 4: guemr = &qe_immr->ucc5.slow.guemr;
76 		break;
77 	case 5: guemr = &qe_immr->ucc6.slow.guemr;
78 		break;
79 	case 6: guemr = &qe_immr->ucc7.slow.guemr;
80 		break;
81 	case 7: guemr = &qe_immr->ucc8.slow.guemr;
82 		break;
83 	default:
84 		return -EINVAL;
85 	}
86 
87 	clrsetbits_8(guemr, UCC_GUEMR_MODE_MASK,
88 		UCC_GUEMR_SET_RESERVED3 | speed);
89 
90 	return 0;
91 }
92 
93 static void get_cmxucr_reg(unsigned int ucc_num, __be32 __iomem **cmxucr,
94 	unsigned int *reg_num, unsigned int *shift)
95 {
96 	unsigned int cmx = ((ucc_num & 1) << 1) + (ucc_num > 3);
97 
98 	*reg_num = cmx + 1;
99 	*cmxucr = &qe_immr->qmx.cmxucr[cmx];
100 	*shift = 16 - 8 * (ucc_num & 2);
101 }
102 
103 int ucc_mux_set_grant_tsa_bkpt(unsigned int ucc_num, int set, u32 mask)
104 {
105 	__be32 __iomem *cmxucr;
106 	unsigned int reg_num;
107 	unsigned int shift;
108 
109 	/* check if the UCC number is in range. */
110 	if (ucc_num > UCC_MAX_NUM - 1)
111 		return -EINVAL;
112 
113 	get_cmxucr_reg(ucc_num, &cmxucr, &reg_num, &shift);
114 
115 	if (set)
116 		setbits32(cmxucr, mask << shift);
117 	else
118 		clrbits32(cmxucr, mask << shift);
119 
120 	return 0;
121 }
122 
123 int ucc_set_qe_mux_rxtx(unsigned int ucc_num, enum qe_clock clock,
124 	enum comm_dir mode)
125 {
126 	__be32 __iomem *cmxucr;
127 	unsigned int reg_num;
128 	unsigned int shift;
129 	u32 clock_bits = 0;
130 
131 	/* check if the UCC number is in range. */
132 	if (ucc_num > UCC_MAX_NUM - 1)
133 		return -EINVAL;
134 
135 	/* The communications direction must be RX or TX */
136 	if (!((mode == COMM_DIR_RX) || (mode == COMM_DIR_TX)))
137 		return -EINVAL;
138 
139 	get_cmxucr_reg(ucc_num, &cmxucr, &reg_num, &shift);
140 
141 	switch (reg_num) {
142 	case 1:
143 		switch (clock) {
144 		case QE_BRG1:	clock_bits = 1; break;
145 		case QE_BRG2:	clock_bits = 2; break;
146 		case QE_BRG7:	clock_bits = 3; break;
147 		case QE_BRG8:	clock_bits = 4; break;
148 		case QE_CLK9:	clock_bits = 5; break;
149 		case QE_CLK10:	clock_bits = 6; break;
150 		case QE_CLK11:	clock_bits = 7; break;
151 		case QE_CLK12:	clock_bits = 8; break;
152 		case QE_CLK15:	clock_bits = 9; break;
153 		case QE_CLK16:	clock_bits = 10; break;
154 		default: break;
155 		}
156 		break;
157 	case 2:
158 		switch (clock) {
159 		case QE_BRG5:	clock_bits = 1; break;
160 		case QE_BRG6:	clock_bits = 2; break;
161 		case QE_BRG7:	clock_bits = 3; break;
162 		case QE_BRG8:	clock_bits = 4; break;
163 		case QE_CLK13:	clock_bits = 5; break;
164 		case QE_CLK14:	clock_bits = 6; break;
165 		case QE_CLK19:	clock_bits = 7; break;
166 		case QE_CLK20:	clock_bits = 8; break;
167 		case QE_CLK15:	clock_bits = 9; break;
168 		case QE_CLK16:	clock_bits = 10; break;
169 		default: break;
170 		}
171 		break;
172 	case 3:
173 		switch (clock) {
174 		case QE_BRG9:	clock_bits = 1; break;
175 		case QE_BRG10:	clock_bits = 2; break;
176 		case QE_BRG15:	clock_bits = 3; break;
177 		case QE_BRG16:	clock_bits = 4; break;
178 		case QE_CLK3:	clock_bits = 5; break;
179 		case QE_CLK4:	clock_bits = 6; break;
180 		case QE_CLK17:	clock_bits = 7; break;
181 		case QE_CLK18:	clock_bits = 8; break;
182 		case QE_CLK7:	clock_bits = 9; break;
183 		case QE_CLK8:	clock_bits = 10; break;
184 		case QE_CLK16:	clock_bits = 11; break;
185 		default: break;
186 		}
187 		break;
188 	case 4:
189 		switch (clock) {
190 		case QE_BRG13:	clock_bits = 1; break;
191 		case QE_BRG14:	clock_bits = 2; break;
192 		case QE_BRG15:	clock_bits = 3; break;
193 		case QE_BRG16:	clock_bits = 4; break;
194 		case QE_CLK5:	clock_bits = 5; break;
195 		case QE_CLK6:	clock_bits = 6; break;
196 		case QE_CLK21:	clock_bits = 7; break;
197 		case QE_CLK22:	clock_bits = 8; break;
198 		case QE_CLK7:	clock_bits = 9; break;
199 		case QE_CLK8:	clock_bits = 10; break;
200 		case QE_CLK16:	clock_bits = 11; break;
201 		default: break;
202 		}
203 		break;
204 	default: break;
205 	}
206 
207 	/* Check for invalid combination of clock and UCC number */
208 	if (!clock_bits)
209 		return -ENOENT;
210 
211 	if (mode == COMM_DIR_RX)
212 		shift += 4;
213 
214 	clrsetbits_be32(cmxucr, QE_CMXUCR_TX_CLK_SRC_MASK << shift,
215 		clock_bits << shift);
216 
217 	return 0;
218 }
219 
220 static int ucc_get_tdm_common_clk(u32 tdm_num, enum qe_clock clock)
221 {
222 	int clock_bits = -EINVAL;
223 
224 	/*
225 	 * for TDM[0, 1, 2, 3], TX and RX use  common
226 	 * clock source BRG3,4 and CLK1,2
227 	 * for TDM[4, 5, 6, 7], TX and RX use  common
228 	 * clock source BRG12,13 and CLK23,24
229 	 */
230 	switch (tdm_num) {
231 	case 0:
232 	case 1:
233 	case 2:
234 	case 3:
235 		switch (clock) {
236 		case QE_BRG3:
237 			clock_bits = 1;
238 			break;
239 		case QE_BRG4:
240 			clock_bits = 2;
241 			break;
242 		case QE_CLK1:
243 			clock_bits = 4;
244 			break;
245 		case QE_CLK2:
246 			clock_bits = 5;
247 			break;
248 		default:
249 			break;
250 		}
251 		break;
252 	case 4:
253 	case 5:
254 	case 6:
255 	case 7:
256 		switch (clock) {
257 		case QE_BRG12:
258 			clock_bits = 1;
259 			break;
260 		case QE_BRG13:
261 			clock_bits = 2;
262 			break;
263 		case QE_CLK23:
264 			clock_bits = 4;
265 			break;
266 		case QE_CLK24:
267 			clock_bits = 5;
268 			break;
269 		default:
270 			break;
271 		}
272 		break;
273 	default:
274 		break;
275 	}
276 
277 	return clock_bits;
278 }
279 
280 static int ucc_get_tdm_rx_clk(u32 tdm_num, enum qe_clock clock)
281 {
282 	int clock_bits = -EINVAL;
283 
284 	switch (tdm_num) {
285 	case 0:
286 		switch (clock) {
287 		case QE_CLK3:
288 			clock_bits = 6;
289 			break;
290 		case QE_CLK8:
291 			clock_bits = 7;
292 			break;
293 		default:
294 			break;
295 		}
296 		break;
297 	case 1:
298 		switch (clock) {
299 		case QE_CLK5:
300 			clock_bits = 6;
301 			break;
302 		case QE_CLK10:
303 			clock_bits = 7;
304 			break;
305 		default:
306 			break;
307 		}
308 		break;
309 	case 2:
310 		switch (clock) {
311 		case QE_CLK7:
312 			clock_bits = 6;
313 			break;
314 		case QE_CLK12:
315 			clock_bits = 7;
316 			break;
317 		default:
318 			break;
319 		}
320 		break;
321 	case 3:
322 		switch (clock) {
323 		case QE_CLK9:
324 			clock_bits = 6;
325 			break;
326 		case QE_CLK14:
327 			clock_bits = 7;
328 			break;
329 		default:
330 			break;
331 		}
332 		break;
333 	case 4:
334 		switch (clock) {
335 		case QE_CLK11:
336 			clock_bits = 6;
337 			break;
338 		case QE_CLK16:
339 			clock_bits = 7;
340 			break;
341 		default:
342 			break;
343 		}
344 		break;
345 	case 5:
346 		switch (clock) {
347 		case QE_CLK13:
348 			clock_bits = 6;
349 			break;
350 		case QE_CLK18:
351 			clock_bits = 7;
352 			break;
353 		default:
354 			break;
355 		}
356 		break;
357 	case 6:
358 		switch (clock) {
359 		case QE_CLK15:
360 			clock_bits = 6;
361 			break;
362 		case QE_CLK20:
363 			clock_bits = 7;
364 			break;
365 		default:
366 			break;
367 		}
368 		break;
369 	case 7:
370 		switch (clock) {
371 		case QE_CLK17:
372 			clock_bits = 6;
373 			break;
374 		case QE_CLK22:
375 			clock_bits = 7;
376 			break;
377 		default:
378 			break;
379 		}
380 		break;
381 	}
382 
383 	return clock_bits;
384 }
385 
386 static int ucc_get_tdm_tx_clk(u32 tdm_num, enum qe_clock clock)
387 {
388 	int clock_bits = -EINVAL;
389 
390 	switch (tdm_num) {
391 	case 0:
392 		switch (clock) {
393 		case QE_CLK4:
394 			clock_bits = 6;
395 			break;
396 		case QE_CLK9:
397 			clock_bits = 7;
398 			break;
399 		default:
400 			break;
401 		}
402 		break;
403 	case 1:
404 		switch (clock) {
405 		case QE_CLK6:
406 			clock_bits = 6;
407 			break;
408 		case QE_CLK11:
409 			clock_bits = 7;
410 			break;
411 		default:
412 			break;
413 		}
414 		break;
415 	case 2:
416 		switch (clock) {
417 		case QE_CLK8:
418 			clock_bits = 6;
419 			break;
420 		case QE_CLK13:
421 			clock_bits = 7;
422 			break;
423 		default:
424 			break;
425 		}
426 		break;
427 	case 3:
428 		switch (clock) {
429 		case QE_CLK10:
430 			clock_bits = 6;
431 			break;
432 		case QE_CLK15:
433 			clock_bits = 7;
434 			break;
435 		default:
436 			break;
437 		}
438 		break;
439 	case 4:
440 		switch (clock) {
441 		case QE_CLK12:
442 			clock_bits = 6;
443 			break;
444 		case QE_CLK17:
445 			clock_bits = 7;
446 			break;
447 		default:
448 			break;
449 		}
450 		break;
451 	case 5:
452 		switch (clock) {
453 		case QE_CLK14:
454 			clock_bits = 6;
455 			break;
456 		case QE_CLK19:
457 			clock_bits = 7;
458 			break;
459 		default:
460 			break;
461 		}
462 		break;
463 	case 6:
464 		switch (clock) {
465 		case QE_CLK16:
466 			clock_bits = 6;
467 			break;
468 		case QE_CLK21:
469 			clock_bits = 7;
470 			break;
471 		default:
472 			break;
473 		}
474 		break;
475 	case 7:
476 		switch (clock) {
477 		case QE_CLK18:
478 			clock_bits = 6;
479 			break;
480 		case QE_CLK3:
481 			clock_bits = 7;
482 			break;
483 		default:
484 			break;
485 		}
486 		break;
487 	}
488 
489 	return clock_bits;
490 }
491 
492 /* tdm_num: TDM A-H port num is 0-7 */
493 static int ucc_get_tdm_rxtx_clk(enum comm_dir mode, u32 tdm_num,
494 				enum qe_clock clock)
495 {
496 	int clock_bits;
497 
498 	clock_bits = ucc_get_tdm_common_clk(tdm_num, clock);
499 	if (clock_bits > 0)
500 		return clock_bits;
501 	if (mode == COMM_DIR_RX)
502 		clock_bits = ucc_get_tdm_rx_clk(tdm_num, clock);
503 	if (mode == COMM_DIR_TX)
504 		clock_bits = ucc_get_tdm_tx_clk(tdm_num, clock);
505 	return clock_bits;
506 }
507 
508 static u32 ucc_get_tdm_clk_shift(enum comm_dir mode, u32 tdm_num)
509 {
510 	u32 shift;
511 
512 	shift = (mode == COMM_DIR_RX) ? RX_CLK_SHIFT_BASE : TX_CLK_SHIFT_BASE;
513 	if (tdm_num < 4)
514 		shift -= tdm_num * 4;
515 	else
516 		shift -= (tdm_num - 4) * 4;
517 
518 	return shift;
519 }
520 
521 int ucc_set_tdm_rxtx_clk(u32 tdm_num, enum qe_clock clock,
522 			 enum comm_dir mode)
523 {
524 	int clock_bits;
525 	u32 shift;
526 	struct qe_mux __iomem *qe_mux_reg;
527 	 __be32 __iomem *cmxs1cr;
528 
529 	qe_mux_reg = &qe_immr->qmx;
530 
531 	if (tdm_num > 7 || tdm_num < 0)
532 		return -EINVAL;
533 
534 	/* The communications direction must be RX or TX */
535 	if (mode != COMM_DIR_RX && mode != COMM_DIR_TX)
536 		return -EINVAL;
537 
538 	clock_bits = ucc_get_tdm_rxtx_clk(mode, tdm_num, clock);
539 	if (clock_bits < 0)
540 		return -EINVAL;
541 
542 	shift = ucc_get_tdm_clk_shift(mode, tdm_num);
543 
544 	cmxs1cr = (tdm_num < 4) ? &qe_mux_reg->cmxsi1cr_l :
545 				  &qe_mux_reg->cmxsi1cr_h;
546 
547 	qe_clrsetbits32(cmxs1cr, QE_CMXUCR_TX_CLK_SRC_MASK << shift,
548 			clock_bits << shift);
549 
550 	return 0;
551 }
552 
553 static int ucc_get_tdm_sync_source(u32 tdm_num, enum qe_clock clock,
554 				   enum comm_dir mode)
555 {
556 	int source = -EINVAL;
557 
558 	if (mode == COMM_DIR_RX && clock == QE_RSYNC_PIN) {
559 		source = 0;
560 		return source;
561 	}
562 	if (mode == COMM_DIR_TX && clock == QE_TSYNC_PIN) {
563 		source = 0;
564 		return source;
565 	}
566 
567 	switch (tdm_num) {
568 	case 0:
569 	case 1:
570 		switch (clock) {
571 		case QE_BRG9:
572 			source = 1;
573 			break;
574 		case QE_BRG10:
575 			source = 2;
576 			break;
577 		default:
578 			break;
579 		}
580 		break;
581 	case 2:
582 	case 3:
583 		switch (clock) {
584 		case QE_BRG9:
585 			source = 1;
586 			break;
587 		case QE_BRG11:
588 			source = 2;
589 			break;
590 		default:
591 			break;
592 		}
593 		break;
594 	case 4:
595 	case 5:
596 		switch (clock) {
597 		case QE_BRG13:
598 			source = 1;
599 			break;
600 		case QE_BRG14:
601 			source = 2;
602 			break;
603 		default:
604 			break;
605 		}
606 		break;
607 	case 6:
608 	case 7:
609 		switch (clock) {
610 		case QE_BRG13:
611 			source = 1;
612 			break;
613 		case QE_BRG15:
614 			source = 2;
615 			break;
616 		default:
617 			break;
618 		}
619 		break;
620 	}
621 
622 	return source;
623 }
624 
625 static u32 ucc_get_tdm_sync_shift(enum comm_dir mode, u32 tdm_num)
626 {
627 	u32 shift;
628 
629 	shift = (mode == COMM_DIR_RX) ? RX_SYNC_SHIFT_BASE : RX_SYNC_SHIFT_BASE;
630 	shift -= tdm_num * 2;
631 
632 	return shift;
633 }
634 
635 int ucc_set_tdm_rxtx_sync(u32 tdm_num, enum qe_clock clock,
636 			  enum comm_dir mode)
637 {
638 	int source;
639 	u32 shift;
640 	struct qe_mux *qe_mux_reg;
641 
642 	qe_mux_reg = &qe_immr->qmx;
643 
644 	if (tdm_num >= UCC_TDM_NUM)
645 		return -EINVAL;
646 
647 	/* The communications direction must be RX or TX */
648 	if (mode != COMM_DIR_RX && mode != COMM_DIR_TX)
649 		return -EINVAL;
650 
651 	source = ucc_get_tdm_sync_source(tdm_num, clock, mode);
652 	if (source < 0)
653 		return -EINVAL;
654 
655 	shift = ucc_get_tdm_sync_shift(mode, tdm_num);
656 
657 	qe_clrsetbits32(&qe_mux_reg->cmxsi1syr,
658 			QE_CMXUCR_TX_CLK_SRC_MASK << shift,
659 			source << shift);
660 
661 	return 0;
662 }
663