2 * Copyright 2012 Freescale Semiconductor, Inc.
4 * SPDX-License-Identifier: GPL-2.0+
8 #include <asm/fsl_serdes.h>
9 #include <asm/immap_85xx.h>
11 #include <asm/processor.h>
12 #include <asm/fsl_law.h>
13 #include <asm/errno.h>
14 #include "fsl_corenet2_serdes.h"
16 #ifdef CONFIG_SYS_FSL_SRDS_1
17 static u64 serdes1_prtcl_map
;
19 #ifdef CONFIG_SYS_FSL_SRDS_2
20 static u64 serdes2_prtcl_map
;
22 #ifdef CONFIG_SYS_FSL_SRDS_3
23 static u64 serdes3_prtcl_map
;
25 #ifdef CONFIG_SYS_FSL_SRDS_4
26 static u64 serdes4_prtcl_map
;
30 static const char *serdes_prtcl_str
[] = {
40 [SGMII_FM1_DTSEC1
] = "SGMII_FM1_DTSEC1",
41 [SGMII_FM1_DTSEC2
] = "SGMII_FM1_DTSEC2",
42 [SGMII_FM1_DTSEC3
] = "SGMII_FM1_DTSEC3",
43 [SGMII_FM1_DTSEC4
] = "SGMII_FM1_DTSEC4",
44 [SGMII_FM1_DTSEC5
] = "SGMII_FM1_DTSEC5",
45 [SGMII_FM1_DTSEC6
] = "SGMII_FM1_DTSEC6",
46 [SGMII_FM2_DTSEC1
] = "SGMII_FM2_DTSEC1",
47 [SGMII_FM2_DTSEC2
] = "SGMII_FM2_DTSEC2",
48 [SGMII_FM2_DTSEC3
] = "SGMII_FM2_DTSEC3",
49 [SGMII_FM2_DTSEC4
] = "SGMII_FM2_DTSEC4",
50 [XAUI_FM1
] = "XAUI_FM1",
51 [XAUI_FM2
] = "XAUI_FM2",
61 [XAUI_FM1_MAC9
] = "XAUI_FM1_MAC9",
62 [XAUI_FM1_MAC10
] = "XAUI_FM1_MAC10",
63 [XAUI_FM2_MAC9
] = "XAUI_FM2_MAC9",
64 [XAUI_FM2_MAC10
] = "XAUI_FM2_MAC10",
65 [HIGIG_FM1_MAC9
] = "HiGig_FM1_MAC9",
66 [HIGIG_FM1_MAC10
] = "HiGig_FM1_MAC10",
67 [HIGIG_FM2_MAC9
] = "HiGig_FM2_MAC9",
68 [HIGIG_FM2_MAC10
] = "HiGig_FM2_MAC10",
69 [QSGMII_FM1_A
] = "QSGMII_FM1_A",
70 [QSGMII_FM1_B
] = "QSGMII_FM1_B",
71 [QSGMII_FM2_A
] = "QSGMII_FM2_A",
72 [QSGMII_FM2_B
] = "QSGMII_FM2_B",
73 [XFI_FM1_MAC9
] = "XFI_FM1_MAC9",
74 [XFI_FM1_MAC10
] = "XFI_FM1_MAC10",
75 [XFI_FM2_MAC9
] = "XFI_FM2_MAC9",
76 [XFI_FM2_MAC10
] = "XFI_FM2_MAC10",
77 [INTERLAKEN
] = "INTERLAKEN",
81 int is_serdes_configured(enum srds_prtcl device
)
85 #ifdef CONFIG_SYS_FSL_SRDS_1
86 ret
|= (1ULL << device
) & serdes1_prtcl_map
;
88 #ifdef CONFIG_SYS_FSL_SRDS_2
89 ret
|= (1ULL << device
) & serdes2_prtcl_map
;
91 #ifdef CONFIG_SYS_FSL_SRDS_3
92 ret
|= (1ULL << device
) & serdes3_prtcl_map
;
94 #ifdef CONFIG_SYS_FSL_SRDS_4
95 ret
|= (1ULL << device
) & serdes4_prtcl_map
;
101 int serdes_get_first_lane(u32 sd
, enum srds_prtcl device
)
103 const ccsr_gur_t
*gur
= (void __iomem
*)(CONFIG_SYS_MPC85xx_GUTS_ADDR
);
104 u32 cfg
= in_be32(&gur
->rcwsr
[4]);
108 #ifdef CONFIG_SYS_FSL_SRDS_1
110 cfg
&= FSL_CORENET2_RCWSR4_SRDS1_PRTCL
;
111 cfg
>>= FSL_CORENET2_RCWSR4_SRDS1_PRTCL_SHIFT
;
114 #ifdef CONFIG_SYS_FSL_SRDS_2
116 cfg
&= FSL_CORENET2_RCWSR4_SRDS2_PRTCL
;
117 cfg
>>= FSL_CORENET2_RCWSR4_SRDS2_PRTCL_SHIFT
;
120 #ifdef CONFIG_SYS_FSL_SRDS_3
122 cfg
&= FSL_CORENET2_RCWSR4_SRDS3_PRTCL
;
123 cfg
>>= FSL_CORENET2_RCWSR4_SRDS3_PRTCL_SHIFT
;
126 #ifdef CONFIG_SYS_FSL_SRDS_4
128 cfg
&= FSL_CORENET2_RCWSR4_SRDS4_PRTCL
;
129 cfg
>>= FSL_CORENET2_RCWSR4_SRDS4_PRTCL_SHIFT
;
133 printf("invalid SerDes%d\n", sd
);
136 /* Is serdes enabled at all? */
137 if (unlikely(cfg
== 0))
140 for (i
= 0; i
< SRDS_MAX_LANES
; i
++) {
141 if (serdes_get_prtcl(sd
, cfg
, i
) == device
)
148 u64
serdes_init(u32 sd
, u32 sd_addr
, u32 sd_prctl_mask
, u32 sd_prctl_shift
)
150 ccsr_gur_t
*gur
= (void __iomem
*)(CONFIG_SYS_MPC85xx_GUTS_ADDR
);
151 u64 serdes_prtcl_map
= 0;
155 cfg
= in_be32(&gur
->rcwsr
[4]) & sd_prctl_mask
;
156 /* Is serdes enabled at all? */
158 printf("SERDES%d is not enabled\n", sd
+ 1);
162 cfg
>>= sd_prctl_shift
;
163 printf("Using SERDES%d Protocol: %d (0x%x)\n", sd
+ 1, cfg
, cfg
);
164 if (!is_serdes_prtcl_valid(sd
, cfg
))
165 printf("SERDES%d[PRTCL] = 0x%x is not valid\n", sd
+ 1, cfg
);
167 for (lane
= 0; lane
< SRDS_MAX_LANES
; lane
++) {
168 enum srds_prtcl lane_prtcl
= serdes_get_prtcl(sd
, cfg
, lane
);
169 serdes_prtcl_map
|= (1ULL << lane_prtcl
);
172 return serdes_prtcl_map
;
175 void fsl_serdes_init(void)
178 #ifdef CONFIG_SYS_FSL_SRDS_1
179 serdes1_prtcl_map
= serdes_init(FSL_SRDS_1
,
180 CONFIG_SYS_FSL_CORENET_SERDES_ADDR
,
181 FSL_CORENET2_RCWSR4_SRDS1_PRTCL
,
182 FSL_CORENET2_RCWSR4_SRDS1_PRTCL_SHIFT
);
184 #ifdef CONFIG_SYS_FSL_SRDS_2
185 serdes2_prtcl_map
= serdes_init(FSL_SRDS_2
,
186 CONFIG_SYS_FSL_CORENET_SERDES_ADDR
+ FSL_SRDS_2
* 0x1000,
187 FSL_CORENET2_RCWSR4_SRDS2_PRTCL
,
188 FSL_CORENET2_RCWSR4_SRDS2_PRTCL_SHIFT
);
190 #ifdef CONFIG_SYS_FSL_SRDS_3
191 serdes3_prtcl_map
= serdes_init(FSL_SRDS_3
,
192 CONFIG_SYS_FSL_CORENET_SERDES_ADDR
+ FSL_SRDS_3
* 0x1000,
193 FSL_CORENET2_RCWSR4_SRDS3_PRTCL
,
194 FSL_CORENET2_RCWSR4_SRDS3_PRTCL_SHIFT
);
196 #ifdef CONFIG_SYS_FSL_SRDS_4
197 serdes4_prtcl_map
= serdes_init(FSL_SRDS_4
,
198 CONFIG_SYS_FSL_CORENET_SERDES_ADDR
+ FSL_SRDS_4
* 0x1000,
199 FSL_CORENET2_RCWSR4_SRDS4_PRTCL
,
200 FSL_CORENET2_RCWSR4_SRDS4_PRTCL_SHIFT
);