diff options
| -rw-r--r-- | degesch.c | 64 | 
1 files changed, 44 insertions, 20 deletions
| @@ -1252,17 +1252,13 @@ enum ispect_type  	ISPECT_STR,                         ///< "struct str"  	ISPECT_STR_MAP,                     ///< "struct str_map"  	ISPECT_REF,                         ///< Weakly referenced object -#if 0 -	// XXX: maybe just a PTR type that doesn't warrant weak_refs but is copied, -	//   LIST-ness seems to be more of a direct flag of a type -	ISPECT_LIST,                        ///< Typically copied, depending on type -#endif + +	// XXX: maybe a PTR type that doesn't warrant weak_refs but is copied  };  // TODO: once this finalizes, turn instatiations into macros  struct ispect  { -	// TODO: "list" flag?  	struct ispect_field *fields;        ///< Fields  }; @@ -1271,13 +1267,14 @@ struct ispect_field  	const char *name;                   ///< Name of the field  	size_t offset;                      ///< Offset in the structure  	enum ispect_type type;              ///< Type of the field +	bool is_list;                       ///< This object is a list  	struct ispect *subtype;             ///< Subtype information  };  #define ISPECT(object, field, type)                                            \ -	{ #field, offsetof (struct object, field), ISPECT_ ## type, NULL }, -#define ISPECT_(object, field, type, subtype)                                  \ -	{ #field, offsetof (struct object, field), ISPECT_ ## type,                \ +	{ #field, offsetof (struct object, field), ISPECT_ ## type, false, NULL }, +#define ISPECT_(object, field, type, is_list, subtype)                         \ +	{ #field, offsetof (struct object, field), ISPECT_ ## type, is_list,       \  	  &g_ ## subtype ## _ispect },  // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -1595,9 +1592,9 @@ static struct ispect_field g_buffer_ispect_fields[] =  	ISPECT ( buffer, new_unimportant_count, UINT   )  	ISPECT ( buffer, highlighted,           BOOL   )  	ISPECT ( buffer, hide_unimportant,      BOOL   ) -	ISPECT_( buffer, server,                REF,   server  ) -	ISPECT_( buffer, channel,               REF,   channel ) -	ISPECT_( buffer, user,                  REF,   user    ) +	ISPECT_( buffer, server,                REF, false, server  ) +	ISPECT_( buffer, channel,               REF, false, channel ) +	ISPECT_( buffer, user,                  REF, false, user    )  	{}  }; @@ -1763,11 +1760,13 @@ static struct ispect_field g_server_ispect_fields[] =  	ISPECT ( server, irc_user_host,     STRING )  	ISPECT ( server, autoaway_active,   BOOL   )  	ISPECT ( server, cap_echo_message,  BOOL   ) -	ISPECT_( server, buffer,            REF,   buffer ) +	ISPECT_( server, buffer,            REF, false, buffer )  	// TODO: either rename the underlying field or fix the plugins -	{ "user", offsetof (struct server, irc_user), ISPECT_REF, &g_user_ispect }, -	{ "user_mode", offsetof (struct server, irc_user_mode), ISPECT_STR, NULL }, +	{ "user",      offsetof (struct server, irc_user), +	  ISPECT_REF, false, &g_user_ispect }, +	{ "user_mode", offsetof (struct server, irc_user_mode), +	  ISPECT_STR, false, NULL },  	{}  }; @@ -2112,8 +2111,9 @@ struct app_context  static struct ispect_field g_ctx_ispect_fields[] =  { -	ISPECT_( app_context, global_buffer,  REF, buffer ) -	ISPECT_( app_context, current_buffer, REF, buffer ) +	ISPECT_( app_context, buffers,        REF, true,  buffer ) +	ISPECT_( app_context, global_buffer,  REF, false, buffer ) +	ISPECT_( app_context, current_buffer, REF, false, buffer )  	{}  }; @@ -9817,6 +9817,31 @@ lua_plugin_panic (lua_State *L)  	return 0;  } +struct list_header +{ +	void *next;                         ///< Next item +	void *prev;                         ///< Previous item +}; + +static void +lua_plugin_push_ref (struct lua_plugin *self, void *object, bool is_list, +	struct lua_weak_info *info) +{ +	if (!is_list) +	{ +		lua_weak_push (self, object, info); +		return; +	} + +	int i = 1; +	lua_newtable (self->L); +	LIST_FOR_EACH (struct list_header, iter, object) +	{ +		lua_weak_push (self, iter, info); +		lua_rawseti (self->L, -2, i++); +	} +} +  static bool  lua_plugin_property_get_ispect (lua_State *L, const char *property_name)  { @@ -9863,12 +9888,11 @@ lua_plugin_property_get_ispect (lua_State *L, const char *property_name)  	{  		// TODO: we can definitely make a resolution table right in Lua,  		//   lua_plugin_reg_weak() can fill it automatically (lightud->lightud) -		struct lua_weak_info *info = NULL;  		for (size_t i = 0; i < N_ELEMENTS (lua_types); i++)  			if (lua_types[i].ispect == iter->subtype)  			{ -				info = lua_types[i].info; -				lua_weak_push (weak->plugin, *(void **) p, info); +				lua_plugin_push_ref (weak->plugin, *(void **) p, +					iter->is_list, lua_types[i].info);  				return true;  			}  	} | 
