Added but didn't test the registry for tag names and fixed a bug in the action.bash
This commit is contained in:
parent
3236dc2984
commit
c0c17f6641
|
@ -59,7 +59,7 @@ function compile_module_c_sources {
|
|||
echo $INCLUDE_STATEMENTS
|
||||
|
||||
MODULE_SOURCE_PATH="$REPOSITORY_FOLDER/$MODULE_NAME/src-c/"
|
||||
MODULE_OBJECTS_FOLDER="$REPOSITORY_FOLDER/$MAIN_OBJECTS_FOLDER/$MODULE_NAME/"
|
||||
MODULE_OBJECTS_FOLDER="$MAIN_OBJECTS_FOLDER/$MODULE_NAME/"
|
||||
mkdir -p $MODULE_OBJECTS_FOLDER
|
||||
|
||||
# Loop through all files in the 'src-c'-folder and hand them over to GCC
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
|
||||
#ifndef MT_TAG_REGISTRY_H
|
||||
#define MT_TAG_REGISTRY_H
|
||||
|
||||
#include <librr/types.h>
|
||||
#include <librr/alloc/generic.h>
|
||||
|
||||
typedef struct MtTagRegistry MtTagRegistry;
|
||||
typedef struct MtTagEntry MtTagEntry;
|
||||
typedef struct MtTagCollection MtTagCollection;
|
||||
|
||||
/// @brief Contains an array of every tag's label/name with the identifier,
|
||||
/// meant for resolving one to another. This also is a the head structure
|
||||
/// of a label-to-identifier hash map for quickly inferring an identifier
|
||||
/// from the tag's name.
|
||||
struct MtTagRegistry
|
||||
{
|
||||
void *parent_state;
|
||||
|
||||
u32_t entries_capacity;
|
||||
u32_t num_entries;
|
||||
MtTagEntry *entries;
|
||||
|
||||
u32_t next_identifier;
|
||||
|
||||
u32_t num_collections;
|
||||
MtTagCollection *collections;
|
||||
};
|
||||
|
||||
struct MtTagEntry
|
||||
{
|
||||
u32_t identifier;
|
||||
char *label;
|
||||
};
|
||||
|
||||
struct MtTagCollection
|
||||
{
|
||||
u32_t capacity;
|
||||
u32_t num_tags;
|
||||
|
||||
/// @brief An array of pointers into the tag-registry's 'entries'-array.
|
||||
MtTagEntry **tags;
|
||||
};
|
||||
|
||||
MtTagRegistry mt_create_tag_registry(void *parent_state);
|
||||
void mt_delete_tag_registry(MtTagRegistry registry);
|
||||
|
||||
u32_t mt_get_tag_id(MtTagRegistry *registry, const char *tag_label);
|
||||
const char * mt_get_tag_label(MtTagRegistry *registry, u32_t tag_identifier);
|
||||
|
||||
#endif // MT_TAG_REGISTRY_H
|
|
@ -0,0 +1,137 @@
|
|||
#include <tag_registry.h>
|
||||
#include <librr/strutil.h>
|
||||
#include <librr/memory.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
MtTagRegistry mt_create_tag_registry(void *parent_state)
|
||||
{
|
||||
MtTagRegistry registry;
|
||||
registry.parent_state = parent_state;
|
||||
registry.num_collections = 256;
|
||||
registry.collections = calloc(sizeof(MtTagCollection), registry.num_collections);
|
||||
registry.next_identifier = 1;
|
||||
registry.entries_capacity = 512;
|
||||
registry.num_entries = 0;
|
||||
registry.entries = calloc(sizeof(MtTagEntry), registry.entries_capacity);
|
||||
return registry;
|
||||
}
|
||||
|
||||
void mt_delete_all_tag_registry_collections(MtTagRegistry registry)
|
||||
{
|
||||
usz_t index = 0;
|
||||
while(index < registry.num_collections)
|
||||
{
|
||||
MtTagCollection collection = registry.collections[index];
|
||||
if(collection.capacity == 0)
|
||||
return;
|
||||
|
||||
free(collection.tags);
|
||||
++index;
|
||||
}
|
||||
}
|
||||
|
||||
void mt_delete_all_tag_registry_entries(MtTagRegistry registry)
|
||||
{
|
||||
usz_t index = 0;
|
||||
while(index < registry.num_entries)
|
||||
{
|
||||
MtTagEntry entry = registry.entries[index];
|
||||
if(entry.label == NULL)
|
||||
return;
|
||||
free(entry.label);
|
||||
++index;
|
||||
}
|
||||
free(registry.entries);
|
||||
}
|
||||
|
||||
void mt_delete_tag_registry(MtTagRegistry registry)
|
||||
{
|
||||
mt_delete_all_tag_registry_collections(registry);
|
||||
mt_delete_all_tag_registry_entries(registry);
|
||||
}
|
||||
|
||||
|
||||
|
||||
u32_t mt_tag_label_to_hash(const char *tag_label, usz_t range)
|
||||
{
|
||||
usz_t len_tag_label = rr_measure_string(tag_label);
|
||||
if(len_tag_label <= 4)
|
||||
{
|
||||
const u32_t *tag_label_32 = (const void *) tag_label;
|
||||
return tag_label_32[0] % range;
|
||||
}
|
||||
if(len_tag_label <= 8)
|
||||
{
|
||||
u32_t hash = 0;
|
||||
hash |= tag_label[0] << 24;
|
||||
hash |= tag_label[1] << 16;
|
||||
hash |= tag_label[len_tag_label-2] << 8;
|
||||
hash |= tag_label[len_tag_label-1];
|
||||
return hash % range;
|
||||
}
|
||||
|
||||
u32_t hash = 0;
|
||||
usz_t char_index = 0;
|
||||
while(char_index < len_tag_label)
|
||||
{
|
||||
hash ^= tag_label[char_index] << (24 - ((char_index * 6) % 32));
|
||||
++char_index;
|
||||
}
|
||||
return hash % range;
|
||||
}
|
||||
|
||||
MtTagEntry * mt_create_tag_hash_entry(MtTagRegistry *registry, const char *tag_label)
|
||||
{
|
||||
u32_t collection_index = mt_tag_label_to_hash(tag_label, registry->num_collections);
|
||||
MtTagCollection *collection = ®istry->collections[collection_index];
|
||||
|
||||
if(collection->num_tags >= collection->capacity)
|
||||
{
|
||||
collection->capacity *= 2;
|
||||
collection->tags = realloc(collection->tags, sizeof(MtTagEntry *) * collection->capacity);
|
||||
}
|
||||
MtTagEntry *entry = collection->tags[collection->num_tags];
|
||||
++collection->num_tags;
|
||||
|
||||
usz_t len_tag_label = rr_measure_string(tag_label);
|
||||
|
||||
// TODO: There must be an arena allocator for this!
|
||||
entry->label = malloc(len_tag_label + 1);
|
||||
rr_memcopy(entry->label, tag_label, len_tag_label+1);
|
||||
|
||||
entry->identifier = registry->next_identifier;
|
||||
++registry->next_identifier;
|
||||
|
||||
return entry;
|
||||
}
|
||||
|
||||
u32_t mt_get_tag_id(MtTagRegistry *registry, const char *tag_label)
|
||||
{
|
||||
u32_t collection_index = mt_tag_label_to_hash(tag_label, registry->num_collections);
|
||||
MtTagCollection collection = registry->collections[collection_index];
|
||||
usz_t entry_index = 0;
|
||||
while(entry_index < collection.num_tags)
|
||||
{
|
||||
MtTagEntry *entry = collection.tags[entry_index];
|
||||
if(rr_strings_equal(entry->label, tag_label))
|
||||
return entry->identifier;
|
||||
|
||||
++entry_index;
|
||||
}
|
||||
MtTagEntry *entry = mt_create_tag_hash_entry(registry, tag_label);
|
||||
return entry->identifier;
|
||||
}
|
||||
|
||||
const char * mt_get_tag_label(MtTagRegistry *registry, u32_t tag_identifier)
|
||||
{
|
||||
usz_t entry_index = 0;
|
||||
while(entry_index < registry->num_entries)
|
||||
{
|
||||
MtTagEntry *entry = ®istry->entries[entry_index];
|
||||
if(entry->identifier == tag_identifier)
|
||||
return entry->label;
|
||||
|
||||
++entry_index;
|
||||
}
|
||||
return NULL;
|
||||
}
|
Reference in New Issue