1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 *
4 * HDF is dual licensed: you can use it either under the terms of
5 * the GPL, or the BSD license, at your option.
6 * See the LICENSE file in the root of this repository for complete details.
7 */
8
9 #include "platform_manager_test.h"
10 #include "osal_mem.h"
11 #include "platform_assert.h"
12 #include "platform_manager.h"
13
14 #define HDF_LOG_TAG platform_manager_test
15
16 #define PLAT_MGR_TEST_DEV_NUM 3
17 #define PLAT_MGR_TEST_DEV_NUM_START 0x5A
18 #define PLAT_DEV_NUMBER_0 0
19 #define PLAT_DEV_NUMBER_1 1
20 #define PLAT_DEV_NUMBER_2 2
21
22 static struct PlatformDevice *g_platDevices[PLAT_MGR_TEST_DEV_NUM];
23
PlatformManagerTestCreateDevices(void)24 static int32_t PlatformManagerTestCreateDevices(void)
25 {
26 int i;
27 int j;
28 int32_t ret;
29
30 for (i = 0; i < PLAT_MGR_TEST_DEV_NUM; i++) {
31 g_platDevices[i] = (struct PlatformDevice *)OsalMemCalloc(sizeof(struct PlatformDevice));
32 if (g_platDevices[i] == NULL) {
33 ret = HDF_ERR_MALLOC_FAIL;
34 goto CREATE_ERR__;
35 }
36 g_platDevices[i]->number = i + PLAT_MGR_TEST_DEV_NUM_START;
37 ret = PlatformDeviceInit(g_platDevices[i]);
38 if (ret != HDF_SUCCESS) {
39 OsalMemFree(g_platDevices[i]);
40 g_platDevices[i] = NULL;
41 goto CREATE_ERR__;
42 }
43 }
44
45 return HDF_SUCCESS;
46
47 CREATE_ERR__:
48 for (j = 0; j < i; j++) {
49 PlatformDeviceUninit(g_platDevices[j]);
50 OsalMemFree(g_platDevices[j]);
51 g_platDevices[j] = 0;
52 }
53
54 return ret;
55 }
56
PlatformManagerTestDestroyDevices(void)57 static void PlatformManagerTestDestroyDevices(void)
58 {
59 int i;
60
61 for (i = 0; i < PLAT_MGR_TEST_DEV_NUM; i++) {
62 PlatformDeviceUninit(g_platDevices[i]);
63 OsalMemFree(g_platDevices[i]);
64 g_platDevices[i] = NULL;
65 }
66 }
67
PlatformManagerTestAddAndDel(struct PlatformManager * manager)68 static int32_t PlatformManagerTestAddAndDel(struct PlatformManager *manager)
69 {
70 int32_t ret;
71 struct PlatformDevice *device0 = g_platDevices[PLAT_DEV_NUMBER_0];
72 struct PlatformDevice *device1 = g_platDevices[PLAT_DEV_NUMBER_1];
73 struct PlatformDevice *device2 = g_platDevices[PLAT_DEV_NUMBER_2];
74 struct PlatformDevice *device0Get = NULL;
75 struct PlatformDevice *device1Get = NULL;
76 int32_t refCntBeforeAdd;
77 int32_t refCntAfterAdd;
78 int32_t refCntBeforeDel;
79 int32_t refCntAfterDel;
80 int32_t number;
81
82 PLAT_LOGD("%s: enter", __func__);
83 // should add first device success
84 device0->name = "platform_device0";
85 refCntBeforeAdd = PlatformDeviceRefCount(device0);
86 ret = PlatformManagerAddDevice(manager, device0);
87 CHECK_EQ_RETURN(ret, HDF_SUCCESS, ret);
88 refCntAfterAdd = PlatformDeviceRefCount(device0);
89 // ref count should increase by 1 after add
90 CHECK_EQ_RETURN(refCntAfterAdd, refCntBeforeAdd + 1, HDF_FAILURE);
91
92 // should add another success
93 device1->name = "platform_device1";
94 ret = PlatformManagerAddDevice(manager, device1);
95 CHECK_EQ_RETURN(ret, HDF_SUCCESS, ret);
96
97 // should find the device added
98 device0Get = PlatformManagerGetDeviceByNumber(manager, device0->number);
99 CHECK_EQ_RETURN(device0Get, device0, HDF_FAILURE);
100 PlatformDevicePut(device0Get);
101
102 // should find another device added
103 device1Get = PlatformManagerGetDeviceByNumber(manager, device1->number);
104 CHECK_EQ_RETURN(device1Get, device1, HDF_FAILURE);
105 PlatformDevicePut(device1Get);
106
107 // should add fail on repeated number
108 number = device2->number;
109 device2->number = device0->number;
110 device2->name = "platform_device2";
111 ret = PlatformManagerAddDevice(manager, device2);
112 CHECK_NE_RETURN(ret, HDF_SUCCESS, ret);
113
114 // should add fail on repeated name
115 device2->number = number; // give it a right number
116 device2->name = device0->name;
117 ret = PlatformManagerAddDevice(manager, device2);
118 CHECK_NE_RETURN(ret, HDF_SUCCESS, ret);
119
120 refCntBeforeDel = PlatformDeviceRefCount(device0);
121 (void)PlatformManagerDelDevice(manager, device0);
122 refCntAfterDel = PlatformDeviceRefCount(device0);
123 // ref count should decrease by 1 after del
124 CHECK_EQ_RETURN(refCntAfterDel + 1, refCntBeforeDel, HDF_FAILURE);
125
126 // should not get the device removed
127 device0Get = PlatformManagerGetDeviceByNumber(manager, device0->number);
128 CHECK_EQ_RETURN(device0Get, NULL, HDF_FAILURE);
129
130 PLAT_LOGD("%s: exit", __func__);
131 return HDF_SUCCESS;
132 }
133
PlatformManagerTestGetDevice(struct PlatformManager * manager)134 static int32_t PlatformManagerTestGetDevice(struct PlatformManager *manager)
135 {
136 int32_t ret;
137 struct PlatformDevice *device0 = g_platDevices[PLAT_DEV_NUMBER_0];
138 struct PlatformDevice *device1 = g_platDevices[PLAT_DEV_NUMBER_1];
139 struct PlatformDevice *device2 = g_platDevices[PLAT_DEV_NUMBER_2];
140 struct PlatformDevice *device0Get = NULL;
141 struct PlatformDevice *device1Get = NULL;
142 int32_t refCntBeforeGet;
143 int32_t refCntAfterGet;
144 int32_t refCntBeforePut;
145 int32_t refCntAfterPut;
146
147 PLAT_LOGD("%s: enter", __func__);
148 // we add some devices first
149 device0->name = "platform_device0";
150 ret = PlatformManagerAddDevice(manager, device0);
151 CHECK_EQ_RETURN(ret, HDF_SUCCESS, ret);
152 device1->name = "platform_device1";
153 ret = PlatformManagerAddDevice(manager, device1);
154 CHECK_EQ_RETURN(ret, HDF_SUCCESS, ret);
155 device2->name = "platform_device2";
156 ret = PlatformManagerAddDevice(manager, device2);
157 CHECK_EQ_RETURN(ret, HDF_SUCCESS, ret);
158
159 refCntBeforeGet = PlatformDeviceRefCount(device0);
160 // should get the device by number
161 device0Get = PlatformManagerGetDeviceByNumber(manager, device0->number);
162 CHECK_EQ_RETURN(device0Get, device0, HDF_FAILURE);
163
164 refCntAfterGet = PlatformDeviceRefCount(device0);
165 // should increase refcount after get
166 CHECK_EQ_RETURN(refCntBeforeGet + 1, refCntAfterGet, HDF_FAILURE);
167
168 refCntBeforePut = PlatformDeviceRefCount(device0);
169 PlatformDevicePut(device0Get);
170 refCntAfterPut = PlatformDeviceRefCount(device0);
171 // should dcrease refcount after put
172 CHECK_EQ_RETURN(refCntBeforePut, refCntAfterPut + 1, HDF_FAILURE);
173
174 refCntBeforeGet = PlatformDeviceRefCount(device1);
175 // should get the device by name
176 device1Get = PlatformManagerGetDeviceByName(manager, "platform_device1");
177
178 CHECK_EQ_RETURN(device1Get, device1, HDF_FAILURE);
179 refCntAfterGet = PlatformDeviceRefCount(device1);
180 // should increase refcount after get
181 CHECK_EQ_RETURN(refCntBeforeGet + 1, refCntAfterGet, HDF_FAILURE);
182
183 refCntBeforePut = PlatformDeviceRefCount(device1);
184 PlatformDevicePut(device1Get);
185 refCntAfterPut = PlatformDeviceRefCount(device1);
186 // should dcrease refcount after put
187 CHECK_EQ_RETURN(refCntBeforePut, refCntAfterPut + 1, HDF_FAILURE);
188
189 PLAT_LOGD("%s: exit", __func__);
190 return HDF_SUCCESS;
191 }
192
PlatformManagerTestReliability(struct PlatformManager * manager)193 static int32_t PlatformManagerTestReliability(struct PlatformManager *manager)
194 {
195 int32_t ret;
196 struct PlatformDevice *device = g_platDevices[0];
197 int32_t number = device->number;
198
199 PLAT_LOGD("%s: enter", __func__);
200 // should not add success when manager is NULL
201 ret = PlatformManagerAddDevice(NULL, device);
202 CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
203
204 // should not add success when device is NULL
205 ret = PlatformManagerAddDevice(manager, NULL);
206 CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
207
208 // will not crash ...
209 PlatformManagerAddDevice(manager, NULL);
210 PlatformManagerAddDevice(NULL, device);
211
212 // should not get device by wrong parms
213 device = PlatformManagerGetDeviceByNumber(NULL, number);
214 CHECK_EQ_RETURN(device, NULL, HDF_FAILURE);
215 device = PlatformManagerGetDeviceByName(NULL, "platform_device0");
216 CHECK_EQ_RETURN(device, NULL, HDF_FAILURE);
217
218 PLAT_LOGD("%s: exit", __func__);
219 return HDF_SUCCESS;
220 }
221
222 struct PlatformManagerTestEntry {
223 int cmd;
224 int32_t (*func)(struct PlatformManager *manager);
225 const char *name;
226 };
227
228 static struct PlatformManagerTestEntry g_entry[] = {
229 { PLAT_MANAGER_TEST_ADD_DEVICE, PlatformManagerTestAddAndDel, "PlatformManagerTestAddAndDel" },
230 { PLAT_MANAGER_TEST_GET_DEVICE, PlatformManagerTestGetDevice, "PlatformManagerTestGetDevice" },
231 { PLAT_MANAGER_TEST_RELIABILITY, PlatformManagerTestReliability, "PlatformManagerTestReliability" },
232 };
233
PlatformManagerTestExecute(int cmd)234 int PlatformManagerTestExecute(int cmd)
235 {
236 uint32_t i;
237 int32_t ret = HDF_ERR_NOT_SUPPORT;
238 struct PlatformManager *manager = NULL;
239 struct PlatformManagerTestEntry *entry = NULL;
240
241 if (cmd > PLAT_MANAGER_TEST_CMD_MAX) {
242 PLAT_LOGE("PlatformManagerTestExecute: invalid cmd:%d", cmd);
243 ret = HDF_ERR_NOT_SUPPORT;
244 PLAT_LOGE("[PlatformManagerTestExecute][======cmd:%d====ret:%d======]", cmd, ret);
245 return ret;
246 }
247
248 for (i = 0; i < sizeof(g_entry) / sizeof(g_entry[0]); i++) {
249 if (g_entry[i].cmd != cmd || g_entry[i].func == NULL) {
250 continue;
251 }
252 entry = &g_entry[i];
253 break;
254 }
255
256 if (entry == NULL) {
257 PLAT_LOGE("%s: no entry matched, cmd = %d", __func__, cmd);
258 return HDF_ERR_NOT_SUPPORT;
259 }
260
261 ret = PlatformManagerCreate("platform_test_manager", &manager);
262 if (manager == NULL) {
263 PLAT_LOGE("%s: create manager failed:%d", __func__, ret);
264 return HDF_FAILURE;
265 }
266
267 ret = PlatformManagerTestCreateDevices();
268 if (ret != HDF_SUCCESS) {
269 PLAT_LOGE("%s: create devices failed:%d", __func__, ret);
270 PlatformManagerDestroy(manager);
271 return HDF_FAILURE;
272 }
273
274 ret = entry->func(manager);
275 PlatformManagerDestroy(manager);
276 PlatformManagerTestDestroyDevices();
277
278 PLAT_LOGE("[PlatformManagerTestExecute][======cmd:%d====ret:%d======]", cmd, ret);
279 return ret;
280 }
281
PlatformManagerTestExecuteAll(void)282 void PlatformManagerTestExecuteAll(void)
283 {
284 int32_t i;
285 int32_t ret;
286 int32_t fails = 0;
287
288 for (i = 0; i < PLAT_MANAGER_TEST_CMD_MAX; i++) {
289 ret = PlatformManagerTestExecute(i);
290 fails += (ret != HDF_SUCCESS) ? 1 : 0;
291 }
292
293 PLAT_LOGE("PlatformManagerTestExecuteALL: **********PASS:%d FAIL:%d************\n\n",
294 PLAT_MANAGER_TEST_CMD_MAX - fails, fails);
295 }
296