gawk-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[gawk-diffs] [SCM] gawk branch, extgawk, updated. 1e3ac8a49caeeb991d8163


From: Arnold Robbins
Subject: [gawk-diffs] [SCM] gawk branch, extgawk, updated. 1e3ac8a49caeeb991d8163042a576a66db51c74b
Date: Mon, 18 Jun 2012 20:01:49 +0000

This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "gawk".

The branch, extgawk has been updated
       via  1e3ac8a49caeeb991d8163042a576a66db51c74b (commit)
      from  b0f08ac2443e239b0ed9cc4421758f0ed3f7a94f (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
http://git.sv.gnu.org/cgit/gawk.git/commit/?id=1e3ac8a49caeeb991d8163042a576a66db51c74b

commit 1e3ac8a49caeeb991d8163042a576a66db51c74b
Author: Arnold D. Robbins <address@hidden>
Date:   Mon Jun 18 23:00:58 2012 +0300

    Get most of array flattening done.

diff --git a/ChangeLog b/ChangeLog
index dd143a8..2e4c8cb 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,9 +1,15 @@
 2012-06-18         Arnold D. Robbins     <address@hidden>
 
        * gawkapi.h (get_array_element): Restore `wanted' paramater.
+       (awk_element_t): Use awk_value_t for index. Add awk_flat_array_t.
+       (flatten_array): Change signature to use awk_flat_array_t;
+       (release_flattened_array): Change signature to use awk_flat_array_t;
        * gawkapi.c (api_sym_update): Handle case where variable exists already.
        (api_get_array_element): Restore `wanted' paramater and pass it
        on to node_to_awk_value.
+       (api_set_array_element): Revisse to match changed element type.
+       (api_flatten_array): Revise signature, implement.
+       (api_release_flattened_array): Revise signature, implement.
 
 2012-06-17         Arnold D. Robbins     <address@hidden>
 
diff --git a/extension/ChangeLog b/extension/ChangeLog
index 4315086..54bf3f8 100644
--- a/extension/ChangeLog
+++ b/extension/ChangeLog
@@ -1,6 +1,12 @@
 2012-06-18         Arnold D. Robbins     <address@hidden>
 
-       * testext.c (test_array_elem): Add AWK_UNDEFINED for `wanted'.
+       * filefuncs.c (do_chdir): Change element use to match change types.
+       * fork.c (array_set_numeric): Ditto.
+       * testext.c (valrep2str): New function.
+       (test_array_elem): Add AWK_UNDEFINED for `wanted'. Use valrep2str.
+       Adjust use of element index.
+       (dump_array): Renamed from `dump_procinfo' and implemented.
+       (func_table): Updated.
 
 2012-06-17         Arnold D. Robbins     <address@hidden>
 
diff --git a/extension/filefuncs.c b/extension/filefuncs.c
index 433a0ea..d4e1b57 100644
--- a/extension/filefuncs.c
+++ b/extension/filefuncs.c
@@ -216,7 +216,7 @@ array_set(awk_array_t array, const char *sub, awk_value_t 
*value)
 
        memset(& element, 0, sizeof(element));
 
-       element.index = dup_string(sub, strlen(sub), & tmp)->str_value;
+       element.index = *make_string(sub, strlen(sub), & tmp);
        element.value = *value;
 
        set_array_element(array, & element);
diff --git a/extension/fork.c b/extension/fork.c
index 21a4145..58089d5 100644
--- a/extension/fork.c
+++ b/extension/fork.c
@@ -55,7 +55,7 @@ array_set_numeric(awk_array_t array, const char *sub, double 
num)
 
        memset(& element, 0, sizeof(element));
 
-       element.index = dup_string(sub, strlen(sub), & tmp)->str_value;
+       element.index = *make_string(sub, strlen(sub), & tmp);
        make_number(num, &element.value);
 
        set_array_element(array, & element);
diff --git a/extension/testext.c b/extension/testext.c
index 743a1c2..f5e16ba 100644
--- a/extension/testext.c
+++ b/extension/testext.c
@@ -42,6 +42,35 @@ static awk_ext_id_t *ext_id;
 
 int plugin_is_GPL_compatible;
 
+/* valrep2str --- turn a value into a string */
+
+static const char *
+valrep2str(const awk_value_t *value)
+{
+       static char buf[BUFSIZ];
+       int size = BUFSIZ - 3;
+
+       switch (value->val_type) {
+       case AWK_UNDEFINED:
+               strcpy(buf, "<undefined>");
+               break;
+       case AWK_ARRAY:
+               strcpy(buf, "<array>");
+               break;
+       case AWK_STRING:
+               if (value->str_value.len < size)
+                       size = value->str_value.len;
+               sprintf(buf, "\"%.*s\"",
+                               size,
+                               value->str_value.str);
+               break;
+       case AWK_NUMBER:
+               sprintf(buf, "%g", value->num_value);
+               break;
+       }
+       return buf;
+}
+
 /*
  * The awk code for these tests is embedded in this file and then extracted
  * dynamically to create the script that is run together with this extension.
@@ -51,22 +80,84 @@ int plugin_is_GPL_compatible;
  */
 
 /*
address@hidden "testext"
-#BEGIN {
-#      dump_procinfo()
-#      print ""
-#}
address@hidden "testext"
+BEGIN {
+       n = split("blacky rusty sophie raincloud lucky", pets)
+       printf "pets has %d elements\n", length(pets)
+       ret = dump_array("pets")
+       printf "dump_array(pets) returned %d\n", ret
+       print ""
+}
 */
 static awk_value_t *
-dump_procinfo(int nargs, awk_value_t *result)
+dump_array(int nargs, awk_value_t *result)
 {
+       awk_value_t value, value2;
+       awk_flat_array_t *flat_array;
+       size_t count;
+       int i;
+       char *name;
+
        assert(result != NULL);
-       /* get PROCINFO as flat array and print it */
+       make_number(0.0, result);
+
+       if (nargs != 1) {
+               printf("dump_array: nargs not right (%d should be 1)\n", nargs);
+               goto out;
+       }
+
+       /* get argument named array as flat array and print it */
+       if (get_argument(0, AWK_STRING, & value)) {
+               name = value.str_value.str;
+               if (sym_lookup(name, AWK_ARRAY, & value2))
+                       printf("dump_array: sym_lookup of %s passed\n", name);
+               else {
+                       printf("dump_array: sym_lookup of %s failed\n", name);
+                       goto out;
+               }
+       } else {
+               printf("dump_array: get_argument(0) failed\n");
+               goto out;
+       }
+
+       if (! get_element_count(value2.array_cookie, & count)) {
+               printf("dump_array: get_element_count failed\n");
+               goto out;
+       }
+
+       printf("dump_array: incoming size is %lu\n", (unsigned long) count);
+
+       if (! flatten_array(value2.array_cookie, & flat_array)) {
+               printf("dump_array: could not flatten array\n");
+               goto out;
+       }
+
+       if (flat_array->count != count) {
+               printf("dump_array: flat_array->count (%lu) != count (%lu)\n",
+                               (unsigned long) flat_array->count,
+                               (unsigned long) count);
+               goto out;
+       }
+
+       for (i = 0; i < flat_array->count; i++) {
+               printf("\t%s[\"%.*s\"] = %s\n",
+                       name,
+                       (int) flat_array->elements[i].index.str_value.len,
+                       flat_array->elements[i].index.str_value.str,
+                       valrep2str(& flat_array->elements[i].value));
+       }
+
+       if (! release_flattened_array(value2.array_cookie, flat_array)) {
+               printf("dump_array: could not release flattened array\n");
+               goto out;
+       }
+
+       make_number(1.0, result);
+out:
        return result;
 }
 
 /*
address@hidden "testext"
 BEGIN {
        testvar = "One Adam Twelve"
        ret = var_test("testvar")
@@ -243,25 +334,13 @@ test_array_elem(int nargs, awk_value_t *result)
                printf("test_array_elem: get_array_element failed\n");
                goto out;
        }
-       printf("test_array_elem: a[\"%.*s\"] = ", (int) index.str_value.len,
-                       index.str_value.str);
-       switch (value.val_type) {
-       case AWK_UNDEFINED:
-               printf("<undefined>\n");
-               break;
-       case AWK_ARRAY:
-               printf("<array>\n");
-               break;
-       case AWK_STRING:
-               printf("\"%.*s\"\n", (int) value.str_value.len, 
value.str_value.str);
-               break;
-       case AWK_NUMBER:
-               printf("%g\n", value.num_value);
-               break;
-       }
+       printf("test_array_elem: a[\"%.*s\"] = %s\n",
+                       (int) index.str_value.len,
+                       index.str_value.str,
+                       valrep2str(& value));
 
        /* change the element - "3" */
-       element.index = index.str_value;
+       element.index = index;
        (void) make_number(42.0, & element.value);
        if (! set_array_element(array.array_cookie, & element)) {
                printf("test_array_elem: set_array_element failed\n");
@@ -277,7 +356,7 @@ test_array_elem(int nargs, awk_value_t *result)
 
        /* add a new element - "7" */
        (void) make_string("7", 1, & index);
-       element.index = index.str_value;
+       element.index = index;
        (void) make_string("seven", 5, & element.value);
        if (! set_array_element(array.array_cookie, & element)) {
                printf("test_array_elem: set_array_element failed\n");
@@ -364,7 +443,7 @@ create_new_array()
        a_cookie = create_array();
 
        (void) make_string("hello", 5, & index);
-       element.index = index.str_value;
+       element.index = index;
        (void) make_string("world", 5, & element.value);
        if (! set_array_element(a_cookie, & element)) {
                printf("create_new_array:%d: set_array_element failed\n", 
__LINE__);
@@ -372,7 +451,7 @@ create_new_array()
        }
 
        (void) make_string("answer", 6, & index);
-       element.index = index.str_value;
+       element.index = index;
        (void) make_number(42.0, & element.value);
        if (! set_array_element(a_cookie, & element)) {
                printf("create_new_array:%d: set_array_element failed\n", 
__LINE__);
@@ -425,7 +504,7 @@ static void at_exit2(void *data, int exit_status)
 }
 
 static awk_ext_func_t func_table[] = {
-       { "dump_procinfo", dump_procinfo, 0 },
+       { "dump_array", dump_array, 1 },
        { "var_test", var_test, 1 },
        { "test_errno", test_errno, 0 },
        { "test_array_size", test_array_size, 1 },
diff --git a/gawkapi.c b/gawkapi.c
index b616fbf..b1fba48 100644
--- a/gawkapi.c
+++ b/gawkapi.c
@@ -478,10 +478,11 @@ api_set_array_element(awk_ext_id_t id, awk_array_t 
a_cookie,
        if (   array == NULL
            || array->type != Node_var_array
            || element == NULL
-           || element->index.str == NULL)
+           || element->index.str_value.str == NULL)
                return false;
 
-       tmp = make_string(element->index.str, element->index.len);
+       tmp = make_string(element->index.str_value.str,
+                       element->index.str_value.len);
        aptr = assoc_lookup(array, tmp);
        unref(tmp);
        unref(*aptr);
@@ -570,14 +571,56 @@ api_clear_array(awk_ext_id_t id, awk_array_t a_cookie)
        return true;
 }
 
-/* Flatten out an array so that it can be looped over easily. */
+/* api_flatten_array --- flatten out an array so that it can be looped over 
easily. */
+
 static awk_bool_t
 api_flatten_array(awk_ext_id_t id,
                awk_array_t a_cookie,
-               size_t *count,
-               awk_element_t **data)
+               awk_flat_array_t **data)
 {
-       return true;    /* for now */
+       NODE **list;
+       size_t i, j;
+       NODE *array = (NODE *) a_cookie;
+       size_t alloc_size;
+
+       if (   array == NULL
+           || array->type != Node_var_array
+           || array->table_size == 0
+           || data == NULL)
+               return false;
+
+       alloc_size = sizeof(awk_flat_array_t) +
+                       (array->table_size - 1) * sizeof(awk_element_t);
+
+       emalloc(*data, awk_flat_array_t *, alloc_size,
+                       "api_flatten_array");
+       memset(*data, 0, alloc_size);
+
+       list = assoc_list(array, "@unsorted", ASORTI);
+
+       (*data)->opaque1 = array;
+       (*data)->opaque2 = list;
+       (*data)->count = array->table_size;
+
+       for (i = j = 0; i < 2 * array->table_size; i += 2, j++) {
+               NODE *index, *value;
+
+               index = force_string(list[i]);
+               value = list[i + 1]; /* number or string or subarray */
+
+               /* convert index and value to ext types */
+               if (! node_to_awk_value(index,
+                               & (*data)->elements[j].index, AWK_UNDEFINED)) {
+                       fatal(_("api_flatten_array: could not convert index 
%d\n"),
+                                               (int) i);
+               }
+               if (! node_to_awk_value(value,
+                               & (*data)->elements[j].value, AWK_UNDEFINED)) {
+                       fatal(_("api_flatten_array: could not convert value 
%d\n"),
+                                               (int) i);
+               }
+       }
+       return true;
 }
 
 /*
@@ -587,9 +630,30 @@ api_flatten_array(awk_ext_id_t id,
 static awk_bool_t
 api_release_flattened_array(awk_ext_id_t id,
                awk_array_t a_cookie,
-               size_t count,
-               awk_element_t *data)
+               awk_flat_array_t *data)
 {
+       NODE *array = a_cookie;
+       NODE **list;
+       size_t i;
+
+       if (   array == NULL
+           || array->type != Node_var_array
+           || data == NULL
+           || array != (NODE *) data->opaque1
+           || data->count != array->table_size
+           || data->opaque2 == NULL)
+               return false;
+
+       list = (NODE **) data->opaque2;
+
+       /* FIXME: Delete items flagged for delete. */
+
+       /* free index nodes */
+       for (i = 0; i < 2 * array->table_size; i += 2)
+               unref(list[i]);
+
+       efree(list);
+
        return true;    /* for now */
 }
 
diff --git a/gawkapi.h b/gawkapi.h
index 7fdd763..8102f70 100644
--- a/gawkapi.h
+++ b/gawkapi.h
@@ -145,10 +145,23 @@ typedef struct awk_element {
                AWK_ELEMENT_DELETE = 1          /* set by extension if
                                                   should be deleted */
        } flags;
-       awk_string_t    index;
+       awk_value_t     index;
        awk_value_t     value;
 } awk_element_t;
 
+#ifdef GAWK
+#define awk_const
+#else
+#define awk_const const
+#endif
+
+typedef struct awk_flat_array {
+       void *opaque1;                  /* private data for use by gawk */
+       void *opaque2;                  /* private data for use by gawk */
+       awk_const size_t count;         /* how many elements */
+       awk_element_t elements[1];      /* will be extended */
+} awk_flat_array_t;
+
 /*
  * A record describing an extension function. Upon being
  * loaded, the extension should pass in one of these for
@@ -222,6 +235,11 @@ typedef struct gawk_api {
                                          awk_valtype_t wanted,
                                          awk_value_t *result);
 
+       /*
+        * FIXME: Missing update_argument to convert an undefined
+        * argument into an array or scalar.
+        */
+
        /* Functions to print messages */
        void (*api_fatal)(awk_ext_id_t id, const char *format, ...);
        void (*api_warning)(awk_ext_id_t id, const char *format, ...);
@@ -257,7 +275,8 @@ typedef struct gawk_api {
         * returned. Returns false if the variable doesn't exist
         * or the wrong type was requested.
         * In the latter case, fills in vaule->val_type with the real type.
-        * Built-in variables (except PROCINFO) may not be accessed by an 
extension.
+        * Built-in variables (except PROCINFO) may not be accessed by an
+        * extension.
         *
         *      awk_value_t val;
         *      if (! api->sym_lookup(id, name, wanted, & val))
@@ -322,8 +341,7 @@ typedef struct gawk_api {
        /* Flatten out an array so that it can be looped over easily. */
        awk_bool_t (*flatten_array)(awk_ext_id_t id,
                        awk_array_t a_cookie,
-                       size_t *count,
-                       awk_element_t **data);
+                       awk_flat_array_t **data);
 
        /*
         * When done, delete any marked elements, release the memory.
@@ -332,8 +350,7 @@ typedef struct gawk_api {
         */
        awk_bool_t (*release_flattened_array)(awk_ext_id_t id,
                        awk_array_t a_cookie,
-                       size_t count,
-                       awk_element_t *data);
+                       awk_flat_array_t *data);
 } gawk_api_t;
 
 #ifndef GAWK   /* these are not for the gawk code itself! */
@@ -385,11 +402,11 @@ typedef struct gawk_api {
 
 #define clear_array(array)     (api->clear_array(ext_id, array))
 
-#define flatten_array(array, count, data) \
-       (api->flatten_array(ext_id, array, count, data))
+#define flatten_array(array, data) \
+       (api->flatten_array(ext_id, array, data))
 
-#define release_flattened_array(array, count, data) \
-       (api->release_flattened_array(ext_id, array, count, data))
+#define release_flattened_array(array, data) \
+       (api->release_flattened_array(ext_id, array, data))
 
 #define emalloc(pointer, type, size, message) \
        do { \
diff --git a/test/ChangeLog b/test/ChangeLog
index a171701..f8fc382 100644
--- a/test/ChangeLog
+++ b/test/ChangeLog
@@ -1,6 +1,8 @@
 2012-06-18         Arnold D. Robbins     <address@hidden>
 
        * Makefile.am (testext): New test.
+       (EXTRA_DIST): Add new file testext.ok.
+       (SHLIB_TESTS): Add testext.
        (clean): Add testext.awk to the list.
        * testext.ok: New file.
 
diff --git a/test/testext.ok b/test/testext.ok
index 9cac57a..83711a7 100644
--- a/test/testext.ok
+++ b/test/testext.ok
@@ -1,3 +1,13 @@
+pets has 5 elements
+dump_array: sym_lookup of pets passed
+dump_array: incoming size is 5
+       pets["1"] = "blacky"
+       pets["2"] = "rusty"
+       pets["3"] = "sophie"
+       pets["4"] = "raincloud"
+       pets["5"] = "lucky"
+dump_array(pets) returned 1
+
 var_test: sym_lookup of ARGC passed - did not get a value
 var_test: sym_update("testvar") succeeded
 var_test() returned 1, test_var = 42

-----------------------------------------------------------------------

Summary of changes:
 ChangeLog             |    6 ++
 extension/ChangeLog   |    8 +++-
 extension/filefuncs.c |    2 +-
 extension/fork.c      |    2 +-
 extension/testext.c   |  137 ++++++++++++++++++++++++++++++++++++++----------
 gawkapi.c             |   80 ++++++++++++++++++++++++++---
 gawkapi.h             |   37 ++++++++++----
 test/ChangeLog        |    2 +
 test/testext.ok       |   10 ++++
 9 files changed, 234 insertions(+), 50 deletions(-)


hooks/post-receive
-- 
gawk



reply via email to

[Prev in Thread] Current Thread [Next in Thread]