Squid Web Cache master
Loading...
Searching...
No Matches
refresh.cc
Go to the documentation of this file.
1/*
2 * Copyright (C) 1996-2025 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/* DEBUG: section 22 Refresh Calculation */
10
11#ifndef USE_POSIX_REGEX
12#define USE_POSIX_REGEX /* put before includes; always use POSIX */
13#endif
14
15#include "squid.h"
16#include "base/PackableStream.h"
17#include "HttpHdrCc.h"
18#include "HttpReply.h"
19#include "HttpRequest.h"
20#include "MemObject.h"
21#include "mgr/Registration.h"
22#include "refresh.h"
23#include "RefreshPattern.h"
24#include "SquidConfig.h"
25#include "Store.h"
26#include "util.h"
27
28typedef enum {
31#if USE_HTCP
33#endif
34#if USE_CACHE_DIGESTS
36#endif
40
44typedef struct {
45 bool expires;
46 bool min;
47 bool lmfactor;
48 bool max;
50
51/*
52 * This enumerated list assigns specific values, ala HTTP/FTP status
53 * codes. All Fresh codes are in the range 100-199 and all stale
54 * codes are 200-299. We might want to use these codes in logging,
55 * so best to keep them consistent over time.
56 */
57enum {
73 STALE_DEFAULT = 299
74};
75
76static struct RefreshCounts {
77 const char *proto;
78 int total;
81
83static int refreshStaleness(const StoreEntry * entry, time_t check_time, const time_t age, const RefreshPattern * R, stale_flags * sf);
84
86
91const RefreshPattern *
92refreshLimits(const char *url)
93{
94 for (auto R = Config.Refresh; R; R = R->next) {
95 ++(R->stats.matchTests);
96 if (R->regex().match(url)) {
97 ++(R->stats.matchCount);
98 return R;
99 }
100 }
101
102 return nullptr;
103}
104
106static const RefreshPattern *
108{
109 for (auto R = Config.Refresh; R; R = R->next) {
110 if (R->regex().isDot())
111 return R;
112 }
113
114 return nullptr;
115}
116
138static int
139refreshStaleness(const StoreEntry * entry, time_t check_time, const time_t age, const RefreshPattern * R, stale_flags * sf)
140{
141 // 1. If the cached object has an explicit expiration time, then we rely on this and
142 // completely ignore the Min, Percent and Max values in the refresh_pattern.
143 if (entry->expires > -1) {
144 sf->expires = true;
145
146 if (entry->expires > check_time) {
147 debugs(22, 3, "FRESH: expires " << entry->expires << " > check_time " << check_time);
148 return -1;
149 } else {
150 debugs(22, 3, "STALE: expires " << entry->expires << " <= check_time " << check_time);
151 return (check_time - entry->expires);
152 }
153 }
154
155 debugs(22, 3, "No explicit expiry given, using heuristics to determine freshness");
156
157 // 2. If the entry is older than the maximum age in the refresh_pattern, it is STALE.
158 if (age > R->max) {
159 debugs(22, 3, "STALE: age " << age << " > max " << R->max);
160 sf->max = true;
161 return (age - R->max);
162 }
163
164 // 3. If there is a Last-Modified header, try the last-modified factor algorithm.
165 const time_t lastmod_delta = entry->timestamp - entry->lastModified();
166 if (lastmod_delta > 0) {
167 /* stale_age is the age of the response when it became/becomes stale according to
168 * the last-modified factor algorithm. It's how long we can consider the response
169 * fresh from the time we cached it.
170 */
171 time_t stale_age = static_cast<time_t>(lastmod_delta * R->pct);
172
173 debugs(22,3, "Last modified " << lastmod_delta << " sec before we cached it, L-M factor " <<
174 (100.0 * R->pct) << "% = " << stale_age << " sec freshness lifetime");
175 sf->lmfactor = true;
176
177 if (age >= stale_age) {
178 debugs(22, 3, "STALE: age " << age << " > stale_age " << stale_age);
179 return (age - stale_age);
180 } else {
181 debugs(22, 3, "FRESH: age " << age << " <= stale_age " << stale_age);
182 return -1;
183 }
184 }
185
186 // 4. If the entry is not as old as the minimum age in the refresh_pattern, it is FRESH.
187 if (age < R->min) {
188 debugs(22, 3, "FRESH: age (" << age << " sec) is less than configured minimum (" << R->min << " sec)");
189 sf->min = true;
190 return -1;
191 }
192
193 // 5. default is stale, by the amount we missed the minimum by
194 debugs(22, 3, "STALE: No explicit expiry, no last modified, and older than configured minimum.");
195 return (age - R->min);
196}
197
252static int
253refreshCheck(const StoreEntry * entry, HttpRequest * request, time_t delta)
254{
255 time_t age = 0;
256 time_t check_time = squid_curtime + delta;
257 int staleness;
258 stale_flags sf;
259
260 // get the URL of this entry, if there is one
261 static const SBuf nilUri("<none>");
262 SBuf uri = nilUri;
263 if (entry->mem_obj)
264 uri = entry->mem_obj->storeId();
265 else if (request)
266 uri = request->effectiveRequestUri();
267
268 debugs(22, 3, "checking freshness of " << *entry << " with URI: " << uri);
269
270 // age is not necessarily the age now, but the age at the given check_time
271 if (check_time > entry->timestamp)
272 age = check_time - entry->timestamp;
273
274 // XXX: what to do when age < 0 or counter overflow?
275 assert(age >= 0);
276
277 /* We need a refresh rule. In order of preference:
278 *
279 * 1. the rule that matches this URI by regex
280 * 2. the "." rule from the config file
281 * 3. the default "." rule
282 */
283 // XXX: performance regression. c_str() reallocates
284 const RefreshPattern *R = (uri != nilUri) ? refreshLimits(uri.c_str()) : refreshFirstDotRule();
285 if (nullptr == R)
286 R = &DefaultRefresh;
287
288 debugs(22, 3, "Matched '" << *R << '\'');
289
290 debugs(22, 3, "\tage:\t" << age);
291
292 debugs(22, 3, "\tcheck_time:\t" << Time::FormatRfc1123(check_time));
293
294 debugs(22, 3, "\tentry->timestamp:\t" << Time::FormatRfc1123(entry->timestamp));
295
296 if (request && !request->flags.ignoreCc) {
297 const HttpHdrCc *const cc = request->cache_control;
298 int minFresh = -1;
299 if (cc && cc->hasMinFresh(&minFresh)) {
300 debugs(22, 3, "\tage + min-fresh:\t" << age << " + " <<
301 minFresh << " = " << age + minFresh);
302 debugs(22, 3, "\tcheck_time + min-fresh:\t" << check_time << " + "
303 << minFresh << " = " <<
304 Time::FormatRfc1123(check_time + minFresh));
305 age += minFresh;
306 check_time += minFresh;
307 }
308 }
309
310 memset(&sf, '\0', sizeof(sf));
311
312 staleness = refreshStaleness(entry, check_time, age, R, &sf);
313
314 debugs(22, 3, "Staleness = " << staleness);
315
316 const auto reply = entry->hasFreshestReply(); // may be nil
317
318 // stale-if-error requires any failure be passed thru when its period is over.
319 int staleIfError = -1;
320 if (request && reply && reply->cache_control &&
321 reply->cache_control->hasStaleIfError(&staleIfError) &&
322 staleIfError < staleness) {
323
324 debugs(22, 3, "stale-if-error period expired. Will produce error if validation fails.");
325 request->flags.failOnValidationError = true;
326 }
327
328 /* If the origin server specified either of:
329 * Cache-Control: must-revalidate
330 * Cache-Control: proxy-revalidate
331 * the spec says the response must always be revalidated if stale.
332 */
333 const bool revalidateAlways = EBIT_TEST(entry->flags, ENTRY_REVALIDATE_ALWAYS);
334 if (revalidateAlways || (staleness > -1 &&
336 debugs(22, 3, "YES: Must revalidate stale object (origin set " <<
337 (revalidateAlways ? "no-cache or private" :
338 "must-revalidate, proxy-revalidate or s-maxage") << ")");
339 if (request)
340 request->flags.failOnValidationError = true;
342 }
343
344 /* request-specific checks */
345 if (request && !request->flags.ignoreCc) {
346 HttpHdrCc *cc = request->cache_control;
347
348 /* If the request is an IMS request, and squid is configured NOT to service this from cache
349 * (either by 'refresh-ims' in the refresh pattern or 'refresh_all_ims on' globally)
350 * then force a reload from the origin.
351 */
352 if (request->flags.ims && (R->flags.refresh_ims || Config.onoff.refresh_all_ims)) {
353 // The client's no-cache header is changed into a IMS query
354 debugs(22, 3, "YES: Client IMS request forcing revalidation of object (refresh-ims option)");
355 return STALE_FORCED_RELOAD;
356 }
357
358#if USE_HTTP_VIOLATIONS
359 /* Normally a client reload request ("Cache-Control: no-cache" or "Pragma: no-cache")
360 * means we must treat this response as STALE and fetch a new one.
361 *
362 * However, some options exist to override this behaviour. For example, we might just
363 * revalidate our existing response, or even just serve it up without revalidating it.
364 *
365 * ---- Note on the meaning of nocache_hack -----
366 *
367 * The nocache_hack flag has a very specific and complex meaning:
368 *
369 * (a) this is a reload request ("Cache-Control: no-cache" or "Pragma: no-cache" header)
370 * and (b) the configuration file either has at least one refresh_pattern with
371 * ignore-reload or reload-into-ims (not necessarily the rule matching this request) or
372 * the global reload_into_ims is set to on
373 *
374 * In other words: this is a client reload, and we might need to override
375 * the default behaviour (but we might not).
376 *
377 * "nocache_hack" is a pretty deceptive name for such a complicated meaning.
378 */
379 if (request->flags.noCacheHack()) {
380
381 if (R->flags.ignore_reload) {
382 /* The client's no-cache header is ignored completely - we'll try to serve
383 * what we have (assuming it's still fresh, etc.)
384 */
385 debugs(22, 3, "MAYBE: Ignoring client reload request - trying to serve from cache (ignore-reload option)");
387 /* The client's no-cache header is not honoured completely - we'll just try
388 * to revalidate our cached copy (IMS to origin) instead of fetching a new
389 * copy with an unconditional GET.
390 */
391 debugs(22, 3, "YES: Client reload request - cheating, only revalidating with origin (reload-into-ims option)");
393 } else {
394 /* The client's no-cache header is honoured - we fetch a new copy from origin */
395 debugs(22, 3, "YES: Client reload request - fetching new copy from origin");
396 request->flags.noCache = true;
397 return STALE_FORCED_RELOAD;
398 }
399 }
400#endif
401
402 // Check the Cache-Control client request header
403 if (nullptr != cc) {
404
405 // max-age directive
406 int maxAge = -1;
407 if (cc->hasMaxAge(&maxAge)) {
408
409 // RFC 8246: reply contains CC:immutable then ignore client CC:max-age=N
410 if (reply && reply->cache_control && reply->cache_control->hasImmutable()) {
411 debugs(22, 3, "MAYBE: Ignoring client CC:max-age=" << maxAge << " request - 'Cache-Control: immutable'");
412
413#if USE_HTTP_VIOLATIONS
414 // Ignore of client "Cache-Control: max-age=0" header
415 } else if (R->flags.ignore_reload && maxAge == 0) {
416 debugs(22, 3, "MAYBE: Ignoring client reload request - trying to serve from cache (ignore-reload option)");
417#endif
418
419 // Honour client "Cache-Control: max-age=x" header
420 } else if (age > maxAge || maxAge == 0) {
421 debugs(22, 3, "YES: Revalidating object - client 'Cache-Control: max-age=" << maxAge << "'");
423 }
424 }
425
426 // max-stale directive
427 int maxStale = -1;
428 if (cc->hasMaxStale(&maxStale) && staleness > -1) {
429 if (maxStale==HttpHdrCc::MAX_STALE_ANY) {
430 debugs(22, 3, "NO: Client accepts a stale response of any age - 'Cache-Control: max-stale'");
432 } else if (staleness < maxStale) {
433 debugs(22, 3, "NO: Client accepts a stale response - 'Cache-Control: max-stale=" << maxStale << "'");
435 }
436 }
437 }
438 }
439
440 // If the object is fresh, return the right FRESH_ code
441 if (-1 == staleness) {
442 debugs(22, 3, "Object isn't stale..");
443 if (sf.expires) {
444 debugs(22, 3, "returning FRESH_EXPIRES");
445 return FRESH_EXPIRES;
446 }
447
448 assert(!sf.max);
449
450 if (sf.lmfactor) {
451 debugs(22, 3, "returning FRESH_LMFACTOR_RULE");
452 return FRESH_LMFACTOR_RULE;
453 }
454
455 assert(sf.min);
456
457 debugs(22, 3, "returning FRESH_MIN_RULE");
458 return FRESH_MIN_RULE;
459 }
460
461 /*
462 * At this point the response is stale, unless one of
463 * the override options kicks in.
464 * NOTE: max-stale config blocks the overrides.
465 */
466 int max_stale = (R->max_stale >= 0 ? R->max_stale : Config.maxStale);
467 if ( max_stale >= 0 && staleness > max_stale) {
468 debugs(22, 3, "YES: refresh_pattern max-stale=N limit from squid.conf");
469 if (request)
470 request->flags.failOnValidationError = true;
471 return STALE_MAX_STALE;
472 }
473
474 if (sf.expires) {
475#if USE_HTTP_VIOLATIONS
476
477 if (R->flags.override_expire && age < R->min) {
478 debugs(22, 3, "NO: Serving from cache - even though explicit expiry has passed, we enforce Min value (override-expire option)");
480 }
481
482#endif
483 debugs(22, 3, "returning STALE_EXPIRES");
484 return STALE_EXPIRES;
485 }
486
487 if (sf.max) {
488 debugs(22, 3, "returning STALE_MAX_RULE");
489 return STALE_MAX_RULE;
490 }
491
492 if (sf.lmfactor) {
493#if USE_HTTP_VIOLATIONS
494 if (R->flags.override_lastmod && age < R->min) {
495 debugs(22, 3, "NO: Serving from cache - even though L-M factor says the object is stale, we enforce Min value (override-lastmod option)");
497 }
498#endif
499 debugs(22, 3, "YES: L-M factor says the object is stale'");
500 return STALE_LMFACTOR_RULE;
501 }
502
503 debugs(22, 3, "returning STALE_DEFAULT");
504 return STALE_DEFAULT;
505}
506
517bool
519{
520 /*
521 * Don't look at the request to avoid no-cache and other nuisances.
522 * the object should have a mem_obj so the URL will be found there.
523 * minimum_expiry_time seconds delta (defaults to 60 seconds), to
524 * avoid objects which expire almost immediately, and which can't
525 * be refreshed.
526 *
527 * No hittingRequiresCollapsing() or didCollapse concerns here: This
528 * incoming response is fresh now, but we want to check whether it can be
529 * refreshed Config.minimum_expiry_time seconds later.
530 */
531 int reason = refreshCheck(entry, nullptr, Config.minimum_expiry_time);
533 ++ refreshCounts[rcStore].status[reason];
534
535 if (reason < STALE_MUST_REVALIDATE)
536 /* Does not need refresh. This is certainly cachable */
537 return true;
538
539 if (entry->lastModified() < 0)
540 /* We should know entry's modification time to do a refresh */
541 return false;
542
543 if (entry->mem_obj == nullptr)
544 /* no mem_obj? */
545 return true;
546
547 if (entry->mem_obj->baseReply().content_length == 0)
548 /* No use refreshing (caching?) 0 byte objects */
549 return false;
550
551 /* This seems to be refreshable. Cache it */
552 return true;
553}
554
556static bool
557refreshIsStaleIfHit(const int reason)
558{
559 switch (reason) {
560 case FRESH_MIN_RULE:
562 case FRESH_EXPIRES:
563 return false;
564 default:
565 return true;
566 }
567}
568
581int
582refreshCheckHTTP(const StoreEntry * entry, HttpRequest * request)
583{
584 int reason = refreshCheck(entry, request, 0);
586 ++ refreshCounts[rcHTTP].status[reason];
587 request->flags.staleIfHit = refreshIsStaleIfHit(reason);
588 return (Config.onoff.offline || reason < 200) ? 0 : 1;
589}
590
592int
593refreshCheckICP(const StoreEntry * entry, HttpRequest * request)
594{
595 int reason = refreshCheck(entry, request, 30);
597 ++ refreshCounts[rcICP].status[reason];
598 return (reason < 200) ? 0 : 1;
599}
600
601#if USE_HTCP
603int
604refreshCheckHTCP(const StoreEntry * entry, HttpRequest * request)
605{
606 int reason = refreshCheck(entry, request, 10);
608 ++ refreshCounts[rcHTCP].status[reason];
609 return (reason < 200) ? 0 : 1;
610}
611
612#endif
613
614#if USE_CACHE_DIGESTS
616int
617refreshCheckDigest(const StoreEntry * entry, time_t delta)
618{
619 int reason = refreshCheck(entry,
620 entry->mem_obj ? entry->mem_obj->request.getRaw() : nullptr,
621 delta);
623 ++ refreshCounts[rcCDigest].status[reason];
624 return (reason < 200) ? 0 : 1;
625}
626#endif
627
638time_t
639getMaxAge(const char *url)
640{
641 const RefreshPattern *R;
642 debugs(22, 3, "getMaxAge: '" << url << "'");
643
644 if ((R = refreshLimits(url)))
645 return R->max;
646 else
647 return REFRESH_DEFAULT_MAX;
648}
649
650static int
651refreshCountsStatsEntry(StoreEntry * sentry, struct RefreshCounts &rc, int code, const char *desc)
652{
653 storeAppendPrintf(sentry, "%6d\t%6.2f\t%s\n", rc.status[code], xpercent(rc.status[code], rc.total), desc);
654 return rc.status[code];
655}
656
657static void
659{
660 if (!rc.total)
661 return;
662
663 storeAppendPrintf(sentry, "\n\n%s histogram:\n", rc.proto);
664 storeAppendPrintf(sentry, "Count\t%%Total\tCategory\n");
665
666 refreshCountsStatsEntry(sentry, rc, FRESH_REQUEST_MAX_STALE_ALL, "Fresh: request max-stale wildcard");
667 refreshCountsStatsEntry(sentry, rc, FRESH_REQUEST_MAX_STALE_VALUE, "Fresh: request max-stale value");
668 refreshCountsStatsEntry(sentry, rc, FRESH_EXPIRES, "Fresh: expires time not reached");
669 refreshCountsStatsEntry(sentry, rc, FRESH_LMFACTOR_RULE, "Fresh: refresh_pattern last-mod factor percentage");
670 refreshCountsStatsEntry(sentry, rc, FRESH_MIN_RULE, "Fresh: refresh_pattern min value");
671 refreshCountsStatsEntry(sentry, rc, FRESH_OVERRIDE_EXPIRES, "Fresh: refresh_pattern override-expires");
672 refreshCountsStatsEntry(sentry, rc, FRESH_OVERRIDE_LASTMOD, "Fresh: refresh_pattern override-lastmod");
673 refreshCountsStatsEntry(sentry, rc, STALE_MUST_REVALIDATE, "Stale: response has must-revalidate");
674 refreshCountsStatsEntry(sentry, rc, STALE_RELOAD_INTO_IMS, "Stale: changed reload into IMS");
675 refreshCountsStatsEntry(sentry, rc, STALE_FORCED_RELOAD, "Stale: request has no-cache directive");
676 refreshCountsStatsEntry(sentry, rc, STALE_EXCEEDS_REQUEST_MAX_AGE_VALUE, "Stale: age exceeds request max-age value");
677 refreshCountsStatsEntry(sentry, rc, STALE_EXPIRES, "Stale: expires time reached");
678 refreshCountsStatsEntry(sentry, rc, STALE_MAX_RULE, "Stale: refresh_pattern max age rule");
679 refreshCountsStatsEntry(sentry, rc, STALE_LMFACTOR_RULE, "Stale: refresh_pattern last-mod factor percentage");
680 refreshCountsStatsEntry(sentry, rc, STALE_DEFAULT, "Stale: by default");
681 storeAppendPrintf(sentry, "\n");
682}
683
684static void
686{
687 // display per-rule counts of usage and tests
688 storeAppendPrintf(sentry, "\nRefresh pattern usage:\n\n");
689 storeAppendPrintf(sentry, " Used \tChecks \t%% Matches\tPattern\n");
690 for (const RefreshPattern *R = Config.Refresh; R; R = R->next) {
691 storeAppendPrintf(sentry, " %10" PRIu64 "\t%10" PRIu64 "\t%6.2f\t",
692 R->stats.matchCount,
693 R->stats.matchTests,
694 xpercent(R->stats.matchCount, R->stats.matchTests));
695 PackableStream os(*sentry);
696 R->printPattern(os);
697 os << "\n";
698 }
699
700 int i;
701 int total = 0;
702
703 /* get total usage count */
704
705 for (i = 0; i < rcCount; ++i)
706 total += refreshCounts[i].total;
707
708 /* protocol usage histogram */
709 storeAppendPrintf(sentry, "\nRefreshCheck calls per protocol\n\n");
710
711 storeAppendPrintf(sentry, "Protocol\t#Calls\t%%Calls\n");
712
713 for (i = 0; i < rcCount; ++i)
714 storeAppendPrintf(sentry, "%10s\t%6d\t%6.2f\n",
715 refreshCounts[i].proto,
716 refreshCounts[i].total,
717 xpercent(refreshCounts[i].total, total));
718
719 /* per protocol histograms */
720 storeAppendPrintf(sentry, "\n\nRefreshCheck histograms for various protocols\n");
721
722 for (i = 0; i < rcCount; ++i)
724}
725
726const RegexPattern &
728{
729 assert(regex_);
730 return *regex_;
731}
732
733void
734RefreshPattern::printPattern(std::ostream &os) const
735{
736 if (regex_)
737 regex_->print(os, nullptr); // refresh lines do not inherit line flags
738 else
739 os << "<none>";
740}
741
742void
743RefreshPattern::printHead(std::ostream &os) const
744{
745 printPattern(os);
746 os <<
747 // these adjustments are safe: raw values were configured using integers
748 ' ' << intmax_t(min/60) << // to minutes
749 ' ' << intmax_t(100.0 * pct + 0.5) << '%' << // to percentage points
750 ' ' << intmax_t(max/60); // to minutes
751}
752
753static void
755{
756 Mgr::RegisterAction("refresh", "Refresh Algorithm Statistics", refreshStats, 0, 1);
757}
758
759void
761{
762 memset(refreshCounts, 0, sizeof(refreshCounts));
763 refreshCounts[rcHTTP].proto = "HTTP";
764 refreshCounts[rcICP].proto = "ICP";
765#if USE_HTCP
766
767 refreshCounts[rcHTCP].proto = "HTCP";
768#endif
769
770 refreshCounts[rcStore].proto = "On Store";
771#if USE_CACHE_DIGESTS
772
773 refreshCounts[rcCDigest].proto = "Cache Digests";
774#endif
775
777}
778
time_t squid_curtime
#define REFRESH_DEFAULT_MAX
class SquidConfig Config
#define assert(EX)
Definition assert.h:17
bool hasMaxStale(int32_t *val=nullptr) const
Definition HttpHdrCc.h:132
bool hasMinFresh(int32_t *val=nullptr) const
Definition HttpHdrCc.h:140
static const int32_t MAX_STALE_ANY
Definition HttpHdrCc.h:53
bool hasMaxAge(int32_t *val=nullptr) const
Definition HttpHdrCc.h:122
bool hasStaleIfError(int32_t *val=nullptr) const
Definition HttpHdrCc.h:150
RequestFlags flags
const SBuf & effectiveRequestUri() const
RFC 7230 section 5.5 - Effective Request URI.
int64_t content_length
Definition Message.h:83
HttpHdrCc * cache_control
Definition Message.h:76
HttpRequestPointer request
Definition MemObject.h:205
const char * storeId() const
Definition MemObject.cc:53
const HttpReply & baseReply() const
Definition MemObject.h:60
C * getRaw() const
Definition RefCount.h:89
a representation of a refresh pattern.
struct RefreshPattern::@72 flags
void printPattern(std::ostream &os) const
reports the configured pattern or a fake pattern of the implicit rule
Definition refresh.cc:734
const RegexPattern & regex() const
configured regex; do not use except when iterating configured rules
Definition refresh.cc:727
RegexPointer regex_
configured regex or, for the implicit refresh_pattern rule, nil
void printHead(std::ostream &) const
reports configuration excluding trailing options
Definition refresh.cc:743
bool noCacheHack() const
bool failOnValidationError
Definition SBuf.h:94
const char * c_str()
Definition SBuf.cc:516
int reload_into_ims
RefreshPattern * Refresh
struct SquidConfig::@90 onoff
time_t maxStale
time_t minimum_expiry_time
int refresh_all_ims
uint16_t flags
Definition Store.h:231
time_t expires
Definition Store.h:225
void lastModified(const time_t when)
Definition Store.h:175
time_t timestamp
Definition Store.h:223
MemObject * mem_obj
Definition Store.h:220
const HttpReply * hasFreshestReply() const
Definition Store.h:53
A const & min(A const &lhs, A const &rhs)
#define debugs(SECTION, LEVEL, CONTENT)
Definition Stream.h:192
#define EBIT_TEST(flag, bit)
Definition defines.h:67
@ ENTRY_REVALIDATE_STALE
Definition enums.h:95
@ ENTRY_REVALIDATE_ALWAYS
Definition enums.h:80
void OBJH(StoreEntry *)
Definition forward.h:44
void RegisterAction(char const *action, char const *desc, OBJH *handler, Protected, Atomic, Format)
const char * FormatRfc1123(time_t)
Definition rfc1123.cc:202
time_t getMaxAge(const char *url)
Definition refresh.cc:639
static int refreshCountsStatsEntry(StoreEntry *sentry, struct RefreshCounts &rc, int code, const char *desc)
Definition refresh.cc:651
const RefreshPattern * refreshLimits(const char *url)
Definition refresh.cc:92
void refreshInit(void)
Definition refresh.cc:760
int refreshCheckHTCP(const StoreEntry *entry, HttpRequest *request)
Definition refresh.cc:604
static struct RefreshCounts refreshCounts[rcCount]
static int refreshCheck(const StoreEntry *entry, HttpRequest *request, time_t delta)
Definition refresh.cc:253
static void refreshCountsStats(StoreEntry *sentry, struct RefreshCounts &rc)
Definition refresh.cc:658
static int refreshStaleness(const StoreEntry *entry, time_t check_time, const time_t age, const RefreshPattern *R, stale_flags *sf)
Definition refresh.cc:139
int refreshCheckICP(const StoreEntry *entry, HttpRequest *request)
Definition refresh.cc:593
@ STALE_FORCED_RELOAD
Definition refresh.cc:67
@ FRESH_OVERRIDE_EXPIRES
Definition refresh.cc:63
@ STALE_MAX_STALE
Definition refresh.cc:72
@ FRESH_REQUEST_MAX_STALE_ALL
Definition refresh.cc:58
@ STALE_RELOAD_INTO_IMS
Definition refresh.cc:66
@ FRESH_EXPIRES
Definition refresh.cc:60
@ STALE_EXCEEDS_REQUEST_MAX_AGE_VALUE
Definition refresh.cc:68
@ FRESH_REQUEST_MAX_STALE_VALUE
Definition refresh.cc:59
@ FRESH_MIN_RULE
Definition refresh.cc:62
@ STALE_LMFACTOR_RULE
Definition refresh.cc:71
@ STALE_MUST_REVALIDATE
Definition refresh.cc:65
@ FRESH_LMFACTOR_RULE
Definition refresh.cc:61
@ STALE_MAX_RULE
Definition refresh.cc:70
@ STALE_EXPIRES
Definition refresh.cc:69
@ FRESH_OVERRIDE_LASTMOD
Definition refresh.cc:64
@ STALE_DEFAULT
Definition refresh.cc:73
static OBJH refreshStats
Definition refresh.cc:82
bool refreshIsCachable(const StoreEntry *entry)
Definition refresh.cc:518
refreshCountsEnum
Definition refresh.cc:28
@ rcHTCP
Definition refresh.cc:32
@ rcStore
Definition refresh.cc:37
@ rcCDigest
Definition refresh.cc:35
@ rcCount
Definition refresh.cc:38
@ rcHTTP
Definition refresh.cc:29
@ rcICP
Definition refresh.cc:30
static bool refreshIsStaleIfHit(const int reason)
whether reply is stale if it is a hit
Definition refresh.cc:557
int refreshCheckDigest(const StoreEntry *entry, time_t delta)
Definition refresh.cc:617
static void refreshRegisterWithCacheManager(void)
Definition refresh.cc:754
static RefreshPattern DefaultRefresh(nullptr)
int refreshCheckHTTP(const StoreEntry *entry, HttpRequest *request)
Definition refresh.cc:582
static const RefreshPattern * refreshFirstDotRule()
the first explicit refresh_pattern rule that uses a "." regex (or nil)
Definition refresh.cc:107
void storeAppendPrintf(StoreEntry *e, const char *fmt,...)
Definition store.cc:855
const char * proto
Definition refresh.cc:77
int status[STALE_DEFAULT+1]
Definition refresh.cc:79
bool expires
Expires: header absolute timestamp limit.
Definition refresh.cc:45
bool lmfactor
Last-Modified with heuristic determines limit.
Definition refresh.cc:47
bool max
Configured maximum age limit.
Definition refresh.cc:48
bool min
Heuristic minimum age limited.
Definition refresh.cc:46
#define PRIu64
Definition types.h:114
double xpercent(double part, double whole)
Definition util.cc:40