void test_basics() { cache_t cache = create_cache(65536, NULL); uint32_t val_size = 0; const uint8_t *key1 = (uint8_t*)"One key", *key2 = (uint8_t*)"Two key", *key3 = (uint8_t*)"Red key"; uint8_t *value1 = (uint8_t*) "First value"; uint64_t value2 = 20039; int32_t value3 = -12; cache_set(cache, key1, value1, strlen((char *)value1) + 1); cache_set(cache, key2, &value2, sizeof(value2)); cache_set(cache, key3, &value3, sizeof(value3)); uint8_t *result1 = (uint8_t *)cache_get(cache, key1, &val_size); uint64_t *result2 = (uint64_t *)cache_get(cache, key2, &val_size); int32_t *result3 = (int32_t *)cache_get(cache, key3, &val_size); bool results_not_null = result1 != NULL && result2 != NULL && result3 != NULL; bool string_result_correct = strcmp((const char*)value1, (const char*)result1) == 0; bool uint64_result_correct = *result2 == value2; bool int32_result_correct = *result3 == value3; test(results_not_null, "Get returns non null pointers when retrieving valid entries."); test(string_result_correct, "Cache can store and retrieve strings"); test(uint64_result_correct, "Cache can store and retrieve uint64_t integers correctly."); test(int32_result_correct, "Cache can store and retrieve int32_t integers correctly."); test(val_size == sizeof(value3), "cache_get sets val_size pointer to value size."); destroy_cache(cache); }
void test_LRU(){ cache_t cache = create_cache_fake(16*DATASIZE); data_t data1 = create_data(1,(DATATYPE)"123456789012345678901234567890123",8*DATASIZE); data_t data2 = create_data(2,(DATATYPE)"223456789012345678901234567890123",8*DATASIZE); data_t data3 = create_data(3,(DATATYPE)"111",DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); cache_set(cache,data2->key,data2->value,data2->value_size); //Get key1 to put it to the front of the linked_list cache_get(cache,data1->key,data1->value_size_ptr); //Set key3 to evict key2 cache_set(cache,data3->key,data3->value,data3->value_size); data_existence_test(cache,data3); //key1 is supposed to be kept data_existence_test(cache,data1); //key2 is supposed to be evicted already data_nonexistence_test(cache, data2); test_destroy_cache(cache); destroy_data(data1); destroy_data(data2); destroy_data(data3); }
handle_t alloc_blk(ALLOC * a, void *buf, size_t len) { handle_t h = _alloc_blk(a, buf, len); if (h != 0) cache_set(a, h, buf, len); return h; }
int realloc_blk(ALLOC * a, handle_t handle, void *buf, size_t len) { int ret = _realloc_blk(a, handle, buf, len); if (ret == 0) cache_set(a, handle, buf, len); return ret; }
static bool_t svcudp_reply( register SVCXPRT *xprt, struct rpc_msg *msg) { register struct svcudp_data *su = su_data(xprt); register XDR *xdrs = &(su->su_xdrs); register int slen; register bool_t stat = FALSE; xdrs->x_op = XDR_ENCODE; XDR_SETPOS(xdrs, 0); msg->rm_xid = su->su_xid; if (xdr_replymsg(xdrs, msg)) { slen = (int)XDR_GETPOS(xdrs); if (sendto(xprt->xp_sock, rpc_buffer(xprt), slen, 0, (struct sockaddr *)&(xprt->xp_raddr), xprt->xp_addrlen) == (ssize_t)slen) { stat = TRUE; if (su->su_cache) { cache_set(xprt, (unsigned long) slen); } } } return (stat); }
void test_gets(uint8_t* keys, uint32_t* values, uint64_t numpairs) { cache_t cache = create_cache(numpairs*10); char **keystrings = calloc(numpairs,sizeof(char*)); char **valstrings = calloc(numpairs,sizeof(char*)); for(int i = 0; i < numpairs; ++i) { keystrings[i] = calloc(keys[i],1); valstrings[i] = calloc(values[i],1); memset(keystrings[i],'K',keys[i]); memset(valstrings[i],'V',values[i]); keystrings[i][keys[i] - 1] = '\0'; valstrings[i][values[i] - 1] = '\0'; cache_set(cache,keystrings[i],valstrings[i],values[i]); free(valstrings[i]); } free(valstrings); uint32_t val_size = 0; // Get the timebase info // mach_timebase_info_data_t info; // mach_timebase_info(&info); uint64_t errors = 0; const uint64_t requests = numpairs; const double nsToSec = 1000000000; const uint32_t nsToms = 1000000; // uint64_t start = mach_absolute_time(); struct timespec start, end; clock_gettime(CLOCK_MONOTONIC,&start); for(int i = 0; i < requests; ++i) { if( cache_get(cache,keystrings[i],&val_size) == -1) ++errors; //if( val_size == 0) ++errors; //val_size = 0; } // uint64_t end = mach_absolute_time(); clock_gettime(CLOCK_MONOTONIC,&end); // uint64_t duration = end - start; uint64_t duration = (end.tv_sec * nsToSec + end.tv_nsec) - (start.tv_sec * nsToSec + start.tv_nsec); // Convert to nanoseconds // duration *= info.numer; // duration /= info.denom; uint64_t ns = duration; double time_elapsed_sec = (double) duration / nsToSec; double requests_per_second = (double) requests / time_elapsed_sec; double ms = (double) ns / (requests * nsToms); printf("Time per Get: %f milliseconds\n",ms); printf("Requests per second: %f requests\n",requests_per_second); printf("Percent of Requests that failed: %f,%d,%d\n",((double)errors/requests),errors,requests); destroy_cache(cache); }
static bool_t svc_dg_reply(SVCXPRT *xprt, struct rpc_msg *msg) { struct svc_dg_data *su; XDR *xdrs; bool_t stat = FALSE; size_t slen; _DIAGASSERT(xprt != NULL); _DIAGASSERT(msg != NULL); su = su_data(xprt); xdrs = &(su->su_xdrs); xdrs->x_op = XDR_ENCODE; XDR_SETPOS(xdrs, 0); msg->rm_xid = su->su_xid; if (xdr_replymsg(xdrs, msg)) { slen = XDR_GETPOS(xdrs); if (sendto(xprt->xp_fd, rpc_buffer(xprt), slen, 0, (struct sockaddr *)xprt->xp_rtaddr.buf, (socklen_t)xprt->xp_rtaddr.len) == (ssize_t) slen) { stat = TRUE; if (su->su_cache) cache_set(xprt, slen); } } return (stat); }
int main(int argc,char **argv) { int i; char *x; char *y; unsigned int u; uint32 ttl; if (!cache_init(200)) _exit(111); if (*argv) ++argv; while (x = *argv++) { i = str_chr(x,':'); if (x[i]) cache_set(x,i,x + i + 1,str_len(x) - i - 1,86400,0); else { y = cache_get(x,i,&u,&ttl,0); if (y) buffer_put(buffer_1,y,u); buffer_puts(buffer_1,"\n"); } } buffer_flush(buffer_1); _exit(0); }
bool is_up_to_date (url dir) { string name_dir= concretize (dir); if (cache_valid->contains (name_dir)) return cache_valid [name_dir]; int l= last_modified (dir, false); if (is_cached ("validate_cache.scm", name_dir)) { int r= as_int (cache_get ("validate_cache.scm", name_dir) -> label); if (l == r) { cache_valid (name_dir)= true; return true; } //cout << name_dir << " no longer up to date " << r << " -> " << l << "\n"; } //else cout << name_dir << " not up to date " << l << "\n"; cache_set ("validate_cache.scm", name_dir, as_string (l)); cache_valid (name_dir)= false; // FIXME: we should explicitly remove all data concerning files in 'dir' // from the various caches. Indeed, at a next run of TeXmacs, the directory // will be regarded as up to date, but the other caches may still contain // outdated data. Careful: invalidating the cache lines should not // give rise to a performance penaly (e.g. go through all entries of // 'cache_data', or reloading unchanged files many times). // See also 'declare_out_of_date'. return false; }
void packet_init(uint8_t address, uint8_t broadcast) { locladr = address; broadcastadr = broadcast; cache_init(); cache_set(locladr, IFACE_LOCAL); }
// gadget cache copy (both cache must have the same size) struct cache_t *cache_copy (struct cache_t *dest, struct cache_t *src) { int idx_cache; int dest_capacity, src_capacity; void *copied, *cached; // check parameters if ((!dest || !src) || (src == dest)) { fprintf(stderr, "error: cache_copy(): Bad parameters\n"); return NULL; } // cache must be of same sizes dest_capacity = cache_get_capacity(dest); src_capacity = cache_get_capacity(src); if (dest_capacity != src_capacity) { fprintf(stderr, "error: cache_copy(): dest and src are not of the same size\n"); return NULL; } // copy cache for (idx_cache = 0; idx_cache < cache_get_size(src); idx_cache++) { // copying cached = cache_get (src, idx_cache); cache_set (dest, idx_cache, copied); } dest->used = src->used; return dest; }
//Test when there is a hash_collision void test_hash_collision(){ cache_t cache = create_cache_hash_fake(16*DATASIZE,hash_customized); data_t data1 = create_data(1,(DATATYPE)"111",DATASIZE); data_t data2 = create_data(2,(DATATYPE)"222",DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); cache_set(cache,data2->key,data2->value,data2->value_size); data_existence_test(cache,data1); data_existence_test(cache,data2); test_destroy_cache(cache); destroy_data(data1); destroy_data(data2); }
/* Perform various actions on a cache and check it's statistics. */ int main() { cache_t cache = CACHE_INIT; char *data; char *data1 = "data1"; size_t dlen; uint8_t i; char *key1 = "key1"; uint32_t ttl; if (!cache_init(&cache, 512)) return 1; for (i = 1; i < UINT8_MAX; i++) { cache_set(&cache, key1, strlen(key1), data1, strlen(data1), CACHE_MAX_TTL); } cache_get(&cache, key1, strlen(key1), &dlen, &ttl); if (cache.stats.get != 1) return 2; if (cache.stats.set != 254) return 3; if (cache.stats.motion != (CACHE_HEADER_SIZE + 9) * cache.stats.set) return 4; cache_free(&cache); return 0; }
url resolve_tex (url name) { string s= as_string (name); if (is_cached ("font_cache.scm", s)) { url u= url_system (cache_get ("font_cache.scm", s) -> label); if (exists (u)) return u; cache_reset ("font_cache.scm", s); } bench_start ("resolve tex"); url u= url_none (); if (ends (s, "mf" )) { u= resolve_tfm (name); #ifdef OS_WIN32 if (is_none (u)) u= resolve_tfm (replace (s, ".mf", ".tfm")); #endif } if (ends (s, "tfm")) u= resolve_tfm (name); if (ends (s, "pk" )) u= resolve_pk (name); if (ends (s, "pfb")) u= resolve_pfb (name); bench_cumul ("resolve tex"); if (!is_none (u)) cache_set ("font_cache.scm", s, as_string (u)); //cout << "Resolve " << name << " -> " << u << "\n"; return u; }
void declare_out_of_date (url dir) { //cout << "out of date: " << dir << "\n"; string name_dir= concretize (dir); int l= last_modified (dir, false); cache_set ("validate_cache.scm", name_dir, as_string (l)); cache_valid (name_dir)= false; // FIXME: see 'FIXME' in 'is_up_to_date'. }
//Test when query for a key that was evicted; void test_key_evicted(){ cache_t cache = create_cache_fake(16*DATASIZE); data_t data1 = create_data(1,(DATATYPE)"1234567890123456789012345678901234567890123456789012345678901234567890123",16*DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); data_existence_test(cache,data1); //Add a new data to evict the original one data_t data2 = create_data(17,(DATATYPE)"000",DATASIZE); cache_set(cache,data2->key,data2->value,data2->value_size); data_existence_test(cache,data2); //The original data should have been evicted data_nonexistence_test(cache, data1); test_destroy_cache(cache); destroy_data(data1); destroy_data(data2); }
//Test when query for a key that was already inserted; void test_key_inserted(){ cache_t cache = create_cache_fake(16*DATASIZE); data_t data1 = create_data(1,(DATATYPE)"111",DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); data_existence_test(cache,data1); test_destroy_cache(cache); destroy_data(data1); }
bool http_t::cache_load() { FILE* file = fopen( url_cache_file, "rb" ); if ( file ) { double version; uint32_t num_records, max_size; if ( fread( &version, sizeof( double ), 1, file ) && fread( &num_records, sizeof( uint32_t ), 1, file ) && fread( &max_size, sizeof( uint32_t ), 1, file ) ) { if ( version == url_cache_version ) { std::string url, result; char* buffer = new char[ max_size+1 ]; for ( unsigned i=0; i < num_records; i++ ) { int64_t timestamp; uint32_t url_size, result_size; if ( fread( ×tamp, sizeof( int64_t ), 1, file ) && fread( &url_size, sizeof( uint32_t ), 1, file ) && fread( &result_size, sizeof( uint32_t ), 1, file ) ) { assert( url_size > 0 && result_size > 0 ); if ( fread( buffer, sizeof( char ), url_size, file ) ) { buffer[ url_size ] = '\0'; url = buffer; } else break; if ( fread( buffer, sizeof( char ), result_size, file ) ) { buffer[ result_size ] = '\0'; result = buffer; } else break; cache_set( url, result, timestamp ); } else break; } delete[] buffer; } } fclose( file ); } return true; }
//Test when query for a key that was inserted and modified; void test_key_modified(){ cache_t cache = create_cache_fake(16*DATASIZE); data_t data1 = create_data(1,(DATATYPE)"111",DATASIZE); data_t data2 = create_data(1,(DATATYPE)"222",DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); data_existence_test(cache,data1); //modify the value with the original key cache_set(cache,data2->key,data2->value,data2->value_size); data_existence_test(cache,data2); //We are supposed to retrive the new value val_type retrived_value = cache_get(cache,data1->key,data1->value_size_ptr); assert((DATATYPE)(retrived_value)!=data1->value&&"retrived value is incorrect"); test_destroy_cache(cache); destroy_data(data1); destroy_data(data2); }
//Checks if a custom hash at least doesn't crash the cache (since some didn't have this customization) //Sets a value with the custome hash and gets it to see if it was set properly void custom_hash() { uint8_t key[2] = {'a', '\0'}; uint8_t value[6] = "12345"; uint32_t val_size = 0; cache_t cache = create_cache(100 * sizeof(value)); cache_set(cache, key, value, sizeof(value)); uint8_t *ret = (uint8_t*)cache_get(cache, key, &val_size); test(!strcmp(key,"12345"), "cache_get works when given a custom hash (doesn't have to use custom hash)"); destroy_cache(cache); }
//Tests if cache returns val_size from cache //sets a value and checks if the val_size from get is equal to the set value size void test_get_valsize() { uint8_t key[2] = {'a', '\0'}; uint8_t *value = "size me"; uint32_t val_size = 0; cache_t cache = create_cache(100 * sizeof(value)); cache_set(cache, key, value, strlen(value) + 1); cache_get(cache, key, &val_size); test(val_size == 8, "cache_get sets val_size pointer"); destroy_cache(cache); }
void test_get_modified() { cache_t cache = create_cache(65536, NULL); uint32_t val_size = 0; const uint8_t *key = (uint8_t *)"weather"; uint8_t *value = (uint8_t *)"sunny"; cache_set(cache, key, value, strlen((char *)value) + 1); value = (uint8_t *)"pouring rain forever"; cache_set(cache, key, value, strlen((char *)value) + 1); uint8_t *result = (uint8_t *)cache_get(cache, key, &val_size); bool value_is_updated = result != NULL && strcmp((const char*)value, (const char*)result) == 0; bool val_size_updated = val_size == strlen((char *)value) + 1; test(value_is_updated, "Setting to same key updates the value."); test(val_size_updated, "Value size from get is updated by cache_set."); destroy_cache(cache); }
//sets 4 values, gets the first value set, and sets a new value //big enough to force an eviction, checks if the second key (least recently used) //is removed, the third is removed, and finally if the first value added is still there void evict_after_get() { cache_t cache = create_cache(64); key_type key0 = (const uint8_t*) "hello", key1 = (const uint8_t*) "thenumber3", key2 = (const uint8_t*) "goodbye", key3 = (const uint8_t*) "wow"; uint8_t *value0 = "1", *value1 = "3"; uint8_t value2[60] = "01234567890123456789012345678901234567890123456789012345678"; uint8_t *value3 = "123123124"; cache_set(cache,key0,value0,strlen(value0) + 1); cache_set(cache,key1,value1,strlen(value1) + 1); cache_set(cache,key2,value2,60); uint32_t val_size = 0; uint8_t *val; // access first input val = (uint8_t*) cache_get(cache,key0,&val_size); // Set something that will require an eviction cache_set(cache,key3,value3,strlen(value3) + 1); // now get the last used value uint8_t *val0 = (uint8_t*) cache_get(cache,key0,&val_size); uint8_t *val1 = (uint8_t*) cache_get(cache,key1,&val_size); uint8_t *val2 = (uint8_t*) cache_get(cache,key2,&val_size); uint8_t *val3 = (uint8_t*) cache_get(cache,key3,&val_size); test(!strcmp(val0,"1") && val1 == NULL && val2 == NULL && !strcmp(val3,"123123124"),"Last accessed key is evicted"); destroy_cache(cache); }
//cache evicts keys to make room for new ones (jmcosel has a memsize min of 64) //creates a cache with memsize of 64 and sets 4 values so that the 3rd will //cause an eviction (if they didn't mess with the maxmem) void eviction_couple() { cache_t cache = create_cache(64); key_type key0 = (const uint8_t*) "hello", key1 = (const uint8_t*) "thenumber3", key2 = (const uint8_t*) "goodbye", key3 = (const uint8_t*) "wow"; uint8_t *value0 = "a", *value1 = "b"; uint8_t *chararray = "01234567890123456789012345678901234567890123456789012345678"; uint8_t *value3 = "c"; cache_set(cache,key0,value0,strlen(value0) + 1); cache_set(cache,key1,value1,strlen(value1) + 1); cache_set(cache,key2,chararray,60); cache_set(cache,key3,value3,strlen(value3) + 1); uint32_t val_size = 0; uint8_t *val = (uint8_t*) cache_get(cache,key3,&val_size); test(!strcmp(val,"c"),"keys are evicted to make space for new values"); destroy_cache(cache); }
//Sets 4 values and then gets all 4, checks if the values were set correctly void set_multiple() { cache_t cache = init(); const uint8_t *key0 = (const uint8_t*) "hello", *key1 = (const uint8_t*) "thenumber3", *key2 = (const uint8_t*) "goodbye", *key3 = (const uint8_t*) "wow"; uint8_t *value0 = "hello", *value1 = "how are you"; uint8_t *value2 = "good thanks"; uint8_t *value3 = "me too"; cache_set(cache,key0,value0,strlen(value0) + 1); cache_set(cache,key1,value1,strlen(value1) + 1); cache_set(cache,key2,value2,strlen(value2) + 1); cache_set(cache,key3,value3,strlen(value3) + 1); uint32_t val_size = 0; uint8_t *val1 = (uint8_t*)cache_get(cache,key0,&val_size), *val2 = (uint8_t*)cache_get(cache,key1,&val_size); uint8_t *val3 = (uint32_t*)cache_get(cache,key2,&val_size); uint8_t *val4 = (uint64_t*)cache_get(cache,key3,&val_size); test(!strcmp(val1,"hello") && !strcmp(val2,"how are you") && !strcmp(val3,"good thanks") && !strcmp(val4,"me too"), "cache_set stores (multiple) values that are accessible"); free(val1); free(val2); free(val3); free(val4); destroy_cache(cache); }
//Test when query for a key that wasn't inserted; void test_key_not_inserted(){ cache_t cache = create_cache_fake(16*DATASIZE); data_t data1 = create_data(1,(DATATYPE)"111",DATASIZE); data_t data2 = create_data(2,(DATATYPE)"222",DATASIZE); cache_set(cache,data1->key,data1->value,data1->value_size); data_existence_test(cache,data1); //Retrive a key that is not inserted data_nonexistence_test(cache, data2); test_destroy_cache(cache); destroy_data(data1); destroy_data(data2); }
void test_too_big() { cache_t cache = create_cache(10, NULL); uint32_t val_size = 0; const uint8_t *key = (uint8_t *)"chrome"; uint8_t *value = (uint8_t *)"This is supposed to be too big to fit into this cache"; cache_set(cache, key, value, strlen((char *)value) + 1); uint8_t *result = (uint8_t *)cache_get(cache, key, &val_size); bool large_val_wasnt_saved = result == NULL; test(large_val_wasnt_saved, "Cache does not store large values."); destroy_cache(cache); }
// zero entirely the cache int cache_zero (struct cache_t *cache) { int idx_object; // check parameters if (!cache) return -ERR_CACHE_UNDEFINED; // reset cache (heavy one) for (idx_object = 0; idx_object < cache_get_capacity(cache); idx_object++) cache_set(cache, idx_object, NULL); // reset used counter cache->used = 0; return CACHE_OK; }
bool try_tfm (string family, int size, int osize, tex_font_metric& tfm, bool make) { // cout << "Try tfm " << family << size << " (" << osize << ")\n"; make= make && get_setting ("MAKETFM") != "false"; string name_tfm = family * as_string (osize) * ".tfm"; if (tex_font_metric::instances -> contains (name_tfm)) { tfm= tex_font_metric (name_tfm); return true; } string name= family * (size==0? string (""): as_string (size)) * ".tfm"; if (DEBUG_STD) debug_fonts << "Try tfm " << name << "\n"; url u= resolve_tex (name); if (is_none (u)) { if (exists (url ("$TEXMACS_HOME_PATH/fonts/error", name))) { if (DEBUG_STD) debug_fonts << "Error during " << name << " loading\n"; return false; } if (make) { system_wait ("Generating font file", name); make_tex_tfm (name); system_wait (""); u= resolve_tex (name); if (is_none (u)) { reset_tfm_path (); u= resolve_tex (name); save_string (url ("$TEXMACS_HOME_PATH/fonts/error", name), ""); } } if (is_none (u)) return false; } // cout << "Tfm " << family << osize << " -> " << family << size << "\n"; tfm= load_tfm (u, family, osize); if (size != osize) cache_set ("font_cache.scm", "tfm:" * family * as_string (osize), as_string (size)); if (size == 0) { size= tfm->size; if (DEBUG_STD) debug_fonts << "Design size = " << size << "\n"; } if (size != osize) tfm->header[1]= mag (tfm->header[1], osize, size); return true; }
void test_gets(uint8_t* keys, uint32_t* values, uint64_t numpairs) { cache_t cache = create_cache(numpairs*10); struct timespec start, end; const uint64_t requests = numpairs; const double nsToSec = 1000000000; const uint32_t nsToms = 1000000; char **keystrings = calloc(numpairs,sizeof(char*)); char **valstrings = calloc(numpairs,sizeof(char*)); for(int i = 0; i < numpairs; ++i) { keystrings[i] = calloc(keys[i],1); valstrings[i] = calloc(values[i],1); memset(keystrings[i],'K',keys[i]); memset(valstrings[i],'V',values[i]); keystrings[i][keys[i] - 1] = '\0'; valstrings[i][values[i] - 1] = '\0'; } clock_gettime(CLOCK_MONOTONIC,&start); for(int i = 0; i < numpairs; ++i) cache_set(cache,keystrings[i],valstrings[i],values[i]); clock_gettime(CLOCK_MONOTONIC,&end); uint64_t duration = (end.tv_sec * nsToSec + end.tv_nsec) - (start.tv_sec * nsToSec + start.tv_nsec); uint64_t ns = duration; double time_elapsed_sec = (double) duration / nsToSec; double requests_per_second = (double) requests / time_elapsed_sec; double ms = (double) ns / (requests * nsToms); printf("Time per Get: %f milliseconds\n",ms); printf("Requests per second: %f requests\n",requests_per_second); for(int i = 0; i < numpairs; ++i) free(valstrings[i]); free(valstrings); }