summaryrefslogtreecommitdiff
path: root/common
diff options
context:
space:
mode:
Diffstat (limited to 'common')
-rw-r--r--common/Makefile1
-rw-r--r--common/avb_verify.c89
-rw-r--r--common/button_cmd.c83
-rw-r--r--common/event.c5
-rw-r--r--common/main.c3
-rw-r--r--common/spl/Kconfig3
-rw-r--r--common/usb_hub.c6
7 files changed, 169 insertions, 21 deletions
diff --git a/common/Makefile b/common/Makefile
index f010c2a1b9b..e9835473420 100644
--- a/common/Makefile
+++ b/common/Makefile
@@ -12,6 +12,7 @@ obj-y += cli_getch.o cli_simple.o cli_readline.o
obj-$(CONFIG_HUSH_OLD_PARSER) += cli_hush.o
obj-$(CONFIG_HUSH_MODERN_PARSER) += cli_hush_modern.o
obj-$(CONFIG_AUTOBOOT) += autoboot.o
+obj-$(CONFIG_BUTTON_CMD) += button_cmd.o
obj-y += version.o
# # boards
diff --git a/common/avb_verify.c b/common/avb_verify.c
index 48ba8db51e5..cff9117d92f 100644
--- a/common/avb_verify.c
+++ b/common/avb_verify.c
@@ -1,7 +1,6 @@
+// SPDX-License-Identifier: GPL-2.0+
/*
* (C) Copyright 2018, Linaro Limited
- *
- * SPDX-License-Identifier: GPL-2.0+
*/
#include <avb_verify.h>
@@ -120,6 +119,55 @@ static const unsigned char avb_root_pub[1032] = {
0xd8, 0x7e,
};
+const char *str_avb_io_error(AvbIOResult res)
+{
+ switch (res) {
+ case AVB_IO_RESULT_OK:
+ return "Requested operation was successful";
+ case AVB_IO_RESULT_ERROR_IO:
+ return "Underlying hardware encountered an I/O error";
+ case AVB_IO_RESULT_ERROR_OOM:
+ return "Unable to allocate memory";
+ case AVB_IO_RESULT_ERROR_NO_SUCH_PARTITION:
+ return "Requested partition does not exist";
+ case AVB_IO_RESULT_ERROR_RANGE_OUTSIDE_PARTITION:
+ return "Bytes requested is outside the range of partition";
+ case AVB_IO_RESULT_ERROR_NO_SUCH_VALUE:
+ return "Named persistent value does not exist";
+ case AVB_IO_RESULT_ERROR_INVALID_VALUE_SIZE:
+ return "Named persistent value size is not supported";
+ case AVB_IO_RESULT_ERROR_INSUFFICIENT_SPACE:
+ return "Buffer is too small for the requested operation";
+ default:
+ return "Unknown AVB error";
+ }
+}
+
+const char *str_avb_slot_error(AvbSlotVerifyResult res)
+{
+ switch (res) {
+ case AVB_SLOT_VERIFY_RESULT_OK:
+ return "Verification passed successfully";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_OOM:
+ return "Allocation of memory failed";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_IO:
+ return "I/O error occurred while trying to load data";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_VERIFICATION:
+ return "Digest didn't match or signature checks failed";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_ROLLBACK_INDEX:
+ return "Rollback index is less than its stored value";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_PUBLIC_KEY_REJECTED:
+ return "Public keys are not accepted";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_INVALID_METADATA:
+ return "Metadata is invalid or inconsistent";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_UNSUPPORTED_VERSION:
+ return "Metadata requires a newer version of libavb";
+ case AVB_SLOT_VERIFY_RESULT_ERROR_INVALID_ARGUMENT:
+ return "Invalid arguments are used";
+ default:
+ return "Unknown AVB slot verification error";
+ }
+}
/**
* ============================================================================
* Boot states support (GREEN, YELLOW, ORANGE, RED) and dm_verity
@@ -280,9 +328,9 @@ static unsigned long mmc_read_and_flush(struct mmc_part *part,
* Reading fails on unaligned buffers, so we have to
* use aligned temporary buffer and then copy to destination
*/
-
if (unaligned) {
- printf("Handling unaligned read buffer..\n");
+ debug("%s: handling unaligned read buffer, addr = 0x%p\n",
+ __func__, buffer);
tmp_buf = get_sector_buf();
buf_size = get_sector_buf_size();
if (sectors > buf_size / part->info.blksz)
@@ -321,7 +369,8 @@ static unsigned long mmc_write(struct mmc_part *part, lbaint_t start,
if (unaligned) {
tmp_buf = get_sector_buf();
buf_size = get_sector_buf_size();
- printf("Handling unaligned wrire buffer..\n");
+ debug("%s: handling unaligned read buffer, addr = 0x%p\n",
+ __func__, buffer);
if (sectors > buf_size / part->info.blksz)
sectors = buf_size / part->info.blksz;
@@ -349,28 +398,35 @@ static struct mmc_part *get_partition(AvbOps *ops, const char *partition)
dev_num = get_boot_device(ops);
part->mmc = find_mmc_device(dev_num);
if (!part->mmc) {
- printf("No MMC device at slot %x\n", dev_num);
+ printf("%s: no MMC device at slot %x\n", __func__, dev_num);
goto err;
}
- if (mmc_init(part->mmc)) {
- printf("MMC initialization failed\n");
+ ret = mmc_init(part->mmc);
+ if (ret) {
+ printf("%s: MMC initialization failed, err = %d\n",
+ __func__, ret);
goto err;
}
- ret = mmc_switch_part(part->mmc, part_num);
- if (ret)
- goto err;
+ if (IS_MMC(part->mmc)) {
+ ret = mmc_switch_part(part->mmc, part_num);
+ if (ret) {
+ printf("%s: MMC part switch failed, err = %d\n",
+ __func__, ret);
+ goto err;
+ }
+ }
mmc_blk = mmc_get_blk_desc(part->mmc);
if (!mmc_blk) {
- printf("Error - failed to obtain block descriptor\n");
+ printf("%s: failed to obtain block descriptor\n", __func__);
goto err;
}
ret = part_get_info_by_name(mmc_blk, partition, &part->info);
if (ret < 0) {
- printf("Can't find partition '%s'\n", partition);
+ printf("%s: can't find partition '%s'\n", __func__, partition);
goto err;
}
@@ -683,7 +739,7 @@ static AvbIOResult read_rollback_index(AvbOps *ops,
{
#ifndef CONFIG_OPTEE_TA_AVB
/* For now we always return 0 as the stored rollback index. */
- printf("%s not supported yet\n", __func__);
+ debug("%s: rollback protection is not implemented\n", __func__);
if (out_rollback_index)
*out_rollback_index = 0;
@@ -729,7 +785,7 @@ static AvbIOResult write_rollback_index(AvbOps *ops,
{
#ifndef CONFIG_OPTEE_TA_AVB
/* For now this is a no-op. */
- printf("%s not supported yet\n", __func__);
+ debug("%s: rollback protection is not implemented\n", __func__);
return AVB_IO_RESULT_OK;
#else
@@ -765,8 +821,7 @@ static AvbIOResult read_is_device_unlocked(AvbOps *ops, bool *out_is_unlocked)
{
#ifndef CONFIG_OPTEE_TA_AVB
/* For now we always return that the device is unlocked. */
-
- printf("%s not supported yet\n", __func__);
+ debug("%s: device locking is not implemented\n", __func__);
*out_is_unlocked = true;
diff --git a/common/button_cmd.c b/common/button_cmd.c
new file mode 100644
index 00000000000..b6a8434d6f2
--- /dev/null
+++ b/common/button_cmd.c
@@ -0,0 +1,83 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (c) 2023 Linaro Ltd.
+ * Author: Caleb Connolly <caleb.connolly@linaro.org>
+ */
+
+#include <button.h>
+#include <command.h>
+#include <env.h>
+#include <log.h>
+#include <vsprintf.h>
+
+/* Some sane limit "just in case" */
+#define MAX_BTN_CMDS 32
+
+struct button_cmd {
+ bool pressed;
+ const char *btn_name;
+ const char *cmd;
+};
+
+/*
+ * Button commands are set via environment variables, e.g.:
+ * button_cmd_N_name=Volume Up
+ * button_cmd_N=fastboot usb 0
+ *
+ * This function will retrieve the command for the given button N
+ * and populate the cmd struct with the command string and pressed
+ * state of the button.
+ *
+ * Returns 1 if a command was found, 0 otherwise.
+ */
+static int get_button_cmd(int n, struct button_cmd *cmd)
+{
+ const char *cmd_str;
+ struct udevice *btn;
+ char buf[24];
+
+ snprintf(buf, sizeof(buf), "button_cmd_%d_name", n);
+ cmd->btn_name = env_get(buf);
+ if (!cmd->btn_name)
+ return 0;
+
+ button_get_by_label(cmd->btn_name, &btn);
+ if (!btn) {
+ log_err("No button labelled '%s'\n", cmd->btn_name);
+ return 0;
+ }
+
+ cmd->pressed = button_get_state(btn) == BUTTON_ON;
+ /* If the button isn't pressed then cmd->cmd will be unused so don't waste
+ * cycles reading it
+ */
+ if (!cmd->pressed)
+ return 1;
+
+ snprintf(buf, sizeof(buf), "button_cmd_%d", n);
+ cmd_str = env_get(buf);
+ if (!cmd_str) {
+ log_err("No command set for button '%s'\n", cmd->btn_name);
+ return 0;
+ }
+
+ cmd->cmd = cmd_str;
+
+ return 1;
+}
+
+void process_button_cmds(void)
+{
+ struct button_cmd cmd = {0};
+ int i = 0;
+
+ while (get_button_cmd(i++, &cmd) && i < MAX_BTN_CMDS) {
+ if (!cmd.pressed)
+ continue;
+
+ log_info("BTN '%s'> %s\n", cmd.btn_name, cmd.cmd);
+ run_command(cmd.cmd, CMD_FLAG_ENV);
+ /* Don't run commands for multiple buttons */
+ return;
+ }
+}
diff --git a/common/event.c b/common/event.c
index dc61b9672f3..16c2ba6cc92 100644
--- a/common/event.c
+++ b/common/event.c
@@ -56,7 +56,10 @@ _Static_assert(ARRAY_SIZE(type_name) == EVT_COUNT, "event type_name size");
const char *event_type_name(enum event_t type)
{
#if CONFIG_IS_ENABLED(EVENT_DEBUG)
- return type_name[type];
+ if (type < ARRAY_SIZE(type_name))
+ return type_name[type];
+ else
+ return "(unknown)";
#else
return "(unknown)";
#endif
diff --git a/common/main.c b/common/main.c
index 6dba6cba144..82d3aafa53c 100644
--- a/common/main.c
+++ b/common/main.c
@@ -8,6 +8,7 @@
#include <common.h>
#include <autoboot.h>
+#include <button.h>
#include <bootstage.h>
#include <bootstd.h>
#include <cli.h>
@@ -62,6 +63,8 @@ void main_loop(void)
efi_launch_capsules();
}
+ process_button_cmds();
+
s = bootdelay_process();
if (cli_process_fdt(&s))
cli_secure_boot_cmd(s);
diff --git a/common/spl/Kconfig b/common/spl/Kconfig
index 8805dd33fec..6405374bcc1 100644
--- a/common/spl/Kconfig
+++ b/common/spl/Kconfig
@@ -371,7 +371,8 @@ config SPL_SHARES_INIT_SP_ADDR
config SPL_STACK
hex "Initial stack pointer location"
- depends on (ARM || ARCH_JZ47XX || MICROBLAZE || RISCV) && SPL_FRAMEWORK
+ depends on (ARM || ARCH_JZ47XX || MICROBLAZE || RISCV) && \
+ SPL_FRAMEWORK || ROCKCHIP_RK3036
depends on !SPL_SHARES_INIT_SP_ADDR
default 0x946bb8 if ARCH_MX7
default 0x93ffb8 if ARCH_MX6 && MX6_OCRAM_256KB
diff --git a/common/usb_hub.c b/common/usb_hub.c
index 3fb7e14d106..2e054eb9353 100644
--- a/common/usb_hub.c
+++ b/common/usb_hub.c
@@ -174,8 +174,10 @@ static void usb_hub_power_on(struct usb_hub_device *hub)
debug("enabling power on all ports\n");
for (i = 0; i < dev->maxchild; i++) {
- usb_set_port_feature(dev, i + 1, USB_PORT_FEAT_RESET);
- debug("Reset : port %d returns %lX\n", i + 1, dev->status);
+ if (usb_hub_is_superspeed(dev)) {
+ usb_set_port_feature(dev, i + 1, USB_PORT_FEAT_RESET);
+ debug("Reset : port %d returns %lX\n", i + 1, dev->status);
+ }
usb_set_port_feature(dev, i + 1, USB_PORT_FEAT_POWER);
debug("PowerOn : port %d returns %lX\n", i + 1, dev->status);
}