1 /*
2 * This file is part of the openHiTLS project.
3 *
4 * openHiTLS is licensed under the Mulan PSL v2.
5 * You can use this software according to the terms and conditions of the Mulan PSL v2.
6 * You may obtain a copy of Mulan PSL v2 at:
7 *
8 * http://license.coscl.org.cn/MulanPSL2
9 *
10 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
11 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
12 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
13 * See the Mulan PSL v2 for more details.
14 */
15
16 #include "hitls_build.h"
17 #ifdef HITLS_BSL_UIO_PLT
18
19 #include "securec.h"
20 #include "bsl_sal.h"
21 #include "bsl_binlog_id.h"
22 #include "bsl_log_internal.h"
23 #include "bsl_log.h"
24 #include "bsl_err_internal.h"
25 #include "bsl_errno.h"
26 #include "bsl_uio.h"
27 #include "uio_base.h"
28 #include "uio_abstraction.h"
29
BSL_UIO_NewMethod(void)30 BSL_UIO_Method *BSL_UIO_NewMethod(void)
31 {
32 BSL_UIO_Method *meth = (BSL_UIO_Method *)BSL_SAL_Calloc(1u, sizeof(BSL_UIO_Method));
33 if (meth == NULL) {
34 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05058, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
35 "new method is NULL.", NULL, NULL, NULL, NULL);
36 BSL_ERR_PUSH_ERROR(BSL_MALLOC_FAIL);
37 return NULL;
38 }
39
40 return meth;
41 }
42
BSL_UIO_FreeMethod(BSL_UIO_Method * meth)43 void BSL_UIO_FreeMethod(BSL_UIO_Method *meth)
44 {
45 BSL_SAL_FREE(meth);
46 }
47
BSL_UIO_SetMethodType(BSL_UIO_Method * meth,int32_t type)48 int32_t BSL_UIO_SetMethodType(BSL_UIO_Method *meth, int32_t type)
49 {
50 if (meth == NULL) {
51 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
52 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05059, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
53 "set method type is NULL.", NULL, NULL, NULL, NULL);
54 return BSL_NULL_INPUT;
55 }
56 meth->uioType = type;
57 return BSL_SUCCESS;
58 }
59
BSL_UIO_SetMethod(BSL_UIO_Method * meth,int32_t type,void * func)60 int32_t BSL_UIO_SetMethod(BSL_UIO_Method *meth, int32_t type, void *func)
61 {
62 if (meth == NULL || func == NULL) {
63 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
64 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05060, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
65 "set method is NULL.", NULL, NULL, NULL, NULL);
66 return BSL_NULL_INPUT;
67 }
68
69 switch (type) {
70 case BSL_UIO_WRITE_CB:
71 meth->uioWrite = func;
72 break;
73 case BSL_UIO_READ_CB:
74 meth->uioRead = func;
75 break;
76 case BSL_UIO_CTRL_CB:
77 meth->uioCtrl = func;
78 break;
79 case BSL_UIO_CREATE_CB:
80 meth->uioCreate = func;
81 break;
82 case BSL_UIO_DESTROY_CB:
83 meth->uioDestroy = func;
84 break;
85 case BSL_UIO_PUTS_CB:
86 meth->uioPuts = func;
87 break;
88 case BSL_UIO_GETS_CB:
89 meth->uioGets = func;
90 break;
91 default:
92 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05025, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
93 "method type is wrong.", NULL, NULL, NULL, NULL);
94 BSL_ERR_PUSH_ERROR(BSL_INVALID_ARG);
95 return BSL_INVALID_ARG;
96 }
97 return BSL_SUCCESS;
98 }
99
BSL_UIO_New(const BSL_UIO_Method * method)100 BSL_UIO *BSL_UIO_New(const BSL_UIO_Method *method)
101 {
102 int32_t ret = BSL_SUCCESS;
103 if (method == NULL) {
104 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
105 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05021, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
106 "method is NULL.", 0, 0, 0, 0);
107 return NULL;
108 }
109
110 BSL_UIO *uio = (BSL_UIO *)BSL_SAL_Calloc(1, sizeof(struct UIO_ControlBlock));
111 if (uio == NULL) {
112 BSL_ERR_PUSH_ERROR(BSL_MALLOC_FAIL);
113 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05022, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
114 "uio malloc fail.", 0, 0, 0, 0);
115 return NULL;
116 }
117
118 (void)memcpy_s(&uio->method, sizeof(BSL_UIO_Method), method, sizeof(BSL_UIO_Method));
119
120 BSL_SAL_ReferencesInit(&(uio->references));
121 BSL_UIO_SetIsUnderlyingClosedByUio(uio, false);
122
123 if (uio->method.uioCreate != NULL) {
124 ret = uio->method.uioCreate(uio);
125 if (ret != BSL_SUCCESS) {
126 BSL_ERR_PUSH_ERROR(BSL_UIO_FAIL);
127 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05023, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
128 "uio create data fail.", 0, 0, 0, 0);
129 BSL_SAL_FREE(uio);
130 return NULL;
131 }
132 }
133
134 return uio;
135 }
136
BSL_UIO_UpRef(BSL_UIO * uio)137 int32_t BSL_UIO_UpRef(BSL_UIO *uio)
138 {
139 if (uio == NULL) {
140 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05024, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
141 "uio is NULL.", 0, 0, 0, 0);
142 BSL_ERR_PUSH_ERROR(BSL_INTERNAL_EXCEPTION);
143 return BSL_INTERNAL_EXCEPTION;
144 }
145 if (uio->references.count == INT32_MAX) {
146 BSL_ERR_PUSH_ERROR(BSL_UIO_REF_MAX);
147 return BSL_UIO_REF_MAX;
148 }
149 int val = 0;
150 BSL_SAL_AtomicUpReferences(&(uio->references), &val);
151 return BSL_SUCCESS;
152 }
153
BSL_UIO_Free(BSL_UIO * uio)154 void BSL_UIO_Free(BSL_UIO *uio)
155 {
156 if (uio == NULL) {
157 return;
158 }
159 int ret = 0;
160 BSL_SAL_AtomicDownReferences(&(uio->references), &ret);
161 if (ret > 0) {
162 return;
163 }
164 if (uio->userData != NULL && uio->userDataFreeFunc != NULL) {
165 (void)uio->userDataFreeFunc(uio->userData);
166 uio->userData = NULL;
167 }
168 if (uio->method.uioDestroy != NULL) {
169 (void)uio->method.uioDestroy(uio);
170 }
171 BSL_SAL_ReferencesFree(&(uio->references));
172 BSL_SAL_FREE(uio);
173 return;
174 }
175
BSL_UIO_Write(BSL_UIO * uio,const void * data,uint32_t len,uint32_t * writeLen)176 int32_t BSL_UIO_Write(BSL_UIO *uio, const void *data, uint32_t len, uint32_t *writeLen)
177 {
178 if (uio == NULL || uio->method.uioWrite == NULL || data == NULL || writeLen == NULL || len == 0) {
179 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05026, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
180 "uio write: internal input error.", 0, 0, 0, 0);
181 BSL_ERR_PUSH_ERROR(BSL_INTERNAL_EXCEPTION);
182 return BSL_INTERNAL_EXCEPTION; // if the uio is null, the send size is zero, means no data send;
183 }
184
185 if (uio->init != 1) {
186 BSL_ERR_PUSH_ERROR(BSL_UIO_UNINITIALIZED);
187 return BSL_UIO_UNINITIALIZED;
188 }
189
190 int32_t ret = uio->method.uioWrite(uio, data, len, writeLen);
191 if (ret == BSL_SUCCESS) {
192 uio->writeNum += (int64_t)*writeLen;
193 }
194
195 return ret;
196 }
197
BSL_UIO_Puts(BSL_UIO * uio,const char * buf,uint32_t * writeLen)198 int32_t BSL_UIO_Puts(BSL_UIO *uio, const char *buf, uint32_t *writeLen)
199 {
200 if (uio == NULL || uio->method.uioPuts == NULL || writeLen == NULL || buf == NULL) {
201 BSL_ERR_PUSH_ERROR(BSL_INTERNAL_EXCEPTION);
202 return BSL_INTERNAL_EXCEPTION;
203 }
204
205 if (uio->init != 1) {
206 BSL_ERR_PUSH_ERROR(BSL_UIO_UNINITIALIZED);
207 return BSL_UIO_UNINITIALIZED;
208 }
209
210 int32_t ret = uio->method.uioPuts(uio, buf, writeLen);
211 if (ret == BSL_SUCCESS) {
212 uio->writeNum += (int64_t)*writeLen;
213 }
214
215 return ret;
216 }
217
BSL_UIO_Gets(BSL_UIO * uio,char * buf,uint32_t * readLen)218 int32_t BSL_UIO_Gets(BSL_UIO *uio, char *buf, uint32_t *readLen)
219 {
220 if (uio == NULL || uio->method.uioGets == NULL || readLen == NULL || buf == NULL) {
221 BSL_ERR_PUSH_ERROR(BSL_INTERNAL_EXCEPTION);
222 return BSL_INTERNAL_EXCEPTION;
223 }
224
225 if (uio->init != 1) {
226 BSL_ERR_PUSH_ERROR(BSL_UIO_UNINITIALIZED);
227 return BSL_UIO_UNINITIALIZED;
228 }
229
230 int32_t ret = uio->method.uioGets(uio, buf, readLen);
231 if (ret == BSL_SUCCESS) {
232 uio->readNum += (int64_t)*readLen;
233 }
234
235 return ret;
236 }
237
BSL_UIO_Read(BSL_UIO * uio,void * data,uint32_t len,uint32_t * readLen)238 int32_t BSL_UIO_Read(BSL_UIO *uio, void *data, uint32_t len, uint32_t *readLen)
239 {
240 if (uio == NULL || uio->method.uioRead == NULL || data == NULL || len == 0 || readLen == NULL) {
241 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05027, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
242 "uio read: internal input error.", 0, 0, 0, 0);
243 BSL_ERR_PUSH_ERROR(BSL_INTERNAL_EXCEPTION);
244 return BSL_INTERNAL_EXCEPTION;
245 }
246
247 if (uio->init != 1) {
248 BSL_ERR_PUSH_ERROR(BSL_UIO_UNINITIALIZED);
249 return BSL_UIO_UNINITIALIZED;
250 }
251
252 int32_t ret = uio->method.uioRead(uio, data, len, readLen);
253 if (ret == BSL_SUCCESS) {
254 uio->readNum += (int64_t)*readLen;
255 }
256
257 return ret;
258 }
259
BSL_UIO_GetTransportType(const BSL_UIO * uio)260 int32_t BSL_UIO_GetTransportType(const BSL_UIO *uio)
261 {
262 if (uio == NULL) {
263 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05028, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
264 "uio is NULL.", 0, 0, 0, 0);
265 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
266 return BSL_NULL_INPUT;
267 }
268 return uio->method.uioType;
269 }
270
BSL_UIO_GetUioChainTransportType(BSL_UIO * uio,const BSL_UIO_TransportType uioType)271 bool BSL_UIO_GetUioChainTransportType(BSL_UIO *uio, const BSL_UIO_TransportType uioType)
272 {
273 if (uio == NULL) {
274 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05069, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN,
275 "get uio type is NULL.", NULL, NULL, NULL, NULL);
276 return false;
277 }
278
279 while (uio != NULL) {
280 if (BSL_UIO_GetTransportType(uio) == (int32_t)uioType) {
281 return true;
282 }
283 uio = BSL_UIO_Next(uio);
284 }
285 return false;
286 }
287
BSL_UIO_SetUserData(BSL_UIO * uio,void * data)288 int32_t BSL_UIO_SetUserData(BSL_UIO *uio, void *data)
289 {
290 if (uio == NULL) {
291 BSL_LOG_BINLOG_FIXLEN(BINLOG_ID05029, BSL_LOG_LEVEL_ERR, BSL_LOG_BINLOG_TYPE_RUN, "uio is NULL.", 0, 0, 0, 0);
292 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
293 return BSL_NULL_INPUT;
294 }
295
296 uio->userData = data;
297 return BSL_SUCCESS;
298 }
299
BSL_UIO_SetUserDataFreeFunc(BSL_UIO * uio,BSL_UIO_USERDATA_FREE_FUNC userDataFreeFunc)300 int32_t BSL_UIO_SetUserDataFreeFunc(BSL_UIO *uio, BSL_UIO_USERDATA_FREE_FUNC userDataFreeFunc)
301 {
302 if (uio == NULL) {
303 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
304 return BSL_NULL_INPUT;
305 }
306 uio->userDataFreeFunc = userDataFreeFunc;
307 return BSL_SUCCESS;
308 }
309
BSL_UIO_GetUserData(const BSL_UIO * uio)310 void *BSL_UIO_GetUserData(const BSL_UIO *uio)
311 {
312 if (uio == NULL) {
313 return NULL;
314 }
315
316 return uio->userData;
317 }
318
BSL_UIO_GetIsUnderlyingClosedByUio(const BSL_UIO * uio)319 bool BSL_UIO_GetIsUnderlyingClosedByUio(const BSL_UIO *uio)
320 {
321 if (uio == NULL) {
322 return false; // If the value is empty, the function will not release the value.
323 }
324 return uio->isUnderlyingClosedByUio;
325 }
326
BSL_UIO_SetIsUnderlyingClosedByUio(BSL_UIO * uio,bool close)327 void BSL_UIO_SetIsUnderlyingClosedByUio(BSL_UIO *uio, bool close)
328 {
329 if (uio == NULL) {
330 return;
331 }
332 uio->isUnderlyingClosedByUio = close;
333 }
334
BSL_UIO_GetMethod(const BSL_UIO * uio)335 const BSL_UIO_Method *BSL_UIO_GetMethod(const BSL_UIO *uio)
336 {
337 if (uio == NULL) {
338 return NULL;
339 }
340 return &uio->method;
341 }
342
UIO_GetInit(BSL_UIO * uio,int32_t larg,bool * parg)343 static int32_t UIO_GetInit(BSL_UIO *uio, int32_t larg, bool *parg)
344 {
345 if (larg != (int32_t)sizeof(bool) || parg == NULL) {
346 BSL_ERR_PUSH_ERROR(BSL_INVALID_ARG);
347 return BSL_INVALID_ARG;
348 }
349 *parg = uio->init;
350 return BSL_SUCCESS;
351 }
352
UIO_GetReadNum(BSL_UIO * uio,int32_t larg,int64_t * parg)353 static int32_t UIO_GetReadNum(BSL_UIO *uio, int32_t larg, int64_t *parg)
354 {
355 if (larg != (int32_t)sizeof(int64_t) || parg == NULL) {
356 BSL_ERR_PUSH_ERROR(BSL_INVALID_ARG);
357 return BSL_INVALID_ARG;
358 }
359 *parg = uio->readNum;
360 return BSL_SUCCESS;
361 }
362
UIO_GetWriteNum(BSL_UIO * uio,int32_t larg,int64_t * parg)363 static int32_t UIO_GetWriteNum(BSL_UIO *uio, int32_t larg, int64_t *parg)
364 {
365 if (larg != (int32_t)sizeof(int64_t) || parg == NULL) {
366 BSL_ERR_PUSH_ERROR(BSL_INVALID_ARG);
367 return BSL_INVALID_ARG;
368 }
369 *parg = uio->writeNum;
370 return BSL_SUCCESS;
371 }
372
BSL_UIO_Ctrl(BSL_UIO * uio,int32_t cmd,int32_t larg,void * parg)373 int32_t BSL_UIO_Ctrl(BSL_UIO *uio, int32_t cmd, int32_t larg, void *parg)
374 {
375 if (uio == NULL || uio->method.uioCtrl == NULL) {
376 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
377 return BSL_NULL_INPUT;
378 }
379 switch (cmd) {
380 case BSL_UIO_GET_INIT:
381 return UIO_GetInit(uio, larg, parg);
382 case BSL_UIO_GET_READ_NUM:
383 return UIO_GetReadNum(uio, larg, parg);
384 case BSL_UIO_GET_WRITE_NUM:
385 return UIO_GetWriteNum(uio, larg, parg);
386 default:
387 return uio->method.uioCtrl(uio, cmd, larg, parg);
388 }
389 }
390
BSL_UIO_GetCtx(const BSL_UIO * uio)391 void *BSL_UIO_GetCtx(const BSL_UIO *uio)
392 {
393 if (uio == NULL) {
394 return NULL;
395 }
396 return uio->ctx;
397 }
398
BSL_UIO_SetCtx(BSL_UIO * uio,void * ctx)399 void BSL_UIO_SetCtx(BSL_UIO *uio, void *ctx)
400 {
401 if (uio != NULL) {
402 uio->ctx = ctx;
403 }
404 }
405
BSL_UIO_GetFd(BSL_UIO * uio)406 int32_t BSL_UIO_GetFd(BSL_UIO *uio)
407 {
408 int32_t fd = -1;
409 (void)BSL_UIO_Ctrl(uio, BSL_UIO_GET_FD, (int32_t)sizeof(fd), &fd); // Parameters are checked by each ctrl function.
410 return fd;
411 }
412
BSL_UIO_SetFD(BSL_UIO * uio,int fd)413 void BSL_UIO_SetFD(BSL_UIO *uio, int fd)
414 {
415 bool invalid = (uio == NULL) || (fd < 0);
416 if (invalid) {
417 return;
418 }
419 BSL_UIO_Ctrl(uio, BSL_UIO_SET_FD, (int32_t)sizeof(fd), &fd);
420 }
421
BSL_UIO_SetFlags(BSL_UIO * uio,uint32_t flags)422 int32_t BSL_UIO_SetFlags(BSL_UIO *uio, uint32_t flags)
423 {
424 if (uio == NULL) {
425 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
426 return BSL_NULL_INPUT;
427 }
428 uint32_t validFlags =
429 BSL_UIO_FLAGS_RWS | BSL_UIO_FLAGS_SHOULD_RETRY | BSL_UIO_FLAGS_BASE64_NO_NEWLINE | BSL_UIO_FLAGS_BASE64_PEM;
430 if ((flags & validFlags) == 0 || flags > validFlags) {
431 BSL_ERR_PUSH_ERROR(BSL_INVALID_ARG);
432 return BSL_INVALID_ARG;
433 }
434
435 uio->flags |= flags;
436 return BSL_SUCCESS;
437 }
438
BSL_UIO_ClearFlags(BSL_UIO * uio,uint32_t flags)439 int32_t BSL_UIO_ClearFlags(BSL_UIO *uio, uint32_t flags)
440 {
441 if (uio == NULL) {
442 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
443 return BSL_NULL_INPUT;
444 }
445 uio->flags &= ~flags;
446 return BSL_SUCCESS;
447 }
448
BSL_UIO_TestFlags(const BSL_UIO * uio,uint32_t flags,uint32_t * out)449 uint32_t BSL_UIO_TestFlags(const BSL_UIO *uio, uint32_t flags, uint32_t *out)
450 {
451 if (uio == NULL || out == NULL) {
452 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
453 return BSL_NULL_INPUT;
454 }
455 *out = uio->flags & flags;
456 return BSL_SUCCESS;
457 }
458
BSL_UIO_SetInit(BSL_UIO * uio,bool init)459 void BSL_UIO_SetInit(BSL_UIO *uio, bool init)
460 {
461 if (uio != NULL) {
462 uio->init = init;
463 }
464 }
465
466 /**
467 * @brief Checking for Fatal I/O Errors
468 *
469 * @param err [IN] error type
470 *
471 * @return true :Fatal error
472 * false:No fatal errors
473 */
UioIsNonFatalErr(int32_t err)474 bool UioIsNonFatalErr(int32_t err)
475 {
476 bool ret = true;
477 /** @alias Check whether err is a fatal error and modify ret. */
478 switch (err) {
479 #if defined(ENOTCONN)
480 case ENOTCONN:
481 #endif
482
483 #ifdef EINTR
484 case EINTR:
485 #endif
486
487 #ifdef EINPROGRESS
488 case EINPROGRESS:
489 #endif
490
491 #ifdef EWOULDBLOCK
492 #if !defined(WSAEWOULDBLOCK) || WSAEWOULDBLOCK != EWOULDBLOCK
493 case EWOULDBLOCK:
494 #endif
495 #endif
496
497 #ifdef EAGAIN
498 #if EWOULDBLOCK != EAGAIN
499 case EAGAIN:
500 #endif
501 #endif
502
503 #ifdef EALREADY
504 case EALREADY:
505 #endif
506
507 #ifdef EPROTO
508 case EPROTO:
509 #endif
510 ret = true;
511 break;
512 default:
513 ret = false;
514 break;
515 }
516 return ret;
517 }
518
BSL_UIO_Append(BSL_UIO * uio,BSL_UIO * tail)519 int32_t BSL_UIO_Append(BSL_UIO *uio, BSL_UIO *tail)
520 {
521 bool invalid = (uio == NULL) || (tail == NULL);
522 if (invalid) {
523 BSL_ERR_PUSH_ERROR(BSL_NULL_INPUT);
524 return BSL_NULL_INPUT;
525 }
526 BSL_UIO *t = uio;
527 while (t->next != NULL) {
528 t = t->next;
529 }
530 t->next = tail;
531 tail->prev = t;
532 return BSL_SUCCESS;
533 }
534
BSL_UIO_PopCurrent(BSL_UIO * uio)535 BSL_UIO *BSL_UIO_PopCurrent(BSL_UIO *uio)
536 {
537 if (uio == NULL) {
538 return NULL;
539 }
540 BSL_UIO *ret = uio->next;
541 if (uio->prev != NULL) {
542 uio->prev->next = uio->next;
543 }
544 if (uio->next != NULL) {
545 uio->next->prev = uio->prev;
546 }
547 uio->prev = NULL;
548 uio->next = NULL;
549 return ret;
550 }
551
BSL_UIO_FreeChain(BSL_UIO * uio)552 void BSL_UIO_FreeChain(BSL_UIO *uio)
553 {
554 BSL_UIO *b = uio;
555 while (b != NULL) {
556 int ref = b->references.count;
557 BSL_UIO *next = b->next;
558 BSL_UIO_Free(b);
559 if (ref > 1) {
560 break;
561 }
562 b = next;
563 }
564 }
565
BSL_UIO_Next(BSL_UIO * uio)566 BSL_UIO *BSL_UIO_Next(BSL_UIO *uio)
567 {
568 if (uio == NULL) {
569 return NULL;
570 }
571 return uio->next;
572 }
573
574 #endif /* HITLS_BSL_UIO_PLT */
575