Radish alpha
H
rad:z3QDZAW2FAfuLvihrhiyDC9fAD8G9
HardenedBSD Package Manager
Radicle
Git
Sync version 0.2.3 from libucl
Baptiste Daroussin committed 12 years ago
commit 2e0aa7e423dfc498bd3bd721f6f37ed728c5b189
parent 28d5edb
3 files changed +137 -19
modified external/libucl/include/ucl.h
@@ -774,6 +774,16 @@ unsigned char *ucl_object_emit (ucl_object_t *obj, enum ucl_emitter emit_type);
 */
bool ucl_pubkey_add (struct ucl_parser *parser, const unsigned char *key, size_t len);

+
/**
+
 * Set FILENAME and CURDIR variables in parser
+
 * @param parser parser object
+
 * @param filename filename to set or NULL to set FILENAME to "undef" and CURDIR to getcwd()
+
 * @param need_expand perform realpath() if this variable is true and filename is not NULL
+
 * @return true if variables has been set
+
 */
+
bool ucl_parser_set_filevars (struct ucl_parser *parser, const char *filename,
+
		bool need_expand);
+

typedef void* ucl_object_iter_t;

/**
modified external/libucl/src/ucl_parser.c
@@ -86,8 +86,14 @@ ucl_chunk_restore_state (struct ucl_chunk *chunk, struct ucl_parser_saved_state
static inline void
ucl_set_err (struct ucl_chunk *chunk, int code, const char *str, UT_string **err)
{
-
	ucl_create_err (err, "error on line %d at column %d: '%s', character: '%c'",
-
			chunk->line, chunk->column, str, *chunk->pos);
+
	if (isgraph (*chunk->pos)) {
+
		ucl_create_err (err, "error on line %d at column %d: '%s', character: '%c'",
+
				chunk->line, chunk->column, str, *chunk->pos);
+
	}
+
	else {
+
		ucl_create_err (err, "error on line %d at column %d: '%s', character: '0x%02x'",
+
				chunk->line, chunk->column, str, (int)*chunk->pos);
+
	}
}

/**
@@ -926,6 +932,12 @@ ucl_parse_key (struct ucl_parser *parser, struct ucl_chunk *chunk, bool *next_ke
				*end_of_object = true;
				return true;
			}
+
			else if (*p == '.') {
+
				ucl_chunk_skipc (chunk, p);
+
				parser->prev_state = parser->state;
+
				parser->state = UCL_STATE_MACRO_NAME;
+
				return true;
+
			}
			else {
				/* Invalid identifier */
				ucl_set_err (chunk, UCL_ESYNTAX, "key must begin with a letter", &parser->err);
@@ -1534,8 +1546,14 @@ ucl_state_machine (struct ucl_parser *parser)
	bool next_key = false, end_of_object = false;

	if (parser->top_obj == NULL) {
-
		obj = ucl_add_parser_stack (NULL, parser, false, 0);
+
		if (*chunk->pos == '[') {
+
			obj = ucl_add_parser_stack (NULL, parser, true, 0);
+
		}
+
		else {
+
			obj = ucl_add_parser_stack (NULL, parser, false, 0);
+
		}
		parser->top_obj = obj;
+
		parser->cur_obj = obj;
		parser->state = UCL_STATE_INIT;
	}

