Qt: Reload Lua FileHandler when having a capture file

Support reloading a Lua FileHandler when this is in use for a
loaded capture file. Prompt to save the file if having unsaved
changes because the file must be reloaded.

Fixes #17615
This commit is contained in:
Stig Bjørlykke 2021-09-27 13:10:43 +02:00
parent a3c2ad04ee
commit 96cfaf67a3
6 changed files with 53 additions and 2 deletions

View File

@ -180,4 +180,5 @@ libwiretap.so.0 libwiretap0 #MINVER#
wtap_snapshot_length@Base 1.9.1
wtap_strerror@Base 1.9.1
wtap_tsprec_string@Base 1.99.9
wtap_uses_lua_filehandler@Base 3.5.1
wtap_write_shb_comment@Base 1.9.1

View File

@ -296,6 +296,7 @@ struct _wslua_filehandler {
int write_close_ref;
int file_type;
gboolean registered;
gboolean removed; /* This is set during reload Lua plugins */
};
struct _wslua_dir {

View File

@ -75,6 +75,9 @@ report_error(int *err, gchar **err_info, const char *fmt, ...)
report_error(err, err_info, "Error in file %s: no Lua FileHandler object", #name); \
return retval; \
} \
if (fh->removed) { \
return retval; \
} \
if (!fh->registered) { \
report_error(err, err_info, "Error in file %s: Lua FileHandler is not registered", #name); \
return retval; \
@ -310,6 +313,11 @@ wslua_filehandler_seek_read(wtap *wth, gint64 seek_off,
CaptureInfo *fc = NULL;
FrameInfo *fi = NULL;
if (fh->removed) {
/* Return success when removed during reloading Lua plugins */
return TRUE;
}
INIT_FILEHANDLER_ROUTINE(seek_read,FALSE,err,err_info);
/* Reset errno */
@ -1285,7 +1293,9 @@ int FileHandler_register(lua_State* L) {
int wslua_deregister_filehandlers(lua_State* L _U_) {
for (GSList *it = registered_file_handlers; it; it = it->next) {
wslua_deregister_filehandler_work((FileHandler)it->data);
FileHandler fh = (FileHandler)it->data;
wslua_deregister_filehandler_work(fh);
fh->removed = TRUE;
}
g_slist_free(registered_file_handlers);
registered_file_handlers = NULL;

View File

@ -1529,6 +1529,22 @@ void MainWindow::reloadLuaPlugins()
if (wsApp->isReloadingLua())
return;
gboolean uses_lua_filehandler = FALSE;
if (capture_file_.capFile()) {
// Check if the current capture file is opened with a Lua FileHandler
capture_file *cf = capture_file_.capFile();
uses_lua_filehandler = wtap_uses_lua_filehandler(cf->provider.wth);
if (uses_lua_filehandler && cf->unsaved_changes) {
// Prompt to save the file before reloading, in case the FileHandler has changed
QString before_what(tr(" before reloading Lua plugins"));
if (!testCaptureFileClose(before_what, Reload)) {
return;
}
}
}
wsApp->setReloadingLua(true);
wslua_reload_plugins(NULL, NULL);
@ -1544,7 +1560,14 @@ void MainWindow::reloadLuaPlugins()
prefs_apply_all();
fieldsChanged();
redissectPackets();
if (uses_lua_filehandler) {
// Reload the file in case the FileHandler has changed
cf_reload(capture_file_.capFile());
proto_free_deregistered_fields();
} else {
redissectPackets();
}
wsApp->setReloadingLua(false);
SimpleDialog::displayQueuedMessages();

View File

@ -591,6 +591,20 @@ wtap_has_open_info(const gchar *name)
return FALSE;
}
gboolean
wtap_uses_lua_filehandler(const wtap* wth)
{
if (wth && wth->wslua_data != NULL) {
/*
* Currently, wslua_data is set if and only if using a Lua
* file handler.
*/
return TRUE;
}
return FALSE;
}
/*
* Visual C++ on Win32 systems doesn't define these. (Old UNIX systems don't
* define them either.)

View File

@ -2236,6 +2236,8 @@ void wtap_register_open_info(struct open_info *oi, const gboolean first_routine)
WS_DLL_PUBLIC
gboolean wtap_has_open_info(const gchar *name);
WS_DLL_PUBLIC
gboolean wtap_uses_lua_filehandler(const wtap* wth);
WS_DLL_PUBLIC
void wtap_deregister_open_info(const gchar *name);
WS_DLL_PUBLIC