1 /*
2  * Copyright (C) 2022 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 #ifndef FILLP_QUEUE_H
17 #define FILLP_QUEUE_H
18 
19 #include "lf_ring.h"
20 #include "log.h"
21 #include "spunge_mem.h"
22 #include "fillp_function.h"
23 #ifdef __cplusplus
24 extern "C" {
25 #endif
26 
27 typedef struct InnerfillpQueue {
28     FILLP_INT allocType;
29 #ifdef FILLP_64BIT_ALIGN
30     FILLP_UINT8 padd[4];
31 #endif
32     size_t size;
33     struct FillpLfRing ring;
34 } FillpQueue;
35 
FillpQueuePush(FillpQueue * q,void ** msg,FILLP_INT isTryPush,FILLP_UINT count)36 static __inline FillpErrorType FillpQueuePush(FillpQueue *q, void **msg, FILLP_INT isTryPush, FILLP_UINT count)
37 {
38     FILLP_INT ret;
39     FILLP_INT totalPush = 0;
40     for (;;) {
41         ret = FillpLfRingMpEnqueue(&q->ring, &msg[totalPush], count - (FILLP_UINT)totalPush);
42         if (ret > 0) {
43             totalPush += ret;
44             if ((FILLP_UINT)totalPush == count) {
45                 return ERR_OK;
46             }
47         } else if (isTryPush) {
48             return ERR_NOBUFS;
49         }
50     }
51 }
52 
FillpQueuePop(FillpQueue * q,void ** msg,FILLP_UINT count)53 static __inline FILLP_INT FillpQueuePop(FillpQueue *q, void **msg, FILLP_UINT count)
54 {
55     if ((q == FILLP_NULL_PTR) || (msg == FILLP_NULL_PTR)) {
56         return -1;
57     }
58 
59     return FillpLfRingMcDequeue(&q->ring, msg, count);
60 }
61 
QueueEmpty(FILLP_CONST FillpQueue * q)62 static __inline int QueueEmpty(FILLP_CONST FillpQueue *q)
63 {
64     return FillpRingEmpty(&q->ring);
65 }
66 
FillpQueueCalMemSize(size_t size)67 static __inline size_t FillpQueueCalMemSize(size_t size)
68 {
69     size_t tmpSize = FillpLfRingCalMemSize(size);
70     size_t memSize = tmpSize + sizeof(FillpQueue);
71 
72     if ((tmpSize == 0) || (memSize < sizeof(FillpQueue))) {
73         return 0;
74     }
75 
76     return memSize;
77 }
78 
FillpQueueSetProdSafe(FillpQueue * q,FILLP_BOOL safe)79 static __inline void FillpQueueSetProdSafe(FillpQueue *q, FILLP_BOOL safe)
80 {
81     FillpLfRingSetProdSafe(&q->ring, safe);
82 }
83 
FillpQueueSetConsSafe(FillpQueue * q,FILLP_BOOL safe)84 static __inline void FillpQueueSetConsSafe(FillpQueue *q, FILLP_BOOL safe)
85 {
86     FillpLfRingSetConsSafe(&q->ring, safe);
87 }
88 
FillpQueueInit(FillpQueue * q,char * name,size_t size,FILLP_INT allocType)89 static __inline void FillpQueueInit(FillpQueue *q, char *name, size_t size, FILLP_INT allocType)
90 {
91     FillpLfRingInit(&q->ring, name, size);
92 
93     q->allocType = allocType;
94     q->size = size;
95 }
96 
FillpQueueCreate(char * name,size_t size,FILLP_INT allocType)97 static __inline FillpQueue *FillpQueueCreate(char *name, size_t size, FILLP_INT allocType)
98 {
99     FillpQueue *q;
100     q = (FillpQueue *)SpungeAlloc(1, FillpQueueCalMemSize(size), allocType);
101     if (q == FILLP_NULL_PTR) {
102         FILLP_LOGERR("Failed to allocate the memory for queue \r\n");
103         return FILLP_NULL_PTR;
104     }
105 
106     FillpQueueInit(q, name, size, allocType);
107 
108     return q;
109 }
110 
FillpQueueDestroy(FillpQueue * q)111 static __inline void FillpQueueDestroy(FillpQueue *q)
112 {
113     if (q == FILLP_NULL_PTR) {
114         return;
115     }
116 
117     if ((q->allocType == SPUNGE_ALLOC_TYPE_MALLOC) || (q->allocType == SPUNGE_ALLOC_TYPE_CALLOC)) {
118         SpungeFree(q, q->allocType);
119     }
120 }
121 
FillpQueueValidOnes(FillpQueue * q)122 static __inline FILLP_ULONG FillpQueueValidOnes(FillpQueue *q)
123 {
124     if (q == FILLP_NULL_PTR) {
125         return 0;
126     }
127     return FillpRingValidOnes(&q->ring);
128 }
129 
130 #ifdef __cplusplus
131 }
132 #endif
133 
134 #endif /* FILLP_QUEUE_H */
135