Merge branch 'master' of git://git.denx.de/u-boot
[platform/kernel/u-boot.git] / arch / powerpc / cpu / ppc4xx / cmd_chip_config.c
1 /*
2  * (C) Copyright 2008-2009
3  * Stefan Roese, DENX Software Engineering, sr@denx.de.
4  *
5  * (C) Copyright 2009
6  * Dirk Eibach,  Guntermann & Drunck GmbH, eibach@gdsys.de
7  *
8  * SPDX-License-Identifier:     GPL-2.0+
9  */
10
11 #include <common.h>
12 #include <command.h>
13 #include <i2c.h>
14 #include <asm/ppc4xx_config.h>
15 #include <asm/io.h>
16
17 static void print_configs(int cur_config_nr)
18 {
19         int i;
20
21         for (i = 0; i < ppc4xx_config_count; i++) {
22                 printf("%-16s - %s", ppc4xx_config_val[i].label,
23                        ppc4xx_config_val[i].description);
24                 if (i == cur_config_nr)
25                         printf(" ***");
26                 printf("\n");
27         }
28
29 }
30
31 static int do_chip_config(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
32 {
33         int i;
34         int ret;
35         int cur_config_nr = -1;
36         u8 cur_config[CONFIG_4xx_CONFIG_BLOCKSIZE];
37
38         /*
39          * First switch to correct I2C bus. This is I2C bus 0
40          * for all currently available 4xx derivats.
41          */
42         i2c_set_bus_num(0);
43
44 #ifdef CONFIG_CMD_EEPROM
45         ret = eeprom_read(CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR,
46                           CONFIG_4xx_CONFIG_I2C_EEPROM_OFFSET,
47                           cur_config, CONFIG_4xx_CONFIG_BLOCKSIZE);
48 #else
49         ret = i2c_read(CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR,
50                        CONFIG_4xx_CONFIG_I2C_EEPROM_OFFSET,
51                        1, cur_config, CONFIG_4xx_CONFIG_BLOCKSIZE);
52 #endif
53         if (ret) {
54                 printf("Error reading EEPROM at addr 0x%x\n",
55                        CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR);
56                 return -1;
57         }
58
59         /*
60          * Search the current configuration
61          */
62         for (i = 0; i < ppc4xx_config_count; i++) {
63                 if (memcmp(cur_config, ppc4xx_config_val[i].val,
64                            CONFIG_4xx_CONFIG_BLOCKSIZE) == 0)
65                         cur_config_nr = i;
66         }
67
68         if (cur_config_nr == -1) {
69                 printf("Warning: The I2C bootstrap values don't match any"
70                        " of the available options!\n");
71                 printf("I2C bootstrap EEPROM values are (I2C address 0x%02x):\n",
72                         CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR);
73                 for (i = 0; i < CONFIG_4xx_CONFIG_BLOCKSIZE; i++) {
74                         printf("%02x ", cur_config[i]);
75                 }
76                 printf("\n");
77         }
78
79         if (argc < 2) {
80                 printf("Available configurations (I2C address 0x%02x):\n",
81                        CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR);
82                 print_configs(cur_config_nr);
83                 return 0;
84         }
85
86         for (i = 0; i < ppc4xx_config_count; i++) {
87                 /*
88                  * Search for configuration name/label
89                  */
90                 if (strcmp(argv[1], ppc4xx_config_val[i].label) == 0) {
91                         printf("Using configuration:\n%-16s - %s\n",
92                                ppc4xx_config_val[i].label,
93                                ppc4xx_config_val[i].description);
94
95 #ifdef CONFIG_CMD_EEPROM
96                         ret = eeprom_write(CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR,
97                                            CONFIG_4xx_CONFIG_I2C_EEPROM_OFFSET,
98                                            ppc4xx_config_val[i].val,
99                                            CONFIG_4xx_CONFIG_BLOCKSIZE);
100 #else
101                         ret = i2c_write(CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR,
102                                         CONFIG_4xx_CONFIG_I2C_EEPROM_OFFSET,
103                                         1, ppc4xx_config_val[i].val,
104                                         CONFIG_4xx_CONFIG_BLOCKSIZE);
105 #endif
106                         udelay(CONFIG_SYS_EEPROM_PAGE_WRITE_DELAY_MS * 1000);
107                         if (ret) {
108                                 printf("Error updating EEPROM at addr 0x%x\n",
109                                        CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR);
110                                 return -1;
111                         }
112
113                         printf("done (dump via 'i2c md %x 0.1 %x')\n",
114                                CONFIG_4xx_CONFIG_I2C_EEPROM_ADDR,
115                                CONFIG_4xx_CONFIG_BLOCKSIZE);
116                         printf("Reset the board for the changes to"
117                                " take effect\n");
118                         return 0;
119                 }
120         }
121
122         printf("Configuration %s not found!\n", argv[1]);
123         print_configs(cur_config_nr);
124         return -1;
125 }
126
127 U_BOOT_CMD(
128         chip_config,    2,      0,      do_chip_config,
129         "program the I2C bootstrap EEPROM",
130         "[config-label]"
131 );