xref: /openbmc/u-boot/test/dm/regmap.c (revision aac0c29d4b8418c5c78b552070ffeda022b16949)
183d290c5STom Rini // SPDX-License-Identifier: GPL-2.0+
286075babSSimon Glass /*
386075babSSimon Glass  * Copyright (C) 2015 Google, Inc
486075babSSimon Glass  */
586075babSSimon Glass 
686075babSSimon Glass #include <common.h>
786075babSSimon Glass #include <dm.h>
886075babSSimon Glass #include <mapmem.h>
986075babSSimon Glass #include <regmap.h>
1086075babSSimon Glass #include <syscon.h>
1186075babSSimon Glass #include <asm/test.h>
1286075babSSimon Glass #include <dm/test.h>
1386075babSSimon Glass #include <test/ut.h>
1486075babSSimon Glass 
1586075babSSimon Glass /* Base test of register maps */
dm_test_regmap_base(struct unit_test_state * uts)1686075babSSimon Glass static int dm_test_regmap_base(struct unit_test_state *uts)
1786075babSSimon Glass {
1886075babSSimon Glass 	struct udevice *dev;
1986075babSSimon Glass 	struct regmap *map;
2099552c34SMasahiro Yamada 	ofnode node;
2186075babSSimon Glass 	int i;
2286075babSSimon Glass 
2386075babSSimon Glass 	ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
2486075babSSimon Glass 	map = syscon_get_regmap(dev);
2586075babSSimon Glass 	ut_assertok_ptr(map);
2686075babSSimon Glass 	ut_asserteq(1, map->range_count);
278c1de5e0SMasahiro Yamada 	ut_asserteq(0x10, map->ranges[0].start);
2882744c20SMario Six 	ut_asserteq(16, map->ranges[0].size);
2986075babSSimon Glass 	ut_asserteq(0x10, map_to_sysmem(regmap_get_range(map, 0)));
3086075babSSimon Glass 
3186075babSSimon Glass 	ut_assertok(uclass_get_device(UCLASS_SYSCON, 1, &dev));
3286075babSSimon Glass 	map = syscon_get_regmap(dev);
3386075babSSimon Glass 	ut_assertok_ptr(map);
3486075babSSimon Glass 	ut_asserteq(4, map->range_count);
358c1de5e0SMasahiro Yamada 	ut_asserteq(0x20, map->ranges[0].start);
3686075babSSimon Glass 	for (i = 0; i < 4; i++) {
3786075babSSimon Glass 		const unsigned long addr = 0x20 + 8 * i;
3886075babSSimon Glass 
398c1de5e0SMasahiro Yamada 		ut_asserteq(addr, map->ranges[i].start);
408c1de5e0SMasahiro Yamada 		ut_asserteq(5 + i, map->ranges[i].size);
4186075babSSimon Glass 		ut_asserteq(addr, map_to_sysmem(regmap_get_range(map, i)));
4286075babSSimon Glass 	}
4386075babSSimon Glass 
4486075babSSimon Glass 	/* Check that we can't pretend a different device is a syscon */
4586075babSSimon Glass 	ut_assertok(uclass_get_device(UCLASS_I2C, 0, &dev));
4686075babSSimon Glass 	map = syscon_get_regmap(dev);
4786075babSSimon Glass 	ut_asserteq_ptr(ERR_PTR(-ENOEXEC), map);
4886075babSSimon Glass 
4999552c34SMasahiro Yamada 	/* A different device can be a syscon by using Linux-compat API */
5099552c34SMasahiro Yamada 	node = ofnode_path("/syscon@2");
5199552c34SMasahiro Yamada 	ut_assert(ofnode_valid(node));
5299552c34SMasahiro Yamada 
5399552c34SMasahiro Yamada 	map = syscon_node_to_regmap(node);
5499552c34SMasahiro Yamada 	ut_assertok_ptr(map);
5599552c34SMasahiro Yamada 	ut_asserteq(4, map->range_count);
5699552c34SMasahiro Yamada 	ut_asserteq(0x40, map->ranges[0].start);
5799552c34SMasahiro Yamada 	for (i = 0; i < 4; i++) {
5899552c34SMasahiro Yamada 		const unsigned long addr = 0x40 + 8 * i;
5999552c34SMasahiro Yamada 
6099552c34SMasahiro Yamada 		ut_asserteq(addr, map->ranges[i].start);
6199552c34SMasahiro Yamada 		ut_asserteq(5 + i, map->ranges[i].size);
6299552c34SMasahiro Yamada 		ut_asserteq(addr, map_to_sysmem(regmap_get_range(map, i)));
6399552c34SMasahiro Yamada 	}
6499552c34SMasahiro Yamada 
6586075babSSimon Glass 	return 0;
6686075babSSimon Glass }
6786075babSSimon Glass DM_TEST(dm_test_regmap_base, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
6886075babSSimon Glass 
6986075babSSimon Glass /* Test we can access a regmap through syscon */
dm_test_regmap_syscon(struct unit_test_state * uts)7086075babSSimon Glass static int dm_test_regmap_syscon(struct unit_test_state *uts)
7186075babSSimon Glass {
7286075babSSimon Glass 	struct regmap *map;
7386075babSSimon Glass 
7486075babSSimon Glass 	map = syscon_get_regmap_by_driver_data(SYSCON0);
7586075babSSimon Glass 	ut_assertok_ptr(map);
7686075babSSimon Glass 	ut_asserteq(1, map->range_count);
7786075babSSimon Glass 
7886075babSSimon Glass 	map = syscon_get_regmap_by_driver_data(SYSCON1);
7986075babSSimon Glass 	ut_assertok_ptr(map);
8086075babSSimon Glass 	ut_asserteq(4, map->range_count);
8186075babSSimon Glass 
8286075babSSimon Glass 	map = syscon_get_regmap_by_driver_data(SYSCON_COUNT);
8386075babSSimon Glass 	ut_asserteq_ptr(ERR_PTR(-ENODEV), map);
8486075babSSimon Glass 
8586075babSSimon Glass 	ut_asserteq(0x10, map_to_sysmem(syscon_get_first_range(SYSCON0)));
8686075babSSimon Glass 	ut_asserteq(0x20, map_to_sysmem(syscon_get_first_range(SYSCON1)));
8786075babSSimon Glass 	ut_asserteq_ptr(ERR_PTR(-ENODEV),
8886075babSSimon Glass 			syscon_get_first_range(SYSCON_COUNT));
8986075babSSimon Glass 
9086075babSSimon Glass 	return 0;
9186075babSSimon Glass }
9286075babSSimon Glass 
9386075babSSimon Glass DM_TEST(dm_test_regmap_syscon, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
94e068512cSNeil Armstrong 
95e068512cSNeil Armstrong /* Read/Write/Modify test */
dm_test_regmap_rw(struct unit_test_state * uts)96e068512cSNeil Armstrong static int dm_test_regmap_rw(struct unit_test_state *uts)
97e068512cSNeil Armstrong {
98e068512cSNeil Armstrong 	struct udevice *dev;
99e068512cSNeil Armstrong 	struct regmap *map;
100e068512cSNeil Armstrong 	uint reg;
101e068512cSNeil Armstrong 
102e068512cSNeil Armstrong 	ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
103e068512cSNeil Armstrong 	map = syscon_get_regmap(dev);
104e068512cSNeil Armstrong 	ut_assertok_ptr(map);
105e068512cSNeil Armstrong 
106e068512cSNeil Armstrong 	ut_assertok(regmap_write(map, 0, 0xcacafafa));
107e068512cSNeil Armstrong 	ut_assertok(regmap_write(map, 3, 0x55aa2211));
108e068512cSNeil Armstrong 
109e068512cSNeil Armstrong 	ut_assertok(regmap_read(map, 0, &reg));
110e068512cSNeil Armstrong 	ut_assertok(regmap_read(map, 3, &reg));
111e068512cSNeil Armstrong 
112e068512cSNeil Armstrong 	ut_assertok(regmap_update_bits(map, 0, 0xff00ff00, 0x55aa2211));
113e068512cSNeil Armstrong 	ut_assertok(regmap_update_bits(map, 3, 0x00ff00ff, 0xcacafada));
114e068512cSNeil Armstrong 
115e068512cSNeil Armstrong 	return 0;
116e068512cSNeil Armstrong }
117e068512cSNeil Armstrong 
118e068512cSNeil Armstrong DM_TEST(dm_test_regmap_rw, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
11945ef7f55SMario Six 
12045ef7f55SMario Six /* Get/Set test */
dm_test_regmap_getset(struct unit_test_state * uts)12145ef7f55SMario Six static int dm_test_regmap_getset(struct unit_test_state *uts)
12245ef7f55SMario Six {
12345ef7f55SMario Six 	struct udevice *dev;
12445ef7f55SMario Six 	struct regmap *map;
12545ef7f55SMario Six 	uint reg;
12645ef7f55SMario Six 	struct layout {
12745ef7f55SMario Six 		u32 val0;
12845ef7f55SMario Six 		u32 val1;
12945ef7f55SMario Six 		u32 val2;
13045ef7f55SMario Six 		u32 val3;
13145ef7f55SMario Six 	};
13245ef7f55SMario Six 
13345ef7f55SMario Six 	ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
13445ef7f55SMario Six 	map = syscon_get_regmap(dev);
13545ef7f55SMario Six 	ut_assertok_ptr(map);
13645ef7f55SMario Six 
13745ef7f55SMario Six 	regmap_set(map, struct layout, val0, 0xcacafafa);
13845ef7f55SMario Six 	regmap_set(map, struct layout, val3, 0x55aa2211);
13945ef7f55SMario Six 
14045ef7f55SMario Six 	ut_assertok(regmap_get(map, struct layout, val0, &reg));
14145ef7f55SMario Six 	ut_assertok(regmap_get(map, struct layout, val3, &reg));
14245ef7f55SMario Six 
14345ef7f55SMario Six 	return 0;
14445ef7f55SMario Six }
14545ef7f55SMario Six 
14645ef7f55SMario Six DM_TEST(dm_test_regmap_getset, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
147ebe3497cSNeil Armstrong 
148ebe3497cSNeil Armstrong /* Read polling test */
dm_test_regmap_poll(struct unit_test_state * uts)149ebe3497cSNeil Armstrong static int dm_test_regmap_poll(struct unit_test_state *uts)
150ebe3497cSNeil Armstrong {
151ebe3497cSNeil Armstrong 	struct udevice *dev;
152ebe3497cSNeil Armstrong 	struct regmap *map;
153ebe3497cSNeil Armstrong 	uint reg;
154ebe3497cSNeil Armstrong 	unsigned long start;
155ebe3497cSNeil Armstrong 
156ebe3497cSNeil Armstrong 	ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
157ebe3497cSNeil Armstrong 	map = syscon_get_regmap(dev);
158ebe3497cSNeil Armstrong 	ut_assertok_ptr(map);
159ebe3497cSNeil Armstrong 
160ebe3497cSNeil Armstrong 	start = get_timer(0);
161ebe3497cSNeil Armstrong 
162ebe3497cSNeil Armstrong 	ut_asserteq(-ETIMEDOUT,
163*df9cf1ccSSimon Glass 		    regmap_read_poll_timeout_test(map, 0, reg,
164ebe3497cSNeil Armstrong 						  (reg == 0xcacafafa),
165*df9cf1ccSSimon Glass 						  1, 5 * CONFIG_SYS_HZ,
166*df9cf1ccSSimon Glass 						  5 * CONFIG_SYS_HZ));
167ebe3497cSNeil Armstrong 
168ebe3497cSNeil Armstrong 	ut_assert(get_timer(start) > (5 * CONFIG_SYS_HZ));
169ebe3497cSNeil Armstrong 
170ebe3497cSNeil Armstrong 	return 0;
171ebe3497cSNeil Armstrong }
172ebe3497cSNeil Armstrong 
173ebe3497cSNeil Armstrong DM_TEST(dm_test_regmap_poll, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
174