aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorFederico Angelilli <code@fedang.net>2024-09-08 13:07:22 +0200
committerFederico Angelilli <code@fedang.net>2024-09-08 13:07:22 +0200
commit43238419974e599a84f17b5faa8fb52401bdfe90 (patch)
tree6b27b61d081e4f4c8399b3caf8551d1ba75adf1e /src
parent6d0ce31b0ae5df97d4a340c54b66d95598b336a4 (diff)
Refactor config parsing
Diffstat (limited to 'src')
-rw-r--r--src/block.c5
-rw-r--r--src/block.h11
-rw-r--r--src/blocks/group.c15
-rw-r--r--src/blocks/info.h12
-rw-r--r--src/blocks/ram.c22
-rw-r--r--src/blocks/scheme.c5
-rw-r--r--src/blocks/scheme.h17
-rw-r--r--src/blocks/text.c16
-rw-r--r--src/config.c129
-rw-r--r--src/config.h21
10 files changed, 122 insertions, 131 deletions
diff --git a/src/block.c b/src/block.c
index bfe2ec5..a3e7acb 100644
--- a/src/block.c
+++ b/src/block.c
@@ -57,4 +57,9 @@ void block_free(block_t *block)
free(block->group.children);
}
+
+ if (block->finalize_cb != NULL)
+ block->finalize_cb(block);
+
+ free(block->state);
}
diff --git a/src/block.h b/src/block.h
index 5301a7b..1ceedf1 100644
--- a/src/block.h
+++ b/src/block.h
@@ -7,6 +7,7 @@
#include "event.h"
#include "util.h"
+#include "config.h"
// Element or text alignment
//
@@ -33,19 +34,23 @@ typedef void (*block_event_t)(block_t *block, event_t event);
//
typedef void (*block_update_t)(block_t *block);
+// Block finalization routine
+//
+typedef void (*block_finalize_t)(block_t *block);
+
// Block struct
//
struct block {
block_type_t type;
char *label;
bool active;
+ bool hidden;
+ void *state;
struct timespec update_interval;
struct timespec update_last;
block_update_t update_cb;
block_event_t event_cb;
- void *info;
-
- bool hidden;
+ block_finalize_t finalize_cb;
color_t color;
color_t line_color;
int line_width;
diff --git a/src/blocks/group.c b/src/blocks/group.c
deleted file mode 100644
index 00afb00..0000000
--- a/src/blocks/group.c
+++ /dev/null
@@ -1,15 +0,0 @@
-#include "info.h"
-
-static const config_entry_t block_group_entries[] = {
- { "spacing", CONFIG_INT, offsetof(block_t, group.spacing) },
- { 0 },
-};
-
-// TODO
-const config_block_t block_group_info = {
- .type_name = "group",
- .type_size = 0,
- .base = { 0 },
- .entries = block_group_entries,
- .apply = NULL,
-};
diff --git a/src/blocks/info.h b/src/blocks/info.h
deleted file mode 100644
index 2b42c72..0000000
--- a/src/blocks/info.h
+++ /dev/null
@@ -1,12 +0,0 @@
-#ifndef COMET_BLOCKS_H
-#define COMET_BLOCKS_H
-
-#include "../config.h"
-
-extern const config_block_t block_text_info;
-
-extern const config_block_t block_group_info;
-
-extern const config_block_t block_ram_info;
-
-#endif
diff --git a/src/blocks/ram.c b/src/blocks/ram.c
deleted file mode 100644
index 2190b20..0000000
--- a/src/blocks/ram.c
+++ /dev/null
@@ -1,22 +0,0 @@
-#include "info.h"
-
-static bool block_ram_apply(block_t *block, void *result)
-{
- return true;
-}
-
-static const config_entry_t block_ram_entries[] = {
- { "text", CONFIG_STRING, offsetof(block_t, text.text) },
- { "text-color", CONFIG_COLOR, offsetof(block_t, text.text_color) },
- { "text-size", CONFIG_INT, offsetof(block_t, text.text_size) },
- { 0 },
-};
-
-const config_block_t block_ram_info = {
- .type_name = "ram",
- .type_size = 0,
- .base = { 0 },
- .entries = block_ram_entries,
- .apply = block_ram_apply,
-};
-
diff --git a/src/blocks/scheme.c b/src/blocks/scheme.c
new file mode 100644
index 0000000..7a49b90
--- /dev/null
+++ b/src/blocks/scheme.c
@@ -0,0 +1,5 @@
+#include "scheme.h"
+
+const block_scheme_t *block_schemes[] = {
+ NULL,
+};
diff --git a/src/blocks/scheme.h b/src/blocks/scheme.h
new file mode 100644
index 0000000..b73f181
--- /dev/null
+++ b/src/blocks/scheme.h
@@ -0,0 +1,17 @@
+#ifndef COMET_SCHEME_H
+#define COMET_SCHEME_H
+
+#include "../block.h"
+
+typedef struct block_scheme {
+ const char *name;
+ block_t block;
+ size_t size;
+ const config_entry_t *entries;
+
+ bool (*block_scheme_verify_t)(block_t *block, struct block_scheme *scheme);
+} block_scheme_t;
+
+extern const block_scheme_t *block_schemes[];
+
+#endif
diff --git a/src/blocks/text.c b/src/blocks/text.c
deleted file mode 100644
index 74df3c3..0000000
--- a/src/blocks/text.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include "info.h"
-
-static const config_entry_t block_text_entries[] = {
- { "text", CONFIG_STRING, offsetof(block_t, text.text) },
- { "text-color", CONFIG_COLOR, offsetof(block_t, text.text_color) },
- { "text-size", CONFIG_INT, offsetof(block_t, text.text_size) },
- { 0 },
-};
-
-const config_block_t block_text_info = {
- .type_name = "text",
- .type_size = 0,
- .base = { 0 },
- .entries = block_text_entries,
- .apply = NULL,
-};
diff --git a/src/config.c b/src/config.c
index cfeb70f..76551fa 100644
--- a/src/config.c
+++ b/src/config.c
@@ -9,7 +9,7 @@
#include "config.h"
#include "util.h"
#include "block.h"
-#include "blocks/info.h"
+#include "blocks/scheme.h"
#define ANY_INI_IMPLEMENT
#include "any_ini.h"
@@ -21,24 +21,44 @@ typedef enum {
} config_status_t;
static const config_entry_t bar_entries[] = {
- { "width", CONFIG_UINT, offsetof(config_t, width) },
- { "height", CONFIG_UINT, offsetof(config_t, height) },
- { "font", CONFIG_STRING, offsetof(config_t, font) },
- { "monitor", CONFIG_STRING, offsetof(config_t, monitor) },
- { "override-redirect", CONFIG_BOOL, offsetof(config_t, override_redirect) },
- { "background", CONFIG_COLOR, offsetof(config_t, background) },
+ { "width", CONFIG_UINT, NULL, offsetof(config_t, width) },
+ { "height", CONFIG_UINT, NULL, offsetof(config_t, height) },
+ { "font", CONFIG_STRING, NULL, offsetof(config_t, font) },
+ { "monitor", CONFIG_STRING, NULL, offsetof(config_t, monitor) },
+ { "override-redirect", CONFIG_BOOL, NULL, offsetof(config_t, override_redirect) },
+ { "background", CONFIG_COLOR, NULL, offsetof(config_t, background) },
{ 0 },
};
static const config_entry_t block_entries[] = {
- { "hidden", CONFIG_BOOL, offsetof(block_t, hidden) },
- { "color", CONFIG_COLOR, offsetof(block_t, color) },
- { "line-color", CONFIG_COLOR, offsetof(block_t, line_color) },
- { "line-width", CONFIG_INT, offsetof(block_t, line_width) },
- { "x-padding", CONFIG_INT, offsetof(block_t, x_padding) },
- { "y-padding", CONFIG_INT, offsetof(block_t, y_padding) },
- { "min-width", CONFIG_INT, offsetof(block_t, min_width) },
- { "max-width", CONFIG_INT, offsetof(block_t, max_width) },
+ { "hidden", CONFIG_BOOL, NULL, offsetof(block_t, hidden) },
+ { "color", CONFIG_COLOR, NULL, offsetof(block_t, color) },
+ { "line-color", CONFIG_COLOR, NULL, offsetof(block_t, line_color) },
+ { "line-width", CONFIG_INT, NULL, offsetof(block_t, line_width) },
+ { "x-padding", CONFIG_INT, NULL, offsetof(block_t, x_padding) },
+ { "y-padding", CONFIG_INT, NULL, offsetof(block_t, y_padding) },
+ { "min-width", CONFIG_INT, NULL, offsetof(block_t, min_width) },
+ { "max-width", CONFIG_INT, NULL, offsetof(block_t, max_width) },
+ { 0 },
+};
+
+static const config_entry_t block_group_entries[] = {
+ { "spacing", CONFIG_INT, NULL, offsetof(block_t, group.spacing) },
+ { 0 },
+};
+
+static config_enum_t text_align_enum[] = {
+ { "left", ALIGN_LEFT },
+ { "center", ALIGN_CENTER },
+ { "right", ALIGN_RIGHT },
+ { 0 },
+};
+
+static const config_entry_t block_text_entries[] = {
+ { "text", CONFIG_STRING, NULL, offsetof(block_t, text.text) },
+ { "text-color", CONFIG_COLOR, NULL, offsetof(block_t, text.text_color) },
+ { "text-size", CONFIG_INT, NULL, offsetof(block_t, text.text_size) },
+ { "text-align", CONFIG_ENUM, text_align_enum, offsetof(block_t, text.text_size) },
{ 0 },
};
@@ -91,14 +111,12 @@ static bool config_read_double(const char *value, double *result)
static bool config_read_bool(const char *value, bool *result)
{
- size_t lenght = strlen(value);
-
- if (lenght == 5 && !strcmp(value, "false")) {
+ if (!strcmp(value, "false")) {
*result = false;
return true;
}
- if (lenght == 4 && !strcmp(value, "true")) {
+ if (!strcmp(value, "true")) {
*result = true;
return true;
}
@@ -152,6 +170,19 @@ static bool config_read_color(const char *value, color_t *result)
return false;
}
+static bool config_read_enum(const char *value, config_enum_t *data, int *result)
+{
+ for (int i = 0; data[i].label != NULL; i++) {
+ if (!strcmp(value, data[i].label)) {
+ *result = data[i].value;
+ return true;
+ }
+ }
+
+ log_debug("Invalid enum value '%s'", value);
+ return false;
+}
+
static config_status_t config_read_entry(const config_entry_t *entries, void *result, const char **type,
const char *section, const char *key, const char *value)
{
@@ -218,6 +249,13 @@ static config_status_t config_read_entry(const config_entry_t *entries, void *re
}
break;
+ case CONFIG_ENUM:
+ if (config_read_enum(value, (config_enum_t *)entries[i].data, (int *)result)) {
+ log_debug("Set '%s.%s' to '%d'", section, key, *(int *)result);
+ return CONFIG_SUCCESS;
+ }
+ break;
+
default:
unreachable();
}
@@ -229,13 +267,18 @@ static config_status_t config_read_entry(const config_entry_t *entries, void *re
return CONFIG_UNKNOWN;
}
-static config_status_t config_read_block(const config_block_t *info, block_t *block, void *result, const char **type,
+static config_status_t config_read_block(const block_scheme_t *scheme, block_t *block, const char **type,
const char *section, const char *key, const char *value)
{
config_status_t status = config_read_entry(block_entries, block, type, section, key, value);
- return status != CONFIG_UNKNOWN
- ? status
- : config_read_entry(info->entries, result, type, section, key, value);
+ if (status != CONFIG_UNKNOWN) return status;
+
+ status = config_read_entry(block->type == BLOCK_GROUP ? block_group_entries : block_text_entries,
+ block, type, section, key, value);
+
+ return status != CONFIG_UNKNOWN || scheme->entries != NULL
+ ? status
+ : config_read_entry(scheme->entries, block->state, type, section, key, value);
}
void config_init(config_t *config)
@@ -265,9 +308,8 @@ void config_read(config_t *config, FILE *file)
char *key = NULL, *value = NULL;
int errors = 0;
- const config_block_t *info = NULL;
+ const block_scheme_t *scheme = NULL;
const config_entry_t *entries = NULL;
- void *result = NULL;
block_t *block = NULL;
if (section != NULL) {
@@ -303,27 +345,18 @@ void config_read(config_t *config, FILE *file)
goto skip_pair;
}
-
- // FIXME: Move this somewhere else
- const config_block_t block_infos[] = {
- block_text_info,
- block_group_info,
- block_ram_info,
- { 0 }
- };
-
- for (int i = 0; block_infos[i].type_name != NULL; i++) {
- if (strcmp(block_infos[i].type_name, value))
+ for (int i = 0; block_schemes[i] != NULL; i++) {
+ if (strcmp(block_schemes[i]->name, value))
continue;
- info = &block_infos[i];
- block_copy(block, &info->base);
+
+ scheme = block_schemes[i];
+ block_copy(block, &scheme->block);
free(block->label);
block->label = label;
- if (info->type_size == 0)
- result = block;
- else
- block->info = result = malloc(info->type_size);
+ if (scheme->size != 0)
+ block->state = malloc(scheme->size);
+
goto skip_pair;
}
@@ -338,7 +371,6 @@ void config_read(config_t *config, FILE *file)
// TODO
} else if (!strcmp(section, "bar")) {
entries = bar_entries;
- result = config;
} else
log_warn("Unknown section '%s'", section);
}
@@ -357,10 +389,10 @@ void config_read(config_t *config, FILE *file)
config_status_t status;
if (block != NULL)
- status = config_read_block(info, &config->blocks[config->n_blocks - 1], result,
+ status = config_read_block(scheme, &config->blocks[config->n_blocks - 1],
&type, section, key, value);
else if (entries != NULL)
- status = config_read_entry(entries, result, &type, section, key, value);
+ status = config_read_entry(entries, config, &type, section, key, value);
else
goto skip_pair;
@@ -395,13 +427,6 @@ skip_pair:
free(value);
}
- if (block != NULL && info->apply != NULL) {
- if (errors != 0)
- log_trace("Skipped '%s' apply for '%s'", info->type_name, section);
- else
- errors += !info->apply(block, result);
- }
-
free(section);
n_errors += errors;
} while ((section = any_ini_stream_next_section(&ini)) != NULL);
diff --git a/src/config.h b/src/config.h
index d76c515..024b6f6 100644
--- a/src/config.h
+++ b/src/config.h
@@ -4,7 +4,9 @@
#include <stdio.h>
#include <stdint.h>
-#include "block.h"
+#include "util.h"
+
+typedef struct block block_t;
typedef enum {
CONFIG_STRING,
@@ -13,24 +15,16 @@ typedef enum {
CONFIG_DOUBLE,
CONFIG_BOOL,
CONFIG_COLOR,
+ CONFIG_ENUM,
} config_type_t;
typedef struct {
const char *key;
config_type_t type;
+ void *data;
size_t offset;
} config_entry_t;
-typedef bool (*config_block_apply_t)(block_t *block, void *result);
-
-typedef struct {
- const char *type_name;
- size_t type_size;
- block_t base;
- const config_entry_t *entries;
- config_block_apply_t apply;
-} config_block_t;
-
typedef struct {
size_t n_blocks;
block_t *blocks;
@@ -42,6 +36,11 @@ typedef struct {
color_t background;
} config_t;
+typedef struct {
+ const char *label;
+ int value;
+} config_enum_t;
+
void config_init(config_t *config);
void config_read(config_t *config, FILE *file);