]>
git.ipfire.org Git - thirdparty/squid.git/blob - src/MessageDelayPools.cc
7b5d6c44e1a13435b19a0df50d62af91f862a108
2 * Copyright (C) 1996-2022 The Squid Software Foundation and contributors
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.
12 #include "acl/Gadgets.h"
14 #include "ConfigParser.h"
15 #include "DelaySpec.h"
17 #include "MessageBucket.h"
18 #include "MessageDelayPools.h"
25 MessageDelayPools::~MessageDelayPools()
31 MessageDelayPools::Instance()
33 static MessageDelayPools pools
;
37 MessageDelayPool::Pointer
38 MessageDelayPools::pool(const SBuf
&name
)
40 auto it
= std::find_if(pools
.begin(), pools
.end(),
41 [&name
](const MessageDelayPool::Pointer p
) { return p
->poolName
== name
; });
42 return it
== pools
.end() ? nullptr : *it
;
46 MessageDelayPools::add(MessageDelayPool
*p
)
48 const auto it
= std::find_if(pools
.begin(), pools
.end(),
49 [&p
](const MessageDelayPool::Pointer mp
) { return mp
->poolName
== p
->poolName
; });
50 if (it
!= pools
.end()) {
51 debugs(3, DBG_CRITICAL
, "WARNING: Ignoring duplicate " << p
->poolName
<< " response delay pool");
58 MessageDelayPools::freePools()
63 MessageDelayPool::MessageDelayPool(const SBuf
&name
, int64_t bucketSpeed
, int64_t bucketSize
,
64 int64_t aggregateSpeed
, int64_t aggregateSize
, uint16_t initialBucketPercent
):
67 individualRestore(bucketSpeed
),
68 individualMaximum(bucketSize
),
69 aggregateRestore(aggregateSpeed
),
70 aggregateMaximum(aggregateSize
),
71 initialBucketLevel(initialBucketPercent
),
72 lastUpdate(squid_curtime
)
74 theBucket
.level() = aggregateMaximum
;
77 MessageDelayPool::~MessageDelayPool()
80 aclDestroyAccessList(&access
);
84 MessageDelayPool::refillBucket()
88 const int incr
= squid_curtime
- lastUpdate
;
90 lastUpdate
= squid_curtime
;
92 spec
.restore_bps
= aggregateRestore
;
93 spec
.max_bytes
= aggregateMaximum
;
94 theBucket
.update(spec
, incr
);
99 MessageDelayPool::dump(StoreEntry
*entry
) const
101 SBuf
name("response_delay_pool_access ");
102 name
.append(poolName
);
103 dump_acl_access(entry
, name
.c_str(), access
);
104 storeAppendPrintf(entry
, "response_delay_pool parameters %" PRId64
" %" PRId64
" %" PRId64
" %" PRId64
" %d\n",
105 individualRestore
, individualMaximum
, aggregateRestore
, aggregateMaximum
, initialBucketLevel
);
106 storeAppendPrintf(entry
, "\n");
109 MessageBucket::Pointer
110 MessageDelayPool::createBucket()
112 return new MessageBucket(individualRestore
, initialBucketLevel
, individualMaximum
, this);
116 MessageDelayConfig::parseResponseDelayPool()
118 static const SBuf
bucketSpeedLimit("individual-restore");
119 static const SBuf
maxBucketSize("individual-maximum");
120 static const SBuf
aggregateSpeedLimit("aggregate-restore");
121 static const SBuf
maxAggregateSize("aggregate-maximum");
122 static const SBuf
initialBucketPercent("initial-bucket-level");
124 static std::map
<SBuf
, int64_t> params
;
125 params
[bucketSpeedLimit
] = -1;
126 params
[maxBucketSize
] = -1;
127 params
[aggregateSpeedLimit
] = -1;
128 params
[maxAggregateSize
] = -1;
129 params
[initialBucketPercent
] = 50;
131 const SBuf
name(ConfigParser::NextToken());
132 if (name
.isEmpty()) {
133 debugs(3, DBG_CRITICAL
, "FATAL: response_delay_pool missing required \"name\" parameter.");
139 char *value
= nullptr;
140 while (ConfigParser::NextKvPair(key
, value
)) {
142 debugs(3, DBG_CRITICAL
, "FATAL: '" << key
<< "' option missing value");
146 auto it
= params
.find(SBuf(key
));
147 if (it
== params
.end()) {
148 debugs(3, DBG_CRITICAL
, "FATAL: response_delay_pool unknown option '" << key
<< "'");
152 it
->second
= (it
->first
== initialBucketPercent
) ? xatos(value
) : xatoll(value
, 10);
155 const char *fatalMsg
= nullptr;
156 if ((params
[bucketSpeedLimit
] < 0) != (params
[maxBucketSize
] < 0))
157 fatalMsg
= "'individual-restore' and 'individual-maximum'";
158 else if ((params
[aggregateSpeedLimit
] < 0) != (params
[maxAggregateSize
] < 0))
159 fatalMsg
= "'aggregate-restore' and 'aggregate-maximum'";
162 debugs(3, DBG_CRITICAL
, "FATAL: must use " << fatalMsg
<< " options in conjunction");
167 MessageDelayPool
*pool
= new MessageDelayPool(name
,
168 params
[bucketSpeedLimit
],
169 params
[maxBucketSize
],
170 params
[aggregateSpeedLimit
],
171 params
[maxAggregateSize
],
172 static_cast<uint16_t>(params
[initialBucketPercent
])
174 MessageDelayPools::Instance()->add(pool
);
178 MessageDelayConfig::parseResponseDelayPoolAccess() {
179 const char *token
= ConfigParser::NextToken();
181 debugs(3, DBG_CRITICAL
, "ERROR: required pool_name option missing");
184 MessageDelayPool::Pointer pool
= MessageDelayPools::Instance()->pool(SBuf(token
));
185 static ConfigParser parser
;
187 aclParseAccessLine("response_delay_pool_access", parser
, &pool
->access
);
191 MessageDelayConfig::freePools()
193 MessageDelayPools::Instance()->freePools();
197 MessageDelayConfig::dumpResponseDelayPoolParameters(StoreEntry
*entry
)
199 auto &pools
= MessageDelayPools::Instance()->pools
;
200 for (auto pool
: pools
)