Merge https://gitlab.denx.de/u-boot/custodians/u-boot-riscv
[platform/kernel/u-boot.git] / test / dm / regmap.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright (C) 2015 Google, Inc
4  */
5
6 #include <common.h>
7 #include <dm.h>
8 #include <log.h>
9 #include <mapmem.h>
10 #include <regmap.h>
11 #include <syscon.h>
12 #include <asm/test.h>
13 #include <dm/test.h>
14 #include <linux/err.h>
15 #include <test/ut.h>
16
17 /* Base test of register maps */
18 static int dm_test_regmap_base(struct unit_test_state *uts)
19 {
20         struct udevice *dev;
21         struct regmap *map;
22         ofnode node;
23         int i;
24
25         ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
26         map = syscon_get_regmap(dev);
27         ut_assertok_ptr(map);
28         ut_asserteq(1, map->range_count);
29         ut_asserteq(0x10, map->ranges[0].start);
30         ut_asserteq(16, map->ranges[0].size);
31         ut_asserteq(0x10, map_to_sysmem(regmap_get_range(map, 0)));
32
33         ut_assertok(uclass_get_device(UCLASS_SYSCON, 1, &dev));
34         map = syscon_get_regmap(dev);
35         ut_assertok_ptr(map);
36         ut_asserteq(4, map->range_count);
37         ut_asserteq(0x20, map->ranges[0].start);
38         for (i = 0; i < 4; i++) {
39                 const unsigned long addr = 0x20 + 8 * i;
40
41                 ut_asserteq(addr, map->ranges[i].start);
42                 ut_asserteq(5 + i, map->ranges[i].size);
43                 ut_asserteq(addr, map_to_sysmem(regmap_get_range(map, i)));
44         }
45
46         /* Check that we can't pretend a different device is a syscon */
47         ut_assertok(uclass_get_device(UCLASS_I2C, 0, &dev));
48         map = syscon_get_regmap(dev);
49         ut_asserteq_ptr(ERR_PTR(-ENOEXEC), map);
50
51         /* A different device can be a syscon by using Linux-compat API */
52         node = ofnode_path("/syscon@2");
53         ut_assert(ofnode_valid(node));
54
55         map = syscon_node_to_regmap(node);
56         ut_assertok_ptr(map);
57         ut_asserteq(4, map->range_count);
58         ut_asserteq(0x40, map->ranges[0].start);
59         for (i = 0; i < 4; i++) {
60                 const unsigned long addr = 0x40 + 8 * i;
61
62                 ut_asserteq(addr, map->ranges[i].start);
63                 ut_asserteq(5 + i, map->ranges[i].size);
64                 ut_asserteq(addr, map_to_sysmem(regmap_get_range(map, i)));
65         }
66
67         return 0;
68 }
69 DM_TEST(dm_test_regmap_base, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
70
71 /* Test we can access a regmap through syscon */
72 static int dm_test_regmap_syscon(struct unit_test_state *uts)
73 {
74         struct regmap *map;
75
76         map = syscon_get_regmap_by_driver_data(SYSCON0);
77         ut_assertok_ptr(map);
78         ut_asserteq(1, map->range_count);
79
80         map = syscon_get_regmap_by_driver_data(SYSCON1);
81         ut_assertok_ptr(map);
82         ut_asserteq(4, map->range_count);
83
84         map = syscon_get_regmap_by_driver_data(SYSCON_COUNT);
85         ut_asserteq_ptr(ERR_PTR(-ENODEV), map);
86
87         ut_asserteq(0x10, map_to_sysmem(syscon_get_first_range(SYSCON0)));
88         ut_asserteq(0x20, map_to_sysmem(syscon_get_first_range(SYSCON1)));
89         ut_asserteq_ptr(ERR_PTR(-ENODEV),
90                         syscon_get_first_range(SYSCON_COUNT));
91
92         return 0;
93 }
94
95 DM_TEST(dm_test_regmap_syscon, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
96
97 /* Read/Write/Modify test */
98 static int dm_test_regmap_rw(struct unit_test_state *uts)
99 {
100         struct udevice *dev;
101         struct regmap *map;
102         uint reg;
103
104         sandbox_set_enable_memio(true);
105         ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
106         map = syscon_get_regmap(dev);
107         ut_assertok_ptr(map);
108
109         ut_assertok(regmap_write(map, 0, 0xcacafafa));
110         ut_assertok(regmap_write(map, 5, 0x55aa2211));
111
112         ut_assertok(regmap_read(map, 0, &reg));
113         ut_asserteq(0xcacafafa, reg);
114         ut_assertok(regmap_read(map, 5, &reg));
115         ut_asserteq(0x55aa2211, reg);
116
117         ut_assertok(regmap_read(map, 0, &reg));
118         ut_asserteq(0xcacafafa, reg);
119         ut_assertok(regmap_update_bits(map, 0, 0xff00ff00, 0x55aa2211));
120         ut_assertok(regmap_read(map, 0, &reg));
121         ut_asserteq(0x55ca22fa, reg);
122         ut_assertok(regmap_update_bits(map, 5, 0x00ff00ff, 0xcacafada));
123         ut_assertok(regmap_read(map, 5, &reg));
124         ut_asserteq(0x55ca22da, reg);
125
126         return 0;
127 }
128
129 DM_TEST(dm_test_regmap_rw, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
130
131 /* Get/Set test */
132 static int dm_test_regmap_getset(struct unit_test_state *uts)
133 {
134         struct udevice *dev;
135         struct regmap *map;
136         uint reg;
137         struct layout {
138                 u32 val0;
139                 u32 val1;
140                 u32 val2;
141                 u32 val3;
142         };
143
144         sandbox_set_enable_memio(true);
145         ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
146         map = syscon_get_regmap(dev);
147         ut_assertok_ptr(map);
148
149         regmap_set(map, struct layout, val0, 0xcacafafa);
150         regmap_set(map, struct layout, val3, 0x55aa2211);
151
152         ut_assertok(regmap_get(map, struct layout, val0, &reg));
153         ut_asserteq(0xcacafafa, reg);
154         ut_assertok(regmap_get(map, struct layout, val3, &reg));
155         ut_asserteq(0x55aa2211, reg);
156
157         return 0;
158 }
159
160 DM_TEST(dm_test_regmap_getset, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
161
162 /* Read polling test */
163 static int dm_test_regmap_poll(struct unit_test_state *uts)
164 {
165         struct udevice *dev;
166         struct regmap *map;
167         uint reg;
168         unsigned long start;
169
170         ut_assertok(uclass_get_device(UCLASS_SYSCON, 0, &dev));
171         map = syscon_get_regmap(dev);
172         ut_assertok_ptr(map);
173
174         start = get_timer(0);
175
176         ut_assertok(regmap_write(map, 0, 0x0));
177         ut_asserteq(-ETIMEDOUT,
178                     regmap_read_poll_timeout_test(map, 0, reg,
179                                                   (reg == 0xcacafafa),
180                                                   1, 5 * CONFIG_SYS_HZ,
181                                                   5 * CONFIG_SYS_HZ));
182
183         ut_assert(get_timer(start) > (5 * CONFIG_SYS_HZ));
184
185         return 0;
186 }
187
188 DM_TEST(dm_test_regmap_poll, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);