Commit 16ac90c7ee6fe973ee86fa9b08f876e5c33751bc

Authored by Valentin Longchamp
Committed by Tom Rini
1 parent b9ea0c3a20

KM/IVM: split the IVM reading and parsing in 2 parts

This allows to first read the IVM content (earlier in the boot sequence)
and define the ethaddr env variable thanks to the ivm_read_eepromi().
Later, the IVM content can be parsed and used to define some hush
variables, when the hush subsystem is available thanks to
ivm_analyze_eeprom().

To avoid the HW read to happen twice, the buffer passed to
ivm_read_eeprom() has to be reused by ivm_analyze_eeprom (and thus
allocated before calling ivm_read_eeprom()).

Signed-off-by: Valentin Longchamp <valentin.longchamp@keymile.com>

Showing 2 changed files with 63 additions and 25 deletions Side-by-side Diff

board/keymile/common/common.h
... ... @@ -127,6 +127,8 @@
127 127  
128 128 int ethernet_present(void);
129 129 int ivm_read_eeprom(void);
  130 +int ivm_simple_read_eeprom(unsigned char *buf, int len);
  131 +int ivm_analyze_eeprom(unsigned char *buf, int len);
130 132  
131 133 int trigger_fpga_config(void);
132 134 int wait_for_fpga_config(void);
board/keymile/common/ivm.c
... ... @@ -10,6 +10,8 @@
10 10 #include <i2c.h>
11 11 #include "common.h"
12 12  
  13 +#define MAC_STR_SZ 20
  14 +
13 15 static int ivm_calc_crc(unsigned char *buf, int len)
14 16 {
15 17 const unsigned short crc_tab[16] = {
16 18  
17 19  
18 20  
19 21  
20 22  
... ... @@ -185,45 +187,37 @@
185 187 return 0;
186 188 }
187 189  
188   -static int calculate_mac_offset(unsigned char *valbuf, unsigned char *buf,
  190 +/* take care of the possible MAC address offset and the IVM content offset */
  191 +static int process_mac(unsigned char *valbuf, unsigned char *buf,
189 192 int offset)
190 193 {
  194 + unsigned char mac[6];
191 195 unsigned long val = (buf[4] << 16) + (buf[5] << 8) + buf[6];
192 196  
193   - if (offset == 0)
194   - return 0;
  197 + /* use an intermediate buffer, to not change IVM content
  198 + * MAC address is at offset 1
  199 + */
  200 + memcpy(mac, buf+1, 6);
195 201  
196   - val += offset;
197   - buf[4] = (val >> 16) & 0xff;
198   - buf[5] = (val >> 8) & 0xff;
199   - buf[6] = val & 0xff;
200   - sprintf((char *)valbuf, "%pM", buf + 1);
  202 + if (offset) {
  203 + val += offset;
  204 + mac[3] = (val >> 16) & 0xff;
  205 + mac[4] = (val >> 8) & 0xff;
  206 + mac[5] = val & 0xff;
  207 + }
  208 +
  209 + sprintf((char *)valbuf, "%pM", mac);
201 210 return 0;
202 211 }
203 212  
204 213 static int ivm_analyze_block2(unsigned char *buf, int len)
205 214 {
206   - unsigned char valbuf[CONFIG_SYS_IVM_EEPROM_PAGE_LEN];
  215 + unsigned char valbuf[MAC_STR_SZ];
207 216 unsigned long count;
208 217  
209 218 /* IVM_MAC Adress begins at offset 1 */
210 219 sprintf((char *)valbuf, "%pM", buf + 1);
211 220 ivm_set_value("IVM_MacAddress", (char *)valbuf);
212   - /* if an offset is defined, add it */
213   - calculate_mac_offset(buf, valbuf, CONFIG_PIGGY_MAC_ADRESS_OFFSET);
214   -#ifdef MACH_TYPE_KM_KIRKWOOD
215   - setenv((char *)"ethaddr", (char *)valbuf);
216   -#else
217   - if (getenv("ethaddr") == NULL)
218   - setenv((char *)"ethaddr", (char *)valbuf);
219   -#endif
220   -#ifdef CONFIG_KMVECT1
221   -/* KMVECT1 has two ethernet interfaces */
222   - if (getenv("eth1addr") == NULL) {
223   - calculate_mac_offset(buf, valbuf, 1);
224   - setenv((char *)"eth1addr", (char *)valbuf);
225   - }
226   -#endif
227 221 /* IVM_MacCount */
228 222 count = (buf[10] << 24) +
229 223 (buf[11] << 16) +
... ... @@ -236,7 +230,7 @@
236 230 return 0;
237 231 }
238 232  
239   -static int ivm_analyze_eeprom(unsigned char *buf, int len)
  233 +int ivm_analyze_eeprom(unsigned char *buf, int len)
240 234 {
241 235 unsigned short val;
242 236 unsigned char valbuf[CONFIG_SYS_IVM_EEPROM_PAGE_LEN];
... ... @@ -294,6 +288,48 @@
294 288 CONFIG_SYS_IVM_EEPROM_PAGE_LEN);
295 289  
296 290 return 0;
  291 +}
  292 +
  293 +static int ivm_populate_env(unsigned char *buf, int len)
  294 +{
  295 + unsigned char *page2;
  296 + unsigned char valbuf[MAC_STR_SZ];
  297 +
  298 + /* do we have the page 2 filled ? if not return */
  299 + if (ivm_check_crc(buf, 2))
  300 + return 0;
  301 + page2 = &buf[CONFIG_SYS_IVM_EEPROM_PAGE_LEN*2];
  302 +
  303 + /* if an offset is defined, add it */
  304 + process_mac(valbuf, page2, CONFIG_PIGGY_MAC_ADRESS_OFFSET);
  305 + if (getenv("ethaddr") == NULL)
  306 + setenv((char *)"ethaddr", (char *)valbuf);
  307 +#ifdef CONFIG_KMVECT1
  308 +/* KMVECT1 has two ethernet interfaces */
  309 + if (getenv("eth1addr") == NULL) {
  310 + process_mac(valbuf, page2, 1);
  311 + setenv((char *)"eth1addr", (char *)valbuf);
  312 + }
  313 +#endif
  314 +
  315 + return 0;
  316 +}
  317 +
  318 +int ivm_simple_read_eeprom(unsigned char *buf, int len)
  319 +{
  320 + int ret;
  321 +
  322 + i2c_set_bus_num(CONFIG_KM_IVM_BUS);
  323 + /* add deblocking here */
  324 + i2c_make_abort();
  325 +
  326 + ret = i2c_read(CONFIG_SYS_IVM_EEPROM_ADR, 0, 1, buf, len);
  327 + if (ret != 0) {
  328 + printf("Error reading EEprom\n");
  329 + return -2;
  330 + }
  331 +
  332 + return ivm_populate_env(buf, len);
297 333 }
298 334  
299 335 int ivm_read_eeprom(void)