Skip to content

Commit

Permalink
Qt: Reload Lua expert infos
Browse files Browse the repository at this point in the history
Support reloading Lua plugins with expert infos.
Use the same delayed deregister logic as for fields.

Change-Id: I36efa0820050b3a7afed4de7a8b0fa16805e8dfa
Reviewed-on: https://code.wireshark.org/review/12498
Petri-Dish: Stig Bjørlykke <[email protected]>
Tested-by: Petri Dish Buildbot <[email protected]>
Reviewed-by: Anders Broman <[email protected]>
  • Loading branch information
stigbjorlykke authored and AndersBroman committed Dec 11, 2015
1 parent 9c47cb4 commit ea1789f
Show file tree
Hide file tree
Showing 5 changed files with 55 additions and 5 deletions.
40 changes: 38 additions & 2 deletions epan/expert.c
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,9 @@ static gpa_expertinfo_t gpa_expertinfo;
/* Hash table of abbreviations and IDs */
static GHashTable *gpa_name_map = NULL;

/* Deregistered expert infos */
static GPtrArray *deregistered_expertinfos = NULL;

const value_string expert_group_vals[] = {
{ PI_CHECKSUM, "Checksum" },
{ PI_SEQUENCE, "Sequence" },
Expand Down Expand Up @@ -187,6 +190,7 @@ static void uat_expert_post_update_cb(void)
if((guint)eiindex >= gpa_expertinfo.len && getenv("WIRESHARK_ABORT_ON_DISSECTOR_BUG")) \
g_error("Unregistered expert info! index=%d", eiindex); \
DISSECTOR_ASSERT_HINT((guint)eiindex < gpa_expertinfo.len, "Unregistered expert info!"); \
DISSECTOR_ASSERT_HINT(gpa_expertinfo.ei[eiindex] != NULL, "Unregistered expert info!"); \
expinfo = gpa_expertinfo.ei[eiindex];

void
Expand Down Expand Up @@ -265,6 +269,7 @@ expert_init(void)
gpa_expertinfo.ei = NULL;
gpa_name_map = g_hash_table_new_full(g_str_hash, g_str_equal, NULL, NULL);
uat_saved_fields = g_array_new(FALSE, FALSE, sizeof(expert_field_info*));
deregistered_expertinfos = g_ptr_array_new();
}

void
Expand Down Expand Up @@ -293,6 +298,11 @@ expert_cleanup(void)
g_array_free(uat_saved_fields, TRUE);
uat_saved_fields = NULL;
}

if (deregistered_expertinfos) {
g_ptr_array_free(deregistered_expertinfos, FALSE);
deregistered_expertinfos = NULL;
}
}


Expand Down Expand Up @@ -323,9 +333,35 @@ expert_module_t *expert_register_protocol(int id)
return module;
}

void expert_deregister_protocol (expert_module_t *module)
void
expert_deregister_expertinfo (const char *abbrev)
{
expert_field_info *expinfo = (expert_field_info*)g_hash_table_lookup(gpa_name_map, abbrev);
if (expinfo) {
g_ptr_array_add(deregistered_expertinfos, gpa_expertinfo.ei[expinfo->id]);
g_hash_table_steal(gpa_name_map, abbrev);
}
}

void
expert_deregister_protocol (expert_module_t *module)
{
wmem_free(wmem_epan_scope(), module);
}

static void
free_deregistered_expertinfo (gpointer data, gpointer user_data _U_)
{
expert_field_info *expinfo = (expert_field_info *) data;
gpa_expertinfo.ei[expinfo->id] = NULL; /* Invalidate this id */
}

void
expert_free_deregistered_expertinfos (void)
{
wmem_free(wmem_epan_scope(), module);
g_ptr_array_foreach(deregistered_expertinfos, free_deregistered_expertinfo, NULL);
g_ptr_array_free(deregistered_expertinfos, TRUE);
deregistered_expertinfos = g_ptr_array_new();
}

static int
Expand Down
10 changes: 10 additions & 0 deletions epan/expert.h
Original file line number Diff line number Diff line change
Expand Up @@ -171,11 +171,21 @@ proto_tree_add_expert_format(proto_tree *tree, packet_info *pinfo, expert_field
*/
WS_DLL_PUBLIC expert_module_t *expert_register_protocol(int id);

/**
* Deregister a expert info.
*/
void expert_deregister_expertinfo (const char *abbrev);

/**
* Deregister expert info from a protocol.
*/
WS_DLL_PUBLIC void expert_deregister_protocol (expert_module_t *module);

/**
* Free deregistered expert infos.
*/
void expert_free_deregistered_expertinfos (void);

/**
* Get summary text of an expert_info field.
* This is intended for use in expert_add_info_format or proto_tree_add_expert_format
Expand Down
3 changes: 3 additions & 0 deletions epan/proto.c
Original file line number Diff line number Diff line change
Expand Up @@ -5400,6 +5400,7 @@ proto_deregister_protocol(const char *short_name)
for (i = 0; i < protocol->fields->len; i++) {
hfinfo = (header_field_info *)g_ptr_array_index(protocol->fields, i);
hfinfo_remove_from_gpa_name_map(hfinfo);
expert_deregister_expertinfo(hfinfo->abbrev);
g_ptr_array_add(deregistered_fields, gpa_hfinfo.hfi[hfinfo->id]);
}
g_ptr_array_free(protocol->fields, TRUE);
Expand Down Expand Up @@ -5919,6 +5920,8 @@ free_deregistered_data (gpointer data, gpointer user_data _U_)
void
proto_free_deregistered_fields (void)
{
expert_free_deregistered_expertinfos();

g_ptr_array_foreach(deregistered_fields, free_deregistered_field, NULL);
g_ptr_array_free(deregistered_fields, TRUE);
deregistered_fields = g_ptr_array_new();
Expand Down
3 changes: 3 additions & 0 deletions epan/wslua/wslua_proto.c
Original file line number Diff line number Diff line change
Expand Up @@ -715,6 +715,9 @@ int Proto_commit(lua_State* L) {
eiri.eiinfo.severity = e->severity;
eiri.eiinfo.summary = e->text;

/* Copy this because it will be free'd when deregistering fields */
eiri.eiinfo.hf_info.hfinfo.name = g_strdup(eiri.eiinfo.hf_info.hfinfo.name);

if (e->ids.ei != EI_INIT_EI || e->ids.hf != EI_INIT_HF) {
return luaL_error(L,"expert fields can be registered only once");
}
Expand Down
4 changes: 1 addition & 3 deletions epan/wslua/wslua_proto_expert.c
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ WSLUA_CONSTRUCTOR ProtoExpert_new(lua_State* L) {

pe->ids.ei = EI_INIT_EI;
pe->ids.hf = EI_INIT_HF;
pe->abbrev = g_strdup(abbr);
pe->abbrev = g_strdup(abbr);
pe->text = g_strdup(text);
pe->group = group;
pe->severity = severity;
Expand Down Expand Up @@ -101,8 +101,6 @@ static int ProtoExpert__gc(lua_State* L) {

if (pe->ids.hf == -2) {
/* Only free unregistered and deregistered ProtoExpert */
g_free((gchar *)pe->abbrev);
g_free((gchar *)pe->text);
g_free(pe);
}

Expand Down

0 comments on commit ea1789f

Please sign in to comment.