/src/pjsip/pjlib/include/pj/pool_i.h
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (C) 2008-2011 Teluu Inc. (http://www.teluu.com) |
3 | | * Copyright (C) 2003-2008 Benny Prijono <benny@prijono.org> |
4 | | * |
5 | | * This program is free software; you can redistribute it and/or modify |
6 | | * it under the terms of the GNU General Public License as published by |
7 | | * the Free Software Foundation; either version 2 of the License, or |
8 | | * (at your option) any later version. |
9 | | * |
10 | | * This program is distributed in the hope that it will be useful, |
11 | | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 | | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
13 | | * GNU General Public License for more details. |
14 | | * |
15 | | * You should have received a copy of the GNU General Public License |
16 | | * along with this program; if not, write to the Free Software |
17 | | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
18 | | */ |
19 | | |
20 | | |
21 | | #include <pj/string.h> |
22 | | |
23 | 175k | #define PJ_POOL_ALIGN_PTR(PTR,ALIGNMENT) (PTR + (-(pj_ssize_t)(PTR) & (ALIGNMENT-1))) |
24 | | #define PJ_IS_POWER_OF_TWO(val) (((val)>0) && ((val) & ((val)-1))==0) |
25 | | #define PJ_IS_ALIGNED(PTR, ALIGNMENT) (!((pj_ssize_t)(PTR) & ((ALIGNMENT)-1))) |
26 | | |
27 | | PJ_IDEF(pj_size_t) pj_pool_get_capacity( pj_pool_t *pool ) |
28 | 1.37k | { |
29 | 1.37k | return pool->capacity; |
30 | 1.37k | } |
31 | | |
32 | | PJ_IDEF(pj_size_t) pj_pool_get_used_size( pj_pool_t *pool ) |
33 | 0 | { |
34 | 0 | pj_pool_block *b = pool->block_list.next; |
35 | 0 | pj_size_t used_size = sizeof(pj_pool_t); |
36 | 0 | while (b != &pool->block_list) { |
37 | 0 | used_size += (b->cur - b->buf) + sizeof(pj_pool_block); |
38 | 0 | b = b->next; |
39 | 0 | } |
40 | 0 | return used_size; |
41 | 0 | } |
42 | | |
43 | | PJ_IDEF(void*) pj_pool_alloc_from_block( pj_pool_block *block, pj_size_t alignment, |
44 | | pj_size_t size ) |
45 | 175k | { |
46 | 175k | unsigned char *ptr; |
47 | | |
48 | 175k | pj_assert(PJ_IS_POWER_OF_TWO(alignment)); |
49 | | // Size should be already aligned. |
50 | | // this code was moved up to pj_pool_aligned_alloc. |
51 | | // ...and then removed there |
52 | | // |
53 | | ///* The operation below is valid for size==0. |
54 | | // * When size==0, the function will return the pointer to the pool |
55 | | // * memory address, but no memory will be allocated. |
56 | | // */ |
57 | | //if (size & (alignment -1)) { |
58 | | // size = (size + alignment) & ~(alignment -1); |
59 | | //} |
60 | 175k | ptr = PJ_POOL_ALIGN_PTR(block->cur, alignment); |
61 | 175k | if (block->cur <= ptr && /* check pointer overflow */ |
62 | 175k | block->end - ptr >= (pj_ssize_t)size) /* check available size */ |
63 | 128k | { |
64 | | //if (ptr + size <= block->end && |
65 | | // /* here we check pointer overflow */ |
66 | | // block->cur <= ptr && ptr <= ptr + size) { |
67 | 128k | block->cur = ptr + size; |
68 | 128k | return ptr; |
69 | 128k | } |
70 | 46.9k | return NULL; |
71 | 175k | } |
72 | | |
73 | | PJ_IDEF(void*) pj_pool_alloc( pj_pool_t *pool, pj_size_t size) |
74 | 128k | { |
75 | 128k | return pj_pool_aligned_alloc(pool, 0, size); |
76 | 128k | } |
77 | | |
78 | | PJ_IDEF(void*) pj_pool_aligned_alloc(pj_pool_t *pool, pj_size_t alignment, |
79 | | pj_size_t size) |
80 | 128k | { |
81 | 128k | void *ptr; |
82 | | |
83 | 128k | PJ_ASSERT_RETURN(!alignment || PJ_IS_POWER_OF_TWO(alignment), NULL); |
84 | | |
85 | 128k | if (!alignment) |
86 | 128k | alignment = pool->alignment; |
87 | | |
88 | | #if 0 |
89 | | //Rounding up is the compiler's job, not the allocator's. |
90 | | |
91 | | /* The operation below is valid for size==0. |
92 | | * When size==0, the function will return the pointer to the pool |
93 | | * memory address, but no memory will be allocated. |
94 | | */ |
95 | | if (size & (alignment -1)) { |
96 | | size = (size + alignment) & ~(alignment -1); |
97 | | } |
98 | | pj_assert(PJ_IS_ALIGNED(size, alignment)); |
99 | | #endif |
100 | | |
101 | 128k | ptr = pj_pool_alloc_from_block(pool->block_list.next, |
102 | 128k | alignment, size); |
103 | 128k | if (!ptr) |
104 | 7.46k | ptr = pj_pool_allocate_find(pool, alignment, size); |
105 | 128k | return ptr; |
106 | 128k | } |
107 | | |
108 | | |
109 | | PJ_IDEF(void*) pj_pool_calloc( pj_pool_t *pool, pj_size_t count, pj_size_t size) |
110 | 0 | { |
111 | 0 | void *buf = pj_pool_alloc( pool, size*count); |
112 | 0 | if (buf) |
113 | 0 | pj_bzero(buf, size * count); |
114 | 0 | return buf; |
115 | 0 | } |
116 | | |
117 | | PJ_IDEF(const char *) pj_pool_getobjname( const pj_pool_t *pool ) |
118 | 0 | { |
119 | 0 | return pool->obj_name; |
120 | 0 | } |
121 | | |
122 | | PJ_IDEF(pj_pool_t*) pj_pool_create( pj_pool_factory *f, |
123 | | const char *name, |
124 | | pj_size_t initial_size, |
125 | | pj_size_t increment_size, |
126 | | pj_pool_callback *callback) |
127 | 1.37k | { |
128 | 1.37k | return pj_pool_aligned_create(f, name, initial_size, increment_size, 0, callback); |
129 | 1.37k | } |
130 | | |
131 | | PJ_IDEF(pj_pool_t*) pj_pool_aligned_create(pj_pool_factory *f, |
132 | | const char *name, |
133 | | pj_size_t initial_size, |
134 | | pj_size_t increment_size, |
135 | | pj_size_t alignment, |
136 | | pj_pool_callback *callback) |
137 | 1.37k | { |
138 | 1.37k | return (*f->create_pool)(f, name, initial_size, increment_size, alignment, callback); |
139 | 1.37k | } |
140 | | |
141 | | PJ_IDEF(void) pj_pool_release( pj_pool_t *pool ) |
142 | 1.37k | { |
143 | | #if PJ_POOL_RELEASE_WIPE_DATA |
144 | | pj_pool_block *b; |
145 | | |
146 | | b = pool->block_list.next; |
147 | | while (b != &pool->block_list) { |
148 | | volatile unsigned char *p = b->buf; |
149 | | while (p < b->end) *p++ = 0; |
150 | | b = b->next; |
151 | | } |
152 | | #endif |
153 | | |
154 | 1.37k | if (pool->factory->release_pool) |
155 | 1.37k | (*pool->factory->release_pool)(pool->factory, pool); |
156 | 1.37k | } |
157 | | |
158 | | |
159 | | PJ_IDEF(void) pj_pool_safe_release( pj_pool_t **ppool ) |
160 | 0 | { |
161 | 0 | pj_pool_t *pool = *ppool; |
162 | 0 | *ppool = NULL; |
163 | 0 | if (pool) |
164 | 0 | pj_pool_release(pool); |
165 | 0 | } |
166 | | |
167 | | PJ_IDEF(void) pj_pool_secure_release( pj_pool_t **ppool ) |
168 | 0 | { |
169 | 0 | pj_pool_block *b; |
170 | 0 | pj_pool_t *pool = *ppool; |
171 | 0 | *ppool = NULL; |
172 | |
|
173 | 0 | if (!pool) |
174 | 0 | return; |
175 | | |
176 | 0 | b = pool->block_list.next; |
177 | 0 | while (b != &pool->block_list) { |
178 | 0 | volatile unsigned char *p = b->buf; |
179 | 0 | while (p < b->end) *p++ = 0; |
180 | 0 | b = b->next; |
181 | 0 | } |
182 | |
|
183 | 0 | pj_pool_release(pool); |
184 | 0 | } |