cros_ec: Show events in human-readable form
authorSimon Glass <sjg@chromium.org>
Sat, 16 Jan 2021 21:52:29 +0000 (14:52 -0700)
committerSimon Glass <sjg@chromium.org>
Sat, 30 Jan 2021 21:25:41 +0000 (14:25 -0700)
Add a command to show the current events as a list of names. This is
easier to decipher than a bit mask.

Signed-off-by: Simon Glass <sjg@chromium.org>
cmd/cros_ec.c
drivers/misc/cros_ec_sandbox.c
test/dm/cros_ec.c

index a222c75c17c1c5b7b75da3ab486a1cd9549a3481..eb5053d6424ebf110ed6811f5e9d8358e4d31fea 100644 (file)
@@ -197,6 +197,66 @@ static int do_show_switches(struct udevice *dev)
        return 0;
 }
 
+static const char *const event_name[] = {
+       "lid_closed",
+       "lid_open",
+       "power_button",
+       "ac_connected",
+       "ac_disconnected",
+       "battery_low",
+       "battery_critical",
+       "battery",
+       "thermal_threshold",
+       "device",
+       "thermal",
+       "usb_charger",
+       "key_pressed",
+       "interface_ready",
+       "keyboard_recovery",
+       "thermal_shutdown",
+       "battery_shutdown",
+       "throttle_start",
+       "throttle_stop",
+       "hang_detect",
+       "hang_reboot",
+       "pd_mcu",
+       "battery_status",
+       "panic",
+       "keyboard_fastboot",
+       "rtc",
+       "mkbp",
+       "usb_mux",
+       "mode_change",
+       "keyboard_recovery_hw_reinit",
+       "extended",
+       "invalid",
+};
+
+static int do_show_events(struct udevice *dev)
+{
+       u32 events;
+       int ret;
+       uint i;
+
+       ret = cros_ec_get_host_events(dev, &events);
+       if (ret)
+               return ret;
+       printf("%08x\n", events);
+       for (i = 0; i < ARRAY_SIZE(event_name); i++) {
+               enum host_event_code code = i + 1;
+               u64 mask = EC_HOST_EVENT_MASK(code);
+
+               if (events & mask) {
+                       if (event_name[i])
+                               printf("%s\n", event_name[i]);
+                       else
+                               printf("unknown code %#x\n", code);
+               }
+       }
+
+       return 0;
+}
+
 static int do_cros_ec(struct cmd_tbl *cmdtp, int flag, int argc,
                      char *const argv[])
 {
@@ -303,13 +363,10 @@ static int do_cros_ec(struct cmd_tbl *cmdtp, int flag, int argc,
                        return 1;
                }
        } else if (0 == strcmp("events", cmd)) {
-               uint32_t events;
+               ret = do_show_events(dev);
 
-               if (cros_ec_get_host_events(dev, &events)) {
-                       debug("%s: Could not read host events\n", __func__);
-                       return 1;
-               }
-               printf("0x%08x\n", events);
+               if (ret)
+                       printf("Error: %d\n", ret);
        } else if (0 == strcmp("clrevents", cmd)) {
                uint32_t events = 0x7fffffff;
 
@@ -498,6 +555,7 @@ U_BOOT_CMD(
        "crosec hash                Read CROS-EC hash\n"
        "crosec reboot [rw | ro | cold]  Reboot CROS-EC\n"
        "crosec events              Read CROS-EC host events\n"
+       "crosec eventsb             Read CROS-EC host events_b\n"
        "crosec clrevents [mask]    Clear CROS-EC host events\n"
        "crosec regioninfo <ro|rw>  Read image info\n"
        "crosec flashinfo           Read flash info\n"
index 38a2614a9939448c41b66ae347e4535467345578..845876cfb0cff7a7fc69963f66a2e45c6ea2267e 100644 (file)
@@ -364,10 +364,20 @@ static int process_cmd(struct ec_state *ec,
                        resp->mask |= EC_HOST_EVENT_MASK(
                                        EC_HOST_EVENT_KEYBOARD_RECOVERY);
                }
-
+               if (ec->test_flags & CROSECT_LID_OPEN)
+                       resp->mask |=
+                               EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_OPEN);
                len = sizeof(*resp);
                break;
        }
+       case EC_CMD_HOST_EVENT_CLEAR_B: {
+               const struct ec_params_host_event_mask *req = req_data;
+
+               if (req->mask & EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_OPEN))
+                       ec->test_flags &= ~CROSECT_LID_OPEN;
+               len = 0;
+               break;
+               }
        case EC_CMD_VBOOT_HASH: {
                const struct ec_params_vboot_hash *req = req_data;
                struct ec_response_vboot_hash *resp = resp_data;
index 43774400a1e26e54fdbd9ba1b3f8a388ea45b84f..0da7548fd24bd93ad7d0d848b0931bdc57bfa87f 100644 (file)
@@ -101,3 +101,40 @@ static int dm_test_cros_ec_switches(struct unit_test_state *uts)
        return 0;
 }
 DM_TEST(dm_test_cros_ec_switches, UT_TESTF_SCAN_FDT);
+
+static int dm_test_cros_ec_events(struct unit_test_state *uts)
+{
+       struct udevice *dev;
+       u32 events;
+
+       ut_assertok(uclass_first_device_err(UCLASS_CROS_EC, &dev));
+       ut_assertok(cros_ec_get_host_events(dev, &events));
+       ut_asserteq(0, events);
+
+       /* try the command */
+       console_record_reset();
+       ut_assertok(run_command("crosec events", 0));
+       ut_assert_nextline("00000000");
+       ut_assert_console_end();
+
+       /* Open the lid and check the event appears */
+       sandbox_cros_ec_set_test_flags(dev, CROSECT_LID_OPEN);
+       ut_assertok(cros_ec_get_host_events(dev, &events));
+       ut_asserteq(EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_OPEN), events);
+
+       /* try the command */
+       console_record_reset();
+       ut_assertok(run_command("crosec events", 0));
+       ut_assert_nextline("00000002");
+       ut_assert_nextline("lid_open");
+       ut_assert_console_end();
+
+       /* Clear the event */
+       ut_assertok(cros_ec_clear_host_events(dev,
+               EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_OPEN)));
+       ut_assertok(cros_ec_get_host_events(dev, &events));
+       ut_asserteq(0, events);
+
+       return 0;
+}
+DM_TEST(dm_test_cros_ec_events, UT_TESTF_SCAN_FDT);