• Home
Name Date Size #Lines LOC

..--

.application_configD12-May-2024685 1614

BUILD.gnD12-May-2024872 2622

README_zh.mdD12-May-20245.3 KiB255197

os_mutex_example.cD12-May-20244.2 KiB152120

README_zh.md

1# NiobeU4开发板OpenHarmony内核编程开发——mutex
2本示例将演示如何在Niobe u4开发板上使用liteos-m 接口进行互斥锁开发
3
4## mutex API分析
5
6### LOS_MuxCreate()
7
8```c
9UINT32 LOS_MuxCreate(UINT32 *muxHandle);
10```
11**描述:**
12
13创建互斥锁
14
15
16**参数:**
17
18|名字|描述|
19|:--|:------|
20| muxHandle | 互斥锁id |
21
22### LOS_MuxPend()
23
24```c
25UINT32 LOS_MuxPend(UINT32 muxHandle, UINT32 timeout);
26```
27**描述:**
28
29获取互斥锁
30
31
32**参数:**
33
34|名字|描述|
35|:--|:------|
36| muxHandle | 互斥锁id,由LOS_MuxCreate创建得到 |
37| timeout | delay时间 |
38
39
40### LOS_MuxPost()
41
42```c
43UINT32 LOS_MuxPost(UINT32 muxHandle);
44```
45**描述:**
46
47释放互斥锁
48
49
50**参数:**
51
52|名字|描述|
53|:--|:------|
54| muxHandle | 互斥锁id,由LOS_MuxCreate创建得到 |
55
56### LOS_MuxDelete()
57
58```c
59UINT32 LOS_MuxDelete(UINT32 muxHandle);
60```
61**描述:**
62
63删除互斥锁
64
65
66**参数:**
67
68|名字|描述|
69|:--|:------|
70| muxHandle | 互斥锁id,由LOS_MuxCreate创建得到 |
71
72
73## 软件设计
74
75### 主要代码分析
76
77创建四个线程,同时访问全局变量g_str,通过互斥锁控制实现 g_str中的值按照 "firstThread" -->  "firstThread+twoThread"  -->  "firstThread+twoThread+threeThread" --> 清空   上述步骤。
78
79```c
80UINT32 mutex1_id;
81UINT32 mutex2_id;
82
83EVENT_CB_S g_event_clean;
84#define EVENT_MASK_CLEAN 0x00000001
85
86static char g_str[256];
87
88void firstThread(void)
89{
90	//osDelay(100U);
91	while(1)
92	{
93		LOS_MuxPend(mutex1_id, osWaitForever);
94		sprintf(g_str,"firstThread");
95    	printf("firstThread is Acquire. g_str=%s\r\n",g_str);
96		LOS_MuxPost(mutex1_id);
97		LOS_TaskDelay(1000U);
98	}
99}
100
101void twoThread(void)
102{
103	//osDelay(100U);
104	while(1)
105	{
106		LOS_MuxPend(mutex2_id, osWaitForever);
107		char tmp[256]={0};
108		sprintf(tmp,"%s+twoThread",g_str);
109		memcpy(g_str,tmp,sizeof(tmp));
110		printf("twoThread is Acquire. g_str=%s\r\n",g_str);
111		LOS_MuxPost(mutex2_id);
112    	LOS_TaskDelay(1000U);
113	}
114}
115
116void threeThread(void)
117{
118    while(1)
119	{
120		LOS_MuxPend(mutex1_id, osWaitForever);
121		LOS_MuxPend(mutex2_id, osWaitForever);
122		char tmp[256]={0};
123		sprintf(tmp,"%s+threeThread",g_str);
124		memcpy(g_str,tmp,sizeof(tmp));
125    	printf("threeThread is Acquire. g_str=%s\r\n",g_str);
126		UINT32 flags = LOS_EventWrite(&g_event_clean, EVENT_MASK_CLEAN);
127		printf("write event %x\n",flags);
128		LOS_TaskDelay(100U);
129		LOS_MuxPost(mutex1_id);
130		LOS_MuxPost(mutex2_id);
131		LOS_TaskDelay(1000U);
132	}
133}
134
135void fourThread(void)
136{
137    while(1)
138	{
139		LOS_EventRead(&g_event_clean,EVENT_MASK_CLEAN,LOS_WAITMODE_OR,osWaitForever);
140		memset(g_str,0,sizeof(g_str));
141    	printf("threeThread:   clean g_str.\r\n");
142	}
143}
144
145void os_mutex_example(void)
146{
147	memset(g_str,0,sizeof(g_str));
148    TSK_INIT_PARAM_S attr={0};
149    attr.uwStackSize = 1024 * 4;
150    attr.usTaskPrio = 5;
151
152	//创建互斥锁
153	mutex1_id = LOS_MuxCreate(NULL);
154    if (mutex1_id == NULL)
155    {
156      	printf("create Mutex1 failed!\n");
157		  return ;
158    }
159	mutex2_id = osMutexNew(NULL);
160    if (mutex2_id == NULL)
161    {
162      	printf("create Mutex2 failed!\n");
163		LOS_MuxDelete(mutex1_id);
164		return ;
165    }
166
167	//创建事件标志位
168    if(LOS_EventInit(&g_event_clean) != LOS_OK)
169    {
170        printf("Failed to create EventFlags!\n");
171		LOS_MuxDelete(mutex1_id);
172		LOS_MuxDelete(mutex2_id);
173        return ;
174    }
175
176	//锁任务调度
177	LOS_TaskLock();
178    attr.pcName = "firstThread";
179	attr.pfnTaskEntry = (TSK_ENTRY_FUNC)firstThread;
180	UINT32 taskIDFirst;
181    if (osThreadNew(&taskIDFirst, &attr) != LOS_OK)
182	{
183    	printf("create firstThread failed!\n");
184		LOS_MuxDelete(mutex1_id);
185		LOS_MuxDelete(mutex2_id);
186		LOS_EventDestroy(g_event_clean);
187		return ;
188    }
189
190	attr.pcName = "twoThread";
191	attr.pfnTaskEntry = (TSK_ENTRY_FUNC)twoThread;
192	UINT32 taskIDTwo;
193    if (osThreadNew(&taskIDTwo, &attr) != LOS_OK)
194    {
195      	printf("create twoThread failed!\n");
196    }
197
198    attr.pcName = "threeThread";
199	attr.pfnTaskEntry = (TSK_ENTRY_FUNC)threeThread;
200	UINT32 taskIDThree;
201    if (osThreadNew(&taskIDThree, &attr) != LOS_OK)
202    {
203      	printf("create threeThread failed!\n");
204    }
205
206    attr.pcName = "fourThread";
207	attr.pfnTaskEntry = (TSK_ENTRY_FUNC)fourThread;
208	UINT32 taskIDFour;
209    if (osThreadNew(&taskIDFour, &attr) != LOS_OK)
210    {
211      	printf("create fourThread failed!\n");
212    }
213
214	//解锁任务调度
215	LOS_TaskUnlock();
216
217	//osThreadYield()
218}
219
220```
221
222## 编译调试
223
224- 进入//kernel/liteos_m目录, 在menuconfig配置中进入如下选项:
225     `(Top) → Platform → Board Selection → select board niobeu4 → use openvalley niobeu4 application → niobeu4 application choose`
226- 选择 `005_system_los_mutex`
227- 回到sdk根目录,执行`hb build`脚本进行编译。
228
229
230### 运行结果<a name="section_os_mutex_example"></a>
231
232示例代码编译烧录代码后,按下开发板的RESET按键,通过串口助手查看日志
233```c
234firstThread is Acquire. g_str = firstThread
235twoThread is Acquire. g_str = firstThread+twoThread
236threeThread is Acquire. g_str = firstThread+twoThread+threeThread
237write event 1
238threeThread:   clean g_str.
239
240firstThread is Acquire. g_str = firstThread
241twoThread is Acquire. g_str = firstThread+twoThread
242threeThread is Acquire. g_str = firstThread+twoThread+threeThread
243write event 1
244threeThread:   clean g_str.
245
246firstThread is Acquire. g_str = firstThread
247twoThread is Acquire. g_str = firstThread+twoThread
248threeThread is Acquire. g_str = firstThread+twoThread+threeThread
249write event 1
250threeThread:   clean g_str.
251```
252
253
254
255