diff options
author | Taeksu Shin <taeksu.shin@samsung.com> | 2012-08-21 18:39:39 +0900 |
---|---|---|
committer | Taeksu Shin <taeksu.shin@samsung.com> | 2012-08-21 18:39:39 +0900 |
commit | 2742d6ca5da37180225fab6ef8bf55467956d25c (patch) | |
tree | c850c3679b282551927505d3162e6c60118d0609 /src/csv.c | |
parent | b5dc236b1575fe5846d01881893b3aaef43ecbcc (diff) | |
download | epson-inkjet-printer-escpr-master.tar.gz epson-inkjet-printer-escpr-master.tar.bz2 epson-inkjet-printer-escpr-master.zip |
Diffstat (limited to 'src/csv.c')
-rw-r--r-- | src/csv.c | 178 |
1 files changed, 178 insertions, 0 deletions
diff --git a/src/csv.c b/src/csv.c new file mode 100644 index 0000000..b110095 --- /dev/null +++ b/src/csv.c @@ -0,0 +1,178 @@ + +#ifdef HAVE_CONFIG_H +# include <config.h> +#endif + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "def.h" +#include "str.h" +#include "err.h" +#include "mem.h" +#include "csv.h" + +BEGIN_C +static int csvlist_makelist (csvlist_t *, long); +END_C + +csvlist_t * +csvlist_open (const char *path) +{ + csvlist_t *csv_p; + FILE *fp; + char *buffer; + long size; + + if (!path) + return NULL; + + csv_p = mem_new0 (csvlist_t, 1); + csv_p->path = str_clone ((char *) path, strlen (path)); + + fp = fopen (path, "rb"); + if (!fp) + err_system (path); + + fseek (fp, 0L, SEEK_END); + size = ftell (fp); + rewind (fp); + + buffer = mem_new (char, size); + + if (fread (buffer, size, 1, fp) < size) + { + if (ferror (fp)) + err_system ("csv_open"); + } + fclose (fp); + + csv_p->top_p = buffer; + if (csvlist_makelist (csv_p, size)) + { + csvlist_close (csv_p); + return NULL; + } + + return csv_p; +} + + +void +csvlist_close (csvlist_t *csv_p) +{ + if (csv_p) + { + if (csv_p->path) + mem_free (csv_p->path); + + if (csv_p->top_p) + mem_free (csv_p->top_p); + + if (csv_p->list) + mem_free (csv_p->list); + + mem_free (csv_p); + } + + return; +} + + +int +csvlist_search_keyword (csvlist_t *csv_p, int pos, const char *keyword) +{ + char **list = csv_p->list; + int i; + + for (i = pos; i < csv_p->lnum; i ++) + { + if (!strcmp (list[i], keyword)) + return i; + } + + return -1; +} + + +char * +csvlist_get_word (csvlist_t *csv_p, int pos) +{ + if (pos < 0 || pos > csv_p->lnum) + return NULL; + + return csv_p->list[pos]; +} + + +int +csvlist_get_max (csvlist_t *csv_p) +{ + return csv_p->lnum; +} + + +static int +csvlist_makelist (csvlist_t *csv_p, long size) +{ + char *from_buf = csv_p->top_p; + char *to_buf = from_buf; + char **list; + int list_max, list_num; + long from_point, to_point; + bool_t quote_in; + + list_max = 16; /* Initial value = 16 */ + list = mem_new (char *, list_max); + + list_num = 1; + list[0] = to_buf; + to_point = 0; + quote_in = 0; + + for (from_point = 0; from_point < size; from_point ++) + { + if (!quote_in + && from_buf[from_point] == '#') /* In comment */ + { + from_point += strcspn (from_buf + from_point, "\n\0"); + continue; + } + + else if (!quote_in + && (from_buf[from_point] == '\n' || from_buf[from_point] == ',')) + { + to_buf[to_point++] = '\0'; + + list[list_num++] = to_buf + to_point; + + if (list_num >= list_max) + { + list_max *= 2; + list = mem_renew (char *, list, list_max); + } + } + + else if (from_buf[from_point] == '"') + { + quote_in ^= 1; + continue; + } + + else + { + to_buf[to_point++] = from_buf[from_point]; + } + } + + to_buf = mem_renew (char, to_buf, to_point); + list = mem_renew (char *, list, list_num + 1); + + csv_p->top_p = to_buf; + csv_p->size = to_point; + csv_p->list = list; + csv_p->lnum = list_num; + + return 0; +} |