1 /*
2  * Copyright (c) 2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include <thread>
17 #include <chrono>
18 #include <gtest/gtest.h>
19 #include "ffrt_inner.h"
20 #include "c/queue_ext.h"
21 #include "../common.h"
22 
23 using namespace std;
24 using namespace ffrt;
25 using namespace testing;
26 #ifdef HWTEST_TESTING_EXT_ENABLE
27 using namespace testing::ext;
28 #endif
29 
30 class QueueTest : public testing::Test {
31 protected:
SetUpTestCase()32     static void SetUpTestCase()
33     {
34     }
35 
TearDownTestCase()36     static void TearDownTestCase()
37     {
38     }
39 
SetUp()40     virtual void SetUp()
41     {
42     }
43 
TearDown()44     virtual void TearDown()
45     {
46     }
47 };
48 
49 #if defined(__clang__)
50 #define OPTIMIZE_OFF __attribute__((optnone))
51 #elif defined(__GNUC__)
52 #define OPTIMIZE_OFF __attribute__((optimize(0)))
53 #else
54 #define OPTIMIZE_OFF
55 #endif
56 
57 namespace {
OnePlusForTest(void* data)58 void OPTIMIZE_OFF OnePlusForTest(void* data)
59 {
60     *(int*)data += 1;
61 }
62 
PrintForTest(void* data)63 void PrintForTest(void* data)
64 {
65     printf("run no input func PrintForTest\n");
66 }
67 
fibonacci(int n)68 int fibonacci(int n)
69 {
70     if (n == 0 || n == 1) {
71         return n;
72     }
73     return fibonacci(n - 1) + fibonacci(n - 2);
74 }
75 
FibonacciTest(void* data, int fibnum)76 void FibonacciTest(void* data, int fibnum)
77 {
78     int testnum = fibonacci(fibnum);
79     *(int*)data += testnum;
80 }
81 } // namespace
82 
EmptyFunction()83 void EmptyFunction() {}
84 /*
85  * 测试用例名称 : serial_queue_submit_cancel_succ
86  * 测试用例描述:提交、取消串行延时任务成功
87  * 预置条件    :1、调用串行队列创建接口创建队列
88  * 操作步骤    :1、提交串行队列任务并执行
89  *              2、提交延时串行队列任务并执行
90  * 预期结果    :执行成功
91  */
HWTEST_F(QueueTest, serial_queue_submit_cancel_succ, TestSize.Level1)92 HWTEST_F(QueueTest, serial_queue_submit_cancel_succ, TestSize.Level1)
93 {
94     // 创建队列
95     ffrt_queue_attr_t queue_attr;
96     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
97     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
98 
99     int result = 0;
100     std::function<void()> basicFunc = [&result]() { OnePlusForTest(static_cast<void*>(&result)); };
101     ffrt_queue_submit(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), nullptr);
102 
103     ffrt_task_handle_t task1 =
104         ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), nullptr);
105     ffrt_queue_wait(task1);
106     ffrt_task_handle_destroy(task1); // 销毁task_handle,必须
107     EXPECT_EQ(result, 2);
108 
109     ffrt_task_attr_t task_attr;
110     (void)ffrt_task_attr_init(&task_attr); // 初始化task属性,必须
111     ffrt_task_attr_set_delay(&task_attr, 1000); // 设置任务1ms后才执行,非必须
112     ffrt_task_handle_t task2 =
113         ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
114     int cancel = ffrt_queue_cancel(task2);
115     ffrt_task_handle_destroy(task2); // 销毁task_handle,必须
116     ffrt_queue_attr_destroy(&queue_attr);
117     EXPECT_EQ(cancel, 0);
118     EXPECT_EQ(result, 2);
119 
120     // 销毁队列
121     ffrt_queue_destroy(queue_handle);
122 }
123 
124 /*
125  * 测试用例名称 : serial_queue_create_fail
126  * 测试用例描述:串行队列创建和销毁失败
127  * 预置条件    :1、调用串行队列创建接口创建队列
128  * 操作步骤    :1、调用串行队列创建接口创建队列,type为非串行队列
129  *              2、调用串行队列创建接口创建队列,type为串行队列,但name与attr为nullptr
130  *              3、调用串行队列创建接口创建队列,type为串行队列,但name为nullptr
131  * 预期结果    :1创建失败,2、3创建成功
132  */
HWTEST_F(QueueTest, serial_queue_create_fail, TestSize.Level1)133 HWTEST_F(QueueTest, serial_queue_create_fail, TestSize.Level1)
134 {
135     // input invalid
136     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_max, nullptr, nullptr);
137     ffrt_queue_destroy(queue_handle);
138     ffrt_queue_destroy(nullptr);
139 
140     queue_handle = ffrt_queue_create(ffrt_queue_serial, nullptr, nullptr);
141     EXPECT_EQ(queue_handle == nullptr, 0);
142     ffrt_queue_destroy(queue_handle);
143 
144     // succ free
145     ffrt_queue_attr_t queue_attr;
146     (void)ffrt_queue_attr_init(&queue_attr); // attr 缺少 init 无法看护
147     queue_handle = ffrt_queue_create(ffrt_queue_serial, nullptr, &queue_attr);
148     EXPECT_EQ(queue_handle == nullptr, 0);
149     ffrt_queue_attr_destroy(&queue_attr);
150     ffrt_queue_destroy(queue_handle);
151 }
152 
153 /*
154  * 测试用例名称 : ffrt_task_attr_set_get_delay
155  * 测试用例描述:测试 ffrt_task_attr_set_get_delay
156  * 操作步骤    :1、调用ffrt_task_attr_set_delay接口设置队列延时时间
157  *              2、使用ffrt_task_attr_get_delay查询时间
158  * 预期结果    :查询结果与设定相同,初始值为0
159  */
HWTEST_F(QueueTest, ffrt_task_attr_set_get_delay, TestSize.Level1)160 HWTEST_F(QueueTest, ffrt_task_attr_set_get_delay, TestSize.Level1)
161 {
162     // succ free
163     ffrt_task_attr_t task_attr;
164     (void)ffrt_task_attr_init(&task_attr); // attr 缺少 init 无法看护
165     // set_attr_delay
166     uint64_t delay = 100;
167     ffrt_task_attr_set_delay(nullptr, delay);
168     ffrt_task_attr_set_delay(&task_attr, delay);
169     // error and return 0
170     delay = ffrt_task_attr_get_delay(nullptr);
171     EXPECT_EQ(delay, 0);
172     delay = ffrt_task_attr_get_delay(&task_attr);
173     EXPECT_EQ(delay, 100);
174     ffrt_task_attr_destroy(&task_attr);
175 }
176 
177 /*
178  * 测试用例名称 : serial_queue_task_create_destroy_fail
179  * 测试用例描述:串行任务提交和销毁失败
180  * 操作步骤    :1、直接调用串行队列接口提交空任务,随后销毁任务
181  *              2、调用串行队列创建接口创建队列并提交空任务
182  *              3、调用串行队列创建接口创建队列并提交任务,随后销毁任务
183  * 预期结果    :2提交失败并返回nullptr,3提交成功
184  */
HWTEST_F(QueueTest, serial_queue_task_create_destroy_fail, TestSize.Level1)185 HWTEST_F(QueueTest, serial_queue_task_create_destroy_fail, TestSize.Level1)
186 {
187     // input invalid
188     ffrt_task_handle_t task = ffrt_queue_submit_h(nullptr, nullptr, nullptr);
189     ffrt_task_handle_destroy(task);
190 
191     ffrt_queue_attr_t queue_attr;
192     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
193     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
194     task = ffrt_queue_submit_h(queue_handle, nullptr, nullptr);
195     EXPECT_EQ(task == nullptr, 1);
196 
197     std::function<void()> basicFunc = std::bind(PrintForTest, nullptr);
198     task = ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), nullptr);
199     ffrt_queue_wait(task);
200     // succ free
201     EXPECT_EQ(task == nullptr, 0);
202     ffrt_task_handle_destroy(task);
203     ffrt_queue_attr_destroy(&queue_attr);
204 }
205 
206 /*
207  * 测试用例名称 : serial_multi_submit_succ
208  * 测试用例描述:循环提交普通任务和延时任务,执行成功
209  * 操作步骤    :1、循环提交普通任务90次
210  *              2、循环提交延时任务20次,取消10次
211  * 预期结果    :总共应执行100+取消前已执行的次数
212  */
HWTEST_F(QueueTest, serial_multi_submit_succ, TestSize.Level1)213 HWTEST_F(QueueTest, serial_multi_submit_succ, TestSize.Level1)
214 {
215     ffrt_queue_attr_t queue_attr;
216     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
217     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
218 
219     int result = 0;
220     int cancelFailedNum = 0;
221     std::function<void()>&& basicFunc = [&result]() { OnePlusForTest(static_cast<void*>(&result)); };
222     ffrt_task_attr_t task_attr;
223     (void)ffrt_task_attr_init(&task_attr); // 初始化task属性,必须
224     ffrt_task_attr_set_delay(&task_attr, 100); // 设置任务0.1ms后才执行,非必须
225 
226     for (int n = 0; n < 10; ++n) {
227         for (int i = 0; i < 9; ++i) {
228             ffrt_queue_submit(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), nullptr);
229         }
230 
231         ffrt_task_handle_t t1 =
232             ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
233         ffrt_task_handle_t t2 =
234             ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
235         cancelFailedNum += ffrt_queue_cancel(t1);
236         ffrt_task_handle_destroy(t1); // 销毁task_handle,必须
237 
238         ffrt_queue_wait(t2);
239         ffrt_task_handle_destroy(t2);
240     }
241 
242     EXPECT_EQ(result, (cancelFailedNum + 100));
243     ffrt_queue_attr_destroy(&queue_attr);
244     ffrt_queue_destroy(queue_handle);
245 }
246 
247 /*
248  * 测试用例名称 : serial_early_quit_succ
249  * 测试用例描述:主动销毁队列,未执行的任务取消
250  * 操作步骤    :1、提交10000个斐波那契任务
251                 2、至少取消1个
252  * 预期结果    :取消成功
253  */
HWTEST_F(QueueTest, serial_early_quit_succ, TestSize.Level1)254 HWTEST_F(QueueTest, serial_early_quit_succ, TestSize.Level1)
255 {
256     ffrt_queue_attr_t queue_attr;
257     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
258     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
259     int fibnum = 10;
260     int result = 0;
261     int expect = fibonacci(fibnum);
262     std::function<void()>&& basicFunc = [&result, fibnum]() {
263         FibonacciTest(static_cast<void*>(&result), fibnum);
264         usleep(10);
265     };
266     for (int i = 0; i < 10000; ++i) {
267         ffrt_queue_submit(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), nullptr);
268     }
269 
270     ffrt_queue_destroy(queue_handle);
271     printf("result = %d\n", result);
272     EXPECT_EQ(result < expect * 10000, 1);
273 }
274 
275 /*
276  * 测试用例名称 : serial_double_cancel_failed
277  * 测试用例描述:对一个任务取消两次
278  * 操作步骤    :1、调用串行队列创建接口创建队列,设置延时并提交任务
279                 2、调用两次ffrt_queue_cancel取消同一任务
280  * 预期结果    :首次取消成功,第二次取消失败
281  */
282 HWTEST_F(QueueTest, serial_double_cancel_failed, TestSize.Level1)
283 {
284     ffrt_queue_attr_t queue_attr;
285     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
286     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
287 
288     int result = 0;
289     std::function<void()>&& basicFunc = [&result]() { OnePlusForTest(static_cast<void*>(&result)); };
290     ffrt_task_attr_t task_attr;
291     (void)ffrt_task_attr_init(&task_attr); // 初始化task属性,必须
292     ffrt_task_attr_set_delay(&task_attr, 100); // 设置任务0.1ms后才执行,非必须
293 
294     ffrt_task_handle_t t1 =
295         ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
296     int cancel = ffrt_queue_cancel(t1);
297     EXPECT_EQ(cancel, 0);
298     cancel = ffrt_queue_cancel(t1);
299     EXPECT_EQ(cancel, 1);
300     ffrt_task_handle_destroy(t1); // 销毁task_handle,必须
301 
302     ffrt_queue_destroy(queue_handle);
303 }
304 
305 /*
306  * 测试用例名称 : ffrt_queue_attr_des
307  * 测试用例描述:设置串行队列qos等级,销毁队列attr
308  * 操作步骤    :1、设置队列qos等级,调用串行队列创建接口创建队列
309                 2、调用ffrt_queue_attr_destroy接口销毁队列创建的attr
310  * 预期结果    :设置与销毁成功
311  */
312 HWTEST_F(QueueTest, ffrt_queue_attr_des, TestSize.Level1)
313 {
314     ffrt_queue_attr_t queue_attr;
315     (void)ffrt_queue_attr_init(&queue_attr);
316     ffrt_queue_attr_set_qos(&queue_attr, ffrt_qos_background);
317     ffrt_qos_t qos = ffrt_queue_attr_get_qos(&queue_attr);
318     EXPECT_EQ(qos == ffrt_qos_background, 1);
319     ffrt_queue_attr_destroy(&queue_attr);
320 }
321 
322 /*
323  * 测试用例名称 : ffrt_queue_delay_timeout
324  * 测试用例描述:任务队列超时,以及延时任务
325  * 操作步骤    :1、设置队列超时时间与超时回调,调用串行队列创建接口创建队列
326                 2、设置延时并提交任务
327  * 预期结果    :超时执行回调
328  */
329 HWTEST_F(QueueTest, ffrt_queue_delay_timeout, TestSize.Level1)
330 {
331     int x = 0;
332     std::function<void()>&& basicFunc1 = [&]() {
333         x = x + 1;
334     };
335     ffrt_function_header_t* ffrt_header_t = ffrt::create_function_wrapper((basicFunc1));
336 
337     ffrt_queue_attr_t queue_attr;
338     (void)ffrt_queue_attr_init(&queue_attr);
339     ffrt_queue_attr_set_callback(&queue_attr, ffrt_header_t);
340     ffrt_queue_attr_set_timeout(&queue_attr, 2000);
341     uint64_t timeout = ffrt_queue_attr_get_timeout(&queue_attr);
342     EXPECT_EQ(timeout, 2000);
343 
344     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
345 
346     int result = 0;
347     std::function<void()>&& basicFunc = [&result]() {
348         OnePlusForTest(static_cast<void*>(&result));
349         usleep(3000);
350     };
351     ffrt_task_attr_t task_attr;
352     (void)ffrt_task_attr_init(&task_attr);
353     ffrt_task_attr_set_delay(&task_attr, 1000);
354 
355     ffrt_task_handle_t t1 =
356         ffrt_queue_submit_h(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
357 
358     ffrt_queue_wait(t1);
359     ffrt_task_handle_destroy(t1);
360     EXPECT_EQ(result, 1);
361     EXPECT_EQ(x, 1);
362     ffrt_queue_destroy(queue_handle);
363 }
364 
365 HWTEST_F(QueueTest, ffrt_queue_dfx_api_0001, TestSize.Level1)
366 {
367     // ffrt_queue_attr_set_timeout接口attr为异常值
368     ffrt_queue_attr_t queue_attr;
369     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
370     ffrt_queue_attr_set_timeout(nullptr, 10000);
371     uint64_t time = ffrt_queue_attr_get_timeout(&queue_attr);
372     EXPECT_EQ(time, 0);
373     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
374     EXPECT_TRUE(queue_handle != nullptr);
375 
376     // 销毁队列
377     ffrt_queue_attr_destroy(&queue_attr);
378     ffrt_queue_destroy(queue_handle);
379 }
380 
381 HWTEST_F(QueueTest, ffrt_queue_dfx_api_0002, TestSize.Level1)
382 {
383     // ffrt_queue_attr_get_timeout接口attr为异常值
384     ffrt_queue_attr_t queue_attr;
385     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
386     ffrt_queue_attr_set_timeout(&queue_attr, 10000);
387     uint64_t time = ffrt_queue_attr_get_timeout(nullptr);
388     EXPECT_EQ(time, 0);
389     time = ffrt_queue_attr_get_timeout(&queue_attr);
390     EXPECT_EQ(time, 10000);
391     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
392     EXPECT_TRUE(queue_handle != nullptr);
393 
394     // 销毁队列
395     ffrt_queue_attr_destroy(&queue_attr);
396     ffrt_queue_destroy(queue_handle);
397 }
398 
399 HWTEST_F(QueueTest, ffrt_queue_dfx_api_0003, TestSize.Level1)
400 {
401     // ffrt_queue_attr_set_timeoutCb接口attr为异常值
402     std::function<void()> cbOne = []() { printf("first set callback\n"); };
403 
404     ffrt_queue_attr_t queue_attr;
405     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
406     ffrt_queue_attr_set_callback(nullptr, ffrt::create_function_wrapper(cbOne, ffrt_function_kind_queue));
407     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
408     EXPECT_TRUE(queue_handle != nullptr);
409 
410     // 销毁队列
411     ffrt_queue_attr_destroy(&queue_attr);
412     ffrt_queue_destroy(queue_handle);
413 }
414 
415 HWTEST_F(QueueTest, ffrt_queue_dfx_api_0004, TestSize.Level1)
416 {
417     // ffrt_queue_attr_get_timeoutCb接口attr为异常值
418     std::function<void()> cbOne = []() { printf("first set callback\n"); };
419 
420     ffrt_queue_attr_t queue_attr;
421     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
422     ffrt_queue_attr_set_callback(&queue_attr, ffrt::create_function_wrapper(cbOne, ffrt_function_kind_queue));
423     ffrt_function_header_t* func = ffrt_queue_attr_get_callback(nullptr);
424     EXPECT_TRUE(func == nullptr);
425     func = ffrt_queue_attr_get_callback(&queue_attr);
426     EXPECT_TRUE(func != nullptr);
427     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
428     EXPECT_TRUE(queue_handle != nullptr);
429 
430     // 销毁队列
431     ffrt_queue_destroy(queue_handle);
432     ffrt_queue_attr_destroy(&queue_attr);
433 }
434 
435 /*
436  * 测试用例名称 : ffrt_task_attr_set_queue_priority
437  * 测试用例描述 : 测试 ffrt_task_attr_set_queue_priority
438  * 操作步骤     : 1、调用ffrt_task_attr_set_queue_priority接口设置队列优先级
439  *               2、使用ffrt_task_attr_get_queue_priority查询优先级
440  * 预期结果    : 查询结果与设定相同,值为3
441  */
442 HWTEST_F(QueueTest, ffrt_task_attr_set_queue_priority, TestSize.Level1)
443 {
444     ffrt_task_attr_t task_attr;
445     (void)ffrt_task_attr_init(&task_attr);
446     ffrt_queue_priority_t priority = ffrt_queue_priority_low;
447     ffrt_task_attr_set_queue_priority(nullptr, priority);
448     ffrt_task_attr_set_queue_priority(&task_attr, priority);
449     priority = ffrt_task_attr_get_queue_priority(nullptr);
450     EXPECT_EQ(priority, ffrt_queue_priority_immediate);
451     priority = ffrt_task_attr_get_queue_priority(&task_attr);
452     EXPECT_EQ(priority, ffrt_queue_priority_low);
453     ffrt_task_attr_destroy(&task_attr);
454 }
455 
456 /*
457  * 测试用例名称 : ffrt_queue_attr_set_max_concurrency
458  * 测试用例描述 : 测试 ffrt_queue_attr_set_max_concurrency
459  * 操作步骤     : 1、调用ffrt_queue_attr_set_max_concurrency设置FFRT并行队列,并行度为4
460  *               2、使用ffrt_queue_attr_get_max_concurrency查询并行度
461  * 预期结果    : 查询结果与设定相同,值为4
462  */
463 HWTEST_F(QueueTest, ffrt_queue_attr_set_max_concurrency, TestSize.Level1)
464 {
465     ffrt_queue_attr_t queue_attr;
466     (void)ffrt_queue_attr_init(&queue_attr);
467     uint64_t concurrency = 4;
468     ffrt_queue_attr_set_max_concurrency(nullptr, concurrency);
469     ffrt_queue_attr_set_max_concurrency(&queue_attr, concurrency);
470     concurrency = ffrt_queue_attr_get_max_concurrency(nullptr);
471     EXPECT_EQ(concurrency, 0);
472     concurrency = ffrt_queue_attr_get_max_concurrency(&queue_attr);
473     EXPECT_EQ(concurrency, 4);
474     ffrt_queue_attr_destroy(&queue_attr);
475 
476     ffrt_queue_attr_t queue_attr1;
477     (void)ffrt_queue_attr_init(&queue_attr1);
478     concurrency = 0;
479     ffrt_queue_attr_set_max_concurrency(&queue_attr1, concurrency);
480     concurrency = ffrt_queue_attr_get_max_concurrency(&queue_attr1);
481     EXPECT_EQ(concurrency, 1);
482     ffrt_queue_attr_destroy(&queue_attr1);
483 }
484 
485 /*
486  * 测试用例名称 : ffrt_queue_has_task
487  * 测试用例描述 : 测试 ffrt_queue_has_task
488  * 操作步骤     : 1、往队列中提交若干任务,其中包含待查询的任务
489  *               2、调用ffrt_queue_has_task查询任务是否在队列中
490  * 预期结果    : 查询结果与预期相同
491  */
492 HWTEST_F(QueueTest, ffrt_queue_has_task, TestSize.Level1)
493 {
494     ffrt_queue_attr_t queue_attr;
495     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
496     ffrt_queue_t queue_handle = ffrt_queue_create(ffrt_queue_serial, "test_queue", &queue_attr);
497 
498     std::mutex lock;
499     lock.lock();
500     std::function<void()> basicFunc = [&]() { lock.lock(); };
501     std::function<void()> emptyFunc = []() {};
502 
503     ffrt_task_attr_t task_attr;
504     ffrt_task_attr_init(&task_attr);
505     ffrt_task_attr_set_name(&task_attr, "basic_function");
506     ffrt_task_handle_t handle = ffrt_queue_submit_h(queue_handle,
507         create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
508 
509     for (int i = 0; i < 10; i++) {
510         std::string name = "empty_function_" + std::to_string(i);
511         ffrt_task_attr_set_name(&task_attr, name.c_str());
512         ffrt_queue_submit(queue_handle, create_function_wrapper(emptyFunc, ffrt_function_kind_queue), &task_attr);
513     }
514 
515     // 全字匹配
516     for (int i = 0; i < 10; i++) {
517         std::string name = "empty_function_" + std::to_string(i);
518         bool hasEmptyTask = ffrt_queue_has_task(queue_handle, name.c_str());
519         EXPECT_EQ(hasEmptyTask, true);
520     }
521 
522     // 正则匹配
523     bool hasEmptyTask = ffrt_queue_has_task(queue_handle, "empty_function_.*");
524     EXPECT_EQ(hasEmptyTask, true);
525 
526     hasEmptyTask = ffrt_queue_has_task(queue_handle, "random_function");
527     EXPECT_EQ(hasEmptyTask, false);
528 
529     lock.unlock();
530     ffrt_queue_wait(handle);
531 
532     ffrt_queue_attr_destroy(&queue_attr);
533     ffrt_queue_destroy(queue_handle);
534 }
535 
536 /*
537  * 测试用例名称 : ffrt_queue_cancel_all_and_cancel_by_name
538  * 测试用例描述 : 测试 ffrt_queue_cancel_all、ffrt_queue_cancel_by_name
539  * 操作步骤     : 1、往队列中提交若干任务
540  *               2、调用ffrt_queue_cancel_by_name取消指定任务
541  *               3、调用ffrt_queue_cancel_all取消所有任务
542  * 预期结果    : 任务取消成功
543  */
544 HWTEST_F(QueueTest, ffrt_queue_cancel_all_and_cancel_by_name, TestSize.Level1)
545 {
546     ffrt_queue_attr_t queue_attr;
547     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
548     ffrt_queue_t queue_handle = ffrt_queue_create(
549         static_cast<ffrt_queue_type_t>(ffrt_queue_eventhandler_adapter), "test_queue", &queue_attr);
550 
551     std::mutex lock;
552     lock.lock();
553     std::function<void()> basicFunc = [&]() { lock.lock(); };
554     std::function<void()> emptyFunc = []() {};
555 
556     ffrt_task_attr_t task_attr;
557     ffrt_task_attr_init(&task_attr);
558     ffrt_task_attr_set_name(&task_attr, "basic_function");
559     ffrt_task_handle_t handle = ffrt_queue_submit_h(queue_handle,
560         create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
561 
562     for (int i = 0; i < 10; i++) {
563         std::string name = "empty_function_" + std::to_string(i);
564         ffrt_task_attr_set_name(&task_attr, name.c_str());
565         ffrt_queue_submit(queue_handle, create_function_wrapper(emptyFunc, ffrt_function_kind_queue), &task_attr);
566     }
567 
568     // 测试ffrt_queue_cancel_by_name
569     bool hasEmptyTask = ffrt_queue_has_task(queue_handle, "empty_function_3");
570     EXPECT_EQ(hasEmptyTask, true);
571 
572     ffrt_queue_cancel_by_name(queue_handle, "empty_function_3");
573 
574     hasEmptyTask = ffrt_queue_has_task(queue_handle, "empty_function_3");
575     EXPECT_EQ(hasEmptyTask, false);
576 
577     // 测试ffrt_queue_cancel_all
578     hasEmptyTask = ffrt_queue_has_task(queue_handle, "empty_function_.*");
579     EXPECT_EQ(hasEmptyTask, true);
580 
581     bool isIdle = ffrt_queue_is_idle(queue_handle);
582     EXPECT_EQ(isIdle, false);
583 
584     ffrt_queue_cancel_all(queue_handle);
585 
586     hasEmptyTask = ffrt_queue_has_task(queue_handle, "empty_function_.*");
587     EXPECT_EQ(hasEmptyTask, false);
588 
589     lock.unlock();
590     ffrt_queue_cancel_and_wait(queue_handle);
591     ffrt_queue_wait(handle);
592 
593     isIdle = ffrt_queue_is_idle(queue_handle);
594     EXPECT_EQ(isIdle, true);
595 
596     ffrt_queue_attr_destroy(&queue_attr);
597     ffrt_queue_destroy(queue_handle);
598 }
599 
600 /*
601  * 测试用例名称 : ffrt_queue_deque_task_priority_with_greedy
602  * 测试用例描述 : 测试并发队列取任务逻辑
603  * 操作步骤     : 1、往队列中提交不同优先级的若干任务
604  * 预期结果    : 任务按照优先级从高往低执行,每执行5个高优先级任务,就执行一个低优先级任务
605  */
606 HWTEST_F(QueueTest, ffrt_queue_deque_task_priority_with_greedy, TestSize.Level1)
607 {
608     ffrt_queue_attr_t queue_attr;
609     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
610     ffrt_queue_t queue_handle = ffrt_queue_create(
611         static_cast<ffrt_queue_type_t>(ffrt_queue_eventhandler_adapter), "test_queue", &queue_attr);
612 
613     std::mutex lock;
614     lock.lock();
615     std::function<void()> basicFunc = [&]() { lock.lock(); };
616     std::vector<std::function<void()>> priorityFuncs(5, nullptr);
617     std::vector<int> priorityCount(5, 0);
618     for (int idx = 0; idx < 5; idx++) {
619         priorityFuncs[idx] = [idx, &priorityCount]() {
620             if (idx < 4 && priorityCount[idx + 1] == 0) {
621                 priorityCount[idx]++;
622             }
623 
624             if (idx == 4 && priorityCount[idx] == 0) {
625                 for (int prevIdx = 0; prevIdx < 3; prevIdx++) {
626                     if (priorityCount[prevIdx] != 5) {
627                         priorityCount[4] = -1;
628                         return;
629                     }
630                 }
631                 priorityCount[4] = 1;
632             }
633         };
634     }
635 
636     ffrt_task_attr_t task_attr;
637     ffrt_task_attr_init(&task_attr);
638     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_idle);
639     ffrt_queue_submit(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
640 
641     ffrt_task_handle_t handle;
642     for (int prio = 0; prio < 5; prio++) {
643         ffrt_task_attr_set_queue_priority(&task_attr, static_cast<ffrt_queue_priority_t>(prio));
644         for (int i = 0; i < 10; i++) {
645             handle = ffrt_queue_submit_h(queue_handle,
646                 create_function_wrapper(priorityFuncs[prio], ffrt_function_kind_queue), &task_attr);
647         }
648     }
649 
650     lock.unlock();
651     ffrt_queue_wait(handle);
652 
653     for (int idx = 0; idx < 3; idx++) {
654         EXPECT_EQ(priorityCount[idx], 5);
655     }
656     EXPECT_EQ(priorityCount[3], 10);
657     EXPECT_EQ(priorityCount[4], 1);
658 
659     ffrt_queue_attr_destroy(&queue_attr);
660     ffrt_queue_destroy(queue_handle);
661 }
662 
663 /*
664  * 测试用例名称 : ffrt_queue_submit_head
665  * 测试用例描述 : 测试 ffrt_queue_submit_head
666  * 操作步骤     : 1、往队列中提交若干任务
667  *               2、调用ffrt_queue_submit_head提交任务至队头
668  * 预期结果    : 提交到对头的任务优先被执行
669  */
670 HWTEST_F(QueueTest, ffrt_queue_submit_head, TestSize.Level1)
671 {
672     ffrt_queue_attr_t queue_attr;
673     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
674     ffrt_queue_t queue_handle = ffrt_queue_create(
675         static_cast<ffrt_queue_type_t>(ffrt_queue_eventhandler_adapter), "test_queue", &queue_attr);
676 
677     int result = 0;
678     std::mutex lock;
679     lock.lock();
680     std::function<void()> basicFunc = [&]() { lock.lock(); };
681     std::vector<std::function<void()>> assignFuncs(8, nullptr);
682     std::vector<int> results;
683     std::vector<int> expectResults {6, 2, 1, 4, 3, 5, 8, 7};
684     for (int idx = 0; idx < 8; idx++) {
685         assignFuncs[idx] = [idx, &results]() {
686             results.push_back(idx + 1);
687         };
688     }
689 
690     ffrt_task_attr_t task_attr;
691     ffrt_task_attr_init(&task_attr);
692     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_immediate);
693     ffrt_task_attr_set_name(&task_attr, "basic_function");
694     ffrt_queue_submit_head(queue_handle, create_function_wrapper(basicFunc, ffrt_function_kind_queue), &task_attr);
695 
696     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[0], ffrt_function_kind_queue), &task_attr);
697     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[1], ffrt_function_kind_queue), &task_attr);
698 
699     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_high);
700     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[2], ffrt_function_kind_queue), &task_attr);
701     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[3], ffrt_function_kind_queue), &task_attr);
702 
703     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_low);
704     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[4], ffrt_function_kind_queue), &task_attr);
705 
706     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_immediate);
707     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[5], ffrt_function_kind_queue), &task_attr);
708 
709     ffrt_task_attr_set_queue_priority(&task_attr, ffrt_queue_priority_idle);
710     ffrt_task_handle_t handle = ffrt_queue_submit_head_h(queue_handle,
711         create_function_wrapper(assignFuncs[6], ffrt_function_kind_queue), &task_attr);
712     ffrt_queue_submit_head(queue_handle, create_function_wrapper(assignFuncs[7], ffrt_function_kind_queue), &task_attr);
713 
714     lock.unlock();
715     ffrt_queue_wait(handle);
716     EXPECT_EQ(results, expectResults);
717 
718     ffrt_queue_attr_destroy(&queue_attr);
719     ffrt_queue_destroy(queue_handle);
720 }
721 
722 HWTEST_F(QueueTest, ffrt_eventhandler_interactive_queue, TestSize.Level1)
723 {
724     ffrt_queue_attr_t queue_attr;
725     (void)ffrt_queue_attr_init(&queue_attr); // 初始化属性,必须
726     ffrt_queue_t queue_handle = ffrt_queue_create(
727         static_cast<ffrt_queue_type_t>(ffrt_queue_eventhandler_interactive), "test_queue", &queue_attr);
728     EXPECT_TRUE(queue_handle != nullptr);
729 
730     ffrt_queue_attr_destroy(&queue_attr);
731     ffrt_queue_destroy(queue_handle);
732 }
733 
734 HWTEST_F(QueueTest, ffrt_get_main_queue, TestSize.Level1)
735 {
736  // ffrt test case begin
737     ffrt::queue *serialQueue = new ffrt::queue("ffrt_normal_queue", {});
738     ffrt_queue_t mainQueue = ffrt_get_main_queue();
739     ffrt_task_attr_t attr;
740     ffrt_task_attr_init(&attr);
741     ffrt_task_attr_set_qos(&attr, ffrt_qos_user_initiated);
742     int result = 0;
743     std::function<void()>&& basicFunc = [&result]() {
744         OnePlusForTest(static_cast<void*>(&result));
745         OnePlusForTest(static_cast<void*>(&result));
746         EXPECT_EQ(result, 2);
747         usleep(3000);
748     };
749 
750     ffrt::task_handle handle = serialQueue->submit_h(
751         [&] {
752             result = result + 1;
753             ffrt_queue_submit(mainQueue, ffrt::create_function_wrapper(basicFunc, ffrt_function_kind_queue),
754                               &attr);
755         },
756         ffrt::task_attr().qos(3).name("ffrt main_queue."));
757 
758     serialQueue->wait(handle);
759     EXPECT_EQ(result, 1);
760 }
761 
762 HWTEST_F(QueueTest, ffrt_get_current_queue, TestSize.Level1)
763 {
764  // ffrt test case begin
765     ffrt::queue *serialQueue = new ffrt::queue("ffrt_normal_queue", {});
766     ffrt_queue_t currentQueue = ffrt_get_current_queue();
767     ffrt_task_attr_t attr;
768     ffrt_task_attr_init(&attr);
769     ffrt_task_attr_set_qos(&attr, ffrt_qos_user_initiated);
770     int result = 0;
771     std::function<void()>&& basicFunc = [&result]() {
772         OnePlusForTest(static_cast<void*>(&result));
773         OnePlusForTest(static_cast<void*>(&result));
774         EXPECT_EQ(result, 3);
775         usleep(3000);
776     };
777 
778     ffrt::task_handle handle = serialQueue->submit_h(
779         [&] {
780             result = result + 1;
781             ffrt_queue_submit(currentQueue, ffrt::create_function_wrapper(basicFunc, ffrt_function_kind_queue),
782                               &attr);
783         },
784         ffrt::task_attr().qos(3).name("ffrt current_queue."));
785 
786     serialQueue->wait(handle);
787 
788     EXPECT_EQ(result, 1);
789 }