Implement config read function

This commit is contained in:
Mario Hüttel 2020-10-30 23:12:39 +01:00
parent dcec366b0a
commit 3ca5e41602
2 changed files with 88 additions and 5 deletions

View File

@ -26,6 +26,7 @@
#include <config-parser/config-parser.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#define CONFIG_PARSER_MAGIC 0x464a6e2bUL
#define CONFIG_PARSER(p) ((struct config_parser *)(p))
@ -36,7 +37,7 @@
} while (0)
config_parser_handle_t config_parser_open_file(struct config_parser *config_parser, bool write, const char *file_name,
char *working_buffer)
char *working_buffer, size_t buff_size)
{
FRESULT res;
@ -46,6 +47,7 @@ config_parser_handle_t config_parser_open_file(struct config_parser *config_pars
config_parser->magic = CONFIG_PARSER_MAGIC;
config_parser->write = write;
config_parser->buffer = working_buffer;
config_parser->buff_size = buff_size;
res = f_open(&config_parser->file, file_name, (write ? FA_CREATE_ALWAYS | FA_WRITE : FA_READ));
if (res != FR_OK)
@ -54,10 +56,90 @@ config_parser_handle_t config_parser_open_file(struct config_parser *config_pars
return (config_parser_handle_t)config_parser;
}
static const char * const token_delim = " \t";
static int parse_value(struct config_parser_entry *entry, char *value_start_token)
{
char *dot;
char *endptr;
/* Check if token is a float number */
dot = strstr(value_start_token, ".");
if (dot) {
/* Try parsing as float */
entry->value.float_val = strtof(value_start_token, &endptr);
if (endptr == value_start_token)
return -1;
entry->type = CONFIG_PARSER_TYPE_FLOAT;
}
if (value_start_token[0] != '-') {
/* Try parsing as ul */
/* Try parsing as int */
entry->value.uint_val = strtoul(value_start_token, &endptr, 0);
if (endptr == value_start_token) {
return -1;
}
entry->type = CONFIG_PARSER_TYPE_UINT;
} else {
/* Try parsing as int */
entry->value.int_val = strtod(value_start_token, &endptr);
if (endptr == value_start_token) {
return -1;
}
entry->type = CONFIG_PARSER_TYPE_INT;
}
return 0;
}
enum config_parser_ret config_parser_get_line(config_parser_handle_t handle, struct config_parser_entry *entry)
{
(void)entry;
struct config_parser *p;
config_parser_check_handle(handle);
p = CONFIG_PARSER(handle);
char *token;
int token_round = 0;
if (!entry)
return CONFIG_PARSER_PARAM_ERR;
p->buffer[0] = '\0';
if (f_gets(p->buffer, (int)p->buff_size, &p->file) == NULL)
return CONFIG_PARSER_IOERR;
token = strtok(p->buffer, token_delim);
while (token != NULL) {
/* Check for comment */
if (token[0] == '#') {
if (token_round == 0)
return CONFIG_PARSER_LINE_COMMENT;
else
break;
}
switch (token_round) {
case 0: /* KEY */
entry->name = token;
break;
case 1: /* = Symbol */
if (strcmp(token, "=")) {
return CONFIG_PARSER_LINE_MALFORM;
}
break;
case 2: /* VALUE */
if (!parse_value(entry, token))
return CONFIG_PARSER_LINE_MALFORM;
break;
default:
return CONFIG_PARSER_LINE_MALFORM;
}
token_round++;
strtok(NULL, token_delim);
}
return CONFIG_PARSER_OK;
}

View File

@ -29,6 +29,7 @@
#define _CONFIG_PARSER_H_
#include <stdint.h>
#include <stddef.h>
#include <stdbool.h>
#include <fatfs/ff.h>
@ -37,6 +38,7 @@ struct config_parser {
bool write;
FIL file;
char *buffer;
size_t buff_size;
};
typedef void * config_parser_handle_t;
@ -44,7 +46,6 @@ typedef void * config_parser_handle_t;
enum config_parser_value_type {
CONFIG_PARSER_TYPE_UINT = 0,
CONFIG_PARSER_TYPE_INT,
CONFIG_PARSER_TYPE_STRING,
CONFIG_PARSER_TYPE_FLOAT,
};
@ -53,6 +54,7 @@ enum config_parser_ret {
CONFIG_PARSER_PARAM_ERR,
CONFIG_PARSER_GENERIC_ERR,
CONFIG_PARSER_IOERR,
CONFIG_PARSER_LINE_COMMENT,
CONFIG_PARSER_LINE_TOO_LONG,
CONFIG_PARSER_LINE_MALFORM,
CONFIG_PARSER_END_REACHED,
@ -65,13 +67,12 @@ struct config_parser_entry {
union {
uint32_t uint_val;
int32_t int_val;
const char *string_val;
float float_val;
} value;
};
config_parser_handle_t config_parser_open_file(struct config_parser *config_parser, bool write, const char *file_name,
char *working_buffer);
char *working_buffer, size_t buff_size);
/**
* @brief Parse the current line in the config file.