@@ -1548,7 +1566,7 @@ ucl_state_machine (struct ucl_parser *parser)
			 * if we got [ or { correspondingly or can just treat new data as
			 * a key of newly created object
			 */
-
			obj = parser->top_obj;
+
			obj = parser->cur_obj;
			if (!ucl_skip_comments (parser)) {
				parser->prev_state = parser->state;
				parser->state = UCL_STATE_ERROR;
@@ -1558,14 +1576,10 @@ ucl_state_machine (struct ucl_parser *parser)
				p = chunk->pos;
				if (*p == '[') {
					parser->state = UCL_STATE_VALUE;
-
					obj->type = UCL_ARRAY;
-
					ucl_hash_destroy (obj->value.ov, NULL);
-
					obj->value.av = NULL;
					ucl_chunk_skipc (chunk, p);
				}
				else {
					parser->state = UCL_STATE_KEY;
-
					obj->type = UCL_OBJECT;
					if (*p == '{') {
						ucl_chunk_skipc (chunk, p);
					}
@@ -1675,7 +1689,7 @@ ucl_state_machine (struct ucl_parser *parser)
				return false;
			}
			macro_len = ucl_expand_variable (parser, &macro_escaped, macro_start, macro_len);
-
			parser->state = UCL_STATE_KEY;
+
			parser->state = parser->prev_state;
			if (macro_escaped == NULL) {
				if (!macro->handler (macro_start, macro_len, macro->ud)) {
					return false;
@@ -1714,6 +1728,9 @@ ucl_parser_new (int flags)

	new->flags = flags;

+
	/* Initial assumption about filevars */
+
	ucl_parser_set_filevars (new, NULL, false);
+

	return new;
}

@@ -1736,16 +1753,51 @@ void
ucl_parser_register_variable (struct ucl_parser *parser, const char *var,
		const char *value)
{
-
	struct ucl_variable *new;
+
	struct ucl_variable *new = NULL, *cur;
+

+
	if (var == NULL) {
+
		return;
+
	}

-
	new = UCL_ALLOC (sizeof (struct ucl_variable));
-
	memset (new, 0, sizeof (struct ucl_variable));
-
	new->var = strdup (var);
-
	new->var_len = strlen (var);
-
	new->value = strdup (value);
-
	new->value_len = strlen (value);
+
	/* Find whether a variable already exists */
+
	LL_FOREACH (parser->variables, cur) {
+
		if (strcmp (cur->var, var) == 0) {
+
			new = cur;
+
			break;
+
		}
+
	}
+

+
	if (value == NULL) {
+

+
		if (new != NULL) {
+
			/* Remove variable */
+
			LL_DELETE (parser->variables, new);
+
			free (new->var);
+
			free (new->value);
+
			UCL_FREE (sizeof (struct ucl_variable), new);
+
		}
+
		else {
+
			/* Do nothing */
+
			return;
+
		}
+
	}
+
	else {
+
		if (new == NULL) {
+
			new = UCL_ALLOC (sizeof (struct ucl_variable));
+
			memset (new, 0, sizeof (struct ucl_variable));
+
			new->var = strdup (var);
+
			new->var_len = strlen (var);
+
			new->value = strdup (value);
+
			new->value_len = strlen (value);

-
	LL_PREPEND (parser->variables, new);
+
			LL_PREPEND (parser->variables, new);
+
		}
+
		else {
+
			free (new->value);
+
			new->value = strdup (value);
+
			new->value_len = strlen (value);
+
		}
+
	}
}

bool
modified external/libucl/src/ucl_util.c
@@ -25,6 +25,8 @@
#include "ucl_internal.h"
#include "ucl_chartable.h"

+
#include <libgen.h> /* For dirname */
+

#ifdef HAVE_OPENSSL
#include <openssl/err.h>
#include <openssl/sha.h>
@@ -439,7 +441,7 @@ ucl_fetch_file (const unsigned char *filename, unsigned char **buf, size_t *bufl
	int fd;
	struct stat st;

-
	if (stat (filename, &st) == -1) {
+
	if (stat (filename, &st) == -1 || !S_ISREG (st.st_mode)) {
		ucl_create_err (err, "cannot stat file %s: %s",
				filename, strerror (errno));
		return false;
@@ -535,6 +537,7 @@ ucl_include_url (const unsigned char *data, size_t len,
	size_t buflen = 0;
	struct ucl_chunk *chunk;
	char urlbuf[PATH_MAX];
+
	int prev_state;

	snprintf (urlbuf, sizeof (urlbuf), "%.*s", (int)len, data);

@@ -566,6 +569,9 @@ ucl_include_url (const unsigned char *data, size_t len,
#endif
	}

+
	prev_state = parser->state;
+
	parser->state = UCL_STATE_INIT;
+

	res = ucl_parser_add_chunk (parser, buf, buflen);
	if (res == true) {
		/* Remove chunk from the stack */
@@ -575,6 +581,8 @@ ucl_include_url (const unsigned char *data, size_t len,
			UCL_FREE (sizeof (struct ucl_chunk), chunk);
		}
	}
+

+
	parser->state = prev_state;
	free (buf);

	return res;
@@ -597,6 +605,7 @@ ucl_include_file (const unsigned char *data, size_t len,
	unsigned char *buf = NULL;
	size_t buflen;
	char filebuf[PATH_MAX], realbuf[PATH_MAX];
+
	int prev_state;

	snprintf (filebuf, sizeof (filebuf), "%.*s", (int)len, data);
	if (realpath (filebuf, realbuf) == NULL) {
@@ -634,6 +643,11 @@ ucl_include_file (const unsigned char *data, size_t len,
#endif
	}

+
	ucl_parser_set_filevars (parser, realbuf, false);
+

+
	prev_state = parser->state;
+
	parser->state = UCL_STATE_INIT;
+

	res = ucl_parser_add_chunk (parser, buf, buflen);
	if (res == true) {
		/* Remove chunk from the stack */
@@ -643,6 +657,9 @@ ucl_include_file (const unsigned char *data, size_t len,
			UCL_FREE (sizeof (struct ucl_chunk), chunk);
		}
	}
+

+
	parser->state = prev_state;
+

	if (buflen > 0) {
		munmap (buf, buflen);
	}
@@ -693,16 +710,55 @@ ucl_includes_handler (const unsigned char *data, size_t len, void* ud)
}

bool
+
ucl_parser_set_filevars (struct ucl_parser *parser, const char *filename, bool need_expand)
+
{
+
	char realbuf[PATH_MAX], *curdir;
+

+
	if (filename != NULL) {
+
		if (need_expand) {
+
			if (realpath (filename, realbuf) == NULL) {
+
				return false;
+
			}
+
		}
+
		else {
+
			ucl_strlcpy (realbuf, filename, sizeof (realbuf));
+
		}
+

+
		/* Define variables */
+
		ucl_parser_register_variable (parser, "FILENAME", realbuf);
+
		curdir = dirname (realbuf);
+
		ucl_parser_register_variable (parser, "CURDIR", curdir);
+
	}
+
	else {
+
		/* Set everything from the current dir */
+
		curdir = getcwd (realbuf, sizeof (realbuf));
+
		ucl_parser_register_variable (parser, "FILENAME", "undef");
+
		ucl_parser_register_variable (parser, "CURDIR", curdir);
+
	}
+

+
	return true;
+
}
+

+
bool
ucl_parser_add_file (struct ucl_parser *parser, const char *filename)
{
	unsigned char *buf;
	size_t len;
	bool ret;
+
	char realbuf[PATH_MAX];
+

+
	if (realpath (filename, realbuf) == NULL) {
+
		ucl_create_err (&parser->err, "cannot open file %s: %s",
+
				filename,
+
				strerror (errno));
+
		return false;
+
	}

-
	if (!ucl_fetch_file (filename, &buf, &len, &parser->err)) {
+
	if (!ucl_fetch_file (realbuf, &buf, &len, &parser->err)) {
		return false;
	}

+
	ucl_parser_set_filevars (parser, realbuf, false);
	ret = ucl_parser_add_chunk (parser, buf, len);

	if (len > 0) {