From e9d5f13344d1f49763b87fdf2368b0b909ecfd1a Mon Sep 17 00:00:00 2001 From: Carsten Haitzler Date: Thu, 26 Apr 2001 20:41:23 +0000 Subject: [PATCH] handle if efsd goes away and restart it... also have abackoff timeout to try restarting efsd... :) SVN revision: 4673 --- src/e.h | 11 ++++++ src/fs.c | 102 ++++++++++++++++++++++++++++++++++++++++++++++++---- src/icons.c | 4 +-- src/view.c | 76 ++++++++++++++++++++++++++++++++------- 4 files changed, 171 insertions(+), 22 deletions(-) diff --git a/src/e.h b/src/e.h index d00621c86..92fa2a7df 100644 --- a/src/e.h +++ b/src/e.h @@ -146,6 +146,7 @@ typedef struct _E_Build_Menu E_Build_Menu; typedef struct _E_Entry E_Entry; typedef struct _E_Pack_Object_Class E_Pack_Object_Class; typedef struct _E_Pack_Object E_Pack_Object; +typedef struct _E_FS_Restarter E_FS_Restarter; struct _E_Object { @@ -376,6 +377,8 @@ struct _E_View int is_listing; int monitor_id; + E_FS_Restarter *restarter; + Evas_List icons; Evas_List shelves; @@ -654,6 +657,12 @@ struct _E_Pack_Object Evas_List children; }; +struct _E_FS_Restarter +{ + void (*func) (void *data); + void *data; +}; + #define DO(_object, _method, _args...) \ { if (_object->class._method) _object->class._method(_object->data.object, ## _args); } @@ -975,6 +984,8 @@ void e_build_menu_free(E_Build_Menu *bm); E_Build_Menu *e_build_menu_new_from_db(char *file); E_Build_Menu *e_build_menu_new_from_gnome_apps(char *dir); +E_FS_Restarter *e_fs_add_restart_handler(void (*func) (void *data), void *data); +void e_fs_del_restart_handler(E_FS_Restarter *rs); void e_fs_add_event_handler(void (*func) (EfsdEvent *ev)); void e_fs_init(void); EfsdConnection *e_fs_get_connection(void); diff --git a/src/fs.c b/src/fs.c index 70846b3c6..1bf4b1a86 100644 --- a/src/fs.c +++ b/src/fs.c @@ -2,8 +2,29 @@ static EfsdConnection *ec = NULL; static Evas_List fs_handlers = NULL; +static Evas_List fs_restart_handlers = NULL; +static pid_t efsd_pid = 0; +static void e_fs_child_handle(Eevent *ev); static void _e_fs_fd_handle(int fd); +static void _e_fs_restarter(int val, void *data); + +static void +e_fs_child_handle(Eevent *ev) +{ + Ev_Child *e; + + e = ev->event; + printf("child exit code %i pid %i, efsd pid = %i\n", e->exit_code, e->pid, efsd_pid); + if (e->pid == efsd_pid) + { + efsd_close(ec); + efsd_pid = 0; + ec = NULL; + printf("efsd exited.\n"); + _e_fs_restarter(0, NULL); + } +} static void _e_fs_fd_handle(int fd) @@ -34,9 +55,13 @@ _e_fs_fd_handle(int fd) efsd_close(ec); e_del_event_fd(fd); ec = NULL; + if (efsd_pid == -2) + _e_fs_restarter(0, NULL); +/* efsd_pid = 0;*/ /* FIXME: need to queue a popup dialog here saying */ /* efsd went wonky */ printf("EEEEEEEEEEK efsd went wonky\n"); +/* _e_fs_restarter(0, NULL);*/ } /* spent more thna 1/20th of a second here.. get out */ @@ -50,6 +75,63 @@ _e_fs_fd_handle(int fd) /* printf("############## fs done\n"); */ } +static void +_e_fs_restarter(int val, void *data) +{ + if (ec) return; + printf("%i\n", efsd_pid); + if (val > 0) + { + if (efsd_pid <= 0) + efsd_pid = e_exec_run("efsd -f"); + if (efsd_pid > 0) + ec = efsd_open(); + } + if (ec) + { + Evas_List l; + + printf("connect!\n"); + for (l = fs_restart_handlers; l; l = l->next) + { + E_FS_Restarter *rs; + + rs = l->data; + rs->func(rs->data); + } + } + else + { + double gap; + + gap = (double)val / 10; + if (gap > 10.0) gap = 10.0; + e_add_event_timer("e_fs_restarter", gap, _e_fs_restarter, val + 1, NULL); + } +} + +E_FS_Restarter * +e_fs_add_restart_handler(void (*func) (void *data), void *data) +{ + E_FS_Restarter *rs; + + rs = NEW(E_FS_Restarter, 1); + ZERO(rs, E_FS_Restarter, 1); + rs->func = func; + rs->data = data; + fs_restart_handlers = evas_list_append(fs_restart_handlers, rs); +} + +void +e_fs_del_restart_handler(E_FS_Restarter *rs) +{ + if (evas_list_find(fs_restart_handlers, rs)) + { + fs_restart_handlers = evas_list_remove(fs_restart_handlers, rs); + FREE(rs); + } +} + void e_fs_add_event_handler(void (*func) (EfsdEvent *ev)) { @@ -62,26 +144,32 @@ e_fs_init(void) { int i; + e_event_filter_handler_add(EV_CHILD, e_fs_child_handle); /* already have an efsd around? */ ec = efsd_open(); /* no - efsd around */ if (!ec) { /* start efsd */ - e_exec_run("efsd"); - for (i = 0; (!ec) && (i < 4); i++) + efsd_pid = e_exec_run("efsd -f"); + if (efsd_pid > 0) { - sleep(1); - ec = efsd_open(); + for (i = 0; (!ec) && (i < 4); i++) + { + sleep(1); + ec = efsd_open(); + } } } + else + efsd_pid = -2; /* after several atempts to talk to efsd - lets give up */ if (!ec) { - fprintf(stderr, "efsd is not running - please run efsd.\n"); - exit(-1); + fprintf(stderr, "efsd is not running !!!\n"); } - e_add_event_fd(efsd_get_connection_fd(ec), _e_fs_fd_handle); + if (ec) + e_add_event_fd(efsd_get_connection_fd(ec), _e_fs_fd_handle); } EfsdConnection * diff --git a/src/icons.c b/src/icons.c index 89cef5b28..e747079bd 100644 --- a/src/icons.c +++ b/src/icons.c @@ -134,7 +134,7 @@ e_icon_get_icon(E_Icon *icon) if (!found) { strcpy(m2, icon->info.mime.type); - p = strrchr(m2, '-'); + p = strrchr(m2, '/'); while (p) { p[0] = 0; @@ -145,7 +145,7 @@ e_icon_get_icon(E_Icon *icon) found = 1; break; } - p = strrchr(m2, '-'); + p = strrchr(m2, '/'); } } if (!found) diff --git a/src/view.c b/src/view.c index c133d2eda..74a76123d 100644 --- a/src/view.c +++ b/src/view.c @@ -16,6 +16,7 @@ static void e_mouse_in(Eevent * ev); static void e_mouse_out(Eevent * ev); static void e_window_expose(Eevent * ev); static void e_view_handle_fs(EfsdEvent *ev); +static void e_view_handle_fs_restart(void *data); /* FIXME: hack to test entry boxes */ static E_Entry *entry = NULL; @@ -359,6 +360,41 @@ e_window_expose(Eevent * ev) } } +static void +e_view_handle_fs_restart(void *data) +{ + E_View *v; + Evas_List icons = NULL, l; + + v = data; + + printf("e_view_handle_fs_restart\n"); + for (l = v->icons; l; l = l->next) + { + icons = evas_list_prepend(icons, l->data); + } + if (icons) + { + for (l = icons; l; l = l->next) + { + E_Icon *i; + + i = l->data; + e_view_file_deleted(v->monitor_id, i->file); + } + evas_list_free(icons); + } + if (e_fs_get_connection()) + v->monitor_id = efsd_start_monitor(e_fs_get_connection(), v->dir, + efsd_ops(2, + efsd_op_get_stat(), + efsd_op_get_filetype() + ) + ); + printf("restarted monior id (connection = %p), %i for %s\n", e_fs_get_connection(), v->monitor_id, v->dir); + v->is_listing = 1; +} + Eevent * e_view_get_current_event(void) { @@ -452,6 +488,7 @@ e_view_file_deleted(int id, char *file) v = e_view_find_by_monitor_id(id); if (!v) return; icon = e_view_find_icon_by_file(v, file); + printf("%p %s\n", icon, file); if (icon) { e_view_del_icon(v, icon); @@ -542,9 +579,15 @@ e_view_handle_fs(EfsdEvent *ev) ev->efsd_filechange_event.file); */ break; case EFSD_CHANGE_END_EXISTS: - printf("EFSD_CHANGE_END_EXISTS: %i %s\n", - ev->efsd_filechange_event.id, - ev->efsd_filechange_event.file); + { + E_View *v; + + v = e_view_find_by_monitor_id(ev->efsd_filechange_event.id); + if (v) v->is_listing = 0; + printf("EFSD_CHANGE_END_EXISTS: %i %s\n", + ev->efsd_filechange_event.id, + ev->efsd_filechange_event.file); + } break; default: break; @@ -702,6 +745,9 @@ void e_view_free(E_View *v) { views = evas_list_remove(views, v); + if (v->restarter) + e_fs_del_restart_handler(v->restarter); + v->restarter = NULL; FREE(v); } @@ -786,15 +832,18 @@ e_view_set_dir(E_View *v, char *dir) v->dir = e_file_real(dir); /* start monitoring new dir */ - /* v->monitor_id = efsd_start_monitor(e_fs_get_connection(), v->dir); */ - v->monitor_id = efsd_start_monitor(e_fs_get_connection(), v->dir, - efsd_ops(2, - efsd_op_get_stat(), - efsd_op_get_filetype() - ) - ); - v->is_listing = 1; - v->changed = 1; + v->restarter = e_fs_add_restart_handler(e_view_handle_fs_restart, v); + if (e_fs_get_connection()) + { + v->monitor_id = efsd_start_monitor(e_fs_get_connection(), v->dir, + efsd_ops(2, + efsd_op_get_stat(), + efsd_op_get_filetype() + ) + ); + v->is_listing = 1; + v->changed = 1; + } } void @@ -920,6 +969,7 @@ e_view_realize(E_View *v) } /* FIXME: hack to test entry boxes */ +/* { entry = e_entry_new(); e_entry_set_evas(entry, v->evas); @@ -936,7 +986,7 @@ e_view_realize(E_View *v) e_entry_resize(entry, ew, eh); } } - +*/ v->changed = 1; }