#include <libknot/libknot.h>
-// TODO this is just an example, make this more clever
-category_t kr_gc_categorize(gc_record_info_t *info)
+static bool rrtype_is_infrastructure(uint16_t r)
{
- category_t res = 60;
-
- switch (info->rrtype) {
+ switch (r) {
case KNOT_RRTYPE_NS:
case KNOT_RRTYPE_DS:
case KNOT_RRTYPE_DNSKEY:
case KNOT_RRTYPE_A:
case KNOT_RRTYPE_AAAA:
+ return true;
+ default:
+ return false;
+ }
+}
+
+// TODO this is just an example, make this more clever
+category_t kr_gc_categorize(gc_record_info_t *info)
+{
+ category_t res = 60;
+
+ switch (info->no_labels) {
+ case 0:
+ return 1;
+ case 1:
+ return 2;
+ case 2:
+ return (rrtype_is_infrastructure(info->rrtype) ? 3 : 20);
+ }
+
+ if (info->entry_size > 300) {
+ return 90;
+ }
+
+ if (rrtype_is_infrastructure(info->rrtype)) {
if (info->expires_in > 0) {
res = 30;
} else {
res = 45;
}
- break;
}
return res;
#include <lib/cache/impl.h>
//#include <lib/defines.h>
+#include <time.h>
#include <sys/stat.h>
struct libknot_lmdb_env
knot_db_iter_t *it = NULL;
const knot_db_api_t *api = knot_db_lmdb_api();
gc_record_info_t info = { 0 };
- // TODO remove and use time(NULL) ! this is just for debug with pre-generated cache
- int64_t now = 1524301784;
+ int64_t now = time(NULL);
int ret = api->txn_begin(knot_db, &txn, KNOT_DB_RDONLY);
if (ret != KNOT_EOK) {
#include "categories.h"
#include "db.h"
+#define MAX_OK_PERCENT_USAGE 80.0
+#define TO_BE_FREED_PERCENT 10.0
+
// section: timer
// TODO replace/move to contrib
typedef struct {
size_t categories_sizes[CATEGORIES];
+ size_t records;
} ctx_compute_categories_t;
int cb_compute_categories(const knot_db_val_t *key, gc_record_info_t *info, void *vctx)
category_t cat = kr_gc_categorize(info);
(void)key;
ctx->categories_sizes[cat] += info->entry_size;
+ ctx->records++;
return KNOT_EOK;
}
return ret;
}
+ if (db_usage < MAX_OK_PERCENT_USAGE) {
+ kr_gc_cache_close(&kres_db, db);
+ return KNOT_EOK;
+ }
+
gc_timer_t timer_analyze = { 0 }, timer_choose = { 0 }, timer_delete = { 0 }, timer_rw_txn = { 0 };
gc_timer_start(&timer_analyze);
return ret;
}
- category_t limit_category = 50; // TODO fix this computation
- printf("Cache analyzed in %.2lf secs, limit category is %d.\n", gc_timer_end(&timer_analyze), limit_category);
+ ssize_t amount_tofree = (double)knot_db_lmdb_get_mapsize(db) * TO_BE_FREED_PERCENT / 100.0;
+
+ // debug
+ /*printf("tofree: %zd\n", amount_tofree);
+ for (int i = 0; i < CATEGORIES; i++) {
+ if (cats.categories_sizes[i] > 0) {
+ printf("category %d size %zu\n", i, cats.categories_sizes[i]);
+ }
+ }*/
+
+ category_t limit_category = CATEGORIES;
+ while (limit_category > 0 && amount_tofree > 0) {
+ amount_tofree -= cats.categories_sizes[--limit_category];
+ }
+
+ printf("Cache analyzed in %.2lf secs, %zu records, limit category is %d.\n", gc_timer_end(&timer_analyze), cats.records, limit_category);
gc_timer_start(&timer_choose);
ctx_delete_categories_t to_del = { 0 };