Lines Matching +full:cache +full:- +full:to
2 * libwebsockets - small server side websockets and web server implementation
4 * Copyright (C) 2010 - 2021 Andy Green <andy@warmcat.com>
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to
9 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10 * sell copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25 #include <private-lib-core.h>
26 #include "private-lib-misc-cache-ttl.h"
33 update_sul(lws_cache_ttl_lru_t_heap_t *cache);
45 if (c->expiry > d->expiry) in sort_expiry()
47 if (c->expiry < d->expiry) in sort_expiry()
48 return -1; in sort_expiry()
54 _lws_cache_heap_item_destroy(lws_cache_ttl_lru_t_heap_t *cache, in _lws_cache_heap_item_destroy() argument
57 lwsl_cache("%s: %s (%s)\n", __func__, cache->cache.info.name, in _lws_cache_heap_item_destroy()
58 (const char *)&item[1] + item->size); in _lws_cache_heap_item_destroy()
60 lws_dll2_remove(&item->list_expiry); in _lws_cache_heap_item_destroy()
61 lws_dll2_remove(&item->list_lru); in _lws_cache_heap_item_destroy()
63 cache->cache.current_footprint -= item->size; in _lws_cache_heap_item_destroy()
65 update_sul(cache); in _lws_cache_heap_item_destroy()
67 if (cache->cache.info.cb) in _lws_cache_heap_item_destroy()
68 cache->cache.info.cb((void *)((uint8_t *)&item[1]), item->size); in _lws_cache_heap_item_destroy()
74 lws_cache_heap_item_destroy(lws_cache_ttl_lru_t_heap_t *cache, in lws_cache_heap_item_destroy() argument
77 struct lws_cache_ttl_lru *backing = &cache->cache; in lws_cache_heap_item_destroy()
78 const char *tag = ((const char *)&item[1]) + item->size; in lws_cache_heap_item_destroy()
85 /* no, nothing to check here then */ in lws_cache_heap_item_destroy()
88 if (backing->info.parent) in lws_cache_heap_item_destroy()
89 backing = backing->info.parent; in lws_cache_heap_item_destroy()
92 * We need to check any cached meta-results from lookups that in lws_cache_heap_item_destroy()
93 * include this normal item, and if any, invalidate the meta-results in lws_cache_heap_item_destroy()
94 * since they have to be recalculated before being used again. in lws_cache_heap_item_destroy()
98 cache->items_lru.head) { in lws_cache_heap_item_destroy()
102 const char *iname = ((const char *)&item[1]) + item->size; in lws_cache_heap_item_destroy()
103 uint8_t *pay = (uint8_t *)&item[1], *end = pay + item->size; in lws_cache_heap_item_destroy()
109 * If the item about to be destroyed makes an in lws_cache_heap_item_destroy()
111 * the meta result item to force recalc next time in lws_cache_heap_item_destroy()
126 assert (!backing->info.ops->tag_match( in lws_cache_heap_item_destroy()
129 _lws_cache_heap_item_destroy(cache, i); in lws_cache_heap_item_destroy()
141 assert (backing->info.ops->tag_match(backing, iname + 1, in lws_cache_heap_item_destroy()
149 _lws_cache_heap_item_destroy(cache, item); in lws_cache_heap_item_destroy()
153 lws_cache_item_evict_lru(lws_cache_ttl_lru_t_heap_t *cache) in lws_cache_item_evict_lru() argument
157 if (!cache->items_lru.head) in lws_cache_item_evict_lru()
160 ei = lws_container_of(cache->items_lru.head, in lws_cache_item_evict_lru()
163 lws_cache_heap_item_destroy(cache, ei, 0); in lws_cache_item_evict_lru()
167 * We need to weed out expired entries in the backing file
173 lws_cache_ttl_lru_t_heap_t *cache = lws_container_of(sul, in expiry_cb() local
174 lws_cache_ttl_lru_t_heap_t, cache.sul); in expiry_cb()
177 lwsl_cache("%s: %s\n", __func__, cache->cache.info.name); in expiry_cb()
179 while (cache->items_expiry.head) { in expiry_cb()
182 item = lws_container_of(cache->items_expiry.head, in expiry_cb()
185 if (item->expiry > now) in expiry_cb()
188 lws_cache_heap_item_destroy(cache, item, 1); in expiry_cb()
197 earliest_expiry(lws_cache_ttl_lru_t_heap_t *cache, lws_usec_t *pearliest) in earliest_expiry() argument
201 if (!cache->items_expiry.head) in earliest_expiry()
204 item = lws_container_of(cache->items_expiry.head, in earliest_expiry()
207 *pearliest = item->expiry; in earliest_expiry()
213 update_sul(lws_cache_ttl_lru_t_heap_t *cache) in update_sul() argument
217 /* weed out any newly-expired */ in update_sul()
218 expiry_cb(&cache->cache.sul); in update_sul()
221 if (earliest_expiry(cache, &earliest)) { in update_sul()
222 lws_sul_cancel(&cache->cache.sul); in update_sul()
230 lws_cache_schedule(&cache->cache, expiry_cb, earliest); in update_sul()
234 lws_cache_heap_specific(lws_cache_ttl_lru_t_heap_t *cache, in lws_cache_heap_specific() argument
237 lws_start_foreach_dll(struct lws_dll2 *, d, cache->items_lru.head) { in lws_cache_heap_specific()
241 const char *iname = ((const char *)&item[1]) + item->size; in lws_cache_heap_specific()
252 lws_cache_heap_tag_match(struct lws_cache_ttl_lru *cache, const char *wc, in lws_cache_heap_tag_match() argument
262 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_lookup() local
265 lws_start_foreach_dll(struct lws_dll2 *, d, cache->items_lru.head) { in lws_cache_heap_lookup()
269 const char *iname = ((const char *)&item[1]) + item->size; in lws_cache_heap_lookup()
279 * cache level in lws_cache_heap_lookup()
283 results_owner->head) { in lws_cache_heap_lookup()
286 if (i->tag_size == ilen && in lws_cache_heap_lookup()
299 m = lws_fi(&_c->info.cx->fic, in lws_cache_heap_lookup()
308 memset(&m->list, 0, sizeof(m->list)); in lws_cache_heap_lookup()
309 m->tag_size = ilen; in lws_cache_heap_lookup()
312 lws_dll2_add_tail(&m->list, results_owner); in lws_cache_heap_lookup()
326 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_write() local
332 lwsl_cache("%s: %s: len %d\n", __func__, _c->info.name, (int)size); in lws_cache_heap_write()
335 * Is this new tag going to invalidate any existing cached meta-results? in lws_cache_heap_write()
337 * If so, let's destroy any of those first to recover the heap in lws_cache_heap_write()
340 if (backing->info.parent) in lws_cache_heap_write()
341 backing = backing->info.parent; in lws_cache_heap_write()
344 cache->items_lru.head) { in lws_cache_heap_write()
348 const char *iname = ((const char *)&i[1]) + i->size; in lws_cache_heap_write()
353 * If the item about to be added would match any cached in lws_cache_heap_write()
354 * results from before it was added, we have to in lws_cache_heap_write()
355 * invalidate them. To check this, we have to use the in lws_cache_heap_write()
360 _lws_cache_heap_item_destroy(cache, i); in lws_cache_heap_write()
371 while ((cache->cache.info.max_footprint && in lws_cache_heap_write()
372 cache->cache.current_footprint + size > in lws_cache_heap_write()
373 cache->cache.info.max_footprint) || in lws_cache_heap_write()
374 (cache->cache.info.max_items && in lws_cache_heap_write()
375 cache->items_lru.count + 1 > cache->cache.info.max_items)) in lws_cache_heap_write()
376 lws_cache_item_evict_lru(cache); in lws_cache_heap_write()
380 lws_cache_heap_invalidate(&cache->cache, specific_key); in lws_cache_heap_write()
382 item = lws_fi(&_c->info.cx->fic, "cache_write_oom") ? NULL : in lws_cache_heap_write()
387 cache->cache.current_footprint += item->size; in lws_cache_heap_write()
389 /* only need to zero down our item object */ in lws_cache_heap_write()
403 item->expiry = expiry; in lws_cache_heap_write()
404 item->key_len = kl; in lws_cache_heap_write()
405 item->size = size; in lws_cache_heap_write()
408 /* adding to expiry is optional, on nonzero expiry */ in lws_cache_heap_write()
409 lws_dll2_add_sorted(&item->list_expiry, &cache->items_expiry, in lws_cache_heap_write()
411 ei = lws_container_of(cache->items_expiry.head, in lws_cache_heap_write()
414 (unsigned long long)ei->expiry); in lws_cache_heap_write()
415 lws_cache_schedule(&cache->cache, expiry_cb, ei->expiry); in lws_cache_heap_write()
418 /* always add outselves to head of lru list */ in lws_cache_heap_write()
419 lws_dll2_add_head(&item->list_lru, &cache->items_lru); in lws_cache_heap_write()
428 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_get() local
431 item = lws_cache_heap_specific(cache, specific_key); in lws_cache_heap_get()
435 /* we are using it, move it to lru head */ in lws_cache_heap_get()
436 lws_dll2_remove(&item->list_lru); in lws_cache_heap_get()
437 lws_dll2_add_head(&item->list_lru, &cache->items_lru); in lws_cache_heap_get()
441 *psize = item->size; in lws_cache_heap_get()
450 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_invalidate() local
459 if (backing->info.parent) in lws_cache_heap_invalidate()
460 backing = backing->info.parent; in lws_cache_heap_invalidate()
462 item = (lws_cache_ttl_item_heap_t *)(((uint8_t *)user) - sizeof(*item)); in lws_cache_heap_invalidate()
469 cache->items_lru.head) { in lws_cache_heap_invalidate()
473 const char *iname = ((const char *)&i[1]) + i->size; in lws_cache_heap_invalidate()
478 * If the item about to be added would match any cached in lws_cache_heap_invalidate()
479 * results from before it was added, we have to in lws_cache_heap_invalidate()
480 * invalidate them. To check this, we have to use the in lws_cache_heap_invalidate()
484 if (!backing->info.ops->tag_match(backing, iname + 1, in lws_cache_heap_invalidate()
486 _lws_cache_heap_item_destroy(cache, i); in lws_cache_heap_invalidate()
491 lws_cache_heap_item_destroy(cache, item, 0); in lws_cache_heap_invalidate()
499 lws_cache_ttl_lru_t_heap_t *cache; in lws_cache_heap_create() local
501 assert(info->cx); in lws_cache_heap_create()
502 assert(info->name); in lws_cache_heap_create()
504 cache = lws_fi(&info->cx->fic, "cache_createfail") ? NULL : in lws_cache_heap_create()
505 lws_zalloc(sizeof(*cache), __func__); in lws_cache_heap_create()
506 if (!cache) in lws_cache_heap_create()
509 cache->cache.info = *info; in lws_cache_heap_create()
510 if (info->parent) in lws_cache_heap_create()
511 info->parent->child = &cache->cache; in lws_cache_heap_create()
513 // lwsl_cache("%s: create %s\n", __func__, info->name); in lws_cache_heap_create()
515 return (struct lws_cache_ttl_lru *)cache; in lws_cache_heap_create()
522 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in destroy_dll() local
526 lws_cache_heap_item_destroy(cache, item, 0); in destroy_dll()
534 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_expunge() local
536 lws_dll2_foreach_safe(&cache->items_lru, cache, destroy_dll); in lws_cache_heap_expunge()
545 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)c; in lws_cache_heap_destroy() local
547 if (!cache) in lws_cache_heap_destroy()
550 lws_sul_cancel(&c->sul); in lws_cache_heap_destroy()
552 lws_dll2_foreach_safe(&cache->items_lru, cache, destroy_dll); in lws_cache_heap_destroy()
565 (const char *)&item[1] + item->size, in dump_dll()
566 (int)item->size, (unsigned long long)item->expiry); in dump_dll()
568 lwsl_hexdump_cache((const char *)&item[1], item->size); in dump_dll()
576 lws_cache_ttl_lru_t_heap_t *cache = (lws_cache_ttl_lru_t_heap_t *)_c; in lws_cache_heap_debug_dump() local
580 lws_dll2_t *d = cache->items_expiry.head; in lws_cache_heap_debug_dump()
587 cache->cache.info.name, (int)cache->items_lru.count, in lws_cache_heap_debug_dump()
588 item ? (unsigned long long)item->expiry : 0ull); in lws_cache_heap_debug_dump()
591 lws_dll2_foreach_safe(&cache->items_lru, cache, dump_dll); in lws_cache_heap_debug_dump()