diff options
Diffstat (limited to 'test')
-rw-r--r-- | test/dm/Makefile | 3 | ||||
-rw-r--r-- | test/dm/mux-cmd.c | 177 | ||||
-rw-r--r-- | test/dm/mux-emul.c | 105 | ||||
-rw-r--r-- | test/dm/mux-mmio.c | 138 |
4 files changed, 423 insertions, 0 deletions
diff --git a/test/dm/Makefile b/test/dm/Makefile index e2b0798388..8b3d77e34e 100644 --- a/test/dm/Makefile +++ b/test/dm/Makefile @@ -34,6 +34,7 @@ obj-y += irq.o obj-$(CONFIG_LED) += led.o obj-$(CONFIG_DM_MAILBOX) += mailbox.o obj-$(CONFIG_DM_MMC) += mmc.o +obj-$(CONFIG_CMD_MUX) += mux-cmd.o obj-y += fdtdec.o obj-y += ofnode.o obj-y += ofread.o @@ -57,6 +58,8 @@ obj-$(CONFIG_DM_SPI_FLASH) += sf.o obj-$(CONFIG_SMEM) += smem.o obj-$(CONFIG_DM_SPI) += spi.o obj-y += syscon.o +obj-$(CONFIG_MUX_MMIO) += mux-mmio.o +obj-$(CONFIG_MULTIPLEXER) += mux-emul.o obj-$(CONFIG_DM_USB) += usb.o obj-$(CONFIG_DM_PMIC) += pmic.o obj-$(CONFIG_DM_REGULATOR) += regulator.o diff --git a/test/dm/mux-cmd.c b/test/dm/mux-cmd.c new file mode 100644 index 0000000000..11c237b5da --- /dev/null +++ b/test/dm/mux-cmd.c @@ -0,0 +1,177 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (C) 2020 Texas Instruments Inc. + * Pratyush Yadav <p.yadav@ti.com> + */ +#include <common.h> +#include <dm.h> +#include <mux.h> +#include <mux-internal.h> +#include <dt-bindings/mux/mux.h> +#include <asm/test.h> +#include <dm/test.h> +#include <test/ut.h> +#include <console.h> +#include <rand.h> + +#define BUF_SIZE 256 + +/* Test 'mux list' */ +static int dm_test_cmd_mux_list(struct unit_test_state *uts) +{ + char str[BUF_SIZE], *tok; + struct udevice *dev; + struct mux_chip *chip; + struct mux_control *mux; + int i; + unsigned long val; + + sandbox_set_enable_memio(true); + + ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller", + &dev)); + chip = dev_get_uclass_priv(dev); + ut_assertnonnull(chip); + + run_command("mux list", 0); + ut_assert_nextline("a-mux-controller:"); + + /* + * Check the table header to make sure we are not out of sync with the + * code in the command. If we are, catch it early. + */ + console_record_readline(str, BUF_SIZE); + tok = strtok(str, " "); + ut_asserteq_str("ID", tok); + + tok = strtok(NULL, " "); + ut_asserteq_str("Selected", tok); + + tok = strtok(NULL, " "); + ut_asserteq_str("Current", tok); + tok = strtok(NULL, " "); + ut_asserteq_str("State", tok); + + tok = strtok(NULL, " "); + ut_asserteq_str("Idle", tok); + tok = strtok(NULL, " "); + ut_asserteq_str("State", tok); + + tok = strtok(NULL, " "); + ut_asserteq_str("Num", tok); + tok = strtok(NULL, " "); + ut_asserteq_str("States", tok); + + for (i = 0; i < chip->controllers; i++) { + mux = &chip->mux[i]; + + console_record_readline(str, BUF_SIZE); + + /* + * Check if the ID printed matches with the ID of the chip we + * have. + */ + tok = strtok(str, " "); + ut_assertok(strict_strtoul(tok, 10, &val)); + ut_asserteq(i, val); + + /* Check if mux selection state matches. */ + tok = strtok(NULL, " "); + if (mux->in_use) { + ut_asserteq_str("yes", tok); + } else { + ut_asserteq_str("no", tok); + } + + /* Check if the current state matches. */ + tok = strtok(NULL, " "); + if (mux->cached_state == MUX_IDLE_AS_IS) { + ut_asserteq_str("unknown", tok); + } else { + ut_assertok(strict_strtoul(tok, 16, &val)); + ut_asserteq(mux->cached_state, val); + } + + /* Check if the idle state matches */ + tok = strtok(NULL, " "); + if (mux->idle_state == MUX_IDLE_AS_IS) { + ut_asserteq_str("as-is", tok); + } else { + ut_assertok(strict_strtoul(tok, 16, &val)); + ut_asserteq(mux->idle_state, val); + } + + /* Check if the number of states matches */ + tok = strtok(NULL, " "); + ut_assertok(strict_strtoul(tok, 16, &val)); + ut_asserteq(mux->states, val); + } + + return 0; +} +DM_TEST(dm_test_cmd_mux_list, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); + +static int dm_test_cmd_mux_select(struct unit_test_state *uts) +{ + struct udevice *dev; + struct mux_chip *chip; + struct mux_control *mux; + char cmd[BUF_SIZE]; + unsigned int i, state; + + sandbox_set_enable_memio(true); + + ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller", + &dev)); + chip = dev_get_uclass_priv(dev); + ut_assertnonnull(chip); + + srand(get_ticks() + rand()); + for (i = 0; i < chip->controllers; i++) { + mux = &chip->mux[i]; + + state = rand() % mux->states; + + snprintf(cmd, BUF_SIZE, "mux select a-mux-controller %x %x", i, + state); + run_command(cmd, 0); + ut_asserteq(!!mux->in_use, true); + ut_asserteq(state, mux->cached_state); + + ut_assertok(mux_control_deselect(mux)); + } + + return 0; +} +DM_TEST(dm_test_cmd_mux_select, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); + +static int dm_test_cmd_mux_deselect(struct unit_test_state *uts) +{ + struct udevice *dev; + struct mux_chip *chip; + struct mux_control *mux; + char cmd[BUF_SIZE]; + unsigned int i, state; + + sandbox_set_enable_memio(true); + + ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller", + &dev)); + chip = dev_get_uclass_priv(dev); + ut_assertnonnull(chip); + + srand(get_ticks() + rand()); + for (i = 0; i < chip->controllers; i++) { + mux = &chip->mux[i]; + + state = rand() % mux->states; + ut_assertok(mux_control_select(mux, state)); + + snprintf(cmd, BUF_SIZE, "mux deselect a-mux-controller %d", i); + run_command(cmd, 0); + ut_asserteq(!!mux->in_use, false); + } + + return 0; +} +DM_TEST(dm_test_cmd_mux_deselect, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); diff --git a/test/dm/mux-emul.c b/test/dm/mux-emul.c new file mode 100644 index 0000000000..141fd4d908 --- /dev/null +++ b/test/dm/mux-emul.c @@ -0,0 +1,105 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2020 Texas Instruments Incorporated - http://www.ti.com/ + * Pratyush Yadav <p.yadav@ti.com> + */ +#include <common.h> +#include <dm.h> +#include <mux.h> +#include <mux-internal.h> +#include <dm/test.h> +#include <test/ut.h> + +struct mux_emul_priv { + u32 state; +}; + +static int mux_emul_set(struct mux_control *mux, int state) +{ + struct mux_emul_priv *priv = dev_get_priv(mux->dev); + + priv->state = state; + return 0; +} + +static int mux_emul_probe(struct udevice *dev) +{ + struct mux_chip *mux_chip = dev_get_uclass_priv(dev); + struct mux_control *mux; + u32 idle_state; + int ret; + + ret = mux_alloc_controllers(dev, 1); + if (ret < 0) + return ret; + + mux = &mux_chip->mux[0]; + + ret = dev_read_u32(dev, "idle-state", &idle_state); + if (ret) + return ret; + + mux->idle_state = idle_state; + mux->states = 0x100000; + + return 0; +} + +static const struct mux_control_ops mux_emul_ops = { + .set = mux_emul_set, +}; + +static const struct udevice_id mux_emul_of_match[] = { + { .compatible = "mux-emul" }, + { /* sentinel */ }, +}; + +U_BOOT_DRIVER(emul_mux) = { + .name = "mux-emul", + .id = UCLASS_MUX, + .of_match = mux_emul_of_match, + .ops = &mux_emul_ops, + .probe = mux_emul_probe, + .priv_auto_alloc_size = sizeof(struct mux_emul_priv), +}; + +static int dm_test_mux_emul_default_state(struct unit_test_state *uts) +{ + struct udevice *dev; + struct mux_control *mux; + struct mux_emul_priv *priv; + + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "a-test", + &dev)); + ut_assertok(mux_control_get(dev, "mux4", &mux)); + + priv = dev_get_priv(mux->dev); + + ut_asserteq(0xabcd, priv->state); + + return 0; +} +DM_TEST(dm_test_mux_emul_default_state, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); + +static int dm_test_mux_emul_select_deselect(struct unit_test_state *uts) +{ + struct udevice *dev; + struct mux_control *mux; + struct mux_emul_priv *priv; + + gd->flags &= ~(GD_FLG_SILENT | GD_FLG_RECORD); + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "a-test", + &dev)); + ut_assertok(mux_control_get(dev, "mux4", &mux)); + + priv = dev_get_priv(mux->dev); + + ut_assertok(mux_control_select(mux, 0x1234)); + ut_asserteq(priv->state, 0x1234); + + ut_assertok(mux_control_deselect(mux)); + ut_asserteq(priv->state, 0xabcd); + + return 0; +} +DM_TEST(dm_test_mux_emul_select_deselect, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); diff --git a/test/dm/mux-mmio.c b/test/dm/mux-mmio.c new file mode 100644 index 0000000000..fd353d8b15 --- /dev/null +++ b/test/dm/mux-mmio.c @@ -0,0 +1,138 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Copyright (C) 2017-2018 Texas Instruments Incorporated - http://www.ti.com/ + * Jean-Jacques Hiblot <jjhiblot@ti.com> + */ + +#include <common.h> +#include <dm.h> +#include <mux.h> +#include <regmap.h> +#include <syscon.h> +#include <asm/test.h> +#include <dm/test.h> +#include <dm/device-internal.h> +#include <test/ut.h> + +static int dm_test_mux_mmio_select(struct unit_test_state *uts) +{ + struct udevice *dev, *dev_b; + struct regmap *map; + struct mux_control *ctl0_a, *ctl0_b; + struct mux_control *ctl1; + struct mux_control *ctl_err; + u32 val; + int i; + + sandbox_set_enable_memio(true); + + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "a-test", + &dev)); + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "b-test", + &dev_b)); + map = syscon_regmap_lookup_by_phandle(dev, "mux-syscon"); + ut_assertok_ptr(map); + ut_assert(map); + + ut_assertok(mux_control_get(dev, "mux0", &ctl0_a)); + ut_assertok(mux_control_get(dev, "mux1", &ctl1)); + ut_asserteq(-ERANGE, mux_control_get(dev, "mux3", &ctl_err)); + ut_asserteq(-ENODATA, mux_control_get(dev, "dummy", &ctl_err)); + ut_assertok(mux_control_get(dev_b, "mux0", &ctl0_b)); + + for (i = 0; i < mux_control_states(ctl0_a); i++) { + /* Select a new state and verify the value in the regmap. */ + ut_assertok(mux_control_select(ctl0_a, i)); + ut_assertok(regmap_read(map, 0, &val)); + ut_asserteq(i, (val & 0x30) >> 4); + /* + * Deselect the mux and verify that the value in the regmap + * reflects the idle state (fixed to MUX_IDLE_AS_IS). + */ + ut_assertok(mux_control_deselect(ctl0_a)); + ut_assertok(regmap_read(map, 0, &val)); + ut_asserteq(i, (val & 0x30) >> 4); + } + + for (i = 0; i < mux_control_states(ctl1); i++) { + /* Select a new state and verify the value in the regmap. */ + ut_assertok(mux_control_select(ctl1, i)); + ut_assertok(regmap_read(map, 0xc, &val)); + ut_asserteq(i, (val & 0x1E) >> 1); + /* + * Deselect the mux and verify that the value in the regmap + * reflects the idle state (fixed to 2). + */ + ut_assertok(mux_control_deselect(ctl1)); + ut_assertok(regmap_read(map, 0xc, &val)); + ut_asserteq(2, (val & 0x1E) >> 1); + } + + /* Try unbalanced selection/deselection. */ + ut_assertok(mux_control_select(ctl0_a, 0)); + ut_asserteq(-EBUSY, mux_control_select(ctl0_a, 1)); + ut_asserteq(-EBUSY, mux_control_select(ctl0_a, 0)); + ut_assertok(mux_control_deselect(ctl0_a)); + + /* Try concurrent selection. */ + ut_assertok(mux_control_select(ctl0_a, 0)); + ut_assert(mux_control_select(ctl0_b, 0)); + ut_assertok(mux_control_deselect(ctl0_a)); + ut_assertok(mux_control_select(ctl0_b, 0)); + ut_assert(mux_control_select(ctl0_a, 0)); + ut_assertok(mux_control_deselect(ctl0_b)); + ut_assertok(mux_control_select(ctl0_a, 0)); + ut_assertok(mux_control_deselect(ctl0_a)); + + return 0; +} +DM_TEST(dm_test_mux_mmio_select, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); + +/* Test that managed API for mux work correctly */ +static int dm_test_devm_mux_mmio(struct unit_test_state *uts) +{ + struct udevice *dev, *dev_b; + struct mux_control *ctl0_a, *ctl0_b; + struct mux_control *ctl1; + struct mux_control *ctl_err; + + sandbox_set_enable_memio(true); + + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "a-test", + &dev)); + ut_assertok(uclass_get_device_by_name(UCLASS_TEST_FDT, "b-test", + &dev_b)); + + ctl0_a = devm_mux_control_get(dev, "mux0"); + ut_assertok_ptr(ctl0_a); + ut_assert(ctl0_a); + ctl1 = devm_mux_control_get(dev, "mux1"); + ut_assertok_ptr(ctl1); + ut_assert(ctl1); + ctl_err = devm_mux_control_get(dev, "mux3"); + ut_asserteq(-ERANGE, PTR_ERR(ctl_err)); + ctl_err = devm_mux_control_get(dev, "dummy"); + ut_asserteq(-ENODATA, PTR_ERR(ctl_err)); + + ctl0_b = devm_mux_control_get(dev_b, "mux0"); + ut_assertok_ptr(ctl0_b); + ut_assert(ctl0_b); + + /* Try concurrent selection. */ + ut_assertok(mux_control_select(ctl0_a, 0)); + ut_assert(mux_control_select(ctl0_b, 0)); + ut_assertok(mux_control_deselect(ctl0_a)); + ut_assertok(mux_control_select(ctl0_b, 0)); + ut_assert(mux_control_select(ctl0_a, 0)); + ut_assertok(mux_control_deselect(ctl0_b)); + + /* Remove one device and check that the mux is released. */ + ut_assertok(mux_control_select(ctl0_a, 0)); + ut_assert(mux_control_select(ctl0_b, 0)); + device_remove(dev, DM_REMOVE_NORMAL); + ut_assertok(mux_control_select(ctl0_b, 0)); + + device_remove(dev_b, DM_REMOVE_NORMAL); + return 0; +} +DM_TEST(dm_test_devm_mux_mmio, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT); |