]> git.ipfire.org Git - thirdparty/squid.git/blob - src/mem/PoolMalloc.cc
SourceFormat Enforcement
[thirdparty/squid.git] / src / mem / PoolMalloc.cc
1 /*
2 * Copyright (C) 1996-2017 The Squid Software Foundation and contributors
3 *
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
7 */
8
9 /*
10 * DEBUG: section 63 Low Level Memory Pool Management
11 * AUTHOR: Alex Rousskov, Andres Kroonmaa, Robert Collins, Henrik Nordstrom
12 */
13
14 #include "squid.h"
15 #include "mem/PoolMalloc.h"
16
17 #include <cassert>
18 #include <cstring>
19
20 extern time_t squid_curtime;
21
22 void *
23 MemPoolMalloc::allocate()
24 {
25 void *obj = NULL;
26 if (!freelist.empty()) {
27 obj = freelist.top();
28 freelist.pop();
29 }
30 if (obj) {
31 --meter.idle;
32 ++saved_calls;
33 } else {
34 if (doZero)
35 obj = xcalloc(1, obj_size);
36 else
37 obj = xmalloc(obj_size);
38 ++meter.alloc;
39 }
40 ++meter.inuse;
41 return obj;
42 }
43
44 void
45 MemPoolMalloc::deallocate(void *obj, bool aggressive)
46 {
47 --meter.inuse;
48 if (aggressive) {
49 xfree(obj);
50 --meter.alloc;
51 } else {
52 if (doZero)
53 memset(obj, 0, obj_size);
54 ++meter.idle;
55 freelist.push(obj);
56 }
57 }
58
59 /* TODO extract common logic to MemAllocate */
60 int
61 MemPoolMalloc::getStats(MemPoolStats * stats, int accumulate)
62 {
63 if (!accumulate) /* need skip memset for GlobalStats accumulation */
64 memset(stats, 0, sizeof(MemPoolStats));
65
66 stats->pool = this;
67 stats->label = objectType();
68 stats->meter = &meter;
69 stats->obj_size = obj_size;
70 stats->chunk_capacity = 0;
71
72 stats->chunks_alloc += 0;
73 stats->chunks_inuse += 0;
74 stats->chunks_partial += 0;
75 stats->chunks_free += 0;
76
77 stats->items_alloc += meter.alloc.currentLevel();
78 stats->items_inuse += meter.inuse.currentLevel();
79 stats->items_idle += meter.idle.currentLevel();
80
81 stats->overhead += sizeof(MemPoolMalloc) + strlen(objectType()) + 1;
82
83 return meter.inuse.currentLevel();
84 }
85
86 int
87 MemPoolMalloc::getInUseCount()
88 {
89 return meter.inuse.currentLevel();
90 }
91
92 MemPoolMalloc::MemPoolMalloc(char const *aLabel, size_t aSize) : MemImplementingAllocator(aLabel, aSize)
93 {
94 }
95
96 MemPoolMalloc::~MemPoolMalloc()
97 {
98 assert(meter.inuse.currentLevel() == 0);
99 clean(0);
100 }
101
102 bool
103 MemPoolMalloc::idleTrigger(int shift) const
104 {
105 return freelist.size() >> (shift ? 8 : 0);
106 }
107
108 void
109 MemPoolMalloc::clean(time_t)
110 {
111 while (!freelist.empty()) {
112 void *obj = freelist.top();
113 freelist.pop();
114 --meter.idle;
115 --meter.alloc;
116 xfree(obj);
117 }
118 }
119