[v2,4/5] Lua: Dump tables in Lua stack recursive

Message ID 1515769128-29657-4-git-send-email-stefan@herbrechtsmeier.net
State New
Headers show
Series
  • [v2,1/5] dict: Rename dictionary struct and its key to distinguish it from simple lists
Related show

Commit Message

Stefan Herbrechtsmeier Jan. 12, 2018, 2:58 p.m.
From: Stefan Herbrechtsmeier <stefan.herbrechtsmeier@weidmueller.com>

Signed-off-by: Stefan Herbrechtsmeier <stefan.herbrechtsmeier@weidmueller.com>
---

Changes in v2: None

 corelib/lua_interface.c | 87 +++++++++++++++++++++++++++++--------------------
 1 file changed, 51 insertions(+), 36 deletions(-)

Comments

Christian Storm Jan. 15, 2018, 7:28 a.m. | #1
Hi Stefan,

> Signed-off-by: Stefan Herbrechtsmeier <stefan.herbrechtsmeier@weidmueller.com>
> ---
> 
> Changes in v2: None
> 
>  corelib/lua_interface.c | 87 +++++++++++++++++++++++++++++--------------------
>  1 file changed, 51 insertions(+), 36 deletions(-)
> 
> diff --git a/corelib/lua_interface.c b/corelib/lua_interface.c
> index b1a3a92..872cb2f 100644
> --- a/corelib/lua_interface.c
> +++ b/corelib/lua_interface.c
> @@ -74,8 +74,54 @@ static bool is_type(lua_State *L, uintptr_t type)
>  }
>  #endif
>  
> +static void lua_dump_table(lua_State *L, char *str)
> +{
> +	char *s;
> +
> +	/* Stack: table, ... */
> +	lua_pushnil(L);
> +	/* Stack: nil, table, ... */
> +	while (lua_next(L, -2)) {
> +		/* Stack: value, key, table, ... */
> +		lua_pushvalue(L, -2);
> +		/* Stack: key, value, key, table, ... */
> +		switch(lua_type(L, -2)) {
> +			case LUA_TSTRING:
> +			case LUA_TNUMBER:
> +				TRACE("%s %s = %s", str,
> +					lua_tostring(L, -1),
> +					lua_tostring(L, -2));
> +				break;
> +			case LUA_TFUNCTION:
> +				TRACE("%s %s()", str,
> +					lua_tostring(L, -1));
> +				break;
> +			case LUA_TTABLE:
> +				if (asprintf(&s, "%s %s:", str, lua_tostring(L, -1)) != -1) {
> +					lua_pushvalue(L, -2);
> +					lua_dump_table(L, s);

Maybe some kind of indentation or prefix would be useful here
to indicate the level or "deepness" of the table currently 
being processed?


> +					lua_pop(L, 1);
> +					free(s);
> +				}
> +				break;
> +			case LUA_TBOOLEAN:
> +				TRACE("%s %s = %s", str,
> +					lua_tostring(L, -1),
> +					(lua_toboolean(L, -2) ? "true" : "false"));
> +				break;
> +			default:
> +				TRACE("%s %s = <unparsed type>", str,
> +					lua_tostring(L, -1));
> +		}
> +		lua_pop(L, 2);
> +		/* Stack: key, table, ... */
> +	}
> +	/* Stack: table, ... */
> +}
> +
>  void LUAstackDump(lua_State *L)
>  {
> +	char *s;
>  	int top = lua_gettop(L);
>  	for (int i = 1; i <= top; i++) {
>  		int t = lua_type(L, i);
> @@ -97,43 +143,12 @@ void LUAstackDump(lua_State *L)
>  				break;
>  			}
>  			case LUA_TTABLE: {
> -				lua_pushvalue(L, -1);
> -				lua_pushnil(L);
> -				/* Stack: nil, table */
> -				while (lua_next(L, -2)) {
> -					/* Stack: value, key, table */
> -					lua_pushvalue(L, -2);
> -					/* Stack: key, value, key, table */
> -					switch(lua_type(L, -2)) {
> -						case LUA_TSTRING:
> -						case LUA_TNUMBER:
> -							TRACE("(%d) [table ] %s = %s", i,
> -								lua_tostring(L, -1),
> -								lua_tostring(L, -2));
> -							break;
> -						case LUA_TFUNCTION:
> -							TRACE("(%d) [table ] %s()", i,
> -								lua_tostring(L, -1));
> -							break;
> -						case LUA_TTABLE:
> -							TRACE("(%d) [table ] %s <table>", i,
> -								lua_tostring(L, -1));
> -							break;
> -						case LUA_TBOOLEAN:
> -							TRACE("(%d) [table ] %s = %s", i,
> -								lua_tostring(L, -1),
> -								(lua_toboolean(L, -2) ? "true" : "false"));
> -							break;
> -						default:
> -							TRACE("(%d) [table ] %s = <unparsed type>", i,
> -								lua_tostring(L, -1));
> -					}
> -					lua_pop(L, 2);
> -					/* Stack: key, table */
> +				if (asprintf(&s, "(%d) [table ]", i) != -1) {

Well, there's include/util.h:30:#define ENOMEM_ASPRINTF	-1 now, you
may use that, for consistency. Same applies above.

> +					lua_pushvalue(L, -1);
> +					lua_dump_table(L, s);
> +					lua_pop(L, 1);
> +					free(s);
>  				}
> -				/* Stack: table */
> -				lua_pop(L, 1);
> -				/* Stack: <empty> */
>  				break;
>  			}
>  			default: {
> -- 
> 2.7.4
> 


Besten Gruß,
   Christian
Stefan Herbrechtsmeier Jan. 15, 2018, 7:22 p.m. | #2
Hi Christian,

Am 15.01.2018 um 08:28 schrieb Christian Storm:
>> Signed-off-by: Stefan Herbrechtsmeier <stefan.herbrechtsmeier@weidmueller.com>
>> ---
>>
>> Changes in v2: None
>>
>>   corelib/lua_interface.c | 87 +++++++++++++++++++++++++++++--------------------
>>   1 file changed, 51 insertions(+), 36 deletions(-)
>>
>> diff --git a/corelib/lua_interface.c b/corelib/lua_interface.c
>> index b1a3a92..872cb2f 100644
>> --- a/corelib/lua_interface.c
>> +++ b/corelib/lua_interface.c
>> @@ -74,8 +74,54 @@ static bool is_type(lua_State *L, uintptr_t type)
>>   }
>>   #endif
>>   
>> +static void lua_dump_table(lua_State *L, char *str)
>> +{
>> +	char *s;
>> +
>> +	/* Stack: table, ... */
>> +	lua_pushnil(L);
>> +	/* Stack: nil, table, ... */
>> +	while (lua_next(L, -2)) {
>> +		/* Stack: value, key, table, ... */
>> +		lua_pushvalue(L, -2);
>> +		/* Stack: key, value, key, table, ... */
>> +		switch(lua_type(L, -2)) {
>> +			case LUA_TSTRING:
>> +			case LUA_TNUMBER:
>> +				TRACE("%s %s = %s", str,
>> +					lua_tostring(L, -1),
>> +					lua_tostring(L, -2));
>> +				break;
>> +			case LUA_TFUNCTION:
>> +				TRACE("%s %s()", str,
>> +					lua_tostring(L, -1));
>> +				break;
>> +			case LUA_TTABLE:
>> +				if (asprintf(&s, "%s %s:", str, lua_tostring(L, -1)) != -1) {
>> +					lua_pushvalue(L, -2);
>> +					lua_dump_table(L, s);
> Maybe some kind of indentation or prefix would be useful here
> to indicate the level or "deepness" of the table currently
> being processed?

The table name is added to the str variable and thereby prefix:
(%d) [table ] name1: name2: name3: value

>> +					lua_pop(L, 1);
>> +					free(s);
>> +				}
>> +				break;
>> +			case LUA_TBOOLEAN:
>> +				TRACE("%s %s = %s", str,
>> +					lua_tostring(L, -1),
>> +					(lua_toboolean(L, -2) ? "true" : "false"));
>> +				break;
>> +			default:
>> +				TRACE("%s %s = <unparsed type>", str,
>> +					lua_tostring(L, -1));
>> +		}
>> +		lua_pop(L, 2);
>> +		/* Stack: key, table, ... */
>> +	}
>> +	/* Stack: table, ... */
>> +}
>> +
>>   void LUAstackDump(lua_State *L)
>>   {
>> +	char *s;
>>   	int top = lua_gettop(L);
>>   	for (int i = 1; i <= top; i++) {
>>   		int t = lua_type(L, i);
>> @@ -97,43 +143,12 @@ void LUAstackDump(lua_State *L)
>>   				break;
>>   			}
>>   			case LUA_TTABLE: {
>> -				lua_pushvalue(L, -1);
>> -				lua_pushnil(L);
>> -				/* Stack: nil, table */
>> -				while (lua_next(L, -2)) {
>> -					/* Stack: value, key, table */
>> -					lua_pushvalue(L, -2);
>> -					/* Stack: key, value, key, table */
>> -					switch(lua_type(L, -2)) {
>> -						case LUA_TSTRING:
>> -						case LUA_TNUMBER:
>> -							TRACE("(%d) [table ] %s = %s", i,
>> -								lua_tostring(L, -1),
>> -								lua_tostring(L, -2));
>> -							break;
>> -						case LUA_TFUNCTION:
>> -							TRACE("(%d) [table ] %s()", i,
>> -								lua_tostring(L, -1));
>> -							break;
>> -						case LUA_TTABLE:
>> -							TRACE("(%d) [table ] %s <table>", i,
>> -								lua_tostring(L, -1));
>> -							break;
>> -						case LUA_TBOOLEAN:
>> -							TRACE("(%d) [table ] %s = %s", i,
>> -								lua_tostring(L, -1),
>> -								(lua_toboolean(L, -2) ? "true" : "false"));
>> -							break;
>> -						default:
>> -							TRACE("(%d) [table ] %s = <unparsed type>", i,
>> -								lua_tostring(L, -1));
>> -					}
>> -					lua_pop(L, 2);
>> -					/* Stack: key, table */
>> +				if (asprintf(&s, "(%d) [table ]", i) != -1) {
> Well, there's include/util.h:30:#define ENOMEM_ASPRINTF	-1 now, you
> may use that, for consistency. Same applies above.

Okay.

>> +					lua_pushvalue(L, -1);
>> +					lua_dump_table(L, s);
>> +					lua_pop(L, 1);
>> +					free(s);
>>   				}
>> -				/* Stack: table */
>> -				lua_pop(L, 1);
>> -				/* Stack: <empty> */
>>   				break;
>>   			}
>>   			default: {
>> -- 
>> 2.7.4
>>

Best regards,
   Stefan

Patch

diff --git a/corelib/lua_interface.c b/corelib/lua_interface.c
index b1a3a92..872cb2f 100644
--- a/corelib/lua_interface.c
+++ b/corelib/lua_interface.c
@@ -74,8 +74,54 @@  static bool is_type(lua_State *L, uintptr_t type)
 }
 #endif
 
+static void lua_dump_table(lua_State *L, char *str)
+{
+	char *s;
+
+	/* Stack: table, ... */
+	lua_pushnil(L);
+	/* Stack: nil, table, ... */
+	while (lua_next(L, -2)) {
+		/* Stack: value, key, table, ... */
+		lua_pushvalue(L, -2);
+		/* Stack: key, value, key, table, ... */
+		switch(lua_type(L, -2)) {
+			case LUA_TSTRING:
+			case LUA_TNUMBER:
+				TRACE("%s %s = %s", str,
+					lua_tostring(L, -1),
+					lua_tostring(L, -2));
+				break;
+			case LUA_TFUNCTION:
+				TRACE("%s %s()", str,
+					lua_tostring(L, -1));
+				break;
+			case LUA_TTABLE:
+				if (asprintf(&s, "%s %s:", str, lua_tostring(L, -1)) != -1) {
+					lua_pushvalue(L, -2);
+					lua_dump_table(L, s);
+					lua_pop(L, 1);
+					free(s);
+				}
+				break;
+			case LUA_TBOOLEAN:
+				TRACE("%s %s = %s", str,
+					lua_tostring(L, -1),
+					(lua_toboolean(L, -2) ? "true" : "false"));
+				break;
+			default:
+				TRACE("%s %s = <unparsed type>", str,
+					lua_tostring(L, -1));
+		}
+		lua_pop(L, 2);
+		/* Stack: key, table, ... */
+	}
+	/* Stack: table, ... */
+}
+
 void LUAstackDump(lua_State *L)
 {
+	char *s;
 	int top = lua_gettop(L);
 	for (int i = 1; i <= top; i++) {
 		int t = lua_type(L, i);
@@ -97,43 +143,12 @@  void LUAstackDump(lua_State *L)
 				break;
 			}
 			case LUA_TTABLE: {
-				lua_pushvalue(L, -1);
-				lua_pushnil(L);
-				/* Stack: nil, table */
-				while (lua_next(L, -2)) {
-					/* Stack: value, key, table */
-					lua_pushvalue(L, -2);
-					/* Stack: key, value, key, table */
-					switch(lua_type(L, -2)) {
-						case LUA_TSTRING:
-						case LUA_TNUMBER:
-							TRACE("(%d) [table ] %s = %s", i,
-								lua_tostring(L, -1),
-								lua_tostring(L, -2));
-							break;
-						case LUA_TFUNCTION:
-							TRACE("(%d) [table ] %s()", i,
-								lua_tostring(L, -1));
-							break;
-						case LUA_TTABLE:
-							TRACE("(%d) [table ] %s <table>", i,
-								lua_tostring(L, -1));
-							break;
-						case LUA_TBOOLEAN:
-							TRACE("(%d) [table ] %s = %s", i,
-								lua_tostring(L, -1),
-								(lua_toboolean(L, -2) ? "true" : "false"));
-							break;
-						default:
-							TRACE("(%d) [table ] %s = <unparsed type>", i,
-								lua_tostring(L, -1));
-					}
-					lua_pop(L, 2);
-					/* Stack: key, table */
+				if (asprintf(&s, "(%d) [table ]", i) != -1) {
+					lua_pushvalue(L, -1);
+					lua_dump_table(L, s);
+					lua_pop(L, 1);
+					free(s);
 				}
-				/* Stack: table */
-				lua_pop(L, 1);
-				/* Stack: <empty> */
 				break;
 			}
 			default: {