aboutsummaryrefslogtreecommitdiff
path: root/read.c
diff options
context:
space:
mode:
authorHolden Rohrer <hr@hrhr.dev>2020-05-27 16:21:02 -0400
committerHolden Rohrer <hr@hrhr.dev>2020-05-27 16:21:24 -0400
commit290f2b95ee100735f55fe10af457cc65158af043 (patch)
tree6f72fa5c6312460c04cc78dcd71f370097c3903e /read.c
parent37cd5bb9e3742f4893a14e04d49a4ba9716455c8 (diff)
Initial working commit
There are still some errors when run through valgrind, but it performs as expected for the test file.
Diffstat (limited to 'read.c')
-rw-r--r--read.c102
1 files changed, 55 insertions, 47 deletions
diff --git a/read.c b/read.c
index e896863..879b03e 100644
--- a/read.c
+++ b/read.c
@@ -9,103 +9,111 @@
#include "ll.h"
void consumespaces(FILE* file) {
+ // used to consume spaces in an item ("- list item" -> "list item")
int c;
- while ( ( c = fgetc(file) ) != EOF && c != ' ' );
+ while ( ( c = fgetc(file) ) != EOF && c == ' ' );
ungetc(c, file);
}
-void wsclean(char* str, size_t sz) { //
- bool nl = false;
- if (str[sz] == '\n') {
- sz--;
- nl = true;
- }
+void wsclean(char* txt, size_t sz){ // "string \n \n" -> "string\n\n"
+ int nl = 0; // count of newlines
size_t i;
- for (i = sz-1; i >= 0 && str[i] == ' '; i--);
- if (nl) {
- str[i+1] = '\n';
- str[i+2] = 0;
- } else {
- str[i+1] = 0;
+ for (i = sz-1; i >= 0; i--) { // start at end [i-1] and dec
+ if (txt[i] == '\n') nl++; // count up newlines
+ else if (txt[i] != ' ') break; // and break on unpadded text
}
-
+ memset(txt+i, '\n', nl); // add #nl newlines at [i, i+nl)
+ txt[i+nl] = 0; // finish string
}
char* empty(void) {
+ // "" with a freeable memory address
char* str = malloc(sizeof(char));
*str = 0;
return str;
}
-char* line(FILE* file) {
+char* line(FILE* file) { // gets a line from file
char* link = NULL;
- size_t n;
- getline(&link, &n, file);
- wsclean(link, n);
- if (*link == '\n') {
+ size_t n = 0;
+ getline(&link, &n, file); // getline stores a line of size n in link
+ wsclean(link, n); // removes trailing whitespace
+ if (*link == '\n') { // empty line treated as ""
free(link);
- link = empty();
+ char* out = empty(); // DEBGUGU
+ return out;
+ } else { // else return obtained
+ return link;
}
- return link;
}
link* insorget(strbst* tgt, char* name) {
link* get = query(tgt, name);
- if (!(*get)) {
+ if (!get) {
get = newlink(newnode());
insbst(tgt, name, get);
}
return get;
}
-char* getdesc(FILE* file) {
- int c;
- size_t sz;
- llnode *head, *tail;
- head = tail = appendll(NULL, NULL);
- while ( (c = getc()) != EOF && c != ':' && c != '-' ) {
- tail = tail->next = appendll(tail, line());
- sz += strlen(tail->str); // this should be traced but I haven't
- }
- if (c != EOF) ungetc(c, file);
- tail = head->next; free(head);
+link* addbstlink(strbst* tree, char* name, node* to) {
+ link* l = newlink(to);
+ insbst(tree, name, l);
+ return l;
+}
+
+char* resolvell(llnode* head, size_t* sz) {
+ llnode* tail = head->next;
+ head->next = NULL;
char *out, *pos;
- pos = out = malloc(sizeof(char)*(sz+1)); out[sz] = 0;
+ pos = out = malloc(sizeof(char)*(*sz+1)); out[*sz] = 0;
+ *sz = 0;
while (tail != NULL) {
size_t len = strlen(tail->str);
memcpy(pos, tail->str, len);
pos += len;
llnode* tmp = tail;
tail = tail->next;
- free(tmp); free(tmp->str);
+ free(tmp->str); free(tmp);
}
- return pos;
+ return out;
}
node* readfile(char* name) {
FILE* read = fopen(name, "r");
node *root, *cur;
cur = root = newnode();
- link* curl = insbst(root->links, name, root);
- // getline
- while ( ( int c = fgetc(read) ) != EOF ) {
+ link* curl = addbstlink(root->links, name, root);
+
+ llnode start;
+ start.next = NULL; // empty desc isn't undefined
+ llnode *head, *tail;
+ head = tail = &start;
+ size_t sz = 0;
+
+ int c;
+ while ( ( c = fgetc(read) ) != EOF ) {
+ if (c == ':' || c == '-') {
+ curl->desc = resolvell(head, &sz);
+ consumespaces(read);
+ }
switch (c) {
case ':':
- consumespaces(file);
- curl = insorget(root->links, line());
+ curl = insorget(root->links, line(read));
cur = curl->to;
break;
- case '-':
- consumespaces(file);
- char* lname = line();
- curl = insbst(cur->links, lname,
- insorget(root->links, lname)->to);
+ case '-': ;
+ char* lname = line(read);
+ node* at = insorget(root->links, lname)->to;
+ curl = addbstlink(cur->links, lname, at);
break;
default:
ungetc(c, read);
- curl->desc = getdesc();
+ case '.':
+ tail = appendll(tail, line(read));
+ sz += strlen(tail->str);
break;
}
}