aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHugo Hörnquist <hugo@lysator.liu.se>2019-02-19 22:27:43 +0100
committerHugo Hörnquist <hugo@lysator.liu.se>2019-02-19 22:27:43 +0100
commit6d320b0386aa4d7c6bfe2d6fce3d68e227752bed (patch)
tree920b323f7e84bd9c5b6454f44d6f29918fcf9c7d
parentFurther changes. (diff)
downloadcalp-6d320b0386aa4d7c6bfe2d6fce3d68e227752bed.tar.gz
calp-6d320b0386aa4d7c6bfe2d6fce3d68e227752bed.tar.xz
Further C++ improvements, maybe doesn't segfault now.
-rw-r--r--parse.cpp43
-rw-r--r--strbuf.h4
-rw-r--r--trie.cpp124
-rw-r--r--trie.h135
-rw-r--r--vcal.h49
5 files changed, 184 insertions, 171 deletions
diff --git a/parse.cpp b/parse.cpp
index 1b186d4c..d6da0bb4 100644
--- a/parse.cpp
+++ b/parse.cpp
@@ -30,12 +30,7 @@ int parse_file(char* filename, FILE* f, vcomponent* root) {
if (fold(f, &ctx, c) > 0) {
/* Actuall end of line, handle value */
- // std::string& target = CLINE_CUR_VAL(&cline);
- // TODO solve current;
- // std::string& target = cline
-
- cline.value() = ctx.str;
- cline.value().cap();
+ cline.push_value(ctx.str);
ctx.str.soft_reset();
handle_kv(&cline, &ctx);
@@ -86,10 +81,12 @@ int parse_file(char* filename, FILE* f, vcomponent* root) {
/* Border between param {key, value} */
} else if (p_ctx == p_param_name && c == '=') {
- strbuf cpy = ctx.str;
- cpy.cap();
+
+ // ctx.str holds param_key;
+ // cline.values.back()->params.push_back(new __param_set(ctx.str));
+ cline.values.back()->push_param_key(ctx.str);
+
ctx.str.soft_reset();
- cline.push_param_key (cpy);
p_ctx = p_param_value;
@@ -105,21 +102,17 @@ int parse_file(char* filename, FILE* f, vcomponent* root) {
if (p_ctx == p_param_value) {
/* push kv pair */
- auto s = new strbuf(ctx.str);
- s->cap();
+ cline.values.back()->push_param_value(ctx.str);
ctx.str.soft_reset();
-
- cline.push_param_value (s);
}
if (p_ctx == p_key) {
+ /* set key for content line */
cline.key = ctx.str;
cline.key.cap();
ctx.str.soft_reset();
- // TODO?
- // content_set* p = new content_set;
- // cline.second.push(p);
+
}
if (c == ':') p_ctx = p_value;
@@ -144,14 +137,13 @@ int parse_file(char* filename, FILE* f, vcomponent* root) {
* the end here.
*/
- //strbuf* target = CLINE_CUR_VAL(&cline);
- cline.value() = ctx.str;
- cline.value().cap();
- ctx.str.soft_reset();
-
++ctx.line;
ctx.column = 0;
+ cline.values.back()->value = ctx.str;
+ cline.values.back()->value.cap();
+ ctx.str.soft_reset();
+
handle_kv(&cline, &ctx);
}
@@ -174,21 +166,20 @@ int handle_kv (
* and possibly some others I forget.
*/
- strbuf* s = new strbuf(cline->value());
- ctx->key_stack.push(s);
+ ctx->key_stack.push(new strbuf(ctx->str));
- cline->values.reset();
+ // cline->values.reset();
// TODO ompty cline->second here;
// RESET(LLIST(content_set))(&cline->val);
- auto e = new vcomponent(s->to_string(), ctx->filename);
+ auto e = new vcomponent(ctx->str.to_string(), ctx->filename);
e->parent = ctx->comp_stack.top();
ctx->comp_stack.push(e);
} else if (cline->key == "END") {
// strbuf* s = POP(LLIST(strbuf))(&ctx->key_stack);
strbuf* s = ctx->key_stack.top(); ctx->key_stack.pop();
- if (*s == cline->value()) {
+ if (*s == ctx->str) {
#if 0
ERR_P(ctx, "Expected END:%s, got END:%s.\n%s line",
s->mem,
diff --git a/strbuf.h b/strbuf.h
index 04457c0d..38a45b09 100644
--- a/strbuf.h
+++ b/strbuf.h
@@ -75,6 +75,10 @@ struct strbuf {
std::string to_string() {
return std::string (this->mem);
}
+
+ char* c_str() {
+ return this->mem;
+ }
};
/*
diff --git a/trie.cpp b/trie.cpp
deleted file mode 100644
index e3158a2b..00000000
--- a/trie.cpp
+++ /dev/null
@@ -1,124 +0,0 @@
-#include "trie.h"
-
-template <class T>
-trie_node<T>::trie_node (char c, trie_node<T>* next, trie_node<T>* child) {
- this->c = c;
- this->next = next;
- this->child = child;
-}
-
-template <class T>
-int trie<T>::push_back (const char* key, const T& item) {
- trie_node<T> *cur, *last;
-
- last = this->root;
- cur = last->child;
-
- char* subkey = key;
-
- while (true) {
- if (cur == NULL) {
- /* Build direct LL for remaining subkey */
- for (char* c = subkey; c[0] != '\0'; c++) {
- // NEW(TRIE_NODE(TYPE), t, *c);
- auto t = new trie_node<T>(*c);
- last->child = t;
- last = t;
- }
- // TODO fix resolve
- // last->value = RESOLVE(TYPE)(last->value, val);
- last->value = item;
- return 0;
- } else if (cur->c == subkey[0]) {
- /* This node belongs to the key,
- * Decend further */
- last = cur;
- cur = cur->child;
- subkey++;
- } else if (subkey[0] == '\0') {
- /* Key finished */
- // TODO fix resolve
- // last->value = RESOLVE(TYPE)(last->value, val);
- last->value = item;
- return 0;
- } else if (cur->next != NULL) {
- /* This node was not part of the set, but it's sibling might */
- cur = cur->next;
- /* `last` not set since we aren't moving down */
- } else {
- /* No node on self level was part of the set, create a new__
- * sibling and follow down that parse */
- // NEW(TRIE_NODE(TYPE), t, *subkey);
- auto t = new trie_node<T>(*subkey);
- cur->next = t;
- last = cur;
- cur = t;
- }
- }
-}
-
-template <class T>
-T& trie<T>::operator[] (const char* key) {
- trie_node<T>* n = this->root->child;
- char* subkey = key;
-
- while (n != NULL) {
- if (subkey[1] == '\0') {
- return n->value;
- } else if (subkey[0] == n->c) {
- n = n->child;
- subkey++;
- } else {
- n = n->next;
- }
- }
-
- // ERR("Position not found");
- // return 0;
- return nullptr;
-}
-
-template <class T>
-std::ostream& operator<<(std::ostream& o, trie_node<T>* node) {
-#if 0
- va_list ap;
- va_start(ap, buf);
- int argc = va_arg(ap, int);
- int depth = argc >= 1
- ? va_arg(ap, int)
- : 0;
- va_end(ap);
-
- int seek = 0;
-#endif
- // TODO figure out depth
- int depth = 1;
-
- trie_node<T>* n = node;
-
-
- if (n == NULL) { o << std::endl; }
- while (n != NULL) {
- o << '|';
- for (int i = 0; i < depth; i++) o << ' ';
- o << (n->c == '\0' ? '0' : n->c);
- if (n->value != NULL) {
- o << n->value << std::endl;
- }
-
- if (n->child != NULL) {
- o << std::endl;
- o << n->child; // depth + 1
- }
- n = n->next;
- }
- return o;
-}
-
-template <class T>
-std::ostream& operator<<(std::ostream& o, trie<T>* trie) {
- o << "Trie: " << trie << " {\n";
- o << trie->root->child;
- o << "}";
- return o;
-}
diff --git a/trie.h b/trie.h
index 4613694e..4e01e837 100644
--- a/trie.h
+++ b/trie.h
@@ -3,6 +3,9 @@
#include <iostream>
+#include <cstring>
+#include <cstdlib>
+
template <class T>
struct trie_node {
char c;
@@ -23,9 +26,9 @@ struct trie {
trie () : root (new trie_node<T> ('\0')) { }
- int push_back (const char* key, const T&);
+ int push (const char* key, T* item);
- T& operator[] ( const char* key );
+ T* operator[] ( const char* key );
bool empty () { return this->root->child == NULL; }
};
@@ -33,4 +36,132 @@ struct trie {
template <class T>
std::ostream& operator<<(std::ostream&, trie<T>* trie);
+template <class T>
+trie_node<T>::trie_node (char c, trie_node<T>* next, trie_node<T>* child) {
+ this->c = c;
+ this->next = next;
+ this->child = child;
+}
+
+template <class T>
+int trie<T>::push (const char* key, T* item) {
+ trie_node<T> *cur, *last;
+
+ last = this->root;
+ cur = last->child;
+
+ // TODO subkey is never collected
+ char* subkey = static_cast<char*>(malloc(strlen(key)));
+ strcpy (subkey, key);
+
+ while (true) {
+ if (cur == NULL) {
+ /* Build direct LL for remaining subkey */
+ for (char* c = subkey; c[0] != '\0'; c++) {
+ // NEW(TRIE_NODE(TYPE), t, *c);
+ auto t = new trie_node<T>(*c);
+ last->child = t;
+ last = t;
+ }
+ // TODO fix resolve
+ // last->value = RESOLVE(TYPE)(last->value, val);
+ last->value = item;
+ return 0;
+ } else if (cur->c == subkey[0]) {
+ /* This node belongs to the key,
+ * Decend further */
+ last = cur;
+ cur = cur->child;
+ subkey++;
+ } else if (subkey[0] == '\0') {
+ /* Key finished */
+ // TODO fix resolve
+ // last->value = RESOLVE(TYPE)(last->value, val);
+ last->value = item;
+ return 0;
+ } else if (cur->next != NULL) {
+ /* This node was not part of the set, but it's sibling might */
+ cur = cur->next;
+ /* `last` not set since we aren't moving down */
+ } else {
+ /* No node on self level was part of the set, create a new__
+ * sibling and follow down that parse */
+ // NEW(TRIE_NODE(TYPE), t, *subkey);
+ auto t = new trie_node<T>(*subkey);
+ cur->next = t;
+ last = cur;
+ cur = t;
+ }
+ }
+}
+
+template <class T>
+T* trie<T>::operator[] (const char* key) {
+ trie_node<T>* n = this->root->child;
+
+ // TODO subkey is never collected
+ char* subkey = static_cast<char*>(malloc(strlen(key)));
+ strcpy (subkey, key);
+
+ while (n != NULL) {
+ if (subkey[1] == '\0') {
+ return n->value;
+ } else if (subkey[0] == n->c) {
+ n = n->child;
+ subkey++;
+ } else {
+ n = n->next;
+ }
+ }
+
+ // ERR("Position not found");
+ // return 0;
+ return nullptr;
+}
+
+template <class T>
+std::ostream& operator<<(std::ostream& o, trie_node<T>* node) {
+#if 0
+ va_list ap;
+ va_start(ap, buf);
+ int argc = va_arg(ap, int);
+ int depth = argc >= 1
+ ? va_arg(ap, int)
+ : 0;
+ va_end(ap);
+
+ int seek = 0;
+#endif
+ // TODO figure out depth
+ int depth = 1;
+
+ trie_node<T>* n = node;
+
+
+ if (n == NULL) { o << std::endl; }
+ while (n != NULL) {
+ o << '|';
+ for (int i = 0; i < depth; i++) o << ' ';
+ o << (n->c == '\0' ? '0' : n->c);
+ if (n->value != NULL) {
+ o << n->value << std::endl;
+ }
+
+ if (n->child != NULL) {
+ o << std::endl;
+ o << n->child; // depth + 1
+ }
+ n = n->next;
+ }
+ return o;
+}
+
+template <class T>
+std::ostream& operator<<(std::ostream& o, trie<T>* trie) {
+ o << "Trie: " << trie << " {\n";
+ o << trie->root->child;
+ o << "}";
+ return o;
+}
+
#endif /* TRIE_H */
diff --git a/vcal.h b/vcal.h
index ea76e593..21f66063 100644
--- a/vcal.h
+++ b/vcal.h
@@ -13,9 +13,14 @@
struct __param_set {
strbuf key;
- llist<strbuf> values;
+ std::list<strbuf> values;
- __param_set (strbuf key) : key (key) { }
+ __param_set (strbuf key) : key (key) { this->key.cap(); }
+
+ void push_value (strbuf val) {
+ this->values.push_back(val);
+ this->values.back().cap();
+ }
};
/*
@@ -24,7 +29,17 @@ struct __param_set {
*/
struct __content_set {
strbuf value;
- llist<__param_set> params;
+ std::list<__param_set*> params;
+
+ __content_set (strbuf value) : value(value) { this->value.cap(); }
+
+ void push_param_key (strbuf key) {
+ this->params.push_back (new __param_set(key));
+ }
+
+ void push_param_value (strbuf val) {
+ this->params.back()->push_value(val);
+ }
};
/*
@@ -33,18 +48,12 @@ struct __content_set {
*/
struct content_line {
strbuf key;
- llist<__content_set> values;
-
- inline void push_param_key (strbuf key) {
- auto p = new __param_set(key);
- this->values.cur()->params.push(p);
- }
-
- inline void push_param_value (strbuf* value)
- { this->values.cur()->params.cur()->values.push(value); }
-
- inline strbuf& value() { return this->values.cur()->value; }
+ // llist<__content_set> values;
+ std::list<__content_set*> values;
+ void push_value (strbuf str) {
+ this->values.push_back(new __content_set(str));
+ }
};
struct vcomponent {
@@ -58,6 +67,9 @@ struct vcomponent {
vcomponent(const std::string& type, const std::string& filename);
+ void add_content_line (content_line* c) {
+ clines.push(c->key.c_str(), c);
+ }
/*
* Resolves a collision in some form of structure (probably a hash-map
@@ -67,18 +79,17 @@ struct vcomponent {
*/
vcomponent* operator= (vcomponent* other);
- content_line& operator[] (const char* key) {
- return this->clines[key];
- }
+ content_line* operator[] (const char* key)
+ { return this->clines[key]; }
void push_back(const vcomponent& child)
- { this->components.push_back(child); }
+ { this->components.push_back(child); }
};
std::ostream& operator<<(std::ostream&, vcomponent*);
-#if 1
+#if 0
/*
* Helper macros for accessing fields in
* content_line, content_set, and param_set