common: Move device-tree setup functions to fdt_support.h
[platform/kernel/u-boot.git] / board / freescale / b4860qds / b4860qds.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright 2011-2012 Freescale Semiconductor, Inc.
4  */
5
6 #include <common.h>
7 #include <command.h>
8 #include <env.h>
9 #include <fdt_support.h>
10 #include <i2c.h>
11 #include <init.h>
12 #include <irq_func.h>
13 #include <netdev.h>
14 #include <linux/compiler.h>
15 #include <asm/mmu.h>
16 #include <asm/processor.h>
17 #include <linux/errno.h>
18 #include <asm/cache.h>
19 #include <asm/immap_85xx.h>
20 #include <asm/fsl_law.h>
21 #include <asm/fsl_serdes.h>
22 #include <asm/fsl_liodn.h>
23 #include <fm_eth.h>
24 #include <hwconfig.h>
25
26 #include "../common/qixis.h"
27 #include "../common/vsc3316_3308.h"
28 #include "../common/idt8t49n222a_serdes_clk.h"
29 #include "../common/zm7300.h"
30 #include "b4860qds.h"
31 #include "b4860qds_qixis.h"
32 #include "b4860qds_crossbar_con.h"
33
34 #define CLK_MUX_SEL_MASK        0x4
35 #define ETH_PHY_CLK_OUT         0x4
36
37 DECLARE_GLOBAL_DATA_PTR;
38
39 int checkboard(void)
40 {
41         char buf[64];
42         u8 sw;
43         struct cpu_type *cpu = gd->arch.cpu;
44         static const char *const freq[] = {"100", "125", "156.25", "161.13",
45                                                 "122.88", "122.88", "122.88"};
46         int clock;
47
48         printf("Board: %sQDS, ", cpu->name);
49         printf("Sys ID: 0x%02x, Sys Ver: 0x%02x, ",
50                 QIXIS_READ(id), QIXIS_READ(arch));
51
52         sw = QIXIS_READ(brdcfg[0]);
53         sw = (sw & QIXIS_LBMAP_MASK) >> QIXIS_LBMAP_SHIFT;
54
55         if (sw < 0x8)
56                 printf("vBank: %d\n", sw);
57         else if (sw >= 0x8 && sw <= 0xE)
58                 puts("NAND\n");
59         else
60                 printf("invalid setting of SW%u\n", QIXIS_LBMAP_SWITCH);
61
62         printf("FPGA: v%d (%s), build %d",
63                 (int)QIXIS_READ(scver), qixis_read_tag(buf),
64                 (int)qixis_read_minor());
65         /* the timestamp string contains "\n" at the end */
66         printf(" on %s", qixis_read_time(buf));
67
68         /*
69          * Display the actual SERDES reference clocks as configured by the
70          * dip switches on the board.  Note that the SWx registers could
71          * technically be set to force the reference clocks to match the
72          * values that the SERDES expects (or vice versa).  For now, however,
73          * we just display both values and hope the user notices when they
74          * don't match.
75          */
76         puts("SERDES Reference Clocks: ");
77         sw = QIXIS_READ(brdcfg[2]);
78         clock = (sw >> 5) & 7;
79         printf("Bank1=%sMHz ", freq[clock]);
80         sw = QIXIS_READ(brdcfg[4]);
81         clock = (sw >> 6) & 3;
82         printf("Bank2=%sMHz\n", freq[clock]);
83
84         return 0;
85 }
86
87 int select_i2c_ch_pca(u8 ch)
88 {
89         int ret;
90
91         /* Selecting proper channel via PCA*/
92         ret = i2c_write(I2C_MUX_PCA_ADDR, 0x0, 1, &ch, 1);
93         if (ret) {
94                 printf("PCA: failed to select proper channel.\n");
95                 return ret;
96         }
97
98         return 0;
99 }
100
101 /*
102  * read_voltage from sensor on I2C bus
103  * We use average of 4 readings, waiting for 532us befor another reading
104  */
105 #define WAIT_FOR_ADC    532     /* wait for 532 microseconds for ADC */
106 #define NUM_READINGS    4       /* prefer to be power of 2 for efficiency */
107
108 static inline int read_voltage(void)
109 {
110         int i, ret, voltage_read = 0;
111         u16 vol_mon;
112
113         for (i = 0; i < NUM_READINGS; i++) {
114                 ret = i2c_read(I2C_VOL_MONITOR_ADDR,
115                         I2C_VOL_MONITOR_BUS_V_OFFSET, 1, (void *)&vol_mon, 2);
116                 if (ret) {
117                         printf("VID: failed to read core voltage\n");
118                         return ret;
119                 }
120                 if (vol_mon & I2C_VOL_MONITOR_BUS_V_OVF) {
121                         printf("VID: Core voltage sensor error\n");
122                         return -1;
123                 }
124                 debug("VID: bus voltage reads 0x%04x\n", vol_mon);
125                 /* LSB = 4mv */
126                 voltage_read += (vol_mon >> I2C_VOL_MONITOR_BUS_V_SHIFT) * 4;
127                 udelay(WAIT_FOR_ADC);
128         }
129         /* calculate the average */
130         voltage_read /= NUM_READINGS;
131
132         return voltage_read;
133 }
134
135 static int adjust_vdd(ulong vdd_override)
136 {
137         int re_enable = disable_interrupts();
138         ccsr_gur_t __iomem *gur =
139                 (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
140         u32 fusesr;
141         u8 vid;
142         int vdd_target, vdd_last;
143         int existing_voltage, temp_voltage, voltage; /* all in 1/10 mV */
144         int ret;
145         unsigned int orig_i2c_speed;
146         unsigned long vdd_string_override;
147         char *vdd_string;
148         static const uint16_t vdd[32] = {
149                 0,      /* unused */
150                 9875,   /* 0.9875V */
151                 9750,
152                 9625,
153                 9500,
154                 9375,
155                 9250,
156                 9125,
157                 9000,
158                 8875,
159                 8750,
160                 8625,
161                 8500,
162                 8375,
163                 8250,
164                 8125,
165                 10000,  /* 1.0000V */
166                 10125,
167                 10250,
168                 10375,
169                 10500,
170                 10625,
171                 10750,
172                 10875,
173                 11000,
174                 0,      /* reserved */
175         };
176         struct vdd_drive {
177                 u8 vid;
178                 unsigned voltage;
179         };
180
181         ret = select_i2c_ch_pca(I2C_MUX_CH_VOL_MONITOR);
182         if (ret) {
183                 printf("VID: I2c failed to switch channel\n");
184                 ret = -1;
185                 goto exit;
186         }
187
188         /* get the voltage ID from fuse status register */
189         fusesr = in_be32(&gur->dcfg_fusesr);
190         vid = (fusesr >> FSL_CORENET_DCFG_FUSESR_VID_SHIFT) &
191                 FSL_CORENET_DCFG_FUSESR_VID_MASK;
192         if (vid == FSL_CORENET_DCFG_FUSESR_VID_MASK) {
193                 vid = (fusesr >> FSL_CORENET_DCFG_FUSESR_ALTVID_SHIFT) &
194                         FSL_CORENET_DCFG_FUSESR_ALTVID_MASK;
195         }
196         vdd_target = vdd[vid];
197         debug("VID:Reading from from fuse,vid=%x vdd is %dmV\n",
198               vid, vdd_target/10);
199
200         /* check override variable for overriding VDD */
201         vdd_string = env_get("b4qds_vdd_mv");
202         if (vdd_override == 0 && vdd_string &&
203             !strict_strtoul(vdd_string, 10, &vdd_string_override))
204                 vdd_override = vdd_string_override;
205         if (vdd_override >= 819 && vdd_override <= 1212) {
206                 vdd_target = vdd_override * 10; /* convert to 1/10 mV */
207                 debug("VDD override is %lu\n", vdd_override);
208         } else if (vdd_override != 0) {
209                 printf("Invalid value.\n");
210         }
211
212         if (vdd_target == 0) {
213                 printf("VID: VID not used\n");
214                 ret = 0;
215                 goto exit;
216         }
217
218         /*
219          * Read voltage monitor to check real voltage.
220          * Voltage monitor LSB is 4mv.
221          */
222         vdd_last = read_voltage();
223         if (vdd_last < 0) {
224                 printf("VID: abort VID adjustment\n");
225                 ret = -1;
226                 goto exit;
227         }
228
229         debug("VID: Core voltage is at %d mV\n", vdd_last);
230         ret = select_i2c_ch_pca(I2C_MUX_CH_DPM);
231         if (ret) {
232                 printf("VID: I2c failed to switch channel to DPM\n");
233                 ret = -1;
234                 goto exit;
235         }
236
237         /* Round up to the value of step of Voltage regulator */
238         voltage = roundup(vdd_target, ZM_STEP);
239         debug("VID: rounded up voltage = %d\n", voltage);
240
241         /* lower the speed to 100kHz to access ZM7300 device */
242         debug("VID: Setting bus speed to 100KHz if not already set\n");
243         orig_i2c_speed = i2c_get_bus_speed();
244         if (orig_i2c_speed != 100000)
245                 i2c_set_bus_speed(100000);
246
247         /* Read the existing level on board, if equal to requsted one,
248            no need to re-set */
249         existing_voltage = zm_read_voltage();
250
251         /* allowing the voltage difference of one step 0.0125V acceptable */
252         if ((existing_voltage >= voltage) &&
253             (existing_voltage < (voltage + ZM_STEP))) {
254                 debug("VID: voltage already set as requested,returning\n");
255                 ret = existing_voltage;
256                 goto out;
257         }
258         debug("VID: Changing voltage for board from %dmV to %dmV\n",
259               existing_voltage/10, voltage/10);
260
261         if (zm_disable_wp() < 0) {
262                 ret = -1;
263                 goto out;
264         }
265         /* Change Voltage: the change is done through all the steps in the
266            way, to avoid reset to the board due to power good signal fail
267            in big voltage change gap jump.
268         */
269         if (existing_voltage > voltage) {
270                 temp_voltage = existing_voltage - ZM_STEP;
271                         while (temp_voltage >= voltage) {
272                                 ret = zm_write_voltage(temp_voltage);
273                                 if (ret == temp_voltage) {
274                                         temp_voltage -= ZM_STEP;
275                                 } else {
276                                         /* ZM7300 device failed to set
277                                          * the voltage */
278                                         printf
279                                         ("VID:Stepping down vol failed:%dmV\n",
280                                          temp_voltage/10);
281                                      ret = -1;
282                                      goto out;
283                                 }
284                         }
285         } else {
286                 temp_voltage = existing_voltage + ZM_STEP;
287                         while (temp_voltage < (voltage + ZM_STEP)) {
288                                 ret = zm_write_voltage(temp_voltage);
289                                 if (ret == temp_voltage) {
290                                         temp_voltage += ZM_STEP;
291                                 } else {
292                                         /* ZM7300 device failed to set
293                                          * the voltage */
294                                         printf
295                                         ("VID:Stepping up vol failed:%dmV\n",
296                                          temp_voltage/10);
297                                      ret = -1;
298                                      goto out;
299                                 }
300                         }
301         }
302
303         if (zm_enable_wp() < 0)
304                 ret = -1;
305
306         /* restore the speed to 400kHz */
307 out:    debug("VID: Restore the I2C bus speed to %dKHz\n",
308                                 orig_i2c_speed/1000);
309         i2c_set_bus_speed(orig_i2c_speed);
310         if (ret < 0)
311                 goto exit;
312
313         ret = select_i2c_ch_pca(I2C_MUX_CH_VOL_MONITOR);
314         if (ret) {
315                 printf("VID: I2c failed to switch channel\n");
316                 ret = -1;
317                 goto exit;
318         }
319         vdd_last = read_voltage();
320         select_i2c_ch_pca(I2C_CH_DEFAULT);
321
322         if (vdd_last > 0)
323                 printf("VID: Core voltage %d mV\n", vdd_last);
324         else
325                 ret = -1;
326
327 exit:
328         if (re_enable)
329                 enable_interrupts();
330         return ret;
331 }
332
333 int configure_vsc3316_3308(void)
334 {
335         ccsr_gur_t *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
336         unsigned int num_vsc16_con, num_vsc08_con;
337         u32 serdes1_prtcl, serdes2_prtcl;
338         int ret;
339         char buffer[HWCONFIG_BUFFER_SIZE];
340         char *buf = NULL;
341
342         serdes1_prtcl = in_be32(&gur->rcwsr[4]) &
343                         FSL_CORENET2_RCWSR4_SRDS1_PRTCL;
344         if (!serdes1_prtcl) {
345                 printf("SERDES1 is not enabled\n");
346                 return 0;
347         }
348         serdes1_prtcl >>= FSL_CORENET2_RCWSR4_SRDS1_PRTCL_SHIFT;
349         debug("Using SERDES1 Protocol: 0x%x:\n", serdes1_prtcl);
350
351         serdes2_prtcl = in_be32(&gur->rcwsr[4]) &
352                         FSL_CORENET2_RCWSR4_SRDS2_PRTCL;
353         if (!serdes2_prtcl) {
354                 printf("SERDES2 is not enabled\n");
355                 return 0;
356         }
357         serdes2_prtcl >>= FSL_CORENET2_RCWSR4_SRDS2_PRTCL_SHIFT;
358         debug("Using SERDES2 Protocol: 0x%x:\n", serdes2_prtcl);
359
360         switch (serdes1_prtcl) {
361         case 0x29:
362         case 0x2a:
363         case 0x2C:
364         case 0x2D:
365         case 0x2E:
366                         /*
367                          * Configuration:
368                          * SERDES: 1
369                          * Lanes: A,B: SGMII
370                          * Lanes: C,D,E,F,G,H: CPRI
371                          */
372                 debug("Configuring crossbar to use onboard SGMII PHYs:"
373                                 "srds_prctl:%x\n", serdes1_prtcl);
374                 num_vsc16_con = NUM_CON_VSC3316;
375                 /* Configure VSC3316 crossbar switch */
376                 ret = select_i2c_ch_pca(I2C_CH_VSC3316);
377                 if (!ret) {
378                         ret = vsc3316_config(VSC3316_TX_ADDRESS,
379                                         vsc16_tx_4sfp_sgmii_12_56,
380                                         num_vsc16_con);
381                         if (ret)
382                                 return ret;
383                         ret = vsc3316_config(VSC3316_RX_ADDRESS,
384                                         vsc16_rx_4sfp_sgmii_12_56,
385                                         num_vsc16_con);
386                         if (ret)
387                                 return ret;
388                 } else {
389                         return ret;
390                 }
391                 break;
392
393         case 0x01:
394         case 0x02:
395         case 0x04:
396         case 0x05:
397         case 0x06:
398         case 0x07:
399         case 0x08:
400         case 0x09:
401         case 0x0A:
402         case 0x0B:
403         case 0x0C:
404         case 0x2F:
405         case 0x30:
406         case 0x32:
407         case 0x33:
408         case 0x34:
409         case 0x39:
410         case 0x3A:
411         case 0x3C:
412         case 0x3D:
413         case 0x5C:
414         case 0x5D:
415                         /*
416                          * Configuration:
417                          * SERDES: 1
418                          * Lanes: A,B: AURORA
419                          * Lanes: C,d: SGMII
420                          * Lanes: E,F,G,H: CPRI
421                          */
422                 debug("Configuring crossbar for Aurora, SGMII 3 and 4,"
423                                 " and CPRI. srds_prctl:%x\n", serdes1_prtcl);
424                 num_vsc16_con = NUM_CON_VSC3316;
425                 /* Configure VSC3316 crossbar switch */
426                 ret = select_i2c_ch_pca(I2C_CH_VSC3316);
427                 if (!ret) {
428                         ret = vsc3316_config(VSC3316_TX_ADDRESS,
429                                         vsc16_tx_sfp_sgmii_aurora,
430                                         num_vsc16_con);
431                         if (ret)
432                                 return ret;
433                         ret = vsc3316_config(VSC3316_RX_ADDRESS,
434                                         vsc16_rx_sfp_sgmii_aurora,
435                                         num_vsc16_con);
436                         if (ret)
437                                 return ret;
438                 } else {
439                         return ret;
440                 }
441                 break;
442
443 #ifdef CONFIG_ARCH_B4420
444         case 0x17:
445         case 0x18:
446                         /*
447                          * Configuration:
448                          * SERDES: 1
449                          * Lanes: A,B,C,D: SGMII
450                          * Lanes: E,F,G,H: CPRI
451                          */
452                 debug("Configuring crossbar to use onboard SGMII PHYs:"
453                                 "srds_prctl:%x\n", serdes1_prtcl);
454                 num_vsc16_con = NUM_CON_VSC3316;
455                 /* Configure VSC3316 crossbar switch */
456                 ret = select_i2c_ch_pca(I2C_CH_VSC3316);
457                 if (!ret) {
458                         ret = vsc3316_config(VSC3316_TX_ADDRESS,
459                                         vsc16_tx_sgmii_lane_cd, num_vsc16_con);
460                         if (ret)
461                                 return ret;
462                         ret = vsc3316_config(VSC3316_RX_ADDRESS,
463                                         vsc16_rx_sgmii_lane_cd, num_vsc16_con);
464                         if (ret)
465                                 return ret;
466                 } else {
467                         return ret;
468                 }
469                 break;
470 #endif
471
472         case 0x3E:
473         case 0x0D:
474         case 0x0E:
475         case 0x12:
476                 num_vsc16_con = NUM_CON_VSC3316;
477                 /* Configure VSC3316 crossbar switch */
478                 ret = select_i2c_ch_pca(I2C_CH_VSC3316);
479                 if (!ret) {
480                         ret = vsc3316_config(VSC3316_TX_ADDRESS,
481                                         vsc16_tx_sfp, num_vsc16_con);
482                         if (ret)
483                                 return ret;
484                         ret = vsc3316_config(VSC3316_RX_ADDRESS,
485                                         vsc16_rx_sfp, num_vsc16_con);
486                         if (ret)
487                                 return ret;
488                 } else {
489                         return ret;
490                 }
491                 break;
492         default:
493                 printf("WARNING:VSC crossbars programming not supported for:%x"
494                                         " SerDes1 Protocol.\n", serdes1_prtcl);
495                 return -1;
496         }
497
498         num_vsc08_con = NUM_CON_VSC3308;
499         /* Configure VSC3308 crossbar switch */
500         ret = select_i2c_ch_pca(I2C_CH_VSC3308);
501         switch (serdes2_prtcl) {
502 #ifdef CONFIG_ARCH_B4420
503         case 0x9d:
504 #endif
505         case 0x9E:
506         case 0x9A:
507         case 0x98:
508         case 0x48:
509         case 0x49:
510         case 0x4E:
511         case 0x79:
512         case 0x7A:
513                 if (!ret) {
514                         ret = vsc3308_config(VSC3308_TX_ADDRESS,
515                                         vsc08_tx_amc, num_vsc08_con);
516                         if (ret)
517                                 return ret;
518                         ret = vsc3308_config(VSC3308_RX_ADDRESS,
519                                         vsc08_rx_amc, num_vsc08_con);
520                         if (ret)
521                                 return ret;
522                 } else {
523                         return ret;
524                 }
525                 break;
526         case 0x80:
527         case 0x81:
528         case 0x82:
529         case 0x83:
530         case 0x84:
531         case 0x85:
532         case 0x86:
533         case 0x87:
534         case 0x88:
535         case 0x89:
536         case 0x8a:
537         case 0x8b:
538         case 0x8c:
539         case 0x8d:
540         case 0x8e:
541         case 0xb1:
542         case 0xb2:
543                 if (!ret) {
544                         /*
545                          * Extract hwconfig from environment since environment
546                          * is not setup properly yet
547                          */
548                         env_get_f("hwconfig", buffer, sizeof(buffer));
549                         buf = buffer;
550
551                         if (hwconfig_subarg_cmp_f("fsl_b4860_serdes2",
552                                                   "sfp_amc", "sfp", buf)) {
553 #ifdef CONFIG_SYS_FSL_B4860QDS_XFI_ERR
554                                 /* change default VSC3308 for XFI erratum */
555                                 ret = vsc3308_config_adjust(VSC3308_TX_ADDRESS,
556                                                 vsc08_tx_sfp, num_vsc08_con);
557                                 if (ret)
558                                         return ret;
559
560                                 ret = vsc3308_config_adjust(VSC3308_RX_ADDRESS,
561                                                 vsc08_rx_sfp, num_vsc08_con);
562                                 if (ret)
563                                         return ret;
564 #else
565                                 ret = vsc3308_config(VSC3308_TX_ADDRESS,
566                                                 vsc08_tx_sfp, num_vsc08_con);
567                                 if (ret)
568                                         return ret;
569
570                                 ret = vsc3308_config(VSC3308_RX_ADDRESS,
571                                                 vsc08_rx_sfp, num_vsc08_con);
572                                 if (ret)
573                                         return ret;
574 #endif
575                         } else {
576                                 ret = vsc3308_config(VSC3308_TX_ADDRESS,
577                                                 vsc08_tx_amc, num_vsc08_con);
578                                 if (ret)
579                                         return ret;
580
581                                 ret = vsc3308_config(VSC3308_RX_ADDRESS,
582                                                 vsc08_rx_amc, num_vsc08_con);
583                                 if (ret)
584                                         return ret;
585                         }
586
587                 } else {
588                         return ret;
589                 }
590                 break;
591         default:
592                 printf("WARNING:VSC crossbars programming not supported for: %x"
593                                         " SerDes2 Protocol.\n", serdes2_prtcl);
594                 return -1;
595         }
596
597         return 0;
598 }
599
600 static int calibrate_pll(serdes_corenet_t *srds_regs, int pll_num)
601 {
602         u32 rst_err;
603
604         /* Steps For SerDes PLLs reset and reconfiguration
605          * or PLL power-up procedure
606          */
607         debug("CALIBRATE PLL:%d\n", pll_num);
608         clrbits_be32(&srds_regs->bank[pll_num].rstctl,
609                         SRDS_RSTCTL_SDRST_B);
610         udelay(10);
611         clrbits_be32(&srds_regs->bank[pll_num].rstctl,
612                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B));
613         udelay(10);
614         setbits_be32(&srds_regs->bank[pll_num].rstctl,
615                         SRDS_RSTCTL_RST);
616         setbits_be32(&srds_regs->bank[pll_num].rstctl,
617                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
618                 | SRDS_RSTCTL_SDRST_B));
619
620         udelay(20);
621
622         /* Check whether PLL has been locked or not */
623         rst_err = in_be32(&srds_regs->bank[pll_num].rstctl) &
624                                 SRDS_RSTCTL_RSTERR;
625         rst_err >>= SRDS_RSTCTL_RSTERR_SHIFT;
626         debug("RST_ERR value for PLL %d is: 0x%x:\n", pll_num, rst_err);
627         if (rst_err)
628                 return rst_err;
629
630         return rst_err;
631 }
632
633 static int check_pll_locks(serdes_corenet_t *srds_regs, int pll_num)
634 {
635         int ret = 0;
636         u32 fcap, dcbias, bcap, pllcr1, pllcr0;
637
638         if (calibrate_pll(srds_regs, pll_num)) {
639                 /* STEP 1 */
640                 /* Read fcap, dcbias and bcap value */
641                 clrbits_be32(&srds_regs->bank[pll_num].pllcr0,
642                                 SRDS_PLLCR0_DCBIAS_OUT_EN);
643                 fcap = in_be32(&srds_regs->bank[pll_num].pllsr2) &
644                                         SRDS_PLLSR2_FCAP;
645                 fcap >>= SRDS_PLLSR2_FCAP_SHIFT;
646                 bcap = in_be32(&srds_regs->bank[pll_num].pllsr2) &
647                                         SRDS_PLLSR2_BCAP_EN;
648                 bcap >>= SRDS_PLLSR2_BCAP_EN_SHIFT;
649                 setbits_be32(&srds_regs->bank[pll_num].pllcr0,
650                                 SRDS_PLLCR0_DCBIAS_OUT_EN);
651                 dcbias = in_be32(&srds_regs->bank[pll_num].pllsr2) &
652                                         SRDS_PLLSR2_DCBIAS;
653                 dcbias >>= SRDS_PLLSR2_DCBIAS_SHIFT;
654                 debug("values of bcap:%x, fcap:%x and dcbias:%x\n",
655                                         bcap, fcap, dcbias);
656                 if (fcap == 0 && bcap == 1) {
657                         /* Step 3 */
658                         clrbits_be32(&srds_regs->bank[pll_num].rstctl,
659                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
660                                  | SRDS_RSTCTL_SDRST_B));
661                         clrbits_be32(&srds_regs->bank[pll_num].pllcr1,
662                                         SRDS_PLLCR1_BCAP_EN);
663                         setbits_be32(&srds_regs->bank[pll_num].pllcr1,
664                                         SRDS_PLLCR1_BCAP_OVD);
665                         if (calibrate_pll(srds_regs, pll_num)) {
666                                 /*save the fcap, dcbias and bcap values*/
667                                 clrbits_be32(&srds_regs->bank[pll_num].pllcr0,
668                                                 SRDS_PLLCR0_DCBIAS_OUT_EN);
669                                 fcap = in_be32(&srds_regs->bank[pll_num].pllsr2)
670                                         & SRDS_PLLSR2_FCAP;
671                                 fcap >>= SRDS_PLLSR2_FCAP_SHIFT;
672                                 bcap = in_be32(&srds_regs->bank[pll_num].pllsr2)
673                                         & SRDS_PLLSR2_BCAP_EN;
674                                 bcap >>= SRDS_PLLSR2_BCAP_EN_SHIFT;
675                                 setbits_be32(&srds_regs->bank[pll_num].pllcr0,
676                                                 SRDS_PLLCR0_DCBIAS_OUT_EN);
677                                 dcbias = in_be32
678                                         (&srds_regs->bank[pll_num].pllsr2) &
679                                                         SRDS_PLLSR2_DCBIAS;
680                                 dcbias >>= SRDS_PLLSR2_DCBIAS_SHIFT;
681
682                                 /* Step 4*/
683                                 clrbits_be32(&srds_regs->bank[pll_num].rstctl,
684                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
685                                  | SRDS_RSTCTL_SDRST_B));
686                                 setbits_be32(&srds_regs->bank[pll_num].pllcr1,
687                                                 SRDS_PLLCR1_BYP_CAL);
688                                 clrbits_be32(&srds_regs->bank[pll_num].pllcr1,
689                                                 SRDS_PLLCR1_BCAP_EN);
690                                 setbits_be32(&srds_regs->bank[pll_num].pllcr1,
691                                                 SRDS_PLLCR1_BCAP_OVD);
692                                 /* change the fcap and dcbias to the saved
693                                  * values from Step 3 */
694                                 clrbits_be32(&srds_regs->bank[pll_num].pllcr1,
695                                                         SRDS_PLLCR1_PLL_FCAP);
696                                 pllcr1 = (in_be32
697                                         (&srds_regs->bank[pll_num].pllcr1)|
698                                         (fcap << SRDS_PLLCR1_PLL_FCAP_SHIFT));
699                                 out_be32(&srds_regs->bank[pll_num].pllcr1,
700                                                         pllcr1);
701                                 clrbits_be32(&srds_regs->bank[pll_num].pllcr0,
702                                                 SRDS_PLLCR0_DCBIAS_OVRD);
703                                 pllcr0 = (in_be32
704                                 (&srds_regs->bank[pll_num].pllcr0)|
705                                 (dcbias << SRDS_PLLCR0_DCBIAS_OVRD_SHIFT));
706                                 out_be32(&srds_regs->bank[pll_num].pllcr0,
707                                                         pllcr0);
708                                 ret = calibrate_pll(srds_regs, pll_num);
709                                 if (ret)
710                                         return ret;
711                         } else {
712                                 goto out;
713                         }
714                 } else { /* Step 5 */
715                         clrbits_be32(&srds_regs->bank[pll_num].rstctl,
716                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
717                                  | SRDS_RSTCTL_SDRST_B));
718                         udelay(10);
719                         /* Change the fcap, dcbias, and bcap to the
720                          * values from Step 1 */
721                         setbits_be32(&srds_regs->bank[pll_num].pllcr1,
722                                         SRDS_PLLCR1_BYP_CAL);
723                         clrbits_be32(&srds_regs->bank[pll_num].pllcr1,
724                                                 SRDS_PLLCR1_PLL_FCAP);
725                         pllcr1 = (in_be32(&srds_regs->bank[pll_num].pllcr1)|
726                                 (fcap << SRDS_PLLCR1_PLL_FCAP_SHIFT));
727                         out_be32(&srds_regs->bank[pll_num].pllcr1,
728                                                 pllcr1);
729                         clrbits_be32(&srds_regs->bank[pll_num].pllcr0,
730                                                 SRDS_PLLCR0_DCBIAS_OVRD);
731                         pllcr0 = (in_be32(&srds_regs->bank[pll_num].pllcr0)|
732                                 (dcbias << SRDS_PLLCR0_DCBIAS_OVRD_SHIFT));
733                         out_be32(&srds_regs->bank[pll_num].pllcr0,
734                                                 pllcr0);
735                         clrbits_be32(&srds_regs->bank[pll_num].pllcr1,
736                                         SRDS_PLLCR1_BCAP_EN);
737                         setbits_be32(&srds_regs->bank[pll_num].pllcr1,
738                                         SRDS_PLLCR1_BCAP_OVD);
739                         ret = calibrate_pll(srds_regs, pll_num);
740                         if (ret)
741                                 return ret;
742                 }
743         }
744 out:
745         return 0;
746 }
747
748 static int check_serdes_pll_locks(void)
749 {
750         serdes_corenet_t *srds1_regs =
751                 (void *)CONFIG_SYS_FSL_CORENET_SERDES_ADDR;
752         serdes_corenet_t *srds2_regs =
753                 (void *)CONFIG_SYS_FSL_CORENET_SERDES2_ADDR;
754         int i, ret1, ret2;
755
756         debug("\nSerDes1 Lock check\n");
757         for (i = 0; i < CONFIG_SYS_FSL_SRDS_NUM_PLLS; i++) {
758                 ret1 = check_pll_locks(srds1_regs, i);
759                 if (ret1) {
760                         printf("SerDes1, PLL:%d didnt lock\n", i);
761                         return ret1;
762                 }
763         }
764         debug("\nSerDes2 Lock check\n");
765         for (i = 0; i < CONFIG_SYS_FSL_SRDS_NUM_PLLS; i++) {
766                 ret2 = check_pll_locks(srds2_regs, i);
767                 if (ret2) {
768                         printf("SerDes2, PLL:%d didnt lock\n", i);
769                         return ret2;
770                 }
771         }
772
773         return 0;
774 }
775
776 int config_serdes1_refclks(void)
777 {
778         ccsr_gur_t *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
779         serdes_corenet_t *srds_regs =
780                 (void *)CONFIG_SYS_FSL_CORENET_SERDES_ADDR;
781         u32 serdes1_prtcl, lane;
782         unsigned int flag_sgmii_aurora_prtcl = 0;
783         int i;
784         int ret = 0;
785
786         serdes1_prtcl = in_be32(&gur->rcwsr[4]) &
787                         FSL_CORENET2_RCWSR4_SRDS1_PRTCL;
788         if (!serdes1_prtcl) {
789                 printf("SERDES1 is not enabled\n");
790                 return -1;
791         }
792         serdes1_prtcl >>= FSL_CORENET2_RCWSR4_SRDS1_PRTCL_SHIFT;
793         debug("Using SERDES1 Protocol: 0x%x:\n", serdes1_prtcl);
794
795         /* To prevent generation of reset request from SerDes
796          * while changing the refclks, By setting SRDS_RST_MSK bit,
797          * SerDes reset event cannot cause a reset request
798          */
799         setbits_be32(&gur->rstrqmr1, FSL_CORENET_RSTRQMR1_SRDS_RST_MSK);
800
801         /* Reconfigure IDT idt8t49n222a device for CPRI to work
802          * For this SerDes1's Refclk1 and refclk2 need to be set
803          * to 122.88MHz
804          */
805         switch (serdes1_prtcl) {
806         case 0x29:
807         case 0x2A:
808         case 0x2C:
809         case 0x2D:
810         case 0x2E:
811         case 0x01:
812         case 0x02:
813         case 0x04:
814         case 0x05:
815         case 0x06:
816         case 0x07:
817         case 0x08:
818         case 0x09:
819         case 0x0A:
820         case 0x0B:
821         case 0x0C:
822         case 0x2F:
823         case 0x30:
824         case 0x32:
825         case 0x33:
826         case 0x34:
827         case 0x39:
828         case 0x3A:
829         case 0x3C:
830         case 0x3D:
831         case 0x5C:
832         case 0x5D:
833                 debug("Configuring idt8t49n222a for CPRI SerDes clks:"
834                         " for srds_prctl:%x\n", serdes1_prtcl);
835                 ret = select_i2c_ch_pca(I2C_CH_IDT);
836                 if (!ret) {
837                         ret = set_serdes_refclk(IDT_SERDES1_ADDRESS, 1,
838                                         SERDES_REFCLK_122_88,
839                                         SERDES_REFCLK_122_88, 0);
840                         if (ret) {
841                                 printf("IDT8T49N222A configuration failed.\n");
842                                 goto out;
843                         } else
844                                 debug("IDT8T49N222A configured.\n");
845                 } else {
846                         goto out;
847                 }
848                 select_i2c_ch_pca(I2C_CH_DEFAULT);
849
850                 /* Change SerDes1's Refclk1 to 125MHz for on board
851                  * SGMIIs or Aurora to work
852                  */
853                 for (lane = 0; lane < SRDS_MAX_LANES; lane++) {
854                         enum srds_prtcl lane_prtcl = serdes_get_prtcl
855                                                 (0, serdes1_prtcl, lane);
856                         switch (lane_prtcl) {
857                         case SGMII_FM1_DTSEC1:
858                         case SGMII_FM1_DTSEC2:
859                         case SGMII_FM1_DTSEC3:
860                         case SGMII_FM1_DTSEC4:
861                         case SGMII_FM1_DTSEC5:
862                         case SGMII_FM1_DTSEC6:
863                         case AURORA:
864                                 flag_sgmii_aurora_prtcl++;
865                                 break;
866                         default:
867                                 break;
868                         }
869                 }
870
871                 if (flag_sgmii_aurora_prtcl)
872                         QIXIS_WRITE(brdcfg[4], QIXIS_SRDS1CLK_125);
873
874                 /* Steps For SerDes PLLs reset and reconfiguration after
875                  * changing SerDes's refclks
876                  */
877                 for (i = 0; i < CONFIG_SYS_FSL_SRDS_NUM_PLLS; i++) {
878                         debug("For PLL%d reset and reconfiguration after"
879                                " changing refclks\n", i+1);
880                         clrbits_be32(&srds_regs->bank[i].rstctl,
881                                         SRDS_RSTCTL_SDRST_B);
882                         udelay(10);
883                         clrbits_be32(&srds_regs->bank[i].rstctl,
884                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B));
885                         udelay(10);
886                         setbits_be32(&srds_regs->bank[i].rstctl,
887                                         SRDS_RSTCTL_RST);
888                         setbits_be32(&srds_regs->bank[i].rstctl,
889                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
890                                 | SRDS_RSTCTL_SDRST_B));
891                 }
892                 break;
893         default:
894                 printf("WARNING:IDT8T49N222A configuration not"
895                         " supported for:%x SerDes1 Protocol.\n",
896                         serdes1_prtcl);
897         }
898
899 out:
900         /* Clearing SRDS_RST_MSK bit as now
901          * SerDes reset event can cause a reset request
902          */
903         clrbits_be32(&gur->rstrqmr1, FSL_CORENET_RSTRQMR1_SRDS_RST_MSK);
904         return ret;
905 }
906
907 int config_serdes2_refclks(void)
908 {
909         ccsr_gur_t *gur = (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
910         serdes_corenet_t *srds2_regs =
911                 (void *)CONFIG_SYS_FSL_CORENET_SERDES2_ADDR;
912         u32 serdes2_prtcl;
913         int ret = 0;
914         int i;
915
916         serdes2_prtcl = in_be32(&gur->rcwsr[4]) &
917                         FSL_CORENET2_RCWSR4_SRDS2_PRTCL;
918         if (!serdes2_prtcl) {
919                 debug("SERDES2 is not enabled\n");
920                 return -ENODEV;
921         }
922         serdes2_prtcl >>= FSL_CORENET2_RCWSR4_SRDS2_PRTCL_SHIFT;
923         debug("Using SERDES2 Protocol: 0x%x:\n", serdes2_prtcl);
924
925         /* To prevent generation of reset request from SerDes
926          * while changing the refclks, By setting SRDS_RST_MSK bit,
927          * SerDes reset event cannot cause a reset request
928          */
929         setbits_be32(&gur->rstrqmr1, FSL_CORENET_RSTRQMR1_SRDS_RST_MSK);
930
931         /* Reconfigure IDT idt8t49n222a device for PCIe SATA to work
932          * For this SerDes2's Refclk1 need to be set to 100MHz
933          */
934         switch (serdes2_prtcl) {
935 #ifdef CONFIG_ARCH_B4420
936         case 0x9d:
937 #endif
938         case 0x9E:
939         case 0x9A:
940                 /* fallthrough */
941         case 0xb1:
942         case 0xb2:
943                 debug("Configuring IDT for PCIe SATA for srds_prctl:%x\n",
944                         serdes2_prtcl);
945                 ret = select_i2c_ch_pca(I2C_CH_IDT);
946                 if (!ret) {
947                         ret = set_serdes_refclk(IDT_SERDES2_ADDRESS, 2,
948                                         SERDES_REFCLK_100,
949                                         SERDES_REFCLK_156_25, 0);
950                         if (ret) {
951                                 printf("IDT8T49N222A configuration failed.\n");
952                                 goto out;
953                         } else
954                                 debug("IDT8T49N222A configured.\n");
955                 } else {
956                         goto out;
957                 }
958                 select_i2c_ch_pca(I2C_CH_DEFAULT);
959
960                 /* Steps For SerDes PLLs reset and reconfiguration after
961                  * changing SerDes's refclks
962                  */
963                 for (i = 0; i < CONFIG_SYS_FSL_SRDS_NUM_PLLS; i++) {
964                         clrbits_be32(&srds2_regs->bank[i].rstctl,
965                                         SRDS_RSTCTL_SDRST_B);
966                         udelay(10);
967                         clrbits_be32(&srds2_regs->bank[i].rstctl,
968                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B));
969                         udelay(10);
970                         setbits_be32(&srds2_regs->bank[i].rstctl,
971                                         SRDS_RSTCTL_RST);
972                         setbits_be32(&srds2_regs->bank[i].rstctl,
973                                 (SRDS_RSTCTL_SDEN | SRDS_RSTCTL_PLLRST_B
974                                 | SRDS_RSTCTL_SDRST_B));
975
976                         udelay(10);
977                 }
978                 break;
979         default:
980                 printf("IDT configuration not supported for:%x S2 Protocol.\n",
981                         serdes2_prtcl);
982         }
983
984 out:
985         /* Clearing SRDS_RST_MSK bit as now
986          * SerDes reset event can cause a reset request
987          */
988         clrbits_be32(&gur->rstrqmr1, FSL_CORENET_RSTRQMR1_SRDS_RST_MSK);
989         return ret;
990 }
991
992 int board_early_init_r(void)
993 {
994         const unsigned int flashbase = CONFIG_SYS_FLASH_BASE;
995         int flash_esel = find_tlb_idx((void *)flashbase, 1);
996         int ret;
997         u32 svr = SVR_SOC_VER(get_svr());
998
999         /* Create law for MAPLE only for personalities having MAPLE */
1000         if ((svr == SVR_B4860) || (svr == SVR_B4440) ||
1001             (svr == SVR_B4420) || (svr == SVR_B4220)) {
1002                 set_next_law(CONFIG_SYS_MAPLE_MEM_PHYS, LAW_SIZE_16M,
1003                              LAW_TRGT_IF_MAPLE);
1004         }
1005
1006         /*
1007          * Remap Boot flash + PROMJET region to caching-inhibited
1008          * so that flash can be erased properly.
1009          */
1010
1011         /* Flush d-cache and invalidate i-cache of any FLASH data */
1012         flush_dcache();
1013         invalidate_icache();
1014
1015         if (flash_esel == -1) {
1016                 /* very unlikely unless something is messed up */
1017                 puts("Error: Could not find TLB for FLASH BASE\n");
1018                 flash_esel = 2; /* give our best effort to continue */
1019         } else {
1020                 /* invalidate existing TLB entry for flash + promjet */
1021                 disable_tlb(flash_esel);
1022         }
1023
1024         set_tlb(1, flashbase, CONFIG_SYS_FLASH_BASE_PHYS,
1025                         MAS3_SX|MAS3_SW|MAS3_SR, MAS2_I|MAS2_G,
1026                         0, flash_esel, BOOKE_PAGESZ_256M, 1);
1027
1028         /*
1029          * Adjust core voltage according to voltage ID
1030          * This function changes I2C mux to channel 2.
1031          */
1032         if (adjust_vdd(0) < 0)
1033                 printf("Warning: Adjusting core voltage failed\n");
1034
1035         /* SerDes1 refclks need to be set again, as default clks
1036          * are not suitable for CPRI and onboard SGMIIs to work
1037          * simultaneously.
1038          * This function will set SerDes1's Refclk1 and refclk2
1039          * as per SerDes1 protocols
1040          */
1041         if (config_serdes1_refclks())
1042                 printf("SerDes1 Refclks couldn't set properly.\n");
1043         else
1044                 printf("SerDes1 Refclks have been set.\n");
1045
1046         /* SerDes2 refclks need to be set again, as default clks
1047          * are not suitable for PCIe SATA to work
1048          * This function will set SerDes2's Refclk1 and refclk2
1049          * for SerDes2 protocols having PCIe in them
1050          * for PCIe SATA to work
1051          */
1052         ret = config_serdes2_refclks();
1053         if (!ret)
1054                 printf("SerDes2 Refclks have been set.\n");
1055         else if (ret == -ENODEV)
1056                 printf("SerDes disable, Refclks couldn't change.\n");
1057         else
1058                 printf("SerDes2 Refclk reconfiguring failed.\n");
1059
1060 #if defined(CONFIG_SYS_FSL_ERRATUM_A006384) || \
1061                         defined(CONFIG_SYS_FSL_ERRATUM_A006475)
1062         /* Rechecking the SerDes locks after all SerDes configurations
1063          * are done, As SerDes PLLs may not lock reliably at 5 G VCO
1064          * and at cold temperatures.
1065          * Following sequence ensure the proper locking of SerDes PLLs.
1066          */
1067         if (SVR_MAJ(get_svr()) == 1) {
1068                 if (check_serdes_pll_locks())
1069                         printf("SerDes plls still not locked properly.\n");
1070                 else
1071                         printf("SerDes plls have been locked well.\n");
1072         }
1073 #endif
1074
1075         /* Configure VSC3316 and VSC3308 crossbar switches */
1076         if (configure_vsc3316_3308())
1077                 printf("VSC:failed to configure VSC3316/3308.\n");
1078         else
1079                 printf("VSC:VSC3316/3308 successfully configured.\n");
1080
1081         select_i2c_ch_pca(I2C_CH_DEFAULT);
1082
1083         return 0;
1084 }
1085
1086 unsigned long get_board_sys_clk(void)
1087 {
1088         u8 sysclk_conf = QIXIS_READ(brdcfg[1]);
1089
1090         switch ((sysclk_conf & 0x0C) >> 2) {
1091         case QIXIS_CLK_100:
1092                 return 100000000;
1093         case QIXIS_CLK_125:
1094                 return 125000000;
1095         case QIXIS_CLK_133:
1096                 return 133333333;
1097         }
1098         return 66666666;
1099 }
1100
1101 unsigned long get_board_ddr_clk(void)
1102 {
1103         u8 ddrclk_conf = QIXIS_READ(brdcfg[1]);
1104
1105         switch (ddrclk_conf & 0x03) {
1106         case QIXIS_CLK_100:
1107                 return 100000000;
1108         case QIXIS_CLK_125:
1109                 return 125000000;
1110         case QIXIS_CLK_133:
1111                 return 133333333;
1112         }
1113         return 66666666;
1114 }
1115
1116 static int serdes_refclock(u8 sw, u8 sdclk)
1117 {
1118         unsigned int clock;
1119         int ret = -1;
1120         u8 brdcfg4;
1121
1122         if (sdclk == 1) {
1123                 brdcfg4 = QIXIS_READ(brdcfg[4]);
1124                 if ((brdcfg4 & CLK_MUX_SEL_MASK) == ETH_PHY_CLK_OUT)
1125                         return SRDS_PLLCR0_RFCK_SEL_125;
1126                 else
1127                         clock = (sw >> 5) & 7;
1128         } else
1129                 clock = (sw >> 6) & 3;
1130
1131         switch (clock) {
1132         case 0:
1133                 ret = SRDS_PLLCR0_RFCK_SEL_100;
1134                 break;
1135         case 1:
1136                 ret = SRDS_PLLCR0_RFCK_SEL_125;
1137                 break;
1138         case 2:
1139                 ret = SRDS_PLLCR0_RFCK_SEL_156_25;
1140                 break;
1141         case 3:
1142                 ret = SRDS_PLLCR0_RFCK_SEL_161_13;
1143                 break;
1144         case 4:
1145         case 5:
1146         case 6:
1147                 ret = SRDS_PLLCR0_RFCK_SEL_122_88;
1148                 break;
1149         default:
1150                 ret = -1;
1151                 break;
1152         }
1153
1154         return ret;
1155 }
1156
1157 #define NUM_SRDS_BANKS  2
1158
1159 int misc_init_r(void)
1160 {
1161         u8 sw;
1162         serdes_corenet_t *srds_regs =
1163                 (void *)CONFIG_SYS_FSL_CORENET_SERDES_ADDR;
1164         u32 actual[NUM_SRDS_BANKS];
1165         unsigned int i;
1166         int clock;
1167
1168         sw = QIXIS_READ(brdcfg[2]);
1169         clock = serdes_refclock(sw, 1);
1170         if (clock >= 0)
1171                 actual[0] = clock;
1172         else
1173                 printf("Warning: SDREFCLK1 switch setting is unsupported\n");
1174
1175         sw = QIXIS_READ(brdcfg[4]);
1176         clock = serdes_refclock(sw, 2);
1177         if (clock >= 0)
1178                 actual[1] = clock;
1179         else
1180                 printf("Warning: SDREFCLK2 switch setting unsupported\n");
1181
1182         for (i = 0; i < NUM_SRDS_BANKS; i++) {
1183                 u32 pllcr0 = srds_regs->bank[i].pllcr0;
1184                 u32 expected = pllcr0 & SRDS_PLLCR0_RFCK_SEL_MASK;
1185                 if (expected != actual[i]) {
1186                         printf("Warning: SERDES bank %u expects reference clock"
1187                                " %sMHz, but actual is %sMHz\n", i + 1,
1188                                serdes_clock_to_string(expected),
1189                                serdes_clock_to_string(actual[i]));
1190                 }
1191         }
1192
1193         return 0;
1194 }
1195
1196 int ft_board_setup(void *blob, bd_t *bd)
1197 {
1198         phys_addr_t base;
1199         phys_size_t size;
1200
1201         ft_cpu_setup(blob, bd);
1202
1203         base = env_get_bootm_low();
1204         size = env_get_bootm_size();
1205
1206         fdt_fixup_memory(blob, (u64)base, (u64)size);
1207
1208 #ifdef CONFIG_PCI
1209         pci_of_setup(blob, bd);
1210 #endif
1211
1212         fdt_fixup_liodn(blob);
1213
1214 #ifdef CONFIG_HAS_FSL_DR_USB
1215         fsl_fdt_fixup_dr_usb(blob, bd);
1216 #endif
1217
1218 #ifdef CONFIG_SYS_DPAA_FMAN
1219         fdt_fixup_fman_ethernet(blob);
1220         fdt_fixup_board_enet(blob);
1221 #endif
1222
1223         return 0;
1224 }
1225
1226 /*
1227  * Dump board switch settings.
1228  * The bits that cannot be read/sampled via some FPGA or some
1229  * registers, they will be displayed as
1230  * underscore in binary format. mask[] has those bits.
1231  * Some bits are calculated differently than the actual switches
1232  * if booting with overriding by FPGA.
1233  */
1234 void qixis_dump_switch(void)
1235 {
1236         int i;
1237         u8 sw[5];
1238
1239         /*
1240          * Any bit with 1 means that bit cannot be reverse engineered.
1241          * It will be displayed as _ in binary format.
1242          */
1243         static const u8 mask[] = {0x07, 0, 0, 0xff, 0};
1244         char buf[10];
1245         u8 brdcfg[16], dutcfg[16];
1246
1247         for (i = 0; i < 16; i++) {
1248                 brdcfg[i] = qixis_read(offsetof(struct qixis, brdcfg[0]) + i);
1249                 dutcfg[i] = qixis_read(offsetof(struct qixis, dutcfg[0]) + i);
1250         }
1251
1252         sw[0] = ((brdcfg[0] & 0x0f) << 4)       | \
1253                 (brdcfg[9] & 0x08);
1254         sw[1] = ((dutcfg[1] & 0x01) << 7)       | \
1255                 ((dutcfg[2] & 0x07) << 4)       | \
1256                 ((dutcfg[6] & 0x10) >> 1)       | \
1257                 ((dutcfg[6] & 0x80) >> 5)       | \
1258                 ((dutcfg[1] & 0x40) >> 5)       | \
1259                 (dutcfg[6] & 0x01);
1260         sw[2] = dutcfg[0];
1261         sw[3] = 0;
1262         sw[4] = ((brdcfg[1] & 0x30) << 2)       | \
1263                 ((brdcfg[1] & 0xc0) >> 2)       | \
1264                 (brdcfg[1] & 0x0f);
1265
1266         puts("DIP switch settings:\n");
1267         for (i = 0; i < 5; i++) {
1268                 printf("SW%d         = 0b%s (0x%02x)\n",
1269                         i + 1, byte_to_binary_mask(sw[i], mask[i], buf), sw[i]);
1270         }
1271 }