]> Git Repo - u-boot.git/blob - drivers/sysinfo/rcar3.c
clk: a1: add new clocks for USB stack
[u-boot.git] / drivers / sysinfo / rcar3.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright (C) 2021 Marek Vasut <[email protected]>
4  */
5
6 #include <common.h>
7 #include <dm.h>
8 #include <i2c_eeprom.h>
9 #include <log.h>
10 #include <sysinfo.h>
11
12 #define BOARD_CODE_MASK         0xF8
13 #define BOARD_REV_MASK          0x07
14 #define BOARD_CODE_SHIFT        0x03
15
16 #define BOARD_SALVATOR_X        0x0
17 #define BOARD_KRIEK             0x1
18 #define BOARD_STARTER_KIT       0x2
19 #define BOARD_EAGLE             0x3
20 #define BOARD_SALVATOR_XS       0x4
21 #define BOARD_CONDOR            0x6
22 #define BOARD_DRAAK             0x7
23 #define BOARD_EBISU             0x8
24 #define BOARD_STARTER_KIT_PRE   0xB
25 #define BOARD_EBISU_4D          0xD
26 #define BOARD_CONDOR_I          0x10
27
28 /**
29  * struct sysinfo_rcar_priv - sysinfo private data
30  * @boardname: board model and revision
31  * @val: board ID value from eeprom
32  */
33 struct sysinfo_rcar_priv {
34         char    boardmodel[64];
35         u8      val;
36 };
37
38 static int sysinfo_rcar_detect(struct udevice *dev)
39 {
40         struct sysinfo_rcar_priv *priv = dev_get_priv(dev);
41
42         return priv->val == 0xff;
43 }
44
45 static int sysinfo_rcar_get_str(struct udevice *dev, int id, size_t size, char *val)
46 {
47         struct sysinfo_rcar_priv *priv = dev_get_priv(dev);
48
49         switch (id) {
50         case SYSINFO_ID_BOARD_MODEL:
51                 strncpy(val, priv->boardmodel, size);
52                 val[size - 1] = '\0';
53                 return 0;
54         default:
55                 return -EINVAL;
56         };
57 }
58
59 static const struct sysinfo_ops sysinfo_rcar_ops = {
60         .detect = sysinfo_rcar_detect,
61         .get_str = sysinfo_rcar_get_str,
62 };
63
64 static void sysinfo_rcar_parse(struct sysinfo_rcar_priv *priv)
65 {
66         const u8 board_id = (priv->val & BOARD_CODE_MASK) >> BOARD_CODE_SHIFT;
67         const u8 board_rev = priv->val & BOARD_REV_MASK;
68         bool salvator_xs = false;
69         bool ebisu_4d = false;
70         bool condor_i = false;
71         char rev_major = '?';
72         char rev_minor = '?';
73
74         switch (board_id) {
75         case BOARD_SALVATOR_XS:
76                 salvator_xs = true;
77                 fallthrough;
78         case BOARD_SALVATOR_X:
79                 if (!(board_rev & ~1)) { /* Only rev 0 and 1 is valid */
80                         rev_major = '1';
81                         rev_minor = '0' + (board_rev & BIT(0));
82                 }
83                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
84                          "Renesas Salvator-X%s board rev %c.%c",
85                          salvator_xs ? "S" : "", rev_major, rev_minor);
86                 return;
87         case BOARD_STARTER_KIT:
88                 if (!(board_rev & ~1)) { /* Only rev 0 and 1 is valid */
89                         rev_major = (board_rev & BIT(0)) ? '3' : '1';
90                         rev_minor = '0';
91                 }
92                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
93                          "Renesas Starter Kit board rev %c.%c",
94                          rev_major, rev_minor);
95                 return;
96         case BOARD_STARTER_KIT_PRE:
97                 if (!(board_rev & ~3)) { /* Only rev 0..3 is valid */
98                         rev_major = (board_rev & BIT(1)) ? '2' : '1';
99                         rev_minor = (board_rev == 3) ? '1' : '0';
100                 }
101                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
102                          "Renesas Starter Kit Premier board rev %c.%c",
103                          rev_major, rev_minor);
104                 return;
105         case BOARD_EAGLE:
106                 if (!board_rev) { /* Only rev 0 is valid */
107                         rev_major = '1';
108                         rev_minor = '0';
109                 }
110                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
111                          "Renesas Eagle board rev %c.%c",
112                          rev_major, rev_minor);
113                 return;
114         case BOARD_EBISU_4D:
115                 ebisu_4d = true;
116                 fallthrough;
117         case BOARD_EBISU:
118                 if (!board_rev) { /* Only rev 0 is valid */
119                         rev_major = '1';
120                         rev_minor = '0';
121                 }
122                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
123                          "Renesas Ebisu%s board rev %c.%c",
124                          ebisu_4d ? "-4D" : "", rev_major, rev_minor);
125                 return;
126         case BOARD_DRAAK:
127                 if (!board_rev) { /* Only rev 0 is valid */
128                         rev_major = '1';
129                         rev_minor = '0';
130                 }
131                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
132                          "Renesas Draak board rev %c.%c",
133                          rev_major, rev_minor);
134                 return;
135         case BOARD_KRIEK:
136                 if (!board_rev) { /* Only rev 0 is valid */
137                         rev_major = '1';
138                         rev_minor = '0';
139                 }
140                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
141                          "Renesas Kriek board rev %c.%c",
142                          rev_major, rev_minor);
143                 return;
144         case BOARD_CONDOR_I:
145                 condor_i = true;
146                 fallthrough;
147         case BOARD_CONDOR:
148                 if (!board_rev) { /* Only rev 0 is valid */
149                         rev_major = '1';
150                         rev_minor = '0';
151                 }
152                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
153                         "Renesas Condor%s board rev %c.%c",
154                         condor_i ? "-I" : "", rev_major, rev_minor);
155                 return;
156         default:
157                 snprintf(priv->boardmodel, sizeof(priv->boardmodel),
158                          "Renesas -Unknown- board rev ?.?");
159                 priv->val = 0xff;
160                 return;
161         }
162 }
163
164 static int sysinfo_rcar_probe(struct udevice *dev)
165 {
166         struct sysinfo_rcar_priv *priv = dev_get_priv(dev);
167         struct ofnode_phandle_args phandle_args;
168         struct udevice *i2c_eeprom;
169         u32 offset;
170         int ret;
171
172         offset = dev_read_u32_default(dev, "offset", 0x70);
173
174         ret = dev_read_phandle_with_args(dev, "i2c-eeprom", NULL,
175                                          0, 0, &phandle_args);
176         if (ret) {
177                 debug("%s: i2c-eeprom backing device not specified\n",
178                       dev->name);
179                 return ret;
180         }
181
182         ret = uclass_get_device_by_ofnode(UCLASS_I2C_EEPROM, phandle_args.node,
183                                           &i2c_eeprom);
184         if (ret) {
185                 debug("%s: could not get backing device\n", dev->name);
186                 return ret;
187         }
188
189         ret = i2c_eeprom_read(i2c_eeprom, offset, &priv->val, 1);
190         if (ret < 0) {
191                 debug("%s: read failed\n", __func__);
192                 return -EIO;
193         }
194
195         sysinfo_rcar_parse(priv);
196
197         return 0;
198 }
199
200 static const struct udevice_id sysinfo_rcar_ids[] = {
201         { .compatible = "renesas,rcar-sysinfo" },
202         { /* sentinel */ }
203 };
204
205 U_BOOT_DRIVER(sysinfo_rcar) = {
206         .name           = "sysinfo_rcar",
207         .id             = UCLASS_SYSINFO,
208         .of_match       = sysinfo_rcar_ids,
209         .ops            = &sysinfo_rcar_ops,
210         .priv_auto      = sizeof(struct sysinfo_rcar_priv),
211         .probe          = sysinfo_rcar_probe,
212 };
This page took 0.041189 seconds and 4 git commands to generate.