1c2485364SHeiko Schocher /* 2c2485364SHeiko Schocher * (C) Copyright 2008 3c2485364SHeiko Schocher * Heiko Schocher, DENX Software Engineering, hs@denx.de. 4c2485364SHeiko Schocher * 54f745bf4SHolger Brunck * (C) Copyright 2011 64f745bf4SHolger Brunck * Holger Brunck, Keymile GmbH Hannover, holger.brunck@keymile.com 74f745bf4SHolger Brunck * 8c2485364SHeiko Schocher * See file CREDITS for list of people who contributed to this 9c2485364SHeiko Schocher * project. 10c2485364SHeiko Schocher * 11c2485364SHeiko Schocher * This program is free software; you can redistribute it and/or 12c2485364SHeiko Schocher * modify it under the terms of the GNU General Public License as 13c2485364SHeiko Schocher * published by the Free Software Foundation; either version 2 of 14c2485364SHeiko Schocher * the License, or (at your option) any later version. 15c2485364SHeiko Schocher * 16c2485364SHeiko Schocher * This program is distributed in the hope that it will be useful, 17c2485364SHeiko Schocher * but WITHOUT ANY WARRANTY; without even the implied warranty of 18c2485364SHeiko Schocher * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19c2485364SHeiko Schocher * GNU General Public License for more details. 20c2485364SHeiko Schocher * 21c2485364SHeiko Schocher * You should have received a copy of the GNU General Public License 22c2485364SHeiko Schocher * along with this program; if not, write to the Free Software 23c2485364SHeiko Schocher * Foundation, Inc., 59 Temple Place, Suite 330, Boston, 24c2485364SHeiko Schocher * MA 02111-1307 USA 25c2485364SHeiko Schocher */ 26c2485364SHeiko Schocher 27c2485364SHeiko Schocher #include <common.h> 28c2485364SHeiko Schocher #include <ioports.h> 29a9417ce7SHolger Brunck #include <command.h> 30c2485364SHeiko Schocher #include <malloc.h> 318f64da7fSHeiko Schocher #include <hush.h> 32210c8c00SHeiko Schocher #include <net.h> 3362ddcf05SHeiko Schocher #include <netdev.h> 34210c8c00SHeiko Schocher #include <asm/io.h> 3592c91080SThomas Herzmann #include <linux/ctype.h> 36c2485364SHeiko Schocher 374f745bf4SHolger Brunck #include "common.h" 38c2485364SHeiko Schocher #if defined(CONFIG_HARD_I2C) || defined(CONFIG_SOFT_I2C) 39c2485364SHeiko Schocher #include <i2c.h> 401adfd9ddSHolger Brunck #endif 41c2485364SHeiko Schocher 42*e792affeSHolger Brunck #if !defined(CONFIG_MPC83xx) 436c11aeafSHeiko Schocher static void i2c_write_start_seq(void); 44*e792affeSHolger Brunck #endif 45*e792affeSHolger Brunck 46f1fef1d8SHeiko Schocher DECLARE_GLOBAL_DATA_PTR; 476c11aeafSHeiko Schocher 48f1fef1d8SHeiko Schocher /* 49f1fef1d8SHeiko Schocher * Set Keymile specific environment variables 50f1fef1d8SHeiko Schocher * Currently only some memory layout variables are calculated here 51f1fef1d8SHeiko Schocher * ... ------------------------------------------------ 52f1fef1d8SHeiko Schocher * ... |@rootfsaddr |@pnvramaddr |@varaddr |@reserved |@END_OF_RAM 53f1fef1d8SHeiko Schocher * ... |<------------------- pram ------------------->| 54f1fef1d8SHeiko Schocher * ... ------------------------------------------------ 55f1fef1d8SHeiko Schocher * @END_OF_RAM: denotes the RAM size 56f1fef1d8SHeiko Schocher * @pnvramaddr: Startadress of pseudo non volatile RAM in hex 57f1fef1d8SHeiko Schocher * @pram : preserved ram size in k 58f1fef1d8SHeiko Schocher * @varaddr : startadress for /var mounted into RAM 59f1fef1d8SHeiko Schocher */ 60f1fef1d8SHeiko Schocher int set_km_env(void) 61f1fef1d8SHeiko Schocher { 62f1fef1d8SHeiko Schocher uchar buf[32]; 63f1fef1d8SHeiko Schocher unsigned int pnvramaddr; 64f1fef1d8SHeiko Schocher unsigned int pram; 65f1fef1d8SHeiko Schocher unsigned int varaddr; 662a7714ceSAndreas Huber unsigned int kernelmem; 672a7714ceSAndreas Huber char *p; 682a7714ceSAndreas Huber unsigned long rootfssize = 0; 69f1fef1d8SHeiko Schocher 70f1fef1d8SHeiko Schocher pnvramaddr = gd->ram_size - CONFIG_KM_RESERVED_PRAM - CONFIG_KM_PHRAM 71f1fef1d8SHeiko Schocher - CONFIG_KM_PNVRAM; 72f1fef1d8SHeiko Schocher sprintf((char *)buf, "0x%x", pnvramaddr); 73f1fef1d8SHeiko Schocher setenv("pnvramaddr", (char *)buf); 74f1fef1d8SHeiko Schocher 752a7714ceSAndreas Huber /* try to read rootfssize (ram image) from envrionment */ 762a7714ceSAndreas Huber p = getenv("rootfssize"); 772a7714ceSAndreas Huber if (p != NULL) 782a7714ceSAndreas Huber strict_strtoul(p, 16, &rootfssize); 792a7714ceSAndreas Huber pram = (rootfssize + CONFIG_KM_RESERVED_PRAM + CONFIG_KM_PHRAM + 802a7714ceSAndreas Huber CONFIG_KM_PNVRAM) / 0x400; 81f1fef1d8SHeiko Schocher sprintf((char *)buf, "0x%x", pram); 82f1fef1d8SHeiko Schocher setenv("pram", (char *)buf); 83f1fef1d8SHeiko Schocher 84f1fef1d8SHeiko Schocher varaddr = gd->ram_size - CONFIG_KM_RESERVED_PRAM - CONFIG_KM_PHRAM; 85f1fef1d8SHeiko Schocher sprintf((char *)buf, "0x%x", varaddr); 86f1fef1d8SHeiko Schocher setenv("varaddr", (char *)buf); 872a7714ceSAndreas Huber 882a7714ceSAndreas Huber kernelmem = gd->ram_size - 0x400 * pram; 892a7714ceSAndreas Huber sprintf((char *)buf, "0x%x", kernelmem); 902a7714ceSAndreas Huber setenv("kernelmem", (char *)buf); 912a7714ceSAndreas Huber 92f1fef1d8SHeiko Schocher return 0; 93f1fef1d8SHeiko Schocher } 94f1fef1d8SHeiko Schocher 95*e792affeSHolger Brunck #if defined(CONFIG_SYS_I2C_INIT_BOARD) 9662ddcf05SHeiko Schocher #if !defined(CONFIG_MPC83xx) 976c11aeafSHeiko Schocher static void i2c_write_start_seq(void) 98c2485364SHeiko Schocher { 99c2485364SHeiko Schocher set_sda(1); 100c2485364SHeiko Schocher udelay(DELAY_HALF_PERIOD); 101c2485364SHeiko Schocher set_scl(1); 102c2485364SHeiko Schocher udelay(DELAY_HALF_PERIOD); 103c2485364SHeiko Schocher set_sda(0); 104c2485364SHeiko Schocher udelay(DELAY_HALF_PERIOD); 105c2485364SHeiko Schocher set_scl(0); 106c2485364SHeiko Schocher udelay(DELAY_HALF_PERIOD); 107c2485364SHeiko Schocher } 108c2485364SHeiko Schocher 109b11f53f3SHeiko Schocher /* 110b11f53f3SHeiko Schocher * I2C is a synchronous protocol and resets of the processor in the middle 111b11f53f3SHeiko Schocher * of an access can block the I2C Bus until a powerdown of the full unit is 112b11f53f3SHeiko Schocher * done. This function toggles the SCL until the SCL and SCA line are 113b11f53f3SHeiko Schocher * released, but max. 16 times, after this a I2C start-sequence is sent. 114b11f53f3SHeiko Schocher * This I2C Deblocking mechanism was developed by Keymile in association 115b11f53f3SHeiko Schocher * with Anatech and Atmel in 1998. 116c2485364SHeiko Schocher */ 1174f745bf4SHolger Brunck int i2c_make_abort(void) 118c2485364SHeiko Schocher { 1196c11aeafSHeiko Schocher 1206c11aeafSHeiko Schocher #if defined(CONFIG_HARD_I2C) && !defined(MACH_TYPE_KM_KIRKWOOD) 1216c11aeafSHeiko Schocher immap_t *immap = (immap_t *)CONFIG_SYS_IMMR ; 1226c11aeafSHeiko Schocher i2c8260_t *i2c = (i2c8260_t *)&immap->im_i2c; 1236c11aeafSHeiko Schocher 1246c11aeafSHeiko Schocher /* 1256c11aeafSHeiko Schocher * disable I2C controller first, otherwhise it thinks we want to 1266c11aeafSHeiko Schocher * talk to the slave port... 1276c11aeafSHeiko Schocher */ 1286c11aeafSHeiko Schocher clrbits_8(&i2c->i2c_i2mod, 0x01); 1296c11aeafSHeiko Schocher 1306c11aeafSHeiko Schocher /* Set the PortPins to GPIO */ 1316c11aeafSHeiko Schocher setports(1); 1326c11aeafSHeiko Schocher #endif 1336c11aeafSHeiko Schocher 134c2485364SHeiko Schocher int scl_state = 0; 135c2485364SHeiko Schocher int sda_state = 0; 136c2485364SHeiko Schocher int i = 0; 137c2485364SHeiko Schocher int ret = 0; 138c2485364SHeiko Schocher 139c2485364SHeiko Schocher if (!get_sda()) { 140c2485364SHeiko Schocher ret = -1; 141c2485364SHeiko Schocher while (i < 16) { 142c2485364SHeiko Schocher i++; 143c2485364SHeiko Schocher set_scl(0); 144c2485364SHeiko Schocher udelay(DELAY_ABORT_SEQ); 145c2485364SHeiko Schocher set_scl(1); 146c2485364SHeiko Schocher udelay(DELAY_ABORT_SEQ); 147c2485364SHeiko Schocher scl_state = get_scl(); 148c2485364SHeiko Schocher sda_state = get_sda(); 149c2485364SHeiko Schocher if (scl_state && sda_state) { 150c2485364SHeiko Schocher ret = 0; 151c7506c2bSStefan Bigler printf("[INFO] i2c abort after %d clocks\n", i); 152c2485364SHeiko Schocher break; 153c2485364SHeiko Schocher } 154c2485364SHeiko Schocher } 155c2485364SHeiko Schocher } 156b11f53f3SHeiko Schocher if (ret == 0) 157b11f53f3SHeiko Schocher for (i = 0; i < 5; i++) 1586c11aeafSHeiko Schocher i2c_write_start_seq(); 159c7506c2bSStefan Bigler else 160c7506c2bSStefan Bigler printf("[ERROR] i2c abort failed\n"); 161b11f53f3SHeiko Schocher 1626c11aeafSHeiko Schocher /* respect stop setup time */ 1636c11aeafSHeiko Schocher udelay(DELAY_ABORT_SEQ); 1646c11aeafSHeiko Schocher set_scl(1); 1656c11aeafSHeiko Schocher udelay(DELAY_ABORT_SEQ); 1666c11aeafSHeiko Schocher set_sda(1); 167c2485364SHeiko Schocher get_sda(); 168c2485364SHeiko Schocher 169c2485364SHeiko Schocher #if defined(CONFIG_HARD_I2C) 170c2485364SHeiko Schocher /* Set the PortPins back to use for I2C */ 171c2485364SHeiko Schocher setports(0); 172c2485364SHeiko Schocher #endif 1736c11aeafSHeiko Schocher return ret; 1746c11aeafSHeiko Schocher } 1756c11aeafSHeiko Schocher #endif 1766c11aeafSHeiko Schocher 1776c11aeafSHeiko Schocher /** 1786c11aeafSHeiko Schocher * i2c_init_board - reset i2c bus. When the board is powercycled during a 1796c11aeafSHeiko Schocher * bus transfer it might hang; for details see doc/I2C_Edge_Conditions. 1806c11aeafSHeiko Schocher */ 1816c11aeafSHeiko Schocher void i2c_init_board(void) 1826c11aeafSHeiko Schocher { 1836c11aeafSHeiko Schocher /* Now run the AbortSequence() */ 1846c11aeafSHeiko Schocher i2c_make_abort(); 185c2485364SHeiko Schocher } 186*e792affeSHolger Brunck #endif 187*e792affeSHolger Brunck 1886250f0f6SHeiko Schocher 189802d9963SHolger Brunck #if !defined(MACH_TYPE_KM_KIRKWOOD) 190210c8c00SHeiko Schocher int ethernet_present(void) 191210c8c00SHeiko Schocher { 1928ed74341SHeiko Schocher struct km_bec_fpga *base = 1938ed74341SHeiko Schocher (struct km_bec_fpga *)CONFIG_SYS_KMBEC_FPGA_BASE; 194b11f53f3SHeiko Schocher 195b11f53f3SHeiko Schocher return in_8(&base->bprth) & PIGGY_PRESENT; 196210c8c00SHeiko Schocher } 19767fa8c25SHeiko Schocher #endif 198210c8c00SHeiko Schocher 199210c8c00SHeiko Schocher int board_eth_init(bd_t *bis) 200210c8c00SHeiko Schocher { 201b11f53f3SHeiko Schocher if (ethernet_present()) 20262ddcf05SHeiko Schocher return cpu_eth_init(bis); 20362ddcf05SHeiko Schocher 204210c8c00SHeiko Schocher return -1; 205210c8c00SHeiko Schocher } 206a9417ce7SHolger Brunck 207a9417ce7SHolger Brunck /* 208a9417ce7SHolger Brunck * do_setboardid command 209a9417ce7SHolger Brunck * read out the board id and the hw key from the intventory EEPROM and set 210a9417ce7SHolger Brunck * this values as environment variables. 211a9417ce7SHolger Brunck */ 212a9417ce7SHolger Brunck static int do_setboardid(cmd_tbl_t *cmdtp, int flag, int argc, 213a9417ce7SHolger Brunck char *const argv[]) 214a9417ce7SHolger Brunck { 215a9417ce7SHolger Brunck unsigned char buf[32]; 216a9417ce7SHolger Brunck char *p; 217a9417ce7SHolger Brunck 218a9417ce7SHolger Brunck p = get_local_var("IVM_BoardId"); 219a9417ce7SHolger Brunck if (p == NULL) { 220a9417ce7SHolger Brunck printf("can't get the IVM_Boardid\n"); 221a9417ce7SHolger Brunck return 1; 222a9417ce7SHolger Brunck } 223a9417ce7SHolger Brunck sprintf((char *)buf, "%s", p); 224a9417ce7SHolger Brunck setenv("boardid", (char *)buf); 2259485e779SHolger Brunck printf("set boardid=%s\n", buf); 226a9417ce7SHolger Brunck 227a9417ce7SHolger Brunck p = get_local_var("IVM_HWKey"); 228a9417ce7SHolger Brunck if (p == NULL) { 229a9417ce7SHolger Brunck printf("can't get the IVM_HWKey\n"); 230a9417ce7SHolger Brunck return 1; 231a9417ce7SHolger Brunck } 232a9417ce7SHolger Brunck sprintf((char *)buf, "%s", p); 233a9417ce7SHolger Brunck setenv("hwkey", (char *)buf); 2349485e779SHolger Brunck printf("set hwkey=%s\n", buf); 2359485e779SHolger Brunck printf("Execute manually saveenv for persistent storage.\n"); 236a9417ce7SHolger Brunck 237a9417ce7SHolger Brunck return 0; 238a9417ce7SHolger Brunck } 239a9417ce7SHolger Brunck 240a9417ce7SHolger Brunck U_BOOT_CMD(km_setboardid, 1, 0, do_setboardid, "setboardid", "read out bid and " 241a9417ce7SHolger Brunck "hwkey from IVM and set in environment"); 24292c91080SThomas Herzmann 24392c91080SThomas Herzmann /* 24492c91080SThomas Herzmann * command km_checkbidhwk 24592c91080SThomas Herzmann * if "boardid" and "hwkey" are not already set in the environment, do: 24692c91080SThomas Herzmann * if a "boardIdListHex" exists in the environment: 24792c91080SThomas Herzmann * - read ivm data for boardid and hwkey 24892c91080SThomas Herzmann * - compare each entry of the boardIdListHex with the 24992c91080SThomas Herzmann * IVM data: 25092c91080SThomas Herzmann * if match: 25192c91080SThomas Herzmann * set environment variables boardid, boardId, 25292c91080SThomas Herzmann * hwkey, hwKey to the found values 25392c91080SThomas Herzmann * both (boardid and boardId) are set because 25492c91080SThomas Herzmann * they might be used differently in the 25592c91080SThomas Herzmann * application and in the init scripts (?) 25692c91080SThomas Herzmann * return 0 in case of match, 1 if not match or error 25792c91080SThomas Herzmann */ 25892c91080SThomas Herzmann int do_checkboardidhwk(cmd_tbl_t *cmdtp, int flag, int argc, 25992c91080SThomas Herzmann char *const argv[]) 26092c91080SThomas Herzmann { 26192c91080SThomas Herzmann unsigned long ivmbid = 0, ivmhwkey = 0; 26292c91080SThomas Herzmann unsigned long envbid = 0, envhwkey = 0; 26392c91080SThomas Herzmann char *p; 26492c91080SThomas Herzmann int verbose = argc > 1 && *argv[1] == 'v'; 26592c91080SThomas Herzmann int rc = 0; 26692c91080SThomas Herzmann 26792c91080SThomas Herzmann /* 26892c91080SThomas Herzmann * first read out the real inventory values, these values are 26992c91080SThomas Herzmann * already stored in the local hush variables 27092c91080SThomas Herzmann */ 27192c91080SThomas Herzmann p = get_local_var("IVM_BoardId"); 27292c91080SThomas Herzmann if (p == NULL) { 27392c91080SThomas Herzmann printf("can't get the IVM_Boardid\n"); 27492c91080SThomas Herzmann return 1; 27592c91080SThomas Herzmann } 27692c91080SThomas Herzmann rc = strict_strtoul(p, 16, &ivmbid); 27792c91080SThomas Herzmann 27892c91080SThomas Herzmann p = get_local_var("IVM_HWKey"); 27992c91080SThomas Herzmann if (p == NULL) { 28092c91080SThomas Herzmann printf("can't get the IVM_HWKey\n"); 28192c91080SThomas Herzmann return 1; 28292c91080SThomas Herzmann } 28392c91080SThomas Herzmann rc = strict_strtoul(p, 16, &ivmhwkey); 28492c91080SThomas Herzmann 28592c91080SThomas Herzmann if (!ivmbid || !ivmhwkey) { 28692c91080SThomas Herzmann printf("Error: IVM_BoardId and/or IVM_HWKey not set!\n"); 28792c91080SThomas Herzmann return rc; 28892c91080SThomas Herzmann } 28992c91080SThomas Herzmann 29092c91080SThomas Herzmann /* now try to read values from environment if available */ 29192c91080SThomas Herzmann p = getenv("boardid"); 29292c91080SThomas Herzmann if (p != NULL) 29392c91080SThomas Herzmann rc = strict_strtoul(p, 16, &envbid); 29492c91080SThomas Herzmann p = getenv("hwkey"); 29592c91080SThomas Herzmann if (p != NULL) 29692c91080SThomas Herzmann rc = strict_strtoul(p, 16, &envhwkey); 29792c91080SThomas Herzmann 29892c91080SThomas Herzmann if (rc != 0) { 29992c91080SThomas Herzmann printf("strict_strtoul returns error: %d", rc); 30092c91080SThomas Herzmann return rc; 30192c91080SThomas Herzmann } 30292c91080SThomas Herzmann 30392c91080SThomas Herzmann if (!envbid || !envhwkey) { 30492c91080SThomas Herzmann /* 30592c91080SThomas Herzmann * BoardId/HWkey not available in the environment, so try the 30692c91080SThomas Herzmann * environment variable for BoardId/HWkey list 30792c91080SThomas Herzmann */ 30892c91080SThomas Herzmann char *bidhwklist = getenv("boardIdListHex"); 30992c91080SThomas Herzmann 31092c91080SThomas Herzmann if (bidhwklist) { 31192c91080SThomas Herzmann int found = 0; 31292c91080SThomas Herzmann char *rest = bidhwklist; 31392c91080SThomas Herzmann char *endp; 31492c91080SThomas Herzmann 31592c91080SThomas Herzmann if (verbose) { 31692c91080SThomas Herzmann printf("IVM_BoardId: %ld, IVM_HWKey=%ld\n", 31792c91080SThomas Herzmann ivmbid, ivmhwkey); 31892c91080SThomas Herzmann printf("boardIdHwKeyList: %s\n", 31992c91080SThomas Herzmann bidhwklist); 32092c91080SThomas Herzmann } 32192c91080SThomas Herzmann while (!found) { 32292c91080SThomas Herzmann /* loop over each bid/hwkey pair in the list */ 32392c91080SThomas Herzmann unsigned long bid = 0; 32492c91080SThomas Herzmann unsigned long hwkey = 0; 32592c91080SThomas Herzmann 32692c91080SThomas Herzmann while (*rest && !isxdigit(*rest)) 32792c91080SThomas Herzmann rest++; 32892c91080SThomas Herzmann /* 32992c91080SThomas Herzmann * use simple_strtoul because we need &end and 33092c91080SThomas Herzmann * we know we got non numeric char at the end 33192c91080SThomas Herzmann */ 33292c91080SThomas Herzmann bid = simple_strtoul(rest, &endp, 16); 33392c91080SThomas Herzmann /* BoardId and HWkey are separated with a "_" */ 33492c91080SThomas Herzmann if (*endp == '_') { 33592c91080SThomas Herzmann rest = endp + 1; 33692c91080SThomas Herzmann /* 33792c91080SThomas Herzmann * use simple_strtoul because we need 33892c91080SThomas Herzmann * &end 33992c91080SThomas Herzmann */ 34092c91080SThomas Herzmann hwkey = simple_strtoul(rest, &endp, 16); 34192c91080SThomas Herzmann rest = endp; 34292c91080SThomas Herzmann while (*rest && !isxdigit(*rest)) 34392c91080SThomas Herzmann rest++; 34492c91080SThomas Herzmann } 34592c91080SThomas Herzmann if ((!bid) || (!hwkey)) { 34692c91080SThomas Herzmann /* end of list */ 34792c91080SThomas Herzmann break; 34892c91080SThomas Herzmann } 34992c91080SThomas Herzmann if (verbose) { 35092c91080SThomas Herzmann printf("trying bid=0x%lX, hwkey=%ld\n", 35192c91080SThomas Herzmann bid, hwkey); 35292c91080SThomas Herzmann } 35392c91080SThomas Herzmann /* 35492c91080SThomas Herzmann * Compare the values of the found entry in the 35592c91080SThomas Herzmann * list with the valid values which are stored 35692c91080SThomas Herzmann * in the inventory eeprom. If they are equal 357ba8be32aSHolger Brunck * set the values in environment variables. 35892c91080SThomas Herzmann */ 35992c91080SThomas Herzmann if ((bid == ivmbid) && (hwkey == ivmhwkey)) { 36092c91080SThomas Herzmann char buf[10]; 36192c91080SThomas Herzmann 36292c91080SThomas Herzmann found = 1; 36392c91080SThomas Herzmann envbid = bid; 36492c91080SThomas Herzmann envhwkey = hwkey; 36592c91080SThomas Herzmann sprintf(buf, "%lx", bid); 36692c91080SThomas Herzmann setenv("boardid", buf); 36792c91080SThomas Herzmann sprintf(buf, "%lx", hwkey); 36892c91080SThomas Herzmann setenv("hwkey", buf); 36992c91080SThomas Herzmann } 37092c91080SThomas Herzmann } /* end while( ! found ) */ 37192c91080SThomas Herzmann } 37292c91080SThomas Herzmann } 37392c91080SThomas Herzmann 37492c91080SThomas Herzmann /* compare now the values */ 37592c91080SThomas Herzmann if ((ivmbid == envbid) && (ivmhwkey == envhwkey)) { 37692c91080SThomas Herzmann printf("boardid=0x%3lX, hwkey=%ld\n", envbid, envhwkey); 37792c91080SThomas Herzmann rc = 0; /* match */ 37892c91080SThomas Herzmann } else { 3799485e779SHolger Brunck printf("Error: env boardid=0x%3lX, hwkey=%ld\n", envbid, 3809485e779SHolger Brunck envhwkey); 38192c91080SThomas Herzmann printf(" IVM bId=0x%3lX, hwKey=%ld\n", ivmbid, ivmhwkey); 38292c91080SThomas Herzmann rc = 1; /* don't match */ 38392c91080SThomas Herzmann } 38492c91080SThomas Herzmann return rc; 38592c91080SThomas Herzmann } 38692c91080SThomas Herzmann 38792c91080SThomas Herzmann U_BOOT_CMD(km_checkbidhwk, 2, 0, do_checkboardidhwk, 38892c91080SThomas Herzmann "check boardid and hwkey", 38992c91080SThomas Herzmann "[v]\n - check environment parameter "\ 39092c91080SThomas Herzmann "\"boardIdListHex\" against stored boardid and hwkey "\ 39192c91080SThomas Herzmann "from the IVM\n v: verbose output" 39292c91080SThomas Herzmann ); 393