uboot/board/BuR/common/br_resetc.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * common reset-controller functions for B&R boards
   4 *
   5 * Copyright (C) 2019 Hannes Schmelzer <oe5hpm@oevsv.at>
   6 * B&R Industrial Automation GmbH - http://www.br-automation.com/ *
   7 */
   8#include <common.h>
   9#include <env.h>
  10#include <errno.h>
  11#include <i2c.h>
  12#include <dm/uclass.h>
  13#include <linux/delay.h>
  14#include "br_resetc.h"
  15
  16/* I2C Address of controller */
  17#define RSTCTRL_ADDR_PSOC       0x75
  18#define RSTCTRL_ADDR_STM32      0x60
  19
  20#define BMODE_DEFAULTAR         0
  21#define BMODE_SERVICE           2
  22#define BMODE_RUN               4
  23#define BMODE_PME               12
  24#define BMODE_DIAG              15
  25
  26#if CONFIG_IS_ENABLED(LCD) && !CONFIG_IS_ENABLED(DM_VIDEO)
  27#include <lcd.h>
  28#define LCD_SETCURSOR(x, y)     lcd_position_cursor(x, y)
  29#define LCD_PUTS(x)             lcd_puts(x)
  30#else
  31#define LCD_SETCURSOR(x, y)
  32#define LCD_PUTS(x)
  33#endif /* CONFIG_LCD */
  34
  35static const char *bootmodeascii[16] = {
  36        "BOOT",         "reserved",     "reserved",     "reserved",
  37        "RUN",          "reserved",     "reserved",     "reserved",
  38        "reserved",     "reserved",     "reserved",     "reserved",
  39        "PME",          "reserved",     "reserved",     "DIAG",
  40};
  41
  42struct br_reset_t {
  43        struct udevice *i2cdev;
  44        u8 is_psoc;
  45};
  46
  47static struct br_reset_t resetc;
  48
  49__weak int board_boot_key(void)
  50{
  51        return 0;
  52}
  53
  54__weak void board_boot_led(unsigned int on)
  55{
  56}
  57
  58static int resetc_init(void)
  59{
  60        struct udevice *i2cbus;
  61        int rc;
  62
  63        rc = uclass_get_device_by_seq(UCLASS_I2C, 0, &i2cbus);
  64        if (rc) {
  65                printf("Cannot find I2C bus #0!\n");
  66                return -1;
  67        }
  68
  69        resetc.is_psoc = 1;
  70        rc = dm_i2c_probe(i2cbus,
  71                          RSTCTRL_ADDR_PSOC, 0, &resetc.i2cdev);
  72        if (rc) {
  73                resetc.is_psoc = 0;
  74                rc = dm_i2c_probe(i2cbus,
  75                                  RSTCTRL_ADDR_STM32, 0, &resetc.i2cdev);
  76        }
  77
  78        if (rc)
  79                printf("Warning: cannot probe BuR resetcontroller!\n");
  80
  81        return rc;
  82}
  83
  84int br_resetc_regget(u8 reg, u8 *dst)
  85{
  86        int rc = 0;
  87
  88        if (!resetc.i2cdev)
  89                rc = resetc_init();
  90
  91        if (rc != 0)
  92                return rc;
  93
  94        return dm_i2c_read(resetc.i2cdev, reg, dst, 1);
  95}
  96
  97int br_resetc_regset(u8 reg, u8 val)
  98{
  99        int rc = 0;
 100        u16 regw = (val << 8) | val;
 101
 102        if (!resetc.i2cdev)
 103                rc = resetc_init();
 104
 105        if (rc != 0)
 106                return rc;
 107
 108        if (resetc.is_psoc)
 109                return dm_i2c_write(resetc.i2cdev, reg, (u8 *)&regw, 2);
 110
 111        return dm_i2c_write(resetc.i2cdev, reg, (u8 *)&regw, 1);
 112}
 113
 114int br_resetc_bmode(void)
 115{
 116        int rc = 0;
 117        u16 regw;
 118        u8 regb, scr;
 119        int cnt;
 120        unsigned int bmode = 0;
 121
 122        if (!resetc.i2cdev)
 123                rc = resetc_init();
 124
 125        if (rc != 0)
 126                return rc;
 127
 128        rc = dm_i2c_read(resetc.i2cdev, RSTCTRL_ENHSTATUS, &regb, 1);
 129        if (rc != 0) {
 130                printf("WARN: cannot read ENHSTATUS from resetcontroller!\n");
 131                return -1;
 132        }
 133
 134        rc = dm_i2c_read(resetc.i2cdev, RSTCTRL_SCRATCHREG0, &scr, 1);
 135        if (rc != 0) {
 136                printf("WARN: cannot read SCRATCHREG from resetcontroller!\n");
 137                return -1;
 138        }
 139
 140        board_boot_led(1);
 141
 142        /* special bootmode from resetcontroller */
 143        if (regb & 0x4) {
 144                bmode = BMODE_DIAG;
 145        } else if (regb & 0x8) {
 146                bmode = BMODE_DEFAULTAR;
 147        } else if (board_boot_key() != 0) {
 148                cnt = 4;
 149                do {
 150                        LCD_SETCURSOR(1, 8);
 151                        switch (cnt) {
 152                        case 4:
 153                                LCD_PUTS
 154                                ("release KEY to enter SERVICE-mode.     ");
 155                                break;
 156                        case 3:
 157                                LCD_PUTS
 158                                ("release KEY to enter DIAGNOSE-mode.    ");
 159                                break;
 160                        case 2:
 161                                LCD_PUTS
 162                                ("release KEY to enter BOOT-mode.        ");
 163                                break;
 164                        }
 165                        mdelay(1000);
 166                        cnt--;
 167                        if (board_boot_key() == 0)
 168                                break;
 169                } while (cnt);
 170
 171                switch (cnt) {
 172                case 0:
 173                        bmode = BMODE_PME;
 174                        break;
 175                case 1:
 176                        bmode = BMODE_DEFAULTAR;
 177                        break;
 178                case 2:
 179                        bmode = BMODE_DIAG;
 180                        break;
 181                case 3:
 182                        bmode = BMODE_SERVICE;
 183                        break;
 184                }
 185        } else if ((regb & 0x1) || scr == 0xCC) {
 186                bmode = BMODE_PME;
 187        } else {
 188                bmode = BMODE_RUN;
 189        }
 190
 191        LCD_SETCURSOR(1, 8);
 192
 193        switch (bmode) {
 194        case BMODE_PME:
 195                LCD_PUTS("entering PME-Mode (netscript).         ");
 196                regw = 0x0C0C;
 197                break;
 198        case BMODE_DEFAULTAR:
 199                LCD_PUTS("entering BOOT-mode.                    ");
 200                regw = 0x0000;
 201                break;
 202        case BMODE_DIAG:
 203                LCD_PUTS("entering DIAGNOSE-mode.                ");
 204                regw = 0x0F0F;
 205                break;
 206        case BMODE_SERVICE:
 207                LCD_PUTS("entering SERVICE mode.                 ");
 208                regw = 0xB4B4;
 209                break;
 210        case BMODE_RUN:
 211                LCD_PUTS("loading OS...                          ");
 212                regw = 0x0404;
 213                break;
 214        }
 215
 216        board_boot_led(0);
 217
 218        if (resetc.is_psoc)
 219                rc = dm_i2c_write(resetc.i2cdev, RSTCTRL_SCRATCHREG0,
 220                                  (u8 *)&regw, 2);
 221        else
 222                rc = dm_i2c_write(resetc.i2cdev, RSTCTRL_SCRATCHREG0,
 223                                  (u8 *)&regw, 1);
 224
 225        if (rc != 0)
 226                printf("WARN: cannot write into resetcontroller!\n");
 227
 228        if (resetc.is_psoc)
 229                printf("Reset: PSOC controller\n");
 230        else
 231                printf("Reset: STM32 controller\n");
 232
 233        printf("Mode:  %s\n", bootmodeascii[regw & 0x0F]);
 234        env_set_ulong("b_mode", regw & 0x0F);
 235
 236        return rc;
 237}
 238