summaryrefslogtreecommitdiffstats
path: root/src/plugins/fts-squat/squat-trie-private.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/plugins/fts-squat/squat-trie-private.h')
-rw-r--r--src/plugins/fts-squat/squat-trie-private.h192
1 files changed, 192 insertions, 0 deletions
diff --git a/src/plugins/fts-squat/squat-trie-private.h b/src/plugins/fts-squat/squat-trie-private.h
new file mode 100644
index 0000000..b079554
--- /dev/null
+++ b/src/plugins/fts-squat/squat-trie-private.h
@@ -0,0 +1,192 @@
+#ifndef SQUAT_TRIE_PRIVATE_H
+#define SQUAT_TRIE_PRIVATE_H
+
+#include "file-dotlock.h"
+#include "squat-trie.h"
+
+#define SQUAT_TRIE_VERSION 2
+#define SQUAT_TRIE_LOCK_TIMEOUT 60
+#define SQUAT_TRIE_DOTLOCK_STALE_TIMEOUT (15*60)
+
+struct squat_file_header {
+ uint8_t version;
+ uint8_t unused[3];
+
+ uint32_t indexid;
+ uint32_t uidvalidity;
+ uint32_t used_file_size;
+ uint32_t deleted_space;
+ uint32_t node_count;
+
+ uint32_t root_offset;
+ uint32_t root_unused_uids;
+ uint32_t root_next_uid;
+ uint32_t root_uidlist_idx;
+
+ uint8_t partial_len;
+ uint8_t full_len;
+ uint8_t normalize_map[256];
+};
+
+/*
+ node file: FIXME: no up-to-date
+
+ struct squat_file_header;
+
+ // children are written before their parents
+ node[] {
+ uint8_t child_count;
+ unsigned char chars[child_count];
+ packed neg_diff_to_first_child_offset; // relative to node
+ packed diff_to_prev_offset[child_count-1];
+ packed[child_count] {
+ // unused_uids_count == uid if have_uid_offset bit is zero
+ (unused_uids_count << 1) | (have_uid_offset);
+ [diff_to_prev_uid_offset;] // first one is relative to zero
+ }
+ }
+*/
+
+struct squat_node {
+ unsigned int child_count:8;
+
+ /* children.leaf_string contains this many bytes */
+ unsigned int leaf_string_length:16;
+
+ /* TRUE = children.data contains our children.
+ FALSE = children.offset contains offset to our children in the
+ index file. */
+ bool children_not_mapped:1;
+ /* When allocating our children, use a sequential array. */
+ bool want_sequential:1;
+ /* This node's children are in a sequential array, meaning that the
+ first SEQUENTIAL_COUNT children have chars[n] = n. */
+ bool have_sequential:1;
+
+ /* Number of UIDs that exists in parent node but not in this one
+ (i.e. number of UIDs [0..next_uid-1] not in this node's uidlist).
+ This is mainly used when adding new UIDs to our children to set
+ the UID to be relative to this node's UID list. */
+ uint32_t unused_uids;
+
+ /* next_uid=0 means there are no UIDs in this node, otherwise
+ next_uid-1 is the last UID added to this node. */
+ uint32_t next_uid;
+ uint32_t uid_list_idx;
+
+ /*
+ struct {
+ unsigned char chars[child_count];
+ struct squat_node[child_count];
+ } *children;
+ */
+ union {
+ /* children_not_mapped determines if data or offset should
+ be used. */
+ void *data;
+ unsigned char *leaf_string;
+ unsigned char static_leaf_string[sizeof(void *)];
+ uint32_t offset;
+ } children;
+};
+/* Return pointer to node.children.chars[] */
+#define NODE_CHILDREN_CHARS(node) \
+ ((unsigned char *)(node)->children.data)
+/* Return pointer to node.children.node[] */
+#define NODE_CHILDREN_NODES(_node) \
+ ((struct squat_node *)(NODE_CHILDREN_CHARS(_node) + \
+ MEM_ALIGN((_node)->child_count)))
+/* Return number of bytes allocated in node.children.data */
+#define NODE_CHILDREN_ALLOC_SIZE(child_count) \
+ (MEM_ALIGN(child_count) + \
+ ((child_count) / 8 + 1) * 8 * sizeof(struct squat_node))
+/* Return TRUE if children.leaf_string is set. */
+#define NODE_IS_DYNAMIC_LEAF(node) \
+ ((node)->leaf_string_length > \
+ sizeof((node)->children.static_leaf_string))
+/* Return node's leaf string. Assumes that it is set. */
+#define NODE_LEAF_STRING(node) \
+ (NODE_IS_DYNAMIC_LEAF(node) ? \
+ (node)->children.leaf_string : (node)->children.static_leaf_string)
+struct squat_trie {
+ struct squat_node root;
+ struct squat_uidlist *uidlist;
+
+ struct squat_file_header hdr;
+ size_t node_alloc_size;
+ unsigned int unmapped_child_count;
+
+ enum squat_index_flags flags;
+ enum file_lock_method lock_method;
+ mode_t create_mode;
+ gid_t create_gid;
+ uint32_t uidvalidity;
+
+ char *path;
+ int fd;
+ struct file_cache *file_cache;
+ struct dotlock_settings dotlock_set;
+
+ uoff_t locked_file_size;
+ const void *data;
+ size_t data_size;
+
+ void *mmap_base;
+ size_t mmap_size;
+
+ unsigned char default_normalize_map[256];
+ unsigned int default_partial_len;
+ unsigned int default_full_len;
+
+ bool corrupted:1;
+};
+
+#define SQUAT_PACK_MAX_SIZE ((sizeof(uint32_t) * 8 + 7) / 7)
+
+static inline void squat_pack_num(uint8_t **p, uint32_t num)
+{
+ /* number continues as long as the highest bit is set */
+ while (num >= 0x80) {
+ **p = (num & 0x7f) | 0x80;
+ *p += 1;
+ num >>= 7;
+ }
+
+ **p = num;
+ *p += 1;
+}
+
+static inline uint32_t squat_unpack_num(const uint8_t **p, const uint8_t *end)
+{
+ const uint8_t *c = *p;
+ uint32_t value = 0;
+ unsigned int bits = 0;
+
+ for (;;) {
+ if (unlikely(c == end)) {
+ /* we should never see EOF */
+ return 0;
+ }
+
+ value |= (*c & 0x7f) << bits;
+ if (*c < 0x80)
+ break;
+
+ bits += 7;
+ c++;
+ }
+
+ if (unlikely(bits >= 32)) {
+ /* broken input */
+ *p = end;
+ return 0;
+ }
+
+ *p = c + 1;
+ return value;
+}
+
+int squat_trie_create_fd(struct squat_trie *trie, const char *path, int flags);
+void squat_trie_delete(struct squat_trie *trie);
+
+#endif