]> git.ipfire.org Git - pakfire.git/commitdiff
parser: Move namespace & name to stack
authorMichael Tremer <michael.tremer@ipfire.org>
Sat, 1 May 2021 16:59:53 +0000 (16:59 +0000)
committerMichael Tremer <michael.tremer@ipfire.org>
Sat, 1 May 2021 16:59:53 +0000 (16:59 +0000)
Signed-off-by: Michael Tremer <michael.tremer@ipfire.org>
src/libpakfire/include/pakfire/parser.h
src/libpakfire/parser.c
src/libpakfire/parser/grammar.y
tests/libpakfire/parser.c

index e6f7d171fd63ad683bf74ab6b32828b3acc4dcff..f7313b472755d694aeef4fd82468c3cd3e9f894d 100644 (file)
@@ -77,11 +77,13 @@ const char* pakfire_parser_error_get_message(struct pakfire_parser_error* error)
 
 #ifdef PAKFIRE_PRIVATE
 
+#include <linux/limits.h>
+
 Pakfire pakfire_parser_get_pakfire(PakfireParser parser);
 
 struct pakfire_parser_declaration {
-       char* namespace;
-       char* name;
+       char namespace[NAME_MAX];
+       char name[NAME_MAX];
        char* value;
        enum flags {
                PAKFIRE_PARSER_DECLARATION_NONE                         = 0,
index b22e32d03b5fd891281ecd66543593486b95bf4d..e33769bb8422a421b8013b679f73252afd8c9b58 100644 (file)
@@ -19,6 +19,7 @@
 #############################################################################*/
 
 #include <errno.h>
+#include <linux/limits.h>
 #include <regex.h>
 #include <stdlib.h>
 #include <string.h>
@@ -148,10 +149,6 @@ static void pakfire_parser_free_declarations(PakfireParser parser) {
                struct pakfire_parser_declaration* d = parser->declarations[i];
 
                // Free everything
-               if (d->namespace)
-                       free(d->namespace);
-               if (d->name)
-                       free(d->name);
                if (d->value)
                        free(d->value);
                free(d);
@@ -199,23 +196,22 @@ PAKFIRE_EXPORT PakfireParser pakfire_parser_get_parent(PakfireParser parser) {
 
 static struct pakfire_parser_declaration* pakfire_parser_get_declaration(
                PakfireParser parser, const char* namespace, const char* name) {
-       struct pakfire_parser_declaration* d;
+       if (!name) {
+               errno = EINVAL;
+               return NULL;
+       }
+
+       if (!namespace)
+               namespace = "";
 
+       struct pakfire_parser_declaration* d;
        for (unsigned i = 0; i < parser->num_declarations; i++) {
                d = parser->declarations[i];
                if (!d)
                        break;
 
-               // Skip if d does not have a namespace set
-               if (namespace && !d->namespace)
-                       continue;
-
-               // Skip if namespace does not match
-               if (namespace && strcmp(d->namespace, namespace) != 0)
-                       continue;
-
-               // Compare the name
-               if (strcmp(d->name, name) == 0)
+               // Return if namespace and name match
+               if ((strcmp(d->namespace, namespace) == 0) && (strcmp(d->name, name) == 0))
                        return d;
        }
 
@@ -227,6 +223,9 @@ PAKFIRE_EXPORT int pakfire_parser_set(PakfireParser parser,
        if (!name)
                return -EINVAL;
 
+       if (!namespace)
+               namespace = "";
+
        // Handle when name already exists
        struct pakfire_parser_declaration* d = pakfire_parser_get_declaration(parser, namespace, name);
        if (d) {
@@ -251,14 +250,11 @@ PAKFIRE_EXPORT int pakfire_parser_set(PakfireParser parser,
        if (!d)
                return -1;
 
-       // Copy namespace
-       if (namespace)
-               d->namespace = strdup(namespace);
-       else
-               d->namespace = NULL;
+       // Store namespace
+       pakfire_string_set(d->namespace, namespace);
 
        // Import name & value
-       d->name = strdup(name);
+       pakfire_string_set(d->name, name);
        if (value)
                d->value = strdup(value);
 
@@ -328,12 +324,12 @@ static void pakfire_parser_strip_namespace(char** s) {
        if (pos)
                *s[pos - *s] = '\0';
        else
-               *s = NULL;
+               *s[0] = '\0';
 }
 
 static struct pakfire_parser_declaration* pakfire_parser_find_declaration(
                PakfireParser parser, const char* namespace, const char* name) {
-       char* n = NULL;
+       char* n = "";
 
        // Create a working copy of the namespace variable
        if (namespace)
@@ -351,7 +347,7 @@ static struct pakfire_parser_declaration* pakfire_parser_find_declaration(
                        break;
 
                // End if namespace is empty
-               if (!n)
+               if (!n || !*n)
                        break;
 
                /*
@@ -624,32 +620,27 @@ PAKFIRE_EXPORT char** pakfire_parser_get_split(PakfireParser parser,
 
 PAKFIRE_EXPORT int pakfire_parser_merge(PakfireParser parser1, PakfireParser parser2) {
        DEBUG(parser1->pakfire, "Merging parsers %p and %p\n", parser1, parser2);
+       char namespace[NAME_MAX*2+1];
 
        // Do not try to merge a parser with itself
        if (parser1 == parser2)
                return EINVAL;
 
-       char* namespace = NULL;
-
        for (unsigned int i = 0; i < parser2->num_declarations; i++) {
                struct pakfire_parser_declaration* d = parser2->declarations[i];
                if (!d)
                        break;
 
-               if (parser2->namespace && d->namespace)
-                       asprintf(&namespace, "%s.%s", parser2->namespace, d->namespace);
+               if (parser2->namespace && *d->namespace)
+                       pakfire_string_format(namespace, "%s.%s", parser2->namespace, d->namespace);
                else if (parser2->namespace)
-                       asprintf(&namespace, "%s", parser2->namespace);
-               else if (d->namespace)
-                       asprintf(&namespace, "%s", d->namespace);
+                       pakfire_string_set(namespace, parser2->namespace);
+               else if (*d->namespace)
+                       pakfire_string_set(namespace, d->namespace);
                else
-                       namespace = NULL;
+                       pakfire_string_set(namespace, "");
 
                int r = pakfire_parser_set(parser1, namespace, d->name, d->value);
-
-               if (namespace)
-                       free(namespace);
-
                if (r)
                        return r;
        }
@@ -692,18 +683,17 @@ PAKFIRE_EXPORT int pakfire_parser_parse(PakfireParser parser,
 }
 
 PAKFIRE_EXPORT char* pakfire_parser_dump(PakfireParser parser) {
+       char buffer[NAME_MAX*2 + 1];
        char* s = NULL;
 
-       char buffer[1024];
-
        for (unsigned int i = 0; i < parser->num_declarations; i++) {
                struct pakfire_parser_declaration* d = parser->declarations[i];
 
                if (d) {
-                       if (d->namespace)
-                               snprintf(buffer, sizeof(buffer) - 1, "%s.%s", d->namespace, d->name);
+                       if (*d->namespace)
+                               pakfire_string_format(buffer, "%s.%s", d->namespace, d->name);
                        else
-                               snprintf(buffer, sizeof(buffer) - 1, "%s", d->name);
+                               pakfire_string_set(buffer, d->name);
 
                        asprintf(&s, "%s%-24s = %s\n", (s) ? s : "", buffer, d->value);
                }
index b08ddf4e4a1e31df440534f0ee85064e69806a20..f67a5c7edfbc4d5a66c92bf6bff39e276633a430 100644 (file)
@@ -75,20 +75,17 @@ static void yyerror(Pakfire pakfire, PakfireParser* result,
 static PakfireParser make_if_stmt(Pakfire pakfire, PakfireParser* parser, const enum operator op,
                const char* val1, const char* val2, PakfireParser if_block, PakfireParser else_block);
 
-static inline int pakfire_parser_new_declaration(
+static int pakfire_parser_new_declaration(
                struct pakfire_parser_declaration** declaration, const char* name, const char* value, int flags) {
        if (!name)
                return EINVAL;
 
-       struct pakfire_parser_declaration* d = malloc(sizeof(*d));
+       struct pakfire_parser_declaration* d = calloc(1, sizeof(*d));
        if (!d)
                return ENOMEM;
 
-       // Set namespace
-       d->namespace = NULL;
-
-       // Copy name
-       d->name = strdup(name);
+       // Set name
+       pakfire_string_set(d->name, name);
 
        // Copy value
        if (value)
@@ -105,8 +102,6 @@ static inline int pakfire_parser_new_declaration(
 }
 
 static void pakfire_parser_free_declaration(struct pakfire_parser_declaration* declaration) {
-       free(declaration->name);
-
        if (declaration->value)
                free(declaration->value);
 
index 25929810ac29e730dfe0a46ca3410a82d1cc532e..113c2c97d0f6cbd1d07190e88344e9cd49a34313 100644 (file)
@@ -86,7 +86,7 @@ static int test_parser(const struct test* t) {
 
        // Get the value of c
        value = pakfire_parser_get(parser, NULL, "c");
-       ASSERT_STRING_EQUALS(value, "1");
+       ASSERT_STRING_EQUALS(value, "");
 
        // Dump the parser
        char* s = pakfire_parser_dump(parser);