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