aboutsummaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorGabriel A. Giovanini <mail@gabrielgio.me>2024-02-17 11:41:23 +0100
committergabrielgio <gabrielgio@workstation.lan>2024-02-17 16:48:54 +0100
commitd102e028aee6571c0fd9dfd4074cfb3c15f4594e (patch)
treee0f3bdadc96019de0a7576ea591f8b304a962e67 /lib
parentc573d3b7954296d95a0f8a79b8ac2ca261d86a02 (diff)
downloaddict-d102e028aee6571c0fd9dfd4074cfb3c15f4594e.tar.gz
dict-d102e028aee6571c0fd9dfd4074cfb3c15f4594e.tar.bz2
dict-d102e028aee6571c0fd9dfd4074cfb3c15f4594e.zip
ref: Refactor newer folder structure
Create a lib dict and importer project. * dict: holds the main application * importer: code to read from source to a common database. * lib: shared code
Diffstat (limited to 'lib')
-rw-r--r--lib/CMakeLists.txt5
-rw-r--r--lib/data.c117
-rw-r--r--lib/data.h47
-rw-r--r--lib/list.c55
-rw-r--r--lib/list.h29
-rw-r--r--lib/ui.c87
-rw-r--r--lib/ui.h23
-rw-r--r--lib/util.c61
-rw-r--r--lib/util.h15
9 files changed, 439 insertions, 0 deletions
diff --git a/lib/CMakeLists.txt b/lib/CMakeLists.txt
new file mode 100644
index 0000000..023cdf1
--- /dev/null
+++ b/lib/CMakeLists.txt
@@ -0,0 +1,5 @@
+file(GLOB lib CONFIGURE_DEPENDS "*.h" "*.c")
+
+add_library(lib ${lib})
+target_compile_options(lib PRIVATE -Wall -Wextra -Wpedantic -Werror)
+target_link_libraries(lib sqlite3 ncursesw m c)
diff --git a/lib/data.c b/lib/data.c
new file mode 100644
index 0000000..7ebf597
--- /dev/null
+++ b/lib/data.c
@@ -0,0 +1,117 @@
+#include <string.h>
+#include <stdlib.h>
+#include <stdio.h>
+
+#include "data.h"
+
+const char *insert_into = "INSERT INTO words (LINE) VALUES($VVV);";
+const char *select_words = "SELECT Id, Line FROM words WHERE line like $VVV LIMIT 10;";
+const char *create_table = "CREATE TABLE IF NOT EXISTS words (ID INTEGER PRIMARY KEY AUTOINCREMENT, LINE TEXT NOT NULL);";
+
+Data* new_data(const char* con) {
+ Data* data = (Data*)malloc(sizeof(Data));
+
+ int v = sqlite3_open(con, &(data->db));
+ if (v != SQLITE_OK) {
+ print_result_code(v);
+ return NULL;
+ }
+
+ sqlite3_enable_load_extension(data->db, 1);
+ v = sqlite3_load_extension(data->db, "ext/libsqlite3ext", "sqlite3_spellfix_init",0);
+ if (v != SQLITE_OK) {
+ print_result_code(v);
+ return NULL;
+ }
+
+ return data;
+}
+
+void free_data(Data* data) {
+ sqlite3_close(data->db);
+ free(data);
+}
+
+void insert(Data* data, char* line, int len) {
+ sqlite3_stmt *stmt;
+ int r = sqlite3_prepare_v2(data->db, insert_into, -1, &stmt, NULL);
+
+ if (r != SQLITE_OK) {
+ printf("Error executing insert: ");
+ print_result_code(r);
+ printf("\n");
+ return;
+ }
+
+ sqlite3_bind_text(stmt, 1, line, len, NULL);
+
+ int c = sqlite3_step(stmt);
+ if (c != SQLITE_DONE) {
+ printf("Error executing insert: ");
+ print_result_code(r);
+ printf("\n");
+ }
+
+ sqlite3_finalize(stmt);
+}
+
+void bootstrap(Data* data) {
+ sqlite3_stmt *stmt;
+ int r = sqlite3_prepare_v2(data->db, create_table, -1, &stmt, NULL);
+
+ if (r != SQLITE_OK) {
+ printf("Error preparing bootstrap: ");
+ print_result_code(r);
+ printf("\n");
+ return;
+ }
+
+ int c = sqlite3_step(stmt);
+ if (c != SQLITE_DONE) {
+ printf("Error executing bootstrap: ");
+ print_result_code(r);
+ printf("\n");
+ }
+
+ sqlite3_finalize(stmt);
+}
+
+LIST* data_select(Data* data, char *sch, int len) {
+ sqlite3_stmt *stmt;
+ int r = sqlite3_prepare_v2(data->db, select_words, -1, &stmt, NULL);
+
+ if (r != SQLITE_OK) {
+ printf("Error executing select: ");
+ print_result_code(r);
+ printf("\n");
+ return NULL;
+ }
+
+ LIST *list = NULL;
+
+ sqlite3_bind_text(stmt, 1, sch, len, NULL);
+
+ int m = sqlite3_step(stmt);
+ while(m == SQLITE_ROW) {
+ Word *word = (Word*)malloc(sizeof(Word));
+
+ int id = sqlite3_column_int(stmt, 0);
+ const unsigned char *line = sqlite3_column_text(stmt, 1);
+ unsigned char *line2 = malloc(sizeof(char*)+strlen((char*)line));
+ memcpy(line2, line, strlen((char*)line));
+
+ word->Id = id;
+ word->Line = line2;
+ list = list_add(list, word);
+
+ m = sqlite3_step(stmt);
+ }
+
+ sqlite3_finalize(stmt);
+
+ return list;
+}
+
+void print_result_code(int code) {
+ printf(sqlite3_errstr(code));
+}
diff --git a/lib/data.h b/lib/data.h
new file mode 100644
index 0000000..56edd34
--- /dev/null
+++ b/lib/data.h
@@ -0,0 +1,47 @@
+#pragma once
+#include <sqlite3.h>
+#include "list.h"
+
+/*
+ * This word into the dictionary
+ */
+typedef struct word {
+ int Id;
+ const unsigned char *Line;
+} Word;
+
+/*
+ * This is database connection.
+ */
+typedef struct data {
+ sqlite3 *db;
+} Data;
+
+
+/*
+ * create a new data struct from sqlite filename.
+ */
+Data* new_data(const char*);
+
+
+void free_data(Data*);
+
+/*
+ * Create the tables.
+ */
+void bootstrap(Data*);
+
+/*
+ * insert line into database.
+ */
+void insert(Data*, char*, int);
+
+/*
+ * Select all words.
+ */
+LIST* data_select(Data*, char*, int);
+
+/*
+ * Print result code from sqlite.
+ */
+void print_result_code(int error);
diff --git a/lib/list.c b/lib/list.c
new file mode 100644
index 0000000..fc0fddf
--- /dev/null
+++ b/lib/list.c
@@ -0,0 +1,55 @@
+#include "list.h"
+#include <stdlib.h>
+
+LIST* list_add(LIST* list, void* item)
+{
+
+ if (list == NULL)
+ {
+ list = (LIST*)malloc(sizeof(LIST));
+ list->size = 0;
+ list->list = (void**)malloc(sizeof(0));
+
+ }
+
+ list->size ++;
+ void** new_list = (void**)reallocarray(list->list, list->size, sizeof(void*));
+
+ new_list[list->size-1] = item;
+ list->list = new_list;
+
+ return list;
+
+}
+
+LIST* list_remove(LIST* list, unsigned int pos)
+{
+ for(unsigned int i = pos; i < list->size - 1; i++)
+ list->list[i] = list->list[i + 1];
+
+ list->size--;
+
+ void** new_list = reallocarray(list->list, list->size, sizeof(void*));
+ list->list = new_list;
+
+ return list;
+}
+
+void list_free(LIST* list) {
+ for (unsigned int x = 0; x < list->size; x++)
+ free(list->list[x]);
+
+ free(list->list);
+ free(list);
+}
+
+
+void *list_get(LIST *list, unsigned int index) {
+ if (list == NULL)
+ return NULL;
+
+ if (index < list->size)
+ return list->list[index];
+
+ return NULL;
+}
diff --git a/lib/list.h b/lib/list.h
new file mode 100644
index 0000000..dd28722
--- /dev/null
+++ b/lib/list.h
@@ -0,0 +1,29 @@
+#pragma once
+#include <stdlib.h>
+
+#define LIST_SIZE_FACTOR 1.5
+struct list {
+ unsigned int size;
+ unsigned int allocated_size;
+ void** list;
+};
+
+typedef struct list LIST;
+
+/**
+* Add an item to a list
+* @list: array list structure.
+* @item: item to be added to the list.
+*/
+LIST* list_add(LIST* list, void* item);
+
+/**
+* Remove an item from a given list
+* @list: array list structure.
+* @pos: position of item to be removed.
+*/
+LIST *list_remove(LIST *list, unsigned int pos);
+
+void list_free(LIST* list);
+
+void *list_get(LIST *list, unsigned int index);
diff --git a/lib/ui.c b/lib/ui.c
new file mode 100644
index 0000000..1a285a0
--- /dev/null
+++ b/lib/ui.c
@@ -0,0 +1,87 @@
+#define NCURSES_WIDECHAR 1
+
+#include <ncurses.h>
+#include <math.h>
+#include <stdlib.h>
+#include <string.h>
+#include <wchar.h>
+#include "ui.h"
+
+const char *uload = "█";
+
+PROGRESS_BAR* new_progress_bar(WINDOW* scr, float total) {
+ PROGRESS_BAR *bar = (PROGRESS_BAR*)malloc(sizeof(PROGRESS_BAR));
+ bar->scr = scr;
+ bar->total = total;
+ bar->current = 0;
+ return bar;
+}
+
+void bar_step(PROGRESS_BAR* bar, float step){
+ bar->current += step;
+
+ int x, y;
+ int hx, hy;
+
+ getmaxyx(bar->scr, y, x);
+
+ hx = x/2;
+ hy = y/2;
+
+ float total = (bar->current/bar->total);
+
+ wmove(bar->scr, hy-1, 0);
+ for (int i = 0; i < ((float)x*total); i++)
+ wprintw(bar->scr, uload);
+
+ wmove(bar->scr, hy, hx-4);
+ wprintw(bar->scr,"%03.0f%% ", total*100);
+
+ int len = floor(log10(abs((int)bar->total))) + 3;
+
+ wmove(bar->scr, hy+1, hx - len);
+ wprintw(bar->scr, "%.0f/%.0f", bar->current, bar->total);
+
+
+ wmove(bar->scr,0,0);
+ wrefresh(bar->scr);
+}
+
+
+TEXT_BOX* new_text_box(WINDOW* scr, int length) {
+ TEXT_BOX *text = (TEXT_BOX*)malloc(sizeof(TEXT_BOX));
+ text->scr = scr;
+ text->length = length;
+ text->current = 0;
+ text->text = malloc(sizeof(char)*(length+1));
+ memset(text->text, '\0', length);
+ return text;
+}
+
+void get_char(TEXT_BOX* text, void (*sch)(char*, int)) {
+ while(1){
+ wchar_t c;
+ get_wch((wint_t*)&c);
+
+ switch(c) {
+ case KEY_BACKSPACE:
+ if (text->current > 0) {
+ text->text[text->current--] = '\0';
+ }
+ break;
+ default:
+ if (text->current < (text->length-2)) {
+ text->text[text->current] = c;
+ text->text[++text->current] = '\0';
+ }
+ }
+
+ char str[text->length];
+ wcstombs(str, text->text, sizeof(text->text));
+ sch(str, (int)strlen(str));
+
+ move(0,0);
+ wrefresh(text->scr);
+ wprintw(text->scr, "%*ls", text->current,text->text);
+ }
+}
diff --git a/lib/ui.h b/lib/ui.h
new file mode 100644
index 0000000..90b352f
--- /dev/null
+++ b/lib/ui.h
@@ -0,0 +1,23 @@
+#pragma once
+#include <ncurses.h>
+
+typedef struct progress_bar {
+ float total;
+ float current;
+ WINDOW *scr;
+} PROGRESS_BAR;
+
+PROGRESS_BAR* new_progress_bar(WINDOW*, float);
+void bar_step(PROGRESS_BAR*, float);
+
+
+typedef struct text_box {
+ wchar_t *text;
+ int length;
+ int current;
+ WINDOW *scr;
+} TEXT_BOX;
+
+TEXT_BOX* new_text_box(WINDOW*, int);
+void get_char(TEXT_BOX* text, void (*sch)(char*, int));
+
diff --git a/lib/util.c b/lib/util.c
new file mode 100644
index 0000000..6720082
--- /dev/null
+++ b/lib/util.c
@@ -0,0 +1,61 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+
+#include "util.h"
+
+#define BUF_SIZE 100
+
+char* copy_achar(const char* src) {
+ int len = strlen(src) + 1;
+ char* dest = (char*)malloc(sizeof(char)*len);
+ strcpy(dest, src);
+
+ return dest;
+}
+
+
+int load_or_save_db(sqlite3 *pInMemory, const char *zFilename, int isSave){
+ int rc; /* Function return code */
+ sqlite3 *pFile; /* Database connection opened on zFilename */
+ sqlite3_backup *pBackup; /* Backup object used to copy data */
+ sqlite3 *pTo; /* Database to copy to (pFile or pInMemory) */
+ sqlite3 *pFrom; /* Database to copy from (pFile or pInMemory) */
+
+ rc = sqlite3_open(zFilename, &pFile);
+ if( rc==SQLITE_OK ){
+ pFrom = (isSave ? pInMemory : pFile);
+ pTo = (isSave ? pFile : pInMemory);
+
+ pBackup = sqlite3_backup_init(pTo, "main", pFrom, "main");
+ if( pBackup ){
+ (void)sqlite3_backup_step(pBackup, -1);
+ (void)sqlite3_backup_finish(pBackup);
+ }
+ rc = sqlite3_errcode(pTo);
+ }
+
+ (void)sqlite3_close(pFile);
+ return rc;
+}
+
+unsigned int count_file_lines(FILE *file) {
+ char buf[BUF_SIZE];
+ unsigned int counter = 0;
+ for(;;)
+ {
+ size_t res = fread(buf, 1, BUF_SIZE, file);
+ if (ferror(file))
+ return -1;
+
+ size_t i;
+ for(i = 0; i < res; i++)
+ if (buf[i] == '\n')
+ counter++;
+
+ if (feof(file))
+ break;
+ }
+
+ return counter;
+}
diff --git a/lib/util.h b/lib/util.h
new file mode 100644
index 0000000..c03dbae
--- /dev/null
+++ b/lib/util.h
@@ -0,0 +1,15 @@
+#pragma once
+
+#include <sqlite3.h>
+#include <stdio.h>
+
+/*
+ * Copy of a char to a newly created string of the same size.
+ */
+char* copy_achar(const char*);
+
+
+int load_or_save_db(sqlite3 *pInMemory, const char *zFilename, int isSave);
+
+
+unsigned int count_file_lines(FILE *file);