• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2023 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_event_test.h"
10 #include "hdf_base.h"
11 #include "hdf_log.h"
12 #include "osal_sem.h"
13 #include "osal_spinlock.h"
14 #include "osal_time.h"
15 #include "platform_assert.h"
16 #include "platform_event.h"
17 
18 #define HDF_LOG_TAG platform_event_test
19 
20 #define PLAT_EVENT_TEST_TIMEOUT 10
21 
22 enum PlatformTestEvent {
23     PLAT_TEST_EVENT_A = 0x1,
24     PLAT_TEST_EVENT_B = 0x2,
25     PLAT_TEST_EVENT_C = 0x4,
26 };
27 
PlatformEventTestInitAndUninit(struct PlatformEvent * pe)28 static int32_t PlatformEventTestInitAndUninit(struct PlatformEvent *pe)
29 {
30     int32_t ret;
31 
32     PLAT_LOGD("PlatformEventTestInitAndUninit: enter!");
33     // eventsWord should be 0 after init
34     CHECK_EQ_RETURN(pe->eventsWord, 0, HDF_FAILURE);
35 
36     // can use spinlock after init
37     ret = OsalSpinLock(&pe->spin);
38     if (!CHECK_EQ(ret, HDF_SUCCESS)) {
39         return HDF_FAILURE;
40     }
41     (void)OsalSpinUnlock(&pe->spin);
42 
43     // can use sem after init
44     ret = OsalSemPost(&pe->sem);
45     if (!CHECK_EQ(ret, HDF_SUCCESS)) {
46         return HDF_FAILURE;
47     }
48     (void)OsalSemWait(&pe->sem, HDF_WAIT_FOREVER);
49 
50     PLAT_LOGD("PlatformEventTestInitAndUninit: exit!");
51     return HDF_SUCCESS;
52 }
53 
PlatformEventTestPostAndWait(struct PlatformEvent * pe)54 static int32_t PlatformEventTestPostAndWait(struct PlatformEvent *pe)
55 {
56     int32_t ret;
57     uint32_t events;
58 
59     PLAT_LOGD("PlatformEventTestPostAndWait: enter!");
60     // should wait timeout before post
61     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_A, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
62     CHECK_EQ_RETURN(ret, HDF_ERR_TIMEOUT, HDF_FAILURE);
63 
64     // should post success
65     ret = PlatformEventPost(pe, PLAT_TEST_EVENT_A);
66     CHECK_EQ_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
67 
68     // should wait success after post
69     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_A, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
70     CHECK_EQ_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
71     CHECK_EQ_RETURN(events, PLAT_TEST_EVENT_A, HDF_FAILURE);
72 
73     // should wait timeut if wait again
74     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_A, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
75     CHECK_EQ_RETURN(ret, HDF_ERR_TIMEOUT, HDF_FAILURE);
76 
77     // should post success for multi events
78     ret = PlatformEventPost(pe, PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B);
79     CHECK_EQ_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
80 
81     // should wait timeout if events not match
82     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_B | PLAT_TEST_EVENT_C, PLAT_EVENT_MODE_AND,
83         PLAT_EVENT_TEST_TIMEOUT, &events);
84     CHECK_EQ_RETURN(ret, HDF_ERR_TIMEOUT, HDF_FAILURE);
85     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_C, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
86     CHECK_EQ_RETURN(ret, HDF_ERR_TIMEOUT, HDF_FAILURE);
87 
88     // should wait success if events match
89     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B, PLAT_EVENT_MODE_AND,
90         PLAT_EVENT_TEST_TIMEOUT, &events);
91     CHECK_EQ_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
92     CHECK_EQ_RETURN(events, PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B, HDF_FAILURE);
93 
94     // should wait timeut if wait again
95     ret = PlatformEventWait(pe, PLAT_TEST_EVENT_A, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
96     CHECK_EQ_RETURN(ret, HDF_ERR_TIMEOUT, HDF_FAILURE);
97 
98     PLAT_LOGD("PlatformEventTestPostAndWait: exit!");
99     return HDF_SUCCESS;
100 }
101 
PlatformEventListenTestCb(struct PlatformEventListener * listener,uint32_t events)102 static int32_t PlatformEventListenTestCb(struct PlatformEventListener *listener, uint32_t events)
103 {
104     uint32_t *pEvents = (uint32_t *)listener->data;
105 
106     *pEvents = events;
107     return HDF_SUCCESS;
108 }
109 
PlatformEventTestListenAndUnliten(struct PlatformEvent * pe)110 static int32_t PlatformEventTestListenAndUnliten(struct PlatformEvent *pe)
111 {
112     int32_t ret;
113     struct PlatformEventListener listener;
114     uint32_t events = 0;
115 
116     PLAT_LOGD("PlatformEventTestListenAndUnliten: enter!");
117     listener.mask = PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B;
118     listener.cb = PlatformEventListenTestCb;
119     listener.data = (void *)&events;
120 
121     // should listen success
122     ret = PlatformEventListen(pe, &listener);
123     CHECK_EQ_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
124 
125     // no events got before post
126     OsalMSleep(PLAT_EVENT_TEST_TIMEOUT);
127     CHECK_EQ_RETURN(events, 0, HDF_FAILURE);
128 
129     PlatformEventPost(pe, PLAT_TEST_EVENT_A);
130     OsalMSleep(PLAT_EVENT_TEST_TIMEOUT);
131     // should got the events in callback
132     CHECK_EQ_RETURN(events, PLAT_TEST_EVENT_A, HDF_FAILURE);
133 
134     events = 0;
135     PlatformEventPost(pe, PLAT_TEST_EVENT_B);
136     OsalMSleep(PLAT_EVENT_TEST_TIMEOUT);
137     // should got the events in callback
138     CHECK_EQ_RETURN(events, PLAT_TEST_EVENT_B, HDF_FAILURE);
139 
140     events = 0;
141     PlatformEventPost(pe, PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B);
142     OsalMSleep(PLAT_EVENT_TEST_TIMEOUT);
143     // should got the events in callback
144     CHECK_EQ_RETURN(events, PLAT_TEST_EVENT_A | PLAT_TEST_EVENT_B, HDF_FAILURE);
145 
146     PLAT_LOGD("PlatformEventTestListenAndUnliten: exit!");
147     return HDF_SUCCESS;
148 }
149 
PlatformEventTestReliability(struct PlatformEvent * pe)150 static int32_t PlatformEventTestReliability(struct PlatformEvent *pe)
151 {
152     int32_t ret;
153     uint32_t events;
154     struct PlatformEventListener listener;
155 
156     PLAT_LOGD("PlatformEventTestReliability: enter!");
157     // should return invalid obj when init null pointer
158     ret = PlatformEventInit(NULL);
159     CHECK_EQ_RETURN(ret, HDF_ERR_INVALID_OBJECT, HDF_FAILURE);
160 
161     // should not wait success when event instance is NULL
162     ret = PlatformEventWait(NULL, 0x1, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
163     CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
164 
165     // should not wait success when events is NULL
166     ret = PlatformEventWait(pe, 0x1, 0, PLAT_EVENT_TEST_TIMEOUT, NULL);
167     CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
168 
169     // should not wait success when mask is 0
170     ret = PlatformEventWait(pe, 0, 0, PLAT_EVENT_TEST_TIMEOUT, &events);
171     CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
172 
173     // should not listen success when event instance is NULL
174     ret = PlatformEventListen(NULL, &listener);
175     CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
176 
177     // should not wait success when listener is NULL
178     ret = PlatformEventListen(pe, NULL);
179     CHECK_NE_RETURN(ret, HDF_SUCCESS, HDF_FAILURE);
180 
181     PLAT_LOGD("PlatformEventTestReliability: exit!");
182     return HDF_SUCCESS;
183 }
184 
185 struct PlatformEventTestEntry {
186     int cmd;
187     int32_t (*func)(struct PlatformEvent *pe);
188     const char *name;
189 };
190 
191 static struct PlatformEventTestEntry g_entry[] = {
192     { PLAT_EVENT_TEST_INIT_AND_UNINIT, PlatformEventTestInitAndUninit, "PlatformEventTestInitAndUninit" },
193     { PLAT_EVENT_TEST_POST_AND_WAIT, PlatformEventTestPostAndWait, "PlatformEventTestPostAndWait" },
194     { PLAT_EVENT_TEST_LISTEN_AND_UNLISTEN, PlatformEventTestListenAndUnliten, "PlatformEventTestListenAndUnliten" },
195     { PLAT_EVENT_TEST_RELIABILITY, PlatformEventTestReliability, "PlatformEventTestReliability" },
196 };
197 
PlatformEventTestExecute(int cmd)198 int PlatformEventTestExecute(int cmd)
199 {
200     uint32_t i;
201     int32_t ret = HDF_ERR_NOT_SUPPORT;
202     struct PlatformEvent pe;
203     struct PlatformEventTestEntry *entry = NULL;
204 
205     if (cmd > PLAT_EVENT_TEST_CMD_MAX) {
206         PLAT_LOGE("PlatformEventTestExecute: invalid cmd:%d", cmd);
207         ret = HDF_ERR_NOT_SUPPORT;
208         PLAT_LOGE("[PlatformEventTestExecute][======cmd:%d====ret:%d======]", cmd, ret);
209         return ret;
210     }
211 
212     for (i = 0; i < sizeof(g_entry) / sizeof(g_entry[0]); i++) {
213         if (g_entry[i].cmd != cmd || g_entry[i].func == NULL) {
214             continue;
215         }
216         entry = &g_entry[i];
217         break;
218     }
219 
220     if (entry == NULL) {
221         PLAT_LOGE("PlatformEventTestExecute: no entry matched, cmd = %d!", cmd);
222         return HDF_ERR_NOT_SUPPORT;
223     }
224 
225     if ((ret = PlatformEventInit(&pe)) != HDF_SUCCESS) {
226         PLAT_LOGE("PlatformEventTestExecute: init failed, ret = %d!", ret);
227         return ret;
228     }
229 
230     ret = entry->func(&pe);
231     PlatformEventUninit(&pe);
232 
233     PLAT_LOGE("[PlatformEventTestExecute][======cmd:%d====ret:%d======]", cmd, ret);
234     return ret;
235 }
236 
PlatformEventTestExecuteAll(void)237 void PlatformEventTestExecuteAll(void)
238 {
239     int32_t i;
240     int32_t ret;
241     int32_t fails = 0;
242 
243     for (i = 0; i < PLAT_EVENT_TEST_CMD_MAX; i++) {
244         ret = PlatformEventTestExecute(i);
245         fails += (ret != HDF_SUCCESS) ? 1 : 0;
246     }
247 
248     PLAT_LOGE("PlatformEventTestExecuteALL: **********PASS:%d  FAIL:%d************\n\n",
249         PLAT_EVENT_TEST_CMD_MAX - fails, fails);
250 }
251