uboot/cmd/pmic.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * Copyright (C) 2014-2015 Samsung Electronics
   4 * Przemyslaw Marczak <p.marczak@samsung.com>
   5 */
   6#include <common.h>
   7#include <errno.h>
   8#include <dm.h>
   9#include <dm/uclass-internal.h>
  10#include <power/pmic.h>
  11
  12#define LIMIT_DEV       32
  13#define LIMIT_PARENT    20
  14
  15static struct udevice *currdev;
  16
  17static int failure(int ret)
  18{
  19        printf("Error: %d (%s)\n", ret, errno_str(ret));
  20
  21        return CMD_RET_FAILURE;
  22}
  23
  24static int do_dev(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
  25{
  26        char *name;
  27        int ret = -ENODEV;
  28
  29        switch (argc) {
  30        case 2:
  31                name = argv[1];
  32                ret = pmic_get(name, &currdev);
  33                if (ret) {
  34                        printf("Can't get PMIC: %s!\n", name);
  35                        return failure(ret);
  36                }
  37        case 1:
  38                if (!currdev) {
  39                        printf("PMIC device is not set!\n\n");
  40                        return CMD_RET_USAGE;
  41                }
  42
  43                printf("dev: %d @ %s\n", currdev->seq, currdev->name);
  44        }
  45
  46        return CMD_RET_SUCCESS;
  47}
  48
  49static int do_list(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
  50{
  51        struct udevice *dev;
  52        int ret;
  53
  54        printf("| %-*.*s| %-*.*s| %s @ %s\n",
  55               LIMIT_DEV, LIMIT_DEV, "Name",
  56               LIMIT_PARENT, LIMIT_PARENT, "Parent name",
  57               "Parent uclass", "seq");
  58
  59        for (ret = uclass_first_device(UCLASS_PMIC, &dev); dev;
  60             ret = uclass_next_device(&dev)) {
  61                if (ret)
  62                        continue;
  63
  64                printf("| %-*.*s| %-*.*s| %s @ %d\n",
  65                       LIMIT_DEV, LIMIT_DEV, dev->name,
  66                       LIMIT_PARENT, LIMIT_PARENT, dev->parent->name,
  67                       dev_get_uclass_name(dev->parent), dev->parent->seq);
  68        }
  69
  70        if (ret)
  71                return CMD_RET_FAILURE;
  72
  73        return CMD_RET_SUCCESS;
  74}
  75
  76static int do_dump(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
  77{
  78        struct uc_pmic_priv *priv;
  79        struct udevice *dev;
  80        char fmt[16];
  81        uint reg;
  82        int ret;
  83
  84        if (!currdev) {
  85                printf("First, set the PMIC device!\n");
  86                return CMD_RET_USAGE;
  87        }
  88
  89        dev = currdev;
  90        priv = dev_get_uclass_priv(dev);
  91        printf("Dump pmic: %s registers\n", dev->name);
  92
  93        sprintf(fmt, "%%%d.%dx ", priv->trans_len * 2,
  94                priv->trans_len * 2);
  95
  96        for (reg = 0; reg < pmic_reg_count(dev); reg++) {
  97                ret = pmic_reg_read(dev, reg);
  98                if (ret < 0) {
  99                        printf("Can't read register: %d\n", reg);
 100                        return failure(ret);
 101                }
 102
 103                if (!(reg % 16))
 104                        printf("\n0x%02x: ", reg);
 105
 106                printf(fmt, ret);
 107        }
 108        printf("\n");
 109
 110        return CMD_RET_SUCCESS;
 111}
 112
 113static int do_read(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
 114{
 115        struct uc_pmic_priv *priv;
 116        struct udevice *dev;
 117        int regs, ret;
 118        char fmt[24];
 119        uint reg;
 120
 121        if (!currdev) {
 122                printf("First, set the PMIC device!\n");
 123                return CMD_RET_USAGE;
 124        }
 125
 126        dev = currdev;
 127        priv = dev_get_uclass_priv(dev);
 128
 129        if (argc != 2)
 130                return CMD_RET_USAGE;
 131
 132        reg = simple_strtoul(argv[1], NULL, 0);
 133        regs = pmic_reg_count(dev);
 134        if (reg > regs) {
 135                printf("PMIC max reg: %d\n", regs);
 136                return failure(-EFAULT);
 137        }
 138
 139        ret = pmic_reg_read(dev, reg);
 140        if (ret < 0) {
 141                printf("Can't read PMIC register: %d!\n", reg);
 142                return failure(ret);
 143        }
 144
 145        sprintf(fmt, "0x%%02x: 0x%%%d.%dx\n", priv->trans_len * 2,
 146                priv->trans_len * 2);
 147        printf(fmt, reg, ret);
 148
 149        return CMD_RET_SUCCESS;
 150}
 151
 152static int do_write(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
 153{
 154        struct udevice *dev;
 155        uint reg, value;
 156        int regs, ret;
 157
 158        if (!currdev) {
 159                printf("First, set the PMIC device!\n");
 160                return CMD_RET_USAGE;
 161        }
 162
 163        dev = currdev;
 164
 165        if (argc != 3)
 166                return CMD_RET_USAGE;
 167
 168        reg = simple_strtoul(argv[1], NULL, 0);
 169        regs = pmic_reg_count(dev);
 170        if (reg > regs) {
 171                printf("PMIC max reg: %d\n", regs);
 172                return failure(-EFAULT);
 173        }
 174
 175        value = simple_strtoul(argv[2], NULL, 0);
 176
 177        ret = pmic_reg_write(dev, reg, value);
 178        if (ret) {
 179                printf("Can't write PMIC register: %d!\n", reg);
 180                return failure(ret);
 181        }
 182
 183        return CMD_RET_SUCCESS;
 184}
 185
 186static cmd_tbl_t subcmd[] = {
 187        U_BOOT_CMD_MKENT(dev, 2, 1, do_dev, "", ""),
 188        U_BOOT_CMD_MKENT(list, 1, 1, do_list, "", ""),
 189        U_BOOT_CMD_MKENT(dump, 1, 1, do_dump, "", ""),
 190        U_BOOT_CMD_MKENT(read, 2, 1, do_read, "", ""),
 191        U_BOOT_CMD_MKENT(write, 3, 1, do_write, "", ""),
 192};
 193
 194static int do_pmic(cmd_tbl_t *cmdtp, int flag, int argc,
 195                        char * const argv[])
 196{
 197        cmd_tbl_t *cmd;
 198
 199        argc--;
 200        argv++;
 201
 202        cmd = find_cmd_tbl(argv[0], subcmd, ARRAY_SIZE(subcmd));
 203        if (cmd == NULL || argc > cmd->maxargs)
 204                return CMD_RET_USAGE;
 205
 206        return cmd->cmd(cmdtp, flag, argc, argv);
 207}
 208
 209U_BOOT_CMD(pmic, CONFIG_SYS_MAXARGS, 1, do_pmic,
 210        "PMIC sub-system",
 211        "list          - list pmic devices\n"
 212        "pmic dev [name]    - show or [set] operating PMIC device\n"
 213        "pmic dump          - dump registers\n"
 214        "pmic read address  - read byte of register at address\n"
 215        "pmic write address - write byte to register at address\n"
 216);
 217