|
1 /* |
|
2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. |
|
3 * |
|
4 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. |
|
5 * |
|
6 * THE BSD LICENSE |
|
7 * |
|
8 * Redistribution and use in source and binary forms, with or without |
|
9 * modification, are permitted provided that the following conditions are met: |
|
10 * |
|
11 * Redistributions of source code must retain the above copyright notice, this |
|
12 * list of conditions and the following disclaimer. |
|
13 * Redistributions in binary form must reproduce the above copyright notice, |
|
14 * this list of conditions and the following disclaimer in the documentation |
|
15 * and/or other materials provided with the distribution. |
|
16 * |
|
17 * Neither the name of the nor the names of its contributors may be |
|
18 * used to endorse or promote products derived from this software without |
|
19 * specific prior written permission. |
|
20 * |
|
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
|
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
|
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
|
24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER |
|
25 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |
|
26 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, |
|
27 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; |
|
28 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, |
|
29 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR |
|
30 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF |
|
31 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
|
32 */ |
|
33 |
|
34 #ifndef BASE_POOL_PVT_H |
|
35 #define BASE_POOL_PVT_H |
|
36 |
|
37 #ifndef BASE_POOL_H |
|
38 #include "pool.h" |
|
39 #endif /* BASE_POOL_H */ |
|
40 |
|
41 /* |
|
42 * pool_pvt.h - private definitions for memory pools |
|
43 */ |
|
44 |
|
45 /* Definitions */ |
|
46 |
|
47 /* |
|
48 * Define PER_POOL_STATISTICS to get detailed statistics for each |
|
49 * pool. |
|
50 */ |
|
51 #ifdef DEBUG |
|
52 #define PER_POOL_STATISTICS |
|
53 #endif |
|
54 |
|
55 /* Define POOL_GLOBAL_STATISTICS to get global pool statistics */ |
|
56 #define POOL_GLOBAL_STATISTICS |
|
57 |
|
58 /* |
|
59 * When POOL_ZERO_DEBUG is defined, overwrite the contents of freed |
|
60 * pool data structures and memory with the POOL_ZERO_DEBUG byte value. |
|
61 */ |
|
62 #ifdef DEBUG |
|
63 #define POOL_ZERO_DEBUG 0xa |
|
64 #endif |
|
65 |
|
66 /* |
|
67 * DEFAULT_BLOCK_SIZE specifies the minimum granularity, in bytes, used |
|
68 * in allocating memory from the heap for use with a pool. A request |
|
69 * for more than DEFAULT_BLOCK_SIZE bytes from a pool will cause a block |
|
70 * of that size to be allocated from the heap. |
|
71 */ |
|
72 #define DEFAULT_BLOCK_SIZE (32 * 1024) |
|
73 |
|
74 /* |
|
75 * The pool_recycle() mechanism keeps a list of free blocks associated |
|
76 * with each pool, in order to avoid global locking when doing the |
|
77 * pool_recycle() operation, or when subsequently allocating memory |
|
78 * from the pool. DEFAULT_RETENTION_SIZE and DEFAULT_RETENTION_NUM |
|
79 * specify the maximum number of bytes and blocks, respectively, that |
|
80 * will be kept on a per-pool free list. |
|
81 */ |
|
82 #define DEFAULT_RETENTION_SIZE (DEFAULT_BLOCK_SIZE * 2) |
|
83 #define DEFAULT_RETENTION_NUM 2 |
|
84 |
|
85 /* WORD_SIZE 8 sets us up for 8 byte alignment. */ |
|
86 #define WORD_SIZE 8 |
|
87 #undef ALIGN |
|
88 #define ALIGN(x) ( (x + WORD_SIZE-1) & (~(WORD_SIZE-1)) ) |
|
89 |
|
90 /* Types */ |
|
91 |
|
92 /* |
|
93 * pool_stats_t |
|
94 * This structure contains per pool statistics. |
|
95 */ |
|
96 #ifdef PER_POOL_STATISTICS |
|
97 typedef struct pool_stats_t pool_stats_t; |
|
98 struct pool_stats_t { |
|
99 PRUint32 poolId; /* pool id */ |
|
100 PRUint32 maxAlloc; /* maximum bytes ever used from pool */ |
|
101 PRUint32 allocCnt; /* count of memory allocations from pool */ |
|
102 PRUint32 freeCnt; /* count of pool memory free operations */ |
|
103 PRUint32 blkAlloc; /* count of block allocations */ |
|
104 PRUint32 blkFree; /* count of blocks freed (on pool_recycle) */ |
|
105 PRThread *thread; /* last thread to use pool */ |
|
106 PRTime created; /* time of pool creation */ |
|
107 }; |
|
108 #endif /* PER_POOL_STATISTICS */ |
|
109 |
|
110 typedef struct pool_config_t pool_config_t; |
|
111 struct pool_config_t { |
|
112 PRUint32 block_size; /* size of blocks to allocate */ |
|
113 PRUint32 retain_size; /* maximum bytes kept on per-pool free list */ |
|
114 PRUint32 retain_num; /* maximum blocks kept on per-pool free list */ |
|
115 }; |
|
116 |
|
117 #define POOL_CONFIG_INIT { \ |
|
118 DEFAULT_BLOCK_SIZE, /* block_size */ \ |
|
119 DEFAULT_RETENTION_SIZE, /* retain_size */ \ |
|
120 DEFAULT_RETENTION_NUM, /* retain_num */ \ |
|
121 } |
|
122 |
|
123 /* |
|
124 * block_t |
|
125 * When the user allocates space, a DEFAULT_BLOCK_SIZE (or larger) block |
|
126 * is created in the pool. This block is used until all the space is |
|
127 * eaten within it. When all the space is gone, a new block is created. |
|
128 */ |
|
129 typedef struct block_t block_t; |
|
130 struct block_t { |
|
131 char *data; /* the real alloc'd space */ |
|
132 char *start; /* first free byte in block */ |
|
133 char *end; /* ptr to end of block */ |
|
134 block_t *next; /* ptr to next block */ |
|
135 }; |
|
136 |
|
137 #define POOL_PTR_IN_BLOCK(blk, ptr) \ |
|
138 (((char *)(ptr) < (blk)->end) && ((char *)(ptr) >= (blk)->data)) |
|
139 |
|
140 /* |
|
141 * pool_t |
|
142 * A pool is a collection of blocks. The blocks consist of multiple |
|
143 * allocations of memory, but a single allocation cannot be freed by |
|
144 * itself. Once the memory is allocated it is allocated until the |
|
145 * entire pool is freed. |
|
146 */ |
|
147 typedef struct pool_t pool_t; |
|
148 struct pool_t { |
|
149 block_t *curr_block; /* current block being used */ |
|
150 block_t *used_blocks; /* blocks that are all used up */ |
|
151 block_t *free_blocks; /* blocks that are free */ |
|
152 PRUint32 free_size; /* number of bytes in free_blocks */ |
|
153 PRUint32 free_num; /* number of blocks in free_blocks */ |
|
154 size_t size; /* size of memory in pool */ |
|
155 pool_t *next; /* known_pools list */ |
|
156 #ifdef PER_POOL_STATISTICS |
|
157 pool_stats_t stats; /* statistics for this pool */ |
|
158 #endif /* PER_POOL_STATISTICS */ |
|
159 }; |
|
160 |
|
161 typedef struct pool_global_stats_t pool_global_stats_t; |
|
162 struct pool_global_stats_t { |
|
163 PRLock *lock; /* lock for access to poolList */ |
|
164 pool_t *poolList; /* list of known pools */ |
|
165 PRUint32 createCnt; /* count of pools created */ |
|
166 PRUint32 destroyCnt; /* count of pools destroyed */ |
|
167 #ifdef POOL_GLOBAL_STATISTICS |
|
168 PRUint32 blkAlloc; /* count of block allocations from heap */ |
|
169 PRUint32 blkFree; /* count of blocks freed to heap */ |
|
170 #endif /* POOL_GLOBAL_STATISTICS */ |
|
171 }; |
|
172 |
|
173 /* Private functions for inspecting pool configuration/statistics */ |
|
174 |
|
175 NSAPI_PUBLIC pool_config_t *pool_getConfig(void); |
|
176 |
|
177 NSAPI_PUBLIC pool_global_stats_t *pool_getGlobalStats(void); |
|
178 |
|
179 #ifdef PER_POOL_STATISTICS |
|
180 NSAPI_PUBLIC pool_stats_t *pool_getPoolStats(pool_handle_t *pool_handle); |
|
181 #endif |
|
182 |
|
183 #endif /* BASE_POOL_PVT_H */ |