#include "log.h"
#include "common.h"
+/*
// http://stackoverflow.com/questions/7666509/hash-function-for-string
-unsigned long simple_hash(const char *name)
+uint32_t simple_hash(const char *name)
{
const char *s = name;
- unsigned long hash = 5381;
+ uint32_t hash = 5381;
int i;
while((i = *s++)) hash = ((hash << 5) + hash) + i;
return hash;
}
+*/
+
+// http://isthe.com/chongo/tech/comp/fnv/#FNV-1a
+uint32_t simple_hash(const char *name) {
+ unsigned char *s = (unsigned char *)name;
+ uint32_t hval = 0x811c9dc5;
+
+ // FNV-1a algorithm
+ while (*s) {
+ // multiply by the 32 bit FNV magic prime mod 2^32
+ // gcc optimized
+ hval += (hval<<1) + (hval<<4) + (hval<<7) + (hval<<8) + (hval<<24);
+
+ // xor the bottom with the current octet
+ hval ^= (uint32_t)*s++;
+ }
+
+ // fprintf(stderr, "HASH: %u = %s\n", hval, name);
+ return hval;
+}
+
void strreverse(char* begin, char* end)
{
+#include <inttypes.h>
+
#ifndef NETDATA_COMMON_H
#define NETDATA_COMMON_H 1
#define abs(x) ((x < 0)? -x : x)
#define usecdiff(now, last) (((((now)->tv_sec * 1000000ULL) + (now)->tv_usec) - (((last)->tv_sec * 1000000ULL) + (last)->tv_usec)))
-extern unsigned long simple_hash(const char *name);
+extern uint32_t simple_hash(const char *name);
extern void strreverse(char* begin, char* end);
extern char *mystrsep(char **ptr, char *s);
extern char *qstrsep(char **ptr);
struct config_value {
avl avl; // the index - this has to be first!
- unsigned long hash; // a simple hash to speed up searching
+ uint32_t hash; // a simple hash to speed up searching
// we first compare hashes, and only if the hashes are equal we do string comparisons
char *name;
struct config {
avl avl;
- unsigned long hash; // a simple hash to speed up searching
+ uint32_t hash; // a simple hash to speed up searching
// we first compare hashes, and only if the hashes are equal we do string comparisons
char *name;
#define config_value_index_add(co, cv) avl_insert(&((co)->values_index), (avl *)(cv))
#define config_value_index_del(co, cv) avl_remove(&((co)->values_index), (avl *)(cv))
-static struct config_value *config_value_index_find(struct config *co, const char *name, unsigned long hash) {
+static struct config_value *config_value_index_find(struct config *co, const char *name, uint32_t hash) {
struct config_value *result = NULL, tmp;
tmp.hash = (hash)?hash:simple_hash(name);
tmp.name = (char *)name;
#define config_index_add(cfg) avl_insert(&config_root_index, (avl *)(cfg))
#define config_index_del(cfg) avl_remove(&config_root_index, (avl *)(cfg))
-static struct config *config_index_find(const char *name, unsigned long hash) {
+static struct config *config_index_find(const char *name, uint32_t hash) {
struct config *result = NULL, tmp;
tmp.hash = (hash)?hash:simple_hash(name);
tmp.name = (char *)name;
#define name_value_index_add(dict, cv) avl_insert(&((dict)->values_index), (avl *)(cv))
#define name_value_index_del(dict, cv) avl_remove(&((dict)->values_index), (avl *)(cv))
-static NAME_VALUE *dictionary_name_value_index_find(DICTIONARY *dict, const char *name, unsigned long hash) {
+static NAME_VALUE *dictionary_name_value_index_find(DICTIONARY *dict, const char *name, uint32_t hash) {
NAME_VALUE *result = NULL, tmp;
tmp.hash = (hash)?hash:simple_hash(name);
tmp.name = (char *)name;
typedef struct name_value {
avl avl; // the index - this has to be first!
- unsigned long hash; // a simple hash to speed up searching
+ uint32_t hash; // a simple hash to speed up searching
// we first compare hashes, and only if the hashes are equal we do string comparisons
char *name;
snprintf(filename, FILENAME_MAX, "/proc/%d/io", p->pid);
- ff = procfile_reopen(ff, filename, ":");
+ ff = procfile_reopen(ff, filename, "");
if(!ff) return 1;
ff = procfile_readall(ff);
struct file_descriptor {
avl avl;
- unsigned long magic;
- unsigned long hash;
+ uint32_t magic;
+ uint32_t hash;
const char *name;
int type;
long count;
file_descriptor_compare
};
-static struct file_descriptor *file_descriptor_find(const char *name, unsigned long hash) {
+static struct file_descriptor *file_descriptor_find(const char *name, uint32_t hash) {
struct file_descriptor *result = NULL, tmp;
tmp.hash = (hash)?hash:simple_hash(name);
tmp.name = name;
unsigned long file_descriptor_find_or_add(const char *name)
{
static int last_pos = 0;
- unsigned long hash = simple_hash(name);
+ uint32_t hash = simple_hash(name);
- if(debug) fprintf(stderr, "apps.plugin: adding or finding name '%s' with hash %lu\n", name, hash);
+ if(debug) fprintf(stderr, "apps.plugin: adding or finding name '%s' with hash %u\n", name, hash);
struct file_descriptor *fd = file_descriptor_find(name, hash);
if(fd) {
#define rrdset_index_add(st) avl_insert(&rrdset_root_index, (avl *)(st))
#define rrdset_index_del(st) avl_remove(&rrdset_root_index, (avl *)(st))
-static RRDSET *rrdset_index_find(const char *id, unsigned long hash) {
+static RRDSET *rrdset_index_find(const char *id, uint32_t hash) {
RRDSET *result = NULL, tmp;
strncpy(tmp.id, id, RRD_ID_LENGTH_MAX);
tmp.id[RRD_ID_LENGTH_MAX] = '\0';
#define rrdset_index_del_name(st) avl_remove(&rrdset_root_index_name, (avl *)(&st->avlname))
-static RRDSET *rrdset_index_find_name(const char *name, unsigned long hash) {
+static RRDSET *rrdset_index_find_name(const char *name, uint32_t hash) {
void *result = NULL;
RRDSET tmp;
tmp.name = name;
#define rrddim_index_add(st, rd) avl_insert(&((st)->dimensions_index), (avl *)(rd))
#define rrddim_index_del(st,rd ) avl_remove(&((st)->dimensions_index), (avl *)(rd))
-static RRDDIM *rrddim_index_find(RRDSET *st, const char *id, unsigned long hash) {
+static RRDDIM *rrddim_index_find(RRDSET *st, const char *id, uint32_t hash) {
RRDDIM *result = NULL, tmp;
tmp.hash = (hash)?hash:simple_hash(id);
strncpy(tmp.id, id, RRD_ID_LENGTH_MAX);
// ------------------------------------------------------------------------
// members for temporary data we need for calculations
- unsigned long hash; // a simple hash of the id, to speed up searching / indexing
+ uint32_t hash; // a simple hash of the id, to speed up searching / indexing
// instead of strcmp() every item in the binary index
// we first compare the hashes
unsigned long long first_entry_t; // the timestamp (in microseconds) of the oldest entry in the db
- unsigned long hash; // a simple hash on the id, to speed up searching
+ uint32_t hash; // a simple hash on the id, to speed up searching
// we first compare hashes, and only if the hashes are equal we do string comparisons
- unsigned long hash_name; // a simple hash on the name
+ uint32_t hash_name; // a simple hash on the name
unsigned long long usec_since_last_update; // the time in microseconds since the last collection of data