1 /*
2 * Copyright (C) 2021-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 "das_task_main.h"
17 #include "alg_loader.h"
18 #include "base_sub_task.h"
19 #include "das_lite_token_manager.h"
20 #include "das_standard_token_manager.h"
21 #include "das_task_common.h"
22 #include "hc_log.h"
23 #include "iso_task_main.h"
24 #include "pake_v2_task_main.h"
25 #include "pake_protocol_dl_common.h"
26 #include "pake_protocol_ec_common.h"
27 #include "pake_v1_task_main.h"
28 #include "protocol_common.h"
29
30 typedef struct DasProtocolEntityT {
31 ProtocolType type;
32 uint32_t algInProtocol;
33 const TokenManager *tokenManagerInstance;
34 SubTaskBase *(*createSubTask)(const CJson *);
35 } DasProtocolEntity;
36
37 IMPLEMENT_HC_VECTOR(SubTaskVec, void *, 1)
38 DECLARE_HC_VECTOR(DasProtocolEntityVec, void *);
39 IMPLEMENT_HC_VECTOR(DasProtocolEntityVec, void *, 1)
40
41 DasProtocolEntityVec g_protocolEntityVec;
42 ProtocolType g_taskTypeToProtocolType[] = {
43 ISO, // TASK_TYPE_ISO_PROTOCOL = 0,
44 PAKE_V1, // TASK_TYPE_PAKE_V1_PROTOCOL = 1,
45 PAKE_V2 // TASK_TYPE_PAKE_V2_PROTOCOL = 2,
46 };
47
GetMinVersion(VersionStruct * version)48 static void GetMinVersion(VersionStruct *version)
49 {
50 version->first = 1;
51 version->second = 0;
52 version->third = 0;
53 }
54
GetMaxVersion(VersionStruct * version)55 static void GetMaxVersion(VersionStruct *version)
56 {
57 version->first = MAJOR_VERSION_NO;
58 version->second = 0;
59 version->third = 0;
60
61 uint32_t index;
62 void **ptr = NULL;
63 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
64 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
65 version->third = (version->third) | temp->algInProtocol;
66 }
67 }
68
InitVersionInfo(VersionInfo * versionInfo)69 static void InitVersionInfo(VersionInfo *versionInfo)
70 {
71 GetMinVersion(&(versionInfo->minVersion));
72 GetMaxVersion(&(versionInfo->curVersion));
73 versionInfo->versionStatus = INITIAL;
74 }
75
AddVersionToOut(const VersionInfo * versionInfo,CJson * out)76 static int AddVersionToOut(const VersionInfo *versionInfo, CJson *out)
77 {
78 CJson *payload = GetObjFromJson(out, FIELD_PAYLOAD);
79 if (payload == NULL) {
80 LOGD("Not find payload.");
81 return HC_SUCCESS;
82 }
83 return AddVersionToJson(payload, &(versionInfo->minVersion), &(versionInfo->curVersion));
84 }
85
CombineJson(CJson * desObj,const CJson * srcObj)86 static int CombineJson(CJson *desObj, const CJson *srcObj)
87 {
88 CHECK_PTR_RETURN_ERROR_CODE(desObj, "desObj");
89 CHECK_PTR_RETURN_ERROR_CODE(srcObj, "srcObj");
90 int res;
91 int len = GetItemNum(srcObj);
92 for (int i = 0; i < len; i++) {
93 CJson *item = GetItemFromArray(srcObj, i);
94 const char *key = GetItemKey(item);
95 if (key == NULL) {
96 LOGE("key is null.");
97 return HC_ERR_NULL_PTR;
98 }
99 CJson *payload = GetObjFromJson(desObj, FIELD_PAYLOAD);
100 if (strcmp(key, FIELD_PAYLOAD) == 0 && payload != NULL) {
101 res = CombineJson(payload, item);
102 if (res != HC_SUCCESS) {
103 LOGE("Combine payload failed, res: %x.", res);
104 return res;
105 }
106 } else {
107 if (AddObjToJson(desObj, key, item) != HC_SUCCESS) {
108 LOGE("AddObjToJson failed.");
109 return HC_ERR_JSON_ADD;
110 }
111 }
112 }
113 return HC_SUCCESS;
114 }
115
DestroyTaskT(Task * task)116 static void DestroyTaskT(Task *task)
117 {
118 if (task == NULL) {
119 return;
120 }
121 uint32_t index;
122 void **ptr = NULL;
123 FOR_EACH_HC_VECTOR(task->vec, index, ptr) {
124 ((SubTaskBase *)(*ptr))->destroyTask((SubTaskBase *)(*ptr));
125 }
126 DESTROY_HC_VECTOR(SubTaskVec, &(task->vec));
127 HcFree(task);
128 }
129
ProcessMultiTask(Task * task,const CJson * in,CJson * out,int32_t * status)130 static int ProcessMultiTask(Task *task, const CJson *in, CJson *out, int32_t *status)
131 {
132 int res = HC_SUCCESS;
133 uint32_t index;
134 void **ptr = NULL;
135 CJson *tmpOut = NULL;
136 CJson *combinedSendToPeer = CreateJson();
137 if (combinedSendToPeer == NULL) {
138 LOGE("Create combinedSendToPeer failed.");
139 return HC_ERR_JSON_CREATE;
140 }
141 FOR_EACH_HC_VECTOR(task->vec, index, ptr) {
142 tmpOut = CreateJson();
143 if (tmpOut == NULL) {
144 LOGE("Create tmpOut failed.");
145 res = HC_ERR_JSON_CREATE;
146 goto ERR;
147 }
148 res = ((SubTaskBase *)(*ptr))->process((*ptr), in, tmpOut, status);
149 if (res != HC_SUCCESS) {
150 LOGE("Process subTask failed, index: %u, res: %x.", index, res);
151 goto ERR;
152 }
153
154 CJson *tmpSendToPeer = GetObjFromJson(tmpOut, FIELD_SEND_TO_PEER);
155 res = CombineJson(combinedSendToPeer, tmpSendToPeer);
156 if (res != HC_SUCCESS) {
157 LOGE("CombineJson failed, res: %x.", res);
158 goto ERR;
159 }
160 FreeJson(tmpOut);
161 tmpOut = NULL;
162 }
163 if (AddObjToJson(out, FIELD_SEND_TO_PEER, combinedSendToPeer) != HC_SUCCESS) {
164 LOGE("Add combinedSendToPeer to json object failed.");
165 res = HC_ERR_JSON_ADD;
166 goto ERR;
167 }
168 ERR:
169 FreeJson(combinedSendToPeer);
170 FreeJson(tmpOut);
171 return res;
172 }
173
NegotiateAndProcessTask(Task * task,const CJson * in,CJson * out,int32_t * status)174 static int NegotiateAndProcessTask(Task *task, const CJson *in, CJson *out, int32_t *status)
175 {
176 VersionStruct curVersionPeer = { 0, 0, 0 };
177 VersionStruct minVersionPeer = { 0, 0, 0 };
178 int res = GetVersionFromJson(in, &minVersionPeer, &curVersionPeer);
179 if (res != HC_SUCCESS) {
180 LOGE("Get peer version info failed, res: %x.", res);
181 return res;
182 }
183 res = NegotiateVersion(&minVersionPeer, &curVersionPeer, &(task->versionInfo.curVersion));
184 if (res != HC_SUCCESS) {
185 LOGE("NegotiateVersion failed, res: %x.", res);
186 return res;
187 }
188 if (!IsVersionEqual(&(task->versionInfo.curVersion), &curVersionPeer)) {
189 LOGE("Negotiated version is not matched with peer.");
190 return HC_ERR_UNSUPPORTED_VERSION;
191 }
192 ProtocolType protocolType = GetPrototolType(&(task->versionInfo.curVersion), task->versionInfo.opCode);
193 LOGI("Client select protocolType: %d", protocolType);
194
195 SubTaskBase *subTask = NULL;
196 uint32_t index = 0;
197 void **ptr = task->vec.getp(&(task->vec), 0);
198 while (index < task->vec.size(&(task->vec)) && ptr != NULL) {
199 SubTaskBase *temp = (SubTaskBase *)(*ptr);
200 if (g_taskTypeToProtocolType[temp->getTaskType(temp)] == protocolType) {
201 subTask = temp;
202 index++;
203 } else {
204 temp->destroyTask(temp);
205 task->vec.eraseElement(&(task->vec), ptr, index);
206 }
207 ptr = task->vec.getp(&(task->vec), index);
208 }
209 if (subTask == NULL) {
210 LOGE("Can't find matched subTask.");
211 return HC_ERR_NOT_SUPPORT;
212 }
213 subTask->curVersion = task->versionInfo.curVersion;
214 res = subTask->process(subTask, in, out, status);
215 if (res != HC_SUCCESS) {
216 LOGE("Process subTask failed, res: %x.", res);
217 }
218 return res;
219 }
220
IsPeerErrMessage(const CJson * in,int32_t * res)221 static bool IsPeerErrMessage(const CJson *in, int32_t *res)
222 {
223 int32_t message = 0;
224 if (GetIntFromJson(in, FIELD_MESSAGE, &message) != HC_SUCCESS) {
225 LOGD("There is no message code.");
226 return false;
227 }
228 if (message != ERR_MESSAGE) {
229 return false;
230 }
231
232 if (GetIntFromJson(in, FIELD_ERROR_CODE, res) != HC_SUCCESS) {
233 LOGE("Get peer error code failed.");
234 }
235 return true;
236 }
237
ProcessTaskT(Task * task,const CJson * in,CJson * out,int32_t * status)238 static int ProcessTaskT(Task *task, const CJson *in, CJson *out, int32_t *status)
239 {
240 int32_t res;
241 if (IsPeerErrMessage(in, &res)) {
242 LOGE("Receive error message from peer, errCode: %x.", res);
243 DasSendErrMsgToSelf(out, HC_ERR_PEER_ERROR);
244 return HC_ERR_PEER_ERROR;
245 }
246 if (task->vec.size(&(task->vec)) == 0) {
247 LOGE("Task hasn't subTask.");
248 res = HC_ERR_TASK_IS_NULL;
249 goto ERR;
250 }
251
252 if (task->versionInfo.versionStatus == INITIAL) {
253 res = ProcessMultiTask(task, in, out, status);
254 if (res != HC_SUCCESS) {
255 LOGE("ProcessMultiTask failed, res: %x.", res);
256 goto ERR;
257 }
258 task->versionInfo.versionStatus = VERSION_CONFIRM;
259 } else if (task->versionInfo.versionStatus == VERSION_CONFIRM) {
260 res = NegotiateAndProcessTask(task, in, out, status);
261 if (res != HC_SUCCESS) {
262 LOGE("NegotiateAndProcessTask failed, res: %x.", res);
263 goto ERR;
264 }
265 task->versionInfo.versionStatus = VERSION_DECIDED;
266 } else {
267 SubTaskBase *subTask = HC_VECTOR_GET(&(task->vec), 0);
268 res = subTask->process(subTask, in, out, status);
269 if (res != HC_SUCCESS) {
270 LOGE("Process subTask failed, res: %x.", res);
271 goto ERR;
272 }
273 }
274
275 res = AddVersionToOut(&(task->versionInfo), out);
276 if (res != HC_SUCCESS) {
277 LOGE("AddVersionToOut failed, res: %x.", res);
278 goto ERR;
279 }
280 return res;
281 ERR:
282 if (task->versionInfo.versionStatus == INITIAL) {
283 DasSendErrMsgToSelf(out, res);
284 } else {
285 DasSendErrorToOut(out, res);
286 }
287 return res;
288 }
289
290 #ifdef ENABLE_P2P_BIND_LITE_PROTOCOL_CHECK
ShouldSkipIso(Task * task,const CJson * in)291 static bool ShouldSkipIso(Task *task, const CJson *in)
292 {
293 if (task->versionInfo.opCode != OP_BIND) {
294 return false;
295 }
296 int32_t protocolExpandVal = INVALID_PROTOCOL_EXPAND_VALUE;
297 (void)GetIntFromJson(in, FIELD_PROTOCOL_EXPAND, &protocolExpandVal);
298 return protocolExpandVal != LITE_PROTOCOL_STANDARD_MODE && protocolExpandVal != LITE_PROTOCOL_COMPATIBILITY_MODE;
299 }
300 #endif
301
CreateMultiSubTask(Task * task,const CJson * in)302 static int CreateMultiSubTask(Task *task, const CJson *in)
303 {
304 InitVersionInfo(&(task->versionInfo));
305 uint32_t index;
306 void **ptr = NULL;
307 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
308 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
309 #ifdef ENABLE_P2P_BIND_LITE_PROTOCOL_CHECK
310 if (temp->type == ISO && ShouldSkipIso(task, in)) {
311 LOGI("Skip iso protocol!");
312 continue;
313 }
314 #endif
315 SubTaskBase *subTask = temp->createSubTask(in);
316 if (subTask == NULL) {
317 LOGE("Create subTask failed, protocolType: %d.", temp->type);
318 return HC_ERR_ALLOC_MEMORY;
319 }
320 subTask->curVersion = task->versionInfo.curVersion;
321 task->vec.pushBackT(&(task->vec), (void *)subTask);
322 }
323 return HC_SUCCESS;
324 }
325
CreateSingleSubTask(Task * task,const CJson * in)326 static int CreateSingleSubTask(Task *task, const CJson *in)
327 {
328 VersionStruct curVersionPeer = { 0, 0, 0 };
329 VersionStruct minVersionPeer = { 0, 0, 0 };
330 int res = GetVersionFromJson(in, &minVersionPeer, &curVersionPeer);
331 if (res != HC_SUCCESS) {
332 LOGE("Get peer version info failed, res: %x.", res);
333 return res;
334 }
335 InitVersionInfo(&(task->versionInfo));
336 res = NegotiateVersion(&minVersionPeer, &curVersionPeer, &(task->versionInfo.curVersion));
337 if (res != HC_SUCCESS) {
338 LOGE("NegotiateVersion failed, res: %x.", res);
339 return res;
340 }
341 task->versionInfo.versionStatus = VERSION_DECIDED;
342
343 ProtocolType protocolType = GetPrototolType(&(task->versionInfo.curVersion), task->versionInfo.opCode);
344 LOGI("Server select protocolType: %d", protocolType);
345
346 uint32_t index;
347 void **ptr = NULL;
348 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
349 if (((DasProtocolEntity *)(*ptr))->type == protocolType) {
350 #ifdef ENABLE_P2P_BIND_LITE_PROTOCOL_CHECK
351 if (protocolType == ISO && ShouldSkipIso(task, in)) {
352 LOGE("Skip iso protocol!");
353 return HC_ERR_NOT_SUPPORT;
354 }
355 #endif
356 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
357 SubTaskBase *subTask = temp->createSubTask(in);
358 if (subTask == NULL) {
359 LOGE("Create subTask failed.");
360 return HC_ERR_ALLOC_MEMORY;
361 }
362 subTask->curVersion = task->versionInfo.curVersion;
363 task->vec.pushBackT(&(task->vec), (void *)subTask);
364 return HC_SUCCESS;
365 }
366 }
367
368 LOGE("Can't find protocolType.");
369 return HC_ERR_NOT_SUPPORT;
370 }
371
CreateTaskT(int32_t * taskId,const CJson * in,CJson * out)372 Task *CreateTaskT(int32_t *taskId, const CJson *in, CJson *out)
373 {
374 int res;
375 Task *task = NULL;
376 bool isClient = true;
377 if (GetBoolFromJson(in, FIELD_IS_CLIENT, &isClient) != HC_SUCCESS) {
378 LOGE("Get isClient failed.");
379 res = HC_ERR_JSON_GET;
380 goto ERR;
381 }
382 task = (Task *)HcMalloc(sizeof(Task), 0);
383 if (task == NULL) {
384 LOGE("Malloc for das task failed.");
385 res = HC_ERR_ALLOC_MEMORY;
386 goto ERR;
387 }
388 task->vec = CREATE_HC_VECTOR(SubTaskVec);
389 task->destroyTask = DestroyTaskT;
390 task->processTask = ProcessTaskT;
391
392 Uint8Buff taskIdBuf = { (uint8_t *)taskId, sizeof(int) };
393 res = GetLoaderInstance()->generateRandom(&taskIdBuf);
394 if (res != 0) {
395 LOGE("Generate taskId failed.");
396 goto ERR;
397 }
398 task->taskId = *taskId;
399 if (GetIntFromJson(in, FIELD_OPERATION_CODE, &(task->versionInfo.opCode)) != HC_SUCCESS) {
400 LOGE("Get opcode failed.");
401 res = HC_ERR_JSON_GET;
402 goto ERR;
403 }
404 if (isClient) {
405 res = CreateMultiSubTask(task, in);
406 } else {
407 res = CreateSingleSubTask(task, in);
408 }
409 if (res != HC_SUCCESS) {
410 LOGE("Create sub task failed, res: %x.", res);
411 goto ERR;
412 }
413 return task;
414 ERR:
415 if (isClient) {
416 DasSendErrMsgToSelf(out, res);
417 } else {
418 DasSendErrorToOut(out, res);
419 }
420 DestroyTaskT(task);
421 return NULL;
422 }
423
RegisterLocalIdentityInTask(const TokenManagerParams * params)424 int32_t RegisterLocalIdentityInTask(const TokenManagerParams *params)
425 {
426 int32_t res = HC_SUCCESS;
427 uint32_t index;
428 void **ptr = NULL;
429 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
430 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
431 if ((temp->tokenManagerInstance == NULL) || (temp->tokenManagerInstance->registerLocalIdentity == NULL)) {
432 LOGD("Protocol type: %d, unsupported method!", temp->type);
433 continue;
434 }
435 res = temp->tokenManagerInstance->registerLocalIdentity(params);
436 if (res != HC_SUCCESS) {
437 LOGE("Protocol type: %d, registerLocalIdentity failed, res: %d!", temp->type, res);
438 return HC_ERR_GENERATE_KEY_FAILED;
439 }
440 }
441 return res;
442 }
443
UnregisterLocalIdentityInTask(const TokenManagerParams * params)444 int32_t UnregisterLocalIdentityInTask(const TokenManagerParams *params)
445 {
446 int32_t res = HC_SUCCESS;
447 uint32_t index;
448 void **ptr = NULL;
449 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
450 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
451 if ((temp->tokenManagerInstance == NULL) || (temp->tokenManagerInstance->unregisterLocalIdentity == NULL)) {
452 LOGD("Protocol type: %d, unsupported method!", temp->type);
453 continue;
454 }
455 res = temp->tokenManagerInstance->unregisterLocalIdentity(params);
456 if (res != HC_SUCCESS) {
457 LOGE("Protocol type: %d, unregisterLocalIdentity failed, res: %d!", temp->type, res);
458 return res;
459 }
460 }
461 return res;
462 }
463
DeletePeerAuthInfoInTask(const TokenManagerParams * params)464 int32_t DeletePeerAuthInfoInTask(const TokenManagerParams *params)
465 {
466 int32_t res = HC_SUCCESS;
467 uint32_t index;
468 void **ptr = NULL;
469 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
470 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
471 if ((temp->tokenManagerInstance == NULL) || (temp->tokenManagerInstance->deletePeerAuthInfo == NULL)) {
472 LOGD("Protocol type: %d, unsupported method!", temp->type);
473 continue;
474 }
475 res = temp->tokenManagerInstance->deletePeerAuthInfo(params);
476 if (res != HC_SUCCESS) {
477 LOGE("Protocol type: %d, deletePeerAuthInfo failed, res: %d!", temp->type, res);
478 return res;
479 }
480 }
481 return res;
482 }
483
GetPublicKeyInTask(const TokenManagerParams * params,Uint8Buff * returnPk)484 int32_t GetPublicKeyInTask(const TokenManagerParams *params, Uint8Buff *returnPk)
485 {
486 uint32_t index;
487 void **ptr = NULL;
488 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
489 DasProtocolEntity *temp = (DasProtocolEntity *)(*ptr);
490 if ((temp->tokenManagerInstance == NULL) || (temp->tokenManagerInstance->getPublicKey == NULL)) {
491 LOGD("Protocol type: %d, unsupported method!", temp->type);
492 continue;
493 }
494 return temp->tokenManagerInstance->getPublicKey(params, returnPk);
495 }
496 LOGE("Failed to find valid protocol!");
497 return HC_ERR_NOT_SUPPORT;
498 }
499
GetPakeAlgInProtocol(int offset)500 static uint32_t GetPakeAlgInProtocol(int offset)
501 {
502 uint32_t algInProtocol = PSK_SPEKE;
503 #ifdef P2P_PAKE_DL_TYPE
504 algInProtocol |= (GetPakeDlAlg() << offset);
505 #endif
506 #ifdef P2P_PAKE_EC_TYPE
507 algInProtocol |= (GetPakeEcAlg() << offset);
508 #endif
509 (void)offset;
510 return algInProtocol;
511 }
512
InitDasProtocolEntities(void)513 int32_t InitDasProtocolEntities(void)
514 {
515 g_protocolEntityVec = CREATE_HC_VECTOR(DasProtocolEntityVec);
516 DasProtocolEntity *protocol = NULL;
517 if (IsIsoSupported()) {
518 protocol = (DasProtocolEntity *)HcMalloc(sizeof(DasProtocolEntity), 0);
519 if (protocol == NULL) {
520 LOGE("Malloc for Iso dasProtocolEntity failed.");
521 return HC_ERR_ALLOC_MEMORY;
522 }
523 protocol->type = ISO;
524 protocol->algInProtocol = ISO_ALG;
525 protocol->createSubTask = CreateIsoSubTask;
526 protocol->tokenManagerInstance = GetLiteTokenManagerInstance();
527 g_protocolEntityVec.pushBackT(&g_protocolEntityVec, (void *)protocol);
528 }
529
530 if (IsSupportPakeV1()) {
531 protocol = (DasProtocolEntity *)HcMalloc(sizeof(DasProtocolEntity), 0);
532 if (protocol == NULL) {
533 LOGE("Malloc for pake v1 dasProtocolEntity failed.");
534 return HC_ERR_ALLOC_MEMORY;
535 }
536 protocol->type = PAKE_V1;
537 protocol->algInProtocol = GetPakeAlgInProtocol(ALG_OFFSET_FOR_PAKE_V1);
538 protocol->createSubTask = CreatePakeV1SubTask;
539 protocol->tokenManagerInstance = GetStandardTokenManagerInstance();
540 g_protocolEntityVec.pushBackT(&g_protocolEntityVec, (void *)protocol);
541 }
542
543 if (IsSupportPakeV2()) {
544 protocol = (DasProtocolEntity *)HcMalloc(sizeof(DasProtocolEntity), 0);
545 if (protocol == NULL) {
546 LOGE("Malloc for pake v2 dasProtocolEntity failed.");
547 return HC_ERR_ALLOC_MEMORY;
548 }
549 protocol->type = PAKE_V2;
550 protocol->algInProtocol = GetPakeAlgInProtocol(ALG_OFFSET_FOR_PAKE_V2);
551 protocol->createSubTask = CreatePakeV2SubTask;
552 protocol->tokenManagerInstance = GetStandardTokenManagerInstance();
553 g_protocolEntityVec.pushBackT(&g_protocolEntityVec, (void *)protocol);
554 }
555
556 return HC_SUCCESS;
557 }
558
DestroyDasProtocolEntities(void)559 void DestroyDasProtocolEntities(void)
560 {
561 uint32_t index;
562 void **ptr = NULL;
563 FOR_EACH_HC_VECTOR(g_protocolEntityVec, index, ptr) {
564 HcFree((DasProtocolEntity *)(*ptr));
565 *ptr = NULL;
566 }
567 DESTROY_HC_VECTOR(DasProtocolEntityVec, &g_protocolEntityVec);
568 }
569